Image de couverture : Cursor Rules pour PHP/Symfony : éviter les pièges des suggestions IA en 2026
tech

Cursor Rules pour PHP/Symfony : éviter les pièges des suggestions IA en 2026

27 April 2026
5 min de lecture
4 vues
Sébastien Muler

Quand l'IA reproduit les mauvaises pratiques du passé

Les assistants IA comme Cursor ou Claude Code sont devenus des compagnons quotidiens pour de nombreux développeurs PHP. Leur productivité est réelle — mais leur mémoire l'est aussi. Ces modèles ont été entraînés sur des années de code PHP et Laravel, y compris les patterns douteux des années 2015–2020 : contrôleurs obèses, $guarded = [] copié-collé depuis Stack Overflow, requêtes construites par concaténation de chaînes. Sans garde-fous explicites, l'IA reproduit fidèlement ces anti-patterns.

Cet article, inspiré d'un guide publié sur dev.to par Olivia Craft, propose une checklist de Cursor Rules adaptée à un contexte PHP/Symfony pour détecter et corriger ces dérives avant qu'elles n'atteignent la production.


Les trois anti-patterns que l'IA ressuscite systématiquement

1. Le problème N+1 et l'absence d'eager loading

C'est le classique. Une vue itère sur une collection d'entités et accède à une relation à chaque tour de boucle :

// ❌ Génère N+1 requêtes
$users = User::all();
foreach ($users as $user) {
    echo $user->company->name; // SELECT à chaque itération
}

// ✅ Une seule requête jointe
$users = User::with('company')->get();

L'IA suggère souvent la première version car elle est plus courte et syntaxiquement correcte. La règle à définir dans Cursor : toute relation accédée dans une boucle ou une vue doit être chargée en eager loading. Dans un contexte Symfony/Doctrine, le principe est identique avec les jointures dans le repository.

2. Mass-assignment et modèles trop permissifs

L'IA génère régulièrement des modèles avec $guarded = [] ou sans déclaration $fillable, ce qui expose potentiellement tous les champs à une assignation de masse. Un endpoint d'inscription qui accepte is_admin=1 dans le payload devient une faille critique.

// ❌ Tout est assignable
protected $guarded = [];

// ✅ Whitelist explicite
protected $fillable = ['name', 'email', 'password'];

Règle Cursor : chaque modèle doit déclarer explicitement $fillable. La liste doit être revue à chaque ajout de colonne. En Symfony avec des formulaires, le principe équivalent passe par allowedFields ou la validation stricte des DTOs.

3. Injection SQL par concaténation

Moins fréquent mais toujours présent dans les suggestions IA sur les requêtes dynamiques :

// ❌ Vulnérable à l'injection SQL
$results = DB::select("SELECT * FROM products WHERE name LIKE '%" . $search . "%'");

// ✅ Paramètre lié
$results = DB::select('SELECT * FROM products WHERE name LIKE ?', ["%$search%"]);

Règle Cursor : aucune variable utilisateur ne doit apparaître dans une chaîne SQL brute. Toujours utiliser les query builders ou les paramètres liés.


Intégrer l'analyse statique dans la boucle IA

Détecter ces problèmes manuellement à la revue de code est coûteux et peu fiable. La bonne pratique est d'automatiser la détection dès la phase de développement.

Larastan / PHPStan

Pour les projets Laravel, Larastan (wrapper PHPStan) analyse le code généré par l'IA avec une connaissance des classes et macros propres au framework. Pour Symfony, PHPStan seul avec les extensions adaptées couvre la même fonction.

# Installation
composer require --dev phpstan/phpstan
# ou pour Laravel
composer require --dev nunomaduro/larastan

# Lancement
./vendor/bin/phpstan analyse src --level=6

Objectif minimum : niveau 6. Les niveaux supérieurs activent des vérifications de types plus strictes qui réduisent les bugs générés par l'IA sur les nullables et les types de retour.

Intégration CI

Une règle Cursor non vérifiée en CI reste une intention. Le pipeline doit bloquer toute PR qui fait régresser le score PHPStan ou qui introduit des requêtes non-paramétrées détectées par des outils comme Rector ou un linter SQL custom.

# Exemple GitHub Actions
- name: PHPStan
  run: ./vendor/bin/phpstan analyse --error-format=github

- name: Tests
  run: php artisan test --coverage --min=80

L'objectif est que chaque suggestion de l'IA passe par le même filet que le code humain.


Définir des Cursor Rules efficaces : principes pratiques

Une Cursor Rule est une instruction persistante donnée à l'assistant dans le contexte du projet. Elle oriente les suggestions avant même que le développeur ne valide. Voici les règles fondamentales pour un projet PHP :

Domaine Règle à définir
Requêtes Toujours utiliser le query builder ou les paramètres liés
Relations Mentionner les eager loading nécessaires dans les commentaires de contexte
Modèles Déclarer $fillable explicitement, jamais $guarded = []
Types Typer strictement les retours de méthodes et les paramètres
Tâches longues Passer par une queue (email, export, webhook)
Tests Chaque méthode publique générée doit avoir un test unitaire correspondant

Ces règles se configurent dans le fichier .cursorrules à la racine du projet (pour Cursor) ou dans le système prompt de votre assistant maison.


Conclusion : l'IA amplifie vos standards, pas seulement votre vitesse

Les assistants IA sont des multiplicateurs de productivité — mais ils amplifient aussi bien les bonnes pratiques que les mauvaises. Sans Cursor Rules explicites et sans pipeline d'analyse statique, vous externalisez l'écriture du code tout en internalisant la dette technique qu'il génère.

La démarche est simple : définir les règles une fois dans le contexte projet, automatiser leur vérification en CI, et traiter les suggestions IA comme du code en revue — pas comme du code de confiance.

Pour aller plus loin, le guide original d'Olivia Craft sur dev.to détaille les configurations spécifiques à Laravel avec des exemples complets.

Partager cet article