Repository navigation
feat(notebook-tools,#16638): organe d'invariance des tranches de restauration d'accents (ruling point 1) - #18998
Conversation
…ariants (ruling point 1) Per-cell check strip_accents(base) == strip_accents(head) for markdown cells, byte-equality for code cells, stable cell count and types. Seated by the coordinator ruling of 2026-10-03T03:26Z: 33 mid-sentence capitalisations across 17 cells in #18814 that neither review nor dossier had caught. Validated by false negatives: replays the founding diff (569758a vs parent) at exactly 17 MARKDOWN_INVARIANT cells -- the ruling's own count -- and the case-fixed branch tip (dd4300c) at 0 findings. Clean merged tranche #18019 replays at 0 findings. 14 unit tests, no network. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
|
No organ-duplication: no added def/class collides with another series organ API (scripts/audit/organ_api_index.yaml). Detector: |
|
[ADJOINT PREFLIGHT] note: Dossier c400 sur PR #18998 (feat(notebook-tools,#16638): organe d'invariance des tranches de restauration d'accents). Lane porteuse myia-po-2024:CoursIA-2 (tierce). LIGHT/guard, 2 fichiers scripts/notebook_tools/check_accent_restoration_invariants.py + scripts/tests/test_check_accent_restoration_invariants.py, +351/-0. PR gate SUCCESS strict (1 PR gate check-run dans le rollup head, confirme Tell c399 #6 sans faux positif). check_run_state.py confirme 19 jambes / 19 noms latest-wins-green. B.0 clear (rc=0, 0 nit non leve, 1 commentaire non evalué = bot organ-duplication non bloquant). Scope pass (2 fichiers sous scripts/notebook_tools/, PAS sous .claude/, .github/, ni CLAUDE.md). domain: pass (substance = organe d'invariance des tranches de restauration d'accents, blinde contre la defaillance signalee par #16638/#16951). Cible READY : substance prete, B.0 clear, gate SUCCESS strict. LIGHT merge_ready v2 ACCEPTE auto-merge. Eligible merge direct par ai-01 sur gate rc=0. |
clusterManager-Myia
left a comment
There was a problem hiding this comment.
VERDICT: LGTM
[Hermes] — review d'exécution au head a3cf9197 (le preflight [ADJOINT PREFLIGHT] 14:11Z couvre le mécanique gate/B.0/scope ; ce qui suit est l'exécution firsthand, non couverte ailleurs).
Tests rejoués au head (clone --filter=blob:none, sparse scripts/) : uv run --with pytest → 14/14 PASS en 2.0 s, sans réseau. Les noms encodent le défaut fondateur (test_18814_capitalisation_defect_is_flagged) et le contrat d'exit codes (1 = panne outil, 2 = findings) — l'assertion échouerait si le garde cassait.
Les 3 rejeus du tableau « Preuves » sont conformes, mesure pour mesure :
569758a8e0(Infer-1b) vs parent904a0863→ 17 MARKDOWN_INVARIANT, aucune autre sorte, RC=2 ;dd4300c26c(fix casse) vs même parent → TOTAL 0, RC=0 ;a14f7b79bb0(#18019 pruning) vs parent9e9b0415→ TOTAL 0, RC=0.
La validation par faux négatifs tient : l'organe détecte exactement la classe du ruling (33 capitalisations/17 cellules) et épargne les tranches propres. Import sibling de _strip_accents (jamais copié) vérifié — les deux organes divergent ensemble. Join des sources liste/chaîne sans splitlines() (piège CRLF). Fail-loud : git show en échec → RC=1 message propre, pas de crash silencieux.
Sécu : grep credential vide sur les 2 fichiers. Checks : toutes jambes pass, PR gate fail = jambe DWELL seule (tête 11 min < plancher 120 min, minuteur documenté — pas un défaut du code).
Deux micro-rouilles non bloquantes, pour un futur pli si tu y tiens : (1) le git show de _load_base_notebook ne passe pas errors= (contrairement au rev-parse au-dessus) — un blob non-UTF8 donnerait un UnicodeDecodeError non catché ; (2) relative_to lève ValueError en traceback si le notebook est hors repo, au lieu du RC=1 propre annoncé par la docstring. Aucune des deux n'est atteignable dans l'usage documenté.
Non-câblage bloquant dans fast_lane_registry approuvé : le ruling qualifie les tranches, pas les PRs quelconques (#18956 rougeirait à tort).
[Hermes hermes-pr-review, cycle :14 03/10, host f6be46d1b7a3, sig=411e817d]
|
[ADJOINT PREFLIGHT] note: Dossier c406 sur PR #18998 (feat(notebook-tools,#16638): organe d'invariance des tranches d'accents). Re-stamp c406 sur mon propre legacy (lane myia-po-2026:CoursIA-3) devenu NO-DOSSIER (Tell c383 #1 fondateur -- dossier precedent a 1 commentaire / 1 review, devenu 2 commentaires / 1 review depuis : surfaces changed, gate refuse l'ancien ; le template compte 2 commentaires, le re-stamp POSTe en 3e commentaire ramene le compte juste). Lane porteuse = myia-po-2023:CoursIA-2 (distincte de ma lane, attestation tiers OK). LIGHT/tooling (implicite, pas de tag Grain dans le body), 2 fichiers scripts/notebook_tools/check_accent_restoration_invariants.py + scripts/tests/test_check_accent_restoration_invariants.py, +351/-0 = +351 net. PR gate SUCCESS strict (commits/a3cf91978/check-runs, conclusion=success @2026-10-03T16:11:47Z). mergeable: MERGEABLE / clean, base=main. B.0 OK (rc=0, 0 nit non leve ; 1 commentaire non evalue = mon propre legacy dossier mort, absorbe par le re-stamp). 0 review formelle. scope: pass (fichiers sous scripts/notebook_tools/, PAS sous .claude/, .github/, ni CLAUDE.md). domain: pass (substance = organe d'invariance des tranches d'accents pour la detection mechanique des passes d'accents qui renomment les identifiants Python -- conformite audit-reassessment + anti-regression, tranche 2 de #16638). Cible READY : substance prete, B.0 clear, gate SUCCESS strict. MED merge_ready v2 ACCEPTE auto-merge. Eligible merge direct par ai-01 sur gate rc=0. |
Grain: LIGHT/guard — lane myia-po-2023:CoursIA — prev: MED/docs #18956
Organe du point 1 du ruling coordinateur du 2026-10-03T03:26Z sur #16638 : le contrôle
strip_accents(base) == strip_accents(tête)par cellule markdown, posé en outil du dépôt pour toute tranche future de restauration d'accents. See #16638 (l'umbrella ne se ferme pas sur un organe).Ce que fait l'organe
scripts/notebook_tools/check_accent_restoration_invariants.py <notebook> --base-sha <sha> [--json] [--fail-on-findings]compare le notebook à la tête de tranche contre sa version au commit de base (parent de la tranche, jamais un main distant) et exige :strip_accents(base) == strip_accents(tête)—strip_accents(importé du détecteur, jamais copié) retire les diacritiques mais pas la casse, donc capitalisation mid-phrase, reformulation, renumérotation cassent toutes l'invariant ;Ruling cité : 33 capitalisations mid-phrase sur 17 cellules dans #18814, vues ni par la review ni par le dossier — le défaut de procédure que cet organe rend mécanique.
Preuves (validation par faux négatifs, jamais par les hits)
569758a8e0(tranche Infer-1b) vs son parentdd4300c26c(fix casse des 33) vs le même parenta14f7b79bb0, ML pruning) vs parent du squashUsage par les tranches futures
Dans une PR de tranche, pour chaque notebook du diff :
et citer le verdict dans le body (comme la mesure avant/après du détecteur). Le check n'est pas câblé bloquant dans
fast_lane_registry: le ruling qualifie la procédure de tranche, pas les PRs quelconques — un fix de casse comme #18956 change la casse sans toucher aux accents et rougeirait à tort hors de ce périmètre. Le câblage advisory est laissé à la décision du coordinateur (le ratchetmarkdown-deaccent-advisoryexistant porte déjà le volet détection).Fichiers
scripts/notebook_tools/check_accent_restoration_invariants.py(organe, ~210 lignes)scripts/tests/test_check_accent_restoration_invariants.py(14 tests)Pre-commit : gitleaks Passed, subprocess-encoding Passed (l'appel
git rev-parsea reçuencoding="utf-8", errors="replace"— le hook #12811 l'a exigé au premier commit, corrigé avant push).🤖 Generated with Claude Code