9 commits
| Author | SHA1 | Message | Date | |
|---|---|---|---|---|
| c4c2c2ae39 |
fix(planning): la grille remplit l'écran, une case ne grandit plus (#110)
All checks were successful
`table.planning-grid` a `height: 100%` mais des hauteurs de ligne pilotées
par le contenu : un créneau avec plusieurs recettes étirait son `<td>`,
donc toute la ligne (les autres cases gagnant la même hauteur morte sous
`vertical-align: top`), puis la table débordait de `.planning-grid-wrapper`
en scroll vertical.
- `tbody tr { height: 1px }` : les cinq lignes se partagent la hauteur du
wrapper à parts égales (une hauteur de ligne est un minimum que le
navigateur étire pour absorber la hauteur restante de la table), au lieu
d'être aussi hautes que la colonne la plus chargée.
- `.meal-cell__recipes` : `max-height: 8.5rem; overflow-y: auto` — au-delà
d'une poignée de recettes la liste scrolle dans la case. Cap en `rem` et
pas en `%` : les hauteurs en pourcentage sur un `<td>` ne se résolvent
pas de façon fiable selon le moteur. `.add-recipe-btn` (frère flex hors
de cette boîte) reste épinglé juste en dessous.
- `min-width: 62rem` laissé tel quel : les 7 colonnes ont besoin d'un
plancher pour rester lisibles, et le scroll horizontal dessous est
couvert par `layout.cy.ts`. Le breakpoint phone (vue `PlanningDayView`)
n'est pas concerné.
Closes #110
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
|
|||
| 642b37ebec |
fix(planning): affiche les recettes du picker sur mobile (#111)
All checks were successful
Sur téléphone, le dialogue d'ajout d'une recette au planning devenait plein écran mais `.recipe-picker-dialog` gardait un `height: 80vh` figé. Dans cette colonne flex de hauteur bornée, le bloc `.recipe-picker__filters` (rendu pour les 4 onglets non-source) consommait toute la place et `.recipes-page__catalog` (`flex: 1`) s'effondrait à ~0 : la table des recettes était dans le DOM mais dans un scrollport de hauteur nulle, donc les onglets Favoris / Perso / Foyer / Publique paraissaient vides. Sous le breakpoint phone : le dialogue passe vraiment plein écran (comme tout autre `Dialog`), `.recipe-picker__filters` ne se laisse plus compresser, et le catalogue prend sa hauteur de contenu — c'est `.dialog-panel__body` qui scrolle. Closes #111 Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> |
|||
| 964269d3f3 |
feat(planning): vue mobile dédiée "un jour à la fois" pour la grille (#88)
Some checks failed
La grille planning (7 colonnes × 5 repas, min-width: 62rem) était le principal écran inaccessible sur téléphone : sous ce seuil elle ne se réorganisait pas, elle scrollait juste horizontalement — un tableau desktop rétréci, pas un vrai écran mobile. Sous le breakpoint phone (useIsMobileViewport()), PlanningPage bascule désormais entièrement sur PlanningDayView : un sélecteur de jour (jour précédent/suivant, borné au lundi/dimanche de la semaine affichée, pas de bouclage vers la semaine adjacente — ça reste le rôle des flèches du WeekNavigator) suivi des 5 repas du jour sélectionné, empilés en cartes. Le contenu de chaque case (pastilles de recettes + bouton "+") est mutualisé entre les deux layouts via une fonction non-hook partagée, mealCellBody, appelée aussi bien par MealCell (<td>, grille desktop) que par le nouveau MealCellRow (<div>, vue jour) — même logique de drop-target @dnd-kit (useDroppable) des deux côtés, donc le glisser- déposer d'un reste continue de fonctionner à l'identique sur mobile. Mise à jour de layout.cy.ts : son test #39 "la grille reste scrollable horizontalement sur phone" décrivait un comportement désormais remplacé par ce ticket — réécrit pour vérifier la bascule vers la vue jour au lieu du scroll horizontal. Closes #88 Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> |
|||
| a3701acae4 |
fix(planning): popovers flottants surs sur mobile
Some checks failed
CI / build-android (push) Blocked by required conditions
CI / lint (push) Successful in 3m18s
CI / intent-service-test (push) Successful in 4m8s
CI / build (push) Successful in 3m42s
CI / test (push) Failing after 10m11s
CI / e2e (push) Has been cancelled
Ticket #87 du chantier UI mobile & tablette. LeftoversBasket et WeekNavigator's CalendarPopover etaient tous les deux des popovers a largeur fixe (18-20rem), ancres right: 0, sans aucune gestion de bord d'ecran - sur un telephone etroit ils pouvaient deborder hors du viewport. Les deux sont declenches depuis l'en-tete du planning, un ecran central de l'usage quotidien - tres probablement la cause concrete derriere le retour terrain "je n'ai pas acces a tous les boutons" sur mobile qui a lance ce chantier. Les deux basculent desormais sur BottomSheet (ticket #91) sous le breakpoint phone via useIsMobileViewport() - meme contenu, juste une autre enveloppe (le popover flottant + son ecouteur de clic exterieur manuel restent inchanges sur desktop). Le clic-exterieur devient un no-op propre sur mobile plutot qu'un ecouteur qui ne fait jamais rien (le ref ne s'attache a rien dans la branche BottomSheet). Nouvelle cle i18n common.calendar.title ("Choisir une semaine") pour le titre de la feuille - pas de raccourci en decoupant une autre cle interpolee. Verifie en local : tsc -b --force, biome check, build de prod, suite Cypress e2e complete (142/142, 2 nouveaux tests phone dans leftovers-basket.cy.ts et planning-page.cy.ts) et composants (63/63). Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> |
|||
| e8ac2d1629 |
feat(cooking): page /cuisiner + bouton "Commencer a cuisiner"
- Bouton "Commencer a cuisiner" dans l'en-tete du planning, actif seulement quand la semaine affichee contient >= 1 recette ; navigue vers /cuisiner?date=<semaine>. - Page CookingSessionPage (/cuisiner) : consomme GET /cooking-session, rend les phases (mise en place / cuisson / dressage), les taches mutualisees avec badge "Mutualise" + ingredients/ustensiles resolus, et la bande "Pendant ce temps" pour les cuissons de fond. Semaine lue depuis ?date=, WeekNavigator en fallback ; recalcul a chaque visite (comme la liste de courses). - Logique pure extraite dans cooking-session.ts (composition des libelles, formatage des quantites). - i18n : bloc cookingSession.* + planning.startCooking. - apiClient.getCookingPlanForWeek. - Tests Cypress : cooking-session-page.cy.ts (layout, 3 cas), cooking-session .feature (parcours planning -> /cuisiner), assertions bouton dans planning-page.cy.ts ; step generique "button should be disabled" mutualise. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> |
|||
|
|
109dde9c7b
|
feat(shopping-list): liste de courses agrégée depuis le planning (#73)
GET /shopping-list?date= (shopping-list.service.ts/.routes.ts) somme les ingrédients de chaque recette planifiée sur la semaine, mis à l'échelle par les portions de chaque créneau (PlanningItem.portions / Recipe.portions), regroupés par paire (ingredientId, unitId) — jamais null contrairement à GET /planning, une semaine vide redescend en items: []. Côté web, ShoppingListPage rend cette liste groupée par rayon (même IngredientCategory que IngredientPicker), triée alphabétiquement en français à l'intérieur d'un rayon (shopping-list.ts, logique pure extraite du composant). WeekNavigator (flèches + calendrier) est extrait de PlanningPage vers features/planning/ pour être partagé entre les deux pages ; ses libellés migrent de planning.* vers common.weekNav.*/ common.calendar.*/common.days.*, plus génériques pour une page qui n'est plus seulement le planning. ComingSoonPage retiré (plus aucun appelant, Liste de courses avait le dernier stub restant). Tests : Mocha (agrégation, mise à l'échelle par portions, unités non fusionnées) + Cucumber (shopping-list.feature : liste vide, groupement/tri, navigation de semaine) + mise à jour de layout.cy.ts/planning-page.cy.ts pour le nouveau rendu. Co-authored-by: Claude Sonnet 5 <noreply@anthropic.com> |
||
| c29648e293 |
fix(ci): corrige lint/tests cassés par la migration portions
- Dialog.tsx : remplace le div role="dialog" par un <dialog> natif (showModal) — corrige lint/a11y/useSemanticElements, récupère gratuitement le piège de focus et l'Échap natifs. Le clic extérieur est rebranché en imperative addEventListener pour éviter lint/a11y/useKeyWithClickEvents sur un élément non interactif. - RecipePickerDialog.tsx : retire l'autoFocus (lint/a11y/noAutofocus), ordre des imports/formatage corrigés par `biome check --write`. - apps/api/test/planning.test.ts, apps/api/test/recipe.test.ts : les fixtures qui créent un `PlanningItem` directement via Prisma n'avaient pas le nouveau champ `portions` requis. - apps/web/cypress/e2e/planning-page.cy.ts : ajoute `portions` aux items mockés pour rester fidèle au contrat `PlanningItemView`. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> |
|||
|
|
f1fefc1f38
|
refactor: sépare les tests Cypress en parcours utilisateur / layout / composants (#25)
* chore: point de départ pour le refactor des tests Cypress
Sépare les tests Cypress en trois catégories, comme discuté :
1. Parcours utilisateur (cypress/e2e/) — scénarios Gherkin/Cucumber,
pilotés par @badeball/cypress-cucumber-preprocessor@22.2.0 (validé
sur experiment/cucumber-cypress, mergée). Ex. "En tant
qu'utilisateur, je peux créer un compte".
2. Layout applicatif (nouveau dossier à définir) — specs Cypress
classiques (pas de Gherkin), cy.visit() sur une vraie page, mais
centrées sur la disposition/visibilité des éléments, indépendamment
d'un parcours utilisateur scripté.
3. Composants génériques (cypress/component/, nouveau) — vrai
Component Testing Cypress, composant React monté isolément (pas de
routeur, pas de backend). Composants concernés aujourd'hui :
components/ui/{Checkbox,Radio,Dialog}.tsx.
Premier pas : mise en place de l'infra Component Testing (config +
devServer Vite + adapter React 18), validée sur un composant simple
avant de construire le reste.
* feat(web): infra Cypress Component Testing, premier test sur CheckboxOption
Étape 1 du refactor (voir PR) : met en place le vrai mode Component
Testing de Cypress, séparé de l'e2e — monte un composant React isolé
(pas de routeur, pas de backend), pour tester les composants
génériques (components/ui/) indépendamment de tout parcours
utilisateur.
- cypress.config.ts : nouveau bloc `component` (devServer Vite, réutilise
vite.config.ts de l'appli — même plugin React, même Sass). Le hook
GPU-disable est factorisé (`disableGpu`) puisque e2e et component ont
chacun leur propre `setupNodeEvents`, pas de config partagée par défaut.
- cypress/support/component.ts + component-index.html : fichiers de
support standards Cypress CT — importe le vrai global.scss de l'appli
(les composants génériques sont stylés via lui, pas de CSS scopé à eux).
- cypress/component/CheckboxOption.cy.tsx : 4 scénarios sur
components/ui/Checkbox.tsx (rendu du label, reflet du prop `checked`
sur l'input natif + la classe `is-selected`, callback `onChange` avec
la valeur inversée, comportement contrôlé via un wrapper avec état).
Dépendance ajoutée, épinglée : @cypress/vite-dev-server@5.2.1 (dernière
version sans peer dependency cypress >=14 — 6.0.3+ l'exige explicitement,
on est sur cypress@13.17.0).
Testé en local jusqu'au mur GPU/Electron habituel (config + devServer
Vite chargent sans erreur) — l'exécution réelle du montage reste à
vérifier via la CI.
* ci: exécute les tests de composants Cypress
Sans ça, `cypress/component/CheckboxOption.cy.tsx` (commit précédent)
ne tournait jamais en CI : `pnpm --filter web e2e` lance `cypress run`
sans `--component`, donc uniquement la suite e2e par défaut.
- apps/web/package.json : nouveau script `cy:run:component`
- ci.yml : étape dédiée après `pnpm --filter web e2e`, sans
start-server-and-test (Cypress lance son propre dev server Vite en
interne pour le component testing, pas besoin d'attendre l'appli
comme pour l'e2e)
* test(web): refactor user journeys into Cucumber scenarios
Convertit les parcours utilisateur (goal-driven, "en tant que X je peux
Y") en scénarios Gherkin, en réutilisant l'infra Cucumber déjà validée
par le smoke test (PR #24). Retire le smoke test jetable maintenant
superflu.
8 fichiers .feature ajoutés, chacun avec son fichier de step definitions
au même basename (convention de découverte du préprocesseur — voir
login-smoke.ts) :
- auth.feature : inscription (succès, erreur validation, email déjà
pris), connexion (succès, identifiants invalides), déconnexion
- onboarding.feature : les 3 scénarios déjà couverts (wizard complet,
étapes sautées, rejoindre un foyer pendant l'onboarding) — dépend de
household-settings.ts et preferences.ts pour ses steps de
création/rejoint de foyer et de sélection de régime/allergies
- household-settings.feature : créer un foyer, rejoindre par code
d'invitation, renommer (autosave), retirer un membre, supprimer le
foyer, quitter le foyer
- account.feature : suppression de compte (mauvais mot de passe,
succès, annulation)
- recipe-form.feature : les 4 scénarios déjà couverts inchangés (ajout
d'ingrédient + création, régression crypto.randomUUID, exclusion/
réinclusion d'ingrédient, préchargement + édition d'une recette
existante)
- recipes.feature : bascule favori, suppression d'une recette
- preferences.feature : autosave du régime, autosave des allergies
- user-preferences.feature : changement de thème (autosave)
En contrepartie, les anciens .cy.ts perdent uniquement les it() migrés
vers Gherkin — les scénarios de layout/affichage pur (catalogue de
recettes, tabs, recherche, panneau de détail, sidebar, planning grid,
etc.) restent en Cypress classique, conformément au découpage
"parcours utilisateur (Cucumber) vs layout (Cypress pur)" déjà en
place pour les component tests. auth.cy.ts, onboarding.cy.ts et
recipe-form.cy.ts sont supprimés : 100% de leur contenu a migré.
Les commentaires "voir auth.cy.ts pour la justification" désormais
obsolètes (fichier supprimé) sont remplacés par une explication
autonome du mock cy.intercept.
Vérifié statiquement : les 246 steps Gherkin des 8 .feature résolvent
chacun vers exactement une définition (0 non résolu, 0 ambigu) et
`pnpm exec biome check` est propre sur tout cypress/. Reste à confirmer
en CI que les scénarios passent réellement (pas seulement qu'ils se
résolvent).
* fix(web): fix cross-feature step discovery and slash-alternation bug
La CI de la refonte précédente (commit
|
||
| 9d4de338e3 |
Tests: couverture Cypress pour la grille de planning (step 4/4)
- home-planning.cy.ts → planning-page.cy.ts : nav sidebar reprise telle quelle, nouveaux cas pour la grille (case vide, recettes placées dans les bonnes cases, colonne du jour courant, navigation semaine précédente/suivante, popover calendrier) - cy.clock fige "aujourd'hui" (2026-08-17, un lundi) pour des assertions de date déterministes ; cy.viewport élargi (desktop-only, cf. décision produit) pour que les 7 colonnes tiennent sans scroll horizontal lors des assertions de visibilité |