NixOS : immuable et reproductible
Mise à jour :

NixOS est une distribution Linux basée sur le gestionnaire de paquets fonctionnel Nix. Ce qui la rend unique ? Tout le système se déclare dans des fichiers de configuration : du bootloader aux services en passant par les utilisateurs. On appelle ça l’approche déclarative.
J’utilise NixOS depuis quelques temps maintenant pour mon poste de travail personnel. Ce que j’apprécie particulièrement, c’est la possibilité de reconstruire une machine identique à partir d’un simple fichier de configuration versionné dans Git. Pas de surprise, pas de “ça marche pas sur ma machine”.
Pourquoi NixOS pour le DevSecOps ?
Avant de plonger dans la technique, laissez-moi vous expliquer pourquoi NixOS m’intéresse particulièrement dans un contexte DevSecOps :
- Reproductibilité totale : deux machines avec la même configuration sont identiques, byte pour byte
- Rollback instantané : retour à un état précédent en une commande si quelque chose casse
- Audit facilité : la configuration complète du système est versionnée dans Git
- Surface d’attaque réduite : seuls les paquets déclarés sont présents, rien de plus
C’est particulièrement utile pour les bastions et les machines d’administration où la sécurité et la reproductibilité sont primordiales.
Installation de Nix
Avant de pouvoir construire des images NixOS, il faut installer le gestionnaire de paquets Nix sur votre poste de développement. Nix propose deux modes d’installation :
- Single-user : installation dans le répertoire home de l’utilisateur, sans daemon
- Multi-user : installation système avec daemon, pour les machines partagées
Comme je ne partage pas ma machine et que je suis le seul utilisateur, j’installe en mode single-user. C’est plus simple et ça évite de faire tourner un daemon en permanence :
# Installation single-user (sans daemon)sh <(curl -L https://nixos.org/nix/install) --no-daemonL’installateur crée les répertoires nécessaires et ajoute la ligne de chargement du profil dans votre shell. Il suffit d’ouvrir un nouveau terminal pour que Nix soit disponible.
Pour activer les flakes (nous verrons plus tard à quoi ça sert), créez le fichier de configuration :
# Créer le répertoire de configurationmkdir -p ~/.config/nix
# Activer les fonctionnalités expérimentalescat > ~/.config/nix/nix.conf << 'EOF'experimental-features = nix-command flakesEOFVérifiez que tout fonctionne :
# Tester l'installationnix --version
# Tester les flakes avec un hello worldnix run nixpkgs#helloSi la commande nix run affiche “Bonjour, le monde !”, c’est bon, vous êtes prêt !
Comment fonctionne Nix ?
Avant d’aller plus loin, prenons le temps de comprendre comment Nix fonctionne sous le capot. C’est important, car une fois ces concepts assimilés, tout le reste devient logique.
Le Nix Store : le cœur du système
Contrairement à apt ou dnf qui installent les paquets dans /usr/bin,
/usr/lib, etc., Nix stocke tout dans /nix/store/. Chaque paquet a son
propre répertoire avec un nom unique basé sur un hash cryptographique :
# Exemple de chemin dans le store/nix/store/zpzfafanlmgkf1w3m3hbm8n8413hq5mc-firewall-reloadCe hash (la partie zpzfafanlmgkf1w3m3hbm8n8413hq5mc) est calculé à partir de
tout ce qui entre dans la construction du paquet : les sources, les
dépendances, les options de compilation, le compilateur utilisé… Du coup,
deux builds identiques produisent exactement le même résultat, byte pour
byte. C’est ce qu’on appelle la reproductibilité.
Pourquoi c’est génial ? Plusieurs versions d’un même paquet coexistent sans conflit. Vous pouvez avoir Firefox 120 et Firefox 115 installés en même temps, chacun dans son répertoire. Pas de “DLL hell” comme sous Windows, pas de conflits de dépendances comme avec pip ou npm où installer un paquet peut en casser un autre.
Les profils et les générations
Mais alors, comment le système sait quel Firefox lancer quand vous tapez
firefox ? C’est là qu’interviennent les profils. Un profil est simplement
un ensemble de liens symboliques qui pointent vers les paquets dans le store.
Quand vous installez ou supprimez un paquet, Nix crée une nouvelle génération de votre profil. L’ancienne génération reste disponible. Si quelque chose ne va pas après une mise à jour, vous pouvez revenir en arrière instantanément :
# Lister les générationsnix-env --list-generations
# Revenir à la génération précédentenix-env --rollback
# Ou revenir à une génération spécifiquenix-env --switch-generation 42C’est exactement le même principe pour NixOS au niveau système : chaque
nixos-rebuild switch crée une nouvelle génération. Au boot, vous pouvez
choisir quelle génération démarrer dans le menu GRUB.
Configuration déclarative
Sur une distribution classique, pour configurer un serveur SSH, vous :
- Installez le paquet avec
apt install openssh-server - Éditez
/etc/ssh/sshd_config - Lancez
systemctl enable --now sshd
Sur NixOS, tout ça se fait en une seule ligne dans votre configuration :
services.openssh.enable = true;NixOS s’occupe d’installer le paquet, de générer la configuration, de créer le service systemd et de l’activer. Voici un exemple plus complet :
# Configuration NixOS minimale - /etc/nixos/configuration.nix{ config, pkgs, ... }:{ # Bootloader - systemd-boot pour les machines UEFI boot.loader.systemd-boot.enable = true;
# Nom de la machine networking.hostName = "bastion";
# Firewall activé par défaut, on ferme tout sauf SSH networking.firewall.enable = true;
# SSH avec quelques options de sécurité services.openssh.enable = true;
# Paquets disponibles pour tous les utilisateurs environment.systemPackages = with pkgs; [ vim git htop ];
# Création d'un utilisateur admin users.users.admin = { isNormalUser = true; extraGroups = [ "wheel" ]; # wheel = sudo };
# Version de NixOS utilisée lors de l'installation initiale # Ne pas changer après l'installation ! system.stateVersion = "24.11";}Pour appliquer cette configuration :
# Reconstruire et activer la configurationsudo nixos-rebuild switchSimple, non ? Tout est dans un fichier, versionnable dans Git, auditable. Si je
veux ajouter un paquet, je l’ajoute à la liste environment.systemPackages et
je relance la commande. Si je veux activer un service, j’ajoute
services.monservice.enable = true;. Je sais, vous allez me dire: “encore un
langage à apprendre…”. Oui, mais le langage Nix est simple et dédié à la
gestion de paquets et de configurations. Et surtout, le gain en robustesse et en
maintenabilité est énorme.
L’énorme avantage, c’est que je peux prendre ce fichier, le copier sur une autre machine, et obtenir exactement la même configuration. Pas de “j’ai oublié d’installer tel truc” ou “j’ai modifié tel fichier de config, mais je ne me souviens plus lequel”.
Les Flakes : le standard moderne
Les Flakes représentent l’évolution majeure de Nix depuis 2020. Ils sont encore marqués “expérimentaux”, mais tout le monde les utilise en production.
Le problème qu’ils résolvent ? Avant les flakes, quand vous faisiez nix-build,
le résultat dépendait de la version de nixpkgs installée sur votre machine via
les channels. Deux personnes avec des channels différents obtenaient des
résultats différents. Pas très reproductible…
Les flakes apportent le verrouillage des dépendances via un fichier
flake.lock, exactement comme package-lock.json pour npm ou poetry.lock
pour Python. Vous déclarez vos dépendances dans flake.nix, et Nix génère
automatiquement flake.lock avec les versions exactes (commits Git, hashes…).
# flake.nix minimal{ description = "Configuration NixOS moderne";
# Les inputs sont les dépendances du flake inputs = { # On utilise nixpkgs version 24.11 nixpkgs.url = "github:NixOS/nixpkgs/nixos-24.11"; };
# Les outputs sont ce que le flake produit outputs = { self, nixpkgs }: { # Une configuration NixOS nommée "bastion" nixosConfigurations.bastion = nixpkgs.lib.nixosSystem { system = "x86_64-linux"; modules = [ ./configuration.nix ]; }; };}Le fichier flake.lock généré automatiquement ressemble à ça :
{ "nodes": { "nixpkgs": { "locked": { "lastModified": 1701282334, "narHash": "sha256-MxCVrXY6v...", "rev": "057f9aecfb71c4437d2b27d3323df7f93c010b7e", "type": "github" } } }}Plus de surprise lors d’un déploiement : même flake.lock = même système.
Quand vous voulez mettre à jour, vous faites explicitement nix flake update,
vous testez, et vous committez le nouveau flake.lock.
NixOS : un système d’exploitation pas comme les autres
Maintenant qu’on a vu comment fonctionne Nix le gestionnaire de paquets, parlons de NixOS la distribution Linux. Car NixOS pousse le concept beaucoup plus loin : ce n’est pas juste Nix installé sur une base Debian ou Fedora, c’est un système entièrement repensé.
Qu’est-ce qu’un OS “immuable” ?
On entend souvent parler de NixOS comme d’un OS “immuable”. C’est un peu un abus de langage, mais l’idée est là : sur NixOS, vous ne modifiez pas le système en place, vous déclarez un nouvel état et NixOS construit ce nouvel état à côté de l’ancien.
Concrètement, quand vous faites nixos-rebuild switch :
- NixOS lit votre configuration (
/etc/nixos/configuration.nixou votre flake) - Il calcule tout ce qui doit être construit ou téléchargé
- Il télécharge/construit les paquets manquants dans
/nix/store/ - Il crée une nouvelle “génération” du système avec des liens symboliques
- Il active cette nouvelle génération
L’ancienne génération reste intacte dans /nix/store/. Rien n’est supprimé,
rien n’est modifié. C’est pour ça qu’on peut revenir en arrière instantanément.
Le processus de boot
Au démarrage, NixOS présente un menu (GRUB ou systemd-boot) avec la liste des générations disponibles :
NixOS - Configuration 147 (2024-11-28)NixOS - Configuration 146 (2024-11-25)NixOS - Configuration 145 (2024-11-20)...Chaque génération est un système complet et fonctionnel. Si la dernière mise à jour a cassé quelque chose, vous redémarrez sur une génération précédente et tout remarche. Pas besoin de snapshots Btrfs ou de sauvegardes : c’est intégré au système.
En interne, chaque génération pointe vers un chemin dans le store :
# Voir les générations systèmels -la /nix/var/nix/profiles/system-*
# La génération actuellereadlink /run/current-system# /nix/store/abc123...-nixos-system-bastion-24.11Organisation du système de fichiers
Sur une distribution classique, la configuration est éparpillée partout :
/etc/ssh/sshd_config, /etc/nginx/nginx.conf, /etc/systemd/system/… Sur
NixOS, ces fichiers existent aussi, mais ils sont générés à partir de votre
configuration Nix.
Voici comment NixOS organise les choses :
| Répertoire | Contenu | Modifiable ? |
|---|---|---|
/nix/store/ | Tous les paquets et configurations générées | Non (read-only) |
/etc/ | Liens symboliques vers /nix/store/ | Non (régénéré) |
/run/ | État temporaire du système actuel | Non |
/home/ | Données utilisateurs | Oui |
/var/ | Données variables (logs, bases de données) | Oui |
/tmp/ | Fichiers temporaires | Oui |
La partie “immuable” c’est /nix/store/ et /etc/. Les données utilisateurs
dans /home/ et les données applicatives dans /var/ restent modifiables, bien
sûr.
Comment /etc/ fonctionne
Sur NixOS, /etc/ n’est pas un répertoire classique. C’est un mélange de liens
symboliques vers le store et de fichiers générés au boot.
Par exemple, si vous activez SSH :
services.openssh.enable = true;services.openssh.settings.PermitRootLogin = "no";NixOS génère /etc/ssh/sshd_config avec le contenu approprié. Ce fichier pointe
vers quelque chose comme :
ls -la /etc/ssh/sshd_configlrwxrwxrwx 1 root root 27 1 déc. 16:10 ssh/sshd_config -> /etc/static/ssh/sshd_configSi vous éditez /etc/ssh/sshd_config à la main, vos modifications seront
écrasées au prochain nixos-rebuild. C’est voulu ! La configuration doit
passer par les fichiers Nix pour être reproductible.
Les services systemd
NixOS utilise systemd comme init system, mais là encore avec une approche déclarative. Quand vous écrivez :
services.nginx.enable = true;services.nginx.virtualHosts."example.com" = { root = "/var/www/example";};NixOS génère automatiquement :
- Le fichier de configuration nginx
- L’unité systemd
nginx.service - Les dépendances (création des répertoires, utilisateur nginx, etc.)
- L’activation du service au boot
Vous pouvez voir les services générés :
# Lister les services actifssystemctl list-units --type=service
# Voir la configuration générée pour nginxsystemctl cat nginx.serviceCe qui est vraiment immuable (et ce qui ne l’est pas)
Soyons précis sur ce qui est immuable et ce qui ne l’est pas :
Immuable (géré par Nix) :
- Les binaires et bibliothèques (
/nix/store/) - La configuration système (
/etc/généré) - Les services systemd
- Le bootloader et le kernel
Mutable (données persistantes) :
/home/- répertoires utilisateurs/var/- logs, bases de données, état des services/root/- répertoire root- Tout ce que vous déclarez avec
environment.persistencesi vous utilisez impermanence
Cette séparation est importante : NixOS garantit la reproductibilité du système, pas des données. Vos bases de données PostgreSQL, vos fichiers utilisateurs, vos logs… tout ça persiste entre les générations.
Garbage collection
Avec le temps, /nix/store/ accumule les anciennes générations. Pour nettoyer :
# Supprimer les générations de plus de 30 jourssudo nix-collect-garbage --delete-older-than 30d
# Supprimer tout sauf la génération actuelle (attention !)sudo nix-collect-garbage -dAprès un garbage collection, vous ne pourrez plus revenir aux générations supprimées. Je recommande de garder au moins 2-3 générations de secours.
Vous pouvez aussi automatiser le nettoyage dans votre configuration :
nix.gc = { automatic = true; dates = "weekly"; options = "--delete-older-than 30d";};Tester rapidement avec une VM
Assez de théorie ! Le plus simple pour démarrer, c’est de créer une VM locale. Voici comment je fais avec disko pour le partitionnement déclaratif et QEMU/KVM. On va mettre en pratique tout ce qu’on a vu : flakes, configuration déclarative, génération de système, et boot sur une génération.
Structure du projet
Je crée un répertoire avec trois fichiers :
nixos-vm/├── flake.nix # Point d'entrée : dépendances et outputs├── flake.lock # Versions verrouillées (généré automatiquement)├── configuration.nix # Configuration NixOS de la VM└── disko-config.nix # Schéma de partitionnement déclaratifInitialisons le projet :
# Créer le répertoire et initialiser Git (obligatoire pour les flakes)mkdir nixos-vm && cd nixos-vmgit initConfiguration disko
Disko est un outil de la communauté Nix qui permet de décrire le
partitionnement des disques de manière déclarative. Plus besoin de lancer
fdisk ou parted manuellement et de se souvenir des commandes !
{ lib, ... }:{ disko.devices = { disk = { main = { type = "disk"; device = "/dev/vda"; # Disque virtio dans QEMU content = { type = "gpt"; # Table de partition GPT (moderne) partitions = { # Partition EFI pour le boot UEFI ESP = { size = "512M"; type = "EF00"; # Code pour partition EFI System content = { type = "filesystem"; format = "vfat"; mountpoint = "/boot"; mountOptions = [ "umask=0077" ]; }; }; # Partition racine, tout l'espace restant root = { size = "100%"; content = { type = "filesystem"; format = "ext4"; mountpoint = "/"; }; }; }; }; }; }; };}C’est verbeux, mais l’avantage, c’est que c’est explicite et reproductible. Vous savez exactement comment votre disque sera partitionné. Et surtout, c’est versionné dans Git !
Configuration NixOS
Voici la configuration système. On retrouve tout ce qu’on a vu : activation des
services via services.xxx.enable, configuration du bootloader, paquets
système, utilisateur avec hash de mot de passe…
{ config, pkgs, ... }:{ # Boot en UEFI avec systemd-boot (moderne et simple) boot.loader.systemd-boot.enable = true; boot.loader.efi.canTouchEfiVariables = true;
# Hostname de la machine networking.hostName = "nixos-vm";
# Timezone et locale (comme sur une distro classique, mais déclaratif) time.timeZone = "Europe/Paris"; i18n.defaultLocale = "fr_FR.UTF-8"; console.keyMap = "fr";
# SSH activé pour se connecter à la VM # NixOS génère /etc/ssh/sshd_config automatiquement services.openssh = { enable = true; settings = { PermitRootLogin = "prohibit-password"; PasswordAuthentication = false; }; };
# Utilisateur admin avec authentification par clé SSH uniquement # Pas de mot de passe = plus sécurisé (connexion SSH par clé obligatoire) users.users.admin = { isNormalUser = true; extraGroups = [ "wheel" ]; # sudo openssh.authorizedKeys.keys = [ "ssh-ed25519 AAAA... votre-cle-publique" # Remplacez par votre clé ]; };
# Pour autoriser sudo sans mot de passe (optionnel, pour cette VM de test) security.sudo.wheelNeedsPassword = false;
# Paquets système disponibles pour tous les utilisateurs environment.systemPackages = with pkgs; [ vim git htop curl tmux ];
# Activer les flakes et nix-command (déjà fait, mais explicite) nix.settings.experimental-features = [ "nix-command" "flakes" ];
# Garbage collection automatique (ce qu'on a vu plus haut) nix.gc = { automatic = true; dates = "weekly"; options = "--delete-older-than 30d"; };
# Version de NixOS (ne pas changer sans migration) system.stateVersion = "24.11";}Chaque option dans ce fichier correspond à quelque chose de concret :
services.openssh.enable = true→ génère/etc/ssh/sshd_configet le service systemdusers.users.admin→ crée l’utilisateur dans/etc/passwd,/etc/shadowenvironment.systemPackages→ installe les paquets dans le store et crée les liens dans/run/current-system/sw/bin/
Le flake complet
Le flake assemble tout. Il déclare les inputs (dépendances avec leurs versions) et les outputs (ce qu’on produit, ici une configuration NixOS) :
{ description = "VM NixOS de test avec disko";
inputs = { # NixOS 24.11 stable nixpkgs.url = "github:NixOS/nixpkgs/nixos-24.11";
# Disko pour le partitionnement déclaratif disko = { url = "github:nix-community/disko"; inputs.nixpkgs.follows = "nixpkgs"; # Utiliser notre nixpkgs }; };
outputs = { self, nixpkgs, disko, ... }: { # Définition de notre système NixOS nixosConfigurations.nixos-vm = nixpkgs.lib.nixosSystem { system = "x86_64-linux"; modules = [ # Module disko pour gérer le partitionnement disko.nixosModules.disko # Notre schéma de partitionnement ./disko-config.nix # Notre configuration NixOS ./configuration.nix ]; }; };}À la première exécution, Nix va créer flake.lock avec les versions exactes de
nixpkgs et disko. Ce fichier doit être commité dans Git !
Versionner la configuration
Avant de continuer, on commite tout :
# Ajouter les fichiersgit add flake.nix disko-config.nix configuration.nix flake.lock
# Premier commitgit commit -m "Initial NixOS VM configuration"
# Optionnel : pousser sur GitHub pour installer à distancegit remote add origin git@github.com:votre-user/nixos-vm.gitgit push -u origin mainCréer et démarrer la VM
Maintenant, on crée une VM et on démarre sur l’ISO NixOS :
# Télécharger l'ISO NixOS minimal (environ 900 Mo)wget https://channels.nixos.org/nixos-24.11/latest-nixos-minimal-x86_64-linux.iso
# Créer une image disque vide de 20 Go (format QCOW2, sparse)qemu-img create -f qcow2 nixos-vm.qcow2 20G
# Démarrer la VM sur l'ISOqemu-system-x86_64 \ -enable-kvm \ -m 2048 \ -smp 2 \ -boot d \ -cdrom latest-nixos-minimal-x86_64-linux.iso \ -drive file=nixos-vm.qcow2,format=qcow2,if=virtio \ -bios /usr/share/ovmf/OVMF.fd \ -nic user,hostfwd=tcp::2222-:22Options expliquées :
-enable-kvm: virtualisation matérielle (beaucoup plus rapide)-m 2048: 2 Go de RAM-smp 2: 2 CPU virtuels-boot d: booter sur le CD-ROM (l’ISO)-bios /usr/share/ovmf/OVMF.fd: firmware UEFI (nécessaire pour systemd-boot)-nic user,hostfwd=tcp::2222-:22: réseau NAT avec redirection SSH
Installer NixOS depuis le flake
Une fois dans la VM (l’ISO démarre sur un shell root), on doit d’abord activer SSH et définir un mot de passe temporaire pour pouvoir copier nos fichiers :
# Dans la VM : définir un mot de passe pour rootsudo -ipasswd# Entrez un mot de passe temporaire (ex: "nixos")Depuis un autre terminal sur l’hôte, on copie notre configuration via scp :
# Depuis l'hôte, copier le répertoire dans la VMscp -P 2222 -r nixos-vm root@localhost:/root/# Se connecter en SSH à la VMssh -p 2222 root@localhostPuis dans la VM :
# Activer les flakes dans l'ISOsudo -i
export NIX_CONFIG="experimental-features = nix-command flakes"
# Aller dans le répertoire copiécd /root/nixos-vm
# Partitionner et formater avec diskonix run github:nix-community/disko -- --mode disko --flake .#nixos-vm
# Installer NixOSnixos-install --flake .#nixos-vm --no-root-passwd
# RedémarrerrebootVérifier le résultat
Après le reboot, la VM démarre sur le système installé. Connectez-vous en SSH :
# Depuis l'hôtessh -p 2222 admin@localhostUne fois connecté, on peut vérifier que tout fonctionne :
# Voir la génération actuellenixos-version# 24.11.20241201.abc1234 (Vicuña)
# Voir les générations disponibles (une seule pour l'instant)sudo nix-env --list-generations -p /nix/var/nix/profiles/system# 1 2025-12-01 16:10:15 (current)
# Voir où pointe le système actuelreadlink /run/current-system# /nix/store/abc123...-nixos-system-nixos-vm-24.11
# Vérifier que SSH est bien configuré comme déclarécat /etc/ssh/sshd_config | grep -E "^(PermitRootLogin|PasswordAuthentication)"
PermitRootLogin prohibit-passwordPasswordAuthentication noModifier et mettre à jour
La vraie puissance de NixOS apparaît quand on modifie la configuration. Ajoutons nginx à notre VM :
# Dans configuration.nix, ajouter :services.nginx = { enable = true; virtualHosts."localhost" = { root = "/var/www/html"; locations."/" = { index = "index.html"; }; };};
# Créer le contenu websystemd.tmpfiles.rules = [ "d /var/www/html 0755 root root -" "f /var/www/html/index.html 0644 root root - '<h1>Hello from NixOS!</h1>'"];Puis, on applique. Deux options :
# Option 1 : recopier via scp (rapide pour les tests)scp -P 2222 -r nixos-vm admin@localhost:/home/admin/ssh -p 2222 admin@localhostcd /home/admin/nixos-vmsudo nixos-rebuild switch --flake .#nixos-vm
# Option 2 : cloner depuis Git (recommandé, plus reproductible)ssh -p 2222 admin@localhostgit clone https://github.com/votre-user/nixos-vm.gitcd nixos-vmsudo nixos-rebuild switch --flake .#nixos-vmL’option Git est préférable en production : la configuration vient toujours du dépôt, pas d’un répertoire local qui pourrait différer.
Après le rebuild, vous avez maintenant deux générations. Vous pouvez vérifier avec :
sudo nix-env --list-generations -p /nix/var/nix/profiles/system 1 2025-12-01 16:10:15 2 2025-12-01 16:23:45 (current)sudo systemctl status nginx.service● nginx.service - Nginx Web Server Loaded: loaded (/etc/systemd/system/nginx.service; enabled; preset: ignored) Active: active (running) since Mon 2025-12-01 16:24:47 CET; 1min 11s ago Invocation: 178e2181c1a8472e84e3b28eca9d20c5 Process: 693 ExecStartPre=/nix/store/x8nbgq6myz2js47r03j520srlcy0bg25-unit-script-nginx-pre-start/bin/nginx-pre-sta> Main PID: 716 (nginx) IP: 0B in, 0B out IO: 4.6M read, 0B written Tasks: 2 (limit: 4678) Memory: 6.9M (peak: 8.1M) CPU: 151ms CGroup: /system.slice/nginx.service ├─716 "nginx: master process /nix/store/yvhfvc77k124mbdqpiclq7m129anph3v-nginx-1.26.3/bin/nginx -c /nix/st> └─717 "nginx: worker process"
déc. 01 16:24:47 nixos-vm systemd[1]: Starting Nginx Web Server...déc. 01 16:24:47 nixos-vm nginx-pre-start[701]: nginx: the configuration file /nix/store/id8vp83giycaw4s0r7bvbq4kjqpzpi>déc. 01 16:24:47 nixos-vm nginx-pre-start[701]: nginx: configuration file /nix/store/id8vp83giycaw4s0r7bvbq4kjqpzpik4-n>déc. 01 16:24:47 nixos-vm systemd[1]: Started Nginx Web Server.Si nginx pose problème, vous pouvez revenir à la génération 1 :
# Rollback immédiatsudo nixos-rebuild switch --rollback
# Vérifier que nginx n'est plus làsudo systemctl status nginx.service# Unit nginx.service could not be found.Une fois que vous avez validé que le système fonctionne correctement sur une génération stable, vous pouvez nettoyer les anciennes générations :
# Supprimer les générations de plus de 7 jourssudo nix-collect-garbage --delete-older-than 7dEt voilà ! Vous avez une VM NixOS fonctionnelle, entièrement définie par du code versionné. Configuration déclarative, flakes pour la reproductibilité, disko pour le partitionnement, et rollback automatique. Tout ce qu’on a expliqué dans ce guide, en pratique.
Pour aller plus loin
Cet article pose les bases de NixOS : le Nix Store, les générations, la configuration déclarative, les flakes, et le fonctionnement interne de l’OS. Vous avez maintenant une VM fonctionnelle pour expérimenter.
J’apprécie vraiment la partie définition du système via des fichiers de configuration, même si cela impose d’apprendre le langage Nix. L’approche est un peu “hard” au début, mais une fois qu’on a compris les concepts, c’est très puissant.
J’adore aussi la possibilité de tester des outils sans les installer via
nix-shell ou nix run. Par exemple :
# Lancer temporairement un outil sans l'installernix run nixpkgs#htop
# Ou créer un shell avec plusieurs outilsnix-shell -p git vim curlVoici la liste des sujets que je compte approfondir (à partir d’une recherche faite ce matin) :
- Le langage Nix : expressions, fonctions, listes, attributs
- Les Flakes en détail : overlays, modules réutilisables
- Écrire ses propres modules NixOS
- nixos-generators : images QCOW2, RAW, ISO, AMI
- nixos-anywhere : installation à distance via kexec
- Intégration cloud Outscale : Outscale Machine Image (OMI)
- Hardening niveau BP-28 : recommandations ANSSI
- Colmena : déploiements multi-serveurs
Ressources complémentaires
- Documentation officielle NixOS ↗
- Nix Pills ↗ : tutoriels approfondis sur le langage Nix
- Zero to Nix ↗ : introduction interactive
- NixOS Wiki ↗ : base de connaissances communautaire
- Mon article original sur NixOS : premiers pas avec la génération d’images