Tester l'écart entre l'unité et l'intégration: intégration dans les tests d'intégration petits, composants et unitaires

9

Au cours des dernières semaines, j'ai réfléchi et recherché comment combler une lacune dans notre méthodologie de test. En termes simplifiés, les tests unitaires sont trop petits et les tests d'intégration traditionnels sont trop grands.

Un scénario fréquent se présente où Aet les Bdeux utilisent le composant C. Cependant Aet Bont des exigences légèrement différentes pour, et font des hypothèses légèrement différentes sur C. Si je suis le développeur de Acomment et où dois-je tester mes hypothèses C?

De toute évidence, les tests unitaires Aavec des hypothèses simulées Csont corrects pour les tests Ade manière isolée, mais ils ne testent pas les hypothèses elles-mêmes.

Une autre possibilité consiste à ajouter des tests unitaires pour C. Cependant, ce n'est pas idéal car, Aen cours de développement, la modification des tests Cavec des hypothèses évolutives Asera excessivement maladroite. En effet, Ale développeur peut ne pas même avoir un accès adéquat aux tests unitaires de C(par exemple une bibliothèque externe).

Pour encadrer cela avec un exemple plus concret: Supposons qu'il s'agit d'une application de nœud. A, et Bdépendent Cde la lecture d'un fichier (entre autres) et du stockage du contenu du fichier dans l'objet transmis à C. Au début, tous les fichiers qui Csont gérés sont petits et peuvent être lus de manière synchrone sans blocage significatif. Cependant, le développeur de se Brend compte que ses fichiers deviennent énormes et doit passer Cà une lecture asynchrone. Il en résulte un bogue de synchronisation sporadique A, qui suppose toujours la Clecture des fichiers de manière synchrone.

Il s'agit du type de bogue qui est notoirement difficile à détecter à partir des tests d'intégration complets et qui peut ne pas être détecté du tout dans les tests d'intégration. Il n'est pas non plus pris en compte par Ales tests unitaires car les Ahypothèses sont faussées. Cependant, il pourrait facilement être rattrapé par un "mini" test d'intégration qui s'exerce simplement Aet C.

Je n'ai trouvé que quelques références à ce type de test. Intégration dans les petites , tests d' intégration des composants , Unité de l' intégration de test. Il se rapporte également quelque peu à la direction des tests BDD plutôt qu'aux tests unitaires TDD formels.

Comment puis-je combler cette lacune de test? Plus précisément - où dois-je mettre ces tests? Comment se moquer des entrées de Aet Cpour les "mini" tests d'intégration? Et combien d'efforts devraient être déployés pour séparer les problèmes de test entre ces tests et les tests unitaires? Ou existe-t-il une meilleure façon de combler l'écart de test?

mjhm
la source
1
avez-vous envisagé de versionner les modules AC et d'utiliser une certaine forme de gestion des dépendances?
miraculixx
1
@gnat Merci pour l'astuce. J'ai rendu la question moins vague.
mjhm
@miraclixx Merci pour votre suggestion. Pourriez-vous élaborer? Si vous voulez dire quelque chose comme blog.nodejitsu.com/package-dependencies-done-right - je pense que cela résout un problème différent de celui que je pose. Les composants auxquels je fais référence sont généralement trop petits pour être utilisés indépendamment en tant que module de nœud - par exemple un fichier de composant de modèle ou de contrôleur. De plus, le contrôle de version ne donne que des conseils sur la sécurité et les sources de pannes, plutôt que des tests explicites pour des problèmes spécifiques.
mjhm

Réponses:

6

Il me semble que vous avez un problème fondamental avec vos composants.

C devrait faire ce que C doit faire et être testé, documenté et conçu pour faire exactement cela. Lorsque vous avez une situation où C est conçu pour «faire ce que B veut», vous avez une relation abusive, qui devient très claire lorsque A arrive et veut que C fasse quelque chose de légèrement différent.

Ce que vous ne devriez pas faire, c'est tester les unités C dans le contexte de A, et surtout pas A dans le contexte de C - vous testez A indépendamment, et vous fournissez les résultats d'un C simulé à A. Si la version réelle de C ne fournit pas ces mêmes résultats, alors vous avez un bug ou un défaut de conception dans C qui sera détecté lorsque vous effectuerez vos gros tests d'intégration. Les tests unitaires ont toujours été de cette façon - vous ne pouvez pas tester une unité en testant une autre unité en même temps. Les tests unitaires ne sont tout simplement pas conçus pour cela.

Les tests d'intégration ne doivent pas nécessairement être "l'ensemble du programme", bien qu'ils soient souvent configurés de cette façon. Ils peuvent être un banc d'essai qui exécute A et C ensemble sans exécuter le reste du programme (ou aussi peu que possible). À ce stade, je ne peux pas vous conseiller davantage car cela dépend de ce que font ces composants et de la façon dont ils interagissent avec le reste de votre programme, mais il est généralement possible d'écrire un banc de test qui fournit une couverture de test des deux composants. Que cela vaille la peine de le faire ou qu'il soit plus efficace de tester l'intégralité du programme en un seul (même si vous exécutez un sous-ensemble des tests d'intégration) est une question à laquelle vous seul pouvez répondre. La plupart des tests d'intégration sont composés de nombreuses sections, donc j'espère que vous devriez être en mesure d'exécuter uniquement celles pertinentes pour ces 2 composants (et sinon,

gbjbaanb
la source
Ouais, c'est un peu ce que je pense. Cela dépasse la portée et l'objectif des tests unitaires. Malheureusement, je ne vis pas dans un monde logiciel où les composants dépendants sont parfaitement conçus, testés et documentés. Et le peu de tests d'intégration dont nous disposons est généralement de bout en bout et géré par des spécialistes de l'assurance qualité, plutôt que par les développeurs source. Comme vous pouvez le deviner, il y a des problèmes de gestion et d'organisation dans le mélange.
mjhm
Je suppose que vous devrez ajouter vos propres tests d'intégration, mais les appeler des tests unitaires, « nous sommes unité tester le module de connexion client » que vous avez jusqu'à concombre ou le sélénium.
gbjbaanb