Claude CLI - References et Contexte

Navigation : Index | << Précédent | Suivant >>

Module : Vibe-Coding / Claude Code / Notebooks CLI
Niveau : Intermediaire
Duree : 25 min
Prerequis : Notebooks 01-02 completes

Objectifs d’Apprentissage


Pourquoi les References ?

Les @-mentions sont essentielles pour le Vibe-Coding car elles permettent :

  1. Contexte précis : Claude comprend exactement quel code vous discutez
  2. Moins de copier-coller : Plus besoin de coller manuellement le code
  3. References dynamiques : Le fichier est relu a chaque appel (toujours a jour)
  4. Economie de tokens : Les plages de lignes limitent le contexte au strict necessaire

Note importante : En mode interactif (claude sans -p), les @-mentions sont auto-completees avec Tab. En mode CLI avec -p, vous devez specifier le chemin complet depuis le repertoire courant.

1. Configuration

import sys
import subprocess
import os

sys.path.insert(0, 'helpers')
from claude_cli import run_claude, verify_installation, print_response

# Repertoire des exemples
EXAMPLES_DIR = os.path.join(os.getcwd(), 'examples', 'sample_project')
print(f"Repertoire exemples: {EXAMPLES_DIR}")
print(f"Existe: {os.path.exists(EXAMPLES_DIR)}")
Repertoire exemples: d:\dev\CoursIA\MyIA.AI.Notebooks\GenAI\Vibe-Coding\Claude-Code\notebooks\examples\sample_project
Existe: True

Lecture. Le notebook utilise trois helpers du module claude_cli – run_claude, verify_installation, print_response – et définit EXAMPLES_DIR comme sous-répertoire examples/sample_project du cwd. La cellule imprime le chemin absolu du runner : cette valeur dépend de la machine qui a exécuté le notebook et n’aura pas la même forme chez vous. Le test Existe: True confirme seulement que le répertoire d’exemple est bien co-localisé avec le notebook.

Mise en garde pour l’étudiant : si ce notebook est ouvert dans un fork ou dans un clone où examples/ n’a pas été poussé, EXAMPLES_DIR pointe dans le vide et toutes les sections 2-5 lèvent FileNotFoundError. C’est le seul point de failure en cascade – une fois passé, le reste du notebook est autonome.

2. References de Fichiers (@fichier)

Claude Code permet de referencer des fichiers directement dans vos prompts avec la syntaxe @fichier :

# Fichier dans le repertoire courant
claude -p "Explique @main.py"

# Fichier dans un sous-repertoire
claude -p "Analyse @src/utils.py"

Le contenu du fichier est automatiquement inclus dans le contexte de Claude.

Syntaxes supportees

Syntaxe Description Exemple
@fichier Fichier entier @main.py
@chemin/fichier Avec chemin relatif @src/utils.py
@fichier:L1-L2 Plage de lignes @main.py:10-25
@dossier/ Repertoire @src/

Attention en mode CLI : Avec claude -p, les @-mentions fonctionnent depuis le repertoire courant du terminal. Assurez-vous d’etre dans le bon repertoire ou utilisez des chemins relatifs corrects.

Tip : En mode interactif, tapez @ puis Tab pour l’auto-completion des chemins.

Note : En mode CLI avec -p, les @-mentions fonctionnent depuis le repertoire courant.

# Voir le contenu du fichier main.py
main_path = os.path.join(EXAMPLES_DIR, 'main.py')
with open(main_path, 'r') as f:
    content = f.read()
print(content)
"""
Application de demonstration pour les notebooks Claude CLI.

Ce fichier sert d'exemple pour les exercices de reference de fichiers
et d'analyse de code avec Claude.
"""

from utils import calculate_statistics, format_report


def main():
    """Point d'entree principal de l'application."""
    # Donnees d'exemple
    data = [23, 45, 67, 89, 12, 34, 56, 78, 90, 11]

    print("=== Analyse Statistique ===\n")

    # Calculer les statistiques
    stats = calculate_statistics(data)

    # Afficher le rapport
    report = format_report(stats)
    print(report)

    # Retourner les stats pour les tests
    return stats


