@windyroad/itil 0.47.1 → 0.47.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json
CHANGED
|
@@ -251,8 +251,16 @@ if [ -d "$PROBLEMS_DIR" ]; then
|
|
|
251
251
|
# problem_rfc_ids["P168"] = "RFC-001 RFC-002 ..."
|
|
252
252
|
declare -A problem_rfc_rows
|
|
253
253
|
declare -A problem_rfc_ids
|
|
254
|
+
# P312 / ADR-031: scan both flat docs/problems/<NNN>-*.md AND per-state
|
|
255
|
+
# subdir docs/problems/<state>/<NNN>-*.md layouts so the reverse-trace
|
|
256
|
+
# remains valid post-migration. Mirrors reconcile-readme.sh lines 74-110.
|
|
254
257
|
shopt -s nullglob
|
|
255
|
-
|
|
258
|
+
problem_files=( "$PROBLEMS_DIR"/[0-9][0-9][0-9]-*.md )
|
|
259
|
+
for ticket_status in open known-error verifying closed parked; do
|
|
260
|
+
problem_files+=( "$PROBLEMS_DIR"/"$ticket_status"/[0-9][0-9][0-9]-*.md )
|
|
261
|
+
done
|
|
262
|
+
shopt -u nullglob
|
|
263
|
+
for pf in "${problem_files[@]}"; do
|
|
256
264
|
pbase="$(basename "$pf")"
|
|
257
265
|
pnum="${pbase%%-*}"
|
|
258
266
|
pid="P${pnum}"
|
|
@@ -274,7 +282,6 @@ if [ -d "$PROBLEMS_DIR" ]; then
|
|
|
274
282
|
done < <(awk -v start="$sec_start" 'NR>start { if (/^## /) exit; print }' "$pf")
|
|
275
283
|
problem_rfc_ids["$pid"]="$rfcs_in_p"
|
|
276
284
|
done
|
|
277
|
-
shopt -u nullglob
|
|
278
285
|
|
|
279
286
|
# 1. MISSING_REVERSE_TRACE: RFC claims P, P does not list RFC.
|
|
280
287
|
for rfc_id in "${!rfc_problems_claim[@]}"; do
|
|
@@ -131,6 +131,40 @@ EOF
|
|
|
131
131
|
fi
|
|
132
132
|
}
|
|
133
133
|
|
|
134
|
+
# Helper: write a problem ticket under the per-state subdir layout per
|
|
135
|
+
# ADR-031 (state is the parent directory; filename has NO `.state.md` suffix).
|
|
136
|
+
# Args: <pid-num> <slug> <state> <rfcs-rows-block>
|
|
137
|
+
# Used to regression-test P312 — reconcile-rfcs reverse-trace must traverse
|
|
138
|
+
# docs/problems/<state>/<NNN>-*.md, not just flat docs/problems/<NNN>-*.<state>.md.
|
|
139
|
+
write_problem_subdir() {
|
|
140
|
+
local num="$1" slug="$2" state="$3" rfcs_rows="${4:-}"
|
|
141
|
+
mkdir -p "$PROBLEMS_DIR/$state"
|
|
142
|
+
local file="$PROBLEMS_DIR/$state/${num}-${slug}.md"
|
|
143
|
+
cat > "$file" <<EOF
|
|
144
|
+
# Problem ${num}: ${slug}
|
|
145
|
+
|
|
146
|
+
**Status**: ${state}
|
|
147
|
+
|
|
148
|
+
## Description
|
|
149
|
+
|
|
150
|
+
stub
|
|
151
|
+
|
|
152
|
+
## Related
|
|
153
|
+
|
|
154
|
+
stub
|
|
155
|
+
EOF
|
|
156
|
+
if [ -n "$rfcs_rows" ]; then
|
|
157
|
+
cat >> "$file" <<EOF
|
|
158
|
+
|
|
159
|
+
## RFCs
|
|
160
|
+
|
|
161
|
+
| RFC | Status | Title |
|
|
162
|
+
|-----|--------|-------|
|
|
163
|
+
${rfcs_rows}
|
|
164
|
+
EOF
|
|
165
|
+
fi
|
|
166
|
+
}
|
|
167
|
+
|
|
134
168
|
# ── Existence + executable ──────────────────────────────────────────────────
|
|
135
169
|
|
|
136
170
|
@test "reconcile-rfcs: script exists" {
|
|
@@ -413,6 +447,35 @@ EOF
|
|
|
413
447
|
done <<< "$output"
|
|
414
448
|
}
|
|
415
449
|
|
|
450
|
+
# ── P312: per-state subdir reverse-trace (ADR-031 layout) ───────────────────
|
|
451
|
+
# Closes P312 — reconcile-rfcs reported spurious MISSING_REVERSE_TRACE for
|
|
452
|
+
# tickets that live under docs/problems/<state>/<NNN>-*.md because the
|
|
453
|
+
# reverse-trace pass only globbed the flat docs/problems/<NNN>-*.md layout.
|
|
454
|
+
# RFC-002-class dual-tolerant-glob fix mirroring the sibling already shipped
|
|
455
|
+
# in reconcile-readme.sh (P118).
|
|
456
|
+
|
|
457
|
+
@test "P312: reverse-trace clean when problem ticket lives in per-state subdir" {
|
|
458
|
+
write_rfc "001" "foo" "accepted"
|
|
459
|
+
write_minimal_readme "| 2.0 | RFC-001 | foo | 3 Med | Accepted | M | 2026-05-05 |"
|
|
460
|
+
# Ticket lives under docs/problems/verifying/168-p168.md (no .state suffix).
|
|
461
|
+
write_problem_subdir "168" "p168" "verifying" "| RFC-001 | accepted | foo |"
|
|
462
|
+
run bash "$SCRIPT" "$FIXTURE_DIR" "$PROBLEMS_DIR"
|
|
463
|
+
[ "$status" -eq 0 ]
|
|
464
|
+
[[ "$output" != *"MISSING_REVERSE_TRACE"* ]]
|
|
465
|
+
}
|
|
466
|
+
|
|
467
|
+
@test "P312: reverse-trace detects missing trace when problem ticket lives in per-state subdir" {
|
|
468
|
+
write_rfc "001" "foo" "accepted"
|
|
469
|
+
write_minimal_readme "| 2.0 | RFC-001 | foo | 3 Med | Accepted | M | 2026-05-05 |"
|
|
470
|
+
# Subdir ticket WITHOUT a `## RFCs` section → MISSING_REVERSE_TRACE must fire.
|
|
471
|
+
write_problem_subdir "168" "p168" "verifying" ""
|
|
472
|
+
run bash "$SCRIPT" "$FIXTURE_DIR" "$PROBLEMS_DIR"
|
|
473
|
+
[ "$status" -eq 1 ]
|
|
474
|
+
[[ "$output" == *"MISSING_REVERSE_TRACE"* ]]
|
|
475
|
+
[[ "$output" == *"RFC-001"* ]]
|
|
476
|
+
[[ "$output" == *"P168"* ]]
|
|
477
|
+
}
|
|
478
|
+
|
|
416
479
|
# ── ADR-049 bin shim contract ───────────────────────────────────────────────
|
|
417
480
|
|
|
418
481
|
@test "wr-itil-reconcile-rfcs bin shim exists" {
|
|
@@ -170,6 +170,7 @@ If interactive (AskUserQuestion available) AND the description is short enough t
|
|
|
170
170
|
status: proposed
|
|
171
171
|
rfc-id: <kebab-slug>
|
|
172
172
|
reported: <YYYY-MM-DD>
|
|
173
|
+
human-oversight: unconfirmed
|
|
173
174
|
decision-makers: [<git config user.name>]
|
|
174
175
|
problems: [P<NNN>, P<NNN>, ...]
|
|
175
176
|
adrs: []
|
|
@@ -275,6 +276,8 @@ After the commit, report:
|
|
|
275
276
|
|
|
276
277
|
The trailing pointer is **not optional** — it is the user-visible signal that the RFC is intentionally skeleton-only and how to advance it.
|
|
277
278
|
|
|
279
|
+
**Oversight marker discipline (ADR-066 + ADR-068 amendments 2026-06-02 / P348).** The skeleton frontmatter MUST include `human-oversight: unconfirmed`. capture-rfc is the AFK-friendly aside surface; there is no substance-confirm `AskUserQuestion` pass in this flow (deferred to `/wr-itil:manage-rfc accepted`), so `confirmed` would be a hollow marker (the P348 bug class). The architect-side hook (`architect-oversight-marker-discipline.sh`) does NOT gate `docs/rfcs/`, but downstream paths that promote a captured RFC to `confirmed` MUST do so via a proper substance-confirm AskUserQuestion (e.g. `/wr-itil:manage-rfc accepted` for genuine ratification) — agents authoring RFCs at capture-time MUST NOT write `confirmed`. The drain pattern mirrors the ADR drain: an RFC's `unconfirmed` state surfaces interactively during the `accepted` transition.
|
|
280
|
+
|
|
278
281
|
## Composition with manage-rfc
|
|
279
282
|
|
|
280
283
|
| Concern | manage-rfc | capture-rfc |
|
|
@@ -216,7 +216,11 @@ For stop-conditions #1 and #3 (no actionable problems / all blocked), Step 2.5 s
|
|
|
216
216
|
|
|
217
217
|
Before the orchestrator emits the final `ALL_DONE` sentinel for the AFK loop, it MUST run the following gate sequence. The sequence fires **unconditionally** — at every stop-condition (`#1`, `#2`, `#3` per Step 2) AND at every halt-path that emits a final AFK summary AND on quota-exhaustion / natural loop end. The sequence has three parts that MUST complete in order; the structural rule is `ALL_DONE` emits ONLY after (a) AND (b) complete cleanly. Per-state subdir layout reminder: this step's order in the SKILL is logical (Step 2.4 fires *between* the Step 2 stop-check and the Step 2.5 surfacing routine *only as a wrapper*); the numerical ordering reflects the conceptual sequence (Step 2.4 wraps Step 2.5 + the new retro gate, then Step 2.5/2.5b execute as gate (a)'s worker).
|
|
218
218
|
|
|
219
|
-
**Gate (a) — Outstanding-questions surface
|
|
219
|
+
**Gate (a) — Outstanding-questions surface + oversight-unconfirmed drain (P348 amendment 2026-06-02).** Two sub-surfaces, both fire in this gate:
|
|
220
|
+
|
|
221
|
+
1. *Outstanding-questions surface.* Read `.afk-run-state/outstanding-questions.jsonl`. If non-empty, invoke Step 2.5b's surfacing routine to present the accumulated queue (via `AskUserQuestion`-when-available-else-table per ADR-013 Rule 1 / Rule 6). On completion, truncate the queue file. If the queue is empty, this sub-surface returns immediately. The surfacing routine is the existing Step 2.5b — Step 2.4 does NOT re-implement; it sequences.
|
|
222
|
+
|
|
223
|
+
2. *Oversight-unconfirmed drain.* Run `wr-architect-detect-unoversighted` and `wr-jtbd-detect-unoversighted` (both ADR-049 PATH shims, both always exit 0; output is the list of unoversighted artefact paths). If either lists ≥ 1 artefact whose frontmatter carries `human-oversight: unconfirmed` (the AFK-explicit-deferred state, distinct from the implicit-absent state pre-existing ADR/JTBD files carry), surface a one-line nudge: *"N iter-deferred decision(s)/job(s) carry `human-oversight: unconfirmed`. Run `/wr-architect:review-decisions` and `/wr-jtbd:confirm-jobs-and-personas` to drain."* If `AskUserQuestion` is available (`/wr-itil:work-problems` was invoked interactively before the AFK loop started), surface a 2-option choice — `Drain now` (invokes the appropriate drain skill before `ALL_DONE`) / `Defer to next session` (proceeds to gate (b) with the nudge in the final summary). If `AskUserQuestion` is unavailable, the nudge prints in the final summary table and gate (b) proceeds. The drain is NOT a halt — `unconfirmed` markers are explicit-by-design AFK signals (the iter wrote them KNOWING the user would need to confirm), and the drain is the documented path. Detector difference matters: ADRs/JTBDs that pre-date the ADR-066/ADR-068 marker contract carry NO `human-oversight:` line at all; they fall through to the existing review-decisions/confirm-jobs-and-personas backlog drain (no new surfacing here). The new surfacing fires ONLY on the explicit `unconfirmed` value — the AFK-iter-deferred class P348 introduces.
|
|
220
224
|
|
|
221
225
|
**Gate (b) — Session-level retro.** Invoke `/wr-retrospective:run-retro` via the Skill tool. This is the **orchestrator-main-turn session-level retro**, distinct from the per-iter retro fired inside each iter subprocess (per P086 / Step 5 retro-on-exit clause). The session-level retro covers cross-iter patterns, friction observations, framework-improvement candidates, and the AFK loop's overall trajectory — surface visible only after multiple iters have completed. Retro commits its own work per ADR-014; any tickets retro creates ride retro's own commit, and the orchestrator picks them up on the *next* invocation of `/wr-itil:work-problems` rather than re-entering the loop here.
|
|
222
226
|
|