[CLAUDE] Scripts: H25-closeout-ritual fold-per-label + batch>=3 INFORM guard (owner S137) — FP W3 tail-adjacency retired; fault-inject 12/12 PASS (9 regression + 3 fold-case); repo TOTAL 46->45, diff = dung 1 FP classified, W1/W2 window giu nguyen
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
@ -913,12 +913,15 @@ else {
|
||||
# log is not opening this session's log. The other three books accept any touch
|
||||
# (STATUS/HANDOFF/diaries are appended, not recreated).
|
||||
#
|
||||
# HONEST LIMIT (surfaced, NOT silenced): a tail-close commit whose previous close is
|
||||
# its own parent AND the same session batch yields a 1-commit window; that batch's
|
||||
# real ritual lives in the excluded lower-bound commit, so the tail reads incomplete
|
||||
# = a FALSE POSITIVE. The canonical spec baseline calls for per-session-label folding
|
||||
# of same-batch closes; this build is per-commit as handed. Do NOT special-case it to
|
||||
# green a report -- classify the flag and let the owner choose the grouping.
|
||||
# FOLD-PER-LABEL (owner decision S137; was HONEST LIMIT): consecutive closes whose
|
||||
# S-label ranges OVERLAP (batch close 'S131-S132' + tail-supplement 'S132') fold into
|
||||
# ONE close-group, scored once over the union window that opens at the previous
|
||||
# group's newest close. This is the per-session-label folding the canonical spec
|
||||
# baseline (phep-3 union-per-label) called for; it retires the tail-adjacency
|
||||
# false-positive class (W3/S132 - FP verified 3/3 on real git data in S136).
|
||||
# GUARD (owner-set, same decision): folding must not become a ritual-evasion lane --
|
||||
# a group spanning >= 3 sessions prints an INFORM line (not a flag) so a batch label
|
||||
# that swallows many sessions stays visible to the owner.
|
||||
#
|
||||
# git-based, so it honours -RepoRoot (fault-injection runs on a temp git tree). A
|
||||
# RepoRoot that is not a git work-tree SKIPs with a reason; a probe never crashes.
|
||||
@ -941,8 +944,14 @@ if ($gitTree) {
|
||||
$parts = $ln -split '\|', 2
|
||||
if ($parts.Count -lt 2) { continue }
|
||||
if ($parts[1] -match $CloseoutSubjectRx) {
|
||||
$lab = if ($parts[1] -match 'S(\d+)') { 'S' + $Matches[1] } else { 'S?' }
|
||||
$closeouts += [pscustomobject]@{ Hash = $parts[0]; Short = $parts[0].Substring(0, 7); Label = $lab }
|
||||
$lo = $null; $hi = $null; $lab = 'S?'
|
||||
if ($parts[1] -match 'S(\d+)(?:\s*-\s*S(\d+))?') {
|
||||
$lo = [int]$Matches[1]
|
||||
$hi = if ($Matches[2]) { [int]$Matches[2] } else { $lo }
|
||||
if ($hi -lt $lo) { $swp = $lo; $lo = $hi; $hi = $swp }
|
||||
$lab = if ($hi -ne $lo) { ('S{0}-S{1}' -f $lo, $hi) } else { ('S{0}' -f $lo) }
|
||||
}
|
||||
$closeouts += [pscustomobject]@{ Hash = $parts[0]; Short = $parts[0].Substring(0, 7); Label = $lab; Lo = $lo; Hi = $hi }
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -955,15 +964,40 @@ elseif ($closeouts.Count -eq 0) {
|
||||
Write-Host ' [skip] no commit matches the closeout subject shape - nothing to score' -ForegroundColor DarkGray
|
||||
}
|
||||
else {
|
||||
$take = [Math]::Min(3, $closeouts.Count)
|
||||
Write-Host (" closeouts found: {0} ; scoring {1} most-recent (union-window per close)" -f $closeouts.Count, $take)
|
||||
# Fold consecutive closes with OVERLAPPING S-label ranges into close-groups
|
||||
# (newest-first order preserved; 'S?' labels never fold). Owner decision S137.
|
||||
$closeGroups = @()
|
||||
foreach ($c in $closeouts) {
|
||||
$joined = $false
|
||||
if ($closeGroups.Count -gt 0 -and $null -ne $c.Lo) {
|
||||
$g = $closeGroups[$closeGroups.Count - 1]
|
||||
if ($null -ne $g.Lo -and ($c.Lo -le $g.Hi) -and ($g.Lo -le $c.Hi)) {
|
||||
$g.Members += $c
|
||||
if ($c.Lo -lt $g.Lo) { $g.Lo = $c.Lo }
|
||||
if ($c.Hi -gt $g.Hi) { $g.Hi = $c.Hi }
|
||||
$joined = $true
|
||||
}
|
||||
}
|
||||
if (-not $joined) {
|
||||
$closeGroups += [pscustomobject]@{ Tip = $c; Members = @($c); Lo = $c.Lo; Hi = $c.Hi }
|
||||
}
|
||||
}
|
||||
|
||||
$take = [Math]::Min(3, $closeGroups.Count)
|
||||
Write-Host (" closeouts found: {0} in {1} close-group(s) ; scoring {2} most-recent group(s) (label-folded union-window per group)" -f $closeouts.Count, $closeGroups.Count, $take)
|
||||
for ($i = 0; $i -lt $take; $i++) {
|
||||
$cur = $closeouts[$i]
|
||||
if ($i + 1 -ge $closeouts.Count) {
|
||||
Write-Host (" [skip] {0} {1}: no earlier close to open the window (oldest close in history) - not scored, not flagged" -f $cur.Short, $cur.Label) -ForegroundColor DarkGray
|
||||
$gcur = $closeGroups[$i]
|
||||
$cur = $gcur.Tip
|
||||
$glab = if ($null -eq $gcur.Lo) { 'S?' } elseif ($gcur.Hi -ne $gcur.Lo) { ('S{0}-S{1}' -f $gcur.Lo, $gcur.Hi) } else { ('S{0}' -f $gcur.Lo) }
|
||||
$span = if ($null -eq $gcur.Lo) { 1 } else { $gcur.Hi - $gcur.Lo + 1 }
|
||||
if ($span -ge 3) {
|
||||
Write-Host (" [INFORM] batch-label guard: group {0} folds {1} sessions into one ritual window - a batch label must not become a ritual-evasion lane (threshold >=3, owner-set S137)" -f $glab, $span) -ForegroundColor Yellow
|
||||
}
|
||||
if ($i + 1 -ge $closeGroups.Count) {
|
||||
Write-Host (" [skip] {0} {1}: no earlier close to open the window (oldest close in history) - not scored, not flagged" -f $cur.Short, $glab) -ForegroundColor DarkGray
|
||||
continue
|
||||
}
|
||||
$prev = $closeouts[$i + 1]
|
||||
$prev = $closeGroups[$i + 1].Tip
|
||||
$range = ("{0}..{1}" -f $prev.Hash, $cur.Hash)
|
||||
|
||||
$union = @()
|
||||
@ -981,10 +1015,10 @@ else {
|
||||
if (@($union | Where-Object { $_ -match '^\.claude/agent-memory/' }).Count -eq 0) { $missing += '.claude/agent-memory/**' }
|
||||
|
||||
if ($missing.Count -eq 0) {
|
||||
Write-Host (" [ok] {0} {1}: union ({2}..{3}] has all 4 ritual books" -f $cur.Short, $cur.Label, $prev.Short, $cur.Short) -ForegroundColor DarkGray
|
||||
Write-Host (" [ok] {0} {1}: union ({2}..{3}] has all 4 ritual books" -f $cur.Short, $glab, $prev.Short, $cur.Short) -ForegroundColor DarkGray
|
||||
}
|
||||
else {
|
||||
Write-Flag 'MED' ("git:{0} ({1})" -f $cur.Short, $cur.Label) `
|
||||
Write-Flag 'MED' ("git:{0} ({1})" -f $cur.Short, $glab) `
|
||||
("closeout-ritual gap: window ({0}..{1}] missing {2} of 4 books -> {3}" -f $prev.Short, $cur.Short, $missing.Count, ($missing -join ', ')) `
|
||||
'the session-close (or its window since the prior close) must touch STATUS + HANDOFF + a NEW session-log + an agent-memory diary'
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user