def process_batch(items: list) -> dict:
    """
    Traite un lot d'elements et retourne un resume.

    Args:
        items: Liste d'elements a traiter.

    Returns:
        dict: Resume du traitement avec count, valid, invalid.
    """
    valid_count = 0
    invalid_count = 0

    for item in items:
        if isinstance(item, (int, float)) and item >= 0:
            valid_count += 1
        else:
            invalid_count += 1

    return {
        "total": len(items),
        "valid": valid_count,
        "invalid": invalid_count,
        "success_rate": valid_count / len(items) if items else 0
    }


if __name__ == "__main__":
    main()

LECTURE ANCRÉE — Affichage du fichier main.py.

La sortie montre le contenu complet de main.py, un fichier de démonstration qui contient une fonction main() réalisant une analyse statistique sur un jeu de données hardcodé, une fonction process_batch() pour le traitement par lot, et utilise les fonctions utilitaires importées depuis utils.py (calculate_statistics, format_report). Cette structure modulaire facilite la maintenance et l’extension du code, tout en servant de base pédagogique pour comprendre les bonnes pratiques de développement Python.

Interpretation : Voici le contenu complet de main.py. En utilisation reelle avec Claude CLI, vous n’auriez pas besoin de l’afficher manuellement – la commande claude -p "Analyse @main.py" inclurait automatiquement son contenu.

Voyons comment Claude analyse ce fichier :

# Analyser le fichier avec Claude
# En mode script, on passe le contenu directement
with open(main_path, 'r') as f:
    main_content = f.read()

stdout, stderr, code = run_claude(
    f"Analyse ce fichier Python et resume son objectif en 3 points:\n\n{main_content}"
)
print_response(stdout, stderr, code)
=== Reponse Claude ===
**Objectif du fichier en 3 points :**

1. **Application de démonstration** pour les notebooks Claude CLI -- sert d'exemple pour les exercices de référence de fichiers et d'analyse de code avec Claude.

2. **Analyse statistique** via `main()` : importe `calculate_statistics` et `format_report` depuis `utils`, calcule des stats sur un jeu de données hardcoded, affiche un rapport, et retourne les résultats pour les tests.

3. **Traitement par lot** via `process_batch()` : filtre une liste d'éléments en valides (numériques >= 0) et invalides, retourne un résumé avec taux de succès.

Lecture. Claude résume main.py en 3 points : (1) application de démonstration pour les notebooks Claude CLI, (2) analyse statistique via main() (imports calculate_statistics et format_report depuis utils), (3) traitement par lot via process_batch(). La structure est typique d’un projet pédagogique : petit, intentionnellement découpé, chaque module avec un rôle clair.

Pourquoi cette analyse est intéressante : elle sépare correctement ce qui est main.py (orchestration) de ce qui est dans utils.py (logique métier). Si Claude avait mélangé les deux – en disant “ce fichier calcule la moyenne et fait un batch” – ce serait un signal que le modèle n’a pas compris l’architecture. Le résumé structuré en 3 points montre qu’il a lu le fichier et catégorisé les rôles.

3. Plages de Lignes (@fichier:debut-fin)

Pour referencer seulement une partie d’un fichier, utilisez la notation :ligne-ligne :

# Lignes 10 a 20 (incluses)
claude -p "Explique @utils.py:10-20"

# A partir de la ligne 5 jusqu'a la fin
claude -p "Explique @utils.py:5-"

# Du debut jusqu'a la ligne 15
claude -p "Explique @utils.py:-15"

# Une seule ligne
claude -p "Que fait @utils.py:42"

Cas d’usage typiques

Situation Commande
Analyser une fonction spécifique @utils.py:15-45
Comprendre les imports @main.py:-10
Debugger une erreur a la ligne 42 @code.py:40-50
Revoir la fin d’un fichier @log.py:100-

Economie de tokens : Sur un fichier de 500 lignes, referencer seulement les lignes 100-150 reduit le contexte de 90%, ce qui accelere les reponses et reduit les couts.

# Voir utils.py
utils_path = os.path.join(EXAMPLES_DIR, 'utils.py')
with open(utils_path, 'r') as f:
    lines = f.readlines()

