Esc
 Naviguer  Ouvrir Esc Fermer
Aller au contenu

11.4 — Documentation

🎯 Objectif : écrire une doc qu’on lit vraiment. Une doc obsolète est pire que pas de doc : elle ment.

À l'issue de cet axe, tu sauras :

  • Rédiger un README qui amène un nouveau dev à `npm run dev` en 5 minutes
  • Tracer les décisions d'archi avec un ADR
  • Maintenir un CHANGELOG conforme à Keep a Changelog
  • Générer une doc API OpenAPI à jour automatiquement
  • Documenter les composants UI avec Storybook
  • Distinguer les types de doc (Diátaxis : tutoriel, how-to, référence, explication)

Confirmé 10 min prérequis : axes 5-10 lus

Le code est la source de vérité. La documentation l’accompagne, ne le remplace pas.

Conséquences :

  • Code lisible > commentaires expliquant un code obscur.
  • Doc auto-générée (OpenAPI, TypeDoc) > doc manuelle qui dérive.
  • Doc proche du code (même repo) > wiki externe à part qui meurt.

C’est la première chose qu’un nouveau dev (ou ton toi-de-dans-6-mois) lit. Elle doit le mener à un projet qui tourne en quelques minutes.

# Nom du projet
> Description en une phrase
## Pourquoi
[2-3 phrases sur le problème résolu]
## Démarrage rapide
```bash
git clone ...
cd ...
npm install
cp .env.example .env
npm run dev
  • Next.js 16, TypeScript, Tailwind
  • PostgreSQL via Prisma
  • Vercel pour le déploiement
CommandeAction
npm run devLance le serveur de dev
npm run buildBuild de prod
npm testLance les tests Vitest
src/
├── app/ ← Next.js App Router
├── components/ ← Composants partagés
└── lib/ ← Helpers, utils

Voir CONTRIBUTING.md.

MIT — voir LICENSE.

### Anti-patterns à éviter
- 📛 **Histoire du projet** (« Initié en 2019 par X… ») — personne ne lit.
- 📛 **Captures floues**, vidéos qui ne marchent plus.
- 📛 **Liens vers le wiki interne** (404 pour 80 % des lecteurs).
- 📛 **Étapes d'installation manuelles** que `npm install` fait déjà.
## Le CHANGELOG — qui change quoi quand
Le standard : [Keep a Changelog](https://keepachangelog.com/) + [Semantic Versioning](https://semver.org/).
```markdown
# Changelog
Tous les changements notables.
## [Unreleased]
## [1.4.0] — 2026-04-15
### Added
- Endpoint `/api/v1/exports` pour exporter les commandes en CSV.
- Mode sombre activé par défaut sur l'OS dark.
### Changed
- Le format des dates passe de `dd/mm/yyyy` à `yyyy-mm-dd`.
### Fixed
- Crash quand le mot de passe contient des accents.
### Security
- Mise à jour de `lodash` (CVE-2026-1234).
## [1.3.0] — 2026-03-22

Avec changesets :

Fenêtre de terminal
npx changeset # ajoute un changeset à ton PR
npx changeset version # bump version + génère CHANGELOG
npx changeset publish # publish npm

Avec Conventional Commits + semantic-release, le bump est même automatique.

Déjà couvert en 3.4. Rappel : un fichier Markdown par décision, dans docs/adr/, versionné dans Git.

# ADR-007 : Migrer de Prisma vers Drizzle
## Statut
Accepté — 2026-04-29
## Contexte
Prisma engine consomme 200 Mo en cold start sur Cloudflare Workers,
ce qui dépasse la limite. Drizzle est compatible Workers natif.
## Décision
Migration progressive vers Drizzle. Co-existence pendant 1 sprint, puis suppression.
## Conséquences
✅ Bundle Workers passe de 12 Mo à 1.5 Mo
✅ Schema déclaratif comme Prisma
❌ Migration coût ~3 jours
❌ Drizzle ORM moins de magie (relations explicites)
## Alternatives
- Garder Prisma + Edge Runtime preview : retardé indéfiniment côté Vercel
- Kysely : bon mais pas de migrations DSL

Quand tu écris une API REST, génère la spec OpenAPI plutôt que de la maintenir à la main.

OpenAPI automatique. Tu écris :

class UserOut(BaseModel):
id: int
email: EmailStr
name: str
@app.get("/users/{user_id}", response_model=UserOut)
async def get_user(user_id: int) -> User: ...

/docs te donne Swagger UI + /openapi.json à jour. Zéro maintenance.

