Testez les interfaces de vos applications React avec Cypress

Illustration Cypress & React
Prérequis : Avoir installé Node.js pour la 1ère Méthode

Il est de plus en plus important d’assurer la qualité d’une application web, la mise en place de tests fonctionnels devient donc primordiale.

Qu’est-ce qu’un test fonctionnel?

Un test fonctionnel est un test qui permettra de tester automatiquement toutes les fonctionnalités de votre application étant demandé dans le cahier des charges.

Un test fonctionnel a donc pour objectif de dérouler un scénario composé d’une liste d’actions, et pour chaque action d’effectuer une liste de vérifications validant la conformité de l’exigence avec l’attendu.

Par exemple, on peut tester de voir que l’utilisateur peut bien se connecter, se déconnecter ou bien vérifier la véracité des informations dans un formulaire.

Cypress ?

Cypress est un outil open source permettant de créer des scénarios de tests, puis de les jouer sur différents navigateurs. Cet outil permet donc de tester des applications / services Web.

Pourquoi Cypress ?

C’est vrai, ils existent de nombreux concurrents à Cypress comme Jest ou bien Nightwatch. Pourquoi donc Cypress?

Pour commencer, le développement de tests fonctionnels est assez visuel avec Cypress grâce à son interface graphique. 

Cypress rend les tests plus faciles à écrire et plus rapide à exécuter comparé aux deux autres. Nous avons aussi, entre autres, accès à la liste des tests, le choix du navigateur et un récapitulatif de la configuration. Cypress fonctionne, quel que soit le framework JavaScript que vous utilisez : React Js, Angular, Vue Js,… .

Démonstration de Cypress exécutant une suite de tests prédéfinie

Le GIF ci-dessus montre l’exemple de spécification de test Cypress appelé «actions.spec.js». Vous pouvez voir que Cypress ouvre son propre navigateur, exécute vos tests et vous permet de sauter à n’importe quel point de l’historique des tests et de voir l’état de l’application tel qu’il était.

Pour finir, c’est grâce à cet environnement simple que j’ai pu apprendre à réaliser des tests fonctionnels, je le recommande fortement pour les débutants.

Installation de Cypress

Méthode npm

Pour commencer, vous utiliserez la commande suivante pour démarrer le processus d’installation de Cypress:

npm install cypress --save-dev

Cypress va alors s’installer dans votre projet dans les paquets de développement.

npx cypress open

npx est un outil inclus dans npm qui ira chercher le paquet “cypress” et l’exécutera.

Cette commande va ouvrir l’interface graphique de Cypress et vous rendre cette page :

Vous pouvez voir les exemples de base fournis par Cypress, il contient les différentes commandes de Cypress et il vous montre leurs utilisations.

Il n’est pas obligatoire de supprimer le dossier “examples”. Cependant, par soucis de lisibilité, il a été supprimé dans cet exemple.

L’interface graphique de Cypress une fois les tests d’exemple supprimés.

Méthode Direct Download

Si vous ne voulez ou ne pouvez installer Node.js, nous allons essayer une autre méthode, l’installation directe de Cypress dans votre projet.

Télécharger le zip de cypress sur : cypresse.io

Une fois obtenu, décompressez le fichier et exécutez l’application Cypress. Une fois Cypress lancé, vous devriez obtenir une interface similaire à celle-ci :

Vous pouvez maintenant faire glisser / sélectionner votre projet :

Mise en pratique de Cypress

Vous pouvez changer sur Cypress, le navigateur web :

Mise en place des tests fonctionnels

Lancez votre éditeur de code, nous allons faire pas à pas les tests fonctionnels.

Créer un fichier au format nomDuTest.test.js dans le répertoire integration.

Ainsi, vous pouvez voir que votre fichier de test est bien apparu dans Cypress :

Voici les différentes parties de Cypress quand on lance article.test.js :

0 – Paramétrage

Commençons : dès la première ligne, ajoutez cette la ligne de code suivante, permettant d’activer les fonctionnalités d’auto-complétion pour Cypress :

/// <reference types="Cypress" /> 

Voici le code que nous allons utiliser pour cet article.

