1

ChatGPT a cassé mon serveur - mais il l'a réparé

This commit is contained in:
2026-04-01 18:11:22 +02:00
parent b0cc28a36a
commit 2fbbd9c905
3 changed files with 217 additions and 0 deletions

View File

@@ -0,0 +1,4 @@
#title: ""
attribution: "ChatGPT"
description: "Il ne faut pas brider des LLM, il faut les cadrer."
#prompt: ""

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 MiB

View File

@@ -0,0 +1,213 @@
---
comments_url: https://com.richard-dern.fr/post/550
cover: images/cover.png
date: '2026-04-01 18:05:51'
entreprises:
- OpenAI
tags:
- ChatGPT
- NixOS
- SOPS
title: ChatGPT a cassé mon serveur - mais il l'a réparé
weather:
humidity: 56.0
illuminance: 16328.4
precipitations: false
pressure: 1022.68936938298
source:
- influxdb
temperature: 8.88888888888889
wind_direction: 102.0
wind_speed: 5.632704
---
Suite à [un article](https://xieme-art.org/post/gerer-ses-secrets-avec-sops/) relayé par [le journal du hacker](https://www.journalduhacker.net/s/v5e4rj/g_rer_ses_secrets_avec_sops), j'ai décidé de passer à [SOPS](https://getsops.io) pour la [gestion des secrets](https://github.com/Mic92/sops-nix) dans ma configuration de [NixOS](https://nixos.org/).
En parallèle, j'ai confié à [ChatGPT](https://chat.openai.com/) [les clés de mon réseau](/interets/informatique/2026/03/04/free-ipv6-et-opnsense/) : je l'ai rendu capable d'administrer l'ensemble de mes serveurs.
C'est lui qui a procédé à la migration vers SOPS, et ça a été un succès total pendant plusieurs jours.
Jusqu'à aujourd'hui, que je redémarre mon serveur et qu'il ne réponde plus.
## (kernel) panique
Après avoir branché un écran et un clavier, je vois que le chargement de NixOS bute (avec un `kernel panic`) sur la création du fichier de secret déchiffré pour la clé d'API de MeiliSearch, en raison d'un utilisateur inconnu (`meilisearch`).
Logique : je (le module NixOS) n'ai pas créé d'utilisateur spécifique pour MeiliSearch.
Je me dis que ce n'est pas bien grave, il me suffit de redémarrer sur une génération antérieure de NixOS.
Après tout, le système est fait pour ça.
Sauf que, c'est plus compliqué que ça, et aucune génération ne pouvait plus booter.
Je redémarre la machine sur une clé d'installation de NixOS, pour au moins avoir un shell et accéder à mes fichiers sur le disque, au cas où tout espoir de reprise serait vaincu, puis j'en profite quand même pour voir ce que c'est que cette histoire d'utilisateur inconnu.
Je monte les disques pour que l'installateur y ait accès :
```shell
mkdir /mnt/boot
mount /dev/disk/by-label/nixos /mnt
mount /dev/disk/by-label/boot /mnt/boot
```
Et j'inspecte ma configuration, stockée dans `/mnt/etc/nixos/`.
Je réalise alors que ChatGPT avait affecté ce fameux utilisateur `meilisearch` au fichier concerné :
```nix
secrets."services/meilisearch/master-key" = mkSecret {
path = "/etc/nixos/secrets/services/meilisearch/master-key";
owner = "meilisearch";
group = "meilisearch";
restartUnits = [ "meilisearch.service" ];
};
```
C'est parfaitement logique pour un outil prédictif : s'il y a un service `meilisearch`, l'administrateur a forcément créé un utilisateur `meilisearch`.
Principe de base de la sécurité informatique.
Mais le paquet fournit par NixOS ne crée pas automatiquement cet utilisateur, et en prime, ce fichier doit être lisible à un utilisateur particulier (que j'avais pourtant indiqué à ChatGPT dans mes instructions).
Je corrige la déclaration d'appartenance de ce fichier selon ma convenance, puis j'essaye de me `chroot` avec `nix-enter` afin d'appliquer ma configuration.
Et là, les ennuis ont réellement commencé.
## Shell en état de choc
```shell
[root@nixos:~]# nixos-enter --root /mnt setting up /etc
... setting up secrets...
/nix/store/r6wx09ss7v1775x67pypl5gqzwm71irg-sops-install-secrets-0.0.1/bin/sops-install-secrets: manifest is not valid: failed to lookup user 'meilisearch': user: unknown user meilisearch
Activation script snippet 'setupSecrets' failed (1) /nix/var/nix/profiles/system/activate: line 247: /run/current-system/sw/bin/mktemp: No such file or directory
```
Le problème à ce stade, c'est que j'ai cramé mes tokens Codex jusqu'au 3 avril (on est le 1er).
Il n'y a que le chat en ligne qui peut m'aider, et il n'a pas accès à ma configuration (que je n'ai pas envie de lui envoyer compte tenu de sa complexité).
Néanmoins, il me suggère quand même de faire autrement, sans `chroot`, avec un simple `nixos-install --root /mnt`.
La commande échoue sur `error: path '/var/lib/sops-nix/recovery-keys.txt' does not exist`.
Le point important est le suivant : en Nix, un chemin écrit comme un vrai chemin Nix, par exemple `/var/lib/...`, est traité comme un objet `path` et il doit exister au moment de lévaluation.
[La documentation Nix](https://nix.dev/manual/nix/2.18/language/builtins) indique bien quun chemin référencé doit exister, et que lexistence dun chemin peut être testée à lévaluation avec `builtins.pathExists`.
Donc, dans ma configuration, au lieu de faire :
```nix
sops.age.keyFile = /var/lib/sops-nix/recovery-keys.txt;
```
Je devais faire :
```nix
sops.age.keyFile = "/var/lib/sops-nix/recovery-keys.txt";
```
Notez les guillemets.
Après cette rapide correction, je relance l'installation :
```shell
[root@nixos:~]# nixos-install --root /mnt
copying channel...
building the configuration in /mnt/etc/nixos/configuration.nix...
these 2 derivations will be built:
/nix/store/r4bgszxqmfikbsg9xv40a1p034gl597g-manifest.json.drv
/nix/store/rf2zl9lh7qiidifvckfr1c0kl633ss97-nixos-system-server-main-25.11.8023.4590696c8693.drv
building '/nix/store/r4bgszxqmfikbsg9xv40a1p034gl597g-manifest.json.drv'...
building '/nix/store/rf2zl9lh7qiidifvckfr1c0kl633ss97-nixos-system-server-main-25.11.8023.4590696c8693.drv'...
/nix/store/isdjvp7wwxwi1a7c8vp3l8hgrdh5yfny-nixos-system-server-main-25.11.8023.4590696c8693
installing the boot loader...
setting up /etc...
setting up secrets...
sops-install-secrets: Imported /etc/ssh/ssh_host_ed25519_key as age key with fingerprint age13kq73j2ka8y5tq7nl4cccajk9dftz45k2jl7v2ymuuu24n5frues58h2r5
/nix/var/nix/profiles/system/activate: line 230: /run/current-system/sw/bin/mktemp: No such file or directory
/nix/var/nix/profiles/system/sw/bin/bash: line 12: /run/current-system/bin/switch-to-configuration: No such file or directory
```
ChatGPT me conseille alors de rebooter sans tenir compte de ces erreurs.
Je redémarre, mais je vois qu'il n'y a aucune entrée GRUB pour la nouvelle génération (logique : regardez la dernière ligne d'historique ci-dessus).
Malheureusement, nouveau `kernel panic`, cette fois sur l'absence de `mktemp`.
Nouveau redémarrage sur la clé et nouveau montage des disques, et en faisant `nixos-enter`, je commence à me dire qu'il ne sait pas où chercher ses exécutables.
```shell
[root@nixos:~]# ls -l /mnt/nix/var/nix/profiles/system/bin
ls -l /mnt/nix/var/nix/profiles/system/sw/bin | grep bootctl
ls: cannot access '/mnt/nix/var/nix/profiles/system/bin': No such file or directory
ls: cannot access '/mnt/nix/var/nix/profiles/system/sw/bin': No such file or directory
```
On sait qu'un truc déconne bien quand même `ls` ne répond pas...
Pourtant, je vois que de nouvelles générations ont été produites :
```shell
/run/current-system/sw/bin/ls -l /boot/loader/entries | /run/current-system/sw/bin/tail -n 10
```
Me montre bien un fichier `nixos-generation-481.conf`.
C'est donc à l'étape de la génération du bootloader que ça déconne.
## Laisser NixOS gérer les chemins de fichiers...
On a finalement déterminé la cause exacte de mon problème :
```nix
tmp=$(/run/current-system/sw/bin/mktemp)
trap 'rm -f "$tmp"' EXIT
/run/current-system/sw/bin/ssh-to-age -private-key -i "$agentSshKey" > "$tmp"
```
On ne devrait jamais déclarer un chemin vers un exécutable sans l'extrapoler depuis `pkgs`.
Il a suffi de corriger cela :
```nix
tmp=$(${pkgs.coreutils}/bin/mktemp -p /run sops-age-key.XXXXXXXXXX)
trap '${pkgs.coreutils}/bin/rm -f "$tmp"' EXIT
${pkgs.ssh-to-age}/bin/ssh-to-age -private-key -i "$agentSshKey" > "$tmp"
```
Nouveau `nixos-install`.
Les dernières étapes sont toujours problématiques, notamment la mise à jour de GRUB.
Mais au moins, je pouvais enfin accéder à mon `chroot`, en précisant à `nixos-enter` la génération 482 qui devait avoir réglé mes problèmes, afin de régénérer GRUB manuellement :
```shell
[root@nixos:~]# nixos-enter --root /mnt --system /nix/var/nix/profiles/system-482-link -- \
/nix/var/nix/profiles/system-482-link/sw/bin/bash --noprofile --norc
setting up /etc...
setting up secrets...
sops-install-secrets: Imported /etc/ssh/ssh_host_ed25519_key as age key with fingerprint age13kq73j2ka8y5tq7nl4cccajk9dftz45k2jl7v2ymuuu24n5frues58h2r5
/nix/var/nix/profiles/system-482-link/activate: line 230: /run/current-system/sw/bin/mktemp: No such file or directory
bash-5.3# /nix/var/nix/profiles/system-482-link/sw/bin/mkdir -p /run
/nix/var/nix/profiles/system-482-link/sw/bin/ln -sfn /nix/var/nix/profiles/system-482-link /run/current-system
export PATH=/run/current-system/sw/bin:/nix/var/nix/profiles/system-482-link/sw/bin:$PATH
NIXOS_INSTALL_BOOTLOADER=1 /run/current-system/bin/switch-to-configuration boot
Running in a chroot, enabling --graceful.
Copied "/nix/store/bigkpra9jw48fip69q4wndsf4kb3d2w9-systemd-258.3/lib/systemd/boot/efi/systemd-bootx64.efi" to "/boot/EFI/systemd/systemd-bootx64.efi".
Copied "/nix/store/bigkpra9jw48fip69q4wndsf4kb3d2w9-systemd-258.3/lib/systemd/boot/efi/systemd-bootx64.efi" to "/boot/EFI/BOOT/BOOTX64.EFI".
⚠️ Mount point '/boot' which backs the random seed file is world accessible, which is a security hole! ⚠️
⚠️ Random seed file '/boot/loader/random-seed' is world accessible, which is a security hole! ⚠️
Random seed file /boot/loader/random-seed successfully refreshed (32 bytes).
Created EFI boot entry "Linux Boot Manager".
bash-5.3# /run/current-system/sw/bin/ls -l /boot/loader/entries | /run/current-system/sw/bin/tail -n 10
total 16
-rwxr-xr-x 1 root root 473 Apr 1 15:25 nixos-generation-479.conf
-rwxr-xr-x 1 root root 473 Apr 1 15:25 nixos-generation-480.conf
-rwxr-xr-x 1 root root 473 Apr 1 15:25 nixos-generation-481.conf
-rwxr-xr-x 1 root root 473 Apr 1 15:25 nixos-generation-482.conf
bash-5.3#
```
Un dernier `nixos-install` et, cette fois, il va jusqu'au bout, sans le moindre message d'erreur.
J'ai redémarré, les entrées GRUB étaient mises à jour, et NixOS a démarré sans broncher.
Aucune perte à déplorer.
## Conclusion
Franchement, c'est flippant à mort quand on fait ce genre d'expérience pour la première fois.
J'en ai voulu à ChatGPT, à SOPS et à NixOS, et j'étais en train de me demander si je n'allais pas formater et réinstaller.
Le problème s'est révélé être double :
- ChatGPT a présumé de l'existence d'un utilisateur, parce qu'en théorie, installer un service devrait s'accompagner de la création d'un utilisateur dédié (tous les modules que j'utilise le font, à l'exception donc de MeiliSearch)
- ChatGPT n'a pas utilisé des chemins construits par NixOS (extrapolés par `pkgs`).
Je suis totalement responsable du second point étant donné que je ne le fais pas toujours.
Mais ChatGPT aurait pu prendre les devants et m'aider à les corriger, au lieu de se contenter de (mal) faire comme moi.
Mais maintenant, je sais quelles instructions supplémentaires je dois donner à ChatGPT pour éviter qu'il ne commette à nouveau ce genre d'erreur (ne jamais indiquer des chemins sans extrapoler `pkgs` quand c'est possible, par exemple).
Je n'ai pas moins confiance en ce que produit ChatGPT.
Je ne crois pas que l'on doit donner moins de privilèges aux LLM.
Je crois juste qu'ils ont besoin d'être cadrés, et je ne l'ai pas fait suffisamment.