🎯 Objectif : À la fin de ce chapitre, tu sauras créer des rôles Ansible propres, structurés et réutilisables d’un projet à l’autre. ⏱️ Durée estimée : 45 minutes | Niveau : Intermédiaire
Tu sais écrire des playbooks. Mais ton playbook de 400 lignes qui installe Nginx, configure le firewall et déploie ton app, personne n’a envie de le maintenir — toi inclus dans 6 mois. Les roles Ansible règlent ce problème : tu découpes ta logique en blocs indépendants, paramétrables et réutilisables. C’est le passage obligé pour faire de l’infra-as-code propre en équipe.
Pourquoi les roles changent tout
Sans roles, ton code Ansible ressemble à un script bash géant : ça marche, mais c’est fragile. Dès que tu ajoutes un deuxième projet ou un collègue, c’est le chaos.
Un role, c’est une fonction pour ton infra. Tu encapsules une responsabilité unique (installer Nginx, configurer un user, déployer une app), tu exposes des variables pour le paramétrage, et tu réutilises ce bloc partout. Plus de copier-coller entre projets.
🔥 Cas réel — Une équipe SRE que je connais maintenait 12 playbooks quasi identiques pour 12 microservices. Passage aux roles : un seul role deploy-app paramétré par variables, 12 fichiers de config de 10 lignes chacun. Temps de maintenance divisé par 5.
Les bénéfices concrets :
- Lisibilité : un playbook principal de 20 lignes au lieu de 500
- Réutilisation : le même role Nginx sur tes environnements dev, staging et prod
- Testabilité : tu testes un role isolément avec Molecule
- Collaboration : chaque role a son owner, son README, ses defaults documentés
Comprendre la structure d’un role
Ansible impose une convention de répertoires stricte. Pas de config à faire : si les dossiers existent au bon endroit, Ansible les trouve tout seul.
Voici l’arborescence type d’un role nginx :
roles/
└── nginx/
├── defaults/main.yml # Variables par défaut (facilement surchargées)
├── vars/main.yml # Variables internes (priorité haute)
├── tasks/main.yml # Tâches à exécuter
├── handlers/main.yml # Actions sur notify (restart, reload)
├── templates/ # Fichiers Jinja2 (.j2)
├── files/ # Fichiers statiques copiés tels quels
├── meta/main.yml # Dépendances et métadonnées
└── README.md
💡 Tip DevOps — defaults/ vs vars/ : mets dans defaults/ tout ce que l’utilisateur du role peut vouloir changer (ports, chemins, feature flags). Réserve vars/ aux valeurs internes que personne ne devrait toucher. La différence est la priorité dans le système de précédence d’Ansible.
🧠 À retenir — Tu n’es pas obligé de créer tous les dossiers. Un role avec juste tasks/main.yml fonctionne. Ajoute les autres au fur et à mesure du besoin.
Commandes essentielles
Pour initialiser un role, ansible-galaxy te génère le squelette complet en une commande :
# Créer la structure d'un role
ansible-galaxy init roles/nginx
# Lister les roles installés
ansible-galaxy list
# Installer un role depuis Galaxy (le registry communautaire)
ansible-galaxy install geerlingguy.docker
⚠️ Attention — ansible-galaxy init crée aussi des dossiers tests/ et des fichiers souvent inutiles. Supprime ce que tu n’utilises pas pour garder ton repo clean.
Pour utiliser un role dans un playbook, la syntaxe est directe :
---
- name: Configurer les serveurs web
hosts: webservers
become: true
roles:
- role: nginx
vars:
nginx_port: 8080
- role: certbot
Tu peux aussi appeler un role dynamiquement dans une tâche avec include_role quand tu as besoin de logique conditionnelle :
- name: Installer le monitoring si activé
ansible.builtin.include_role:
name: monitoring
when: monitoring_enabled | default(false)
Cas concret : role Nginx production-ready
Imaginons que tu dois déployer Nginx sur 30 serveurs avec des configs différentes par environnement. Voici comment structurer ça proprement.
Le fichier defaults/main.yml expose les paramètres que chaque équipe peut surcharger :
---
nginx_port: 80
nginx_worker_processes: auto
nginx_worker_connections: 1024
nginx_server_tokens: "off"
nginx_client_max_body_size: "64m"
nginx_gzip: true
nginx_vhosts: []
Le fichier tasks/main.yml contient la logique d’installation et de configuration. Chaque tâche qui modifie la config notifie un handler pour recharger Nginx :
---
- name: Installer Nginx
ansible.builtin.apt:
name: nginx
state: present
update_cache: true
cache_valid_time: 3600
- name: Déployer la configuration principale
ansible.builtin.template:
src: nginx.conf.j2
dest: /etc/nginx/nginx.conf
validate: nginx -t -c %s
notify: Reload nginx
- name: Configurer les vhosts
ansible.builtin.template:
src: vhost.conf.j2
dest: "/etc/nginx/sites-available/{{ item.server_name }}.conf"
loop: "{{ nginx_vhosts }}"
notify: Reload nginx
- name: Activer les vhosts
ansible.builtin.file:
src: "/etc/nginx/sites-available/{{ item.server_name }}.conf"
dest: "/etc/nginx/sites-enabled/{{ item.server_name }}.conf"
state: link
loop: "{{ nginx_vhosts }}"
- name: Démarrer et activer Nginx
ansible.builtin.service:
name: nginx
state: started
enabled: true
Et le fichier handlers/main.yml gère les redémarrages. Le handler ne se déclenche qu’une seule fois en fin de play, même si plusieurs tâches l’appellent :
---
- name: Reload nginx
ansible.builtin.service:
name: nginx
state: reloaded
- name: Restart nginx
ansible.builtin.service:
name: nginx
state: restarted
🔥 Cas réel — L’option validate: nginx -t -c %s dans la tâche template est un filet de sécurité crucial. Ansible vérifie la syntaxe de ta config avant de l’écrire. Sans ça, un template cassé = Nginx qui refuse de reload = downtime.
Pièges fréquents
1. Confondre defaults/ et vars/
Les variables dans vars/ écrasent presque tout, y compris ce que l’utilisateur passe dans son playbook. Si tu mets un port dans vars/main.yml, personne ne pourra le surcharger facilement. Règle simple : 90% de tes variables vont dans defaults/.
⚠️ Attention — L’ordre de précédence des variables Ansible a 22 niveaux. Retiens juste : defaults < variables de playbook < vars < extra-vars CLI. Le reste, consulte la doc quand tu as un doute.
2. Handlers qui ne se déclenchent pas
Un handler ne s’exécute que si la tâche qui le notifie a effectivement changé quelque chose (status changed). Si ta config est déjà à jour, pas de notify, pas de reload. C’est voulu — mais ça surprend.
3. Roles trop gros Un role qui installe Nginx, configure le SSL, déploie ton app et met en place le monitoring fait trop de choses. Un role = une responsabilité. Découpe.
💡 Tip DevOps — Nomme tes roles avec un préfixe si tu en as beaucoup : infra-nginx, app-api, monitoring-prometheus. Ça aide à naviguer dans un roles/ avec 20+ entrées.
4. Oublier le README
Un role sans documentation est un role que personne (y compris toi dans 3 mois) ne réutilisera. Liste les variables de defaults/, donne un exemple de playbook, mentionne les dépendances.
Exercice pratique
Crée un role app-deploy qui :
- Installe les dépendances système (paquet
gitetpython3-pip) - Clone un dépôt Git dans
/opt/myapp(URL paramétrable viadefaults/) - Copie un fichier de config depuis un template Jinja2 avec les variables d’environnement
- Redémarre un service
myappvia un handler quand la config change
Teste-le avec un playbook qui appelle ton role sur localhost :
---
- name: Déployer mon application
hosts: localhost
connection: local
become: true
roles:
- role: app-deploy
vars:
app_repo: "https://github.com/ton-user/ton-app.git"
app_env: production
🧠 À retenir — Les roles sont le building block fondamental d’une infra Ansible maintenable. Un role = une responsabilité, des defaults documentés, un README, et des handlers pour les side-effects. Commence simple, découpe quand ça grossit. Dans le prochain chapitre, on explore Ansible Galaxy pour tirer parti des roles communautaires et accélérer tes déploiements.
🖥️ Pratique sur ton propre serveur
Pour suivre Ansible en conditions réelles, tu as besoin d'un VPS. DigitalOcean offre 200$ de crédit gratuit pour démarrer.
Contenu réservé aux abonnés
Ce chapitre fait partie de la formation complète. Abonne-toi pour débloquer tous les contenus.
Débloquer pour 29 CHF/moisLe chapitre 1 de chaque formation est gratuit.
Série pas encore débloquée
Termine la série prérequise d'abord pour accéder à ce contenu.
Aller à la série prérequiseSérie : Ansible
3 / 8Sur cette page
Articles liés
Déploiement avancé et orchestration
Stratégies de déploiement rolling et canary, intégration CI/CD avec GitHub Actions, et AWX / Ansible Automation Platform.
Variables et priorités
Maîtrise la hiérarchie des variables Ansible, host_vars et group_vars, et sécurise tes secrets avec Ansible Vault.
Ansible Galaxy et collections
Exploite Ansible Galaxy pour réutiliser des roles communautaires, gère les dépendances et déploie une stack LAMP complète avec des roles.