jerem ef6bf9813a API HelloFresh réelle câblée + filtrage coco validé en local
- Endpoints découverts: menu (menus-service) + détails batch (recipes/recipes)
- get_menu en 2 temps: menu (ids) -> batch détails (ingrédients/allergènes)
- Fix faux positifs: exclusion sur ingrédients/allergènes/nom, plus sur les tags
  (HelloFresh pose un tag interne 'coconut' sur ~la moitié des recettes)
- Token mis en cache (pas de navigateur si frais)
- endpoints.json versionné (sans secret), semaine optionnelle (défaut = courante)
- Testé: 4 recettes coco/85 détectées, shortlist classée, tous les outils MCP OK
- set_selection (écriture) reste à découvrir sur un compte avec box active
2026-06-15 22:28:40 +02:00

AntiCoco 🥥🚫

Serveur MCP qui donne accès à ton compte HelloFresh (France, hellofresh.fr) pour : lire le menu de la semaine, exclure des ingrédients (la noix de coco en priorité), proposer une shortlist de recettes, puis enregistrer ta sélection après confirmation.

Client MCP visé : Hermes (Nous Research), qui tourne sur le même homelab.

⚠️ HelloFresh n'a pas d'API publique. AntiCoco s'appuie sur l'API interne gw/ du site (non documentée, susceptible de changer) — usage strictement personnel.

État (testé en local, 2026-06)

Lecture validée sur le menu réel : login Playwright + token, menu de la semaine (menus-service/menus) → détails en 1 appel batch (recipes/recipes?ids=…), filtrage coco correct (4 recettes coco détectées sur 85, faux positifs des tags internes neutralisés), scoring par préférences, gestion de la liste d'exclusion. Serveur MCP fonctionnel (handshake OK).

Écriture (hf_confirm_selection) à finaliser : l'endpoint d'enregistrement de la sélection (set_selection) n'a pas pu être capturé (compte de test sans abonnement actif). À découvrir via discover_api.py sur un compte avec une box modifiable (changer une recette pour observer l'appel PUT/POST), puis renseigner config/endpoints.json.

Architecture

Hermes ──HTTP──▶ server.py (FastMCP, :9200/mcp)
                   ├─ hellofresh/auth.py    login Playwright + capture du bearer token
                   ├─ hellofresh/api.py     appels httpx vers le gateway HelloFresh
                   ├─ hellofresh/filter.py  exclusion (coco !) + scoring préférences
                   └─ config/               excludes.json · prefs.json · endpoints.json

Mise en route

1. Installer

pip install -r requirements.txt
playwright install chromium
cp .env.example .env   # remplir HF_EMAIL / HF_PASSWORD (optionnels, fallback re-login)

2. Découvrir les endpoints (étape 0, en local, fenêtre visible)

ANTICOCO_HEADLESS=0 python tools/discover_api.py

Connecte-toi, ouvre le menu de la semaine, change une recette pour capturer l'écriture, puis Entrée. Vérifie/complète ensuite config/endpoints.json (généré depuis le trafic capturé, voir aussi .session/discovery_log.json).

3. Tester en local

ANTICOCO_HEADLESS=0 python server.py      # 1er run : login dans la fenêtre si besoin

Le login crée .session/profile (profil Playwright persistant) — réutilisé ensuite headless.

Déploiement homelab (Docker)

.session/ et .env ne sont jamais versionnés. Workflow :

# 1. Sur le Mac : générer une session connectée (fenêtre visible)
ANTICOCO_HEADLESS=0 python server.py      # se connecter, puis Ctrl-C

# 2. Pousser le code
git add -A && git commit -m "..." && git push

# 3. Synchroniser la session vers le homelab (NON versionnée ; endpoints.json est dans git)
scp -r .session jerem@192.168.0.43:<path>/AntiCoco/

# 4. Sur le homelab : déployer
ssh homelab
cd <path>/AntiCoco && git pull && docker compose up -d --build

Vérifier : curl -s http://127.0.0.1:9200/mcp (le serveur répond au handshake MCP).

Intégration Hermes

Enregistrer AntiCoco dans la config MCP de Hermes (côté homelab), URL http://127.0.0.1:9200/mcp (transport streamable-http).

Si Hermes n'accepte que le stdio, changer la dernière ligne de server.py (mcp.run(transport="stdio")) et lancer le serveur en sous-processus — le reste est identique.

Outils MCP exposés

Outil Rôle
hf_auth_status() état de connexion
hf_login() (re)connexion + capture token
hf_list_weeks() semaines modifiables
hf_get_menu(week) toutes les recettes, avec flag contains_excluded
hf_propose(week, count=0) shortlist sans coco, classée par préférences
hf_confirm_selection(week, recipe_ids) écrit la sélection (refuse la coco)
hf_get_excludes() / hf_add_exclude(term) / hf_remove_exclude(term) gérer la liste d'exclusion

Configuration

  • config/excludes.json — ingrédients bannis (matching insensible casse/accents). Coco déjà listée.
  • config/prefs.json — mots-clés liked/disliked pour classer les propositions.
  • config/endpoints.json — URLs gateway réelles (généré par discover_api.py, non versionné).
Description
No description provided
Readme 183 KiB
Languages
Python 99.5%
Dockerfile 0.5%