D-85 : ce que le retrait de cloud-init NE ferme pas
La premiere redaction se lisait comme une emancipation. Elle n en est pas une, et il valait mieux le dire que de laisser un lecteur presse en conclure trop. Retirer cloud-init n ote AUCUN pouvoir a l hebergeur. qemu-guest-agent est au gabarit — il doit y etre (P56) — et l API Proxmox expose sur son dos, sur toute VM vivante de la flotte, un pouvoir strictement plus grand que le lecteur cloud-init. Releve le 2026-09-09 sur edge-mta-01, avec le jeton du site : exec, exec-status, file-read, file-write, set-user-password, shutdown. Ce que D-85 ferme est donc precis et etroit : une reapplication AUTOMATIQUE a chaque demarrage, depuis un support que le plan ne possede pas et qu aucune preuve ne lit ; et le code de cloud-init lui-meme, un interpreteur Python complet execute en root au boot avec ses ~29 dependances. La mainmise d un hyperviseur sur ses invites est une propriete de la VIRTUALISATION, pas de cloud-init — elle appelle sa propre decision, qui n est pas prise. LE SEUIL EST NOMME. L alternative existe et sa piece est deja au gabarit : poser adresse et cle par agent/file-write + agent/exec, sans reseau. Aujourd hui ce serait reimplementer un standard, ce que positionnement.md interdit, au moment le plus fragile et pour le pire mode de panne — une VM injoignable. Le jour ou une premiere seconde ne pourra plus etre amorcee par Proxmox (autre hyperviseur, metal nu, hebergeur sans API), ce chemin devient LE chemin portable. La nuance est portee partout ou l affirmation est faite : D-85, le README et l entete du role, AGENTS.md, le wiki. make prouver : CONFORME, 62 OK, 0 echec, 1 saute. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01Crgis8CxCWkAGFA1ecBz3q
This commit is contained in:
parent
a6457a161b
commit
f89b097b26
6 changed files with 88 additions and 1 deletions
|
|
@ -644,6 +644,15 @@ comptes, clés SSH, mots de passe et réseau. Sur une machine que le plan possè
|
|||
produisait un va-et-vient à chaque déploiement. **Le gabarit, lui, le garde** — sans lui un
|
||||
clone n'a ni adresse ni nom. **P63** garde les trois moitiés.
|
||||
|
||||
**Ce que ce retrait ne ferme pas.** Il n'ôte **aucun pouvoir à l'hébergeur** :
|
||||
`qemu-guest-agent` est au gabarit (il doit y être — P56), et l'API Proxmox expose sur son
|
||||
dos `exec`, `file-write`, `set-user-password`, `shutdown` — strictement plus que le lecteur
|
||||
cloud-init. Ce qui est fermé est étroit et réel : une réapplication *automatique, à chaque
|
||||
démarrage*, depuis un support que le plan ne possède pas, et un interpréteur Python
|
||||
complet exécuté en root au boot. La mainmise de l'hyperviseur sur ses invités est une
|
||||
propriété de la virtualisation, pas de cloud-init — elle appelle sa propre décision, non
|
||||
prise.
|
||||
|
||||
---
|
||||
|
||||
## Nettoyage avant template
|
||||
|
|
|
|||
39
CHANGELOG.md
39
CHANGELOG.md
|
|
@ -72,6 +72,45 @@ existe pour qui veut, en connaissance de cause.
|
|||
`/etc/cloud/cloud-init.disabled` est lu par cloud-init lui-meme au demarrage et l'arrete
|
||||
avant qu'il ne lise la moindre source de donnees.
|
||||
|
||||
### Ce que cette decision NE ferme PAS
|
||||
|
||||
Ajoute le meme jour, apres la question « cloud-init est-il vraiment une valeur ajoutee
|
||||
ici ? ». La premiere redaction de D-85 se lisait comme une emancipation. Elle n'en est
|
||||
pas une, et il valait mieux le dire que de laisser un lecteur presse en conclure trop.
|
||||
|
||||
**Retirer cloud-init n'ote AUCUN pouvoir a l'hebergeur.** `qemu-guest-agent` est au
|
||||
gabarit — il doit y etre (P56 : c'est par lui que `creer-vm` confirme la materialisation
|
||||
sans entrer chez le tenant). Releve du 2026-09-09 sur `edge-mta-01`, avec le jeton d'API
|
||||
du site, les sous-chemins que l'API expose sur son dos :
|
||||
|
||||
exec · exec-status · file-read · file-write · set-user-password · shutdown · ...
|
||||
|
||||
C'est un pouvoir STRICTEMENT PLUS GRAND que le lecteur cloud-init, et il est deja la, sur
|
||||
chaque VM vivante de la flotte.
|
||||
|
||||
Ce que D-85 ferme est donc precis et etroit :
|
||||
|
||||
1. une reapplication AUTOMATIQUE, a chaque demarrage, depuis un support que le plan ne
|
||||
possede pas et qu'aucune preuve ne lit ;
|
||||
2. le code de cloud-init lui-meme — un interpreteur Python complet execute en root au
|
||||
demarrage, et ses ~29 dependances.
|
||||
|
||||
La mainmise d'un hyperviseur sur ses invites est une propriete de la VIRTUALISATION, pas
|
||||
de cloud-init. Elle appelle sa propre decision, qui n'est pas prise.
|
||||
|
||||
### Le seuil ou le remplacer deviendrait juste
|
||||
|
||||
L'alternative existe et sa piece est deja au gabarit : ecrire l'adresse et la cle par
|
||||
`agent/file-write` + `agent/exec` depuis l'hyperviseur, sans reseau. Aujourd'hui ce serait
|
||||
REIMPLEMENTER UN STANDARD — ce que `positionnement.md` interdit — et echanger un mecanisme
|
||||
eprouve contre du code maison au moment le plus fragile, dont le mode de panne est le
|
||||
pire : une VM injoignable.
|
||||
|
||||
Le jour ou une premiere seconde ne pourra plus etre amorcee par Proxmox — autre
|
||||
hyperviseur, metal nu, hebergeur sans API — ce chemin cesse d'etre une reimplementation et
|
||||
devient LE CHEMIN PORTABLE. C'est l'axe emancipation que le depot suit deja. Le seuil est
|
||||
nomme ici pour ne pas etre franchi sans le voir.
|
||||
|
||||
### Non deploye
|
||||
|
||||
Le code est ecrit, valide et prouve ; **il n'a pas ete applique a la flotte**. Retirer un
|
||||
|
|
|
|||
|
|
@ -58,7 +58,7 @@ sont les seules vérifiables.
|
|||
| **D-82** | **Patient 0 n'est le parent de personne.** Il est la **mise en œuvre de référence** du modèle `origine` — le plus petit écosystème complet — et un pair de la famille du génome, pas sa racine | trois faits l'ont retiré un par un : D-81 a donné l'autorité du génome à la forge du SITE (son dernier lecteur corrigé le 2026-08-26, Technolibre le 08-31) ; le dénominateur commun vit dans les modèles depuis le 08-24 ; et **l'ancêtre était locataire de son enfant** — index 29 sur la fabric de `SITE-Chezlepro`, qui descend de lui. Ce qu'il devait éliminer — le SPOF `eregion`, hors flotte — n'a PAS été éliminé mais **promu** : le poste y pousse, la forge du site en tire. Cette dette appartient désormais au SITE, et la nommer est le minimum : *un objectif qu'on abandonne sans le dire devient un objectif qu'on croit atteint* | `OPS-Patient0/README.md`, `docs/filiation-emancipation.md` | — |
|
||||
| **D-83** | **Patient 0 a été retiré** — ses machines n'existent plus (constaté le 2026-09-06) | D-82 lui avait laissé une raison d'être : la mise en œuvre de référence du modèle `origine`, et un **témoin** de plus du génome. Le retrait solde la première et **abaisse la seconde de trois copies vivantes à deux** (`eregion`, la forge du site). Ce qu'il devait éliminer — le SPOF `eregion` — reste entier, et sans lui il n'y a plus de miroir indépendant pour l'absorber. **Son plan reste sur disque et la fédération lui réserve toujours l'index 29** : tant que ce n'est pas tranché, le site ouvre SSH, apt, DNS et HTTPS à `10.29.0.0/16` — un périmètre vide | `OPS-Patient0/`, `SITE-Chezlepro/flux-genere/` | **P21** (index), **P23** |
|
||||
| **D-84** | **Le plan de contrôle reste gelé — c'est la CARTE DES SEUILS qui était fausse** | La question « et si on retirait le gel ? » a mis à l'épreuve les cinq seuils de `positionnement.md`, et deux ne tenaient pas. **RBAC** : couvert depuis que trois classes d'acteurs aux pouvoirs disjoints existent — poste, runner de site, runners de tenant — séparés **cryptographiquement** (une voûte, une clé, 2026-08-28) et non par une table de permissions qu'une faille applicative contournerait ; adopter AWX pour ce besoin serait **régresser**. **IPAM** : sans objet par construction — rien ne s'alloue, tout dérive du seed, et P20/P21/P23/P28/P33 tiennent déjà ce qu'un IPAM vérifierait *a posteriori*. Les deux lignes sont retirées du tableau : les garder aurait fait adopter un outil pour un besoin déjà rempli. **Et un seuil manquait** — l'**émancipation** : le GUI est mono-utilisateur (`127.0.0.1` + jeton), or la trajectoire mène à plusieurs humains aux portées disjointes, sur des machines qui ne sont pas les nôtres. Ce seuil n'appelle pas AWX, il appelle une décision non prise. *Un seuil qu'on ne nomme pas est un seuil qu'on franchit sans le voir.* Corollaire consigné : le gel porte sur les **fonctions**, jamais sur les **vues** — montrer à l'écran ce que le moteur sait déjà ne franchit aucun seuil | `positionnement.md` §3, §4, §5 | — |
|
||||
| **D-85** | **cloud-init naît avec la VM et ne lui survit pas** | cloud-init n'est pas un logiciel d'installation : c'est une **source de vérité externe**. À chaque démarrage il relit le lecteur attaché par l'hyperviseur, qui peut redéfinir comptes, clés SSH autorisées, mots de passe et réseau. Sur une machine que le plan possède, c'est un **second maître** — que le plan ne décrit pas, que `make valider` ne mesure pas, et qui gagne parce qu'il parle en premier. Sa tâche est pourtant finie à la première seconde : c'est parce qu'il a **réussi** à poser l'adresse et les clés qu'Ansible a pu entrer. **La décision a trois moitiés, et elles se défont séparément** : le **gabarit** le garde (sans lui un clone ne naît pas — P56) ; le **socle** ne l'installe plus (le garder produisait un va-et-vient à chaque déploiement : le socle installe, le durcissement retire, deux `changed` par passage) ; le **durcissement** le retire (`cloud_init_retrait`). **Ce qui rend le retrait sûr est mesuré, pas supposé** (2026-09-09, `obs-01`) : `/etc/network/interfaces.d/50-cloud-init` n'appartient à aucun paquet — `dpkg -S` ne le trouve pas — et le `postrm` ne le nomme jamais, même en `purge`. L'adresse survit. Le rôle le **vérifie** malgré tout, avant et après : une VM qui perd ce fichier ne se plaint pas, elle repart sans adresse et plus personne ne peut entrer pour le constater | `roles/cloud_init_retrait/`, `serveur_durci.yml` | **P63** |
|
||||
| **D-85** | **cloud-init naît avec la VM et ne lui survit pas** | cloud-init n'est pas un logiciel d'installation : c'est une **source de vérité externe**, qui se réveille à *chaque* démarrage et relit le lecteur attaché par l'hyperviseur — lequel peut redéfinir comptes, clés SSH autorisées, mots de passe et réseau. Sur une machine que le plan possède, c'est un **second maître** : le plan ne le décrit pas, `make valider` ne le mesure pas, et il parle en premier. Sa tâche est pourtant finie à la première seconde — c'est parce qu'il a **réussi** à poser l'adresse et les clés qu'Ansible a pu entrer. **Trois moitiés, qui se défont séparément** : le **gabarit** le garde (sans lui un clone ne naît pas — P56) ; le **socle** ne l'installe plus (le garder produisait un va-et-vient à chaque déploiement : le socle installe, le durcissement retire, deux `changed` par passage) ; le **durcissement** le retire (`cloud_init_retrait`, en dernier). **Ce qui rend le retrait sûr est mesuré, pas supposé** (2026-09-09, `obs-01`) : `/etc/network/interfaces.d/50-cloud-init` n'appartient à aucun paquet — `dpkg -S` ne le trouve pas — et le `postrm` ne le nomme jamais, même en `purge`. L'adresse survit. Le rôle le **vérifie** malgré tout, avant et après : une VM qui perd ce fichier ne se plaint pas, elle repart sans adresse et plus personne ne peut entrer pour le constater. **⚠ CE QUE CETTE DÉCISION NE FERME PAS — et il faut le dire, sinon elle se lit comme une émancipation qu'elle n'est pas.** Retirer cloud-init **n'ôte aucun pouvoir à l'hébergeur**. `qemu-guest-agent` est au gabarit (P56 : il doit y être — c'est par lui que `creer-vm` confirme la matérialisation sans entrer chez le tenant), et l'API Proxmox expose sur son dos, sur toute VM vivante de la flotte, un pouvoir **strictement plus grand** que le lecteur cloud-init : `exec`, `file-write`, `file-read`, `set-user-password`, `shutdown` (relevé le 2026-09-09 sur `edge-mta-01`, jeton d'API du site). Ce que D-85 ferme est donc **précis et étroit** : (a) une réapplication **automatique, à chaque démarrage**, depuis un support que le plan ne possède pas et qu'aucune preuve ne lit ; (b) le code de cloud-init lui-même — un interpréteur Python complet, exécuté en root au démarrage, et ses ~29 dépendances. Elle ne ferme **pas** la mainmise de l'hyperviseur sur ses invités : celle-là est une propriété de la virtualisation, pas de cloud-init, et elle appelle sa propre décision — non prise. **Le seuil où le remplacer deviendrait juste** : le jour où une première seconde ne peut plus être amorcée par Proxmox (autre hyperviseur, métal nu, hébergeur sans API), le chemin par l'agent invite cesse d'être une réimplémentation d'un standard — que `positionnement.md` interdit — et devient **le chemin portable**. Tant que ce seuil n'est pas atteint, écrire soi-même l'amorçage serait échanger un standard éprouvé contre du code maison au moment le plus fragile, dont le mode de panne est le pire : une VM injoignable | `roles/cloud_init_retrait/`, `serveur_durci.yml`, `positionnement.md` | **P63** |
|
||||
| **D-81** | **La forge du SITE fait autorité pour le génome.** Toute autre copie — y compris celle d'où le moteur a été poussé jusqu'ici — est un **miroir**. Le poste de l'exploitant ne route pas jusqu'à elle : c'est le **runner du site** qui publie, par `make genome-pousser` | un écosystème se reproduit depuis la forge de son site : c'est de là qu'il clone son moteur, ses plans, ses modèles. Si l'autorité est ailleurs, cette forge devient un cache qu'on croit à jour — et le 2026-08-26 elle était **quatre commits en arrière** sans que rien ne le signale, dont le correctif qui désarme le pare-feu Proxmox. **Un écosystème qui se reproduit depuis une forge en retard reproduit ses défauts.** Le poste n'a de patte que sur l'administration, et on ne perce pas de chemin pour lui : le runner existe pour ce travail | `playbooks/maintenance/genome_pousser.yml`, `scripts/genome_colis.py`, `Makefile` §genome-pousser | — |
|
||||
| **D-13** | Un **hébergeur** sert plusieurs **tenants** et a son tenant par défaut | Chezlepro est les deux à la fois, ce qui masquait la distinction | `frontiere-opnsense.md` §2 | — |
|
||||
| **D-14** | `underlay.yml` appartient à l'**hébergeur**, monté par symlink | ce sont ses commutateurs, ses câbles ; le moteur est générique, un tenant n'en possède pas | `sdn-evpn.md`, `underlay.yml.example` | — |
|
||||
|
|
|
|||
|
|
@ -16,6 +16,24 @@ d'aller plus loin si le fichier a disparu.
|
|||
**Ce qui n'est pas retiré.** `cloud-guest-utils` (`growpart`) : aucun service, aucune
|
||||
source de données, aucun pouvoir. Le retirer ne fermerait rien.
|
||||
|
||||
## Ce que ce rôle ne ferme PAS
|
||||
|
||||
Il **n'ôte aucun pouvoir à l'hébergeur**, et le croire serait la mauvaise leçon.
|
||||
`qemu-guest-agent` est au gabarit — il doit y être (P56) — et l'API Proxmox expose sur son
|
||||
dos, sur toute VM vivante, un pouvoir **strictement plus grand** que le lecteur
|
||||
cloud-init : `exec`, `file-write`, `file-read`, `set-user-password`, `shutdown` (relevé le
|
||||
2026-09-09 sur `edge-mta-01`).
|
||||
|
||||
Ce que ce rôle ferme est précis et étroit :
|
||||
|
||||
1. une réapplication **automatique, à chaque démarrage**, depuis un support que le plan ne
|
||||
possède pas et qu'aucune preuve ne lit ;
|
||||
2. le code de cloud-init lui-même — un interpréteur Python complet exécuté en root au
|
||||
démarrage, et ses ~29 dépendances.
|
||||
|
||||
La mainmise de l'hyperviseur sur ses invités est une propriété de la virtualisation, pas de
|
||||
cloud-init. Elle appelle sa propre décision, qui n'est pas prise. Cf. **D-85**.
|
||||
|
||||
**Le gabarit garde cloud-init** — il est le seul chemin vers la première seconde d'un
|
||||
clone (P56). Le retrait n'intervient qu'après, sur la machine déployée. C'est pourquoi
|
||||
`serveur_debian` ne l'applique plus : sinon le socle l'installerait et le durcissement le
|
||||
|
|
|
|||
|
|
@ -9,6 +9,18 @@
|
|||
# Sa tache est finie : il a donne a la VM son adresse, son nom et ses cles d'hote a la
|
||||
# premiere seconde. C'est precisement parce qu'il a REUSSI qu'Ansible a pu entrer.
|
||||
#
|
||||
# CE QUE CE ROLE NE FERME PAS, et le croire serait la mauvaise lecon. Il n'ote AUCUN
|
||||
# pouvoir a l'hebergeur. `qemu-guest-agent` est au gabarit — il doit y etre (P56) — et
|
||||
# l'API Proxmox expose sur son dos, sur toute VM vivante, un pouvoir STRICTEMENT PLUS
|
||||
# GRAND que le lecteur cloud-init : `exec`, `file-write`, `file-read`,
|
||||
# `set-user-password`, `shutdown` (releve le 2026-09-09 sur `edge-mta-01`).
|
||||
#
|
||||
# Ce qui est ferme ici est etroit et reel : (a) une reapplication AUTOMATIQUE, a chaque
|
||||
# demarrage, depuis un support que le plan ne possede pas et qu'aucune preuve ne lit ;
|
||||
# (b) le code de cloud-init lui-meme, un interpreteur Python complet execute en root au
|
||||
# demarrage. La mainmise de l'hyperviseur sur ses invites est une propriete de la
|
||||
# virtualisation, pas de cloud-init : elle appelle sa propre decision (D-85).
|
||||
#
|
||||
# POURQUOI LE RETIRER NE COUPE PAS LE RESEAU (mesure du 2026-09-09 sur `obs-01`) :
|
||||
#
|
||||
# /etc/network/interfaces.d/50-cloud-init -> dpkg -S : aucun paquet ne le possede
|
||||
|
|
|
|||
|
|
@ -49,6 +49,15 @@ Le durcissement (`serveur_durci`) le **retire** donc, une fois qu'il a réussi
|
|||
parce qu'il a réussi qu'Ansible a pu entrer. Le gabarit, lui, le garde : sans lui, un clone
|
||||
n'a ni adresse ni nom d'hôte.
|
||||
|
||||
*Ce que ça ne fait pas* : ça **ne reprend pas la main à l'hébergeur**. `qemu-guest-agent`
|
||||
reste sur chaque VM — il doit y être, c'est par lui que la création confirme qu'une machine
|
||||
existe — et l'API de l'hyperviseur expose sur son dos `exec`, `file-write`,
|
||||
`set-user-password`, `shutdown` : strictement plus que le lecteur cloud-init. Ce qui est
|
||||
fermé est plus étroit, et bien réel : une réapplication *automatique, à chaque démarrage*,
|
||||
depuis un support que le plan ne possède pas, et un interpréteur Python complet lancé en
|
||||
root au démarrage. Qu'un hyperviseur puisse tout faire chez ses invités est une propriété
|
||||
de la virtualisation, pas de cloud-init.
|
||||
|
||||
*Pourquoi ça ne coupe pas le réseau* : l'adresse posée à la naissance vit dans
|
||||
`/etc/network/interfaces.d/50-cloud-init`, un fichier qui **n'appartient à aucun paquet** —
|
||||
`dpkg -S` ne le trouve pas, et le `postrm` ne le nomme jamais, même en `purge` (mesuré le
|
||||
|
|
|
|||
Loading…
Reference in a new issue