# 07 — Plan de tests (recette manuelle) > Périmètre v1 : **aucun test automatisé** (décision du GOAL.md : « pas de test pour démarrer — à prévoir pour plus tard »). La recette ci-dessous est un **plan de tests manuels** aligné sur les critères d'acceptation du GOAL.md. Elle servira aussi de **cahier de recette** pour le livrable ECF. ## 1. Environnement de test | Paramètre | Valeur | | --- | --- | | Navigateur principal | Chrome / Edge (dernière version) — engine Chromium recommandé | | Navigateur secondaire | Firefox (contrôle croisé) | | Résolution principale | ≥ 1024 px (desktop) | | Commande de lancement | `pnpm dev` (ou `pnpm build && pnpm start` pour la recette finale) | ## 2. Critères d'acceptation globaux (rappel GOAL.md) - [ ] Application « desktop first » opérationnelle. - [ ] Interface en deux colonnes respectant le ratio 1/3 – 2/3. - [ ] Saisie Markdown à gauche, preview temps réel à droite au **format A4**. - [ ] Sauvegarde localStorage à chaque frappe + restauration au rechargement. - [ ] Impression du CV en PDF. - [ ] Pages Documentation et Mentions légales accessibles. ## 3. Tests fonctionnels détaillés ### 3.1 Écran général et layout | # | Action | Résultat attendu | | --- | --- | --- | | G1 | Ouvrir `/` | Deux colonnes : gauche (1/3) avec tab 1 actif, droite (2/3) avec feuille A4 (blanche, ombragée) | | G2 | Réduire la fenêtre sous 1024 px | Les panneaux s'empilent (gauche au-dessus de la droite) sans casse | | G3 | Vérifier la barre d'app et le footer | Barre : logo, bouton « Imprimer / PDF », lien Documentation. Footer : lien Mentions légales (masqué à l'impression) | ### 3.2 Onglets 1 à 5 (zones de saisie) | # | Action | Résultat attendu | | --- | --- | --- | | T1 | Cliquer sur les onglets 1→5 | L'onglet actif change ; le textarea affiche le contenu **de cet onglet uniquement** | | T2 | Saisir du Markdown dans l'onglet 1 (`**Jean Dupont**`) | Rendu temps réel dans le **header** de la feuille A4 (gras) | | T3 | Idem dans l'onglet 2 (nom, e-mail, site, GitHub en listes) | Rendu dans la section **État civil** (colonne 1/3) | | T4 | Onglet 3 (formation ex. `### Master` + liste) | Rendu dans la section **Formations** | | T5 | Onglet 4 | Rendu dans la section **Soft skills** | | T6 | Onglet 5 | Rendu dans la section **Centres d'intérêt** | | T7 | Basculer entre onglets après saisie | Chaque contenu est conservé, aucun écrasement croisé | | T8 | Vider complètement une section | La section correspondante disparaît de la preview | ### 3.3 Expériences professionnelles | # | Action | Résultat attendu | | --- | --- | --- | | X1 | Cliquer sur le bouton **+** | Un formulaire (titre + contenu) apparaît, vide | | X2 | Saisir titre + contenu puis **Enregistrer** | L'expérience apparaît dans la liste numérotée du panneau gauche (numéro 1) ET en tête de la section « Expériences professionnelles » | | X3 | Ajouter une 2ᵉ expérience | Elle s'affiche **sous** la 1ʳᵉ ; les listes se renumérotent (1, 2… dans l'ordre de saisie) | | X4 | Cliquer **Modifier** sur une entrée | Le formulaire se remplit avec titre + contenu de cette expérience (mode modification) | | X5 | Modifier puis **Enregistrer** | Le rendu preview met à jour la section Expériences | | X6 | Cliquer **Annuler** en cours de modification | Aucune modification appliquée | | X7 | Cliquer **×** sur une entrée | Confirmation demandée → confirmer → l'expérience disparaît (panneau gauche + preview) | | X8 | Supprimer la dernière expérience | La section affiche le message d'incitation « Ajoutez une expérience… » | | X9 | Contenu Markdown d'une expérience | Rendu temps réel en HTML dans la preview | ### 3.4 Persistance (localStorage) | # | Action | Résultat attendu | | --- | --- | --- | | P1 | Saisir du contenu dans 2-3 zones puis **recharger la page** (F5) | Tous les contenus et la liste des expériences sont restaurés | | P2 | Vérifier en devtools → Application → localStorage | Une clé `cv-maker:v1` existe, au format JSON avec `version: 1` | | P3 | Vider localStorage (ou supprimer la clé) puis recharger | L'application démarre avec des zones vides, **sans erreur** | | P4 | Introduire un JSON corrompu dans la clé (`cv-maker:v1`) puis recharger | Pas de crash ; état par défaut restauré | | P5 | Cliquer **Exporter JSON** | Un fichier `cv-maker.json` est téléchargé contenant le contenu saisi | | P6 | Créer/exporter un CV, **Importer JSON** sur ce fichier après modification | Un second clic sur **Importer** (bouton/badge) remplace le contenu par celui du fichier (cas nominal validé) | ### 3.5 Impression / PDF | # | Action | Résultat attendu | | --- | --- | --- | | M1 | Cliquer **Imprimer / PDF** | L'aperçu d'impression ne contient que la feuille A4 (pas de panneau de saisie ni toolbar) | | M2 | Choisir « Enregistrer en PDF » avec format A4 | Un PDF d'une page (contenu court) ; mise en page 1/3–2/3 respectée | | M3 | Format A4 par défaut | `@page size: A4` appliqué (aucun choix manuel requis) | ### 3.6 Rendu Markdown et sécurité | # | Action | Résultat attendu | | --- | --- | --- | | S1 | Saisir tous les éléments supportés (titres ###, gras, liste `-`, lien `[t](url)`, code `` ` ``) | Rendu HTML correct dans la preview | | S2 | Saisir `` dans une zone | Aucune alerte/exécution ; la balise est neutralisée | | S3 | Saisir `` | Affiché sans exécution (ou supprimé) — pas d'alerte | | S4 | Saisir `x` | Lien inoffensif ou supprimé ; aucun dialogue | ### 3.7 Pages Documentation et Mentions légales | # | Action | Résultat attendu | | --- | --- | --- | | D1 | Naviguer vers `/documentation` depuis la toolbar | Page d'aide affichée (prise en main + syntaxe Markdown) | | D2 | Naviguer vers `/mentions-legales` depuis le footer | Page affichée avec les sections attendues (module `06-` §4), **sans** paragraphe contact | | D3 | Retour vers l'éditeur | Lien retour fonctionnel ; les données du CV n'ont pas bougé | ### 3.8 PWA (recette avancée — build production requis) | # | Action | Résultat attendu | | --- | --- | --- | | W1 | `pnpm build && pnpm start` | Aucune erreur de build liée à Serwist | | W2 | DevTools → Application | Service worker enregistré, manifest chargé | | W3 | Clic « Installer l'application » | Installation proposée (icône et nom corrects) | | W4 | Passer hors-ligne puis recharger `/` | La page (squelette + app shell) est servie par le cache | | W5 | Données du CV hors-ligne | Le CV reste intact (localStorage) — pas de régression | ## 4. Hygiène du code (vérifications finales) - [ ] `pnpm lint` sans erreur ni warning bloquant. - [ ] `pnpm typecheck` sans erreur. - [ ] `pnpm audit` sans vulnérabilité critique. - [ ] Aucun `console.log` résiduel (à l'exception éventuelle du `console.warn` d'échec de sauvegarde documenté). ## 5. Évolutions testables (v2 — hors périmètre v1) Dès leur mise en place, ajouter à la recette : - Tests **Vitest** pour `lib/markdown.ts` (rendu + assainissement) et `lib/storage.ts` (parse/corruption) ; - Mise en place de **drag & drop** des expériences (réordonnancement) avec tests correspondants ; - Tests composants (React Testing Library) sur `CvTabs`, `ExperienceManager`, `CvPreview` (rendu conditionnel des sections vides). ## 6. Bilan de recette | Critère global GOAL.md | Tests concernés | Statut final | | --- | --- | --- | | Desktop first, 2 colonnes 1/3–2/3 | G1, G2 | ☐ | | Markdown → HTML temps réel | T2–T6, X9, S1 | ☐ | | Preview A4 | G1, M1–M3 | ☐ | | Persistance localStorage | P1–P5 | ☐ | | Impression PDF | M1–M3 | ☐ | | Expériences (+, liste, modif, ×) | X1–X9 | ☐ | | Onglets 1-5 | T1–T8 | ☐ | | Documentation + Mentions légales | D1–D3 | ☐ | | PWA | W1–W5 | ☐ | Tout critère ☐ non coché en livraison = anomalie à corriger avant livraison finale.