Architecture et profils¶
Mise en place de l'arborescence Ansible, du système de state par variables prefixees, et des profils de configuration.
Couches d'infrastructure¶
graph TB
subgraph "Image VDI Linux"
SEC["Securite<br/>fail2ban, firewall, SSH"]
SES["Service de session<br/>XFCE + xRDP"]
APP["Services applicatifs<br/>LibreOffice, Firefox, VS Code"]
SHR["Shared services<br/>Podman + QEMU"]
K8S["Orchestration<br/>K3s standalone"]
end
SEC --> SES
SES --> APP
SES --> SHR
SHR --> K8S | Couche | Rôle Ansible | Responsabilité |
|---|---|---|
| Service de session | desktop | XFCE, xRDP, locale, clavier |
| Service applicatif | apps, k3s | Outils bureautiques, dev, orchestration |
| Shared services | podman, qemu | Conteneurisation, compilation croisee |
| Sécurité | security | fail2ban, firewall, SSH hardening |
Arborescence des rôles¶
Créez la structure complète :
mkdir -p packer-vdi-linux/{packer,ansible/{profiles,group_vars}}
mkdir -p packer-vdi-linux/ansible/roles/{desktop,apps,podman,qemu,k3s,security}/{tasks,handlers,defaults}
Structure cible :
ansible/
├── playbook.yml
├── profiles/
│ ├── developer.yml
│ ├── office.yml
│ └── full.yml
├── group_vars/
│ ├── ubuntu.yml
│ └── rocky.yml
└── roles/
├── desktop/
│ ├── tasks/
│ │ ├── main.yml
│ │ └── validate.yml
│ ├── handlers/main.yml
│ └── defaults/main.yml
├── apps/
│ ├── tasks/
│ │ ├── main.yml
│ │ └── validate.yml
│ └── defaults/main.yml
├── podman/
│ ├── tasks/
│ │ ├── main.yml
│ │ └── validate.yml
│ └── defaults/main.yml
├── qemu/
│ ├── tasks/
│ │ ├── main.yml
│ │ └── validate.yml
│ └── defaults/main.yml
├── k3s/
│ ├── tasks/
│ │ ├── main.yml
│ │ └── validate.yml
│ └── defaults/main.yml
└── security/
├── tasks/
│ ├── main.yml
│ └── validate.yml
├── handlers/main.yml
└── defaults/main.yml
Système de state¶
Chaque rôle utilise des variables prefixees par son nom. Cela evite les collisions et rend la configuration lisible :
# Variables du role desktop
desktop_enabled: true
desktop_xrdp_port: 3389
desktop_locale: "fr_FR.UTF-8"
desktop_keyboard_layout: "fr"
desktop_run_rdp_test: false
# Variables du role apps
apps_enabled: true
apps_libreoffice: true
apps_vscode: true
apps_firefox: true
apps_test_user: "vdi-user"
# Variables du role podman
podman_enabled: true
podman_rootless: true
podman_registries: ["docker.io", "ghcr.io"]
podman_test_user: "vdi-user"
# Variables du role qemu
qemu_enabled: true
qemu_user_static: true
qemu_system: false
# Variables du role k3s
k3s_enabled: false
k3s_rootless: true
# Variables du role security
security_enabled: true
security_fail2ban: true
security_ufw: true
security_firewalld: true
security_ssh_hardening: true
Convention de nommage
Préfixe = nom du rôle. Exemple : podman_rootless, desktop_locale, k3s_enabled. Aucune variable ne peut entrer en conflit avec un autre rôle.
Profils¶
Un profil est un fichier YAML qui définit un ensemble cohérent de flags. Les flags individuels peuvent être overrides en extra-vars.
Profil developer¶
# profiles/developer.yml
desktop_enabled: true
desktop_locale: "fr_FR.UTF-8"
apps_enabled: true
apps_vscode: true
apps_libreoffice: false
apps_firefox: true
podman_enabled: true
podman_rootless: true
qemu_enabled: true
qemu_user_static: true
qemu_system: false
k3s_enabled: true
k3s_rootless: true
security_enabled: true
Profil office¶
# profiles/office.yml
desktop_enabled: true
desktop_locale: "fr_FR.UTF-8"
apps_enabled: true
apps_vscode: false
apps_libreoffice: true
apps_firefox: true
podman_enabled: false
qemu_enabled: false
k3s_enabled: false
security_enabled: true
Profil full¶
# profiles/full.yml
desktop_enabled: true
desktop_locale: "fr_FR.UTF-8"
apps_enabled: true
apps_vscode: true
apps_libreoffice: true
apps_firefox: true
podman_enabled: true
podman_rootless: true
qemu_enabled: true
qemu_user_static: true
qemu_system: true
k3s_enabled: true
k3s_rootless: true
security_enabled: true
Playbook principal¶
Le playbook charge le profil puis exécuté les rôles conditionnellement :
# ansible/playbook.yml
---
- name: Build VDI Linux image
hosts: all
become: true
pre_tasks:
- name: Charger le profil
ansible.builtin.include_vars:
file: "profiles/{{ profile | default('full') }}.yml"
roles:
- role: desktop
when: desktop_enabled | default(false)
- role: apps
when: apps_enabled | default(false)
- role: podman
when: podman_enabled | default(false)
- role: qemu
when: qemu_enabled | default(false)
- role: k3s
when: k3s_enabled | default(false)
- role: security
when: security_enabled | default(false)
Multi-OS avec group_vars¶
Les différences entre Ubuntu et Rocky sont isolées dans group_vars/ :
# group_vars/ubuntu.yml
desktop_packages:
- xfce4
- xfce4-goodies
- xrdp
- xorgxrdp
desktop_xrdp_service: xrdp
security_firewall_package: ufw
security_firewall_service: ufw
pkg_manager: apt
podman_package: podman
qemu_user_static_package: qemu-user-static
# group_vars/rocky.yml
desktop_packages:
- "@Xfce"
- xrdp
- xorgxrdp
desktop_xrdp_service: xrdp
security_firewall_package: firewalld
security_firewall_service: firewalld
pkg_manager: dnf
podman_package: podman
qemu_user_static_package: qemu-user-static
Détection de l'OS
Ansible détecté automatiquement ansible_os_family (Debian ou RedHat). Les group_vars sont charges selon l'inventaire ou via un pre_task qui set le groupe dynamiquement.
Assertions¶
Chaque rôle contient un fichier tasks/validate.yml exécuté en fin de rôle. Les assertions sont a deux niveaux :
| Niveau | Objectif | Exemple |
|---|---|---|
| Technique | Le composant est installé et actif | podman --version retourné un résultat |
| Cas d'usage | Le parametrage permet le use-case attendu | Un user non-root peut lancer un conteneur Podman |