@rune-kit/rune 2.20.0 → 2.22.0

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.
@@ -5,13 +5,13 @@ context: fork
5
5
  agent: general-purpose
6
6
  metadata:
7
7
  author: runedev
8
- version: "2.5.0"
8
+ version: "2.6.1"
9
9
  layer: L1
10
10
  model: sonnet
11
11
  group: orchestrator
12
12
  tools: "Read, Write, Edit, Bash, Glob, Grep"
13
13
  emit: phase.complete, checkpoint.request
14
- listen: plan.ready, review.complete, ideas.ready, preflight.passed, verification.complete
14
+ listen: plan.ready, review.complete, ideas.ready, preflight.passed, verification.complete, convergence.gaps, convergence.clean
15
15
  ---
16
16
 
17
17
  # cook
@@ -110,8 +110,8 @@ Not every task needs every phase:
110
110
  Nano task: DO → VERIFY → DONE (no phases, auto-detected)
111
111
  Simple bug fix: Phase 1 → 4 → 6 → 7
112
112
  Small refactor: Phase 1 → 4 → 5 → 6 → 7
113
- New feature: Phase 1 → 1.5 → 2 → 3 → 4 → 5 → 6 → 7 → 8
114
- Complex feature: All phases + brainstorm in Phase 2
113
+ New feature: Phase 1 → 1.5 → 2 → 3 → 4 → 5 → 6 → 6.5 → 7 → 8 (6.5: conditional — requires requirements.md)
114
+ Complex feature: All phases (incl. 6.5) + brainstorm in Phase 2
115
115
  Security-sensitive: All phases + sentinel escalated to opus
116
116
  Fast mode: Phase 1 → 4 → 6 → 7 (auto-detected, see below)
117
117
  Multi-session: Phase 0 (resume) → 3 → 4 → 5 → 6 → 7 (one plan phase per session)
@@ -507,12 +507,37 @@ Invoke `rune:session-bridge` after Phase 2, 4, and 5 to save intermediate state.
507
507
 
508
508
  Before entering ANY Phase N+1, assert: Phase N `completed` in TodoWrite | gate condition met | no BLOCK from sub-skills | no unresolved CRITICAL findings. If any fails → STOP, log "BLOCKED at Phase N→N+1: [assertion]", fix, re-check.
509
509
 
510
- **Key transitions:** 1→2: scout done | 2→3: plan approved | 3→4: failing tests exist | 4→5: all tests pass | 5→6: no CRITICAL findings | 6→7: lint+types+build green.
510
+ **Key transitions:** 1→2: scout done | 2→3: plan approved | 3→4: failing tests exist | 4→5: all tests pass | 5→6: no CRITICAL findings | 6→6.5: lint+types+build green | 6.5→7: convergence.clean or documented escalation (features with requirements.md; others pass through).
511
511
 
512
512
  ## Phase 6: VERIFY
513
513
 
514
514
  **REQUIRED SUB-SKILL**: Use `rune:verification` — run lint, type check, full test suite, build. Then `rune:hallucination-guard` to verify imports and API signatures. ALL checks MUST pass before commit.
515
515
 
516
+ **Quickstart execution**: if `.rune/features/<name>/quickstart.md` exists (plan Step 3.7 boundary artifact), execute its validation blocks — run each command, compare against its **Expect** line. Any mismatch = verification FAIL (treat like a failing test). If the environment cannot run a block (no browser, no DB), SKIP it with the reason named in the Cook Report — a skipped quickstart is visible debt, never silent.
517
+
518
+ ## Phase 6.5: CONVERGE (Spec↔Code Gap Scan)
519
+
520
+ **REQUIRED SUB-SKILL**: Use `rune:converge` — verify the ACTUAL codebase matches the spec before committing.
521
+
522
+ **Trigger**: feature/greenfield chains where `.rune/features/<name>/requirements.md` exists.
523
+ **Skip** (announce the skip): nano/fast/bugfix/refactor/hotfix chains, or no requirements.md (ad-hoc task — Phase 5 gates are the only protection).
524
+
525
+ 1. Invoke `rune:converge` — it re-reads spec/plan/contracts as sole intent, scans present code state, classifies gaps (`missing` / `partial` / `contradicts` / `unrequested`)
526
+ 2. **`convergence.clean`** → proceed to Phase 7
527
+ 3. **`convergence.gaps`** → inspect the signal's `counts` payload first:
528
+ - **Unrequested-only** (`counts.missing`=0, `counts.partial`=0, `counts.contradicts`=0, `counts.unrequested`>0): no CV tasks were appended — surface the findings in the Cook Report and proceed to Phase 7. Do NOT enter the remediation loop for informational scope-creep findings
529
+ - **Otherwise**: converge appended `CV-*` remediation tasks to the active phase file:
530
+ - Execute the CV tasks (return to Phase 4 loop for them; CRITICAL/HIGH first)
531
+ - Re-run Phase 6 VERIFY on the remediated code, then re-invoke converge (round 2)
532
+ - **Max 2 remediation rounds.** Gaps still present after round 2 → produce a Structured Escalation Report (the same gap surviving 2 rounds means the approach is wrong, not the effort)
533
+ 4. `unrequested` findings are surfaced to the user in the Cook Report — never silently deleted, never blocking
534
+ 5. **Stale CV tasks**: if converge reports clean but unchecked `CV-*` tasks remain from earlier rounds (e.g., rules changed between rounds), cook closes them as `[x] (resolved — superseded)` with a Cook Report note — converge's append-only contract means only cook may touch them
535
+
536
+ <HARD-GATE>
537
+ A P1 story with a CRITICAL convergence gap (missing/contradicts) MUST NOT be committed as "done."
538
+ Either remediate within the round cap, or escalate with the gap documented — never claim completion over a known dead path.
539
+ </HARD-GATE>
540
+
516
541
  ## Phase 7: COMMIT
517
542
 
518
543
  **RECOMMENDED SUB-SKILL**: Use `rune:git` — stage specific files (`git add <files>`, NOT `git add .`), generate semantic commit message from diff. If working from master plan: update phase status `🔄 → ✅`, announce next phase or "All phases complete."
@@ -777,6 +802,7 @@ Mentally track tool call fingerprints. 3 identical calls → WARN. 5 identical c
777
802
  | 5 | `constraint-check` | L3 | Audit HARD-GATE compliance across workflow |