<Fragment className="margin">
   <h1>Hello world</h1>
   <p className="text-test">Ce texte est bleu !</p>
   <button
      onClick={() =>
        this.setState({ buttonClicked: !this.state.buttonClicked })
      }
      className={this.state.buttonClicked ? "button-green" : "button-red"}
    >
      {this.state.buttonClicked ? "Activé" : "Désactivé}
    </button>
</Fragment>

Ainsi que le fichier CSS, pour connaître la couleur principalement.

.button-green {
  background-color: #4caf50; /* Green */
  border: none;
  color: white;
  padding: 8px 10px;
  text-align: center;
  text-decoration: none;
  display: inline-block;
  font-size: 16px;
  border-radius: 5px;
}

.button-red {
  background-color: #cf0a1d; /* Red */
  border: none;
  color: white;
  padding: 8px 10px;
  text-align: center;
  text-decoration: none;
  display: inline-block;
  font-size: 16px;
  border-radius: 5px;
}

.text-test {
  color: blue;
}

1 – Afficher la page

Pour afficher votre page sur cypress :

describe('Test de la page principale', () => {
    it('Affichage de la page', () => {
        //On se dirige vers notre page
        cy.visit('http://localhost:3000');
    }); 
});

La fonction describe() permettra l’organisation des tests dans un ensemble.
La fonction it() permettra de sous-développé les tests à exécuter.
La méthode « cy.visit » visite une URL.

Résultat :

2 – Vérifier le titre

Erreur de texte

it('Vérification du titre', () => {
        //On prend la balise h1
        cy.get('h1');
        //Erreur de texte
        cy.should(Titre => {
            expect(Titre).to.contain("Bonjour le monde");
        });
});

La méthode « cy.get » permet d’obtenir un ou plusieurs éléments DOM (la représentation des éléments).
La méthode « cy.should » décrit l’état souhaité de vos éléments, de vos objets et de votre application.
expect permet de vérifier que le texte correspond.

<h1>Hello world</h1>

Ce code entraîne une erreur, l’erreur est que la classe “h1” ne contient pas “Bonjour le monde” mais “Hello world”.

Correction

it('Vérification du titre', () => {
        //On prend la balise h1
        cy.get('h1');
        //On vérifie que le titre correspond bien
        cy.should(Titre => {
            expect(Titre).to.contain("Hello world");
        });
});

Résultat :

3 – Vérifier le texte

Erreur de couleur

it('Vérification du contenu du texte', () => {
        //On prend la balise "p.text-test" 
        cy.get('.text-test');
        //On vérifie que le texte correspond bien
        cy.should(Texte => {
            expect(Texte).to.contain("Ce texte est bleu !");
        });
});
    
it('Vérification de la couleur du texte', () => {
        //On prend la balise "p.text-test" 
        cy.get('.text-test');
        //Erreur de couleur, la couleur est bleu et non rouge
        cy.should('have.css', 'color', 'rgb(255, 0, 0)');
});
<p className="text-test">Ce texte est bleu !</p>
.text-test {
  color: blue;
}

Cette fois l’erreur est que je dis que la couleur du texte est rouge [rgb(255, 0, 0)], mais Cypress me dit que la couleur exacte du texte est bleue [rgb(0, 0, 255)].

Correction

it('Vérification du contenu du texte', () => {
        //On prend la balise "p.text-test" 
        cy.get('.text-test');
        //On vérifie que le texte correspond bien
        cy.should(Texte => {
            expect(Texte).to.contain("Ce texte est bleu !");
        });
});
    
it('Vérification de la couleur du texte', () => {
        //On prend la balise "p.text-test" 
        cy.get('.text-test');
        //On vérifie que la couleur du texte est bleu
        cy.should('have.css', 'color', 'rgb(0, 0, 255)');
});

Résultat :

4 – Vérifier le bouton

Erreur d’inattention

describe('Vérification du bouton', () => {
        it('Vérification du bouton', () => {
            //On prend la balise "button.button-red"
            cy.get('.button-red');
            //Erreur d'inattention
            cy.contains('Désactivés');
            //On vérifie que le texte dans le bouton est blanc
            cy.should('have.css', 'color', 'rgb(255, 255, 255)');
            //On vérifie que le fond du bouton est rouge
            cy.should('have.css', 'background-color', 'rgb(207, 10, 29)');
        });
});
<button
  onClick={() =>
    this.setState({ buttonClicked: !this.state.buttonClicked })
  }
  className={this.state.buttonClicked ? "button-green" : "button-red"}
>
  {this.state.buttonClicked ? "Activé" : "Désactivé}
</button>

Ici, c’est une erreur d’inattention, j’ai rajouté un “s” à Désactivé. Cypress me signale qui n’existe pas de “Désactivés” dans le bouton. Il faut donc faire attention à l’orthographe du texte, lorsqu’on réalise des tests.

Correction

describe('Vérification du bouton', () => {
        it('Vérification du bouton', () => {
            //On prend la balise "button.button-red"
            cy.get('.button-red');
            //On vérifie que le texte du bouton correspond bien
            cy.contains('Désactivé');
            //On vérifie que le texte dans le bouton est blanc
            cy.should('have.css', 'color', 'rgb(255, 255, 255)');
            //On vérifie que le fond du bouton est rouge
            cy.should('have.css', 'background-color', 'rgb(207, 10, 29)');
        });
});

La méthode « cy.contains » permet d’obtenir l’élement DOM contenant le texte

1 ère partie de la vérification :

Multiples erreurs

it('Vérification du changement de bouton', () => {
            //On prend la balise "button.button-red" et on clique dessus
            cy.get('.button-red').click();
            //Erreur texte
            cy.contains('Désactivé');
            //On vérifie que le texte dans le bouton est blanc
            cy.should('have.css', 'color', 'rgb(255, 255, 255)');
            //Erreur couleur 
            cy.should('have.css', 'background-color', 'rgb(207, 10, 29)');
});

Cypress fait ses tests de haut en bas, lorsqu’il détecte une erreur, il affichera cette erreur et il passera au “it” suivant et ne cherchera pas à détecter s’il y a d’autres erreurs dans cette partie.

Après avoir réglé l’erreur “Désactivé en “Activé”, il affiche bien l’erreur suivante. Attention, une erreur peut en cacher d’autres.

Correction

it('Vérification du changement de bouton', () => {
            //On prend la balise "button.button-red" et on clique dessus
            cy.get('.button-red').click();
            //On vérifie que le texte du bouton correspond bien
            cy.contains('Activé');
            //On vérifie que le texte dans le bouton est blanc
            cy.should('have.css', 'color', 'rgb(255, 255, 255)');
            //On vérifie que le fond du bouton est vert
            cy.should('have.css', 'background-color', 'rgb(76, 175, 80)');
});

2ème partie de la vérification :

Conclusion : Et voilà, vous êtes prêts à réaliser vous-même vos propres tests fonctionnels sur vos applications.

Cependant durant cet article, je n’ai utilisé qu’une partie de Cypress, il reste plein de fonction à découvrir.

Alors, n’hésitez pas à consulter la documentation de Cypress : ici

CONSULTER PLUS D'ARTICLES

Illustration comment bien choisir son BE
Electronique

Bureau d’études électronique, comment choisir ?

Les bureaux d’études électroniques sont nombreux en France. Le recours à un prestataire pour faire développer un prototype ou même un produit fini pour mise en production est une démarche