@windyroad/itil 0.3.2-preview.75 → 0.3.3-preview.77

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
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@windyroad/itil",
3
- "version": "0.3.2-preview.75",
3
+ "version": "0.3.3-preview.77",
4
4
  "description": "ITIL-aligned IT service management for Claude Code (problem, and future incident/change skills)",
5
5
  "bin": {
6
6
  "windyroad-itil": "./bin/install.mjs"
@@ -28,8 +28,16 @@ Create, update, or transition problem tickets following an ITIL-aligned problem
28
28
  |--------|-----------|---------|----------------|
29
29
  | **Open** | `.open.md` | Reported, under investigation | New problem identified |
30
30
  | **Known Error** | `.known-error.md` | Root cause confirmed, fix path clear | Root cause documented, reproduction test exists, workaround in place |
31
+ | **Parked** | `.parked.md` | Blocked on upstream or suspended by user decision | Upstream blocker identified, or user explicitly suspends; reason and un-park trigger documented |
31
32
  | **Closed** | `.closed.md` | Fix verified in production | Fix released AND user explicitly confirms it works |
32
33
 
34
+ **Parked problems** are excluded from WSJF ranking and work selection. They are listed separately in review output so users can see them without them polluting the backlog. To park a problem:
35
+ 1. `git mv docs/problems/<NNN>-<title>.<current>.md docs/problems/<NNN>-<title>.parked.md`
36
+ 2. Update the Status field to "Parked"
37
+ 3. Add a `## Parked` section with: reason for parking, expected trigger to un-park, date parked
38
+
39
+ To un-park: `git mv` back to `.open.md` (or `.known-error.md` if root cause is confirmed), update Status, remove `## Parked` section.
40
+
33
41
  **Test-driven resolution:** When root cause is identified, create a failing test that reproduces the problem. Skip/disable the test if a feature-disabling workaround is applied. Re-enable the test when the permanent fix is implemented — the test passing confirms resolution.
34
42
 
35
43
  ## WSJF Prioritisation
@@ -225,11 +233,29 @@ Read all `.open.md` and `.known-error.md` files in `docs/problems/`. Extract ID,
225
233
 
226
234
  This is a batch operation that reviews every open/known-error problem and updates it.
227
235
 
236
+ **Fast-path for `work` (skip full re-scan when cache is fresh):**
237
+
238
+ Before running the full review, check whether `docs/problems/README.md` exists and is up to date:
239
+
240
+ ```bash
241
+ find docs/problems -name "*.md" ! -name "README.md" -newer docs/problems/README.md 2>/dev/null | head -1
242
+ ```
243
+
244
+ If this command produces **no output** (README.md is newer than all problem files), the cache is fresh:
245
+ - Read `docs/problems/README.md` only — it contains the ranked table from the last review
246
+ - Skip steps 9a–9b entirely
247
+ - Proceed directly to step 9c (work selection) using the cached table
248
+ - Note in the output: "Using cached ranking from [timestamp in README.md]"
249
+
250
+ If the command produces output, or `README.md` does not exist, run the full review (steps 9a–9e) and refresh the cache.
251
+
228
252
  **Step 9a: Read the risk framework**
229
253
 
230
254
  Read `RISK-POLICY.md` to get the current impact levels (1-5), likelihood levels (1-5), risk matrix, and label bands. These are the authoritative definitions — do not use outdated scales.
231
255
 
232
- **Step 9b: For each open/known-error problem:**
256
+ **Step 9b: For each open/known-error problem (skip `.parked.md` files entirely):**
257
+
258
+ Parked problems are excluded from WSJF ranking — do not read, score, or update them in this step. They are shown in a separate section in step 9c.
233
259
 
234
260
  1. Read the problem file
235
261
  2. Read the codebase context — check if the problem's root cause has been investigated, if there are related fixes in git history, or if the problem is stale
@@ -247,11 +273,16 @@ Read `RISK-POLICY.md` to get the current impact levels (1-5), likelihood levels
247
273
 
248
274
  **Step 9c: Present summary and select problem to work**
249
275
 
250
- After reviewing all problems, present a WSJF-ranked table:
276
+ After reviewing all problems, present a WSJF-ranked table for open/known-error problems:
251
277
 
252
278
  | WSJF | ID | Title | Severity | Status | Effort | Notes |
253
279
  |------|-----|-------|----------|--------|--------|-------|
254
280
 
281
+ Then present a separate **Parked** section listing `.parked.md` files (no ranking):
282
+
283
+ | ID | Title | Reason | Parked since |
284
+ |----|-------|--------|-------------|
285
+
255
286
  Highlight:
256
287
  - Problems whose priority changed (↑ or ↓)
257
288
  - Problems that were auto-transitioned to known-error
@@ -275,10 +306,33 @@ Highlight:
275
306
 
276
307
  For each known-error that has a `## Fix Released` section, use `AskUserQuestion` to ask the user if the fix has been verified in production. If the user confirms, close the problem (`git mv` to `.closed.md`, update Status). If the user says no or is unsure, leave it as known-error.
277
308
 
278
- **Step 9e: Update files**
309
+ **Step 9e: Update files and refresh README.md cache**
310
+
311
+ Edit each problem file where the priority changed. Then write/overwrite `docs/problems/README.md` with the current ranked table so future `work` invocations can skip the full re-scan:
312
+
313
+ ```markdown
314
+ # Problem Backlog
315
+
316
+ > Last reviewed: <ISO timestamp>
317
+ > Run `/wr-itil:manage-problem review` to refresh.
318
+
319
+ ## WSJF Rankings
320
+
321
+ | WSJF | ID | Title | Severity | Status | Effort |
322
+ |------|-----|-------|----------|--------|--------|
323
+ | <score> | P<NNN> | <title> | <severity> | <status> | <effort> |
324
+ ...
325
+
326
+ ## Parked
327
+
328
+ | ID | Title | Reason | Parked since |
329
+ |----|-------|--------|-------------|
330
+ | P<NNN> | <title> | <reason> | <date> |
331
+ ...
332
+ ```
279
333
 
280
- Edit each problem file where the priority changed. Then commit the updated files per ADR-014:
281
- 1. `git add` the changed problem files
334
+ Then commit all changed files per ADR-014:
335
+ 1. `git add` the changed problem files and `docs/problems/README.md`
282
336
  2. Delegate to `wr-risk-scorer:pipeline` to assess and create a bypass marker
283
337
  3. `git commit -m "docs(problems): review — re-rank priorities"`
284
338
  If `AskUserQuestion` is unavailable and risk is above appetite, skip the commit and report the uncommitted state.
@@ -44,3 +44,20 @@ setup() {
44
44
  run grep -n "which way?" "$SKILL_FILE"
45
45
  [ "$status" -ne 0 ]
46
46
  }
47
+
48
+ @test "SKILL.md mandates AskUserQuestion for work-next selection (WSJF tie-break)" {
49
+ # ADR-013 Rule 1: the step 9c work-selection branch must use AskUserQuestion,
50
+ # not a prose '(a)/(b)/(c)' list. This is a regression guard — if step 9c is
51
+ # edited and the AskUserQuestion mandate is removed, this test catches it.
52
+ # P021 investigation task: manage-problem WSJF tie → assert AskUserQuestion.
53
+ run grep -n "AskUserQuestion" "$SKILL_FILE"
54
+ [ "$status" -eq 0 ] # file MUST reference AskUserQuestion
55
+ }
56
+
57
+ @test "SKILL.md mandates AskUserQuestion for scope-change decisions during work" {
58
+ # ADR-013 Rule 1: the 'Scope expansion during work' branch must use AskUserQuestion.
59
+ # 'Scope change' is the header text used in the AskUserQuestion call for scope decisions
60
+ # (per P021 amendment). Regression guard.
61
+ run grep -n "Scope change" "$SKILL_FILE"
62
+ [ "$status" -eq 0 ]
63
+ }
@@ -0,0 +1,68 @@
1
+ #!/usr/bin/env bats
2
+ # Doc-lint guard: manage-problem SKILL.md must define the Parked lifecycle
3
+ # status and the README.md fast-path cache for the `work` operation.
4
+ #
5
+ # Structural assertions — Permitted Exception to the source-grep ban (ADR-005 / P011).
6
+ # These tests assert that the skill specification document conforms to the
7
+ # P027 fix: first-class Parked status + README.md-based WSJF cache.
8
+ #
9
+ # Cross-reference:
10
+ # P027: docs/problems/027-manage-problem-work-flow-is-expensive.open.md
11
+ # @jtbd JTBD-001 (enforce governance without slowing down — under 60s)
12
+ # @jtbd JTBD-005 (invoke governance assessments on demand)
13
+
14
+ setup() {
15
+ SKILL_DIR="$(cd "$(dirname "$BATS_TEST_FILENAME")/.." && pwd)"
16
+ SKILL_FILE="${SKILL_DIR}/SKILL.md"
17
+ }
18
+
19
+ # ──────────────────────────────────────────────────────────────────────────────
20
+ # Parked lifecycle status
21
+ # ──────────────────────────────────────────────────────────────────────────────
22
+
23
+ @test "SKILL.md lifecycle table includes Parked status" {
24
+ # P027: Parked must be a first-class status so parked problems are
25
+ # auto-excluded from work selection without manual user flags each session.
26
+ run grep -q "Parked" "$SKILL_FILE"
27
+ [ "$status" -eq 0 ]
28
+ }
29
+
30
+ @test "SKILL.md defines .parked.md file suffix" {
31
+ # Parked problems need a distinct file suffix so the review step can
32
+ # identify and exclude them by filename pattern alone.
33
+ run grep -q "\.parked\.md" "$SKILL_FILE"
34
+ [ "$status" -eq 0 ]
35
+ }
36
+
37
+ @test "SKILL.md excludes parked problems from WSJF ranking" {
38
+ # Parked problems must not appear in the WSJF table — they are listed
39
+ # separately so users can see them but they don't pollute the ranking.
40
+ run grep -q "parked.*exclud\|exclud.*parked\|Parked.*exclud\|exclud.*Parked\|skip.*[Pp]arked\|[Pp]arked.*skip" "$SKILL_FILE"
41
+ [ "$status" -eq 0 ]
42
+ }
43
+
44
+ # ──────────────────────────────────────────────────────────────────────────────
45
+ # README.md cache (fast-path for `problem work`)
46
+ # ──────────────────────────────────────────────────────────────────────────────
47
+
48
+ @test "SKILL.md references README.md as the cache file" {
49
+ # P027: docs/problems/README.md is the WSJF cache written by review
50
+ # and read by work to skip the full re-scan when nothing changed.
51
+ run grep -q "README\.md" "$SKILL_FILE"
52
+ [ "$status" -eq 0 ]
53
+ }
54
+
55
+ @test "SKILL.md describes writing README.md after review" {
56
+ # The review step (9e) must write/overwrite README.md with the ranked table.
57
+ # Without this write, the cache never gets populated.
58
+ run grep -q "README\.md" "$SKILL_FILE"
59
+ [ "$status" -eq 0 ]
60
+ }
61
+
62
+ @test "SKILL.md describes checking README.md freshness before full re-scan" {
63
+ # The work fast-path: if README.md is newer than all problem files,
64
+ # skip the 18-file re-scan and read the cached table directly.
65
+ # Proxy: SKILL.md mentions -newer (the find flag used for mtime comparison).
66
+ run grep -q "\-newer" "$SKILL_FILE"
67
+ [ "$status" -eq 0 ]
68
+ }