Tester efficacement avec Terraform
Peter De Tender
2 août 2022
0 minutes de lectureTerraform est une solution d’infrastructure as code (IaC) qui permet aux équipes DevOps d’utiliser des concepts de programmation pour déployer automatiquement des composants d’infrastructure sur site ou dans le cloud public. Ces composants peuvent inclure des machines virtuelles, des composants réseau, du stockage, des applications ou des services de base de données.
Terraform fournit le HashiCorp Configuration Language (HCL). HCL est un langage unifié et spécifique à un domaine qui simplifie la rédaction de modèles pour différents fournisseurs de cloud, notamment Amazon AWS CloudFormation, les modèles ARM et Bicep de Microsoft Azure, ainsi que Cloud Deployment Manager de Google pour GCP.
Tout comme les tests de code sont essentiels au développement logiciel, tester une solution IaC comme Terraform est indispensable. Correctement intégrés, les tests IaC peuvent limiter les problèmes importants de gestion des ressources et permettre aux équipes DevOps de valider l’efficacité des configurations.
Cependant, intégrer ces tests au processus DevOps peut s’avérer complexe. Plusieurs questions se posent : que doivent-ils inclure, que peut-on omettre et quels mécanismes disponibles sont les plus efficaces ?
Il existe de nombreuses façons de tester les modèles Terraform. La plus simple consiste à utiliser les commandes intégrées de Terraform, comme terraform validate ou terraform plan. Ces commandes permettent d’écrire des tests unitaires, d’intégration, de conformité ou de bout en bout, conformément aux pratiques de test traditionnelles du développement logiciel. Autre possibilité : adopter une approche davantage axée sur les développeurs en effectuant des tests avec le Cloud Development Kit for Terraform (CDKTF).
En définitive, les équipes DevOps doivent définir clairement les objectifs du processus de validation. Il peut s’agir de vérifier la syntaxe du modèle et de s’assurer que son déploiement aboutit. L’objectif peut aussi être de concevoir un scénario de test plus avancé : effectuer des tests ciblés pour repérer les problèmes de sécurité ou les mauvaises configurations, et détecter les conséquences sur la sécurité lors des déploiements. L’idée principale est de déterminer précisément ce qui doit être testé, puis de trouver la bonne combinaison de solutions de test.
Stratégies de test Terraform
Examinons quelques stratégies de test pour Terraform.
Tests de dérive
Terraform valide votre infrastructure actuelle à l’aide du fichier d’état terraform. Chaque déploiement Terraform consigne l’état final dans un fichier d’état, généralement stocké dans un emplacement partagé.
Cependant, si certains déploiements de votre environnement cible ne sont pas déclenchés par Terraform, il peut y avoir un écart entre les ressources « réelles » et celles que le fichier d’état Terraform indique comme étant en cours d’exécution. Si ce déploiement concerne une ressource déjà gérée par Terraform, la commande intégrée terraform plan est utile, car elle peut mettre en évidence les modifications ou les différences entre le contenu du fichier d’état et l’environnement cible réel. Si le déploiement crée une ressource entièrement nouvelle, des outils comme driftctl et CloudQuery sont utiles, car ils recensent toutes les ressources qui ne sont pas gérées par Terraform.
Tests unitaires
Les tests unitaires sont parmi les tests les plus faciles à réaliser. Ils consistent à exécuter un test ciblé et relativement simple, généralement sur un objet donné. Il s’agit souvent de vérifier que la syntaxe du modèle est correcte.
Pour cela, nous pouvons utiliser terraform validate. En cas d’erreur de syntaxe dans le modèle, terraform validate renvoie un message d’erreur (même si la détection d’une erreur de syntaxe dans le modèle ne garantit pas nécessairement la réussite des déploiements).
Pour valider un déploiement, nous pouvons nous appuyer sur une autre commande intégrée : terraform plan. En exécutant la phase de planification, Terraform simule un déploiement réel, communique avec le back-end du fournisseur et indique le résultat du déploiement à l’aide de la commande terraform apply.
L’exécution de terraform plan met en évidence les modifications détectées par rapport à l’environnement existant. Il peut s’agir de la création, de la modification ou de la suppression de ressources. Ces informations peuvent aider notre équipe DevOps à identifier l’impact du déploiement avant de l’exécuter.
L’étape suivante consiste à utiliser Terraform apply, qui exécute le déploiement réel. Gardez toutefois à l’esprit que cette phase ne reflète pas toujours entièrement la situation. Si vous supprimez une ressource de votre HCL Terraform, puis utilisez terraform apply, la ressource sera supprimée sur l’IaaS : même si elle ne figure plus dans le HCL, elle est toujours présente dans l’état Terraform depuis son dernier déploiement réussi. Terraform compare l’état TF à l’API IaaS, constate que la ressource ne doit plus être déployée et la supprime. Vous devez donc rester attentif aux dépendances et contraintes éventuelles de votre environnement. Dans les environnements cloud comme AWS ou Azure, cela est généralement géré par la gouvernance des politiques.
Analyse statique
L’utilisation d’un linter est également utile. Un linter permet aux équipes DevOps d’analyser le code à la recherche d’erreurs, de bugs ou de blocs de code suspects. Cela aide à repérer les problèmes de syntaxe, mais répond aussi à des besoins plus critiques, comme la détection des problèmes de sécurité.
Il existe plusieurs outils open source d’analyse statique pour Terraform, qui utilisent différents mécanismes d’analyse selon les plateformes ciblées. GitHub propose divers modèles utilisant tflint avec différents fournisseurs de cloud.
Selon la complexité du cas d’usage de l’analyse statique, le processus peut relever d’un simple test unitaire ou s’inscrire dans un scénario de test plus complexe ou avancé. Par exemple, si le modèle autorise le déploiement d’une machine virtuelle avec une adresse IP publique, la validation par notre linter peut détecter la présence de l’objet d’adresse IP publique et générer une erreur. Le linter peut également repérer les mots de passe ou les chaînes de connexion codés en dur dans notre code.
Tests d’intégration
Même si chaque test unitaire réussit, l’exécution séquentielle de tous les plans Terraform ne garantit pas la réussite globale. C’est pourquoi les tests d’intégration sont essentiels. En termes simples, ils consistent à exécuter une combinaison de tests unitaires. Dans Terraform, les tests unitaires ciblent généralement un seul module, tandis que les tests d’intégration valident plusieurs modules comportant de nombreuses dépendances.
Supposons que nous ayons deux modèles Terraform distincts : l’un pour créer un réseau virtuel ou un cloud privé virtuel (VPC), l’autre pour déployer une infrastructure de machines virtuelles. Nous pourrions les tester séparément, mais nous voudrons ensuite déployer les machines virtuelles avec succès sur les composants du réseau virtuel déployé. Si l’un des modules est déployé dans une autre région, les tests unitaires réussiront, mais les tests d’intégration échoueront.
Autre différence importante : les tests unitaires peuvent être exécutés hors ligne, sans déployer quoi que ce soit, tandis que les tests d’intégration nécessitent le déploiement de ressources pour en valider l’impact et la réussite.
Terratest de Gruntwork est un outil qui facilite les tests d’intégration. Il s’appuie sur le framework du langage Go, qui intègre des outils de test de packages, et permet aux équipes DevOps d’appliquer les mêmes principes aux scénarios IaC.
Tests de conformité
Lors de la validation des modèles Terraform, les déploiements techniques doivent respecter les règles de conformité de l’entreprise. Des tests de conformité sont donc nécessaires : ils vérifient les normes de conformité régionales, les conventions de nommage, les normes d’infrastructure telles que les types spécifiques de machines virtuelles, ainsi que la sécurité du stockage sur disque.
Dans la plupart des cas, la validation de conformité fait (ou devrait faire) partie de la configuration de l’environnement cible, au même titre que l’intégration des stratégies Azure ou du centre de conformité AWS. Toutefois, ces stratégies ne sont validées que lors d’un déploiement réel, qui échouera s’il ne les respecte pas.
En intégrant les tests de conformité au processus DevOps Terraform, les tests sont exécutés avant les déploiements, ce qui permet de s’assurer de leur réussite. Une solution consiste à utiliser Terraform-compliance, un outil externe qui vérifie la conformité des modèles Terraform d’une organisation.
Tests de bout en bout
En définitive, les équipes DevOps chercheront à réunir toutes les méthodes de test dans un même scénario. Idéalement, elles testeront tous les modèles, déploieront tous les modules et valideront les réussites ou les échecs.
Cette approche semble idéale, mais les tests de bout en bout présentent des difficultés. Leur durée crée un goulot d’étranglement : il faut parfois beaucoup plus de temps pour obtenir un résultat qu’avec les tests unitaires, qui s’exécutent rapidement et fournissent des résultats immédiats.
Tests unitaires avec CDKTF
Jusqu’ici, nos exemples supposent que nous utilisons le langage natif HashiCorp pour nos fichiers de modèle. Toutefois, Terraform propose aussi une approche de l’IaC plus axée sur les développeurs avec le CDKTF - Cloud Development Kit for Terraform.
Avec CDKTF, les équipes DevOps peuvent déployer une infrastructure à l’aide de langages de développement traditionnels, comme Python, C#, Go et Java. Tous les fournisseurs et modules Terraform sont compatibles avec ce kit. Son principal avantage est que notre équipe n’a pas besoin d’apprendre le HCL et peut s’appuyer sur ses connaissances des langages de développement qu’elle maîtrise déjà.
CDKTF s’appuie sur une approche différente pour rédiger les modèles et exécuter les déploiements ; les tests unitaires s’exécutent donc différemment. La documentation à jour sur les tests CDKTF est disponible sur le site Web de Terraform.
Outils de sécurité Snyk
Tester votre IaC est essentiel à la santé de votre environnement. En plus d’évaluer différentes méthodes de test, il est important de mettre en évidence les aspects liés à la sécurité. Snyk propose des outils utiles à cet effet :
Snyk Infrastructure as Code aide à intégrer la sécurité à toutes les étapes de la rédaction de code IaC, en analysant le code à la recherche de vulnérabilités, comme pour le code source des applications traditionnelles.
driftctl, l’outil de test de dérive mentionné précédemment, est développé par Snyk et proposé comme moteur open source de détection des dérives.
Snyk IaC intègre un vaste ensemble de règles de sécurité prédéfinies et éprouvées dans le secteur, de bonnes pratiques des fournisseurs cloud et les résultats de recherche de Snyk sur les modèles de menace. Nous pouvons également créer des règles personnalisées avec Snyk IaC, à l’aide du framework Open Policy Agent (OPA) et du langage de requête Rego.
En savoir plus sur la sécurité pour Terraform
Tester les modèles est une étape essentielle de leur création. En plus de ses avantages fonctionnels, le test contribue à optimiser la sécurité des déploiements Terraform. Si vous souhaitez en savoir plus sur l’intégration de la sécurité à vos modèles de déploiement Terraform, découvrez Snyk, qui fournit des outils de validation de la sécurité pour vos pipelines DevOps et d’automatisation, y compris Terraform.
Sécurisez votre infrastructure dès la source
Snyk automatise la sécurité et la conformité de l’IaC dans vos workflows, et détecte les ressources dont la configuration a dérivé ou qui sont manquantes.



