Différences
Ci-dessous, les différences entre deux révisions de la page.
| Les deux révisions précédentes Révision précédente Prochaine révision | Révision précédente | ||
| eadl:bloc4:fm2:td2 [2026/05/03 14:35] – [7. Compréhension] jcheron | eadl:bloc4:fm2:td2 [2026/05/13 16:52] (Version actuelle) – [13.3 Création d’un composant réutilisable] jcheron | ||
|---|---|---|---|
| Ligne 1: | Ligne 1: | ||
| - | ====== TD2 : Créer un module Terraform réutilisable | + | ====== TD2 : Bases du provisionning |
| - | ===== Objectifs | + | ===== Terraform et Modularisation |
| * Comprendre l’intérêt des variables et des outputs | * Comprendre l’intérêt des variables et des outputs | ||
| Ligne 179: | Ligne 179: | ||
| </ | </ | ||
| - | <WRAP round help> | + | <WRAP round question> |
| Questions : | Questions : | ||
| Ligne 193: | Ligne 193: | ||
| </ | </ | ||
| - | <WRAP round help> | + | <WRAP round question> |
| Question : | Question : | ||
| Ligne 367: | Ligne 367: | ||
| Terraform crée une instance par entrée dans la map. | Terraform crée une instance par entrée dans la map. | ||
| </ | </ | ||
| - | <WRAP round help> | + | <WRAP round question> |
| Question : | Question : | ||
| Ligne 413: | Ligne 413: | ||
| ==== 11.5 Analyse ==== | ==== 11.5 Analyse ==== | ||
| - | <WRAP round help> | + | <WRAP round question> |
| * Si vous supprimez un environnement de la map, que va faire Terraform ? | * Si vous supprimez un environnement de la map, que va faire Terraform ? | ||
| * Que se passe-t-il si vous renommez une clé ? | * Que se passe-t-il si vous renommez une clé ? | ||
| Ligne 419: | Ligne 419: | ||
| </ | </ | ||
| - | ==== 11.6 Comparaison | + | ==== 11.6 Limites |
| - | <WRAP round help> | + | <WRAP round question> |
| Question : | Question : | ||
| - | * Dans un projet réel avec plusieurs | + | * Votre équipe utilise cette approche avec '' |
| + | Un développeur renomme la clé '' | ||
| + | |||
| + | * Que va faire Terraform lors du prochain apply ? | ||
| + | * Pourquoi ce comportement peut-il être dangereux en production ? | ||
| + | * Comment éviter ce problème dans un projet réel ? | ||
| + | </ | ||
| + | |||
| + | |||
| + | ===== 12. Extension — Terraform → Ansible ===== | ||
| + | |||
| + | ==== Objectifs ==== | ||
| + | |||
| + | * Réutiliser les outputs Terraform | ||
| + | * Introduire Ansible comme outil de configuration | ||
| + | * Comprendre l’intégration entre outils | ||
| + | * Comparer deux approches d’architecture | ||
| + | |||
| + | |||
| + | ==== 12.1 Contexte ==== | ||
| + | |||
| + | Vous avez déployé | ||
| + | |||
| + | Chaque conteneur est accessible via une URL différente : | ||
| + | |||
| + | * frontend → http:// | ||
| + | * backend → http:// | ||
| + | * data → http:// | ||
| + | |||
| + | Problème : | ||
| + | |||
| + | * toutes les pages nginx sont identiques | ||
| + | * impossible | ||
| + | |||
| + | Objectif : | ||
| + | |||
| + | Configurer dynamiquement chaque conteneur avec Ansible. | ||
| + | |||
| + | |||
| + | ==== 12.2 Mise en place d’Ansible ==== | ||
| + | |||
| + | Créer un dossier : | ||
| + | |||
| + | <sxh bash; | ||
| + | mkdir ansible | ||
| + | cd ansible | ||
| + | </ | ||
| + | |||
| + | Créer un fichier '' | ||
| + | |||
| + | <sxh yaml> | ||
| + | - name: Configuration des conteneurs nginx | ||
| + | hosts: all | ||
| + | gather_facts: | ||
| + | |||
| + | tasks: | ||
| + | - name: Copier une page HTML personnalisée | ||
| + | copy: | ||
| + | content: | | ||
| + | < | ||
| + | < | ||
| + | dest: / | ||
| + | </ | ||
| + | |||
| + | <WRAP round info> | ||
| + | Chaque conteneur aura une page différente en fonction de son nom. | ||
| + | |||
| + | Vous utilisez ici les variables Ansible : | ||
| + | |||
| + | * inventory_hostname → nom de l’hôte | ||
| + | * ansible_port → port utilisé | ||
| + | </ | ||
| + | |||
| + | ==== 12.3 Problème à résoudre ==== | ||
| + | |||
| + | Ansible a besoin d’un **inventory** pour savoir : | ||
| + | |||
| + | * quelles machines cibler | ||
| + | * comment s’y connecter | ||
| + | |||
| + | Or, ces informations sont connues par Terraform. | ||
| + | |||
| + | Comment faire le lien entre les deux ? | ||
| + | |||
| + | |||
| + | ==== 12.4 Approche A — Génération via Terraform ==== | ||
| + | |||
| + | Modifier Terraform pour générer un fichier '' | ||
| + | |||
| + | Indice : | ||
| + | |||
| + | * utiliser '' | ||
| + | * utiliser '' | ||
| + | |||
| + | Exemple attendu : | ||
| + | |||
| + | <sxh ini> | ||
| + | [web] | ||
| + | frontend ansible_host=localhost ansible_port=8080 | ||
| + | backend ansible_host=localhost ansible_port=8081 | ||
| + | data ansible_host=localhost ansible_port=8082 | ||
| + | </ | ||
| + | |||
| + | |||
| + | ==== 12.5 Approche B — Approche découplée ==== | ||
| + | |||
| + | Utiliser les outputs Terraform pour générer l’inventory avec un script externe. | ||
| + | |||
| + | <sxh bash; | ||
| + | terraform output -json > outputs.json | ||
| + | </ | ||
| + | |||
| + | Transformer ce fichier en '' | ||
| + | |||
| + | Langage au choix : | ||
| + | |||
| + | * bash | ||
| + | * python | ||
| + | * jq | ||
| + | |||
| + | ==== 12.6 Exécution ==== | ||
| + | |||
| + | Lancer Ansible : | ||
| + | |||
| + | <sxh bash; | ||
| + | ansible-playbook -i inventory.ini playbook.yml | ||
| + | </ | ||
| + | |||
| + | <WRAP round todo> | ||
| + | Vérifier : | ||
| + | |||
| + | * chaque URL affiche un contenu différent | ||
| + | </ | ||
| + | |||
| + | |||
| + | ==== 12.7 Analyse ==== | ||
| + | |||
| + | <WRAP round question> | ||
| + | Questions : | ||
| + | |||
| + | * Quelle approche est la plus simple à mettre en place ? | ||
| + | * Quelle approche est la plus maintenable ? | ||
| + | * Que se passe-t-il si vous ajoutez un nouvel environnement ? | ||
| + | * Quelle solution limite le couplage entre Terraform et Ansible ? | ||
| + | * Dans un projet réel, laquelle choisiriez-vous ? Pourquoi ? | ||
| + | </ | ||
| + | |||
| + | |||
| + | ==== 12.8 Bonus ==== | ||
| + | |||
| + | <WRAP round todo> | ||
| + | * Ajouter une variable Terraform '' | ||
| + | * L’afficher dans la page HTML via Ansible | ||
| + | </ | ||
| + | |||
| + | <WRAP round info> | ||
| + | Objectif : | ||
| + | |||
| + | Comprendre comment une information définie dans Terraform | ||
| + | peut être utilisée dans Ansible. | ||
| + | |||
| + | C’est un cas réel fréquent en DevOps. | ||
| + | </ | ||
| + | |||
| + | ===== 13. Extension : Alternative avec Pulumi (approche orientée développeur) ===== | ||
| + | |||
| + | ==== Objectifs ==== | ||
| + | |||
| + | * Découvrir une alternative à Terraform | ||
| + | * Comprendre la différence déclaratif vs programmation | ||
| + | * Réécrire une logique Terraform avec un langage classique | ||
| + | * Identifier | ||
| + | |||
| + | ==== 13.1 Principe ==== | ||
| + | |||
| + | Contrairement à Terraform : | ||
| + | |||
| + | * Terraform → langage déclaratif (HCL) | ||
| + | * Pulumi → langage de programmation (TypeScript ici) | ||
| + | |||
| + | Un module Terraform devient : | ||
| + | |||
| + | * une fonction | ||
| + | * ou une classe | ||
| + | |||
| + | Un '' | ||
| + | |||
| + | * une boucle classique | ||
| + | |||
| + | ==== 13.2 Initialisation du projet ==== | ||
| + | |||
| + | <sxh bash; | ||
| + | mkdir pulumi-td2 | ||
| + | cd pulumi-td2 | ||
| + | |||
| + | pulumi new typescript | ||
| + | </ | ||
| + | |||
| + | Choisir : | ||
| + | |||
| + | * project name : pulumi-td2 | ||
| + | * stack : dev | ||
| + | |||
| + | Installer le provider Docker : | ||
| + | |||
| + | <sxh bash; | ||
| + | npm install @pulumi/ | ||
| + | </ | ||
| + | |||
| + | ==== 13.3 Création d’un composant réutilisable ==== | ||
| + | |||
| + | Créer un fichier '' | ||
| + | |||
| + | <sxh ts> | ||
| + | import * as docker from " | ||
| + | |||
| + | export function createNginx(name: | ||
| + | |||
| + | const image = new docker.RemoteImage(name, | ||
| + | name: " | ||
| + | }); | ||
| + | |||
| + | const container = new docker.Container(name, | ||
| + | image: image.imageId, | ||
| + | ports: [ | ||
| + | { | ||
| + | internal: 80, | ||
| + | external: port, | ||
| + | }, | ||
| + | ], | ||
| + | }); | ||
| + | |||
| + | return { | ||
| + | url: `http:// | ||
| + | }; | ||
| + | } | ||
| + | </ | ||
| + | |||
| + | <WRAP round info> | ||
| + | En Pulumi, on remplace | ||
| + | </ | ||
| + | |||
| + | ==== 13.4 Utilisation (équivalent main.tf) ==== | ||
| + | |||
| + | Modifier '' | ||
| + | |||
| + | <sxh ts> | ||
| + | import { createNginx } from " | ||
| + | |||
| + | const frontend = createNginx(" | ||
| + | const backend = createNginx(" | ||
| + | |||
| + | export const frontendUrl = frontend.url; | ||
| + | export const backendUrl = backend.url; | ||
| + | </ | ||
| + | |||
| + | ==== 13.5 Exécution ==== | ||
| + | |||
| + | <sxh bash; | ||
| + | pulumi up | ||
| + | </ | ||
| + | |||
| + | ==== 13.6 Version dynamique ==== | ||
| + | |||
| + | Equivalent du '' | ||
| + | |||
| + | <sxh ts> | ||
| + | import { createNginx } from " | ||
| + | |||
| + | const environments: | ||
| + | frontend: 8080, | ||
| + | backend: 8081, | ||
| + | data: 8082, | ||
| + | }; | ||
| + | |||
| + | const urls: Record< | ||
| + | |||
| + | for (const [name, port] of Object.entries(environments)) { | ||
| + | const nginx = createNginx(name, | ||
| + | urls[name] = nginx.url; | ||
| + | } | ||
| + | |||
| + | export { urls }; | ||
| + | </ | ||
| + | |||
| + | ==== 13.7 Validation des erreurs ==== | ||
| + | |||
| + | <sxh ts> | ||
| + | const ports = Object.values(environments); | ||
| + | |||
| + | if (new Set(ports).size !== ports.length) { | ||
| + | throw new Error(" | ||
| + | } | ||
| + | </ | ||
| + | |||
| + | <WRAP round info> | ||
| + | Contrairement à Terraform, Pulumi permet d’ajouter des validations personnalisées | ||
| + | avant même le déploiement. | ||
| + | </ | ||
| + | |||
| + | ==== 13.8 Comparaison ==== | ||
| + | |||
| + | <WRAP round question> | ||
| + | Questions : | ||
| + | |||
| + | * Qu’est-ce qui est plus simple à écrire ? | ||
| + | * Qu’est-ce qui est plus lisible ? | ||
| + | * Où Pulumi est-il plus puissant ? | ||
| + | * Où Terraform est-il plus prévisible ? | ||
| + | </ | ||
| + | |||
| + | ==== 13.9 Analyse ==== | ||
| + | |||
| + | <WRAP round info> | ||
| + | Pulumi permet : | ||
| + | |||
| + | * d’utiliser des structures natives (boucles, fonctions) | ||
| + | * de factoriser facilement le code | ||
| + | * d’ajouter des validations complexes | ||
| + | |||
| + | Mais : | ||
| + | |||
| + | * nécessite des compétences en développement | ||
| + | * peut introduire de la complexité inutile | ||
| + | </ | ||
| + | |||
| + | ==== 13.10 Conclusion ==== | ||
| + | |||
| + | <WRAP round info> | ||
| + | Terraform et Pulumi répondent au même besoin avec deux approches : | ||
| + | |||
| + | * Terraform → simplicité, | ||
| + | * Pulumi → flexibilité, | ||
| + | |||
| + | Dans un projet réel : | ||
| + | |||
| + | * Terraform est souvent utilisé côté Ops | ||
| + | * Pulumi est pertinent pour des équipes orientées développement | ||
| </ | </ | ||