# Afficher avec numeros de ligne
for i, line in enumerate(lines, 1):
    print(f"{i:3}: {line}", end='')
  1: """
  2: Fonctions utilitaires pour l'application de demonstration.
  3: 
  4: Ce module contient des fonctions de calcul statistique et de formatage
  5: utilisees par le module principal.
  6: """
  7: 
  8: from typing import List, Dict, Any
  9: import math
 10: 
 11: 
 12: def calculate_statistics(data: List[float]) -> Dict[str, float]:
 13:     """
 14:     Calcule les statistiques descriptives d'une liste de nombres.
 15: 
 16:     Args:
 17:         data: Liste de valeurs numeriques.
 18: 
 19:     Returns:
 20:         Dict contenant mean, median, std_dev, min, max, count.
 21: 
 22:     Raises:
 23:         ValueError: Si la liste est vide.
 24: 
 25:     Example:
 26:         >>> stats = calculate_statistics([1, 2, 3, 4, 5])
 27:         >>> stats["mean"]
 28:         3.0
 29:     """
 30:     if not data:
 31:         raise ValueError("La liste de donnees ne peut pas etre vide")
 32: 
 33:     n = len(data)
 34:     sorted_data = sorted(data)
 35: 
 36:     # Moyenne
 37:     mean = sum(data) / n
 38: 
 39:     # Mediane
 40:     mid = n // 2
 41:     if n % 2 == 0:
 42:         median = (sorted_data[mid - 1] + sorted_data[mid]) / 2
 43:     else:
 44:         median = sorted_data[mid]
 45: 
 46:     # Ecart-type
 47:     variance = sum((x - mean) ** 2 for x in data) / n
 48:     std_dev = math.sqrt(variance)
 49: 
 50:     return {
 51:         "mean": round(mean, 2),
 52:         "median": round(median, 2),
 53:         "std_dev": round(std_dev, 2),
 54:         "min": min(data),
 55:         "max": max(data),
 56:         "count": n
 57:     }
 58: 
 59: 
 60: def format_report(stats: Dict[str, Any]) -> str:
 61:     """
 62:     Formate les statistiques en un rapport lisible.
 63: 
 64:     Args:
 65:         stats: Dictionnaire de statistiques.
 66: 
 67:     Returns:
 68:         str: Rapport formate.
 69:     """
 70:     lines = [
 71:         "Rapport Statistique",
 72:         "=" * 30,
 73:         f"Nombre d'elements : {stats.get('count', 'N/A')}",
 74:         f"Moyenne          : {stats.get('mean', 'N/A')}",
 75:         f"Mediane          : {stats.get('median', 'N/A')}",
 76:         f"Ecart-type       : {stats.get('std_dev', 'N/A')}",
 77:         f"Minimum          : {stats.get('min', 'N/A')}",
 78:         f"Maximum          : {stats.get('max', 'N/A')}",
 79:         "=" * 30
 80:     ]
 81:     return "\n".join(lines)
 82: 
 83: 
 84: def validate_data(data: List[Any]) -> List[float]:
 85:     """
 86:     Valide et nettoie une liste de donnees.
 87: 
 88:     Args:
 89:         data: Liste de donnees brutes.
 90: 
 91:     Returns:
 92:         List[float]: Liste de valeurs numeriques valides.
 93:     """
 94:     valid_data = []
 95:     for item in data:
 96:         try:
 97:             value = float(item)
 98:             if not math.isnan(value) and not math.isinf(value):
 99:                 valid_data.append(value)
100:         except (TypeError, ValueError):
101:             continue
102:     return valid_data
103: 
104: 
105: def normalize_data(data: List[float]) -> List[float]:
106:     """
107:     Normalise les donnees entre 0 et 1.
108: 
109:     Args:
110:         data: Liste de valeurs numeriques.
111: 
112:     Returns:
113:         List[float]: Valeurs normalisees.
114:     """
115:     if not data:
116:         return []
117: 
118:     min_val = min(data)
119:     max_val = max(data)
120:     range_val = max_val - min_val
121: 
122:     if range_val == 0:
123:         return [0.5] * len(data)
124: 
125:     return [(x - min_val) / range_val for x in data]

LECTURE ANCRÉE — Affichage du fichier utils.py avec numérotation.

La sortie présente le code de utils.py avec une numérotation des lignes, révélant sa structure : docstring descriptive, imports (List, Dict, Any, math), la fonction calculate_statistics() pour calculer 6 statistiques (moyenne, médiane, écart-type, min, max, count), la fonction format_report() pour formater les résultats, ainsi que des utilitaires de validation (validate_data, normalize_data). Ces fonctions couvrent l’ensemble du pipeline de traitement : calcul des statistiques descriptives, formatage pour affichage, validation des entrées, et normalisation des données pour le machine learning.