778
803
  | 6 | `verification` | L3 | Lint + types + tests + build |
779
804
  | 6 | `hallucination-guard` | L3 | Verify imports and API calls are real |
805
+ | 6.5 | `converge` | L3 | Spec↔code gap scan for features with requirements.md — dead buttons, missing backends, contradicted decisions |
780
806
  | 7 | `journal` | L3 | Record architectural decisions |
781
807
  | 8 | `session-bridge` | L3 | Save context for future sessions |
782
808
  | any | `context-pack` | L3 | create structured handoff briefings before spawning subagents |
@@ -815,6 +841,7 @@ Mentally track tool call fingerprints. 3 identical calls → WARN. 5 identical c
815
841
  | Test-First Gate | Failing tests before Phase 4 | Write tests or get explicit skip |
816
842
  | Quality Gate | preflight + sentinel + review before Phase 7 | Fix findings, re-run |
817
843
  | Verification Gate | lint + types + tests + build green before commit | Fix, re-run |
844
+ | Convergence Gate | `convergence.clean` (or documented escalation) before Phase 7 for features with requirements.md | Execute CV tasks, re-verify, re-converge (max 2 rounds) |
818
845
 
819
846
  ## Structured Output Contract (Prompt-as-API Pattern)
820
847
 
@@ -910,6 +937,7 @@ SELF-VALIDATION (run before emitting Cook Report):
910
937
  - [ ] Plan approval gate was not bypassed — user said "go" (check conversation history)
911
938
  - [ ] No Phase 4 code was written before Phase 3 tests (TDD order preserved)
912
939
  - [ ] All Phase 5 quality gates (preflight, sentinel, review) ran — not just claimed
940
+ - [ ] Phase 6.5 converge ran for features with requirements.md — or skip announced (no spec) / escalation documented
913
941
  - [ ] No quality gate exceeded 3 remediation cycles without user escalation
914
942
  - [ ] No upstream issue was fixed by code change alone — UPSTREAM findings re-invoked the source skill
915
943
  - [ ] Cook Report contains actual commit hash, not placeholder
@@ -919,6 +947,7 @@ SELF-VALIDATION (run before emitting Cook Report):
919
947
 
920
948
  All applicable phases complete + Self-Validation passed:
921
949
  - User approved plan | All tests PASS (output shown) | preflight+sentinel+review PASS | build green
950
+ - Convergence: `convergence.clean` OR skip announced (no requirements.md) OR escalation documented — never silent
922
951
  - Cook Report emitted with commit hash | Session state saved to .rune/ via session-bridge
923
952
 
924
953
  ## Cost Profile
@@ -4,13 +4,13 @@ description: "Deploy application to target platform. Use when user explicitly sa
4
4
  disable-model-invocation: true
5
5
  metadata:
6
6
  author: runedev
7
- version: "0.7.0"
7
+ version: "0.8.0"
8
8
  layer: L2
9
9
  model: sonnet
10
10
  group: delivery
11
11
  tools: "Read, Write, Edit, Bash, Glob, Grep"
12
12
  emit: deploy.complete
13
- listen: security.passed, tests.passed, docs.updated, audit.complete, db.migrated
13
+ listen: security.passed, tests.passed, docs.updated, audit.complete, db.migrated, integration.verified, convergence.clean
14
14
  ---
15
15
 
16
16
  # deploy
@@ -58,6 +58,8 @@ Call `rune:verification` to run the full test suite and build.
58
58
  If verification fails → STOP. Do NOT proceed. Report failure with test output.
59
59
  ```
60
60
 
61
+ **Wiring evidence check (advisory)**: when deploying a FEATURE (not a hotfix — hotfix chain exempt) whose changes touch both UI and api/service/data files, look for cross-layer evidence: `integration.verified` (verification Level 3.5 passed) or `convergence.clean` (converge found zero gaps). Neither present → WARN the user explicitly — "Deploying UI+data changes with no cross-layer wiring evidence. Unit tests alone don't prove the buttons work. Proceed?" — and require confirmation. Advisory, not a block: the user can proceed, but never unknowingly.
62
+
61
63
  Call `rune:sentinel` to run security scan.
62
64
 
63
65
  ```
@@ -3,7 +3,7 @@ name: design
3
3
  description: "Design system reasoning. Maps product domain to style, palette, typography, and platform-specific patterns. Generates .rune/design-system.md as the shared design contract for all UI-generating skills."
4
4
  metadata:
5
5
  author: runedev
6
- version: "0.6.0"
6
+ version: "0.7.0"
7
7
  layer: L2
8
8
  model: sonnet
9
9
  group: creation
@@ -183,6 +183,18 @@ If the design calls for an icon, illustration, or graphic that the agent cannot
183
183
  - For illustrations, reference a placeholder string (e.g., `[ILLUSTRATION: empty-state-dashboard]`) that a human or asset-creator pass fills in later.
184
184
  - Malformed SVG is the #1 AI tell. A clean labeled placeholder is honest and professional.
185
185
 
186
+ **Placeholder Ownership (MANDATORY)**: every placeholder or intentionally inert element the design ships — `[ ICON: ... ]`, `[ILLUSTRATION: ...]`, `[ PLACEHOLDER: ... ]`, and any button/link/form rendered as visual-only (no behavior designed yet) — MUST be listed in `.rune/ui-spec.md` under a `## Unwired Elements` section:
187
+
188
+ ```markdown
189
+ ## Unwired Elements
190
+ | Element | Location | Why unwired | Owner of wiring |
191
+ |---------|----------|-------------|-----------------|
192
+ | product-grid | ProductGrid.tsx | awaiting US-2 backend | US-2 Endpoint task |
193
+ | [ ICON: dashboard ] | Sidebar.tsx | asset pass pending | asset-creator |
194
+ ```
195
+
196
+ This list is how downstream gates tell **declared debt** from **accidental dead UI**: `preflight` skips these elements, `verification` reports them as INFO (visible, non-failing), and `converge` counts them as `missing` until wired. A placeholder NOT on this list that reaches implementation = a dead element with no owner — that's the bug this section exists to prevent.
197
+
186
198
  #### Rule 3 — Color Derivation via oklch(), not Manual Shading
187
199
 
188
200
  When the design needs a darker hover, lighter surface, or tinted state, **derive from the accent via oklch()** — never eyeball a hex value.
