Stage Integration-Testing
Les test d'intégration sont une step encore plus évolué que le simple test unitaire.
On a bien souvent besoin de dependances pour la réalisation de ceux-ci.
Un exemple courant peut être, lors du développement d'un micro service backend qui fourni différents endpoint afin d'envoyer au frontend, les datas nécéssaires provenant d'une base de donnée, d'avoir à la fois de lancé :
- Le backend qui est lancé en arrière plan,
- d'avoir en plus d'avoir nos tests lancé,
- Et enfin d'avoir une database de lancé afin de pouvoir tester notre API qui discute bien avec notre base de donnée
Il va falloir s'organiser d'avantage pour cette section afin de lancer l'ensemble de nos services et dans le bon ordre.
Introduction¶
Ici je vais te montrer comment dérouler des tests avec :
- Jest, comme orchestrateur de test
- Docker-compose, permettant de lancer nos services en fond, pour les tests d'intégrations lancés en local
- Gitlab Services, permettant de lancer nos services en fond, pour les tests d'intégrations lancés en CI/CD
Lancement des tests en local¶
Creation d'un backend qui fourni une API¶
On commence cette section par réaliser un petit serveur web, qui expose un seul end point. On fais quelque chose de simple ici, un endpoint POST qui va aller enregistrer une props lorsque l'on requête ce endpoint, et l'inscrire dans une database NoSQL, MongoDB.
Ici on défini un serveur express qui tourne sur localhost:3000.
On a crée un seul endpoint, accessible sur localhost:3000/addData.
Attention, bien effectuer sur ce endpoint la requête avec un POST, et y ajouter en body de requête un attribut name, avec une valeure associée.
Mongoose permettant de nous faciliter les échanges avec la database MongoDB.
Creation de la database en local avec Docker-Compose¶
On a un serveur qui tourne, mais il nous faut bien lancer une database avec laquelle il va communiquer sur l'adresse mongodb://localhost:27017/mydatabase, défini dans le précédent fichier.
On va utiliser docker compose, nous permettant de lancer des services en tâche de fond.
Pour cela on va créer un docker-compose.yml comme suit :
Ajout des tests avec Jest¶
Je propose ici deux tests. On va vérifier que notre unique end point sur /addData, réponds bien lorsque la requête reçoit en body le bon paramètre, et que cet endpoint tombe en erreur lorsque l'on oubli ce parametre.
Pour cela on créer le fichier de test suivant :
Petite subtilité ici, est l'utilisations des hooks beforeEach et afterEach provenant de la librairie de test Jest, permettant :
- d'initialiser la connexion à mongodb avant l'exécution d'un test
- la fermeture de connexion à mongodb après l'execution d'un test
Cela permet le bon déroulement des tests et d'éviter des fuites si on oublie de fermer la connexion.
Lancement des tests en local¶
Maintenant que l'on a le code de notre application, nos tests de prêt, et une mongodb en local avec docker-compose, faisons un dernier point sur les scripts que l'on va mettre en place dans notre package.json :
Ici deux scripts mis en plance :
- start: permet de lancer mon backend en local
- test: permet de lancer mon jeu de test avec Jest
Maintenant, pour lancer nos 3 services ensembles et dans le bon ordre :
- Lancer notre mongodb
- Lancer notre backend
- Lancer nos tests
Nous allons faire un petit script bash nous facilitant la tâche :
Warning
N'oubliez pas de stopper votre docker-compose en fin de test
Le but ici est de pouvoir tout lancer avec une simple et unique commande que cela soit en local, ou en CI/CD avec ./runTest.sh
Tip
Pensez bien à autoriser les droits d'éxecution de ce script avec chmod +x ./runtTest.sh
Comment gérer les tests en local et en CI/CD avec les variables¶
On sait que la connexion string pour un mongodb lancé en local est mongodb://localhost:27017. On le verra plus tard, mais nous allons avoir une tout autre connexion string lorsque on lancera nos tests sur Gitlab.
Je vais spoil un peu, mais celle-ci sera mongodb://mongo:27017, nous le verrons pourquoi par la suite.
Nous devons donc gérer une variabilisation de cette connexion string, afin de pouvoir lancer avec une même et unique commande nos tests en local mais aussi en CI/CD afin d'avoir un code propre et efficace. Sinon cela risque d'être un gros merdier si on doit maintenir 2 code différents 🫠
Creation de fichiers .env¶
On commence donc par créer 2 fichiers d'environnements, nous permettant de distinguer les 2 differentes connexion string à mongo, et d'en avoir une chargé selon le type d'environnement ou on execute le test.
On va vouloir, charger la bonne configuration, injecter ces valeurs en variables d'environnements selon le bon type d'environnement ou tu lances tes tests.
Update du Backend¶
Update du code¶
Maintenante que nous utilisations une variable d'environnement pour setter notre connexion string pour la MongoDB, nous allons mettre à jour la fonction qui nous connecte à celle-ci avec cette varible :
Update du package.json pour le lancement du backend¶
Nous devons modifier notre script NPM de lancement du backend afin de lui injecter la variable
On peut desormais lancer notre backend pour le developpement en local avec npm run start
qui va aller taper sur la nouvelle connexion string.
Update des Tests¶
Update du code¶
Faisons la même chose pour notre test Jest :
Update de Jest pour le lancement des tests¶
Ici on va devoir faire un peu plus de modification afin de lancer Jest avec les bonnes variables selon ton environnement.
Ici on ajoute un fichier, qui défini des paramètres pour l'éxecution de Jest. On ajoute une option permettant de charger un fichier JS qui s'executera avant le lancement de Jest et des tests.
On va donc creer un nouveau fichier qui va s'occuper d'injecter la bonne variable selon ton environnement :
Ici rien de bien complexe. Je me base, pour selectioner le bon fichier d'env à injecter, selon si on a setter une var d'env CI ou non. Le but ici est, en local de n'en avoir aucune et donc d'injecter .env.local par défaut, et donc en CI/CD, de setter une var CI: true
qui ira donc charger le fichier .env.ci ce coup-ci.
Lancement des tests en CI/CD avec Gitlab Services¶
Maintenance que l'on a un code qui s'adapte selon si il est lancé en local ou CI, nous n'avons plus qu'a créer un nouveau job sur Gitlab :
Ici nous avons besoin d'une alpine avec NodeJs d'intégré.
Comme je l'ai dit dans la partie précédente, afin d'activer le bon environnement au lancement de Jest, on set une var d'env CI:true
On utilise ici un nouvel attribut de Gitlab, services, qui agit ici comme notre docker-compose en local. Il va simplement charger une image mongo et la faire tourner en arrière-plan. L'alias ici permet de différencier nos services le jour ou nous devons en faire tourner plusieurs. C'est très utile car cela permet de leur setter un hostname différent entre eux.