Repository navigation
ci(guard,#16645): cable check_link_label_agreement en TRANCHE12 advisory - #17014
Conversation
Le predicat « le libelle nomme un notebook different de la cible » (incident fondateur #13645 + extension scope decks #15867) vivait dans `scripts/notebook_tools/check_link_label_agreement.py` sans aucun workflow dedie qui le fasse tourner sur les PRs. La tranche 12 le cable en garde NATIVE de la voie rapide (FAST_LANE_NATIVE -- pas de workflow source a absorber : aucun n'existait), en scan global simple (`--fail`), blocking=False (advisory), paths incluant notebooks + READMEs series + docs + decks + le script lui-meme + ses tests + le registre. Le nom de check-run porte `advisory` pour que `pr_gate.is_advisory` matche et que le verdict reste neutral (jamais failure, jamais success -- signal visible sans rougir). Dette repo-wide mesuree au cablage : 0 finding sur main (scan 2198 fichiers, cf body #16645). Cout CI : ~5 s par scan global, dans le budget voie rapide. Tests : TRANCHE12 importe + agregee par fast_lane.py (parite registre->moteur epinglee par `test_every_tranche_in_the_registry_is_run_by_the_engine`), nouveau `test_tranche12_link_label_agreement_advisory` valide les invariants (nom advisory, blocking=False, source=FAST_LANE_NATIVE, paths incluant script + tests + registre + decks). 83/83 tests verts (48+9+1+25, aucune regression). Co-Authored-By: Claude Haiku 4.5 (1M context) <noreply@anthropic.com>
Path-collision (organ #13359/#13615)Cette PR #17014 (
|
|
[ADJOINT PREFLIGHT] |
|
[ADJOINT PREFLIGHT] |
Grain: MED/guard — lane myia-po-2027:CoursIA-2 — prev: MED/guard #17009
ci(guard,#16645): cable check_link_label_agreement en TRANCHE12 advisory
Diagnostic
Le predicat « le libelle nomme un notebook different de la cible » (un
defaut qui suit un renommage qui met a jour le
hrefen laissant le texteaffiche derriere -- incident fondateur #13645 + extension scope decks
#15867) vivait dans
scripts/notebook_tools/check_link_label_agreement.py(self-test PASS,organe de portee notebooks + READMEs series + docs + decks), mais sans
aucun workflow dedie qui le fasse tourner sur les PRs.
Issue #16645 demandait de cabler ce script en check CI advisory via
scripts/ci/fast_lane_registry.py. C'est la suite directe de laconsolidation #14624 (CLOSE_WITH_FOLLOWUP) : l'organe est eprouve
(self-test + 8 tests), il scanne clean (aucun desaccord sur le corpus au
moment du cablage, mesure datant du 2026-09-20), il manque juste le cable.
Changements
scripts/ci/fast_lane_registry.py: nouvelleTRANCHE12(un seulgarde) :
name="Link-label agreement (per-notebook, advisory)"(le motadvisorydans le nom assure quepr_gate.is_advisorymatche-- sans lui le verdict deviendrait bloquant par defaut, cf le
precedent TRANCHE6 markdown-deaccent).
source=FAST_LANE_NATIVE: pas de workflow dedie a absorber (l'issueci: câbler check_link_label_agreement.py en check advisory (fille de #14624) #16645 precise qu'aucun n'existait -- c'est une tranche de cablage,
pas une absorption).
paths=[MyIA.AI.Notebooks/**/*.ipynb, MyIA.AI.Notebooks/**/README.md, docs/**/*.md, slides/**/slides.md, scripts/notebook_tools/check_link_label_agreement.py, scripts/notebook_tools/tests/test_check_link_label_agreement.py, scripts/ci/fast_lane_registry.py]-- le script lui-meme + sestests + le registre figurent dans paths (clause guard(#5081): sécuriser les renames — collisions, suffixes noyau et réservation de slots #15489 : une
edition du script ne rejouerait pas le garde dont elle change la
portee).
argv=["python", "scripts/notebook_tools/check_link_label_agreement.py", "--fail"]: scan global simple, sans base (le script comparelibelle a cible dans chaque document, ne confronte pas a une version
de reference). Meme cabine que TRANCHE1 check-links (forme 1).
blocking=False,absorbed=True.scripts/ci/fast_lane.py: TRANCHE12 ajoutee aux imports et al'agregat
guards = [g for g in PILOT + TRANCHE1 + ... + TRANCHE12].La parite registre -> moteur est epinglee par
test_every_tranche_in_the_registry_is_run_by_the_engine(incidentfondateur feat(ci,#14325): cabler detect_markdown_deaccent en advisory per-PR (registre TRANCHE6) #14469 : TRANCHE6 etait definie mais JAMAIS importee
ni agregee, garde muet sur toutes les PRs).
scripts/tests/test_fast_lane.py: nouveautest_tranche12_link_label_agreement_advisoryqui valide lesinvariants (nom advisory, blocking=False, source=FAST_LANE_NATIVE,
absorbed=True, needs_base=False, iterates_paths=False, argv contient
--failmais pas{changed_paths}, paths inclut le script + sestests + le registre + decks). TRANCHE12 ajoutee a l'import en tete
du fichier.
Pourquoi advisory, pas bloquant
La dette repo-wide mesuree au cablage est de 0 finding sur main
(scan global du corpus notebooks + READMEs series + docs + decks, cf
body #16645). Demarrer en
blocking=Trueserait strict sur du vide :aucune PR ne declencherait le garde avec un verdict defect, mais aucune
non plus ne verrait le verdoyer "signale (advisory)" -- le caractere
report-only serait perdu.
Le passage en bloquant sera tranche par le coordinateur quand la dette
aura ete calibree (meme voie que TRANCHE11 source-collapse et que
TRANCHE6 markdown-deaccent, qui suivent le meme scenario).
Cout CI
~5 s par scan global (
--failrend 0 en 4-5 s sur le corpus global,mesure datant du 2026-09-20). Le check-run apparait en
neutralsur laPR -- signal visible, jamais rougissant, dans le budget voie rapide.
Validation post-fix
python -m pytest scripts/tests/test_fast_lane.py scripts/notebook_tools/tests/test_check_link_label_agreement.py -q-> 83 passed in 49.13s (48 fast-lane + 25 check-link-label + nouveau test_tranche12, aucune regression).python scripts/ci/fast_lane.py --only "Link-label agreement (per-notebook, advisory)" --base-sha HEAD-> garde reconnu, « hors perimetre (filtre paths) » sur main (diff HEAD vs main vide : aucun notebook modifie, normal).python scripts/notebook_tools/check_link_label_agreement.py --fail-> rc=0, scan global propre (aucun desaccord sur le corpus).python scripts/notebook_tools/check_link_label_agreement.py --self-test-> 7/7 PASS (controles positifs + negatifs du fondateur Lean-27 : référence résiduelle ICT-15d dans le texte, href vers ICT-15j-NerveDiscriminant #13645).Acceptance #16645
blocking=False(jamais bloquant dans un premier temps, decision reportee au coordinateur post-calibration)test_tranche12_link_label_agreement_advisoryvalide 13 invariants, dont la parite avecpr_gate.is_advisoryvia le mot-cle dans le nom)Note de cablage
Le precedent check_output_collapse.py (TRANCHE2, registre
advisory, mentionne dans l'issue #16645) suit la forme 2 (delta
base-vs-head,
--base {base_ref}). Notre garde suit la forme 1(scan global simple, sans base) -- le script ne confronte pas a une
version de reference, juste a la consistance interne libelle/cible.
Les deux formes sont legitimes ; le choix suit la nature du predicat.
🤖 Generated with Claude Code