@@ -655,6 +667,7 @@ Trading/Fintech — Data-Dense Dark — Web
655
667
  11. MUST write measurable rules into design-system.md — never vague directives like "modern typography" or "tasteful spacing" (Step 2.9 Rule 4)
656
668
  12. MUST NOT use pure `#000` / `#fff` for default text or background, MUST NOT ship lorem ipsum (Step 2.9 Rule 5)
657
669
  13. MUST list CJK-capable font FIRST in stack if product targets Chinese/Japanese/Korean (Step 2.9 Rule 6)
670
+ 14. MUST list every intentionally inert/placeholder element in `.rune/ui-spec.md` under `## Unwired Elements` (element, location, why unwired, wiring owner) — Placeholder Ownership (Step 2.9 Rule 2)
658
671
 
659
672
  ## Mesh Gates (L1/L2 only)
660
673
 
@@ -670,6 +683,7 @@ Trading/Fintech — Data-Dense Dark — Web
670
683
  | oklch-Derivation Gate | All accent variants derived via `oklch(from ...)` | Rewrite manual hex shades as relative oklch |
671
684
  | Measurable-Constraints Gate | Every rule in design-system.md is testable (concrete units, hex/oklch, ratios) | Rewrite vague directives as measurable specs (Step 2.9 Rule 4 table) |
672
685
  | No-Pure-No-Lorem Gate | No `#000`/`#fff` in semantic tokens; no lorem ipsum in output | Swap to oklch neutrals; replace lorem with real data or labelled placeholder |
686
+ | Placeholder-Ownership Gate | Every inert/placeholder element shipped is listed in `.rune/ui-spec.md` `## Unwired Elements` (element, location, why, wiring owner) | Add the missing rows before reporting done — an unlisted placeholder is a dead element with no owner |
673
687
 
674
688
  ## Returns
675
689
 
@@ -1,9 +1,9 @@
1
1
  ---
2
2
  name: plan
3
- description: "Create structured implementation plans from requirements. Produces master plan + phase files for enterprise-scale project management. Master plan = overview (<80 lines). Phase files = execution detail (<150 lines each). Each session handles 1 phase. Uses opus for deep reasoning."
3
+ description: "Create structured implementation plans from requirements. Produces master plan + phase files for enterprise-scale project management. Master plan = overview (<80 lines). Phase files = execution detail (<200 lines each). Each session handles 1 phase. Uses opus for deep reasoning."
4
4
  metadata:
5
5
  author: runedev
6
- version: "1.6.0"
6
+ version: "1.7.0"
7
7
  layer: L2
8
8
  model: opus
9
9
  group: creation
@@ -16,7 +16,7 @@ metadata:
16
16
 
17
17
  ## Purpose
18
18
 
19
- Strategic planning engine for the Rune ecosystem. Produces a **master plan + phase files** architecture — NOT a single monolithic plan. The master plan is a concise overview (<80 lines) that references separate phase files, each containing enough detail (<150 lines) that ANY model can execute with high accuracy.
19
+ Strategic planning engine for the Rune ecosystem. Produces a **master plan + phase files** architecture — NOT a single monolithic plan. The master plan is a concise overview (<80 lines) that references separate phase files, each containing enough detail (<200 lines) that ANY model can execute with high accuracy.
20
20
 
21
21
  **Design principle: Plan for the weakest coder.** Phase files are designed so that even an Amateur-level model (Haiku) can execute them with minimal errors. When the plan satisfies the Amateur's needs, every model benefits — Junior (Sonnet) executes near-perfectly, Senior (Opus) executes flawlessly.
22
22
 
@@ -34,7 +34,7 @@ For trivial tasks (1-2 phases, < 5 files): inline plan is acceptable.
34
34
  ```
35
35
  .rune/
36
36
  plan-<feature>.md ← Master plan: phases overview, goals, status tracker (<80 lines)
37
- plan-<feature>-phase1.md ← Phase 1 detail: tasks, acceptance criteria, files to touch (<150 lines)
37
+ plan-<feature>-phase1.md ← Phase 1 detail: tasks, acceptance criteria, files to touch (<200 lines)
38
38
  plan-<feature>-phase2.md ← Phase 2 detail
39
39
  ...
40
40
  ```
@@ -162,14 +162,35 @@ Phase files are SELF-CONTAINED execution instructions — designed for the weake
162
162
  </HARD-GATE>
163
163
 
164
164
  Phase decomposition rules:
165
- - **Foundation first**: types, schemas, core engine
165
+ - **Foundation first**: types, schemas, core engine. A Foundational phase holds ONLY what 2+ stories share — it BLOCKS story phases but stays minimal
166
166
  - **Dependencies before consumers**: create what's imported before the importer
167
+ - **Ordering law WITHIN each slice**: Data → Logic → Endpoints/Services → UI → Integration. UI is structurally LAST — a UI task whose slice has no upstream data/logic/endpoint task (and doesn't consume Foundational or a prior slice's contract) is an INVALID plan, not a style choice. The button and the endpoint it calls are one slice's tasks, never split across slices
167
168
  - **Test alongside**: each phase includes its own test tasks
168
169
  - **Max 5-7 tasks per phase**: if more, split the phase
169
170
  - **Vertical slices over horizontal layers**: prefer "auth end-to-end" over "all models → all APIs → all UI" (see `references/vertical-slice.md` for tracer-bullet template, AFK/HITL labels, granularity rules)
171
+ - **Story-grouped backbone from BA**: if `.rune/features/<name>/tasks.md` exists, its `## US-n` sections map to slices — refine them, do NOT flatten back into layer groups
170
172
 
171
173
  Tasks within each phase MUST be organized into waves (parallel-safe groupings). See `references/wave-planning.md`.
172
174
 