Avec hono/zod-openapi :

import { OpenAPIHono, createRoute, z } from '@hono/zod-openapi';
const route = createRoute({
method: 'get',
path: '/users/{id}',
request: { params: z.object({ id: z.coerce.number() }) },
responses: {
200: { content: { 'application/json': { schema: UserSchema } }, description: 'OK' },
},
});
app.openapi(route, (c) => c.json({ id: 1, email: 'a@a.com', name: 'A' }));

API Platform génère OpenAPI à partir de tes entités. Voir axe 8 PHP/Symfony.

Scribe ou Swagger PHP — annotations.

Storybook génère un site qui montre tous les états de tes composants UI, en isolation.

Fenêtre de terminal
npx storybook@latest init
Button.stories.tsx
import type { Meta, StoryObj } from '@storybook/react';
import { Button } from './Button';
const meta: Meta<typeof Button> = {
component: Button,
title: 'UI/Button',
};
export default meta;
type Story = StoryObj<typeof Button>;
export const Primary: Story = {
args: { variant: 'primary', children: 'Click me' },
};
export const Disabled: Story = {
args: { variant: 'primary', disabled: true, children: 'Disabled' },
};
export const Loading: Story = {
args: { variant: 'primary', loading: true, children: 'Loading' },
};

✅ Designers et devs partagent le même langage visuel. ✅ Tu vois tous les états sans avoir à recréer le contexte applicatif. ✅ Tu testes l’a11y et la responsivité par composant.

❌ Maintenance non triviale sur de gros design systems.

Verdict : utile pour les design systems d’entreprise (équipes 10+ devs). Surdimensionné pour un side-project ou un MVP.

Tu l’as vu partout dans ce site. Mermaid est un format texte qui génère des diagrammes :

flowchart LR
Client --> API
API --> DB[(Postgres)]
API --> Cache[(Redis)]

Bénéfices :

  • Versionné dans Git (un diff Mermaid = un diff lisible).
  • GitHub/GitLab rendent Mermaid nativement dans les README/MD.
  • Pas besoin de Visio/draw.io ou de PNG qui dérivent.

Types de diagrammes utiles : flowchart, sequenceDiagram, erDiagram, gantt, classDiagram, stateDiagram-v2.

Le framework Diátaxis (créé par Daniele Procida) sépare la doc en 4 catégories distinctes :

TypeQuestion répondueStyle
Tutoriel« Comment apprendre X depuis zéro ? »Pas-à-pas guidé, axé apprentissage
How-to« Comment faire Y ? »Recette ciblée, axée objectif
Référence« Quels sont les paramètres de Z ? »Liste exhaustive, axée précision
Explication« Pourquoi X marche ainsi ? »Discussion, axée compréhension

Erreur classique : un README qui mélange tout → le tutoriel est interrompu par des détails de référence, et personne ne s’y retrouve.

Bonne pratique :

docs/
├── tutorials/ ← « démarrer avec X »
├── how-to/ ← « envoyer un email transactionnel »
├── reference/ ← OpenAPI, types, configs
└── explanation/ ← « pourquoi RLS plutôt que middleware »

« Code tells you HOW; comments tell you WHY. »

Bon commentaireMauvais commentaire
// Stripe expects amounts in cents// increment counter (le nom le dit)
// HACK: workaround for Safari bug #234// for loop over users (le code le dit)
// Uses logarithmic complexity for large arrays(commentaire long expliquant un mauvais nom)

Pour les APIs publiques d’une lib ou d’un service :

/**
* Calcule le total TTC d'une commande.
*
* @param items - les lignes avec prix HT et quantité
* @param taxRate - taux de TVA en décimal (0.20 pour 20 %)
* @throws {InvalidOrderError} si items est vide
* @returns le total TTC en centimes
*
* @example
* ```ts
* const total = computeTotal([{ priceCents: 1000, qty: 2 }], 0.20);
* // 2400
* ```
*/
export function computeTotal(items: Line[], taxRate: number): number { ... }

TypeDoc génère un site HTML à partir des TSDoc. Idem phpDocumentor, pdoc (Python).

Un nouveau dev rejoint l'équipe et clone le repo. Combien de temps avant `npm run dev` réussi ?
Pour ton API REST en Hono ou FastAPI, doc OpenAPI ?
Tu vois `// increment counter` dans le code. Avis ?

Fin de l’axe 11. Direction l’axe 12 — Sécurité applicative, ou attaque le projet Refactor + tests.