Instabilité des tests automatisés de l’interface utilisateur

Écrit par Virginie Rochat

Article realesed - site web (1)

Qu’est-ce qu’un test instable ?

Un test instable – souvent appelé flaky test – est un test automatisé quigénère des résultats incohérents, sans raison apparente. Ces tests sont connus pour leur imprévisibilité, car ils peuvent échouer ou réussir par intermittence sans qu’aucune modification ni de code ni de l'application testée n’ait été effectuée, générant alors de faux négatifs ainsi que de potentielles fausses réussites :

Publication d'articles (6)

En résumé, les tests flaky sont des tests quiparfois réussissent et parfois échouent, sans qu'aucune modification ne soit apportée au code de productionou des scripts de test. Une enquête menée en 2024 par Dorothy Graham​ [1]​ a mis en évidence que l’instabilité (ou flakiness) figure toujours dans le top 4 des plus gros problèmes liés à l'automatisation des tests. D'une manière générale, les tests d'automatisation de l'interface utilisateur sont considérés comme :

  • Instables
  • Fragiles
  • Peu fiables
  •  
  • Présentant des échecs non déterministes inexpliqués

L'automatisation des tests a son propre paradoxe ; en effet lorsque l’on exécute des tests automatisés, ce sont en fait deux choses qui sont testées simultanément : 

  1. Le système testé, ou en anglais le System Under Test (SUT)
  2. Le code/script d'automatisation des tests

Sachant cela, comment peut-on établir la fiabilité de la solution d'automatisation? C'est simple : en l'exécutant de  multiples fois sur le SUT.

Des tests instables, c’est mieux que pas de test du tout… non ?

L'hypothèse générale de départ est qu'un test instable c’est toujours mieux que de n’avoir aucun test. Si un test peut réussir 99 % du temps, il peut empêcher l’apparition de régressions la plupart du temps. Cette hypothèse semble raisonnable, jusqu'à ce que l’on fasse le calcul :

Scénario 1

  • Suite de tests comportant 300 tests
  • Chaque test a un taux d’échec de 0.5% → taux de réussite individuel = 99.5%
  • Quel est l'impact global de cette mesure sur l'ensemble de la série de tests ?

Taux de réussite de la suite de tests = (99.5%)300 = 22.2%

Scénario 2

  • La même suite de tests avec 300 tests
  • Chaque test a un taux d’échec de 0.2% → taux de réussite individuel = 99.8%
  • Quel est l'impact global de cette mesure sur l'ensemble de la série de tests ?

Taux de réussite de la suite de tests = (99.8%)300 = 54.8%

Dans le premier scénario, cela signifie que les ¾ du temps, la suite de tests échouera sans raison apparente ! C’est évidemment loin d’être idéal, et il est important de garder à l’esprit que plus il y a de tests dans la suite de tests, plus le taux de réussite global sera faible…

Le deuxième scénario met en évidence qu’une diminution de 0,3 % du taux d’échec individuel des tests permet de réduire de plus de deux fois l’inconsistance globale !

Maintenant, la question est de savoir si l’évaluation initiale selon laquelle un flaky test vaut mieux qu’aucun test est correcte (alerte spoiler : ce n’est pas le cas !), et pour cela il faut s’intéresser à tous les impacts potentiels de telles inconsistances :

Publication d'articles (5)

L'impact est en effet massif et conduira finalement (mais inévitablement) à la conclusion que les tests d'interface utilisateur automatisés ne valent rien.

Donc, pour répondre à la question posée dans le chapitre précédent, nous pouvons dire en toute sécurité qu'en fait, un test instable est PIRE que pas de test !

Cette incohérence est-elle vraiment aléatoire ? Ou y a-t-il une cause?

Dans la presque totalité des cas, la « bancalité » d’un test n’est pas sans raison, et cette incohérence découle d’une cause concrète : il faut examiner ces erreurs, trouver la cause et résoudre le problème initial!

