dorfl 0.1.1 → 0.1.2
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/dist/advance-ci-template.d.ts +3 -3
- package/dist/advance-ci-template.js +1 -1
- package/dist/advance-ci-template.js.map +1 -1
- package/dist/advance-classify.d.ts +5 -5
- package/dist/advance-classify.d.ts.map +1 -1
- package/dist/advance-classify.js +4 -4
- package/dist/advance-drivers.d.ts +7 -7
- package/dist/advance-drivers.d.ts.map +1 -1
- package/dist/advance-drivers.js +5 -5
- package/dist/advance-drivers.js.map +1 -1
- package/dist/advance-isolated.d.ts +3 -3
- package/dist/advance-isolated.d.ts.map +1 -1
- package/dist/advance-isolated.js +1 -1
- package/dist/advance-lifecycle-template.d.ts +2 -2
- package/dist/advance-lifecycle-template.js +9 -9
- package/dist/advance-lifecycle-template.js.map +1 -1
- package/dist/advance-loop-driver.d.ts +3 -3
- package/dist/advance-loop-driver.d.ts.map +1 -1
- package/dist/advance-loop-driver.js +1 -1
- package/dist/advance-treeless-publish.d.ts +1 -1
- package/dist/advance.d.ts +11 -11
- package/dist/advance.d.ts.map +1 -1
- package/dist/advance.js +21 -21
- package/dist/advance.js.map +1 -1
- package/dist/advancing-lock.d.ts +1 -1
- package/dist/advancing-lock.js +5 -5
- package/dist/apply-decide.d.ts +2 -2
- package/dist/apply-decide.js +2 -2
- package/dist/apply-merge-action.d.ts +4 -4
- package/dist/apply-merge-action.js +2 -2
- package/dist/apply-persist.d.ts +5 -5
- package/dist/apply-persist.d.ts.map +1 -1
- package/dist/apply-persist.js +7 -7
- package/dist/apply-persist.js.map +1 -1
- package/dist/buildable-body.d.ts +14 -14
- package/dist/buildable-body.js +9 -9
- package/dist/claim-cas.d.ts +3 -3
- package/dist/claim-cas.js +1 -1
- package/dist/claim-cas.js.map +1 -1
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +76 -76
- package/dist/cli.js.map +1 -1
- package/dist/close-job-template.d.ts +3 -3
- package/dist/close-job-template.js +8 -8
- package/dist/close-job.d.ts +8 -8
- package/dist/close-job.js +25 -25
- package/dist/close-job.js.map +1 -1
- package/dist/complete.d.ts +3 -3
- package/dist/complete.js +8 -8
- package/dist/complete.js.map +1 -1
- package/dist/concurrency.d.ts +1 -1
- package/dist/concurrency.js +1 -1
- package/dist/config.d.ts +32 -32
- package/dist/config.js +5 -5
- package/dist/config.js.map +1 -1
- package/dist/continue-branch.d.ts +1 -1
- package/dist/continue-branch.js +1 -1
- package/dist/cwd-section.js +1 -1
- package/dist/cwd-section.js.map +1 -1
- package/dist/decision-engine.d.ts +2 -2
- package/dist/do-autopick.d.ts +6 -6
- package/dist/do-autopick.d.ts.map +1 -1
- package/dist/do-autopick.js +5 -5
- package/dist/do-autopick.js.map +1 -1
- package/dist/do-config.d.ts +3 -3
- package/dist/do-config.js +3 -3
- package/dist/do-config.js.map +1 -1
- package/dist/do-remote-auto.d.ts +2 -2
- package/dist/do-remote-auto.js +1 -1
- package/dist/do.d.ts +25 -25
- package/dist/do.d.ts.map +1 -1
- package/dist/do.js +20 -20
- package/dist/do.js.map +1 -1
- package/dist/drop-source.d.ts +2 -2
- package/dist/env-config.js +8 -8
- package/dist/env-config.js.map +1 -1
- package/dist/format.js +3 -3
- package/dist/format.js.map +1 -1
- package/dist/frontmatter.d.ts +14 -13
- package/dist/frontmatter.d.ts.map +1 -1
- package/dist/frontmatter.js +12 -24
- package/dist/frontmatter.js.map +1 -1
- package/dist/install-ci-branch-protection.d.ts +1 -1
- package/dist/install-ci-branch-protection.js +1 -1
- package/dist/install-ci-capabilities/advance-lifecycle.d.ts +1 -1
- package/dist/install-ci-capabilities/advance-lifecycle.js +1 -1
- package/dist/install-ci-capabilities/close-job.d.ts +1 -1
- package/dist/install-ci-capabilities/close-job.js +1 -1
- package/dist/install-ci-capabilities/example-noop.d.ts +1 -1
- package/dist/install-ci-capabilities/example-noop.js +1 -1
- package/dist/install-ci-capabilities/intake.d.ts +2 -2
- package/dist/install-ci-capabilities/intake.js +2 -2
- package/dist/install-ci-capabilities/verify.d.ts +1 -1
- package/dist/install-ci-capabilities/verify.js +1 -1
- package/dist/install-ci-core.d.ts +3 -3
- package/dist/install-ci-core.js +2 -2
- package/dist/install-ci-core.js.map +1 -1
- package/dist/install-ci-github.d.ts +1 -1
- package/dist/install-ci-github.js +1 -1
- package/dist/install-ci.d.ts +1 -1
- package/dist/install-ci.js +4 -4
- package/dist/install-ci.js.map +1 -1
- package/dist/intake-event.d.ts +6 -6
- package/dist/intake-event.js +6 -6
- package/dist/intake-marker.d.ts +3 -3
- package/dist/intake-marker.d.ts.map +1 -1
- package/dist/intake-triage.d.ts +1 -1
- package/dist/intake-triage.js +2 -2
- package/dist/intake-trigger-template.d.ts +8 -8
- package/dist/intake-trigger-template.d.ts.map +1 -1
- package/dist/intake-trigger-template.js +16 -16
- package/dist/intake-trigger-template.js.map +1 -1
- package/dist/intake.d.ts +50 -50
- package/dist/intake.d.ts.map +1 -1
- package/dist/intake.js +70 -70
- package/dist/intake.js.map +1 -1
- package/dist/integration-core.d.ts +17 -17
- package/dist/integration-core.js +17 -17
- package/dist/integration-core.js.map +1 -1
- package/dist/isolation.d.ts +3 -3
- package/dist/issue-provider.d.ts +4 -4
- package/dist/issue-provider.js +1 -1
- package/dist/item-lock.d.ts +21 -21
- package/dist/item-lock.d.ts.map +1 -1
- package/dist/item-lock.js +16 -16
- package/dist/item-path.d.ts +2 -2
- package/dist/item-path.js +2 -2
- package/dist/ledger-lint.d.ts +9 -9
- package/dist/ledger-lint.js +9 -9
- package/dist/ledger-read.d.ts +57 -57
- package/dist/ledger-read.d.ts.map +1 -1
- package/dist/ledger-read.js +24 -24
- package/dist/ledger-read.js.map +1 -1
- package/dist/ledger-write.d.ts +2 -2
- package/dist/ledger-write.js +1 -1
- package/dist/lifecycle-gather.d.ts +1 -1
- package/dist/lifecycle-gather.js +16 -16
- package/dist/lifecycle-gather.js.map +1 -1
- package/dist/lifecycle-pools.d.ts +4 -4
- package/dist/lifecycle-pools.js +1 -1
- package/dist/merge-question-surfacer.d.ts +3 -3
- package/dist/merge-question-surfacer.js +2 -2
- package/dist/merge-question-surfacer.js.map +1 -1
- package/dist/mint-adr.js +4 -4
- package/dist/mirror-pool-scan.d.ts +2 -2
- package/dist/mirror-pool-scan.js +3 -3
- package/dist/mirror-pool-scan.js.map +1 -1
- package/dist/needs-attention.d.ts +13 -13
- package/dist/needs-attention.d.ts.map +1 -1
- package/dist/needs-attention.js +11 -11
- package/dist/needs-attention.js.map +1 -1
- package/dist/orphan-sidecar.d.ts +2 -2
- package/dist/placement.d.ts +6 -6
- package/dist/placement.js +2 -2
- package/dist/prompt.d.ts +16 -19
- package/dist/prompt.d.ts.map +1 -1
- package/dist/prompt.js +17 -19
- package/dist/prompt.js.map +1 -1
- package/dist/readiness.d.ts +1 -1
- package/dist/recover-isolated.js +1 -1
- package/dist/repo-config.js +12 -12
- package/dist/repo-config.js.map +1 -1
- package/dist/review-gate.d.ts +3 -3
- package/dist/review-gate.d.ts.map +1 -1
- package/dist/review-gate.js +11 -10
- package/dist/review-gate.js.map +1 -1
- package/dist/review-verdict.d.ts +2 -2
- package/dist/review-verdict.d.ts.map +1 -1
- package/dist/review-verdict.js +1 -1
- package/dist/run.d.ts +1 -1
- package/dist/run.js +4 -4
- package/dist/run.js.map +1 -1
- package/dist/scan.d.ts +10 -10
- package/dist/scan.d.ts.map +1 -1
- package/dist/scan.js +8 -8
- package/dist/scan.js.map +1 -1
- package/dist/select-order.d.ts +1 -1
- package/dist/select-priority.d.ts +12 -12
- package/dist/select-priority.d.ts.map +1 -1
- package/dist/select-priority.js +5 -5
- package/dist/select-priority.js.map +1 -1
- package/dist/sidecar.d.ts +2 -2
- package/dist/sidecar.js +2 -2
- package/dist/sidecar.js.map +1 -1
- package/dist/slug-namespace.d.ts +1 -1
- package/dist/slug-namespace.js +3 -3
- package/dist/slug-namespace.js.map +1 -1
- package/dist/spec-complete.js +2 -2
- package/dist/spec-complete.js.map +1 -1
- package/dist/start.d.ts +1 -1
- package/dist/start.js +3 -3
- package/dist/start.js.map +1 -1
- package/dist/status.d.ts +3 -3
- package/dist/status.js +4 -4
- package/dist/status.js.map +1 -1
- package/dist/surface-gate.d.ts +2 -2
- package/dist/surface-gate.d.ts.map +1 -1
- package/dist/surface-persist.d.ts +2 -2
- package/dist/surface-persist.d.ts.map +1 -1
- package/dist/tasker-review-loop.d.ts +8 -8
- package/dist/tasker-review-loop.d.ts.map +1 -1
- package/dist/tasker-review-loop.js +8 -8
- package/dist/tasker-review-loop.js.map +1 -1
- package/dist/tasking-eligibility.d.ts +21 -21
- package/dist/tasking-eligibility.d.ts.map +1 -1
- package/dist/tasking-eligibility.js +10 -10
- package/dist/tasking-lock.d.ts +8 -8
- package/dist/tasking-lock.d.ts.map +1 -1
- package/dist/tasking-lock.js +20 -21
- package/dist/tasking-lock.js.map +1 -1
- package/dist/tasking.d.ts +33 -33
- package/dist/tasking.d.ts.map +1 -1
- package/dist/tasking.js +88 -86
- package/dist/tasking.js.map +1 -1
- package/dist/triage-gate.d.ts +1 -1
- package/dist/triage-persist.d.ts +5 -5
- package/dist/triage-persist.js +15 -15
- package/dist/triage-persist.js.map +1 -1
- package/dist/verify-workflow-template.d.ts +1 -1
- package/dist/verify-workflow-template.js +2 -2
- package/dist/work-layout.d.ts +9 -7
- package/dist/work-layout.d.ts.map +1 -1
- package/dist/work-layout.js +9 -7
- package/dist/work-layout.js.map +1 -1
- package/dist/workspace.d.ts +1 -1
- package/package.json +1 -1
- package/src/advance-ci-template.ts +4 -4
- package/src/advance-classify.ts +5 -5
- package/src/advance-drivers.ts +10 -10
- package/src/advance-isolated.ts +3 -3
- package/src/advance-lifecycle-template.ts +9 -9
- package/src/advance-loop-driver.ts +3 -3
- package/src/advance-treeless-publish.ts +1 -1
- package/src/advance.ts +30 -30
- package/src/advancing-lock.ts +6 -6
- package/src/apply-decide.ts +2 -2
- package/src/apply-merge-action.ts +5 -5
- package/src/apply-persist.ts +8 -8
- package/src/buildable-body.ts +14 -14
- package/src/claim-cas.ts +4 -4
- package/src/cli.ts +83 -83
- package/src/close-job-template.ts +8 -8
- package/src/close-job.ts +26 -26
- package/src/complete.ts +11 -11
- package/src/concurrency.ts +1 -1
- package/src/config.ts +37 -37
- package/src/continue-branch.ts +1 -1
- package/src/cwd-section.ts +1 -1
- package/src/decision-engine.ts +3 -3
- package/src/do-autopick.ts +9 -9
- package/src/do-config.ts +6 -6
- package/src/do-remote-auto.ts +2 -2
- package/src/do.ts +47 -47
- package/src/drop-source.ts +2 -2
- package/src/env-config.ts +8 -8
- package/src/format.ts +3 -3
- package/src/frontmatter.ts +23 -33
- package/src/install-ci-branch-protection.ts +1 -1
- package/src/install-ci-capabilities/advance-lifecycle.ts +1 -1
- package/src/install-ci-capabilities/close-job.ts +1 -1
- package/src/install-ci-capabilities/example-noop.ts +1 -1
- package/src/install-ci-capabilities/intake.ts +2 -2
- package/src/install-ci-capabilities/verify.ts +1 -1
- package/src/install-ci-core.ts +4 -4
- package/src/install-ci-github.ts +1 -1
- package/src/install-ci.ts +4 -4
- package/src/intake-event.ts +6 -6
- package/src/intake-marker.ts +3 -3
- package/src/intake-triage.ts +2 -2
- package/src/intake-trigger-template.ts +17 -17
- package/src/intake.ts +97 -97
- package/src/integration-core.ts +35 -35
- package/src/isolation.ts +3 -3
- package/src/issue-provider.ts +4 -4
- package/src/item-lock.ts +21 -21
- package/src/item-path.ts +2 -2
- package/src/ledger-lint.ts +9 -9
- package/src/ledger-read.ts +81 -81
- package/src/ledger-write.ts +3 -3
- package/src/lifecycle-gather.ts +16 -16
- package/src/lifecycle-pools.ts +4 -4
- package/src/merge-question-surfacer.ts +4 -4
- package/src/mint-adr.ts +4 -4
- package/src/mirror-pool-scan.ts +5 -5
- package/src/needs-attention.ts +22 -22
- package/src/orphan-sidecar.ts +2 -2
- package/src/placement.ts +6 -6
- package/src/prompt.ts +20 -25
- package/src/readiness.ts +1 -1
- package/src/recover-isolated.ts +1 -1
- package/src/repo-config.ts +12 -12
- package/src/review-gate.ts +12 -11
- package/src/review-verdict.ts +2 -2
- package/src/run.ts +5 -5
- package/src/scan.ts +15 -15
- package/src/select-order.ts +1 -1
- package/src/select-priority.ts +13 -13
- package/src/sidecar.ts +3 -3
- package/src/slug-namespace.ts +3 -3
- package/src/spec-complete.ts +2 -2
- package/src/start.ts +4 -4
- package/src/status.ts +7 -7
- package/src/surface-gate.ts +2 -2
- package/src/surface-persist.ts +2 -2
- package/src/tasker-review-loop.ts +15 -15
- package/src/tasking-eligibility.ts +21 -21
- package/src/tasking-lock.ts +27 -28
- package/src/tasking.ts +123 -121
- package/src/triage-gate.ts +1 -1
- package/src/triage-persist.ts +16 -16
- package/src/verify-workflow-template.ts +2 -2
- package/src/work-layout.ts +9 -7
- package/src/workspace.ts +1 -1
package/src/needs-attention.ts
CHANGED
|
@@ -30,7 +30,7 @@ import {
|
|
|
30
30
|
|
|
31
31
|
/**
|
|
32
32
|
* The **needs-attention mechanism** (ADR `ledger-status-on-per-item-lock-refs`;
|
|
33
|
-
*
|
|
33
|
+
* spec `ledger-status-per-item-lock-refs`; ADR §12 for the original folder model).
|
|
34
34
|
* Every "couldn't finish, a human must look" outcome (a failed acceptance gate
|
|
35
35
|
* (red `verify`), a rebase/merge conflict (ADR §10), a task the agent reported
|
|
36
36
|
* too ambiguous to build, a timeout, or a rejected review) resolves to ONE
|
|
@@ -81,7 +81,7 @@ export interface RouteToNeedsAttentionOptions {
|
|
|
81
81
|
/**
|
|
82
82
|
* The work branch to push to the arbiter (the RECOVERABLE half — see the seam
|
|
83
83
|
* docstring). DEFAULT `work/<slug>`: the build-bounce branch the wip/move
|
|
84
|
-
* commits landed on. A tasking bounce passes its own branch (`work/
|
|
84
|
+
* commits landed on. A tasking bounce passes its own branch (`work/specs/
|
|
85
85
|
* ready-<slug>`). The supplied branch MUST be the one HEAD is on (the branch the
|
|
86
86
|
* wip/move commits landed on) — NEVER a default that differs from HEAD; a
|
|
87
87
|
* caller NOT checked out on the work branch (e.g. a temp branch off main) must
|
|
@@ -259,7 +259,7 @@ export interface SurfaceToNeedsAttentionResult {
|
|
|
259
259
|
* (an unreachable arbiter leaves the local branch standing — recovery
|
|
260
260
|
* degrades, never crashes the bounce; retried with bounded backoff on an
|
|
261
261
|
* outage), BRANCH-PARAMETERISED (default `work/<slug>`; an explicit `branch`
|
|
262
|
-
* overrides — the tasking bounce passes `work/
|
|
262
|
+
* overrides — the tasking bounce passes `work/specs/ready-<slug>`; `pushBranch: false`
|
|
263
263
|
* ⇒ push NOTHING), and EMPTINESS-GUARDED (a branch with no commits beyond
|
|
264
264
|
* main, or an absent branch, is skipped). The branch MUST be the one HEAD is
|
|
265
265
|
* on. The work-branch push is NOT a `main` write.
|
|
@@ -316,7 +316,7 @@ export async function routeToNeedsAttention(
|
|
|
316
316
|
let pushError: string | undefined;
|
|
317
317
|
if (options.arbiter && options.pushBranch !== false) {
|
|
318
318
|
// DEFAULT to the task-namespaced build-bounce branch; a non-task caller
|
|
319
|
-
// (the tasking bounce) passes its own `work/
|
|
319
|
+
// (the tasking bounce) passes its own `work/specs/ready-<slug>` via `branch`.
|
|
320
320
|
const branch = options.branch ?? workBranchRef('task', slug);
|
|
321
321
|
if (branchAheadOf(cwd, branch, 'main', env)) {
|
|
322
322
|
const arbiter = options.arbiter;
|
|
@@ -652,7 +652,7 @@ export async function returnToBacklog(
|
|
|
652
652
|
}
|
|
653
653
|
|
|
654
654
|
/**
|
|
655
|
-
* **Promote a STAGED task into the agent-eligible pool** (
|
|
655
|
+
* **Promote a STAGED task into the agent-eligible pool** (spec
|
|
656
656
|
* `staging-pool-position-gate-and-trust-model`, task
|
|
657
657
|
* `pre-backlog-staging-folder-and-promote-step-a`, governing ADR
|
|
658
658
|
* `placement-is-runner-deterministic-humanonly-is-agent-judgement`). Moves
|
|
@@ -733,7 +733,7 @@ export async function promoteFromPreBacklog(
|
|
|
733
733
|
// arbiter's TRUTH. A fetch, not a checkout — the working tree is untouched.
|
|
734
734
|
await gitSoftAsync(['fetch', '--quiet', arbiter], cwd, env);
|
|
735
735
|
|
|
736
|
-
// UNIFIED PER-ITEM LOCK around the CAS window (
|
|
736
|
+
// UNIFIED PER-ITEM LOCK around the CAS window (spec
|
|
737
737
|
// `staging-surface-and-apply-promote-safety`, task
|
|
738
738
|
// `f3b-promote-takes-per-item-advancing-lock`): promote and apply BOTH key onto
|
|
739
739
|
// the item's `refs/dorfl/lock/<entry>` ref with `action: advance` (the
|
|
@@ -850,34 +850,34 @@ export async function promoteFromPreBacklog(
|
|
|
850
850
|
}
|
|
851
851
|
|
|
852
852
|
/**
|
|
853
|
-
* **Promote a STAGED
|
|
853
|
+
* **Promote a STAGED spec into the auto-task pool** (spec
|
|
854
854
|
* `staging-pool-position-gate-and-trust-model`, task
|
|
855
855
|
* `pre-prd-staging-pool-split-and-untrusted-prd-placement`, governing ADR
|
|
856
|
-
* `placement-is-runner-deterministic-humanonly-is-agent-judgement`). The
|
|
856
|
+
* `placement-is-runner-deterministic-humanonly-is-agent-judgement`). The spec
|
|
857
857
|
* twin of {@link promoteFromPreBacklog}: moves
|
|
858
|
-
* `work/
|
|
858
|
+
* `work/specs/proposed/<slug>.md → work/specs/ready/<slug>.md` as a durable `main` move
|
|
859
859
|
* (tree-less CAS via {@link runTreelessLedgerMove}). After this transition
|
|
860
|
-
* the
|
|
860
|
+
* the spec is in the auto-task POOL and eligible to be auto-tasked (subject
|
|
861
861
|
* to the existing `autoTask`/`humanOnly`/`needsAnswers`/`taskedAfter` gates,
|
|
862
862
|
* which are UNCHANGED — the staging/pool split changes only WHICH folder is
|
|
863
863
|
* the auto-task pool, not the gates).
|
|
864
864
|
*
|
|
865
865
|
* **RUNNER/human-owned.** There is no agent-facing path that performs this:
|
|
866
|
-
* `intake`'s `prd` dispatch lands the
|
|
866
|
+
* `intake`'s `prd` dispatch lands the spec STAGED in `work/specs/proposed/` (the
|
|
867
867
|
* runner's deterministic placement decision), and only a runner/human
|
|
868
868
|
* invocation moves it into the pool. The agent does no git here, as
|
|
869
869
|
* everywhere; this function is not reachable from any agent surface.
|
|
870
870
|
*
|
|
871
871
|
* Storage-agnostic + tree-less, exactly like {@link promoteFromPreBacklog}:
|
|
872
872
|
* cwd index/HEAD/working tree are never touched, an arbiter remote is
|
|
873
|
-
* REQUIRED, and "not in
|
|
873
|
+
* REQUIRED, and "not in specs/proposed/" / contention-exhausted cases are returned
|
|
874
874
|
* (NEVER thrown) via `{moved: false, reasonNotMoved}` so callers branch
|
|
875
875
|
* cleanly. Idempotent: re-running after the move LANDED is a no-op success.
|
|
876
876
|
*/
|
|
877
877
|
export interface PromoteFromPreSpecOptions {
|
|
878
878
|
/** The working clone the move is originated from (origin source only; never written). */
|
|
879
879
|
cwd: string;
|
|
880
|
-
/** The slug of the staged
|
|
880
|
+
/** The slug of the staged spec to promote into the pool. */
|
|
881
881
|
slug: string;
|
|
882
882
|
/** The arbiter remote the promotion is CAS-published to. REQUIRED. */
|
|
883
883
|
arbiter: string;
|
|
@@ -888,11 +888,11 @@ export interface PromoteFromPreSpecOptions {
|
|
|
888
888
|
}
|
|
889
889
|
|
|
890
890
|
export interface PromoteFromPreSpecResult {
|
|
891
|
-
/** True iff the staged
|
|
891
|
+
/** True iff the staged spec was moved into the pool + committed. */
|
|
892
892
|
moved: boolean;
|
|
893
893
|
/** When `moved`, the committed transition message. */
|
|
894
894
|
commitMessage?: string;
|
|
895
|
-
/** When NOT moved, why (no such
|
|
895
|
+
/** When NOT moved, why (no such specs/proposed item, already in specs/ready/, contention). */
|
|
896
896
|
reasonNotMoved?: string;
|
|
897
897
|
}
|
|
898
898
|
|
|
@@ -927,14 +927,14 @@ export async function promoteFromPreSpec(
|
|
|
927
927
|
await gitSoftAsync(['fetch', '--quiet', arbiter], cwd, env);
|
|
928
928
|
|
|
929
929
|
// UNIFIED PER-ITEM LOCK around the CAS window — symmetric with
|
|
930
|
-
// {@link promoteFromPreBacklog} (
|
|
931
|
-
// task `f3b-promote-takes-per-item-advancing-lock`, decisive
|
|
930
|
+
// {@link promoteFromPreBacklog} (spec `staging-surface-and-apply-promote-safety`,
|
|
931
|
+
// task `f3b-promote-takes-per-item-advancing-lock`, decisive spec q4 answer:
|
|
932
932
|
// specs share the apply×promote mutual-exclusion fix with tasks). The lock
|
|
933
933
|
// keys on `spec:${slug}` (a distinct ref from a task with the same slug, via
|
|
934
934
|
// {@link lockEntryFor}'s `<type>-<slug>` encoding), with `action: advance` —
|
|
935
935
|
// the SAME action an apply for a spec would take — so spec promote and spec
|
|
936
936
|
// apply on the same item are mutually exclusive by construction. MIGRATE step
|
|
937
|
-
// (
|
|
937
|
+
// (spec `prd-to-spec-vocabulary-cutover-and-migration-command`): the lock
|
|
938
938
|
// identity is `spec:${slug}` to match the `spec-<slug>` entry the tasking/apply
|
|
939
939
|
// path now acquires (`tasking.ts` releases under `spec:${slug}`); a stale
|
|
940
940
|
// `prd:${slug}` here would key a DIFFERENT ref and break the mutual exclusion.
|
|
@@ -1009,7 +1009,7 @@ export async function promoteFromPreSpec(
|
|
|
1009
1009
|
base,
|
|
1010
1010
|
sourceRel,
|
|
1011
1011
|
destRel,
|
|
1012
|
-
// The body is carried byte-for-byte from
|
|
1012
|
+
// The body is carried byte-for-byte from specs/proposed into the pool —
|
|
1013
1013
|
// promotion is a placement decision, not a content transform.
|
|
1014
1014
|
transformBody: (body) => body,
|
|
1015
1015
|
commitMessage,
|
|
@@ -1020,14 +1020,14 @@ export async function promoteFromPreSpec(
|
|
|
1020
1020
|
});
|
|
1021
1021
|
if (moved) {
|
|
1022
1022
|
note(
|
|
1023
|
-
`Promoted
|
|
1023
|
+
`Promoted spec '${slug}' from specs/proposed to specs/ready (auto-taskable).`,
|
|
1024
1024
|
);
|
|
1025
1025
|
return {moved: true, commitMessage};
|
|
1026
1026
|
}
|
|
1027
1027
|
|
|
1028
1028
|
const message =
|
|
1029
1029
|
`promote for '${slug}': the arbiter's main kept moving (contended) ` +
|
|
1030
|
-
`after ${TREELESS_CONTENTION_ATTEMPTS} attempts — item left in
|
|
1030
|
+
`after ${TREELESS_CONTENTION_ATTEMPTS} attempts — item left in specs/proposed ` +
|
|
1031
1031
|
'(no move). Try again shortly.';
|
|
1032
1032
|
note(message);
|
|
1033
1033
|
return {moved: false, reasonNotMoved: message};
|
|
@@ -1062,7 +1062,7 @@ export interface ListPromotableResult {
|
|
|
1062
1062
|
|
|
1063
1063
|
/**
|
|
1064
1064
|
* LIST every staged item awaiting a runner/human promotion — the tasks in
|
|
1065
|
-
* `work/pre-backlog/` and the prds in `work/
|
|
1065
|
+
* `work/pre-backlog/` and the prds in `work/specs/proposed/` on `<arbiter>/main` (the
|
|
1066
1066
|
* discovery half of the `promote` verb, so `promote` with no argument answers
|
|
1067
1067
|
* "what is staged waiting for me?"). It reads the ARBITER's truth (a fetch + a
|
|
1068
1068
|
* tree read), NOT the local working tree (which may be stale) — the same source
|
package/src/orphan-sidecar.ts
CHANGED
|
@@ -8,12 +8,12 @@ import {workFolderPath, workFolderRel} from './work-layout.js';
|
|
|
8
8
|
/**
|
|
9
9
|
* The **orphan-sidecar reaper** — the WORKING-TREE counterpart of the job-worktree
|
|
10
10
|
* and remote-branch reapers (`gc.ts` / `reap-branches.ts`), folded into `dorfl gc`
|
|
11
|
-
* (
|
|
11
|
+
* (spec `agentic-question-resolution-retire-disposition-vocabulary`, US #10).
|
|
12
12
|
*
|
|
13
13
|
* A question sidecar is a tooling-owned file `work/questions/<type>-<slug>.md`
|
|
14
14
|
* keyed on its source item's `(type, slug)` identity (`sidecarPathFor`). The
|
|
15
15
|
* contract is that notes/sidecars leave by DELETION (git history is the archive),
|
|
16
|
-
* so when a human deletes the source observation (or task/
|
|
16
|
+
* so when a human deletes the source observation (or task/spec) out-of-band, its
|
|
17
17
|
* sidecar is ORPHANED.
|
|
18
18
|
*
|
|
19
19
|
* WHY THIS IS A SWEEP, NOT AN APPLY STEP. An orphan's source item is GONE, so it
|
package/src/placement.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* **The shared STAGING/POOL placement resolver** (
|
|
2
|
+
* **The shared STAGING/POOL placement resolver** (spec
|
|
3
3
|
* `staging-pool-position-gate-and-trust-model`, task
|
|
4
4
|
* `runner-deterministic-slice-placement-policy-and-precedence`, governing ADR
|
|
5
5
|
* `placement-is-runner-deterministic-humanonly-is-agent-judgement`).
|
|
@@ -32,18 +32,18 @@
|
|
|
32
32
|
* onto the lifecycle's concrete folder name via {@link PlacementSlots}.
|
|
33
33
|
*
|
|
34
34
|
* - `'staging'` — land in the staging area (tasks: `pre-backlog/`; prds:
|
|
35
|
-
* `
|
|
35
|
+
* `specs/proposed/`). Not in the agent pool; a human/runner promotion is needed to make
|
|
36
36
|
* the item eligible. Review-without-PR review surface.
|
|
37
37
|
* - `'pool'` — land directly in the agent-eligible pool (tasks: `tasks/ready/`;
|
|
38
|
-
* prds: `
|
|
38
|
+
* prds: `specs/ready/`). The trusted-fast-path landing.
|
|
39
39
|
*/
|
|
40
40
|
export type PlacementSide = 'staging' | 'pool';
|
|
41
41
|
|
|
42
42
|
/**
|
|
43
43
|
* The two folder names a lifecycle uses for its staging/pool split. Supplied by
|
|
44
44
|
* the caller so this resolver stays lifecycle-generic (the TASK caller passes
|
|
45
|
-
* `{staging: 'pre-backlog', pool: 'tasks/ready'}`; the
|
|
46
|
-
* `{staging: '
|
|
45
|
+
* `{staging: 'pre-backlog', pool: 'tasks/ready'}`; the SPEC-placement caller passes
|
|
46
|
+
* `{staging: 'specs/proposed', pool: 'specs/ready'}`).
|
|
47
47
|
*/
|
|
48
48
|
export interface PlacementSlots {
|
|
49
49
|
staging: string;
|
|
@@ -100,7 +100,7 @@ const BUILT_IN_FLOOR: PlacementSide = 'staging';
|
|
|
100
100
|
* explicit > untrusted-origin ⇒ staging > configured default > built-in
|
|
101
101
|
*
|
|
102
102
|
* Pure: no I/O, no env reads — the caller resolves config + reads the
|
|
103
|
-
* frontmatter and passes both in. Reused by every lifecycle (task +
|
|
103
|
+
* frontmatter and passes both in. Reused by every lifecycle (task + spec
|
|
104
104
|
* placement + future intake variants) so a precedence change touches ONE place.
|
|
105
105
|
*/
|
|
106
106
|
export function resolvePlacement(
|
package/src/prompt.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Builds the prompt the runner hands to `agentCmd`: a small CONSTANT wrapper
|
|
3
|
-
* (only the `<slug>` / source-
|
|
3
|
+
* (only the `<slug>` / source-spec path vary) around the claimed task's own
|
|
4
4
|
* `## Prompt` section. This is dual-use — the SAME assembly the autonomous
|
|
5
5
|
* runner feeds `agentCmd` and the human `dorfl prompt [<slug>]` command.
|
|
6
6
|
*
|
|
@@ -416,7 +416,7 @@ export function buildContinueBlock(slug: string, ctx: ContinueContext): string {
|
|
|
416
416
|
}
|
|
417
417
|
|
|
418
418
|
/**
|
|
419
|
-
* Build the full prompt: the canonical wrapper for `slug` (with its source
|
|
419
|
+
* Build the full prompt: the canonical wrapper for `slug` (with its source spec
|
|
420
420
|
* substituted) followed by the task's own `## Prompt` body, appended verbatim.
|
|
421
421
|
*
|
|
422
422
|
* In CONTINUE-mode (a {@link ContinueContext} is supplied), a CONTINUE block is
|
|
@@ -459,10 +459,7 @@ export interface ResolvedTask {
|
|
|
459
459
|
path: string;
|
|
460
460
|
/** The folder the task was resolved from (in-progress wins over tasks-ready). */
|
|
461
461
|
folder: TaskFolder;
|
|
462
|
-
/**
|
|
463
|
-
* The task's source SPEC slug (frontmatter `spec:`, or the legacy `prd:` key
|
|
464
|
-
* as read-only back-compat), if any.
|
|
465
|
-
*/
|
|
462
|
+
/** The task's source SPEC slug (frontmatter `spec:`), if any. */
|
|
466
463
|
spec: string | undefined;
|
|
467
464
|
/** The extracted `## Prompt` body. */
|
|
468
465
|
taskPrompt: string;
|
|
@@ -493,7 +490,7 @@ export class PromptError extends Error {}
|
|
|
493
490
|
/**
|
|
494
491
|
* The CONTINUE-only gate that lets {@link resolveTask} reach a task that has
|
|
495
492
|
* already been done-moved into `work/done/` — story 5 of the `ledger-integrity`
|
|
496
|
-
*
|
|
493
|
+
* spec (defect 3). A continue/re-claim can legitimately land on a branch whose
|
|
497
494
|
* task was ALREADY moved to `done/` (the green-but-unpushed STRAND state), and
|
|
498
495
|
* onboard must find it; but a `done/` task is folder-indistinguishable between
|
|
499
496
|
* two states and re-onboarding a genuinely-finished one would RE-RUN it. So
|
|
@@ -533,7 +530,7 @@ export interface ContinueResolutionGate {
|
|
|
533
530
|
|
|
534
531
|
/**
|
|
535
532
|
* Extra knobs for {@link resolveTask} beyond the continue gate. Today the only
|
|
536
|
-
* member is `allowBacklog` (
|
|
533
|
+
* member is `allowBacklog` (spec
|
|
537
534
|
* `do-allow-backlog-drive-staged-tasks-without-promotion`): the operator's
|
|
538
535
|
* EXPLICIT `do … --allow-backlog`, which widens resolution to also search
|
|
539
536
|
* `tasks-backlog` (staging) at LOWEST priority. Default off (omitted) \u21d2 the
|
|
@@ -574,7 +571,7 @@ function isStrandedDoneTip(gate: ContinueResolutionGate): boolean {
|
|
|
574
571
|
|
|
575
572
|
/**
|
|
576
573
|
* Resolve a task's file: prefer `work/in-progress/<slug>.md`, fall back to
|
|
577
|
-
* `work/tasks/ready/<slug>.md` (the pool). Returns the parsed
|
|
574
|
+
* `work/tasks/ready/<slug>.md` (the pool). Returns the parsed spec + extracted
|
|
578
575
|
* `## Prompt` body. Throws {@link PromptError} when neither file exists or it has
|
|
579
576
|
* no prompt body.
|
|
580
577
|
*
|
|
@@ -588,11 +585,11 @@ function isStrandedDoneTip(gate: ContinueResolutionGate): boolean {
|
|
|
588
585
|
* the only addition, and it is gated. With no gate (a fresh claim) the behaviour
|
|
589
586
|
* is byte-identical to the original `['in-progress','tasks-ready']`-only resolution.
|
|
590
587
|
*
|
|
591
|
-
* `--allow-backlog` (
|
|
588
|
+
* `--allow-backlog` (spec `do-allow-backlog-drive-staged-tasks-without-promotion`):
|
|
592
589
|
* when {@link ResolveTaskOptions.allowBacklog} is set, `tasks-backlog` (the staging
|
|
593
590
|
* folder) is appended at the LOWEST priority — after `tasks-ready`, so a slug
|
|
594
591
|
* present in BOTH the pool and staging resolves to the READY copy (the same-slug
|
|
595
|
-
* precedence the
|
|
592
|
+
* precedence the spec's decision 5 fixes). Default off ⇒ byte-identical to today
|
|
596
593
|
* (no autonomous path sets it; staging stays unreachable to `run`/auto-pick).
|
|
597
594
|
*/
|
|
598
595
|
export function resolveTask(
|
|
@@ -627,9 +624,8 @@ export function resolveTask(
|
|
|
627
624
|
);
|
|
628
625
|
}
|
|
629
626
|
const fm = parseFrontmatter(content);
|
|
630
|
-
// Read the parent-spec pointer off `fm.spec` (populated from
|
|
631
|
-
//
|
|
632
|
-
// `spec`-only `ResolvedTask` (spec
|
|
627
|
+
// Read the parent-spec pointer off `fm.spec` (populated from the canonical
|
|
628
|
+
// `spec:` key) into the `spec`-only `ResolvedTask` (spec
|
|
633
629
|
// `prd-to-spec-vocabulary-cutover-and-migration-command`).
|
|
634
630
|
return {slug, path, folder, spec: fm.spec, taskPrompt};
|
|
635
631
|
}
|
|
@@ -665,13 +661,13 @@ export function inferSlugFromBranch(
|
|
|
665
661
|
*/
|
|
666
662
|
/**
|
|
667
663
|
* Resolve the EFFECTIVE `promptGuidance` for an item by walking the precedence
|
|
668
|
-
* chain (highest → lowest): the per-task frontmatter override, the per-
|
|
669
|
-
* frontmatter override (only when the task carries a `
|
|
664
|
+
* chain (highest → lowest): the per-task frontmatter override, the per-spec
|
|
665
|
+
* frontmatter override (only when the task carries a `spec:`), then the
|
|
670
666
|
* already-resolved repo policy. Each nudge member resolves independently — a
|
|
671
667
|
* task's `promptGuidance.testFirst` override never bleeds into a sibling
|
|
672
668
|
* member — mirroring the `humanOnly`/`autoBuild` per-item override shape.
|
|
673
669
|
*
|
|
674
|
-
* A task may carry the override even when it has NO `
|
|
670
|
+
* A task may carry the override even when it has NO `spec:` (a self-contained
|
|
675
671
|
* chore), by symmetry with `humanOnly` at the item level; `specFrontmatter`
|
|
676
672
|
* is then simply absent and the chain reads task ⇒ repo.
|
|
677
673
|
*/
|
|
@@ -688,11 +684,11 @@ export function resolveItemPromptGuidance(
|
|
|
688
684
|
}
|
|
689
685
|
|
|
690
686
|
/**
|
|
691
|
-
* Locate a
|
|
692
|
-
* auto-slice pool), then fall back to `work/
|
|
687
|
+
* Locate a spec's file on disk: prefer `work/specs/ready/<slug>.md` (the
|
|
688
|
+
* auto-slice pool), then fall back to `work/specs/tasked/<slug>.md` (tasked,
|
|
693
689
|
* resting). Returns `undefined` when neither exists — the caller treats that
|
|
694
|
-
* as "no
|
|
695
|
-
* through to the repo policy (a missing
|
|
690
|
+
* as "no spec-level override available" and the precedence chain falls
|
|
691
|
+
* through to the repo policy (a missing spec is NOT an error at this seam;
|
|
696
692
|
* the per-item override is OPTIONAL by design).
|
|
697
693
|
*/
|
|
698
694
|
export function findSpecPath(
|
|
@@ -714,7 +710,7 @@ export function findSpecPath(
|
|
|
714
710
|
/**
|
|
715
711
|
* The convenience seam every caller of {@link buildAgentPrompt} reuses to
|
|
716
712
|
* resolve the per-item override: load the task frontmatter from its file +
|
|
717
|
-
* (when the task carries `
|
|
713
|
+
* (when the task carries `spec:`) the spec frontmatter, then walk
|
|
718
714
|
* {@link resolveItemPromptGuidance}. Pure-ish (reads at most two files);
|
|
719
715
|
* returns the repo policy verbatim when neither item layer overrides anything.
|
|
720
716
|
*/
|
|
@@ -725,8 +721,7 @@ export function resolvePromptGuidanceForItem(options: {
|
|
|
725
721
|
}): PromptGuidance {
|
|
726
722
|
const taskFm = parseFrontmatter(options.taskContent);
|
|
727
723
|
let specFm: Frontmatter | undefined;
|
|
728
|
-
// Read the parent-spec pointer off `fm.spec` (populated from the `spec:` key
|
|
729
|
-
// the legacy `prd:` back-compat alias).
|
|
724
|
+
// Read the parent-spec pointer off `fm.spec` (populated from the `spec:` key).
|
|
730
725
|
if (taskFm.spec !== undefined) {
|
|
731
726
|
const specPath = findSpecPath(options.cwd, taskFm.spec);
|
|
732
727
|
if (specPath !== undefined) {
|
|
@@ -745,7 +740,7 @@ export function renderPrompt(options: PromptOptions): string {
|
|
|
745
740
|
);
|
|
746
741
|
}
|
|
747
742
|
const task = resolveTask(options.cwd, slug);
|
|
748
|
-
// Per-item override layer: a task or
|
|
743
|
+
// Per-item override layer: a task or spec may pin `promptGuidance.testFirst`
|
|
749
744
|
// in its frontmatter, superseding the resolved repo policy for THIS item.
|
|
750
745
|
// We ALWAYS walk the resolver (even when no repo policy was threaded), so a
|
|
751
746
|
// task can opt IN to the strengthened nudge even on a repo whose default is
|
package/src/readiness.ts
CHANGED
|
@@ -16,7 +16,7 @@ import {ledgerRead} from './ledger-read.js';
|
|
|
16
16
|
* the shared {@link resolveBlockedBy} (no reimplemented dep resolution).
|
|
17
17
|
*
|
|
18
18
|
* The two axes are deliberately treated differently (see WORK-CONTRACT and the
|
|
19
|
-
* task
|
|
19
|
+
* task spec):
|
|
20
20
|
*
|
|
21
21
|
* - `blockedBy` unmet is a FACTUAL prerequisite (the dep work does not exist
|
|
22
22
|
* yet) → REFUSE by default. An override flag is the human escape hatch.
|
package/src/recover-isolated.ts
CHANGED
|
@@ -11,7 +11,7 @@ import type {ReviewProvider} from './integrator.js';
|
|
|
11
11
|
|
|
12
12
|
/**
|
|
13
13
|
* **`complete --isolated <slug>` — FINISH an already-committed, already-done-moved
|
|
14
|
-
* STRANDED isolated worktree** (
|
|
14
|
+
* STRANDED isolated worktree** (spec `ledger-integrity` story 6, the
|
|
15
15
|
* `finish-already-committed-branch` task). The LOCATE-EXISTING inverse of
|
|
16
16
|
* `do --isolated` (which CREATES a worktree): it resolves the slug's RETAINED job
|
|
17
17
|
* worktree via the existing arbiter-URL-keyed naming
|
package/src/repo-config.ts
CHANGED
|
@@ -61,16 +61,16 @@ export const REPO_CONFIG_FILENAME = brand.repoConfigFilename;
|
|
|
61
61
|
*/
|
|
62
62
|
export const REPO_ALLOWED_KEYS = [
|
|
63
63
|
'integration',
|
|
64
|
-
// `taskingIntegration` (the per-TRANSITION override for the
|
|
64
|
+
// `taskingIntegration` (the per-TRANSITION override for the spec→tasks TASKING
|
|
65
65
|
// transition ONLY) is a genuine repo property exactly like `integration`: whether
|
|
66
|
-
// THIS repo tasks a
|
|
66
|
+
// THIS repo tasks a spec straight onto `main` (task FILES land, no PR) while it
|
|
67
67
|
// still BUILDS each task as a reviewable PR is agreed by all collaborators +
|
|
68
68
|
// travels with the repo. Resolved per-repo through the SAME chain as
|
|
69
69
|
// `integration`, then falls back to `integration` when unset. DISTINCT from
|
|
70
70
|
// intake's per-EMITTED-TYPE `{task, prd}` resolver (front door, author-trust):
|
|
71
71
|
// this is a per-lifecycle-transition knob, inside the boundary, config-resolved.
|
|
72
72
|
'taskingIntegration',
|
|
73
|
-
// `tasksLandIn` (the per-repo TASK-PLACEMENT default — staging vs pool,
|
|
73
|
+
// `tasksLandIn` (the per-repo TASK-PLACEMENT default — staging vs pool, spec
|
|
74
74
|
// `staging-pool-position-gate-and-trust-model` US #5) is a genuine repo property
|
|
75
75
|
// exactly like `taskingIntegration`/`integration`: whether THIS repo's tasker
|
|
76
76
|
// output lands STAGED (`pre-backlog/`, review-without-PR human-promote path) or
|
|
@@ -91,7 +91,7 @@ export const REPO_ALLOWED_KEYS = [
|
|
|
91
91
|
// through the SAME chain as `tasksLandIn` (flag `--specs-land-in` > env
|
|
92
92
|
// `DORFL_SPECS_LAND_IN` > per-repo > global > built-in). Fed into the shared
|
|
93
93
|
// placement resolver as the configured-default rung for the spec lifecycle
|
|
94
|
-
// (`src/placement.ts`). The sole spec-placement key after the prd → spec HARD
|
|
94
|
+
// (`src/placement.ts`). The sole spec-placement key after the `prd` → `spec` HARD
|
|
95
95
|
// CUTOVER (the legacy `prdsLandIn` key is GONE — clean break, no accepted alias).
|
|
96
96
|
'specsLandIn',
|
|
97
97
|
// `noPR` (the PR-INTENT axis — push the branch but deliberately skip the PR) is
|
|
@@ -116,7 +116,7 @@ export const REPO_ALLOWED_KEYS = [
|
|
|
116
116
|
'autoBuild',
|
|
117
117
|
// `autoTask` (may an agent auto-task undeclared prds in this repo?) is a
|
|
118
118
|
// genuine repo property — the tasking-autonomy mirror of `autoBuild`
|
|
119
|
-
// (`work/
|
|
119
|
+
// (`work/specs/auto-task.md`), resolved per-repo through the same chain.
|
|
120
120
|
'autoTask',
|
|
121
121
|
// `observationTriage` (the 3-state `off|ask|auto` gate over the observation
|
|
122
122
|
// INBOX) is a genuine repo property — the observation-side question-surfacing
|
|
@@ -125,7 +125,7 @@ export const REPO_ALLOWED_KEYS = [
|
|
|
125
125
|
// boolean (no alias; no external users owed a migration window, 2026-06-12).
|
|
126
126
|
'observationTriage',
|
|
127
127
|
// `mergeQuestions` (the 3-state `off|ask|auto` gate over the MERGE-QUESTION
|
|
128
|
-
// SURFACER —
|
|
128
|
+
// SURFACER — spec `land-time-reverify-and-parallel-merge-ceiling` Story 17 /
|
|
129
129
|
// task `merge-questions-gate-axis`) is a genuine repo property exactly like
|
|
130
130
|
// `observationTriage`: whether THIS repo's unmerged `work/*` branches surface
|
|
131
131
|
// as merge-questions (and whether they auto-land) is agreed by all
|
|
@@ -136,13 +136,13 @@ export const REPO_ALLOWED_KEYS = [
|
|
|
136
136
|
// (flag > env > per-repo > global > default `ask`).
|
|
137
137
|
'mergeQuestions',
|
|
138
138
|
// `surfaceBlockers` (the BOOLEAN gate over DECLARED blocked work — whether a
|
|
139
|
-
// task/
|
|
139
|
+
// task/spec carrying `needsAnswers:true` is rendered into a question sidecar) is a
|
|
140
140
|
// genuine repo property — the blocked-work side of the question-surfacing gate
|
|
141
141
|
// family (ADR `ci-config-policy-and-gate-family`), the orthogonal peer of
|
|
142
142
|
// `observationTriage`, resolved per-repo through the same chain as `autoBuild`.
|
|
143
143
|
'surfaceBlockers',
|
|
144
144
|
// `surfaceStaging` (the BOOLEAN gate-family member that widens SURFACE into
|
|
145
|
-
// STAGING —
|
|
145
|
+
// STAGING — spec `staging-surface-and-apply-promote-safety` F2) is a genuine
|
|
146
146
|
// repo property exactly like its siblings (`surfaceBlockers`/`autoBuild`):
|
|
147
147
|
// whether THIS repo inspects staging for questions is agreed by all
|
|
148
148
|
// collaborators + travels with the repo. Default `true`; resolved per-repo
|
|
@@ -161,8 +161,8 @@ export const REPO_ALLOWED_KEYS = [
|
|
|
161
161
|
// (machine paths/commands), so they are rejected below.
|
|
162
162
|
'model',
|
|
163
163
|
'harness',
|
|
164
|
-
// Gate 2 (PR/code review) policy is a genuine repo property (GATES
|
|
165
|
-
// `work/
|
|
164
|
+
// Gate 2 (PR/code review) policy is a genuine repo property (GATES spec
|
|
165
|
+
// `work/specs/tasked/review.md`), resolved per-repo like `integration`/`autoBuild`:
|
|
166
166
|
// whether this repo runs Gate 2 (`review`), which model the review agent runs
|
|
167
167
|
// on (`reviewModel`), and the revise↔review loop bound (`reviewMaxRounds`).
|
|
168
168
|
// `reviewModel` is routing intent (not auth), so — like `model` — it is
|
|
@@ -185,7 +185,7 @@ export const REPO_ALLOWED_KEYS = [
|
|
|
185
185
|
// artifact (and pays the per-gate install cost) is agreed by all collaborators
|
|
186
186
|
// + travels with the repo. Resolved per-repo through the SAME chain.
|
|
187
187
|
'freshWorktreeGate',
|
|
188
|
-
// `mergeRetries` (the cross-job merge serialiser's CAS-retry cap —
|
|
188
|
+
// `mergeRetries` (the cross-job merge serialiser's CAS-retry cap — spec
|
|
189
189
|
// `land-time-reverify-and-parallel-merge-ceiling` Story 5 / Applied Answer q1 (a))
|
|
190
190
|
// is a genuine repo property exactly like `freshWorktreeGate`: "how many
|
|
191
191
|
// re-rebase-and-retry attempts before a contender bounces to needs-attention"
|
|
@@ -195,7 +195,7 @@ export const REPO_ALLOWED_KEYS = [
|
|
|
195
195
|
// CAS still costs only a re-rebase + re-gate retry, never a `--force`.
|
|
196
196
|
'mergeRetries',
|
|
197
197
|
// `strictMergeApproval` (the OPT-IN strictness layered on the OQ6
|
|
198
|
-
// stale-approval default —
|
|
198
|
+
// stale-approval default — spec `land-time-reverify-and-parallel-merge-ceiling`
|
|
199
199
|
// sidecar OQ6 / task `strict-merge-approval-gate`) is a genuine repo property
|
|
200
200
|
// exactly like `mergeQuestions`/`mergeRetries`: whether THIS repo re-surfaces
|
|
201
201
|
// the merge-question on a merge-base change (the host-agnostic analogue of
|
package/src/review-gate.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import {NullHarness, substituteModel, type Harness} from './harness.js';
|
|
2
2
|
import {launchWithOptionalWatch} from './agent-launch.js';
|
|
3
3
|
import {boundaryLine} from './watch-session.js';
|
|
4
|
+
import {workItemRel} from './work-layout.js';
|
|
4
5
|
import {
|
|
5
6
|
parseReviewVerdict,
|
|
6
7
|
ReviewParseError,
|
|
@@ -18,7 +19,7 @@ export {
|
|
|
18
19
|
} from './review-verdict.js';
|
|
19
20
|
|
|
20
21
|
/**
|
|
21
|
-
* **Gate 2 — the PR/code review gate** (GATES
|
|
22
|
+
* **Gate 2 — the PR/code review gate** (GATES spec `work/specs/tasked/review.md`), the
|
|
22
23
|
* JUDGEMENT layer that rides ON TOP of the deterministic `verify` floor (ADR §8).
|
|
23
24
|
*
|
|
24
25
|
* After the green `verify` and BEFORE the done-move, `complete`/`do` invoke the
|
|
@@ -110,7 +111,7 @@ export function buildReviewPrompt(slug: string): string {
|
|
|
110
111
|
return [
|
|
111
112
|
`You are a FRESH-CONTEXT reviewer (Gate 2 — PR/code review). Review the`,
|
|
112
113
|
`code changes on this work branch AGAINST the task that specified them`,
|
|
113
|
-
`(work/in-progress/${slug}.md or work/done/${slug}.md) and its source
|
|
114
|
+
`(work/in-progress/${slug}.md or work/done/${slug}.md) and its source spec.`,
|
|
114
115
|
``,
|
|
115
116
|
reviewDisciplinePrompt(),
|
|
116
117
|
``,
|
|
@@ -150,7 +151,7 @@ export function buildReviewPrompt(slug: string): string {
|
|
|
150
151
|
`comment on the PR — write it FOR a human landing there, NOT as scratch`,
|
|
151
152
|
`thinking. LEAD with the verdict ("Approved" or "Blocked") and then give the`,
|
|
152
153
|
`lenses' reasoning and the destination check ("merged as written, do we reach`,
|
|
153
|
-
`the task/
|
|
154
|
+
`the task/spec goal?"). Write it deliberately; do NOT narrate your process`,
|
|
154
155
|
`("Let me check…"). Keep it TIGHT: aim for a few short sentences and DO NOT`,
|
|
155
156
|
`exceed ~1500 characters — a long, multi-paragraph field is exactly what`,
|
|
156
157
|
`corrupts the JSON on large diffs; say less, not more. It is plain text inside`,
|
|
@@ -247,10 +248,10 @@ export function harnessReviewGate(
|
|
|
247
248
|
* Render the TASK-SET acceptance-gate PROMPT — the task-path mirror of
|
|
248
249
|
* {@link buildReviewPrompt} (task `slice-acceptance-gate`). Instead of
|
|
249
250
|
* reviewing a code diff against ONE task, this instructs a FRESH-CONTEXT
|
|
250
|
-
* agent to review the WHOLE candidate SET of tasks produced for
|
|
251
|
+
* agent to review the WHOLE candidate SET of tasks produced for spec `slug`,
|
|
251
252
|
* using the **review discipline**'s SET-OF-TASKS lens (coherence / dependency
|
|
252
253
|
* graph / gaps + overlap / "if every task is built exactly as written, do we
|
|
253
|
-
* reach the system the
|
|
254
|
+
* reach the system the spec describes, and is each task
|
|
254
255
|
* correct-if-implemented?"). It emits the SAME unified `ReviewVerdict` shape
|
|
255
256
|
* so {@link parseReviewVerdict} reads it identically.
|
|
256
257
|
*
|
|
@@ -265,24 +266,24 @@ export function harnessReviewGate(
|
|
|
265
266
|
export function buildTaskAcceptancePrompt(slug: string): string {
|
|
266
267
|
return [
|
|
267
268
|
`You are a FRESH-CONTEXT reviewer (the task-SET ACCEPTANCE GATE). Review`,
|
|
268
|
-
`the candidate tasks this tasking run produced for the
|
|
269
|
+
`the candidate tasks this tasking run produced for the spec "${slug}" — the`,
|
|
269
270
|
`new/changed candidate task files on this work branch — AGAINST their source`,
|
|
270
|
-
`
|
|
271
|
+
`spec (${workItemRel('specs-ready', `${slug}.md`)} — the held spec stays in specs/ready/ while it is being`,
|
|
271
272
|
`tasked).`,
|
|
272
273
|
``,
|
|
273
274
|
reviewDisciplinePrompt(),
|
|
274
275
|
``,
|
|
275
276
|
`Review the WHOLE SET as a SET, not each task in isolation. The set-level`,
|
|
276
277
|
`framings the review discipline names:`,
|
|
277
|
-
` - COHERENCE — do the tasks speak the
|
|
278
|
-
` consistently; no task re-means or forks a concept another task/the
|
|
278
|
+
` - COHERENCE — do the tasks speak the spec's (and the system's) language`,
|
|
279
|
+
` consistently; no task re-means or forks a concept another task/the spec`,
|
|
279
280
|
` already owns?`,
|
|
280
281
|
` - DEPENDENCY GRAPH — is the \`blockedBy\`/ordering graph sound (acyclic, the`,
|
|
281
282
|
` keystone first, each task's stated blockers really land its premise)?`,
|
|
282
|
-
` - GAPS + OVERLAP — does the set COVER the
|
|
283
|
+
` - GAPS + OVERLAP — does the set COVER the spec with no missing piece, and`,
|
|
283
284
|
` without two tasks doing the same work or fighting over the same seam?`,
|
|
284
285
|
` - CORRECT-IF-IMPLEMENTED — if EVERY task is built EXACTLY as written, do we`,
|
|
285
|
-
` reach the system the
|
|
286
|
+
` reach the system the spec describes, and is each task individually`,
|
|
286
287
|
` correct-if-implemented (no task that compiles but builds the wrong thing)?`,
|
|
287
288
|
``,
|
|
288
289
|
`This is a TERMINAL one-shot accept/reject gate: do NOT edit any task, do NOT`,
|
package/src/review-verdict.ts
CHANGED
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
* (`work/protocol/REVIEW-PROTOCOL.md`, source-of-truth
|
|
5
5
|
* `skills/setup/protocol/REVIEW-PROTOCOL.md`).
|
|
6
6
|
*
|
|
7
|
-
* This is the keystone of the `runner-invoked-disciplines-into-protocol`
|
|
7
|
+
* This is the keystone of the `runner-invoked-disciplines-into-protocol` spec
|
|
8
8
|
* (task 1, D4): every runner-invoked review prompt builder
|
|
9
9
|
* ({@link buildReviewPrompt}, {@link buildTaskAcceptancePrompt} in
|
|
10
10
|
* `review-gate.ts`; {@link buildLoneTaskReviewPrompt} in `intake.ts`;
|
|
@@ -84,7 +84,7 @@ export interface ReviewVerdict {
|
|
|
84
84
|
questions?: string[];
|
|
85
85
|
/** For the tasker improver loop: specific tasks to emit `needsAnswers: true`. */
|
|
86
86
|
uncertainTasks?: UncertainTask[];
|
|
87
|
-
/** For the tasker improver loop: route the WHOLE
|
|
87
|
+
/** For the tasker improver loop: route the WHOLE spec to needs-attention. */
|
|
88
88
|
decompositionUnclear?: {questions: string[]};
|
|
89
89
|
}
|
|
90
90
|
|
package/src/run.ts
CHANGED
|
@@ -765,7 +765,7 @@ async function runOneItem(
|
|
|
765
765
|
}
|
|
766
766
|
|
|
767
767
|
// 3. Build the prompt — the SAME dual-use assembly `dorfl prompt`
|
|
768
|
-
// emits: the canonical wrapper (+ source
|
|
768
|
+
// emits: the canonical wrapper (+ source spec) + the task's ## Prompt.
|
|
769
769
|
let prompt: string;
|
|
770
770
|
try {
|
|
771
771
|
// CONTINUE-aware resolution: only on a continue (the job continued a kept
|
|
@@ -801,7 +801,7 @@ async function runOneItem(
|
|
|
801
801
|
})
|
|
802
802
|
: undefined;
|
|
803
803
|
// Thread the resolved per-repo nudge through the per-item override layer
|
|
804
|
-
// (a task or
|
|
804
|
+
// (a task or spec may pin `promptGuidance.testFirst` in its frontmatter,
|
|
805
805
|
// superseding the repo policy for THIS item) before the wrapper is built.
|
|
806
806
|
const itemGuidance = resolvePromptGuidanceForItem({
|
|
807
807
|
cwd: tree.dir,
|
|
@@ -879,7 +879,7 @@ async function runOneItem(
|
|
|
879
879
|
// 5–7 (CONVERGED). The whole gate → review → done-move → commit → rebase →
|
|
880
880
|
// integrate band — plus the needs-attention routing on any failure — now runs
|
|
881
881
|
// through the SHARED `performIntegration` core (`integration-core.ts`, the
|
|
882
|
-
// run/do convergence
|
|
882
|
+
// run/do convergence spec). `run` no longer forks its own gate / done-move /
|
|
883
883
|
// completion commit / `Integrator`+`integrateWithRebase`: that closed all
|
|
884
884
|
// three drift instances at once (the fleet now gets the review gate, the PR
|
|
885
885
|
// title/body, AND the per-repo language-agnostic `verify` gate instead of the
|
|
@@ -954,7 +954,7 @@ async function runOneItem(
|
|
|
954
954
|
// (`do`/`--isolated`/`--remote`/`complete`) already pass it unconditionally.
|
|
955
955
|
freshWorktreeGate: config.freshWorktreeGate,
|
|
956
956
|
// The cross-job merge-serialiser CAS-retry cap (config `mergeRetries`) —
|
|
957
|
-
// the git-alone FLOOR of the cross-job land queue (
|
|
957
|
+
// the git-alone FLOOR of the cross-job land queue (spec `land-time-reverify-
|
|
958
958
|
// and-parallel-merge-ceiling` Story 5 / Applied Answer q1 (a)). Threaded
|
|
959
959
|
// from the per-repo resolved config so a wide-matrix CI's raised cap actually
|
|
960
960
|
// reaches the merge loop — across separate `run` fleet jobs the CAS loop IS
|
|
@@ -1262,7 +1262,7 @@ export function defaultRunWorkspace(): string {
|
|
|
1262
1262
|
* One supervised TICK over the registry, as a swappable unit. Today the tick IS
|
|
1263
1263
|
* `runOnce` (claim+build+integrate a concurrent batch of eligible TASKS). The
|
|
1264
1264
|
* loop ({@link runLoop}) is deliberately written against this signature — NOT
|
|
1265
|
-
* against `runOnce` directly — so the advance-loop
|
|
1265
|
+
* against `runOnce` directly — so the advance-loop spec can later swap the tick
|
|
1266
1266
|
* (build / task / triage / surface / apply) WITHOUT re-architecting the loop
|
|
1267
1267
|
* (the forward-pointer: the loop owns concurrency/scheduling, the tick owns one
|
|
1268
1268
|
* item's work). The loop never reaches inside a tick.
|