Blog ENI : Toute la veille numérique !
Accès illimité 24h/24 à tous nos livres & vidéos ! 
Découvrez la Bibliothèque Numérique ENI. Cliquez ici
💥 Du 22 au 24 novembre : Accès 100% GRATUIT
à la Bibliothèque Numérique ENI. Je m'inscris !

Le design pattern Data Driven Testing

Principe et avantages

Lors des tests fonctionnels, nous devons tester les interactions utilisateur relatives à la saisie de données. Ces interactions sont en général les plus importantes pour vérifier le bon comportement de notre application Web.

Jusqu’à présent, nous avons codé en dur les données que nos tests entrent dans les formulaires. Que se passe-t-il si un type de données change ou si son format change ? Nous devons parcourir nos classes et/ou nos scripts Pytest et modifier les valeurs de nos variables. C’est un long travail en termes de temps, ce n’est donc absolument pas productif en programmation et en maintenance.

Pour éliminer les longues heures de maintenance, pourquoi ne pas enregistrer les valeurs saisies lors des interactions utilisateur dans un endroit unique, facile d’accès et aisé à lire ?

C’est le principe du design pattern Data Driven Testing : stocker en dehors des programmes de test les valeurs qui seront utilisées pour simuler les interactions utilisateur et donc valider le comportement de notre application.

Nous pouvons utiliser le design pattern Data Driven Testing avec ou sans le design pattern Page Object Model car il ne concerne pas la modélisation des pages, mais juste le stockage des valeurs de test.

Comme le montre la figure ci-après, toutes les données texte et numériques...

Data Driven Testing avec POM et fichiers

Intégrons maintenant le design pattern Data Driven Testing dans notre application multipage sur laquelle nous travaillons depuis le chapitre Les waits pour une interaction optimale. Nos tests implémentent déjà le design pattern Page Object Model.

Les données que nous devons stocker pour tester cette application concernent le formulaire de la page d’accueil :

  • l’adresse électronique ;

  • le mot de passe ;

  • la civilité ;

  • le nom.

images/12EI03.png

Formulaire de notre application de démonstration

Nous ajoutons dans notre script JavaScript une règle pour valider le mot de passe : il doit contenir entre sept et quatorze caractères, avec au moins un chiffre.

var passPattern =  /^(?=.*\d)(?=.*[a-z])(?=.*[A-Z]).{7,14}$/;  
          var password = document.getElementById('pass');  
          if(! password.value.match(passPattern)) {  
                 // Changer la phrase par défaut du navigateur  
                 txtErreur += "Le mot de passe n'est pas valide. "; 
          } 

Notre jeu de données de test doit couvrir tous les cas possibles :

  • Toutes les entrées sont valides.

  • L’adresse de courriel n’est pas valide.

  • Le nom n’est pas valide.

  • La civilité est manquante.

  • Le mot de passe n’est pas valide.

Nous devons avoir deux jeux de test : un pour les données validant le formulaire et un deuxième pour celles qui ne permettent pas de valider le formulaire. En effet, nous devons tester deux comportements distincts avec deux fonctions de test différentes.

Nous prenons en compte dans nos tests la vérification de la politique de mot de passe en vérifiant qu’un mot de passe sans chiffre ou trop petit ou tout simplement manquant ne validera pas le formulaire.

Nous pouvons maintenant simplifier le comportement de notre classe contenant le formulaire, les données étant fournies par les tests :

import pytest  
from selenium import webdriver  
from selenium.webdriver.common.by import...

Data Driven Testing et BD

Commençons par créer une base de données testdatas pour enregistrer notre jeu de données de test. Au sein de cette base, nous allons créer une table formdatas et les colonnes nécessaires pour enregistrer un identifiant, une adresse électronique, un mot de passe, une civilité, un nom et un booléen pour indiquer si les données valident ou non le formulaire.

CREATE SCHEMA `testdatas` ;  
CREATE TABLE `testdatas`.`formdatas` (  
  `iddata` INT NOT NULL AUTO_INCREMENT,  
  `email` VARCHAR(255) NULL,  
  `pass` VARCHAR(45) NULL,  
  `civilite` VARCHAR(45) NULL,  
  `name` VARCHAR(45) NULL,  
  `valide` TINYINT NULL,  
  PRIMARY KEY (`iddata`)); 

Insérons maintenant notre jeu de données de test dans la table formdatas.

INSERT INTO `testdatas`.`formdatas` (`email`, `pass`, `civilite`, 
`name`, `valide`) VALUES ('ludi@ludi.fr', 'Azerty8', 'mme', 
'Ludivine', '1');  
INSERT INTO `testdatas`.`formdatas` (`pass`, `civilite`, `name`, 
`valide`) VALUES ('Azerty8', 'mme', 'Ludivine', '0');  
INSERT INTO `testdatas`.`formdatas` (`email`, `pass`, `valide`) 
VALUES ('ludi@ludi.fr', 'Azerty8', '0');  
INSERT INTO `testdatas`.`formdatas` (`email`, `pass`, `civilite`, 
`name`, `valide`) VALUES ('ludi@ludi.fr', 'Azerty8', '', 
'Ludivine', '0');  
INSERT INTO `testdatas`.`formdatas` (`email`, `pass`, `civilite`, 
`name`, `valide`) VALUES ('ludi@ludi.fr', 'Azer8'...

Data Driven Testing sans POM

Nous fournissons dans cette section un test fonctionnel avec le design pattern Data Driven Testing sans le design pattern Page Object Model pour le lecteur qui ne veut pas implémenter de design pattern. Notre démarche reste la même, nous chargeons au début notre jeu de données de test qui sera fourni aux fonctions de test liées au formulaire.

Nous stockons nos données de test dans un fichier CSV.

import pytest  
from selenium import webdriver  
from selenium.webdriver.common.by import By  
from selenium.webdriver.support.wait import WebDriverWait  
from selenium.webdriver.support import expected_conditions as EC  
from selenium.webdriver.common.action_chains import ActionChains  
import csv  
   
def initData(file) :  
    with open(file) as csvFile:  
          csv_reader = csv.reader(csvFile, delimiter=',')  
          datas = []  
          entete = True  
          for data in csv_reader :  
                 if entete :  
                        entete = False  
                 else :  
                        datas.append([data[0], data[1], data[2], 
data[3]])  
    print(datas)  
    return datas  
   
dataNop = initData('dataFormulaireConnexionNop.csv')...

Exercice

Ajoutez le design pattern Data Driven Testing aux tests de l’exercice du chapitre Le design pattern Page Object Model, afin d’avoir des tests complets respectant toutes les bonnes pratiques. Choisissez le support de stockage le plus intéressant pour vous.