PHPUnit vs Pest : tester une application Laravel
Pest tourne au-dessus de PHPUnit, donc le choix porte sur la syntaxe et le workflow, pas sur le moteur. Voici ce que chacun apporte, à quoi ressemble un test Laravel dans les deux, et comment décider.
PHPUnit est le framework de test PHP standard : basé sur des classes, conventions xUnit, partout. Pest est une couche au-dessus avec une syntaxe basée sur des fonctions, une API d'expectations, et des extras comme les tests d'architecture. Comme Pest utilise le moteur PHPUnit en dessous, le choix porte sur la façon d'écrire et d'organiser les tests, pas sur la capacité ou la vitesse. Laravel supporte les deux par défaut.
PHPUnit vs Pest en un coup d'oeil
| Aspect | PHPUnit | Pest |
|---|---|---|
| Style de test | Classes étendant TestCase, méthodes de test | Fonctions it() / test(), expectations |
| Courbe d'apprentissage | Familière à tout développeur PHP | Rapide, surtout depuis le test JS (façon Jest) |
| Laravel | Supporté, le défaut historique | Supporté, le défaut des nouveaux projets Laravel |
| Assertions | Méthodes assert*() | API fluide expect() (assert*() reste disponible) |
| Tests d'architecture | Non | Oui, règles arch() sur votre codebase |
| Datasets / paramétrage | Méthodes data provider | Datasets with(), inline ou partagés |
| Moteur sous-jacent | PHPUnit | PHPUnit |
PHPUnit : basé sur des classes et ubiquitaire
Un test PHPUnit est une classe qui étend le TestCase du framework, avec des méthodes nommées test* ou annotées comme tests. C'est verbeux, mais chaque développeur PHP et chaque système de CI le connaissent déjà, le support IDE est complet, et il y a une décennie d'exemples pour n'importe quel scénario. Pour une équipe qui vit dans PHPUnit, il n'y a aucune raison forcée de bouger.
Pest : des fonctions et des expectations
Pest remplace la classe par des fonctions it() et test() de haut niveau et les appels assert*() par une API chaînable expect(). Les datasets paramètrent un test sans méthode data provider, les expectations d'ordre supérieur se chaînent naturellement, et arch() vous laisse affirmer des règles sur votre propre code (pas de helpers de debug en production, les contrôleurs ne dépendent pas directement des modèles). Ça se lit bien et ça coupe le boilerplate.
Le même feature test Laravel, des deux façons
// PHPUnit
public function test_il_liste_les_commandes_de_l_utilisateur(): void
{
$user = User::factory()->has(Order::factory()->count(2))->create();
$this->actingAs($user)
->getJson('/api/v1/orders')
->assertOk()
->assertJsonCount(2, 'data');
}
// Pest
it('liste les commandes de l utilisateur', function () {
$user = User::factory()->has(Order::factory()->count(2))->create();
$this->actingAs($user)
->getJson('/api/v1/orders')
->assertOk()
->assertJsonCount(2, 'data');
});Migrer PHPUnit vers Pest
Ils coexistent dans la même suite : Pest exécute vos classes PHPUnit existantes sans changement, donc vous pouvez l'adopter pour les nouveaux tests et convertir les anciens progressivement, ou pas du tout. Il y a aussi un outil de conversion qui réécrit les patterns courants. Aucune migration big-bang n'est requise.
Ce qui compte vraiment
Le framework est un petit facteur à côté du fait d'avoir des tests, de savoir s'ils couvrent les parties risquées, et s'ils tournent assez vite pour que les gens les lancent. Une app bien testée en PHPUnit bat une app peu testée en Pest à chaque fois. Prenez la syntaxe que votre équipe aimera écrire, parce que c'est ça qui pilote la couverture.
FAQ
- Pest ou PHPUnit pour un nouveau projet Laravel ?
- Pest est le défaut des nouvelles applications Laravel et sa syntaxe coupe le boilerplate, donc c'est un choix raisonnable sauf si votre équipe est profondément investie dans les conventions PHPUnit. Les deux utilisent le même moteur, donc vous n'échangez ni capacité ni vitesse, seulement le style.
- Peut-on utiliser Pest et PHPUnit ensemble ?
- Oui. Pest exécute les classes de test PHPUnit sans changement dans la même suite, donc vous pouvez ajouter des tests Pest à côté des existants et convertir progressivement ou les laisser. Il n'y a aucune obligation de tout migrer.
- Pest est-il plus lent que PHPUnit ?
- Pas de façon significative. Pest s'exécute sur le moteur PHPUnit, donc le temps d'exécution est essentiellement le même. La vitesse des tests est pilotée par ce que font vos tests (base de données, HTTP, factories), pas par la couche de syntaxe utilisée pour les écrire.
- Qu'est-ce qu'un test d'architecture avec Pest ?
- Une assertion arch() vérifie des règles sur votre codebase plutôt que son comportement à l'exécution : qu'un namespace n'a pas de helpers de debug, que les contrôleurs n'importent pas les modèles directement, que les value objects sont final. Ça attrape la dérive structurelle en CI sans écrire une règle d'analyse statique custom.
- Faut-il migrer de PHPUnit vers Pest ?
- Seulement si l'équipe veut la syntaxe. Il n'y a aucun gain fonctionnel qui force une migration, et ils coexistent, donc le chemin pragmatique est d'écrire les nouveaux tests en Pest si vous l'aimez et de laisser les tests PHPUnit existants tant que vous n'avez pas de raison d'y toucher.
PHPUnit et Pest sont le même moteur avec une ergonomie différente. PHPUnit est le défaut sûr et universel ; Pest échange un peu de familiarité contre moins de boilerplate et les tests d'architecture. L'un ou l'autre convient. Ce qui compte, c'est que la suite existe, couvre le code risqué, et tourne assez vite pour que l'équipe continue de la lancer.
Besoin d'aide sur ce sujet ? Développement Full Stack
Découvrir ce service →