Les causes les plus courantes d’instabilité sont les suivantes :

  1. Conception et design du test :l’une des raisons les plus courantes d’instabilité provient en fait d’un mauvais design ! L’instabilité peut survenir en raison de problèmes liés à des stratégies de localisation incorrectes (comme l'identification d'un bouton par son texte interne lorsque ce dernier est dynamique) ou à des assertions manquantes.
  2. Problèmes de timing et de synchronisation : les instabilités sont également très courantes lorsqu'il est nécessaire d'assurer une synchronisation appropriée entre les phases de test (la page Web n'est pas encore entièrement chargée lorsque le test est exécuté), ou lorsque des dépendances temporelles existent (le test échoue parce que le SUT prend plus de temps que prévu à charger)
  3. Facteurs environnementaux : de nombreux facteurs environnementaux peuvent conduire un test à échouer alors qu'il ne le devrait pas, tels que des problèmes de connectivité réseau, des fluctuations des ressources système (mémoire, CPU), des dépendances vis-à-vis des API ou des services tiers, etc.
  4. Environnement de test instable : si l'environnement de test est instable, les tests le sont aussi... Par environnement de test instable, on peut entendre un environnement de test inégal (comme des versions de navigateur ou de système d'exploitation différentes), une configuration inadéquate (comme des paramètres de chemin incorrects ou des dépendances/bibliothèques manquantes), une infrastructure de test peu fiable ou une variation partielle de la configuration de test dans l'environnement.
  5. Attentes asynchrones : une gestion inappropriée des attentes et des opérations asynchrones – telles que les requêtes réseau ou les mises à jour de l'interface utilisateur – peuvent introduire des conditions de concurrence et des problèmes de synchronisation.
  6. Concurrence des opérations : une déclaration inappropriée sur l'ordre dans lequel les différentes opérations s’applique peut également être cause d’inconsistances.

Prévenir l’instabilité des tests

S’il y a une cause dans le fait qu’un test échoue alors qu’il ne le devrait pas, alors il est possible d’agir en amont et de rendre les scripts de tests automatisés robustes. Voici quelques conseils et éléments auxquels il faut prêter attention afin de limiter et gérer cette instabilité dès le départ :

  • Ajuster et vérifier l’ordre des opérations permet de diminuer la concurrence et de réduire les dépendances (tests atomiques). En ordonnant soigneusement les actions d’un test, il est possible de contrôler les probabilités de conditions ou de conflits susceptibles d'entraîner des défaillances.
  • Créer un environnement d'essai stable et cohérenten s’assurant que les facteurs externes (comme les ressources système ou la connectivité réseau) soient contrôlés, que les dépendances soient gérées et que l’accessibilité des ressources essentielles à la mise en œuvre des tests soit confirmée.
  • Prendre le temps de réfléchir à la stratégie de test avant la mise en œuvre, car comme mentionné précédemment, un test mal écrit, une mauvaise stratégie de test et une mauvaise conception de test sont des facteurs majeurs d’instabilité. Il est crucial de commencer par une compréhension approfondie du SUT, puis d'introduire des conventions de nommage ainsi que des règles de bonnes pratiques pour la rédaction des tests.
  • Favoriser la culture du retourfeedback : mise en place d’une surveillance continue des résultats, recueil des retours de l'équipe d'assurance qualité. Il est important d’encourager les testeurs à signaler toutes les instabilités rencontrées, de les examiner régulièrement et de prendre des mesures proactives pour les résoudre.
  • Utiliser des techniques de synchronisation appropriéesdans les scripts de tests automatisés ou dans l'outil de test pour confirmer la synchronisation appropriée entre le SUT et la phase de test ; cela peut se faire au moyen d’attentes explicites, des conditions d'attente ou des méthodes de synchronisation.
  • Optimiser le timing des tests en planifiant les exécutions tout en tenant compte de facteurs tels que la congestion du réseau, la charge du système, etc. qui pourraient influencer la fiabilité des tests.
  • Mettre en place des pratiques de gestion des données de test ppropriées pour conserver la fiabilité et la cohérence ; éviter d'utiliser des données de test mutables ou partagées qui peuvent entraîner une instabilité.
  • Isoler les tests en réduisant les dépendances , et diminuez les risques d'interférences entre les tests.

Points clés

  • Ne tombez pas dans le piège de prendre l’habitude que vos tests automatisés échouent sans raison apparente !
  • Apprendre de l'échec : l'ingénierie est une hypothèse ; un échec est le point de départ d'unemeilleure hypothèse.
  • Ne pas cacher l'échec, mais étudiez-le et améliorez-vous
  • L’instabilité découle presque toujours d’une cause concrète : il faut examiner les erreurs, trouver la cause et résoudre le problème initial!
  • Si vous ne parvenez pas à trouver la cause première de l'échec, votre meilleure option est de collecter davantage de preuves de la défaillance
  • Investiguer l’instabilité des tests est une chance de mieux comprendre à la fois le SUT ainsi que votre framework de tests automatisés !
Instabilité des tests automatisés de l’interface utilisateur-Image3

Références

Graham, Dorothy. 2024. "Test Automation Community Survey". AutomationSTAR. https://automation.eurostarsoftwaretesting.com/wp-content/uploads/2024/10/AS-Test-Automation-Community-Survey-Results-Rev02.pdf?utm_source=testguild&utm_campaign=promo&utm_medium=post.