From a3222db3aed2919d03efc7996bafcffa7d8859c2 Mon Sep 17 00:00:00 2001 From: jsboige Date: Sun, 13 Sep 2026 02:57:21 +0200 Subject: [PATCH] fix(ci,#15864): refuser la continuation de lane apres un point de prose Un point suivi d'un blanc est de la ponctuation de phrase, jamais une partie de : ; un point interne (hostname, Foo.Bar) survit. Implemente par (? lane nue (primaire, fallback, parse_grain_tag, temoin) ; _run_check payload reel CLEAR (rc 0) ; 6/6 nouveaux tests FAIL avant fix / PASS apres ; non-regressions LivresAgites Episode, A.B, host.example:Baz, date nue, point final ; 402 tests grain_tag+lane_claim verts, 208 consommateurs verts. Co-Authored-By: Claude Sonnet 5 --- scripts/grain_tag.py | 25 +++++++++++- scripts/tests/test_check_lane_claim.py | 32 +++++++++++++++ scripts/tests/test_grain_tag.py | 56 ++++++++++++++++++++++++++ 3 files changed, 111 insertions(+), 2 deletions(-) diff --git a/scripts/grain_tag.py b/scripts/grain_tag.py index 9c1cd131b0..9debccebd5 100644 --- a/scripts/grain_tag.py +++ b/scripts/grain_tag.py @@ -192,6 +192,27 @@ def _strip_title_hashes(flat: str) -> str: # body class widens to the corresponding lowercase range (`à-öø-ÿ` + ſ) so the # maximal-munch `(?![A-Za-z0-9._À-ſ-])` keeps working with the new characters. # Tested in `test_lane_workspace_accented` + the existing #12145 / #12719 set. +# #15864 -- a PROSE PERIOD followed by an accented continuation word is the +# fourth variant of the self-blocking class (#12145 space-workspace, #12719 +# bare date, #13830 accents, now #12719 x #13830). The founder marker of +# issue #15674: +# +# [DELIVERED] PR #15733 — lane myia-po-2023:CoursIA. Énoncé réécrit ... +# +# The workspace class admits `.` (hostnames need it, #12719), so it eats +# `CoursIA.`; the continuation then legitimately admits `Énoncé` (#13830 +# accented uppercase) and the read token becomes `myia-po-2023:CoursIA. +# Énoncé` -- a lane that exists nowhere, which check_lane_claim used to +# block the declaring lane on (its OWN [DELIVERED] re-marker, #12320). +# +# Rule: a `.` followed by whitespace is PROSE PUNCTUATION, never part of a +# `:` token; a `.` INSIDE a token (hostname, `Foo.Bar`) +# is followed by a non-blank and survives. Implemented by a `(? str: # `test_lane_workspace_accented` + the existing #12145 / #12719 set # + the #13869 comparative table (LivresAgités / Cours×IA / Łódź). r"([A-Za-z0-9._-]+:[A-Za-zÀ-ÖØ-öø-ÿĀ-ſ0-9._-]+" - r"(?:[ \t]+(?!\d{4}-\d{2}-\d{2})(?-i:[A-Z0-9À-ÖØ-ÞĀ-ſ])[A-Za-z0-9._À-ÖØ-öø-ÿĀ-ſ-]*(?![A-Za-z0-9._À-ÖØ-öø-ÿĀ-ſ-])(?![:@])){0,3})", + r"(?:(? str: # The twin MUST move with the primary or the founder's class of bug # (#12145) re-opens on the fallback only. r"\b(myia-[A-Za-z0-9._-]+:[A-Za-zÀ-ÖØ-öø-ÿĀ-ſ][A-Za-zÀ-ÖØ-öø-ÿĀ-ſ0-9._-]*" - r"(?:[ \t]+(?!\d{4}-\d{2}-\d{2})(?-i:[A-Z0-9À-ÖØ-ÞĀ-ſ])[A-Za-z0-9._À-ÖØ-öø-ÿĀ-ſ-]*(?![A-Za-z0-9._À-ÖØ-öø-ÿĀ-ſ-])(?![:@])){0,3})" + r"(?:(? lane None (surfaced, not guessed). ev = clc.parse_claim_event(comment( diff --git a/scripts/tests/test_grain_tag.py b/scripts/tests/test_grain_tag.py index 6986f5a0b7..03ad17e219 100644 --- a/scripts/tests/test_grain_tag.py +++ b/scripts/tests/test_grain_tag.py @@ -1102,6 +1102,62 @@ def test_lane_workspace_rejects_multiplication_sign(): assert g == "myia-x:Cours", "× (U+00D7) must not be admitted as a letter" +# --- #15864: prose period + accented continuation = phantom lane ----------- +# +# Founder marker of issue #15674 (4th variant of the self-blocking class: +# #12145 x #12719 x #13830). The workspace class eats the sentence period +# (`CoursIA.`), the #13830 accented-continuation then admits `Énoncé`, and +# the read token `myia-po-2023:CoursIA. Énoncé` blocked the declaring lane +# on its OWN [DELIVERED] re-marker. The `(?