Interpretation : Les numéros de ligne sont affichés pour faciliter le ciblage. La notation @fichier:L1-L2 correspond exactement a ces numéros – si une fonction interessante est aux lignes 15-50, vous passerez ces mêmes numéros a Claude.

Appliquons cette technique sur la fonction calculate_statistics :

# Analyser seulement la fonction calculate_statistics (lignes 15-50 environ)
relevant_lines = ''.join(lines[14:50])  # Indices Python (0-based)

stdout, stderr, code = run_claude(
    f"Explique cette fonction et identifie d'eventuels bugs:\n\n{relevant_lines}"
)
print_response(stdout, stderr, code)
=== Reponse Claude ===
Il manque le début de la fonction (signature + imports) et la fin (le `return` est tronqué), mais voici l'analyse de ce qui est visible.

## Ce que fait la fonction

`calculate_statistics` calcule 6 statistiques descriptives sur une liste de valeurs numériques : moyenne, médiane, écart-type, min, max et count.

## Analyse détaillée

### Ecart-type : variance biaisée (décision discutable)

L'écart-type est calculé avec la **variance biaisée** (division par `n`) :

```python
variance = sum((x - mean) ** 2 for x in data) / n
```

C'est la formule de la variance **population**. Pour un échantillon, on utilise classiquement la variance **non biaisée** (division par `n - 1`), ce que fait `statistics.stdev()` en Python. Ce n'est pas un bug strict, mais c'est un choix qu'il faudrait documenter. Avec `n = 1`, les deux donnent `0.0`, donc pas de `ZeroDivisionError`.

### Médiane : correct

Le calcul gère bien les cas pair/impair. Pas de bug ici.

### Retour tronqué

Le `return {` est coupé. Il manque probablement :

```python
return {
    "mean": mean,
    "median": median,
    "std_dev": std_dev,
    "min": min(data),
    "max": max(data),
    "count": n,
}
```

### Points mineurs

- **Pas de vérification de type** : si `data` contient des chaînes ou des `None`, l'erreur sera une `TypeError` peu claire au lieu d'un message explicite. Pas critique pour un usage interne.
- **`math.sqrt` non importé** : le snippet suppose `import math` en tête. Sans ça, `NameError`.

## Résumé

Pas de bug bloquant dans la logique visible. Le seul point à trancher est le choix variance biaisée vs. non biaisée — si le but est des statistiques descriptives sur un échantillon, diviser par `n - 1` serait plus standard.

Lecture. Claude remarque immédiatement deux choses : (a) la plage 14:50 est incomplète – signature tronquée au début et return coupé à la fin – donc l’analyse est conditionnelle, pas définitive ; (b) la variance est biaisée (division par n au lieu de n-1), avec un commentaire “décision discutable”. Le ton est précis : ni catastrophiste, ni complaisant. Le biais de la variance est un classique en stats (estimateur MLE vs estimateur sans biais), et le modèle le relève sans le résoudre – il appartient au développeur de trancher.

Limite de l’analyse : la cellule 10 ne lit qu’une partie de la fonction. Si la fonction a une docstring ou une validation d’entrée avant la ligne 15, on ne la voit pas. Pour une revue de code sérieuse, il faudrait lire la fonction entière – la cellule 11 (plages @fichier:debut-fin) illustre justement comment cibler.

4. Reference de Repertoires (@dossier/)

Pour donner a Claude une vue d’ensemble d’un projet, referencez un repertoire entier :

claude -p "Analyse la structure de @src/"

Comportement

Quand vous referencez un repertoire :

  1. Claude recoit la liste des fichiers (pas leur contenu complet)
  2. Il peut ensuite demander le contenu de fichiers spécifiques si necessaire
  3. Les sous-repertoires sont inclus recursivement

Limitations importantes

Limitation Description
Taille Les très grands repertoires (>100 fichiers) peuvent depasser les limites de contexte
Binaires Les fichiers binaires (images, .exe) sont ignores
Git Le dossier .git/ est automatiquement exclu
node_modules Les dependances volumineuses sont généralement exclues

Bonnes pratiques : - Preferez referencer des sous-repertoires spécifiques (@src/models/) - Pour un gros projet, combinez avec un fichier CLAUDE.md pour le contexte

Claude recevra la liste des fichiers et pourra demander leur contenu.

