← Accueil / Exemples

Claude en action

Ce que Claude fait concrètement quand tu lui donnes une vraie tâche. Clique sur un filtre pour voir par catégorie.

Java SQL MongoDB Revue de code Git
Java Corriger une NullPointerException
Toi
J'ai cette erreur et je comprends pas d'ou ca vient :
Exception in thread "main" java.lang.NullPointerException at EtudiantDAO.getAll(EtudiantDAO.java:34) at Main.main(Main.java:12)
Mon code :
public List<Etudiant> getAll() { List<Etudiant> liste; while (rs.next()) { liste.add(new Etudiant(rs.getString("nom"))); } return liste; }
Claude
Le problème est ligne 2 : liste est déclarée mais jamais initialisée. Java la voit comme null, et appeler null.add(...) provoque la NPE.
// Avant — liste vaut null List<Etudiant> liste; // Après — initialise la liste vide List<Etudiant> liste = new ArrayList<>();
Règle : en Java, déclarer une variable ne l'initialise pas. Toujours faire = new ArrayList<>() avant de l'utiliser.
SQL Ecrire une requête avec note moyenne
Toi
Je veux lister tous les étudiants avec leur note moyenne. Même ceux qui n'ont encore aucune note doivent apparaître dans les résultats.
Claude
Il faut un LEFT JOIN pour garder les étudiants sans notes (un INNER JOIN les exclurait).
SELECT e.nom, e.prenom, ROUND(AVG(n.valeur), 2) AS moyenne FROM etudiants e LEFT JOIN notes n ON n.etudiant_id = e.id GROUP BY e.id, e.nom, e.prenom ORDER BY moyenne DESC; -- Résultat : étudiants sans notes → moyenne NULL -- ROUND(..., 2) → arrondi à 2 décimales
MongoDB Top 5 produits les plus commandés
Toi
Je veux les 5 produits les plus vendus ce mois-ci, avec leur total de quantités commandées.
Claude
Voici l'agrégation pipeline, étape par étape :
db.commandes.aggregate([ // 1. Filtre sur le mois en cours { $match: { date: { $gte: new Date("2026-04-01") } }}, // 2. Déroule le tableau produits { $unwind: "$produits" }, // 3. Groupe par nom de produit { $group: { _id: "$produits.nom", total: { $sum: "$produits.quantite" } }}, // 4. Trie par total décroissant { $sort: { total: -1 } }, { $limit: 5 } ])
Revue de code Détecter les problèmes dans une méthode Java
Toi
Relis cette méthode, dis-moi ce qui va pas :
public void saveEtudiant(String nom, String email) { try { Statement stmt = conn.createStatement(); stmt.execute("INSERT INTO etudiants VALUES ('" + nom + "','" + email + "')"); } catch (Exception e) {} }
Claude
3 problèmes critiques :
// PROBLÈME 1 — Injection SQL // Tu concatènes directement les variables dans la requête. // Quelqu'un peut passer : nom = "x'); DROP TABLE etudiants;--" // FIX : utilise PreparedStatement // PROBLÈME 2 — catch vide // Les erreurs SQL sont silencieuses. Tu ne sauras jamais si ça plante. // FIX : au minimum logger l'exception // PROBLÈME 3 — Statement non fermé // Fuite de ressources à chaque appel. // FIX : try-with-resources // Version corrigée : public void saveEtudiant(String nom, String email) throws SQLException { String sql = "INSERT INTO etudiants (nom, email) VALUES (?, ?)"; try (PreparedStatement ps = conn.prepareStatement(sql)) { ps.setString(1, nom); ps.setString(2, email); ps.executeUpdate(); } }
Java Expliquer le polymorphisme
Toi
/explain le polymorphisme en Java
Claude
En une phrase : un même appel de méthode peut produire des résultats différents selon le type réel de l'objet.

Analogie : une télécommande universelle. Tu appuies sur "volume+" : peu importe si c'est une TV Samsung ou LG, chacune réagit à sa façon.
// Classe parent abstract class Animal { abstract void parler(); } class Chien extends Animal { void parler() { System.out.println("Woof !"); } } class Chat extends Animal { void parler() { System.out.println("Miaou !"); } } Animal a = new Chien(); a.parler(); // → "Woof !" a = new Chat(); a.parler(); // → "Miaou !" — même appel, résultat différent
Piège classique : oublier @Override. Java appelle alors la méthode du parent sans erreur, et tu te demandes pourquoi ton code "ne fait rien".
Git Commit + push + PR en une commande
Toi
/commit-push-pr
Claude
Analyse des changements... 3 fichiers modifiés : EtudiantDAO.java +68 -0 Main.java +12 -3 schema.sql +15 -0 Commit créé : feat(etudiant): add DAO with full CRUD operations - EtudiantDAO : findAll, findById, save, delete - PreparedStatement sur toutes les requêtes SQL - try-with-resources pour fermer les connexions Push vers origin/main... OK PR ouverte : #12 "feat(etudiant): add DAO with full CRUD" → github.com/jibril/projet-java/pull/12
Java Convertir en try-with-resources
Toi
Ce code ne ferme pas la connexion proprement. Réécris-le correctement.
Connection conn = DriverManager.getConnection(url, user, pass); PreparedStatement ps = conn.prepareStatement(sql); ResultSet rs = ps.executeQuery(); // ... traitement ... rs.close(); ps.close(); conn.close();
Claude
Le problème avec les close() manuels : si une exception est levée avant, la connexion reste ouverte. try-with-resources ferme automatiquement, même en cas d'erreur.
try ( Connection conn = DriverManager.getConnection(url, user, pass); PreparedStatement ps = conn.prepareStatement(sql); ResultSet rs = ps.executeQuery() ) { // ... traitement ... } catch (SQLException e) { logger.error("Erreur DB", e); } // conn, ps, rs fermés automatiquement ici
SQL Optimiser une requête lente
Toi
Cette requête prend 3 secondes sur 10 000 lignes, c'est trop lent :
SELECT * FROM commandes WHERE statut = 'en_attente' AND date_creation > '2026-01-01';
Claude
La requête fait un full table scan parce qu'il n'y a pas d'index sur les colonnes du WHERE. Ajoute un index composé dans le bon ordre :
-- Index composé (statut d'abord, date ensuite) -- Ordre important : filtre d'égalité AVANT filtre de range CREATE INDEX idx_commandes_statut_date ON commandes (statut, date_creation); -- Vérifie que MySQL utilise l'index : EXPLAIN SELECT * FROM commandes WHERE statut = 'en_attente' AND date_creation > '2026-01-01'; -- Colonne "key" doit afficher : idx_commandes_statut_date
✦ Capacités Générer une classe entière depuis zéro
Toi
Crée un EtudiantDAO complet avec findAll, findById, save et delete. Table : etudiants(id, nom, email, date_inscription).
Claude
public class EtudiantDAO { private final Connection conn; public EtudiantDAO(Connection conn) { this.conn = conn; } public List<Etudiant> findAll() throws SQLException { List<Etudiant> list = new ArrayList<>(); try (Statement st = conn.createStatement(); ResultSet rs = st.executeQuery("SELECT * FROM etudiants")) { while (rs.next()) list.add(map(rs)); } return list; } public Optional<Etudiant> findById(int id) throws SQLException { try (PreparedStatement ps = conn.prepareStatement( "SELECT * FROM etudiants WHERE id = ?")) { ps.setInt(1, id); try (ResultSet rs = ps.executeQuery()) { return rs.next() ? Optional.of(map(rs)) : Optional.empty(); } } } public void save(Etudiant e) throws SQLException { try (PreparedStatement ps = conn.prepareStatement( "INSERT INTO etudiants (nom, email) VALUES (?, ?)", Statement.RETURN_GENERATED_KEYS)) { ps.setString(1, e.getNom()); ps.setString(2, e.getEmail()); ps.executeUpdate(); try (ResultSet keys = ps.getGeneratedKeys()) { if (keys.next()) e.setId(keys.getInt(1)); } } } public void delete(int id) throws SQLException { try (PreparedStatement ps = conn.prepareStatement( "DELETE FROM etudiants WHERE id = ?")) { ps.setInt(1, id); ps.executeUpdate(); } } private Etudiant map(ResultSet rs) throws SQLException { return new Etudiant( rs.getInt("id"), rs.getString("nom"), rs.getString("email"), rs.getDate("date_inscription") ); } }
70 lignes, zéro copier-coller, tout suit les conventions du projet.
✦ Capacités Concevoir un schéma de base de données
Toi
Conçois le schéma SQL pour une appli de bibliothèque : livres, membres, emprunts. Avec les contraintes et les index utiles.
Claude
CREATE TABLE livres ( id INT PRIMARY KEY AUTO_INCREMENT, titre VARCHAR(255) NOT NULL, auteur VARCHAR(150) NOT NULL, isbn VARCHAR(13) UNIQUE NOT NULL, disponible BOOLEAN DEFAULT TRUE ); CREATE TABLE membres ( id INT PRIMARY KEY AUTO_INCREMENT, nom VARCHAR(100) NOT NULL, email VARCHAR(150) UNIQUE NOT NULL, inscrit_le DATE DEFAULT (CURDATE()) ); CREATE TABLE emprunts ( id INT PRIMARY KEY AUTO_INCREMENT, livre_id INT NOT NULL, membre_id INT NOT NULL, emprunte_le DATE NOT NULL DEFAULT (CURDATE()), retour_prevu DATE NOT NULL, rendu_le DATE, FOREIGN KEY (livre_id) REFERENCES livres(id), FOREIGN KEY (membre_id) REFERENCES membres(id) ); -- Index pour les recherches fréquentes CREATE INDEX idx_emprunts_membre ON emprunts (membre_id); CREATE INDEX idx_emprunts_retour ON emprunts (retour_prevu) WHERE rendu_le IS NULL; -- index partiel : que les emprunts actifs
✦ Capacités Refactoriser du code illisible
Toi
Ce code marche mais c'est illisible. Refactorise sans changer le comportement.
public String f(List<String> l, String s) { String r = ""; for (int i = 0; i < l.size(); i++) { if (l.get(i) != null && l.get(i).contains(s)) { r = r + l.get(i) + ","; } } if (r.length() > 0) r = r.substring(0, r.length() - 1); return r; }
Claude
4 problèmes : noms illisibles, concaténation dans une boucle (O(n²)), null check manuel, suppression du dernier caractère à la main. Version refactorisée :
/** * Filtre les éléments contenant le mot-clé * et les rejoint par des virgules. */ public String joinMatching(List<String> items, String keyword) { return items.stream() .filter(item -> item != null && item.contains(keyword)) .collect(Collectors.joining(",")); }
8 lignes → 4. Même comportement. Lisible, performant, idiomatique Java 8+.
Prêt à l'utiliser ?

Installe le kit et commence en 5 minutes

Le student kit inclut tout ce qu'il faut : CLAUDE.md préconfiguré, skills Java/SQL/MongoDB, sous-agents et hooks de sécurité automatiques.