@deftai/directive-content 0.106.0 → 0.108.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.
- package/Taskfile.yml +14 -1
- package/UPGRADING.md +24 -5
- package/commands.md +29 -4
- package/contracts/design-critique.md +369 -14
- package/contracts/issue-eval.md +77 -0
- package/contracts/path-write-fence.md +126 -1
- package/contracts/runtime-authority.md +2 -0
- package/contracts/scm-readiness.md +2 -2
- package/docs/delivery-attempt.md +2 -1
- package/docs/freshness-contract.md +6 -1
- package/docs/getting-started.md +10 -11
- package/docs/hook-runtime-unavailable.md +54 -0
- package/docs/orphan-active-verdict-basis.md +166 -0
- package/docs/scope-provenance.md +1 -1
- package/package.json +1 -1
- package/packs/skills/skills-pack-0.1.json +24 -10
- package/scm/github.md +65 -2
- package/skills/deft-directive-build/SKILL.md +2 -2
- package/skills/deft-directive-cost/SKILL.md +7 -11
- package/skills/deft-directive-design-critique/SKILL.md +22 -6
- package/skills/deft-directive-design-critique/references/motion-shape.md +19 -0
- package/skills/deft-directive-feedback/SKILL.md +11 -2
- package/skills/deft-directive-interview/SKILL.md +10 -10
- package/skills/deft-directive-issue-eval/SKILL.md +48 -0
- package/skills/deft-directive-release/SKILL.md +10 -6
- package/skills/deft-directive-review-cycle/SKILL.md +33 -0
- package/skills/deft-directive-setup/SKILL.md +53 -22
- package/skills/deft-directive-swarm/references/core-ops.md +4 -0
- package/skills/deft-directive-swarm/references/core-phase-1-2.md +1 -1
- package/skills/deft-directive-swarm/references/core-phase-3.md +3 -1
- package/skills/deft-directive-swarm/references/core-phase-4.md +11 -8
- package/skills/deft-directive-swarm/references/host-cursor.md +1 -0
- package/skills/deft-directive-swarm/references/host-grok-build.md +1 -0
- package/skills/deft-directive-triage/SKILL.md +3 -2
- package/tasks/engine.yml +4 -0
- package/tasks/feedback.yml +1 -1
- package/tasks/occupancy.yml +34 -1
- package/tasks/prd.yml +4 -5
- package/tasks/scm.yml +14 -2
- package/tasks/session.yml +13 -2
- package/tasks/toolchain.yml +2 -2
- package/tasks/triage-evaluate.yml +22 -0
- package/tasks/verify.yml +21 -1
- package/templates/agent-prompt-preamble.md +28 -4
- package/templates/agents-entry.md +10 -5
- package/templates/design-critique-brief.md +19 -5
|
@@ -127,6 +127,8 @@ When guiding an operator through migration on the pinned release, mention the mi
|
|
|
127
127
|
- ! If `$DEFT_USER_PATH` is set, it takes precedence on any platform
|
|
128
128
|
- ! Create parent directories as needed when writing USER.md
|
|
129
129
|
- ~ `$DEFT_PROJECT_PATH` overrides the default project config path (`./xbrief/PROJECT-DEFINITION.xbrief.json`) if set
|
|
130
|
+
- ! Resolve `<policy-project-root>` to the user's working directory at skill entry. When `$DEFT_PROJECT_PATH` is set, resolve it relative to that root and preserve the environment variable for every Phase 2 command; the public policy writer, inspector, lock, and conformance gate honor the configured file even when it is outside the canonical `xbrief/` path.
|
|
131
|
+
- ! Pass `--project-root <policy-project-root>` to every Phase 2 policy inspector, writer, and conformance command. Do not unset or rewrite `$DEFT_PROJECT_PATH`, and do not let those commands fall back to a different working directory.
|
|
130
132
|
|
|
131
133
|
## Agent Behavior
|
|
132
134
|
|
|
@@ -418,6 +420,15 @@ for project-scoped settings (strategy, coverage).
|
|
|
418
420
|
- ~ Skip if `./xbrief/PROJECT-DEFINITION.xbrief.json` exists (or `$DEFT_PROJECT_PATH` if set) and user doesn't want to replace
|
|
419
421
|
- ⊗ Count `./deft/PROJECT-DEFINITION.xbrief.json` or `./deft/core/project.md` as the user's project config — those are framework-internal
|
|
420
422
|
|
|
423
|
+
### Re-entry shadow guard (#3609)
|
|
424
|
+
|
|
425
|
+
! Before any Phase 2 confirmation or file mutation when PROJECT-DEFINITION already exists, run `deft policy:show --field=plan.policy.allowDirectCommitsToMaster --project-root <policy-project-root>` and inspect **stderr as well as the exit code**. The inspector intentionally exits 0 when it can still read the namespaced value, so a warning that bare `plan.policy` coexists with `plan["x-directive/policy"]` is a hard stop even when the command succeeds.
|
|
426
|
+
|
|
427
|
+
! On that warning, do not regenerate, overwrite, or run a policy writer. Inventory the keys in both blocks; fold every bare-only key into `plan["x-directive/policy"]`; resolve every collision explicitly; delete bare `plan.policy`; then rerun the inspector. Preserve all unrelated PROJECT-DEFINITION content. Resume only when exactly one policy block remains.
|
|
428
|
+
|
|
429
|
+
⊗ Treat matching `allowDirectCommitsToMaster` values as safe while other keys may still be stranded in the shadowed block
|
|
430
|
+
⊗ Copy arbitrary policy values into a diagnostic or silently choose one side of a collision
|
|
431
|
+
|
|
421
432
|
### Inference
|
|
422
433
|
|
|
423
434
|
- ! Before asking, infer from codebase — look for `package.json`, `go.mod`, `requirements.txt`, `Cargo.toml`, `pyproject.toml`, `*.csproj`
|
|
@@ -491,21 +502,21 @@ apply here too. Do not combine questions. See `skills/deft-directive-interview/S
|
|
|
491
502
|
! **Capability-cost disclosure (#746):** When the user picks option 2 (trunk-based), the agent MUST present the capability-cost disclosure verbatim BEFORE writing the typed flag, then re-prompt for explicit confirmation:
|
|
492
503
|
|
|
493
504
|
> "Capability-cost disclosure -- enabling direct commits to the default branch turns OFF the deft branch-protection policy. The pre-commit + pre-push hooks will no longer block default-branch commits, `task verify:branch` will pass on the default branch, and the skill-level guards in deft-directive-{swarm,review-cycle,pre-pr,release} will not halt for default-branch work. The change is reversible (`task policy:enforce-branches`) and is recorded to meta/policy-changes.log for auditability. The CI sanity check (head_ref != base_ref) remains independent and will continue to flag master->master PRs. Are you sure?"
|
|
494
|
-
> 1. Yes, opt out --
|
|
495
|
-
> 2. No, keep branch-protection enforced --
|
|
505
|
+
> 1. Yes, opt out -- persist `allowDirectCommitsToMaster=true` through the policy writer
|
|
506
|
+
> 2. No, keep branch-protection enforced -- persist `allowDirectCommitsToMaster=false` through the policy writer
|
|
496
507
|
> 3. Discuss
|
|
497
508
|
> 4. Back
|
|
498
509
|
|
|
499
510
|
! Default to option 2 (enforce). Explicit affirmative on option 1 is required to opt out -- a broad `proceed` does NOT satisfy this gate. The same affirmative-only rule applies as in `/deft:change` (`yes`, `confirmed`, `approve`).
|
|
500
511
|
|
|
501
|
-
!
|
|
512
|
+
! Record the answer as the logical field `plan.policy.allowDirectCommitsToMaster`, but do not hand-write either policy block. The common Output Path gate below invokes the only writer and stores the boolean under `plan["x-directive/policy"].allowDirectCommitsToMaster`. Default `false` (enforce branches) when the user picks option 2 OR omits the question entirely. Agents MUST NOT write bare `plan.policy` or the legacy free-form `Allow direct commits to master:` narrative key.
|
|
502
513
|
|
|
503
|
-
! **Re-running the interview detects the existing flag (#746 part G2):**
|
|
514
|
+
! **Re-running the interview detects the existing flag (#746 part G2):** After the Re-entry shadow guard passes, surface the resolved current value (e.g. "Current setting: `allowDirectCommitsToMaster=false` (branch-protection ON)") and ask whether to keep it or change it before re-prompting. A keep choice still runs the selected writer so legacy-only storage is migrated; an already-namespaced match is a no-op with no audit append. On Track 2 or 3, preserve an existing resolved boolean by default without asking a new branching question. Never replace an existing `true` with the greenfield `false` default unless the operator explicitly chooses the Track 1 change flow.
|
|
504
515
|
|
|
505
|
-
! **
|
|
506
|
-
-
|
|
507
|
-
-
|
|
508
|
-
-
|
|
516
|
+
! **Consumer command alternatives (#746 part G2):** Once the project is set up, use the public CLI directly:
|
|
517
|
+
- `deft policy:show --field=plan.policy.allowDirectCommitsToMaster --project-root <policy-project-root>` -- display the current resolved policy and source
|
|
518
|
+
- `deft policy:enforce-branches --actor agent:deft-directive-setup --project-root <policy-project-root>` -- set `allowDirectCommitsToMaster=false`
|
|
519
|
+
- `deft policy:allow-direct-commits --confirm --actor agent:deft-directive-setup --project-root <policy-project-root>` -- set `allowDirectCommitsToMaster=true`
|
|
509
520
|
|
|
510
521
|
Each transition is recorded to `meta/policy-changes.log` for auditability.
|
|
511
522
|
|
|
@@ -515,14 +526,30 @@ apply here too. Do not combine questions. See `skills/deft-directive-interview/S
|
|
|
515
526
|
- Step 3: Ask languages (show detected, confirm or adjust; if none detected, infer from type and ask)
|
|
516
527
|
- Step 4: Ask strategy (default to USER.md Defaults; ask if this project needs different — show Available Strategies numbered list with descriptions and recommended marker)
|
|
517
528
|
- Default coverage to USER.md Defaults without asking
|
|
529
|
+
- ! Do not ask a branching question. For greenfield or absent policy, the common Output Path gate persists `allowDirectCommitsToMaster=false`. On re-entry it preserves the resolved existing boolean, including `true`; change it only through the Track 1 disclosure gate.
|
|
518
530
|
|
|
519
531
|
**Track 3 (non-technical) — 1 step:**
|
|
520
532
|
- Step 1: Present summary of inferences: "Based on your project: {name} ({type}), built with {stack}. Look right?"
|
|
521
533
|
- ⊗ Ask about strategy or coverage — use Phase 1 defaults
|
|
534
|
+
- ! Do not ask a branching question. For greenfield or absent policy, the common Output Path gate persists `allowDirectCommitsToMaster=false`. On re-entry it preserves the resolved existing boolean, including `true`; change it only through the Track 1 disclosure gate.
|
|
522
535
|
|
|
523
536
|
### Output Path
|
|
524
537
|
|
|
525
|
-
`./xbrief/PROJECT-DEFINITION.xbrief.json` (or `$DEFT_PROJECT_PATH` if set). Create
|
|
538
|
+
`./xbrief/PROJECT-DEFINITION.xbrief.json` (or the resolved `$DEFT_PROJECT_PATH` if set). Create `<policy-project-root>/xbrief/` and its lifecycle subfolders (`proposed/`, `pending/`, `active/`, `completed/`, `cancelled/`) if they don't exist. A configured PROJECT-DEFINITION may live elsewhere; the lifecycle root remains under `<policy-project-root>`.
|
|
539
|
+
|
|
540
|
+
### Branch-policy persistence gate (#3609)
|
|
541
|
+
|
|
542
|
+
! This gate applies to **every track**, including default/greenfield and keep/re-entry paths. For greenfield setup, first write the confirmed PROJECT-DEFINITION base without any hand-authored policy block. On re-entry, merge base changes while preserving the existing policy block byte-for-byte: keep a legacy-only bare `plan.policy` intact until the shared writer migrates the whole block, and keep a namespaced block intact until that writer updates it. Never delete or reconstruct a legacy-only block before the writer because it may contain unrelated keys such as `wipCap`. Then invoke exactly one public writer:
|
|
543
|
+
|
|
544
|
+
- Branch-based/greenfield-default/keep-false: `deft policy:enforce-branches --actor agent:deft-directive-setup --project-root <policy-project-root>`
|
|
545
|
+
- Explicitly confirmed trunk-based/keep-true/Track 2 or 3 existing-true: `deft policy:allow-direct-commits --confirm --actor agent:deft-directive-setup --project-root <policy-project-root>`
|
|
546
|
+
|
|
547
|
+
! A nonzero writer exit halts Phase 2 immediately. Do not print a completion claim and do not retry by hand-editing JSON. Resolve the reported configuration problem, rerun the Re-entry shadow guard, and invoke the writer again.
|
|
548
|
+
|
|
549
|
+
! Before Phase 2 can complete, re-read PROJECT-DEFINITION and verify all three postconditions: `plan["x-directive/policy"].allowDirectCommitsToMaster` is the selected boolean; bare `plan.policy` is absent; and `deft verify:vbrief-conformance --project-root <policy-project-root>` exits 0. Also run `deft policy:show --field=plan.policy.allowDirectCommitsToMaster --project-root <policy-project-root>` and confirm its resolved value matches the selection. Any mismatch is a hard stop.
|
|
550
|
+
|
|
551
|
+
⊗ Finish Phase 2 after writing only the narrative template
|
|
552
|
+
⊗ Add a setup-specific policy writer or weaken conformance to permit bare `plan.policy`
|
|
526
553
|
|
|
527
554
|
### GitHub PR Template Scaffolding (#531)
|
|
528
555
|
|
|
@@ -579,7 +606,7 @@ omit = [
|
|
|
579
606
|
"Strategy": "Use {strategy name} for this project",
|
|
580
607
|
"Quality": "Run task check before every commit. Achieve >= {coverage}% coverage overall + per-module. Store secrets in secrets/ dir.",
|
|
581
608
|
"ProjectRules": "{Any rules the user specified, or 'No project-specific rules defined.'}",
|
|
582
|
-
"Branching": "{If trunk-based: '
|
|
609
|
+
"Branching": "{If confirmed trunk-based: 'Trunk-based workflow', otherwise 'Branch-based workflow (default)'}",
|
|
583
610
|
"DeftVersion": "0.20.0"
|
|
584
611
|
},
|
|
585
612
|
"items": []
|
|
@@ -614,7 +641,7 @@ omit = [
|
|
|
614
641
|
! **Path Resolution Anchor**: Same rule as Phase 2 -- resolve ALL paths relative to the user's pwd at skill entry, never relative to the skill file, AGENTS.md, or any framework directory.
|
|
615
642
|
|
|
616
643
|
- ~ Skip if user already has scope xBRIEFs in `./xbrief/` they're happy with
|
|
617
|
-
- ! Check `./xbrief/
|
|
644
|
+
- ! Check `./xbrief/PROJECT-DEFINITION.xbrief.json` and `./xbrief/proposed/` for existing greenfield authority; treat `./xbrief/specification.xbrief.json` as a full-spec compatibility artifact only
|
|
618
645
|
- ⊗ Count ANY file inside `./deft/` as the project's spec — those are framework-internal
|
|
619
646
|
(e.g. `deft/PROJECT.md`, `deft/specs/`, `deft/templates/`, `deft/core/project.md`
|
|
620
647
|
are all part of the framework, NOT the user's project)
|
|
@@ -682,8 +709,10 @@ project complexity per [strategies/interview.md](../../strategies/interview.md#s
|
|
|
682
709
|
- ⊗ Combine the sizing proposal with the first interview question
|
|
683
710
|
- ⊗ Proceed to interview questions before the user has confirmed the path
|
|
684
711
|
|
|
685
|
-
**Light** (small/medium): Interview →
|
|
686
|
-
**Full** (large/complex): Interview → rich narratives
|
|
712
|
+
**Light** (small/medium): Interview → slim narratives (Overview + Architecture) in `PROJECT-DEFINITION.xbrief.json` → scope xBRIEFs in `xbrief/proposed/`.
|
|
713
|
+
**Full** (large/complex): Interview → rich PROJECT-DEFINITION narratives for user approval → scope xBRIEFs with traceability.
|
|
714
|
+
|
|
715
|
+
! Neither greenfield path creates `xbrief/specification.xbrief.json`; that file remains a full-spec compatibility artifact.
|
|
687
716
|
|
|
688
717
|
### Interview Process (interview strategy)
|
|
689
718
|
|
|
@@ -715,7 +744,7 @@ Per [strategies/interview.md](../../strategies/interview.md#interview-rules-shar
|
|
|
715
744
|
|
|
716
745
|
### Output — Light Path
|
|
717
746
|
|
|
718
|
-
1. !
|
|
747
|
+
1. ! Merge the confirmed slim narratives into `./xbrief/PROJECT-DEFINITION.xbrief.json`:
|
|
719
748
|
- `Overview`: Brief project summary
|
|
720
749
|
- `Architecture`: System design description
|
|
721
750
|
2. ! Create scope xBRIEFs in `./xbrief/proposed/` for each identified work item
|
|
@@ -733,8 +762,8 @@ Per [strategies/interview.md](../../strategies/interview.md#interview-rules-shar
|
|
|
733
762
|
}
|
|
734
763
|
]
|
|
735
764
|
```
|
|
736
|
-
3. ! Summarize decisions
|
|
737
|
-
4. !
|
|
765
|
+
3. ! Summarize decisions and ask the user to approve the PROJECT-DEFINITION narratives and proposed scope set
|
|
766
|
+
4. ! Record approval in the setup session; do not manufacture or require `specification.xbrief.json`
|
|
738
767
|
- ⊗ Create a separate PRD.md on the Light path
|
|
739
768
|
- ⊗ Generate an authoritative PRD.md — if needed, users run `task prd:render`
|
|
740
769
|
|
|
@@ -747,7 +776,7 @@ Per [strategies/interview.md](../../strategies/interview.md#interview-rules-shar
|
|
|
747
776
|
|
|
748
777
|
### Output — Full Path
|
|
749
778
|
|
|
750
|
-
1. !
|
|
779
|
+
1. ! Merge these rich narratives into `./xbrief/PROJECT-DEFINITION.xbrief.json` for review:
|
|
751
780
|
- `ProblemStatement`: What problem this project solves
|
|
752
781
|
- `Goals`: High-level project goals
|
|
753
782
|
- `UserStories`: User stories in standard format
|
|
@@ -755,8 +784,8 @@ Per [strategies/interview.md](../../strategies/interview.md#interview-rules-shar
|
|
|
755
784
|
- `SuccessMetrics`: Measurable success criteria
|
|
756
785
|
- `Architecture`: System design and technical architecture
|
|
757
786
|
- `Overview`: Brief project summary
|
|
758
|
-
2. ! **Human approval gate**: Present the
|
|
759
|
-
3. !
|
|
787
|
+
2. ! **Human approval gate**: Present the PROJECT-DEFINITION narratives and proposed scope plan to the user for review. The user may request changes before approving.
|
|
788
|
+
3. ! Record approval in the setup session and proceed to downstream generation; do not manufacture or require `specification.xbrief.json`
|
|
760
789
|
4. ! Create scope xBRIEFs in `./xbrief/proposed/` with traceability to requirement IDs from the narratives
|
|
761
790
|
- ! Scope xBRIEFs MUST trace tasks back to requirement IDs (FR-1, NFR-1) from the `Requirements` narrative
|
|
762
791
|
- ⊗ Generate an authoritative PRD.md — if needed, users run `task prd:render`
|
|
@@ -813,8 +842,9 @@ Per [strategies/interview.md](../../strategies/interview.md#interview-rules-shar
|
|
|
813
842
|
|
|
814
843
|
### Handoff to deft-directive-build
|
|
815
844
|
|
|
816
|
-
- ! Emit a structured-tool question asking whether to continue
|
|
817
|
-
-
|
|
845
|
+
- ! Emit a structured-tool question asking whether to continue toward the build phase only when the host preserves numeric labels; otherwise emit the deterministic numbered menu in chat. Options: `1. Yes (run cost phase)`, `2. Not now (exit setup)`, `3. Discuss`, `4. Back (revisit previous phase)`. The numeric labels MUST remain visible and be returned as numeric selections or exact displayed option text.
|
|
846
|
+
- ! If the user picks Yes, invoke `skills/deft-directive-cost/SKILL.md`; only a recorded Build or Skip decision from that skill may hand off to `skills/deft-directive-build/SKILL.md`
|
|
847
|
+
- ⊗ Invoke the build skill directly from setup and bypass the required cost decision
|
|
818
848
|
- ⊗ Leave user with a dead end -- always offer the next step via the structured-tool phase-transition question
|
|
819
849
|
- ⊗ Ask the handoff-to-build question as unnumbered conversational prose or through a structured UI that hides the canonical numeric labels -- it is a deterministic menu and MUST preserve visible numbers (#478, #1563).
|
|
820
850
|
|
|
@@ -832,7 +862,8 @@ Per [strategies/interview.md](../../strategies/interview.md#interview-rules-shar
|
|
|
832
862
|
4. ! If the user says `no`: re-display the values and ask which ones to correct, then re-confirm before writing
|
|
833
863
|
5. ! If any value appears to be auto-generated filler (e.g. repeated default text, placeholder strings, or values that echo the question prompt), warn the user explicitly: "Some values look like they may have been auto-filled rather than provided by you. Please review carefully."
|
|
834
864
|
|
|
835
|
-
⊗ Write USER.md, PROJECT-DEFINITION.xbrief.json,
|
|
865
|
+
⊗ Write USER.md, PROJECT-DEFINITION.xbrief.json, lifecycle scope xBRIEFs, or any other deft-directive-setup artifact without first displaying captured values and receiving explicit user confirmation.
|
|
866
|
+
⊗ Create `specification.xbrief.json` on a greenfield Light or Full path solely to satisfy export, cost, or build handoff.
|
|
836
867
|
⊗ Treat a broad "proceed" or "continue" as confirmation to write files -- the user must explicitly confirm the displayed values.
|
|
837
868
|
|
|
838
869
|
? **Yolo strategy carve-out**: When the user's chosen strategy is `yolo` (auto-pilot), the confirmation gate still applies but the agent (Johnbot) may self-confirm on the user's behalf by displaying the summary and immediately proceeding -- the user has already opted into auto-pilot by selecting yolo. The summary must still be displayed so the user can interrupt if values look wrong.
|
|
@@ -61,6 +61,8 @@ Task B (xBRIEF: [filename], issue #[N]): [one-paragraph description with specifi
|
|
|
61
61
|
STEP 3 — Validate: Use iteration fast lane during commits (affected/static gates). Run full task check once before push/PR (#1704). Fix any failures.
|
|
62
62
|
|
|
63
63
|
STEP 4 — Commit: Add CHANGELOG.md entries under [Unreleased].
|
|
64
|
+
Commit early: as soon as a coherent unit exists (source + tests that compile), then at checkpoints.
|
|
65
|
+
A host-kill must not leave the only copy unversioned (#3730).
|
|
64
66
|
Commit with message: [type]([scope]): [description] — with bullet-point body.
|
|
65
67
|
|
|
66
68
|
STEP 5 — Push and PR: Push branch to origin. Create PR targeting <configured-base-branch> using gh CLI.
|
|
@@ -77,6 +79,8 @@ CONSTRAINTS:
|
|
|
77
79
|
- Iteration commits: affected/static fast lane only; full task check required before push (#1704)
|
|
78
80
|
- Never force-push
|
|
79
81
|
- Dual stop (#2442): multi-iteration fix/repair loops need success + failure/budget stop (build defaults: max 5 quality-fix iters or 3 identical no-progress; pre-PR: max 3 polish passes). On halt: operator-visible report (tried / missing / human decision). Single-turn work is exempt. Delivery/acceptance mechanical ledger is #3143 (`packages/core/src/delivery-attempt/` / `docs/delivery-attempt.md`).
|
|
82
|
+
- Heartbeat (#1365 / #3730): write `.deft-scratch/subagent-status/<agent-id>.json` immediately on start (`phase: starting`) and every 2-3 minutes. See `docs/subagent-heartbeat.md`.
|
|
83
|
+
- Commit early (#3730): first coherent unit, then checkpoints. Do not hold a complete correct diff uncommitted until PR time.
|
|
80
84
|
```
|
|
81
85
|
|
|
82
86
|
### Template Rules
|
|
@@ -37,7 +37,7 @@
|
|
|
37
37
|
#### Mode A -- Pre-created worktree map (C3, headless via `--worktree-map`)
|
|
38
38
|
|
|
39
39
|
- ! When `task swarm:launch -- ... --worktree-map <path>` supplied a **pre-created worktree map** (**C3**), Phase 2 CONSUMES it instead of running `git worktree add` per agent. The C3 map is a JSON array of `{ "story_id": str, "worktree_path": str, "base_branch": str }`.
|
|
40
|
-
- ! The launch engine resolves the worktree map via `resolveWorktreeMap` (`packages/core/src/swarm/worktrees.ts`), which validates normalized C3 records and RAISES on same-path collisions
|
|
40
|
+
- ! The launch engine resolves the worktree map via `resolveWorktreeMap` (`packages/core/src/swarm/worktrees.ts`), which validates normalized C3 records and RAISES on same-path collisions, base-branch mismatches, or a registered path whose HEAD OID differs from the requested base OID. The HEAD check is a snapshot at resolution time -- `swarm:launch` emits a manifest and stops, so HEAD can still move before spawn. The monitor MUST surface any such raise verbatim and HALT setup -- a same-path collision means two agents would share one worktree (the Duplicate-Agent Failure Mode in Phase 4).
|
|
41
41
|
- ! Each resolved record's `worktree_path` and `base_branch` feed straight into Phase 3 dispatch and MUST match the **C2** launch-manifest's `worktree_path` / `branch` fields for the same `story_id`.
|
|
42
42
|
|
|
43
43
|
#### Mode B -- Monitor-created worktrees (interactive path)
|
|
@@ -100,7 +100,9 @@ Cross-references: `packages/core/src/platform/platform-capabilities.ts` (#1557a)
|
|
|
100
100
|
|
|
101
101
|
! **Supported backend examples (none mandatory):** Composer-class coding agents, Grok Build `spawn_subagent` workers, Cursor/cloud agents, and future adapters are all first-class examples. No single backend is required — Grok Build is one implementation of provider-neutral routing, not the only target.
|
|
102
102
|
|
|
103
|
-
! **Implement-leaf pre-dispatch (#3228):** Before the actual spawn primitive for an implement leaf (and before any re-dispatch), run `task swarm:pre-dispatch -- --scope-id <id> --target-id <worktree-or-branch>` — exit **0** only means spawn is allowed; exit **1** is `DENY_DUPLICATE_ACTIVE` (do not spawn). Depth + takeover: [`core-phase-4.md`](core-phase-4.md) Pre-dispatch deny gate; library #3143.
|
|
103
|
+
! **Implement-leaf pre-dispatch (#3228 / #3730):** Before the actual spawn primitive for an implement leaf (and before any re-dispatch), run `task swarm:pre-dispatch -- --scope-id <id> --target-id <worktree-or-branch>` — exit **0** only means spawn is allowed; exit **1** is `DENY_DUPLICATE_ACTIVE` (do not spawn). Begin on a filesystem worktree target also mkdirs `.deft-scratch/subagent-status/` so `verify:subagent-alive --require-agent` can return REDISPATCH_OK instead of exit 2. Depth + takeover: [`core-phase-4.md`](core-phase-4.md) Pre-dispatch deny gate; library #3143.
|
|
104
|
+
|
|
105
|
+
! **Arm the heartbeat path at dispatch (#3730):** Create the worker worktree's `.deft-scratch/subagent-status/` before spawn (mechanical on `swarm:launch` worktree-map and `swarm:pre-dispatch` begin). Instruct the worker to heartbeat per `templates/agent-prompt-preamble.md` § 10.5 and to commit early. Monitors MUST pass `--require-agent <agent-id>` on `task verify:subagent-alive`. ⊗ Put liveness on the C2 launch manifest or in `occupancy.json`.
|
|
104
106
|
|
|
105
107
|
! **Operator model routing (#1739):** the concrete per-role model lives in the gitignored, per-machine `.deft/routing.local.json`, keyed by `(dispatch_provider, worker_role)`. Record a decision with `task swarm:routing-set -- --role <role> (--model <slug> | --harness-default)`. `task swarm:launch` resolves the active provider's route and stamps `resolved_model` + `model_source` into each C2 manifest record. When `resolved_model` is non-null, the monitor MUST pass it as the **model argument of the actual dispatch primitive** (e.g. the Task tool's `model` field for a Cursor sub-agent) — stamping the manifest is prep; a recorded model that never reaches the spawn call is the bug #1739 closes. Run `task verify:routing` before dispatching a cohort (pre-dispatch hard gate; fails when a dispatched role is undecided) and `task verify:routing -- --advise` at session start (non-blocking disclosure). For harness-bound providers (e.g. `grok`) only `--harness-default` is recordable and `resolved_model` stays null.
|
|
106
108
|
|
|
@@ -11,16 +11,17 @@
|
|
|
11
11
|
|
|
12
12
|
! On the Grok Build hybrid path (`spawn_subagent` dispatch, no native lifecycle channel back to the monitor), worktree git state alone is INSUFFICIENT to distinguish a healthy mid-poll sub-agent from a stalled one. Long-running review-cycle pollers spend most of their wall-clock waiting on Greptile and emit no commits during that wait -- the #1166 swarm session is the recurrence record (two of three dispatched pollers went silent with zero observable signals; the monitor could not tell).
|
|
13
13
|
|
|
14
|
-
! The canonical alive-check on the Grok Build hybrid path is the heartbeat contract documented in `docs/subagent-heartbeat.md`. Every long-running sub-agent (pollers, watchdogs, implementation agents whose tool loop exceeds ~3 min) writes a JSON heartbeat to `.deft-scratch/subagent-status/<agent-id>.json` per the canonical poller template + agent preamble
|
|
14
|
+
! The canonical alive-check on the Grok Build hybrid path is the heartbeat contract documented in `docs/subagent-heartbeat.md`. Every long-running sub-agent (pollers, watchdogs, implementation agents whose tool loop exceeds ~3 min) writes a JSON heartbeat to `.deft-scratch/subagent-status/<agent-id>.json` per the canonical poller template + agent preamble. Default threshold is 30 minutes; `--threshold-minutes` overrides.
|
|
15
|
+
|
|
16
|
+
! Monitors MUST poll with `task verify:subagent-alive -- --require-agent <agent-id> [--scratch-dir <worktree>/.deft-scratch/subagent-status]` so a missing required record is exit `1` + `REDISPATCH_OK`, not a raw sweep that treats an empty dir as OK. `task agent:monitor` remains the raw sweep.
|
|
15
17
|
|
|
16
18
|
```
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
--scratch-dir <worktree
|
|
20
|
-
--scratch-dir <worktree-2>/.deft-scratch/subagent-status
|
|
19
|
+
task verify:subagent-alive -- \
|
|
20
|
+
--require-agent <agent-id> \
|
|
21
|
+
--scratch-dir <worktree>/.deft-scratch/subagent-status
|
|
21
22
|
```
|
|
22
23
|
|
|
23
|
-
! Run the
|
|
24
|
+
! Run the liveness gate alongside the worktree git checks at every monitor polling iteration (~2-3 min). When a record is reported STALE (mid-flight, terminal_state unpopulated, age > threshold), treat it as a candidate for the Takeover Triggers below; when it is reported MALFORMED, surface the diagnostics to the user and re-dispatch the agent with a fresh prompt that re-establishes the heartbeat contract. A TERMINAL record (terminal_state set) is NEVER stale -- the agent reached its exit on its own terms.
|
|
24
25
|
|
|
25
26
|
~ The heartbeat is filesystem-only by design; a network partition or rate-limit ceiling cannot mask agent liveness. Pair the on-disk sweep with the worktree git checks (`git status --short`, `git log --oneline -3`) and the per-PR readiness gate (`task pr:merge-ready`) for the full alive + progressing + clean picture.
|
|
26
27
|
|
|
@@ -144,12 +145,14 @@ task swarm:pre-dispatch -- \
|
|
|
144
145
|
--scope-id <id> --target-id <target> \
|
|
145
146
|
--action complete --status succeeded|failed|cancelled|blocked
|
|
146
147
|
|
|
147
|
-
# Takeover: cancel prior attempt, THEN pre-dispatch begin again (never dual active)
|
|
148
|
+
# Takeover after REDISPATCH_OK: cancel prior attempt, THEN pre-dispatch begin again (never dual active)
|
|
148
149
|
task swarm:pre-dispatch -- --scope-id <id> --target-id <target> --action cancel
|
|
149
150
|
task swarm:pre-dispatch -- --scope-id <id> --target-id <target> # begin
|
|
151
|
+
# If verify:session-ritual --tier=gated fails first:
|
|
152
|
+
task session:start --rearm --session-id=<same>
|
|
150
153
|
```
|
|
151
154
|
|
|
152
|
-
! Gate authority is **#3143** `DENY_DUPLICATE_ACTIVE` (`maxActiveAttempts: 1`) on the delivery-attempt unit ledger (`scopeId` + `targetId` + `workflowId`, default workflow `drive-to:merge-ready`). CLI is authoritative; this section is a pointer only.
|
|
155
|
+
! Gate authority is **#3143** `DENY_DUPLICATE_ACTIVE` (`maxActiveAttempts: 1`) on the delivery-attempt unit ledger (`scopeId` + `targetId` + `workflowId`, default workflow `drive-to:merge-ready`). A killed worker stays `queued`/`running` until cancel; `REDISPATCH_OK` does not lift the deny (#3730). CLI is authoritative; this section is a pointer only.
|
|
153
156
|
⊗ Spawn a second implement leaf while pre-dispatch exits 1 (active attempt exists).
|
|
154
157
|
⊗ Treat "resume failed" / host false-alive as license to skip the gate.
|
|
155
158
|
⊗ Lift DENY by concurrent dual active — escape hatch is cancel-then-begin, not override-while-both-run.
|
|
@@ -11,6 +11,7 @@ Load this file only after detect selects Cursor. Do not load other host adapters
|
|
|
11
11
|
### Step 2e: Cursor Launch (Task tool available) — #1877
|
|
12
12
|
|
|
13
13
|
! When the platform descriptor is `cursor-composer` or `cursor-cloud-agent` (Cursor `Task` tool detected with Cursor signals, no `start_agent`, no `WARP_*`, no Claude Code classification, no OpenClaw `sessions_spawn`, no `spawn_subagent`), dispatch each worker via the Cursor `Task` tool with:
|
|
14
|
+
0. Create `<worktree>/.deft-scratch/subagent-status/` before spawn if `swarm:launch` / `swarm:pre-dispatch` did not already (#3730). Include preamble § 10.5 (heartbeat + commit early) and poll with `task verify:subagent-alive -- --require-agent <agent-id>`.
|
|
14
15
|
1. The canonical `templates/agent-prompt-preamble.md` content as the preamble (AGENTS.md read mandate, #810 xBRIEF gate, #798 PowerShell UTF-8, pre-PR + review-cycle mandates).
|
|
15
16
|
2. The standard worktree prompt (STEP 1-6 from the Prompt Template below).
|
|
16
17
|
3. The worktree path set to the agent's isolated git worktree.
|
|
@@ -24,6 +24,7 @@ This path became first-class in #1342 (platform adapter slices 1-3) and is fully
|
|
|
24
24
|
### Step 2d: Grok Build Launch (spawn_subagent available)
|
|
25
25
|
|
|
26
26
|
! When the platform descriptor is `grok-build` (spawn_subagent detected, no start_agent, no WARP_*, no Cursor `Task`, no OpenClaw `sessions_spawn`), dispatch each worker via `spawn_subagent` with:
|
|
27
|
+
0. Create `<worktree>/.deft-scratch/subagent-status/` before spawn if launch/pre-dispatch did not already, and instruct the worker to heartbeat + commit early (#3730).
|
|
27
28
|
1. The canonical `templates/agent-prompt-preamble.md` content as the preamble
|
|
28
29
|
2. The standard worktree prompt (STEP 1-6 from the Prompt Template below), adapted to use `get_command_or_subagent_output` for polling rather than `start_agent` lifecycle events
|
|
29
30
|
3. The worktree path set to the agent's isolated git worktree
|
|
@@ -37,7 +37,7 @@ Legend (from RFC2119): !=MUST, ~=SHOULD, ≉=SHOULD NOT, ⊗=MUST NOT, ?=MAY.
|
|
|
37
37
|
|
|
38
38
|
## Deterministic Questions Contract
|
|
39
39
|
|
|
40
|
-
! Every numbered-menu prompt rendered in this skill (Phase 2 candidate selection, Phase 3 per-item decision walk) ! MUST follow [`../../contracts/deterministic-questions.md`](../../contracts/deterministic-questions.md): render the canonical numbered menu in chat unless the host UI visibly preserves numeric option labels and returns numeric selections or exact displayed option text. The final two numbered options are `Discuss` and `Back`, in that order, and the Discuss-pause semantic from the contract applies verbatim -- on `Discuss` the agent halts the in-progress sequence and resumes only on an explicit user signal.
|
|
40
|
+
! Every numbered-menu prompt rendered in this skill (Phase 2 candidate selection, Phase 3 per-item decision walk, post-Accept offer) ! MUST follow [`../../contracts/deterministic-questions.md`](../../contracts/deterministic-questions.md): render the canonical numbered menu in chat unless the host UI visibly preserves numeric option labels and returns numeric selections or exact displayed option text. The final two numbered options are `Discuss` and `Back`, in that order, and the Discuss-pause semantic from the contract applies verbatim -- on `Discuss` the agent halts the in-progress sequence and resumes only on an explicit user signal.
|
|
41
41
|
|
|
42
42
|
## Work selection fork (#2542 / #2402)
|
|
43
43
|
|
|
@@ -101,6 +101,7 @@ What would you like to do with this candidate?
|
|
|
101
101
|
- ~ Bulk: `task triage:bulk-{accept,reject,defer,needs-ac}`; results still flow through the audit log.
|
|
102
102
|
- ⊗ Write to `xbrief/proposed/` directly -- only `task triage:accept` is authorised.
|
|
103
103
|
- ~ **Accept → pending chain (#1136):** `task triage:accept` ingests into **`proposed/`**. To stage into WIP (`pending/`) in one operator action: `task triage:accept -- --issue <N> --repo OWNER/NAME --auto-promote` (WIP cap still enforced; use `--force` on the accept command for WIP override). Separately, promote an already-accepted proposed scope by issue: `task scope:promote -- --from-issue=<N> [--repo OWNER/NAME]` (gates on latest `candidates.jsonl` decision = `accept`; non-accept refuses unless `--force-no-cache`; no decision soft-warns, `--strict` fails). Path-based `task scope:promote -- <file>` remains ungated for refinement scaffolds.
|
|
104
|
+
- ? **After Accept (#3708):** offer `deft-directive-design-critique`. Optional; same after `--auto-promote` (promote already happened). Decline writes nothing. Menu: 1. Run critique (existing ADR-005 path) 2. Skip 3. Discuss 4. Back. Back = Skip (do not re-open Accept; undo is `task triage:reset`).
|
|
104
105
|
|
|
105
106
|
## Phase 4 -- Audit
|
|
106
107
|
|
|
@@ -141,5 +142,5 @@ Live walkers (`triage:queue`, scope-drift, bootstrap) scan `.deft-cache/github-i
|
|
|
141
142
|
|
|
142
143
|
## References
|
|
143
144
|
|
|
144
|
-
- #1119 D6; #1128 D11 (`triage:queue` / `show` / `audit`); #2890 Phase 3 operator brief; #3116 validity + URL-first; #1122 / #1123 / #1127 / #1129 / #1131; #1136 (`scope:promote --from-issue` / `triage:accept --auto-promote`)
|
|
145
|
+
- #1119 D6; #1128 D11 (`triage:queue` / `show` / `audit`); #2890 Phase 3 operator brief; #3116 validity + URL-first; #1122 / #1123 / #1127 / #1129 / #1131; #1136 (`scope:promote --from-issue` / `triage:accept --auto-promote`); #3708 (post-Accept design-critique offer)
|
|
145
146
|
- Siblings: `deft-directive-refinement`, `deft-directive-swarm`, `deft-directive-sync`
|
package/tasks/engine.yml
CHANGED
|
@@ -102,6 +102,10 @@ tasks:
|
|
|
102
102
|
" session:start "|" session-start "|\
|
|
103
103
|
" session:ready "|" session-ready "|\
|
|
104
104
|
" occupancy:steal "|" occupancy-steal "|\
|
|
105
|
+
" occupancy:release "|" occupancy-release "|\
|
|
106
|
+
" occupancy:heartbeat "|" occupancy-heartbeat "|\
|
|
107
|
+
" occupancy:grant "|" occupancy-grant "|\
|
|
108
|
+
" session:end "|" session-end "|\
|
|
105
109
|
" lifecycle:event "|" lifecycle-event "|\
|
|
106
110
|
" verify:session-ritual "|" verify-session-ritual "|\
|
|
107
111
|
" verify:tools "|" verify-tools "|\
|
package/tasks/feedback.yml
CHANGED
|
@@ -5,7 +5,7 @@ vars:
|
|
|
5
5
|
|
|
6
6
|
tasks:
|
|
7
7
|
file:
|
|
8
|
-
desc: "Draft or file a deduped framework-gap issue upstream (#1709). -- task feedback:file -- [--summary TEXT | positional] [--context ...] [--confirm] [--dry-run] [--json]"
|
|
8
|
+
desc: "Draft or file a deduped framework-gap issue upstream (#1709 / #3713). -- task feedback:file -- [--summary TEXT | positional] [--context ...] [--blocker] [--confirm] [--dry-run] [--json]"
|
|
9
9
|
deps:
|
|
10
10
|
- task: :engine:_ts-build
|
|
11
11
|
cmds:
|
package/tasks/occupancy.yml
CHANGED
|
@@ -7,7 +7,7 @@ vars:
|
|
|
7
7
|
|
|
8
8
|
tasks:
|
|
9
9
|
steal:
|
|
10
|
-
desc: "
|
|
10
|
+
desc: "Lease-only confirmed steal (#3433/#3611). Flags: --confirm --occupant <reported-session-id>; manual/Grok owner: --session-id <your-session-id> or DEFT_SESSION_ID. If ritual differs, align that ID with eligible re-arm or cold session:start. Prefer session:start --steal."
|
|
11
11
|
dir: '{{.USER_WORKING_DIR}}'
|
|
12
12
|
env:
|
|
13
13
|
PYTHONUTF8: "1"
|
|
@@ -15,3 +15,36 @@ tasks:
|
|
|
15
15
|
- task: :engine:invoke
|
|
16
16
|
vars:
|
|
17
17
|
ENGINE_CMD: 'occupancy:steal --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
|
18
|
+
|
|
19
|
+
release:
|
|
20
|
+
desc: "Release this worktree occupancy lease (#3604/#3611). Manual/Grok owner: --session-id <id> or DEFT_SESSION_ID. Owner live or expired residue; non-owner live denied."
|
|
21
|
+
dir: '{{.USER_WORKING_DIR}}'
|
|
22
|
+
# Runtime/session dispatch: no engine:_ts-build / pnpm build (#2181).
|
|
23
|
+
env:
|
|
24
|
+
PYTHONUTF8: "1"
|
|
25
|
+
cmds:
|
|
26
|
+
- task: :engine:invoke
|
|
27
|
+
vars:
|
|
28
|
+
ENGINE_CMD: 'occupancy:release --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
|
29
|
+
|
|
30
|
+
heartbeat:
|
|
31
|
+
desc: "Refresh your own live lease during long quiet stretches (#3599). Manual/Grok owner: --session-id <id> or DEFT_SESSION_ID. Gated writes refresh automatically; this never claims."
|
|
32
|
+
dir: '{{.USER_WORKING_DIR}}'
|
|
33
|
+
# Runtime/session dispatch: no engine:_ts-build / pnpm build (#2181).
|
|
34
|
+
env:
|
|
35
|
+
PYTHONUTF8: "1"
|
|
36
|
+
cmds:
|
|
37
|
+
- task: :engine:invoke
|
|
38
|
+
vars:
|
|
39
|
+
ENGINE_CMD: 'occupancy:heartbeat --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
|
40
|
+
|
|
41
|
+
grant:
|
|
42
|
+
desc: "Admit a dispatched child to your lease for writes (#3755). Owner-only: --session-id <id> or DEFT_SESSION_ID, plus --child-session-id <id> --role <worker-role> [--ttl-minutes N] [--revoke]. Grants admit writes, never administration."
|
|
43
|
+
dir: '{{.USER_WORKING_DIR}}'
|
|
44
|
+
# Runtime/session dispatch: no engine:_ts-build / pnpm build (#2181).
|
|
45
|
+
env:
|
|
46
|
+
PYTHONUTF8: "1"
|
|
47
|
+
cmds:
|
|
48
|
+
- task: :engine:invoke
|
|
49
|
+
vars:
|
|
50
|
+
ENGINE_CMD: 'occupancy:grant --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
package/tasks/prd.yml
CHANGED
|
@@ -21,12 +21,11 @@ tasks:
|
|
|
21
21
|
# would cause go-task to short-circuit before `cmds:` runs, dropping
|
|
22
22
|
# CLI_ARGS and silently breaking the #539 recovery path (#573, #574).
|
|
23
23
|
# See deft/conventions/task-caching.md for the full rule.
|
|
24
|
-
desc: Export
|
|
24
|
+
desc: Export resolved project narratives to a read-only PRD.md
|
|
25
25
|
summary: |
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
never authoritative -- the xBRIEF is the source of truth.
|
|
26
|
+
Resolves full-spec or greenfield authority from the project root and extracts
|
|
27
|
+
stakeholder-safe narratives into a human-readable PRD.md. Explicit --spec remains
|
|
28
|
+
supported. PRD.md is never authoritative -- the resolved xBRIEF is the source of truth.
|
|
30
29
|
dir: '{{.USER_WORKING_DIR}}'
|
|
31
30
|
deps:
|
|
32
31
|
- task: :engine:_ts-build
|
package/tasks/scm.yml
CHANGED
|
@@ -13,6 +13,7 @@ version: '3'
|
|
|
13
13
|
# - scm:issue:view (thin wrapper over `ghx|gh issue view`)
|
|
14
14
|
# - scm:issue:close (thin wrapper over `ghx|gh issue close`)
|
|
15
15
|
# - scm:issue:edit (thin wrapper over `ghx|gh issue edit`)
|
|
16
|
+
# - scm:issue:design-critique-chip (#3642 closed catalog remaining-set)
|
|
16
17
|
# - scm:body:* (#1555 safe Markdown body posting via github-body TS CLI)
|
|
17
18
|
#
|
|
18
19
|
# Each command is a thin pass-through to `ghx <verb>` (when ghx is on PATH)
|
|
@@ -34,8 +35,9 @@ version: '3'
|
|
|
34
35
|
# stub deliberately does not re-implement; #881 owns the full surface.
|
|
35
36
|
#
|
|
36
37
|
# Forward-compat marker: v1 was issue:* plus #1555 body-posting. #3391
|
|
37
|
-
# adds scm:sync-default (dest-targeted staged sync PRs).
|
|
38
|
-
#
|
|
38
|
+
# adds scm:sync-default (dest-targeted staged sync PRs). #3642 adds
|
|
39
|
+
# scm:issue:design-critique-chip (closed catalog remaining-set). Other PR
|
|
40
|
+
# verbs remain #881.
|
|
39
41
|
# ---------------------------------------------------------------------------
|
|
40
42
|
|
|
41
43
|
vars:
|
|
@@ -89,6 +91,16 @@ tasks:
|
|
|
89
91
|
vars:
|
|
90
92
|
ENGINE_CMD: 'scm issue edit {{.CLI_ARGS}}'
|
|
91
93
|
|
|
94
|
+
issue:design-critique-chip:
|
|
95
|
+
desc: "[#3642] Exclusive design-critique catalog chip -- task scm:issue:design-critique-chip -- --issue N --chip triage-ready|mechanism-shaped [--repo OWNER/NAME]"
|
|
96
|
+
dir: '{{.USER_WORKING_DIR}}'
|
|
97
|
+
deps:
|
|
98
|
+
- task: :engine:_ts-build
|
|
99
|
+
cmds:
|
|
100
|
+
- task: :engine:invoke
|
|
101
|
+
vars:
|
|
102
|
+
ENGINE_CMD: 'scm issue design-critique-chip {{.CLI_ARGS}}'
|
|
103
|
+
|
|
92
104
|
body:issue:create:
|
|
93
105
|
desc: "[#1555] Safely create an issue body from --body-file without shell Markdown interpolation"
|
|
94
106
|
dir: '{{.USER_WORKING_DIR}}'
|
package/tasks/session.yml
CHANGED
|
@@ -10,7 +10,7 @@ vars:
|
|
|
10
10
|
|
|
11
11
|
tasks:
|
|
12
12
|
start:
|
|
13
|
-
desc: "
|
|
13
|
+
desc: "Claim occupancy and run the quick-tier ritual for one owner (#1348/#3611). Flags: --session-id <id> / --steal --confirm --occupant <current-id> / --defer step=reason / --json"
|
|
14
14
|
dir: '{{.USER_WORKING_DIR}}'
|
|
15
15
|
# Runtime/session dispatch: no engine:_ts-build / pnpm build (#2181).
|
|
16
16
|
env:
|
|
@@ -21,7 +21,7 @@ tasks:
|
|
|
21
21
|
ENGINE_CMD: 'session:start --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
|
22
22
|
|
|
23
23
|
ready:
|
|
24
|
-
desc: "One-shot mutation recovery to gated write-ready (#2993). Composes session:start + verify:session-ritual --tier=gated + cache fetch-all when needed. Flags: --json / --repo OWNER/NAME / --with-network"
|
|
24
|
+
desc: "One-shot mutation recovery to gated write-ready (#2993/#3611). Composes session:start + verify:session-ritual --tier=gated + cache fetch-all when needed. Flags: --session-id <id> / --json / --repo OWNER/NAME / --with-network"
|
|
25
25
|
dir: '{{.USER_WORKING_DIR}}'
|
|
26
26
|
# Runtime/session dispatch: no engine:_ts-build / pnpm build (#2181).
|
|
27
27
|
env:
|
|
@@ -30,3 +30,14 @@ tasks:
|
|
|
30
30
|
- task: :engine:invoke
|
|
31
31
|
vars:
|
|
32
32
|
ENGINE_CMD: 'session:ready --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
|
33
|
+
|
|
34
|
+
end:
|
|
35
|
+
desc: "End this mutation session by releasing occupancy (#3604/#3611). Manual/Grok owner: --session-id <id> or DEFT_SESSION_ID. Same as occupancy:release."
|
|
36
|
+
dir: '{{.USER_WORKING_DIR}}'
|
|
37
|
+
# Runtime/session dispatch: no engine:_ts-build / pnpm build (#2181).
|
|
38
|
+
env:
|
|
39
|
+
PYTHONUTF8: "1"
|
|
40
|
+
cmds:
|
|
41
|
+
- task: :engine:invoke
|
|
42
|
+
vars:
|
|
43
|
+
ENGINE_CMD: 'session:end --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
package/tasks/toolchain.yml
CHANGED
|
@@ -14,10 +14,10 @@ tasks:
|
|
|
14
14
|
ENGINE_CMD: 'toolchain-check'
|
|
15
15
|
|
|
16
16
|
check-consumer:
|
|
17
|
-
desc: Verify
|
|
17
|
+
desc: Verify git, gh, node, and the consumer's selected npm or pnpm; this gate does not probe go-task/Python/go/uv (#3610/#3335).
|
|
18
18
|
deps:
|
|
19
19
|
- task: :engine:_ts-build
|
|
20
20
|
cmds:
|
|
21
21
|
- task: :engine:invoke
|
|
22
22
|
vars:
|
|
23
|
-
ENGINE_CMD: 'toolchain-check --consumer'
|
|
23
|
+
ENGINE_CMD: 'toolchain-check --consumer --project-root "{{.USER_WORKING_DIR}}"'
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
version: '3'
|
|
2
|
+
|
|
3
|
+
# tasks/triage-evaluate.yml -- Stage A isolated issue-eval (#3648).
|
|
4
|
+
#
|
|
5
|
+
# Wired into Taskfile.yml under include key `triage-evaluate`. Inner task
|
|
6
|
+
# `evaluate` is exposed as `task triage:evaluate`.
|
|
7
|
+
#
|
|
8
|
+
# Per conventions/task-caching.md: NO sources/generates -- user-facing flags.
|
|
9
|
+
|
|
10
|
+
vars:
|
|
11
|
+
DEFT_ROOT: '{{joinPath .TASKFILE_DIR ".."}}'
|
|
12
|
+
|
|
13
|
+
tasks:
|
|
14
|
+
evaluate:
|
|
15
|
+
desc: "Evaluate issues off origin/master (validity + parent WIP + value). -- task triage:evaluate -- <N...> [--concurrency N] [--repo OWNER/NAME] [--json]"
|
|
16
|
+
internal: true
|
|
17
|
+
deps: [":engine:_ts-build"]
|
|
18
|
+
dir: '{{.USER_WORKING_DIR}}'
|
|
19
|
+
cmds:
|
|
20
|
+
- task: :engine:invoke
|
|
21
|
+
vars:
|
|
22
|
+
ENGINE_CMD: 'triage-evaluate --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
package/tasks/verify.yml
CHANGED
|
@@ -503,7 +503,7 @@ tasks:
|
|
|
503
503
|
ENGINE_CMD: 'verify:lifecycle-visible --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
|
504
504
|
|
|
505
505
|
orphan-active:
|
|
506
|
-
desc: "Fail-closed orphan-active guard (#2321 / #3429). Detects xbrief/active/ briefs with plan.status==running whose referenced GitHub issues are all closed and/or whose linked PR is merged — the stop-at:pr-open lifecycle leak. Confirmed shipped remediates with task scope:complete / scope:cancel or swarm finalize. Unresolved GitHub lookup still exits 1 but prints a retry, not scope:complete. Three-state exit (0 clean / 1 orphan / 2 config). Pass --issue N to scan one origin after merge; --skip-gh to rely on triage cache only."
|
|
506
|
+
desc: "Fail-closed orphan-active guard (#2321 / #3429). Detects xbrief/active/ briefs with plan.status==running whose referenced GitHub issues are all closed and/or whose linked PR is merged — the stop-at:pr-open lifecycle leak. Confirmed shipped remediates with task scope:complete / scope:cancel or swarm finalize. Unresolved GitHub lookup still exits 1 but prints a retry, not scope:complete. Three-state exit (0 clean / 1 orphan / 2 config). Pass --issue N to scan one origin after merge; --skip-gh to rely on triage cache only. Issue state resolves by query shape (#3767): scoped --issue N takes an authoritative read and stays fail-closed on unknown; the unscoped sweep uses one complete open-issue inventory and stays fail-open on unknown. A cache hit counts only within 15 minutes, and every run prints the basis of its verdict — see content/docs/orphan-active-verdict-basis.md."
|
|
507
507
|
dir: '{{.USER_WORKING_DIR}}'
|
|
508
508
|
deps:
|
|
509
509
|
- task: :engine:_ts-build
|
|
@@ -512,6 +512,26 @@ tasks:
|
|
|
512
512
|
vars:
|
|
513
513
|
ENGINE_CMD: 'verify:orphan-active --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
|
514
514
|
|
|
515
|
+
pr-closeout-attestable:
|
|
516
|
+
desc: "Fail-closed merge-time closeout gate (#3781). Refuses a merge when the PR's structured closing references name an issue whose brief is still running in xbrief/active/ with acceptance criteria carrying neither x-directive/evidence nor x-directive/disposition. The trigger is the closing reference, not the branch diff — CI runs before the merge and the issue closes on it, so a diff-keyed gate can never fail the PR that creates the orphan. Reuses evaluateAcceptanceEvidenceGate, the same rule scope:complete enforces. A PR that leaves an unattested brief WITHOUT closing its issue is unaffected. Three-state exit (0 attestable or closes nothing / 1 unattested closeout / 2 config or closing-reference lookup error). -- task verify:pr-closeout-attestable -- --pr N [--repo OWNER/REPO]"
|
|
517
|
+
dir: '{{.USER_WORKING_DIR}}'
|
|
518
|
+
deps:
|
|
519
|
+
- task: :engine:_ts-build
|
|
520
|
+
cmds:
|
|
521
|
+
- task: :engine:invoke
|
|
522
|
+
vars:
|
|
523
|
+
ENGINE_CMD: 'verify:pr-closeout-attestable --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
|
524
|
+
|
|
525
|
+
completed-write-guard:
|
|
526
|
+
desc: "Fail-closed completed/ write guard (#3679). Newly added xbrief/completed/ (or vbrief/completed/) artifacts must have been written by scope:complete / scope:fail. Historical corpus is advisory via doctor. Remediation names the leftover land PR (#3476). Three-state exit (0 clean / 1 unguarded add / 2 config). Does not change verify:completed-tracked."
|
|
527
|
+
dir: '{{.USER_WORKING_DIR}}'
|
|
528
|
+
deps:
|
|
529
|
+
- task: :engine:_ts-build
|
|
530
|
+
cmds:
|
|
531
|
+
- task: :engine:invoke
|
|
532
|
+
vars:
|
|
533
|
+
ENGINE_CMD: 'verify:completed-write-guard --project-root "{{.USER_WORKING_DIR}}" {{.CLI_ARGS}}'
|
|
534
|
+
|
|
515
535
|
completed-tracked:
|
|
516
536
|
desc: "Fail-closed completed-tracked land guard (#3264 / #1358 / #3476). Closed scoped GitHub issues with a known lifecycle xBRIEF origin must have a tracked xbrief/completed/ or xbrief/cancelled/ artifact on the delivery tip. --issue N is the drive-to DONE form. Remediation: task swarm:finalize-cohort or a lifecycle PR. Three-state exit (0 clean / 1 missing land / 2 config). Pass --skip-gh to rely on triage cache only; --tip to override delivery tip."
|
|
517
537
|
dir: '{{.USER_WORKING_DIR}}'
|