Repository navigation
fix(sécurité): la solution de référence, chiffrée par ansible-vault - #74
Merged
Merged
Conversation
Le workflow de `fondations-premier-workflow` était commité en clair dans un dépôt public : l'apprenant qui clone avait la réponse sous la main. `meta.yml` déclarait `solutions: plaintext` et motivait ce choix par le fait qu'un workflow chiffré « ne se relirait pas ». C'était vrai des OUTILS du dépôt, pas une fatalité : deux lecteurs lisaient le fichier en clair, et il suffisait de leur apprendre à déchiffrer. `scripts/valider-labs.py` pose la solution par-dessus le répertoire de travail : il la déchiffre à la pose, sinon l'erreur parlerait de YAML invalide et non de chiffrement. `tests/test_solutions_exemplaires.py` contrôle que la solution épingle ses actions sur un SHA et déclare ses `permissions` : ses trois lectures déchiffrent. Sans cette seconde adaptation, il aurait gardé ses quinze verts en n'ayant plus aucun `uses:` à examiner, ce qui est précisément le défaut que ce dépôt traque chez les autres. Vérifié sur le comportement : le contrôle voit les 62 lignes du workflow et ses 2 `uses:` épinglés ; sans le secret, la lecture lève et les tests se déclarent non joués. `validate-structure` est vert et les 15 tests passent. Le rejeu « 0 avant, 100 après » ne se joue plus en CI, et c'est le coût assumé du chiffrement : le cycle a besoin du clair, et `.vault-pass` n'est pas sur la forge, comme dans aucun catalogue de la collection. Les deux étapes se déclarent non jouées par un avertissement visible. L'opposabilité du relevé ne tient donc plus à cette CI mais à la campagne locale qui l'a produit. L'autre voie, confier le secret au dépôt GitHub, a été écartée en connaissance. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Un troisième lecteur que mon inventaire avait manqué, et c'est la CI qui l'a trouvé : actionlint et zizmor analysent « le dépôt ET les solutions », par `scripts/hooks/cibles-workflows.sh`. Sur un fichier chiffré, actionlint rend « "on" section is missing » et « "jobs" section is missing » : un échec qui ne parle pas de chiffrement et qu'on ne peut pas corriger côté workflow. J'avais cherché les lecteurs dans `scripts/` et `tests/`, pas dans les workflows ni les hooks. Le bon périmètre était tout ce qui NOMME un chemin de solution, et c'est ce que ce correctif couvre : les trois appelants passent par le même script, donc un seul endroit à reprendre. Un répertoire de solution dont tous les workflows sont chiffrés est désormais écarté, et l'avertissement part sur STDERR : stdout est la liste des cibles, un message y deviendrait un chemin à analyser. Ce qui reste couvert, et par quoi : l'exemplarité des solutions (actions épinglées sur un SHA, bloc `permissions` déclaré) est contrôlée par `tests/test_solutions_exemplaires.py`, qui déchiffre. C'est là que vit la valeur pédagogique du contrôle. La syntaxe du workflow de solution est, elle, éprouvée autrement et mieux : le cycle local le fait jouer par `act`. Vérifié localement : actionlint analyse les 6 workflows du dépôt et sort en 0, zizmor ne rend aucune trouvaille, et le script annonce le répertoire écarté. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Le défaut
Le workflow de
fondations-premier-workflowétait commité en clair dans un dépôt public : l'apprenant qui clone avait la réponse sous la main.meta.ymlle déclarait, et motivait le choix par le fait qu'un workflow chiffré « ne se relirait pas ». C'était vrai des outils du dépôt, pas une fatalité : deux lecteurs consommaient le fichier en clair, et il suffisait de leur apprendre à déchiffrer.Les deux lecteurs, et pourquoi le second était le plus important
scripts/valider-labs.pytests/test_solutions_exemplaires.pypermissionsuses:à examinerLe second cas est précisément le défaut que ce dépôt traque chez les autres, et son propre
test_le_depot_a_des_workflows_a_controlerexiste pour cette raison : « un glob qui ne trouve rien produit zéro cas paramétré, donc zéro échec possible ». Le chiffrement aurait créé la même cécité un cran plus bas, sans vider la liste.Les trois lectures de ce test passent donc par
scripts/lecture_solution.py, qui déchiffre et lève quand il ne peut pas, plutôt que de rendre une chaîne vide.Contrôles joués, sur le comportement
uses:épinglés, donc il porte bien sur un workflow : 15 testspassedn'auraient rien prouvé seuls.dsoxlab validate-structureest vert,actionlintpropre.Le coût, assumé et écrit
Le rejeu « 0 avant, 100 après » ne se joue plus en CI. Le cycle a besoin du clair, et
.vault-passn'est pas sur la forge, comme dans aucun catalogue de la collection (ansible l'exclut même de ses archives de release). Les deux étapes concernées se déclarent non jouées par un avertissement visible, au lieu de passer pour un succès ou de rendre un rouge permanent qui finirait désactivé.L'opposabilité de
validation-labs.jsonne tient donc plus à cette CI mais à la campagne locale qui l'a produit, ce qui est la situation des onze autres catalogues. L'autre voie, confier.vault-passà un secret de dépôt, a été écartée en connaissance : elle aurait gardé le rejeu au prix de mettre sur la forge le secret qu'aucun catalogue n'y met.meta.ymlne porte plussolutions: plaintext; le paragraphe qui le motivait a été remplacé par ce que coûte le chiffrement, écrit sur place plutôt que redécouvert.Au passage
.gitignorene mentionnait pas.vault-pass. Le secret vit hors de git par construction : 48 octets d'aléa, mode 600.L'historique garde la solution en clair : ce commit la retire de l'arbre, pas du passé.
CHANGELOG EN et FR, bump en
0.2.2,uv.lockrafraîchi.🤖 Generated with Claude Code