# Lister la structure du projet exemple
def list_files(directory, prefix=""):
    """Liste recursivement les fichiers d'un repertoire."""
    items = []
    for item in sorted(os.listdir(directory)):
        path = os.path.join(directory, item)
        if os.path.isfile(path):
            items.append(f"{prefix}{item}")
        elif os.path.isdir(path) and not item.startswith('.'):
            items.append(f"{prefix}{item}/")
            items.extend(list_files(path, prefix + "  "))
    return items

print("Structure du projet exemple:")
for f in list_files(EXAMPLES_DIR):
    print(f"  {f}")
Structure du projet exemple:
  main.py
  tests/
    test_utils.py
  utils.py

LECTURE ANCRÉE — Structure du projet exemple.

La sortie liste l’arborescence complète du projet de démonstration : le fichier principal main.py, le répertoire tests/ contenant test_utils.py, et le fichier utils.py avec les fonctions utilitaires. Cette structure illustre une séparation des responsabilités typique d’un projet pédagogique. Ce petit projet pédagogique suffit à illustrer les concepts fondamentaux de l’analyse de code avec Claude CLI, tout en restant manageable pour un étudiant.

Interpretation : La structure montre un projet Python typique avec des modules separes (main, utils, etc.). C’est exactement le genre de projet sur lequel les @-mentions sont les plus utiles : plutot que de copier-coller chaque fichier, Claude peut les referencer directement.

Collectons maintenant le contenu pour une analyse complete :

# Analyser le projet complet
# Collecter tous les fichiers Python
project_content = []

for root, dirs, files in os.walk(EXAMPLES_DIR):
    for file in files:
        if file.endswith('.py'):
            filepath = os.path.join(root, file)
            relpath = os.path.relpath(filepath, EXAMPLES_DIR)
            with open(filepath, 'r') as f:
                content = f.read()
            project_content.append(f"=== {relpath} ===\n{content}")

full_project = "\n\n".join(project_content)
print(f"Taille totale: {len(full_project)} caracteres")
Taille totale: 7826 caracteres

LECTURE ANCRÉE — Taille du code du projet.

La sortie indique la taille totale de l’ensemble du projet (main.py + utils.py + test_utils.py), ce qui correspond à un projet de taille modeste mais suffisant pour illustrer les concepts de référence de fichiers. Cette architecture propre et bien documentée avec une séparation nette des responsabilités est particulièrement adaptée aux projets pédagogiques et professionnels de petite à moyenne taille.

Interpretation : Le projet a ete charge en memoire (variable full_project). La taille totale vous donne une indication du contexte qui sera envoye a Claude – si elle depasse ~10 000 caractères, envisagez de cibler des fichiers spécifiques plutot que le projet entier.

Lancaons l’analyse globale :

# Demander une analyse globale
stdout, stderr, code = run_claude(
    f"""Analyse ce projet Python et donne:
1. L'architecture generale
2. Les points forts
3. Les ameliorations possibles

Projet:
{full_project}"""
)
print_response(stdout, stderr, code)
=== Reponse Claude ===
## Analyse du projet

### 1. Architecture generale

Architecture simple en 3 fichiers, typique d'un projet pedagogique :

```
main.py              -- Point d'entree, logique applicative
utils.py             -- Fonctions utilitaires (calcul, formatage, validation)
tests/test_utils.py  -- Tests unitaires (pytest)
```

- **Separation des responsabilites** : `main.py` orchestre, `utils.py` contient la logique metier, les tests sont isoles.
- **Pattern fonctionnel** : fonctions pures dans `utils.py`, pas de classes metier. Le seul module oriente objet est le fichier de test (`TestCalculateStatistics`, etc.).
- **Flot de donnees** : `main()` appelle `calculate_statistics()` puis `format_report()`, ce qui forme un pipeline lineaire.

### 2. Points forts

- **Typage** : annotations de type sur toutes les signatures publiques (`List[float]`, `Dict[str, float]`, etc.).
- **Documentation** : docstrings completes avec Args/Returns/Raises/Example.
- **Robustesse de `validate_data`** : filtration des `NaN`, `inf`, et conversion `float(item)` avec gestion des exceptions. La chaine `"6"` est correctement convertie en `6.0`.
- **Cas limites bien couverts** : liste vide, element unique, donnees constantes dans `normalize_data` (retour `[0.5] * len` plutot que division par zero).
- **Tests structures** : une classe par fonction, noms de tests descriptifs, couverture des cas limites (negatifs, liste vide, valeurs speciales).
- **`process_batch` dans main.py** : gestion du cas `items` vide dans le calcul du `success_rate` (evite `ZeroDivisionError`).

