Un test de contrat vérifie que deux logiciels continuent à respecter le format et le comportement convenus pour leurs échanges.
Une intégration peut fonctionner pendant des mois, puis échouer après une modification d’un champ, d’un statut ou d’un code d’erreur. Les tests unitaires de chaque application ne voient pas toujours cette rupture. Le test de contrat observe l’accord entre le fournisseur et le consommateur de l’API.
Le contrat doit décrire les requêtes, les réponses, les règles d’authentification, les erreurs et les changements compatibles. Une documentation générique ne suffit pas si elle ne précise pas les cas réellement utilisés par l’entreprise.
Identifier le fournisseur et le consommateur
Le fournisseur expose une API et promet un comportement. Le consommateur envoie des requêtes et utilise certaines données. Dans un échange bidirectionnel, une application peut jouer les deux rôles selon la route. Écrivez cette relation pour chaque contrat afin de savoir qui valide une modification.
Listez les opérations utilisées, les champs lus et les valeurs réellement attendues. Un champ optionnel dans la documentation peut être indispensable au consommateur. À l’inverse, un champ renvoyé mais ignoré ne doit pas bloquer une évolution si sa présence n’est pas garantie.
Conservez quelques exemples anonymisés représentatifs. Ils doivent couvrir une réponse ordinaire, une collection vide, une erreur d’autorisation et une erreur de validation. Les données de test doivent éviter les identifiants ou informations appartenant à de vrais clients.
Tester le format et les règles
Le schéma vérifie les types, les champs obligatoires, les valeurs autorisées et les formats. Les tests doivent aussi vérifier la sémantique. Un montant en centimes et un montant en dirhams peuvent partager un type numérique tout en ayant une signification différente.
Les dates demandent une règle précise : fuseau, précision et événement représenté. Les identifiants doivent indiquer leur format et leur stabilité. Une valeur qui change de sens selon la version crée une erreur difficile à repérer dans un simple test de structure.
Les erreurs font partie du contrat. Documentez le code, le message destiné au support et l’action attendue du consommateur. Un code générique ne doit pas être utilisé pour distinguer une permission refusée, une ressource absente et une validation impossible si le consommateur doit réagir différemment.
Exécuter les tests dans le cycle de livraison
Le consommateur peut publier son contrat attendu. Le fournisseur exécute ces attentes avant une mise en production. Cette approche permet de repérer une modification incompatible avant que les deux équipes déploient des versions différentes.
Pour une API externe, utilisez un environnement de test ou un simulateur contrôlé. Le test ne doit pas créer de vrais paiements, envoyer des notifications à des clients ou supprimer des dossiers. Les clés de test doivent être séparées des clés de production.
Un test peut vérifier la présence d’un champ sans imposer une égalité complète de la réponse. Les fournisseurs ajoutent parfois des champs compatibles. Le consommateur doit ignorer ce qu’il ne connaît pas et ne dépendre que des éléments promis.
La vérification doit produire un résultat lisible. Indiquez la route, la version, l’exemple et la différence observée. Un message « contrat invalide » oblige l’équipe à refaire l’enquête. Conservez le lien vers le changement de code ou la décision qui explique une nouvelle version.
Gérer la compatibilité
Un nouveau champ facultatif peut être compatible. Supprimer un champ obligatoire, changer son type ou modifier la signification d’un statut demande une stratégie. Ajoutez une version, maintenez une période de transition ou adaptez le consommateur avant la suppression.
Les changements de base et les changements d’API doivent être coordonnés. Un fournisseur qui expose une donnée après une migration progressive doit fonctionner avec l’ancien schéma pendant la période prévue. Le plan de retour arrière d’un déploiement doit inclure cette coexistence.
Une version d’API ne résout pas tout. Il faut indiquer la durée de support, la date de retrait et le comportement des clients qui n’ont pas migré. Une version provisoire qui reste sans propriétaire devient une deuxième interface à maintenir.
Tester les limites opérationnelles
Le contrat peut préciser les limites de taille, de débit et de pagination. Testez une collection vide, une page complète, une dernière page et une reprise après délai. Vérifiez le comportement lorsqu’un client répète la même requête ou demande un curseur expiré.
Les reprises sont sûres seulement si les opérations d’écriture supportent une clé d’idempotence ou une vérification équivalente. Cette exigence doit apparaître dans le contrat et dans les scénarios de test, avec une réponse stable pour une répétition déjà traitée.
Surveillez les échecs de contrat en production, sans journaliser les données sensibles. Une hausse des erreurs peut venir d’un nouveau consommateur, d’une modification non documentée ou d’un certificat arrivé à expiration. Le suivi technique doit être relié à l’opération métier qui a été interrompue.
Documenter la responsabilité
Chaque contrat doit avoir un propriétaire et un canal d’escalade. Une équipe valide les changements, une autre applique la migration et une procédure indique comment revenir à une version supportée. La spécification d’API partenaire peut regrouper ces informations.
Les tests de contrat ne remplacent pas les tests de bout en bout. Ils vérifient l’interface et le comportement convenu. Un test de bout en bout vérifie ensuite qu’une commande complète, une notification ou un export produit le résultat attendu dans l’ensemble du système.
Un contrat bien testé réduit les surprises parce qu’il transforme les hypothèses d’intégration en règles vérifiables. L’équipe sait ce qui peut évoluer librement, ce qui exige une transition et qui doit décider lorsqu’un besoin change.
Sources : Pact, documentation sur les tests de contrat, OpenAPI Initiative, spécification.