Pourquoi l'infrastructure as code
Pourquoi
Relisez de mémoire ce que vous avez fait dans le cours Le cloud : les fondamentaux. Un VPC, un réseau privé en 172.16.20.0/22, deux instances dans deux zones avec un fichier cloud-init, une base PostgreSQL managée dont on a retiré le point d'accès public, une passerelle avec bastion, un répartiteur de charge et sa vérification de santé, un bucket, une application IAM et sa politique. Une quarantaine de commandes scw, tapées dans un ordre précis, avec des identifiants recopiés d'une sortie JSON à la suivante. Le cours Scaleway en pratique en a ajouté autant.
Maintenant, trois questions.
- Une métropole cliente demande un environnement de préproduction identique à la production. Combien de temps pour le reconstruire, et comment savoir qu'il est vraiment identique ?
- Quelqu'un a ouvert le port 22 du groupe de sécurité « pour déboguer » il y a trois semaines. Qui ? Pourquoi ? Est-ce encore nécessaire ? La console ne le dit pas, et personne ne s'en souvient.
- La zone
fr-par-1est indisponible pour la journée, et vous voulez remonter les instances ailleurs. La procédure existe-t-elle ailleurs que dans la tête de la personne qui a tout monté, et cette personne est-elle en congé ?
C'est le problème que Kief Morris, dans Infrastructure as Code, appelle la dérive de configuration (configuration drift) et les serveurs flocons de neige (snowflake servers) : une infrastructure modifiée à la main, petit à petit, devient unique, inexplicable et impossible à reproduire. Chaque correction sauve la journée et rend la suivante plus difficile. Le cloud a aggravé le problème au lieu de le résoudre : créer une ressource ne prend plus des semaines mais quelques secondes, donc on en crée beaucoup, et beaucoup plus vite que l'on ne les documente.
L'infrastructure as code (infrastructure as code, souvent abrégée IaC) répond par un changement de support : l'infrastructure n'est plus le résultat d'une suite de gestes, c'est un texte, versionné dans Git, relu comme du code, et appliqué par un outil. Les trois questions deviennent faciles. La préproduction est le même texte avec d'autres valeurs. Le port 22 apparaît dans une demande de fusion, avec son auteur, sa justification et sa relecture. La procédure de reconstruction est le dépôt lui-même.
Ce cours vous apprend à écrire ce texte avec Terraform et OpenTofu, les deux outils les plus utilisés pour décrire une infrastructure cloud. Cette première leçon pose les principes, situe les outils, raconte pourquoi il y en a deux, et vous montre votre premier plan.
Les concepts
Décrire plutôt que faire
Il y a deux façons de dire à un ordinateur ce que l'on veut.
La façon impérative donne des ordres, dans l'ordre : « crée un réseau privé, puis crée une instance, puis attache l'instance au réseau ». C'est ce que vous avez fait avec scw, et c'est ce que fait un script Bash. Le résultat dépend de l'état de départ : relancez le script, il essaie de créer un second réseau, échoue sur un nom déjà pris, ou réussit et crée un doublon.
La façon déclarative décrit le résultat : « il existe un réseau privé pn-signalements, et une instance sig-app-1 qui y est attachée ». C'est à l'outil de comparer cette description à ce qui existe, et d'en déduire les actions nécessaires : tout créer la première fois, ne rien faire la deuxième, seulement attacher l'instance si quelqu'un l'a détachée entre-temps.
flowchart LR
D["Description<br/>(fichiers .tf)"] --> C{"Comparaison"}
E["État connu<br/>+ réalité"] --> C
C --> P["Plan :<br/>créer, modifier,<br/>détruire"]
P --> A["Application<br/>par appels d'API"]
A --> E
Trois mots reviennent sans cesse :
- Une opération est idempotente quand l'appliquer une fois ou dix fois donne le même résultat.
terraform applysur une description inchangée ne fait rien la deuxième fois : c'est l'idempotence que vous verrez dans la pratique (glossaire). - La convergence est la propriété d'un outil qui, quel que soit l'état de départ, rapproche la réalité de la description. Terraform converge quand on le lance ; un contrôleur comme Argo CD (cours GitOps) converge en permanence, par une boucle de réconciliation.
- La dérive est l'écart entre la description et la réalité, quand quelqu'un ou quelque chose modifie l'infrastructure sans passer par le code. La leçon 11 apprend à la détecter et à la résorber.
Le déclaratif n'est pas magique. Il faut toujours, sous le capot, des appels d'API dans un certain ordre ; simplement, c'est l'outil qui calcule cet ordre à partir des dépendances entre ressources (leçon 8), et non vous.
Ce que l'on gagne, et ce que l'on paie
Kief Morris résume les pratiques de l'infrastructure as code en quelques principes : tout définir dans du code, vérifier et livrer ce code en continu, construire de petits éléments simples et indépendants. Concrètement, pour l'équipe de Signalements :
| Avant (à la main) | Après (en code) |
|---|---|
| La configuration vit dans la console et dans des mémoires | Elle vit dans un dépôt Git, signalements-iac |
| Une modification se fait, puis s'oublie | Une modification se propose, se relit, se fusionne, se trace |
| Reconstruire, c'est se souvenir | Reconstruire, c'est appliquer le dépôt |
| La préproduction ressemble à la production | La préproduction est la même description, avec d'autres valeurs |
| On découvre une erreur après coup | On lit le plan avant d'appliquer |
| Un retour arrière est une enquête | Un retour arrière commence par un git revert |
Le prix existe aussi, et il vaut mieux le connaître avant de commencer :
- Un outil de plus à maîtriser, avec son langage, ses pièges et son état (leçon 6), un fichier qui doit être stocké, partagé et protégé.
- Une discipline : une modification faite à la main dans la console, même urgente, crée une dérive que le prochain
applyrisque d'annuler. Il faut que toute l'équipe joue le jeu. - Un temps de démarrage : décrire une architecture existante prend plus de temps que de la cliquer la première fois. Le gain vient à la deuxième, à la dixième, et le jour de l'incident.
Les familles d'outils
« Infrastructure as code » recouvre des outils qui ne font pas la même chose. Les confondre mène à des architectures bancales, comme installer des paquets avec Terraform ou créer des réseaux avec Ansible.
| Famille | Ce qu'elle gère | Exemples | Dans le catalogue |
|---|---|---|---|
| Provisionnement | Les ressources du fournisseur : réseaux, machines, bases, droits, DNS | Terraform, OpenTofu, Pulumi, AWS CloudFormation | Ce cours |
| Gestion de configuration | L'intérieur des machines : paquets, fichiers, services | Ansible, Puppet, Chef, Salt | Ansible : les fondamentaux |
| Fabrication d'images | Des images de machine prêtes à démarrer | Packer, mkosi | Images de machines avec Packer |
| Initialisation au démarrage | La première configuration d'une instance | cloud-init | Leçon 4 du cours cloud |
| Réconciliation continue dans Kubernetes | Des ressources (y compris cloud) décrites comme objets Kubernetes | Argo CD, Flux, opérateurs, Crossplane | GitOps avec Argo CD |
Quelques repères sur les voisins de Terraform dans la première famille :
- AWS CloudFormation et Azure Resource Manager (avec son langage Bicep) sont propres à un fournisseur. Scaleway ne propose pas de langage maison équivalent : sa documentation renvoie à son fournisseur Terraform.
- Pulumi décrit l'infrastructure dans un langage de programmation généraliste (TypeScript, Python, Go). On gagne les boucles, les tests et les bibliothèques d'un vrai langage ; on perd la lisibilité uniforme d'une description déclarative que tout le monde, y compris un auditeur, peut relire.
- Crossplane fait de Kubernetes le plan de contrôle de l'infrastructure cloud : une base de données devient un objet Kubernetes, réconcilié en permanence.
Dans le parcours Lyneko, la frontière est simple : Terraform ou OpenTofu crée tout ce qui se commande à l'API du fournisseur (y compris le cluster Kubernetes et son registre) ; cloud-init ou une image fabriquée prépare l'intérieur des machines ; Argo CD déploie ce qui tourne dans le cluster.
Terraform, de 2014 à aujourd'hui
Terraform a été écrit par Mitchell Hashimoto, cofondateur de HashiCorp ; la version 0.1 est sortie en juillet 2014 et ne connaissait que deux fournisseurs, AWS et DigitalOcean. Ses idées tiennent en trois choix :
- Un langage déclaratif dédié, HCL (HashiCorp Configuration Language), lisible par des humains et sans les pièges d'un langage de programmation (leçon 3).
- Des fournisseurs (providers) séparés du cœur : des programmes indépendants, un par API, que Terraform télécharge et pilote. Le cœur ne connaît ni AWS ni Scaleway : il sait lire une description, calculer un plan et appeler des fournisseurs. Le registre public en compte aujourd'hui des milliers, écrits par les fournisseurs de cloud eux-mêmes (Scaleway maintient le sien) ou par la communauté (leçon 4).
- Un état (state) : un fichier où Terraform note quelles ressources réelles correspondent à quels blocs de la description, pour pouvoir les modifier ou les détruire plus tard (leçon 6).
La documentation résume le flux de travail en trois verbes, write, plan, apply : écrire la description, laisser Terraform calculer un plan « décrivant l'infrastructure qu'il va créer, mettre à jour ou détruire », puis l'appliquer « dans le bon ordre, en respectant les dépendances entre ressources ». La version 1.0, en juin 2021, a figé la compatibilité du langage. Au 5 octobre 2026, la version stable la plus récente est la 1.16.5 (2 octobre 2026), et une version 1.17 est en bêta.
Août 2023 : la licence change, la communauté bifurque
Jusqu'en août 2023, Terraform était un logiciel libre, sous licence Mozilla Public License 2.0 (MPL) : chacun pouvait l'utiliser, le modifier et le redistribuer, y compris dans un produit commercial.
Le 10 août 2023, HashiCorp annonce que toutes les versions futures de ses produits passent sous Business Source License 1.1 (BUSL ou BSL). Le texte de la licence, toujours en tête du dépôt de Terraform, contient l'essentiel dans sa clause d'usage additionnel : vous pouvez faire un usage de production de l'outil, « à condition que cet usage ne consiste pas à l'offrir à des tiers, en mode hébergé ou embarqué, pour concurrencer » les offres payantes de l'éditeur. Chaque version repasse sous MPL quatre ans après sa publication. Ce n'est plus une licence libre au sens de l'Open Source Initiative : une restriction porte sur l'usage. La dernière version sous MPL est la 1.5.7.
Ce que cela change dépend de qui vous êtes :
- Une équipe qui utilise Terraform pour sa propre infrastructure, comme Lyneko pour ses applications, ou une collectivité pour son système d'information, n'est pas visée : la FAQ de HashiCorp confirme qu'un usage interne, même hébergé comme un service pour l'organisation, reste permis.
- Une entreprise qui vend un service d'exécution de Terraform (plateformes d'automatisation, intégrateurs qui embarquent l'outil dans leur produit) peut tomber sous la restriction, selon la manière dont elle concurrence l'offre de l'éditeur. Les plus concernées ont été les premières à réagir.
Dans les jours qui suivent, un collectif d'entreprises et de contributeurs publie le manifeste OpenTF, qui demande à HashiCorp de revenir à une licence libre « pour garantir à Terraform un foyer unique, impartial et fiable ». Faute de réponse, il bifurque le 25 août à partir de la dernière version sous MPL. Le 20 septembre 2023, la Linux Foundation annonce qu'elle accueille le projet, renommé OpenTofu, avec le soutien déclaré de plus de 140 organisations et l'engagement d'au moins dix-huit développeurs à plein temps pendant cinq ans. La première version stable, OpenTofu 1.6.0, sort le 10 janvier 2024. Le 23 avril 2025, le projet entre à la Cloud Native Computing Foundation (CNCF) au niveau Sandbox, avec une exception à la politique de licence de la fondation pour garder la MPL.
Entre-temps, IBM a racheté HashiCorp : l'opération a été finalisée le 27 février 2025. La licence de Terraform est restée la BUSL ; le texte cite désormais IBM comme titulaire.
| Date | Événement |
|---|---|
| Juillet 2014 | Terraform 0.1 (AWS et DigitalOcean) |
| Juin 2021 | Terraform 1.0 |
| 10 août 2023 | Passage de Terraform sous BUSL 1.1 (la 1.5.7 est la dernière version sous MPL) |
| 25 août 2023 | Bifurcation OpenTF |
| 20 septembre 2023 | La Linux Foundation accueille OpenTofu |
| 10 janvier 2024 | OpenTofu 1.6.0, première version stable |
| 27 février 2025 | IBM finalise le rachat de HashiCorp |
| 23 avril 2025 | OpenTofu entre à la CNCF (Sandbox) |
| Fin septembre 2026 | OpenTofu 1.13.0 ; Terraform 1.16.x |
Deux outils, un langage, des chemins qui s'écartent
Au moment de la bifurcation, les deux outils étaient identiques. Trois ans plus tard, ils partagent l'essentiel : le langage HCL, la structure des fichiers, le format de l'état, les fournisseurs (un fournisseur publié pour l'un fonctionne avec l'autre) et les commandes (tofu init, tofu plan, tofu apply remplacent terraform init, terraform plan, terraform apply). Tout ce que ce cours enseigne vaut pour les deux, sauf mention contraire.
Ils ont pourtant chacun ajouté des fonctionnalités que l'autre n'a pas, ou pas sous la même forme. Au 5 octobre 2026, d'après les notes de version des deux projets :
| Propre à OpenTofu (version d'apparition) | Propre à Terraform (version d'apparition) |
|---|---|
| Chiffrement de l'état et des plans côté client (1.7) | Intégration avec HCP Terraform, l'offre hébergée de l'éditeur (bloc cloud) |
| Variables et valeurs locales utilisables dans la configuration du stockage de l'état et des sources de modules (1.8) | Ressources de liste et commande terraform query pour interroger l'existant (1.14) |
Fichiers .tofu qui remplacent un .tf du même nom, pour écrire un code compatible avec les deux outils (1.8) | Blocs action, des opérations impératives déclenchées par le cycle de vie (1.14) |
for_each sur les blocs provider, et option -exclude (1.9) | Blocs import à l'intérieur des modules (1.16) |
| Distribution des fournisseurs et modules par un registre OCI (1.10) | Terraform Stacks et Terraform Policy, liés à l'offre hébergée |
Méta-argument enabled pour une ressource présente zéro ou une fois (1.11) |
Certaines fonctionnalités sont arrivées des deux côtés, à quelques mois d'écart et parfois avec des différences de détail : les tests intégrés (terraform test, tofu test), les fonctions définies par les fournisseurs, les valeurs éphémères qui ne sont jamais écrites dans l'état, le verrouillage de l'état sur S3 sans base de données annexe (leçon 7). Les deux projets se surveillent et convergent souvent, mais il faut vérifier la documentation de l'outil que l'on utilise.
Une différence pratique vous concerne dès la leçon 2 : chaque outil a son registre. Une source écrite hashicorp/random désigne registry.terraform.io/hashicorp/random pour Terraform et registry.opentofu.org/hashicorp/random pour OpenTofu. Les deux registres publient les mêmes fournisseurs courants, dont celui de Scaleway, mais le fichier de verrouillage des versions (leçon 2) n'est pas interchangeable tel quel.
Comment choisir
La question n'a pas de bonne réponse universelle ; elle a de bonnes questions.
- La licence vous concerne-t-elle ? Si vous éditez un produit ou un service qui exécute Terraform pour des clients, faites lire la clause par un juriste. Si vous gérez votre propre infrastructure, la BUSL ne vous interdit rien aujourd'hui ; la question devient celle de la dépendance à un éditeur qui a déjà changé une fois les règles, et peut le refaire.
- Avez-vous besoin d'une fonctionnalité propre à l'un ? Le chiffrement de l'état côté client d'OpenTofu répond à une vraie exigence chez les clients sensibles (le cours Cloud souverain explique pourquoi garder les clés compte). L'intégration avec HCP Terraform compte si votre organisation l'utilise déjà.
- Qu'utilisent votre équipe et votre écosystème ? Les outils autour (analyse statique, plateformes de CI spécialisées, modules publics) supportent presque tous les deux, mais vérifiez ceux dont vous dépendez.
- Pouvez-vous changer plus tard ? Oui, à condition de rester dans le sous-ensemble commun et de suivre le guide de migration du projet cible. Plus vous utilisez de fonctionnalités propres à un outil, plus le changement coûte.
Ce cours ne tranche pas pour vous : il écrit terraform dans les commandes, parce que c'est l'outil installé dans les sorties montrées, et signale les différences. Chez Lyneko, la règle est de rester dans le langage commun pour tout ce qui est partagé avec les clients, afin que chacun puisse l'exécuter avec l'outil de son choix.
En pratique
La même instance, deux fois
Voici comment le cours cloud créait sig-app-1 :
$ scw instance server create \
name=sig-app-1 type=PRO2-XXS image=ubuntu_noble zone=fr-par-1 \
cloud-init=@signalements.yaml \
tags.0=app=signalements tags.1=env=prod \
--wait -o json > sig-app-1.json
Et voici la même intention, décrite pour le fournisseur Scaleway de Terraform :
resource "scaleway_instance_ip" "sig_app_1" {
zone = "fr-par-1"
}
resource "scaleway_instance_server" "sig_app_1" {
name = "sig-app-1"
type = "PRO2-XXS"
image = "ubuntu_noble"
zone = "fr-par-1"
ip_id = scaleway_instance_ip.sig_app_1.id
user_data = {
cloud-init = file("${path.module}/signalements.yaml")
}
tags = ["app=signalements", "env=prod"]
}Cette configuration a été vérifiée avec terraform validate contre le fournisseur scaleway/scaleway 2.84.0 ; elle n'a pas été appliquée. Comparez :
- La commande est un geste, la ressource une affirmation. Relancer la commande crée une seconde instance du même nom. Réappliquer la ressource ne fait rien si l'instance existe et correspond.
- Les dépendances sont explicites. La commande créait l'IP implicitement (
ip=newpar défaut) et la perdait de vue à la suppression ; ici, l'IP est une ressource à part, et l'expressionscaleway_instance_ip.sig_app_1.iddit à Terraform qu'il doit la créer avant l'instance, et la détruire après. - Pas d'identifiant recopié à la main. Dans le cours cloud, il fallait extraire
.idd'une sortie JSON avecjqet le passer à la commande suivante. Ici, une ressource référence l'autre par son nom dans la description. - Le texte se relit. Une modification de
typeapparaît dans ungit diff, et dans le plan.
Votre premier plan
Le fournisseur Scaleway attendra la leçon 4 : il faut un compte, et chaque erreur coûte. Pour lire un premier plan sans rien dépenser, on utilise deux fournisseurs qui ne créent rien dans le cloud : random, qui fabrique des valeurs aléatoires (ici, un suffixe pour le nom du bucket), et local, qui écrit des fichiers sur votre poste. Créez un répertoire ~/signalements-iac et un fichier main.tf :
terraform {
required_version = ">= 1.10"
required_providers {
random = {
source = "hashicorp/random"
version = "~> 3.7"
}
local = {
source = "hashicorp/local"
version = "~> 2.5"
}
}
}
resource "random_pet" "suffixe" {
length = 2
}
resource "local_file" "inventaire" {
filename = "${path.module}/inventaire.txt"
content = "Bucket des pièces jointes : signalements-pj-${random_pet.suffixe.id}\n"
}Le bloc terraform dit quels fournisseurs télécharger et dans quelles versions ; les deux blocs resource décrivent ce qui doit exister. La leçon 2 détaille chaque ligne. Lancez terraform init (qui télécharge les fournisseurs), puis terraform plan. Voici la sortie obtenue avec Terraform 1.16.1, avec l'option -no-color :
Terraform used the selected providers to generate the following execution
plan. Resource actions are indicated with the following symbols:
+ create
Terraform will perform the following actions:
# local_file.inventaire will be created
+ resource "local_file" "inventaire" {
+ content = (known after apply)
+ content_base64sha256 = (known after apply)
+ content_base64sha512 = (known after apply)
+ content_md5 = (known after apply)
+ content_sha1 = (known after apply)
+ content_sha256 = (known after apply)
+ content_sha512 = (known after apply)
+ directory_permission = "0777"
+ file_permission = "0777"
+ filename = "./inventaire.txt"
+ id = (known after apply)
}
# random_pet.suffixe will be created
+ resource "random_pet" "suffixe" {
+ id = (known after apply)
+ length = 2
+ separator = "-"
}
Plan: 2 to add, 0 to change, 0 to destroy.Lisez-le comme une liste de courses commentée :
- La légende en tête annonce les symboles utilisés : ici seulement
+, création. - Chaque ressource est introduite par son adresse (
local_file.inventaire, le type puis le nom) et par ce qui va lui arriver (will be created). - Les attributs connus à l'avance sont affichés (
length = 2,filename). Ceux qui ne le seront qu'après la création portent la mention(known after apply): le contenu du fichier dépend du nom aléatoire, qui n'existe pas encore. - Des attributs que vous n'avez pas écrits apparaissent avec leur valeur par défaut, comme
file_permission = "0777". Le plan vous montre ce que vous allez obtenir, pas seulement ce que vous avez demandé ; ce détail-là est un sujet de sécurité (voir plus bas). - La dernière ligne résume : deux créations, aucune modification, aucune destruction. C'est la ligne à lire en premier, et celle qui doit vous arrêter si elle annonce une destruction que vous n'attendiez pas.
Le plan n'a rien fait : aucun fichier n'est créé. Il faut terraform apply pour cela, ce que fera la leçon 2.
Sous le capot
Ce que fait plan. Terraform lit tous les fichiers .tf du répertoire et en construit un modèle. Il lit ensuite l'état (vide au départ), demande à chaque fournisseur de rafraîchir les ressources connues (ici aucune), puis compare : chaque bloc sans ressource réelle correspondante doit être créé, chaque ressource connue dont la description a changé doit être modifiée ou remplacée, chaque ressource connue dont le bloc a disparu doit être détruite. Les fournisseurs participent au calcul : c'est le fournisseur Scaleway, pas Terraform, qui sait que changer l'image d'une instance impose de la remplacer.
Un graphe, pas une liste. Les références entre ressources (random_pet.suffixe.id dans le contenu du fichier) forment un graphe orienté sans cycle. Terraform crée d'abord ce dont dépendent les autres, en parallèle quand rien ne les relie (dix opérations simultanées par défaut), et détruit dans l'ordre inverse. C'est pourquoi l'ordre des blocs dans les fichiers n'a aucune importance (leçons 3 et 8).
Les fournisseurs sont des programmes séparés. Le binaire terraform ne contient aucun code propre à un cloud. À l'initialisation, il télécharge pour chaque fournisseur un exécutable (terraform-provider-random_v3.9.1_x5, environ 18 Mo pour celui-ci), le lance, et lui parle par un protocole d'appel de procédure à distance fondé sur gRPC. C'est ce découplage qui a permis la bifurcation sans réécrire les fournisseurs : OpenTofu parle le même protocole.
Pièges courants
Croire que le code suffit. Une infrastructure décrite en code mais modifiée aussi à la main n'a que les inconvénients des deux. Le jour où quelqu'un ouvre un port dans la console, le prochain apply le refermera, peut-être au pire moment. Décidez que toute modification passe par le dépôt, et prévoyez la procédure d'urgence (modifier à la main, puis reporter dans le code dans l'heure).
Mélanger les familles d'outils. Terraform sait lancer des scripts sur une machine (les provisioners), mais sa documentation les présente comme un dernier recours : ils ne sont ni idempotents ni visibles dans le plan. L'intérieur des machines relève de cloud-init, d'une image ou d'Ansible.
Lire le plan en diagonale. La ligne Plan: est la plus importante. Un 1 to destroy inattendu sur une base de données, accepté par habitude, est la façon la plus classique de perdre des données avec Terraform. Le cycle de vie et les protections contre la destruction sont l'objet de la leçon 8.
Confondre les deux outils dans une même équipe. Une personne applique avec Terraform, une autre avec OpenTofu, sur le même état : les fichiers de verrouillage divergent, et une fonctionnalité propre à l'un peut rendre l'état illisible pour l'autre. Fixez l'outil et sa version dans le dépôt (leçon 2 et leçon 12).
Sécurité
L'infrastructure as code déplace la sécurité plus qu'elle ne la crée.
- Le dépôt devient la porte d'entrée. Qui peut fusionner dans
signalements-iacpeut ouvrir un port, créer une clé ou détruire une base. Protégez la branche principale comme celle d'une application (relecture obligatoire, vérifications automatiques), et donnez à l'identité qui applique les droits minimaux (leçon 12, et cours cloud, leçon 7). - La relecture devient une mesure de sécurité. Une règle de pare-feu trop large se voit dans une demande de fusion ; elle passe inaperçue dans une console. Des outils d'analyse statique (Trivy, Checkov) repèrent les configurations dangereuses avant l'application.
- Les valeurs par défaut se lisent dans le plan. Le
file_permission = "0777"ci-dessus en est un petit exemple : le fichier sera lisible et modifiable par tous, au masqueumaskprès. Sur un fournisseur cloud, c'est un bucket public, une base ouverte à0.0.0.0/0ou un groupe de sécurité permissif. Le plan est l'endroit où les voir. - L'état contient des secrets. Mots de passe générés, clés, adresses : tout ce que les fournisseurs renvoient est écrit dans l'état, en clair par défaut. Il ne va jamais dans Git, et son stockage se protège (leçons 6 et 7).
- La chaîne d'approvisionnement. Terraform exécute sur votre poste et en CI des binaires de fournisseurs téléchargés depuis un registre. Leur signature est vérifiée à l'installation et leur empreinte est notée dans le fichier de verrouillage (leçon 2) : c'est le même raisonnement que pour les images de conteneurs.
En production
- Commencez petit. Décrire tout l'existant d'un coup est décourageant. Commencez par les ressources nouvelles, puis importez l'existant ressource par ressource (leçon 11).
- Une règle d'équipe écrite. Quel outil, quelle version, qui applique, depuis où (un poste ou la CI), comment on traite une urgence. Sans elle, le dépôt dérive de la réalité en quelques semaines.
- Séparez par rayon d'impact. Une seule configuration pour toute l'organisation rend chaque plan long et chaque erreur grave. On sépare au moins par environnement et par domaine (réseau, données, applications), avec un état par morceau (leçon 7 et cours Terraform avancé).
- Chez Lyneko, le cluster Kapsule
lyneko-apps, son registre et les identités de déploiement sont décrits en code ; les applications qui tournent dans le cluster sont déployées par Argo CD. Les deux mondes se rejoignent par quelques sorties (adresse du registre, identifiants à ranger dans Secret Manager), jamais par des modifications croisées.
Exercices
1. Impératif ou déclaratif (niveau 100). Pour chacun de ces gestes, dites s'il est impératif ou déclaratif, et s'il est idempotent : (a) scw instance server create name=sig-app-1 ... ; (b) un fichier cloud-init contenant packages: [docker.io] ; (c) un script Bash qui fait useradd exploit ; (d) une Application Argo CD qui pointe vers un répertoire de manifestes.
Solution
(a) Impératif, non idempotent : relancée, la commande crée une seconde instance du même nom. (b) Déclaratif (« ce paquet doit être installé ») et idempotent : le module de cloud-init ne réinstalle pas un paquet présent. (c) Impératif, non idempotent : la seconde exécution échoue, l'utilisateur existe déjà ; on le rend idempotent en testant d'abord (id exploit || useradd exploit), ce qui revient à réinventer un outil déclaratif. (d) Déclaratif et idempotent, et même convergent en continu, puisque le contrôleur réconcilie en boucle.
2. Choisir un outil (niveau 100). Trois situations : (a) une collectivité qui gère sa propre infrastructure Scaleway et veut chiffrer son état avec une clé qu'elle maîtrise ; (b) une jeune entreprise qui vend une plateforme où ses clients lancent des déploiements Terraform ; (c) une équipe déjà équipée de HCP Terraform et de ses politiques. Quel outil recommanderiez-vous à chacune, et sur quel argument ?
Solution
(a) OpenTofu, pour son chiffrement de l'état côté client (Terraform ne le propose pas ; il faudrait compter sur le chiffrement du stockage, géré par le fournisseur). (b) La licence est l'argument décisif : une plateforme qui exécute Terraform pour des clients peut être une « offre concurrente » au sens de la BUSL ; OpenTofu, sous MPL, évite la question, sinon il faut une analyse juridique. (c) Terraform, dont l'intégration avec HCP Terraform est propre à l'éditeur ; changer d'outil voudrait dire changer de plateforme. Dans les trois cas, rester dans le langage commun garde la porte ouverte.
3. Lire un plan (niveau 100). Un plan se termine par Plan: 1 to add, 0 to change, 1 to destroy. et la ressource concernée est scaleway_rdb_instance.sig_db, marquée -/+. Que va-t-il se passer, et que faites-vous ?
Solution
La base va être remplacée : détruite puis recréée (le symbole -/+), probablement parce qu'un argument qui ne se modifie pas en place a changé. Une base recréée est une base vide. On n'applique pas : on cherche dans le plan l'attribut marqué # forces replacement, on comprend pourquoi il a changé, et l'on corrige la description, ou l'on organise une migration des données. La leçon 8 montre comment interdire ce genre de destruction (prevent_destroy).
Récapitulatif
- Une infrastructure faite à la main dérive, ne se reproduit pas et ne se relit pas. L'infrastructure as code en fait un texte versionné, relu et appliqué par un outil.
- Déclaratif : on décrit le résultat, l'outil calcule les actions. Idempotent : appliquer deux fois ne change rien. Convergent : l'outil rapproche la réalité de la description.
- Terraform et OpenTofu font du provisionnement ; l'intérieur des machines relève de cloud-init, des images ou d'Ansible, ce qui tourne dans Kubernetes relève d'Argo CD.
- Terraform repose sur un langage (HCL), des fournisseurs séparés et un état. Son flux : écrire, planifier, appliquer.
- Le 10 août 2023, Terraform est passé sous BUSL 1.1 ; OpenTofu, bifurqué de la 1.5.7, est libre (MPL), hébergé par la Linux Foundation, à la CNCF depuis avril 2025. IBM a racheté HashiCorp en février 2025.
- Les deux outils partagent le langage, l'état et les fournisseurs ; chacun a ses fonctionnalités propres. On choisit sur la licence, les fonctionnalités nécessaires et l'écosystème, et l'on reste autant que possible dans le langage commun.
- Un plan se lit en commençant par sa dernière ligne, et un remplacement inattendu se refuse.
Pour aller plus loin
- Kief Morris, Infrastructure as Code, troisième édition (2025) : les principes, au-delà de tout outil.
- Le manifeste OpenTofu et le texte de la licence de Terraform, à lire dans le texte : deux pages chacun.
- Les pages What's new d'OpenTofu et le CHANGELOG de Terraform, pour suivre la divergence.
- La leçon suivante, qui installe l'outil et fait tourner le cycle complet :
init,plan,apply,destroy.
Sources
- Kief Morris, Infrastructure as Code, 3e édition (O'Reilly, mars 2025)
- HashiCorp, What is Terraform? (introduction de la documentation)
- HashiCorp, HashiCorp adopts the Business Source License (10 août 2023)
- hashicorp/terraform, fichier LICENSE (Business Source License 1.1)
- HashiCorp, Licensing FAQ
- OpenTofu, manifeste
- Linux Foundation, Linux Foundation Launches OpenTofu (20 septembre 2023)
- OpenTofu, OpenTofu is going GA (10 janvier 2024)
- CNCF, fiche du projet OpenTofu (Sandbox depuis le 23 avril 2025)
- IBM, IBM Completes Acquisition of HashiCorp (27 février 2025)
- OpenTofu, What's new (versions 1.7 à 1.12) et notes de version 1.13.0
- hashicorp/terraform, CHANGELOG des versions 1.14 et 1.16