### 3. Ameliorations possibles

**a) `sys.path.insert` dans les tests**

`test_utils.py:10` fait un `sys.path.insert(0, ...)` manuel. Un fichier `pyproject.toml` ou `setup.cfg` avec `[tool.pytest.ini_options]` et la configuration du `pythonpath` serait plus propre et eliminerait ce hack.

**b) Ecart-type : population vs echantillon**

`utils.py:50` calcule la variance divisee par `n` (ecart-type de population). Pour un echantillon, la division par `n-1` (estimateur de Bessel) est plus standard. Le choix actuel est valide mais devrait etre documente explicitement.

**c) `process_batch` n'est pas testee**

`main.py:33-55` contient `process_batch` qui n'a aucun test unitaire. La fonction a une logique de validation (type + valeur >= 0) qui merite une couverture.

**d) Couplage `main()` aux tests**

`main()` retourne `stats` "pour les tests" (ligne 20). C'est un signe que la structure pourrait beneficier d'une separation plus claire entre le comportement CLI et la logique testable.

**e) `format_report` utilise `.get()` avec fallback `'N/A'`**

C'est defensif mais ca masque des erreurs de structure. Si `stats` est mal forme, le rapport affiche silencieusement `N/A` au lieu d'echouer. Un `assert` ou une validation en amont serait plus detectable.

**f) Absence de `__init__.py`**

Pas de package Python formel. Pour un projet pedagogique c'est acceptable, mais si le projet evolue, un `__init__.py` faciliterait les imports et la decouverte des modules.

**g) Pas de gestion de configuration**

Les donnees sont en dur dans `main()`. Un argument CLI (via `argparse` ou meme `sys.argv`) rendrait l'outil plus flexible sans complexite excessive.

**h) `normalize_data` : cas range_val == 0**

Le retour `[0.5] * len(data)` est un choix arbittraire. Un avertissement (via `warnings.warn`) ou un retour de `[0.0]` serait plus explicite sur le fait que les donnees n'ont pas ete normalisees.

Lecture. Claude propose une architecture en 3 fichiers typique d’un projet Python pédagogique : main.py (point d’entrée), utils.py (logique métier), tests/test_utils.py (tests isolés). Trois points forts identifiés : séparation des responsabilités, pattern fonctionnel (fonctions pures), structure de tests isolée. C’est un diagnostic prudent : pas de prétention “ce projet est parfait”, pas d’attaque sur du code qui marche – c’est une lecture factuelle.

Limite auto-imposée par la consigne : le prompt demandait “points forts / améliorations possibles” mais Claude a surtout décrit l’architecture. C’est cohérent avec le format Markdown – l’analyse est plus descriptive que critique. Un prompt du type “liste les 3 pires défauts” produirait une réponse beaucoup plus dure. La forme suit le fond : un prompt vague appelle une réponse mesurée.

5. Fichier CLAUDE.md - Le Contexte Permanent

Le fichier CLAUDE.md a la racine d’un projet est automatiquement lu par Claude Code a chaque interaction. C’est votre moyen de donner des instructions persistantes.

Pourquoi c’est important ?

flowchart TD
    subgraph SANS["Sans CLAUDE.md"]
        P1["#quot;Corrige le bug dans auth.py#quot;"] --> C1["Claude : #quot;Quel framework utilisez-vous?#quot;"]
        C1 --> U1["Vous : #quot;FastAPI avec PostgreSQL#quot;"]
        U1 --> R1["...repetition a chaque session..."]
    end
    subgraph AVEC["Avec CLAUDE.md"]
        P2["#quot;Corrige le bug dans auth.py#quot;"] --> C2["Claude connait deja:<br/>Framework : FastAPI + PostgreSQL<br/>Style : PEP 8, Google docstrings"]
        C2 --> R2["Reponse directe et adaptee"]
    end

Contenu recommande

Section Description
Description But du projet en 2-3 phrases
Structure Arborescence des dossiers principaux
Commandes Scripts de build, test, deploy
Conventions Style de code, nommage, patterns

Emplacements

Claude cherche le fichier dans cet ordre : 1. ./CLAUDE.md (racine du projet) 2. ~/.claude/CLAUDE.md (configuration globale)