175
+ ### Step 3.7 — Boundary Artifacts (Contracts-First)
176
+ <MUST-READ path="references/boundary-artifacts.md" trigger="when the feature crosses a UI↔data boundary — templates for data-model.md, contracts/, quickstart.md"/>
177
+
178
+ **Detect the boundary**: requirements.md has a `## Key Entities` section AND any user story renders a UI surface (page/screen/form/component) — OR the task description implies user interaction with persisted data (submit, save, login, search, checkout).
179
+
180
+ **If the boundary exists, plan MUST emit — BEFORE writing phase files:**
181
+
182
+ | Artifact | Location | Content |
183
+ |----------|----------|---------|
184
+ | `data-model.md` | `.rune/features/<name>/` | Key Entities expanded: fields, types, validation rules, state transitions |
185
+ | `contracts/` | `.rune/features/<name>/contracts/` | One file per interface: endpoint/function, request/response shape, error cases — each mapped to the `US-n` it serves |
186
+ | `quickstart.md` | `.rune/features/<name>/` | Runnable end-to-end validation: prerequisites, setup commands, per-story Independent Test steps, expected outcomes |
187
+
188
+ Rules:
189
+ - Tasks are then DERIVED from contracts: every contract file → ≥1 implementation task + ≥1 test task inside the story it serves. A UI task referencing no contract (and no prior slice's contract) is orphaned — fix the plan
190
+ - A story that touches data but maps to no entity in data-model.md = spec gap → bounce to `ba` (Upstream Inconsistency)
191
+ - quickstart.md is the feature's executable end-to-end validation — write commands that actually run, not prose. Task derivation adds a "run quickstart validation" task to the final phase, so the plan itself guarantees it gets executed
192
+ - **Skip** when no boundary: pure-UI features (styling, layout), pure-backend (cron, migration), libraries. Announce the skip: "No UI↔data boundary — skipping boundary artifacts"
193
+
173
194
  ### Step 4 — Write Master Plan File
174
195
  <MUST-READ path="references/plan-templates.md" trigger="when writing the master plan file"/>
175
196
 
@@ -208,9 +229,35 @@ Performance Constraints section is optional (only when NFRs apply).
208
229
 
209
230
  When presenting alternatives (from brainstorm or Step 3), rate each **Completeness X/10**. Always recommend the higher-completeness option — with AI, the marginal cost of completeness is near-zero.
210
231
 
232
+ ### Step 5.7 — Coverage Gate (after phase files, before presenting)
233
+
234
+ **Task ID scheme**: every task in a phase file carries the ID `P<phase>-T<seq>` — phase number + sequential position within that phase (`P2-T3` = phase 2, task 3). Phase file task labels use this ID (see `references/plan-templates.md`). Coverage Summary, Traceability Matrix, and Change Stacking `depends_on` all reference tasks by this ID.
235
+
236
+ When BA requirements exist, build the **Coverage Summary** — every `FR-n` and `US-n` mapped to the task IDs that implement it:
237
+
238
+ ```markdown
239
+ ## Coverage Summary
240
+ | Key | Priority | Tasks | Covered |
241
+ |-----|----------|-------|---------|
242
+ | US-1 | P1 | P1-T2, P1-T3, P2-T1 | ✅ |
243
+ | FR-3 | — | P2-T4 | ✅ |
244
+ | US-3 | P2 | — | ❌ deferred to v2 (explicit) |
245
+ ```
246
+
247
+ <HARD-GATE>
248
+ A P1 story or its FRs with ZERO tasks = the plan is INCOMPLETE — do NOT present it for approval. Fix the plan first.
249
+ P2/P3 zero-coverage is allowed ONLY with an explicit deferral line in the master plan ("US-3 deferred to v2 — user-visible in Coverage Summary"), never silently.
250
+ </HARD-GATE>
251
+
252
+ **Sequencing note**: task IDs exist only AFTER Step 5 writes the phase files — so this step runs after Step 5, and you MUST go back and `Edit` the already-written master plan file (`.rune/plan-<feature>.md`) to insert the `## Coverage Summary` section (before `## Architecture`). Present the UPDATED master plan at Step 6. A master plan presented without its Coverage Summary is a Step 5.7 violation, not an oversight.
253
+
254
+ **Size spillover**: if the table exceeds ~15 rows, write the full table to `.rune/plan-<feature>-coverage.md` instead, and put a one-line pointer + the ❌/deferred rows only in the master plan (the 80-line cap stays intact; zero-coverage rows are never hidden in the spillover file).
255
+
256
+ Skip when no requirements.md exists (ad-hoc tasks).
257
+
211
258
  ### Step 6 — Present and Get Approval
212
259
 
213
- Present the **master plan** to user (NOT all phase files). User reviews: phase breakdown, key decisions, risks, completeness scores. Wait for explicit approval ("go", "proceed", "yes") before writing phase files.
260
+ Present the **master plan** to user (NOT all phase files). User reviews: phase breakdown, key decisions, risks, completeness scores, **coverage summary**. Wait for explicit approval ("go", "proceed", "yes") before writing phase files.
214
261
 
215
262
  ### Step 6.5 — Update Feature Map (Always)
216
263
  <MUST-READ path="references/feature-map.md" trigger="every plan invocation"/>
@@ -330,6 +377,9 @@ When producing phase files with wave-based task grouping, every task MUST declar
330
377
  12. MUST include rejection criteria — explicit "DO NOT" anti-patterns to prevent common mistakes
331
378
  13. MUST include cross-phase context — what's assumed from prior phases, what's exported for future
332
379
  14. MUST update `.rune/features.md` after every non-trivial plan — feature map is a living artifact
380
+ 15. MUST emit boundary artifacts (data-model.md, contracts/, quickstart.md) when the feature crosses a UI↔data boundary — tasks derive from contracts, not the reverse
381
+ 16. MUST order layers within each slice Data → Logic → Endpoint → UI — a UI task with no upstream chain in its slice is an invalid plan
382
+ 17. MUST NOT present a plan where a P1 story has zero task coverage — Coverage Summary is part of the master plan
333
383
 
334
384
  ## Returns
335
385
 
@@ -338,6 +388,9 @@ When producing phase files with wave-based task grouping, every task MUST declar
338
388
  | Master plan | Markdown | `.rune/plan-<feature>.md` |
339
389
  | Phase files | Markdown | `.rune/plan-<feature>-phase<N>.md` (one per phase) |
340
390
  | Feature spec | Markdown | `.rune/features/<name>/spec.md` (Feature Spec Mode only) |
391
+ | Data model | Markdown | `.rune/features/<name>/data-model.md` (Step 3.7 — UI↔data boundary only) |
392
+ | Interface contracts | Markdown (one per interface) | `.rune/features/<name>/contracts/` (Step 3.7) |
393
+ | Quickstart validation | Markdown (executable steps) | `.rune/features/<name>/quickstart.md` (Step 3.7) |
341
394
  | Roadmap | Markdown | `.rune/roadmap.md` (Roadmap Mode only) |
342
395
  | Feature map | Markdown | `.rune/features.md` (auto-maintained) |
343
396
  | Inline plan | Markdown (inline) | Emitted directly for trivial tasks |
@@ -349,7 +402,7 @@ Append to plan output when invoked standalone. Suppress when called as sub-skill
349
402
  ```yaml
350
403
  chain_metadata:
351
404
  skill: "rune:plan"
352
- version: "1.6.0"
405
+ version: "1.7.0"
353
406
  status: "[DONE | DONE_WITH_CONCERNS | NEEDS_CONTEXT | BLOCKED]"
354
407
  domain: "[area planned]"
355
408
  files_changed:
@@ -401,6 +454,11 @@ chain_metadata:
401
454
  | Missing dependency between tasks that share artifacts | HIGH | Every task declares `provides[]` and `requires[]` — cycle detection + missing dep check before dispatch |
402
455
  | New feature planned without checking existing feature map | HIGH | Step 1 reads `.rune/features.md` — catches overlaps, conflicts, and missing dependencies before planning begins |
403
456
  | Feature map never created — gaps accumulate silently | MEDIUM | Step 6.5 always runs (create or update) — feature map grows organically with each plan invocation |
457
+ | UI task planned with no endpoint/contract behind it (dead button at plan time) | CRITICAL | Step 3.7: contracts/ emitted before phase files; every UI task cites its contract; ordering law makes UI structurally last in its slice |
458
+ | P1 story silently missing from tasks (frontend-only plan) | CRITICAL | Step 5.7 Coverage Gate: P1 zero-coverage = plan not presentable; Coverage Summary visible in master plan at approval |
459
+ | Boundary artifacts skipped because "the feature is simple" | HIGH | Detection is mechanical (Key Entities + UI surface), not judgment. Skips are announced, never silent |
460
+ | quickstart.md written as prose instead of runnable commands | MEDIUM | Every step needs an **Expect** with observable outcome — cook executes this file at VERIFY |
461
+ | BA's story-grouped tasks.md flattened back into layer groups | HIGH | Step 3 rule: `## US-n` sections map to slices — refine, don't flatten |
404
462
 
405
463
  ## Self-Validation
406
464
 
@@ -412,6 +470,9 @@ SELF-VALIDATION (run before presenting plan to user):
412
470
  - [ ] Phase files have ALL Amateur-Proof sections (data flow, code contracts, failure scenarios, rejection criteria)
413
471
  - [ ] Locked decisions from BA are reflected in plan — none contradicted or ignored
414
472
  - [ ] Every BA requirement has a corresponding Req ID in at least one phase's Traceability Matrix
473
+ - [ ] Coverage Summary built (Step 5.7) — no P1 story/FR with zero tasks; P2/P3 gaps have explicit deferral lines
474
+ - [ ] Boundary artifacts emitted if UI↔data boundary detected — every contract has a consumer, every UI task cites its contract (or justifies Contract: none)
475
+ - [ ] Layer order within every slice: no UI task precedes its slice's data/logic/endpoint tasks
415
476
  - [ ] `.rune/features.md` updated with current feature (or created if first run)
416
477
  - [ ] No cross-feature conflicts detected (or flagged to user if found)
417
478
  ```
@@ -427,6 +488,8 @@ SELF-VALIDATION (run before presenting plan to user):
427
488
  - Failure scenarios table, rejection criteria (DO NOTs)
428
489
  - Cross-phase context (assumes/exports), acceptance criteria
429
490
  - Every code-producing phase has test tasks
491
+ - Boundary artifacts emitted (data-model.md + contracts/ + quickstart.md) when UI↔data boundary detected — or skip announced
492
+ - Coverage Summary in master plan — every P1 story/FR covered, P2/P3 gaps explicitly deferred
430
493
  - Master plan presented to user with "Awaiting Approval"
431
494
  - User has explicitly approved
432
495
  - Self-Validation: all checks passed
@@ -0,0 +1,127 @@
1
+ # Boundary Artifacts (Contracts-First)
2
+
3
+ > Reference for `plan` skill — Step 3.7.
4
+ > Load when the feature crosses a UI↔data boundary.
5
+
6
+ The single most common incomplete-implementation failure is a UI element wired to nothing —
7
+ the button renders, the endpoint doesn't exist. Boundary artifacts make the interface surface
8
+ a REVIEWABLE ARTIFACT at plan time, so a missing backend is visible before any code is written.
9
+
10
+ ## Detection
11
+
12
+ Emit boundary artifacts when BOTH are true:
13
+ 1. `requirements.md` has a `## Key Entities` section (feature involves data)
14
+ 2. Any user story renders a UI surface — page, screen, form, component — OR the task
15
+ implies user interaction with persisted data (submit, save, login, search, checkout)
16
+
17
+ Skip (and announce the skip) for: pure-UI features (styling, layout, static content),
18
+ pure-backend (cron jobs, migrations, CLI), libraries with no UI.
19
+
20
+ ## Artifact 1: data-model.md
21
+
22
+ Save to `.rune/features/<name>/data-model.md`. Expand each Key Entity from the spec:
23
+
24
+ ```markdown
25
+ # Data Model: [Feature Name]
26
+
27
+ ## Order
28
+ | Field | Type | Validation | Notes |
29
+ |-------|------|-----------|-------|
30
+ | id | uuid | generated | PK |
31
+ | userId | uuid | must reference existing User | FK → User |
32
+ | status | enum | draft \| submitted \| fulfilled | state machine below |
33
+ | items | OrderItem[] | min 1 item | |
34
+
35
+ **State transitions**: draft → submitted (on user submit, validates items) → fulfilled
36
+ (on admin action). No transition skips submitted. Invalid transition = 409.
37
+
38
+ **Relationships**: User 1—N Order. Order 1—N OrderItem.
39
+ ```
40
+
41
+ Rules: every entity from the spec's Key Entities appears here. Every state named in the
42
+ spec has an explicit transition trigger. Validation rules come from AC error cases.
43
+
44
+ ## Artifact 2: contracts/
45
+
46
+ Save one file per interface to `.rune/features/<name>/contracts/`. Filename: `<verb>-<resource>.md`
47
+ (e.g., `create-order.md`, `list-orders.md`).
48
+
49
+ ```markdown
50
+ # Contract: POST /api/orders
51
+
52
+ **Serves**: US-1 (AC-1.1, AC-1.2)
53
+
54
+ ## Request
55
+ ```json
56
+ { "items": [{ "productId": "uuid", "quantity": 1 }] }
57
+ ```
58
+ Validation: items non-empty; quantity ≥ 1; productId exists.
59
+
60
+ ## Response 201
61
+ ```json
62
+ { "id": "uuid", "status": "submitted", "items": [...] }
63
+ ```
64
+
65
+ ## Errors
66
+ | Case | Status | Body |
67
+ |------|--------|------|
68
+ | empty items (AC-1.2) | 422 | `{ "error": "items must not be empty" }` |
69
+ | unknown productId | 404 | `{ "error": "product not found" }` |
70
+ | unauthenticated | 401 | — |
71
+
72
+ ## Consumers
73
+ - `OrderForm` component (US-1 UI task) — submit handler calls this endpoint
74
+ ```
75
+
76
+ Rules:
77
+ - Every contract names the `US-n` it serves and the AC cases its errors cover
78
+ - Every contract names its **Consumers** — the UI component or caller that will invoke it.
79
+ A contract with no consumer, or a UI task with no contract, is an orphan → fix the plan
80
+ - Non-HTTP interfaces (IPC, function boundary, event) use the same shape: input, output, errors, consumers
81
+
82
+ ## Artifact 3: quickstart.md
83
+
84
+ Save to `.rune/features/<name>/quickstart.md`. This is EXECUTABLE, not prose — the
85
+ final phase carries a "run quickstart validation" task (see Task derivation below),
86
+ and `converge` traces each story's acceptance scenarios against these steps, so the
87
+ feature cannot be declared done without them passing.
88
+
89
+ ```markdown
90
+ # Quickstart: [Feature Name]
91
+
92
+ ## Prerequisites
93
+ - `npm install` done, DB running (`docker compose up -d db`)
94
+ - Migrations applied: `npm run db:migrate`
95
+
96
+ ## Validate US-1 (P1): submit an order
97
+ 1. `npm run dev`
98
+ 2. `curl -s -X POST localhost:3000/api/orders -H 'content-type: application/json' \
99
+ -d '{"items":[{"productId":"<seed-id>","quantity":1}]}'`
100
+ **Expect**: 201, body contains `"status":"submitted"`
101
+ 3. `curl -s localhost:3000/api/orders` — **Expect**: list contains the new order
102
+ 4. UI path: open /orders/new → add item → Submit → **Expect**: redirect to /orders,
103
+ new order visible in list
104
+
105
+ ## Validate US-1 error path (AC-1.2)
106
+ 1. Submit with empty items → **Expect**: 422, form shows "items must not be empty"
107
+ ```
108
+
109
+ Rules:
110
+ - One validation block per P1 story (P2/P3 optional), derived from the story's Independent Test
111
+ - Every step has an **Expect** with an observable outcome — status code, body content, visible UI state
112
+ - Commands must actually run in the project's environment; if the env can't run them
113
+ (no browser, no DB), say so in Prerequisites and give the closest executable check
114
+
115
+ ## Task derivation
116
+
117
+ After emitting the three artifacts, derive tasks:
118
+
119
+ | Source | Derived tasks |
120
+ |--------|---------------|
121
+ | Each entity in data-model.md | 1 schema/model task (in Foundational if shared by 2+ stories, else in its story) |
122
+ | Each contract file | 1 contract test task + 1 implementation task, inside the story it serves, BEFORE that story's UI task |
123
+ | Each contract's Consumers line | the UI task's Logic field references the contract file |
124
+ | quickstart.md | 1 "run quickstart validation" task in the final phase |
125
+
126
+ Cross-check before Coverage Gate (Step 5.7): every contract implemented, every consumer wired,
127
+ every quickstart block runnable. An unimplemented contract = the dead button, caught at plan time.
@@ -29,6 +29,16 @@ Save to `.rune/plan-<feature>.md`. Max 80 lines.
29
29
  - Discretion (agent): [list — agent chose X because Y]
30
30
  - Deferred: [list — explicitly excluded from this feature]
31
31
 
32
+ ## Coverage Summary
33
+ <!-- Step 5.7 — only when BA requirements exist. P1 zero-coverage = plan not presentable.
34
+ Inserted AFTER phase files exist (task IDs come from them). If >15 rows, move the full
35
+ table to .rune/plan-<feature>-coverage.md and keep only a pointer + ❌/deferred rows here. -->
36
+ | Key | Priority | Tasks | Covered |
37
+ |-----|----------|-------|---------|
38
+ | US-1 | P1 | P1-T2, P1-T3 | ✅ |
39
+ | FR-3 | — | P2-T4 | ✅ |
40
+ | US-3 | P2 | — | ❌ deferred to v2 (explicit) |
41
+
32
42
  ## Architecture
33
43
  <brief system diagram or component list — NOT implementation detail>
34
44
 
@@ -89,23 +99,32 @@ function validateInput(raw: unknown): TradeEntry[]; // throws ValidationError
89
99
 
90
100
  Each task MUST include: **File** (exact path), **Test** (test file or N/A), **Verify** (shell command), **Commit** (semantic message). Granularity: 2-5 min per task. If >10min, decompose.
91
101
 
92
- - [ ] Task 1 Create calculateProfit function
93
- - Req: REQ-001 (P&L calculation)
102
+ **Task IDs**: label every task `P<phase>-T<seq>` (phase number + position within phase). Coverage Summary, Traceability Matrix, and `depends_on` reference these IDs.
103
+
104
+ **Req IDs**: when BA produced `FR-n`/`US-n` IDs, use THOSE IDs in the Req field and Traceability Matrix — do NOT renumber as REQ-n. The `REQ-n` format is only for ad-hoc plans with no BA spec.
105
+
106
+ When BA requirements exist, each task also carries **Story** (`US-n` it serves) — and UI tasks carry **Contract** (the `contracts/` file whose endpoint the UI invokes; see `references/boundary-artifacts.md`). A UI task with `Contract: none` MUST justify why (static UI, consumes prior slice's contract).
107
+
108
+ - [ ] P2-T1 — Create calculateProfit function
109
+ - Req: FR-1 (P&L calculation)
110
+ - Story: US-1
94
111
  - File: `src/foo/bar.ts` (new)
95
112
  - Test: `tests/foo/bar.test.ts` (new)
96
113
  - Verify: `npm test -- --grep "calculateProfit"`
97
114
  - Commit: `feat(trading): add calculateProfit with fee calculation`
98
115
  - Logic: sum entries by side, apply fees (0.1% per trade), return net P&L
99
116
  - Edge: empty array → return { netPnL: 0, totalFees: 0, winRate: 0 }
100
- - [ ] Task 2 — Add input validation
101
- - Req: REQ-002 (input validation)
117
+ - [ ] P2-T2 — Add input validation
118
+ - Req: FR-2 (input validation)
119
+ - Story: US-1
102
120
  - File: `src/foo/baz.ts` (modify)
103
121
  - Test: `tests/foo/baz.test.ts` (new)
104
122
  - Verify: `npm test -- --grep "validateInput"`
105
123
  - Commit: `feat(trading): add input validation for trade entries`
106
124
  - Logic: check side is 'long'|'short', prices > 0, quantity > 0
107
- - [ ] Task 3 — Write integration tests
108
- - Req: REQ-001, REQ-002 (integration coverage)
125
+ - [ ] P2-T3 — Write integration tests
126
+ - Req: FR-1, FR-2 (integration coverage)
127
+ - Story: US-1
109
128
  - File: `tests/foo/bar.test.ts` (modify)
110
129
  - Test: N/A — this IS the test task
111
130
  - Verify: `npm test -- --grep "trading" && npx tsc --noEmit`
@@ -157,10 +176,10 @@ Each task MUST include: **File** (exact path), **Test** (test file or N/A), **Ve
157
176
  ## Traceability Matrix
158
177
  | Req ID | Requirement | Task(s) | Test(s) | Status |
159
178
  |--------|-------------|---------|---------|--------|
160
- | REQ-001 | P&L calculation with fees | Task 1 | `tests/foo/bar.test.ts` | ⬚ |
161
- | REQ-002 | Input validation | Task 2 | `tests/foo/baz.test.ts` | ⬚ |
179
+ | FR-1 | P&L calculation with fees | P2-T1 | `tests/foo/bar.test.ts` | ⬚ |
180
+ | FR-2 | Input validation | P2-T2 | `tests/foo/baz.test.ts` | ⬚ |
162
181
 
163
- Every requirement from BA's Requirements Document MUST appear in this matrix. Missing requirement = incomplete phase. `completion-gate` checks this matrix during verification.
182
+ Every requirement from BA's Requirements Document MUST appear in this matrix, using BA's own IDs (`FR-n`/`US-n` — REQ-n only when no BA spec exists). Missing requirement = incomplete phase. `completion-gate` checks this matrix during verification.
164
183
 
165
184
  ## Files Touched
166
185
  - `src/foo/bar.ts` — new
@@ -10,6 +10,7 @@
10
10
  2. **Demoable on its own** — when the slice is merged, you can demo it (or run a single command to verify). If demoing requires "and now switch to the other PR", the slices were drawn wrong.
11
11
  3. **Narrow but complete** — one user story, one happy path, minimal error handling. Edge cases are *separate slices*, not bigger versions of the same slice.
12
12
  4. **Independently grabbable** — any developer or agent should be able to pick up Slice N without reading Slice N+1. Dependencies declared explicitly, not implicit.
13
+ 5. **Layer order WITHIN the slice: Data → Logic → Endpoint/Service → UI → Integration.** UI is structurally last. The button and the endpoint it calls are ONE slice's tasks — a slice whose UI task has no upstream endpoint task (and consumes no prior slice's contract) ships a dead button. If the slice has a contract file (`references/boundary-artifacts.md`), the contract test task precedes the implementation task.
13
14
 
14
15
  ## Slice types
15
16
 
@@ -25,13 +26,14 @@
25
26
  ```markdown
26
27
  ### Slice: [verb-led title]
27
28
  - **Type**: AFK | HITL
28
- - **Story**: As a [persona], I want to [action] so that [benefit]
29
- - **Path through layers**:
29
+ - **Story**: US-n — As a [persona], I want to [action] so that [benefit]
30
+ - **Path through layers** (this is also the BUILD ORDER — top to bottom):
30
31
  - Schema: [migration / type addition]
31
- - API: [endpoint or function signature]
32
- - UI: [component or surface]
33
- - Test: [verification approach]
34
- - **Demoable**: [exact command or click-path that shows it works]
32
+ - Logic: [business rule / validation]
33
+ - API: [endpoint or function signature — cite `contracts/<file>.md` if one exists]
34
+ - UI: [component or surface — names the API line above as its call target]
35
+ - Test: [verification approach must cross UI→API, not mock the whole chain]
36
+ - **Demoable**: [exact command or click-path that shows it works — reuse the story's Independent Test]
35
37
  - **Blocked by**: [slice IDs] | None — can start immediately
36
38
  - **Out of scope** (explicit): [what this slice does NOT cover]
37
39
  ```
@@ -3,7 +3,7 @@ name: preflight
3
3
  description: "Pre-commit quality gate that catches 'almost right' code. Use when about to commit — auto-fires before commit to validate logic correctness, error handling, regressions, and completeness. Goes beyond linting."
4
4
  metadata:
5
5
  author: runedev
6
- version: "1.1.0"
6
+ version: "1.2.0"
7
7
  layer: L2
8
8
  model: sonnet
9
9
  group: quality
@@ -150,6 +150,7 @@ Verify that new code ships complete:
150
150
  - New feature → has at least one test file
151
151
  - New configuration option → has documentation (inline comment or docs file)
152
152
  - New database query → has corresponding migration file if schema changed
153
+ - **Cross-layer pairing**: new interactive component (button/form/action) → its handler chain reaches a REAL endpoint/service that exists in the codebase — OR the plan explicitly scopes it UI-only with a mock (stated, not assumed). Unexcused missing pair = **BLOCK**, not WARN: a dead interactive element is incomplete work presented as complete. (Mirror check: new endpoint this diff → ≥1 consumer or a NAMED future task consuming it)
153
154
 
154
155
  **Framework-specific completeness (apply only if detected):**
155
156
  - React component with async data → must have `loading` state AND `error` state
@@ -238,6 +239,7 @@ When UI/Frontend hook is triggered, run these checks on all `.tsx`/`.jsx`/`.svel
238
239
  | **Scale Minimum — hero display** | `<h1>` with `text-3xl` or smaller (30px) when the heading is in a hero/landing section | WARN: "Hero heading below 48px at {file}:{line} — insufficient visual hierarchy" |
239
240
  | **Hand-rolled SVG for standard icons** | Inline `<svg viewBox=` in JSX when the surrounding comment/class names indicate standard iconography (dashboard, menu, close, chevron, arrow, search, home, user, settings, bell, trash) | WARN: "Hand-rolled SVG at {file}:{line} — use @phosphor-icons/react or huge-icons, or ship boxed placeholder" |
240
241
  | **Manual hex accent shading** | CSS/Tailwind config defining 2+ sibling `--accent-hover` / `--accent-pressed` / `--accent-active` with hex literals (no `oklch(from ...)` or design-token chain) | WARN: "Manual hex shade at {file}:{line} — derive via oklch(from var(--accent) calc(l - 0.08) c h)" |
242
+ | **Dead interactive element** | `<button>`/`<form>`/action element with no bound handler (any framework syntax: `onClick=`, `on:click=`, `@click`, `v-on:`), `onClick={() => {}}`, `href="#"` on an action link (not navigation/scroll anchors), or `preventDefault()`-only submit — in files of THIS diff (skip elements listed in `.rune/ui-spec.md` `## Unwired Elements`; prop-origin handlers like `onClick={props.onSave}` count as bound) | BLOCK: "Dead interactive at {file}:{line} — element renders but does nothing" |
241
243
  | **Missing states** | Components fetching data without loading/error/empty states | WARN: "Async component at {file} missing [loading|error|empty] state" |
242
244
  | **Icon accessibility** | Decorative icons without `aria-hidden="true"`, functional icons without `aria-label` | WARN: "Icon at {file}:{line} missing aria attribute" |
243
245
  | **Inline styles** | `style={{` or `style=` attribute usage instead of classes/tokens | WARN: "Inline style at {file}:{line} — use CSS class or Tailwind" |
@@ -336,8 +338,8 @@ Invoke `rune:sentinel` on the changed files. Attach sentinel's output verbatim u
336
338
 
337
339
  ### Step 6 — Generate Verdict
338
340
  Aggregate all findings:
339
- - Any BLOCK from sentinel OR a logic issue that would cause data corruption or security bypass → overall **BLOCK**
340
- - Any missing error handling, regression risk with no tests, or incomplete feature → **WARN**
341
+ - Any BLOCK from sentinel OR a logic issue that would cause data corruption or security bypass OR a dead interactive element (Step 4 cross-layer pairing / Step 4.5 dead-interactive check) OR a BLOCK from any domain hook → overall **BLOCK**
342
+ - Any missing error handling, regression risk with no tests, or incomplete feature (other than the BLOCK cases above) → **WARN**
341
343
  - Only style or best-practice suggestions → **PASS**
342
344
 
343
345
  Report PASS, WARN, or BLOCK. For WARN, list each item the developer must acknowledge. For BLOCK, list each item that must be fixed before proceeding.
@@ -410,6 +412,8 @@ WARN — 3 issues found (0 blocking, 3 must-acknowledge). Resolve before commit
410
412
  | Domain hooks not triggered when pack is installed | HIGH | Step 4.5 auto-detects file patterns — if pack is installed but hooks don't fire, check file pattern matching |
411
413
  | Domain hooks overriding generic checks | HIGH | HARD-GATE: domain hooks are ADDITIVE — they never replace Steps 1-4 |
412
414
  | Pack Hard-Stop Thresholds ignored in preflight | MEDIUM | Step 4.5 Pack Integration must read installed pack thresholds — test with each new pack |
415
+ | Dead interactive element downgraded to WARN ("just a loading-state issue") | CRITICAL | Step 4 cross-layer pairing + Step 4.5 dead-interactive check are BLOCK — a button wired to nothing is incomplete work, not a style nit |
416
+ | Flagging design's declared placeholders as dead interactives | MEDIUM | Elements listed in `.rune/ui-spec.md` `## Unwired Elements` are design debt tracked by converge — skip, don't BLOCK |
413
417
 
414
418
  ## Done When
415
419
 
@@ -417,6 +421,8 @@ WARN — 3 issues found (0 blocking, 3 must-acknowledge). Resolve before commit
417
421
  - Error handling verified on all async functions and HTTP calls
418
422
  - Regression impact assessed — dependent files identified via scout
419
423
  - Completeness checklist passed (validation schema, loading/error states, test file)
424
+ - Cross-layer pairing checked (Step 4): every new interactive component's handler chain reaches a real endpoint/service or has an explicit UI-only scope
425
+ - Dead-interactive scan done (Step 4.5 UI hook) on all UI files in the diff
420
426
  - Sentinel invoked and its output attached in Security section
421
427
  - Structured report emitted with PASS / WARN / BLOCK verdict and file:line for every finding
422
428
 
@@ -177,6 +177,7 @@ For users who know exactly what they want:
177
177
  | Fix bug / debug only (no fix) | `rune:debug` → `rune:fix` | L2 chain |
178
178
  | Marketing assets only | `rune:marketing` | L2 |
179
179
  | Gather requirements / BA / elicit needs | `rune:ba` | L2 — requires opus |
180
+ | "Did it fully implement?" / "does code match spec?" / check completeness | `rune:converge` | L3 — needs requirements.md |
180
181
  | Generate / update docs | `rune:docs` | L2 |
181
182
  | Build MCP server | `rune:mcp-builder` | L2 |
182
183
  | Red-team / challenge a plan / stress-test | `rune:adversary` | L2 — requires opus |
@@ -193,6 +194,7 @@ These are rarely invoked directly — they're called by Tier 1/2 skills:
193
194
  | `rune:verification` | cook, fix | Run lint/test/build |
194
195
  | `rune:hallucination-guard` | cook, fix | Verify imports |
195
196
  | `rune:completion-gate` | cook | Validate claims |
197
+ | `rune:converge` | cook | Spec↔code gap scan (Phase 6.5) |
196
198
  | `rune:sentinel-env` | cook, scaffold, onboard | Environment pre-flight |
197
199
  | `rune:research` / `rune:docs-seeker` | any | Look up docs |
198
200
  | `rune:session-bridge` | cook, team | Save context (in-session state handoff) |