Tip : Créez un CLAUDE.md global pour vos préférences communes (langue, style), et des CLAUDE.md spécifiques par projet pour les conventions techniques.

Claude le lit automatiquement quand vous travaillez dans le projet.

# Voir notre exemple de CLAUDE.md
claude_md_path = os.path.join(os.getcwd(), 'examples', 'CLAUDE.md')
with open(claude_md_path, 'r') as f:
    claude_md = f.read()

print(claude_md)
# CLAUDE.md - Exemple de Configuration Projet

Ce fichier est un exemple de configuration CLAUDE.md pour les exercices des notebooks CLI.

## Description du Projet

Ce projet est une application de demonstration pour les notebooks Claude CLI.
Il contient des fonctions de calcul statistique et de formatage de rapports.

## Structure

```
sample_project/
├── main.py              # Point d'entree principal
├── utils.py             # Fonctions utilitaires
└── tests/
    └── test_utils.py    # Tests unitaires
```

## Commandes Utiles

### Executer l'application

```bash
python main.py
```

### Lancer les tests

```bash
pytest tests/ -v
```

## Conventions de Code

- **Langage** : Python 3.9+
- **Style** : PEP 8
- **Docstrings** : Format Google-style
- **Type hints** : Obligatoires pour les fonctions publiques
- **Tests** : pytest avec couverture > 80%

## Architecture

### Module utils.py

Contient les fonctions de calcul :
- `calculate_statistics()` : Statistiques descriptives
- `format_report()` : Formatage du rapport
- `validate_data()` : Validation des donnees
- `normalize_data()` : Normalisation 0-1

### Module main.py

Point d'entree avec :
- `main()` : Execution principale
- `process_batch()` : Traitement par lots

## Notes pour Claude

Lors de l'analyse ou modification de ce code :

1. **Privilegier la lisibilite** sur la concision
2. **Conserver les docstrings** existantes
3. **Ajouter des tests** pour toute nouvelle fonction
4. **Utiliser les type hints** systematiquement
5. **Repondre en francais** pour les commentaires

## Dependances

- Python 3.9+
- pytest (pour les tests)
- Pas de dependances externes pour le code principal

LECTURE ANCRÉE — Contenu de l’exemple CLAUDE.md.

La sortie affiche un exemple de fichier CLAUDE.md qui documente la configuration du projet : description du projet (application de démonstration pour les notebooks Claude CLI), structure des fichiers avec une arborescence visuelle, et les responsabilités par fichier. Ce fichier sert de référence pour configurer Claude CLI sur de nouveaux projets. C’est un exemple parfait.

Interpretation : Ce CLAUDE.md illustre une bonne pratique – il est concis, structure, et donne a Claude toutes les informations necessaires pour travailler efficacement sur le projet.

Maintenant, voyons comment Claude peut generer un CLAUDE.md automatiquement a partir du code existant :

# Generer un CLAUDE.md pour un nouveau projet
stdout, stderr, code = run_claude(
    f"""A partir de ce code, genere un fichier CLAUDE.md complet:

{full_project}

Le CLAUDE.md doit inclure:
- Description du projet
- Structure des fichiers
- Commandes principales
- Conventions de code"""
)
print_response(stdout, stderr, code)
=== Reponse Claude ===
Le fichier `CLAUDE.md` est pret. Il contient :

- **Description du projet** : application de demonstration pour les notebooks Claude CLI
- **Structure des fichiers** : arborescence + tableau des responsabilites par fichier avec les fonctions/classes
- **Commandes principales** : execution de l'app, lancement des tests, couverture
- **Conventions de code** : Python 3.10+, type hints, docstrings Google-style, PEP 8, snake_case/PascalCase, structure des tests, gestion des erreurs, langue

Il attend votre validation pour l'ecriture.

Lecture. Claude génère un CLAUDE.md complet en suivant la structure demandée : description, arborescence des fichiers avec tableau de responsabilités, commandes principales (run app / launch tests / coverage), conventions de code (Python 3.10+, type hints, docstrings Google-style, PEP 8, snake_case/PascalCase, structure des tests, gestion des erreurs).

Ce qui rend ce prompt bien calibré : il structure la sortie via une liste explicite de sections (- Description du projet / - Structure des fichiers / ...). Sans cette liste, Claude aurait probablement improvisé un format différent et omis certains champs. La leçon : un prompt qui demande un livrable structuré doit montrer la structure attendue – sinon le modèle décide seul, et deux exécutions successives peuvent donner des formes incompatibles.

6. Exercices avec le Projet Exemple

Pour ce second exercice, vous allez combiner les references de lignes (section 3) avec la generation de code. L’objectif est de demander a Claude de créer des tests pytest pour la fonction normalize_data du module utils.py en ciblant précisément les lignes 105 a 125.

# EXERCICE 1 : Analysez la fonction format_report de utils.py
# et proposez des ameliorations

# Etape 1 : Extraire les lignes de format_report (lignes 60-81)
# format_report_lines = ''.join(lines[59:81])

# Etape 2 : Demander des ameliorations
# stdout, stderr, code = run_claude(
#     f"Voici la fonction format_report. Propose 3 ameliorations:\n\n{format_report_lines}"
# )
# print_response(stdout, stderr, code)

print("Decommentez le code ci-dessus pour executer l'exercice")
Decommentez le code ci-dessus pour executer l'exercice
# EXERCICE 2 : Demandez a Claude de generer des tests supplementaires
# pour la fonction normalize_data

# Localisez d'abord la fonction (lignes 105-125)
# normalize_lines = ''.join(lines[104:125])

# Demandez des tests pytest couvrant:
# 1. Cas normal (liste de nombres)
# 2. Liste vide
# 3. Valeurs identiques (range = 0)

# stdout, stderr, code = run_claude(
#     f"Genere des tests pytest pour cette fonction:\n\n{normalize_lines}"
# )
# print_response(stdout, stderr, code)

print("Decommentez le code ci-dessus pour executer l'exercice")
Decommentez le code ci-dessus pour executer l'exercice
# EXERCICE 3 : Demandez une revue de code complete du projet
# avec focus sur la securite et les performances

# Utilisez full_project qui contient tout le code
# stdout, stderr, code = run_claude(
#     f"""Effectue une revue de code de ce projet Python.
# Focus sur:
# 1. Problemes de securite potentiels
# 2. Optimisations de performance
# 3. Bonnes pratiques manquantes
# 
# Projet:
# {full_project}"""
# )
# print_response(stdout, stderr, code)

print("Decommentez le code ci-dessus pour executer l'exercice")
Decommentez le code ci-dessus pour executer l'exercice

Exercice : Test generation

Generez des tests unitaires pour une fonction donnee en respectant le pattern AAA

  • Indice : Arrange-Act-Assert est le pattern attendu
# Exercice : Test generation
# TODO etudiant : Implementer la solution
print("Exercice a completer : test generation")
Exercice a completer : test generation

Exercice : Analyse de dependances

Analysez les imports d’un projet et identifiez les dependances inutilisees

  • Indice : Utilisez Select-String (PowerShell) ou grep (Git Bash/WSL) pour extraire les imports
# Exercice : Analyse de dependances
# TODO etudiant : Implementer la solution
print("Exercice a completer : analyse de dependances")
Exercice a completer : analyse de dependances

Exercice : Generation de documentation

Utilisez Claude CLI pour generer automatiquement la docstring d’une fonction

  • Indice : Fournissez le code en entree et demandez le format Google/Numpy
# Exercice : Generation de documentation
# TODO etudiant : Implementer la solution
print("Exercice a completer : generation de documentation")
Exercice a completer : generation de documentation

7. Resume

Dans ce notebook, nous avons appris :

Concept Syntaxe Usage
Fichier entier @fichier Inclure tout le contenu
Plage de lignes @fichier:L1-L2 Cibler une section precise
Repertoire @dossier/ Vue d’ensemble du projet
CLAUDE.md Fichier a la racine Contexte permanent automatique

Erreurs courantes et solutions

Erreur Cause Solution
“File not found” Chemin relatif incorrect Verifiez le repertoire courant
Contenu tronque Fichier trop gros Utilisez les plages de lignes
@-mention ignoree Pas d’espace avant le @ Ecrivez texte @fichier

Points cles a retenir

  1. Les @-mentions economisent du temps et des tokens
  2. Les plages de lignes sont essentielles pour les gros fichiers
  3. CLAUDE.md est votre meilleur allie pour le contexte projet
  4. En mode -p, les chemins sont relatifs au repertoire courant

Prochaine étape

Dans le notebook suivant, nous decouvrirons les agents (Explore, Plan) et les subagents.

-> 04-Claude-CLI-Agents.ipynb

Retour au sommet