@shenlee/devcrew 0.1.3 → 0.1.5
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/README.md +1 -1
- package/README.zh-CN.md +1 -1
- package/dist/packages/adapters/src/index.js +188 -7
- package/dist/packages/core/src/active-run.js +13 -1
- package/dist/packages/core/src/config.js +87 -16
- package/dist/packages/core/src/index.js +1 -0
- package/dist/packages/core/src/lock.js +89 -0
- package/dist/packages/core/src/paths.js +3 -0
- package/dist/packages/core/src/store.js +10 -0
- package/dist/packages/core/src/version.js +1 -1
- package/dist/packages/core/src/workflow.js +20 -3
- package/dist/packages/orchestrator/src/index.js +100 -16
- package/dist/packages/service/src/tools.js +79 -18
- package/docs/claude-code.md +14 -1
- package/docs/codex.md +15 -2
- package/docs/quickstart.md +1 -1
- package/docs/workflow.md +11 -2
- package/package.json +2 -2
- package/packages/adapters/src/index.ts +220 -9
- package/packages/core/src/active-run.ts +13 -1
- package/packages/core/src/config.ts +96 -17
- package/packages/core/src/index.ts +1 -0
- package/packages/core/src/lock.ts +104 -0
- package/packages/core/src/paths.ts +4 -0
- package/packages/core/src/store.ts +12 -1
- package/packages/core/src/types.ts +47 -1
- package/packages/core/src/version.ts +1 -1
- package/packages/core/src/workflow.ts +22 -3
- package/packages/orchestrator/src/index.ts +109 -17
- package/packages/service/src/tools.ts +86 -16
- package/plugins/devcrew-codex/.codex-plugin/plugin.json +1 -1
- package/plugins/devcrew-codex/.mcp.json +1 -1
- package/scripts/smoke-codex-plugin.mjs +1 -1
- package/docs/superpowers/plans/2026-07-10-p0-foundation-repair.md +0 -939
- package/docs/superpowers/plans/2026-07-13-safety-semantics.md +0 -313
- package/docs/superpowers/specs/2026-07-10-p0-foundation-repair-design.md +0 -182
- package/docs/superpowers/specs/2026-07-13-execution-boundaries-design.md +0 -126
|
@@ -1,313 +0,0 @@
|
|
|
1
|
-
# Safety Semantics Implementation Plan
|
|
2
|
-
|
|
3
|
-
> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking.
|
|
4
|
-
|
|
5
|
-
**Goal:** Make apply-mode execution policy explicit and prevent failed or absent verification from silently promoting an isolated patch.
|
|
6
|
-
|
|
7
|
-
**Architecture:** Add a persistent execution policy and verification outcome to the workflow state. Interactive apply runs pause with a host-execution handoff instead of launching a nested SDK; explicitly selected headless policies retain SDK execution with declared permissions. Testing only opens a normal promotion gate after successful verification; a separate waiver records the reason before an exception can be approved.
|
|
8
|
-
|
|
9
|
-
**Tech Stack:** TypeScript, Node.js test runner, MCP JSON-RPC tools, Git worktrees.
|
|
10
|
-
|
|
11
|
-
---
|
|
12
|
-
|
|
13
|
-
## File Structure
|
|
14
|
-
|
|
15
|
-
- Modify: `packages/core/src/types.ts` — policy, verification, handoff, and waiver state contracts.
|
|
16
|
-
- Modify: `packages/core/src/validation.ts` — parse policy and waiver input.
|
|
17
|
-
- Modify: `packages/core/src/workflow.ts` — default/apply-policy invariants and waiver transition.
|
|
18
|
-
- Modify: `packages/core/src/store.ts` — migrate persisted legacy runs safely.
|
|
19
|
-
- Modify: `packages/adapters/src/index.ts` — explicit headless SDK options; no implicit approval inheritance.
|
|
20
|
-
- Modify: `packages/orchestrator/src/index.ts` — interactive execution pause/submission and verification gate blocking.
|
|
21
|
-
- Modify: `packages/service/src/tools.ts` — MCP schemas and handlers for execution completion and verification waiver.
|
|
22
|
-
- Modify: `packages/core/src/artifacts.ts` — render policy, verification status, and waiver evidence.
|
|
23
|
-
- Modify: `tests/core.test.ts`, `tests/adapters-sdk.test.ts`, `tests/orchestrator.test.ts`, `tests/service.test.ts` — red/green coverage for every new state transition.
|
|
24
|
-
- Modify: `README.md`, `docs/workflow.md`, `docs/codex.md`, `docs/claude-code.md`, `packages/plugins/src/index.ts` — correct public behavior and generated skill copy.
|
|
25
|
-
|
|
26
|
-
### Task 1: Persist explicit execution and verification semantics
|
|
27
|
-
|
|
28
|
-
**Files:**
|
|
29
|
-
- Modify: `packages/core/src/types.ts`
|
|
30
|
-
- Modify: `packages/core/src/validation.ts`
|
|
31
|
-
- Modify: `packages/core/src/store.ts`
|
|
32
|
-
- Test: `tests/core.test.ts`
|
|
33
|
-
|
|
34
|
-
- [ ] **Step 1: Write failing state-contract tests**
|
|
35
|
-
|
|
36
|
-
Add tests that start an apply workflow with `executionPolicy: "headless-restricted"`, assert the policy persists through `loadState`, and assert unknown policy values fail validation. Add a migration fixture without the new fields and assert it loads as an interactive-host apply run with `verificationStatus: "not_run"` and no waiver.
|
|
37
|
-
|
|
38
|
-
```ts
|
|
39
|
-
assert.equal(state.executionPolicy, "headless-restricted");
|
|
40
|
-
await assert.rejects(
|
|
41
|
-
() => startWorkflow({ ...input, executionMode: "apply", executionPolicy: "unsafe" }),
|
|
42
|
-
/executionPolicy/,
|
|
43
|
-
);
|
|
44
|
-
assert.equal(loaded.verificationStatus, "not_run");
|
|
45
|
-
```
|
|
46
|
-
|
|
47
|
-
- [ ] **Step 2: Run the focused core test and verify RED**
|
|
48
|
-
|
|
49
|
-
Run: `node --import tsx --test tests/core.test.ts`
|
|
50
|
-
|
|
51
|
-
Expected: FAIL because `executionPolicy` and `verificationStatus` are not yet represented in state or input validation.
|
|
52
|
-
|
|
53
|
-
- [ ] **Step 3: Add the minimal state and parsing contracts**
|
|
54
|
-
|
|
55
|
-
In `types.ts`, add:
|
|
56
|
-
|
|
57
|
-
```ts
|
|
58
|
-
export const EXECUTION_POLICIES = ["interactive-host", "headless-restricted", "headless-unattended"] as const;
|
|
59
|
-
export type ExecutionPolicy = (typeof EXECUTION_POLICIES)[number];
|
|
60
|
-
export type VerificationStatus = "not_run" | "passed" | "failed";
|
|
61
|
-
|
|
62
|
-
export interface VerificationWaiver { reason: string; createdAt: string; }
|
|
63
|
-
```
|
|
64
|
-
|
|
65
|
-
Add `executionPolicy` to `StartWorkflowInput` and `RunState`, plus
|
|
66
|
-
`verificationStatus` and optional `verificationWaiver` to `RunState`. Add
|
|
67
|
-
`parseExecutionPolicy()` and `parseWaiverReason()` in `validation.ts`. In
|
|
68
|
-
`loadState`, use `interactive-host` for legacy apply runs and `not_run` for
|
|
69
|
-
missing verification status.
|
|
70
|
-
|
|
71
|
-
- [ ] **Step 4: Run the focused core test and verify GREEN**
|
|
72
|
-
|
|
73
|
-
Run: `node --import tsx --test tests/core.test.ts`
|
|
74
|
-
|
|
75
|
-
Expected: PASS, including new persistence and invalid-policy cases.
|
|
76
|
-
|
|
77
|
-
- [ ] **Step 5: Commit the state contract**
|
|
78
|
-
|
|
79
|
-
```bash
|
|
80
|
-
git add packages/core/src/types.ts packages/core/src/validation.ts packages/core/src/store.ts tests/core.test.ts
|
|
81
|
-
git commit -m "feat: record execution and verification policy"
|
|
82
|
-
```
|
|
83
|
-
|
|
84
|
-
### Task 2: Make SDK execution explicitly headless
|
|
85
|
-
|
|
86
|
-
**Files:**
|
|
87
|
-
- Modify: `packages/adapters/src/index.ts`
|
|
88
|
-
- Test: `tests/adapters-sdk.test.ts`
|
|
89
|
-
|
|
90
|
-
- [ ] **Step 1: Write failing adapter-policy tests**
|
|
91
|
-
|
|
92
|
-
Replace the assertion that Claude apply uses `acceptEdits` with tests proving
|
|
93
|
-
that an interactive-host execution is rejected before SDK invocation and that
|
|
94
|
-
headless policies select explicit SDK options. For Claude restricted mode, the
|
|
95
|
-
test must assert `permissionMode: "dontAsk"` and a narrow tool list. For Codex,
|
|
96
|
-
assert `approvalPolicy: "never"` only for `headless-unattended` and no implicit
|
|
97
|
-
approval-policy value for read-only planning.
|
|
98
|
-
|
|
99
|
-
```ts
|
|
100
|
-
await assert.rejects(
|
|
101
|
-
() => runRole({ ...baseInput, phase: "execution", executionMode: "apply", executionPolicy: "interactive-host", backend: "claude" }),
|
|
102
|
-
/interactive-host execution must be performed by the host/,
|
|
103
|
-
);
|
|
104
|
-
```
|
|
105
|
-
|
|
106
|
-
- [ ] **Step 2: Run the focused adapter test and verify RED**
|
|
107
|
-
|
|
108
|
-
Run: `node --import tsx --test tests/adapters-sdk.test.ts`
|
|
109
|
-
|
|
110
|
-
Expected: FAIL because `RoleRunInput` lacks the policy and Claude currently
|
|
111
|
-
sets `acceptEdits` with bare `Bash` permission.
|
|
112
|
-
|
|
113
|
-
- [ ] **Step 3: Implement explicit headless profiles**
|
|
114
|
-
|
|
115
|
-
Add `executionPolicy` to `RoleRunInput`. Make `roleCanApply()` require a
|
|
116
|
-
headless policy. Reject SDK execution for `interactive-host`. Replace the
|
|
117
|
-
Claude restricted profile with `dontAsk`: implementers receive only `Read`,
|
|
118
|
-
`Grep`, `Glob`, `Edit`, and `Write`; testers receive only `Read`, `Grep`, and
|
|
119
|
-
`Glob`. Neither restricted role receives `Bash`; DevCrew's configured command
|
|
120
|
-
runner supplies verification evidence separately. For the explicitly selected
|
|
121
|
-
unattended policy, add the SDK's dangerous-skip opt-in and set Claude to
|
|
122
|
-
`bypassPermissions`; this is an auditable CI-only policy. Pass Codex
|
|
123
|
-
`approvalPolicy: "never"` only for that unattended policy. Document that both
|
|
124
|
-
headless profiles are DevCrew policies, not inherited host approval.
|
|
125
|
-
|
|
126
|
-
- [ ] **Step 4: Run the focused adapter test and verify GREEN**
|
|
127
|
-
|
|
128
|
-
Run: `node --import tsx --test tests/adapters-sdk.test.ts`
|
|
129
|
-
|
|
130
|
-
Expected: PASS with no `acceptEdits` assertion remaining.
|
|
131
|
-
|
|
132
|
-
- [ ] **Step 5: Commit the adapter boundary**
|
|
133
|
-
|
|
134
|
-
```bash
|
|
135
|
-
git add packages/adapters/src/index.ts tests/adapters-sdk.test.ts
|
|
136
|
-
git commit -m "fix: make SDK apply policies explicit"
|
|
137
|
-
```
|
|
138
|
-
|
|
139
|
-
### Task 3: Add the interactive execution handoff
|
|
140
|
-
|
|
141
|
-
**Files:**
|
|
142
|
-
- Modify: `packages/orchestrator/src/index.ts`
|
|
143
|
-
- Modify: `packages/service/src/tools.ts`
|
|
144
|
-
- Test: `tests/orchestrator.test.ts`
|
|
145
|
-
- Test: `tests/service.test.ts`
|
|
146
|
-
|
|
147
|
-
- [ ] **Step 1: Write failing handoff tests**
|
|
148
|
-
|
|
149
|
-
Add an apply workflow with `executionPolicy: "interactive-host"`. After the
|
|
150
|
-
implementation gate is approved, `devcrew_continue` must create the isolated
|
|
151
|
-
worktree but not call the injected `RoleRunner`; it returns
|
|
152
|
-
`status: "awaiting_execution"` and structured instruction data. A new
|
|
153
|
-
`devcrew_complete_execution` call captures the worktree patch and advances to
|
|
154
|
-
testing without modifying the requester repository. Repeat the same handoff
|
|
155
|
-
for the tester: it receives the test-report instruction, returns exact command
|
|
156
|
-
result records, and DevCrew derives the verification status from those records.
|
|
157
|
-
|
|
158
|
-
```ts
|
|
159
|
-
assert.equal(paused.status, "awaiting_execution");
|
|
160
|
-
assert.equal(runnerCalls.filter((call) => call.phase === "execution").length, 0);
|
|
161
|
-
assert.equal(paused.executionInstruction?.cwd, paused.executionWorkspace?.path);
|
|
162
|
-
```
|
|
163
|
-
|
|
164
|
-
- [ ] **Step 2: Run focused orchestrator and service tests and verify RED**
|
|
165
|
-
|
|
166
|
-
Run: `node --import tsx --test tests/orchestrator.test.ts tests/service.test.ts`
|
|
167
|
-
|
|
168
|
-
Expected: FAIL because the current orchestrator immediately invokes the SDK
|
|
169
|
-
runner and no completion MCP tool exists.
|
|
170
|
-
|
|
171
|
-
- [ ] **Step 3: Implement pause and completion transitions**
|
|
172
|
-
|
|
173
|
-
Add `awaiting_execution` to `RunStatus` and an `ExecutionInstruction` state
|
|
174
|
-
object containing role, phase, worktree cwd, request, standards, approved
|
|
175
|
-
artifacts, and required result sections. In the execution and testing branches
|
|
176
|
-
of `runCurrentPhaseRole`, ensure the worktree, write the instruction, persist
|
|
177
|
-
the state, and return without calling `runner` or `runConfiguredVerification`
|
|
178
|
-
when policy is `interactive-host`.
|
|
179
|
-
|
|
180
|
-
Add `completeInteractiveExecution(input)` to orchestrator. It requires an
|
|
181
|
-
`awaiting_execution` state and a required Markdown summary supplied by the
|
|
182
|
-
host. For execution it captures changes, runs no nested SDK or shell command,
|
|
183
|
-
writes implementation-review evidence, and moves to `testing/ready`. For
|
|
184
|
-
testing it accepts a validated array of `{ command, exitCode, output,
|
|
185
|
-
startedAt, completedAt }`, writes the test report, derives the verification
|
|
186
|
-
status, and either opens the gate or enters the failure path. Expose it as
|
|
187
|
-
`devcrew_complete_execution` with an input schema that includes `summary` and
|
|
188
|
-
optional `verification` records.
|
|
189
|
-
|
|
190
|
-
- [ ] **Step 4: Run focused handoff tests and verify GREEN**
|
|
191
|
-
|
|
192
|
-
Run: `node --import tsx --test tests/orchestrator.test.ts tests/service.test.ts`
|
|
193
|
-
|
|
194
|
-
Expected: PASS; the requester repository remains unchanged until a later
|
|
195
|
-
testing approval.
|
|
196
|
-
|
|
197
|
-
- [ ] **Step 5: Commit the interactive handoff**
|
|
198
|
-
|
|
199
|
-
```bash
|
|
200
|
-
git add packages/orchestrator/src/index.ts packages/service/src/tools.ts tests/orchestrator.test.ts tests/service.test.ts
|
|
201
|
-
git commit -m "feat: hand interactive apply execution to host"
|
|
202
|
-
```
|
|
203
|
-
|
|
204
|
-
### Task 4: Block failed verification and require a recorded waiver
|
|
205
|
-
|
|
206
|
-
**Files:**
|
|
207
|
-
- Modify: `packages/core/src/workflow.ts`
|
|
208
|
-
- Modify: `packages/orchestrator/src/index.ts`
|
|
209
|
-
- Modify: `packages/service/src/tools.ts`
|
|
210
|
-
- Modify: `packages/core/src/artifacts.ts`
|
|
211
|
-
- Test: `tests/orchestrator.test.ts`
|
|
212
|
-
- Test: `tests/service.test.ts`
|
|
213
|
-
|
|
214
|
-
- [ ] **Step 1: Write failing verification tests**
|
|
215
|
-
|
|
216
|
-
Create an apply fixture with `verifyCommands: ["node -e \"process.exit(7)\""]`.
|
|
217
|
-
After testing, assert `verificationStatus === "failed"`, `status ===
|
|
218
|
-
"awaiting_input"`, and that `approveOrchestratedWorkflow({ gate: "testing" })`
|
|
219
|
-
rejects without promoting the patch. Add a second test showing that
|
|
220
|
-
`devcrew_waive_verification` rejects an empty reason, persists a non-empty
|
|
221
|
-
reason, reopens the testing gate, and permits promotion only after normal
|
|
222
|
-
testing approval.
|
|
223
|
-
|
|
224
|
-
```ts
|
|
225
|
-
await assert.rejects(
|
|
226
|
-
() => approveOrchestratedWorkflow({ cwd, runId, gate: "testing" }),
|
|
227
|
-
/verification failed/,
|
|
228
|
-
);
|
|
229
|
-
assert.equal(waived.verificationWaiver?.reason, "Known upstream test outage");
|
|
230
|
-
```
|
|
231
|
-
|
|
232
|
-
- [ ] **Step 2: Run focused workflow tests and verify RED**
|
|
233
|
-
|
|
234
|
-
Run: `node --import tsx --test tests/orchestrator.test.ts tests/service.test.ts`
|
|
235
|
-
|
|
236
|
-
Expected: FAIL because a nonzero command currently still opens the pending
|
|
237
|
-
testing gate and no waiver tool exists.
|
|
238
|
-
|
|
239
|
-
- [ ] **Step 3: Implement verification outcome and waiver flow**
|
|
240
|
-
|
|
241
|
-
After `runConfiguredVerification`, set `verificationStatus` from every result:
|
|
242
|
-
empty is `not_run`, all-zero is `passed`, otherwise `failed`. A failed status
|
|
243
|
-
sets `awaiting_input` and does not set the testing gate to pending. Add
|
|
244
|
-
`waiveVerification(input)` that requires failed verification and a non-empty
|
|
245
|
-
reason, records `VerificationWaiver`, changes the testing gate to pending, and
|
|
246
|
-
sets `awaiting_approval`. Add `devcrew_waive_verification` to the MCP schema
|
|
247
|
-
and handler.
|
|
248
|
-
|
|
249
|
-
Make `approveOrchestratedWorkflow` reject a testing promotion unless status is
|
|
250
|
-
passed or a waiver exists. Render the status, command exit evidence, and waiver
|
|
251
|
-
reason in both the test report and acceptance artifact.
|
|
252
|
-
|
|
253
|
-
- [ ] **Step 4: Run focused verification tests and verify GREEN**
|
|
254
|
-
|
|
255
|
-
Run: `node --import tsx --test tests/orchestrator.test.ts tests/service.test.ts`
|
|
256
|
-
|
|
257
|
-
Expected: PASS; failed verification cannot mutate the requester repository,
|
|
258
|
-
while a recorded waiver remains visible and permits intentional approval.
|
|
259
|
-
|
|
260
|
-
- [ ] **Step 5: Commit verification safety**
|
|
261
|
-
|
|
262
|
-
```bash
|
|
263
|
-
git add packages/core/src/workflow.ts packages/orchestrator/src/index.ts packages/service/src/tools.ts packages/core/src/artifacts.ts tests/orchestrator.test.ts tests/service.test.ts
|
|
264
|
-
git commit -m "fix: block failed verification promotion"
|
|
265
|
-
```
|
|
266
|
-
|
|
267
|
-
### Task 5: Correct generated instructions and user-facing documentation
|
|
268
|
-
|
|
269
|
-
**Files:**
|
|
270
|
-
- Modify: `README.md`
|
|
271
|
-
- Modify: `docs/workflow.md`
|
|
272
|
-
- Modify: `docs/codex.md`
|
|
273
|
-
- Modify: `docs/claude-code.md`
|
|
274
|
-
- Modify: `packages/plugins/src/index.ts`
|
|
275
|
-
- Test: `tests/plugins.test.ts`
|
|
276
|
-
|
|
277
|
-
- [ ] **Step 1: Write failing generated-skill/doc assertions**
|
|
278
|
-
|
|
279
|
-
Extend plugin tests to require the generated skill to distinguish
|
|
280
|
-
interactive-host execution from headless policy and to mention
|
|
281
|
-
`devcrew_complete_execution` and `devcrew_waive_verification`.
|
|
282
|
-
|
|
283
|
-
- [ ] **Step 2: Run plugin tests and verify RED**
|
|
284
|
-
|
|
285
|
-
Run: `node --import tsx --test tests/plugins.test.ts`
|
|
286
|
-
|
|
287
|
-
Expected: FAIL because the generated skill promises inherited host approvals
|
|
288
|
-
and lacks the new handoff/waiver tools.
|
|
289
|
-
|
|
290
|
-
- [ ] **Step 3: Update generated skill and docs**
|
|
291
|
-
|
|
292
|
-
Document that interactive host execution uses the host's native agent after
|
|
293
|
-
DevCrew supplies a worktree instruction; it does not run a nested SDK. Document
|
|
294
|
-
headless policies as explicit DevCrew policies. Replace all claims that DevCrew
|
|
295
|
-
inherits a current host approval boundary. Add the failed-verification and
|
|
296
|
-
recorded-waiver transition to workflow diagrams and tool lists.
|
|
297
|
-
|
|
298
|
-
- [ ] **Step 4: Run plugin tests and verify GREEN**
|
|
299
|
-
|
|
300
|
-
Run: `node --import tsx --test tests/plugins.test.ts`
|
|
301
|
-
|
|
302
|
-
Expected: PASS with the checked-in plugin matching regenerated text.
|
|
303
|
-
|
|
304
|
-
- [ ] **Step 5: Run full validation and commit documentation**
|
|
305
|
-
|
|
306
|
-
Run: `npm run validate`
|
|
307
|
-
|
|
308
|
-
Expected: exit code 0 with all tests passing.
|
|
309
|
-
|
|
310
|
-
```bash
|
|
311
|
-
git add README.md docs/workflow.md docs/codex.md docs/claude-code.md packages/plugins/src/index.ts plugins/devcrew-codex plugins/devcrew-claude tests/plugins.test.ts
|
|
312
|
-
git commit -m "docs: describe explicit apply execution policies"
|
|
313
|
-
```
|
|
@@ -1,182 +0,0 @@
|
|
|
1
|
-
# DevCrew P0 Foundation Repair Design
|
|
2
|
-
|
|
3
|
-
## Objective
|
|
4
|
-
|
|
5
|
-
Repair the P0 workflow and execution-safety defects identified in the 0.1.1 review without expanding into the P1 role-model, semantic architecture review, or configurable workflow work.
|
|
6
|
-
|
|
7
|
-
The repaired workflow must guarantee that requester approval happens before code changes, apply-mode changes remain isolated until final approval, malformed MCP input cannot poison the server, gate mutations are valid and idempotent, local fallback cannot impersonate apply execution, and the checked-in plugin cannot drift from the package version.
|
|
8
|
-
|
|
9
|
-
## Scope
|
|
10
|
-
|
|
11
|
-
This design includes:
|
|
12
|
-
|
|
13
|
-
- Move real implementation after the existing `implementation` gate.
|
|
14
|
-
- Execute apply-mode implementation and verification in a run-owned Git worktree.
|
|
15
|
-
- Capture committed, staged, unstaged, renamed, deleted, binary, and new-file changes as one reviewable patch.
|
|
16
|
-
- Apply the reviewed patch to the requester's repository only after the `testing` gate is approved.
|
|
17
|
-
- Keep rejected testing work isolated and allow the implementer to revise it.
|
|
18
|
-
- Enforce legal, idempotent `approve`, `reject`, and `answer` transitions.
|
|
19
|
-
- Validate JSON-RPC request shape and recover the stdio queue after handler failures.
|
|
20
|
-
- Reject `executionMode=apply` with the `local` backend.
|
|
21
|
-
- Synchronize package, generated plugin, checked-in plugin, and MCP runtime versions.
|
|
22
|
-
|
|
23
|
-
This design does not include:
|
|
24
|
-
|
|
25
|
-
- Real architect-driven semantic diff review.
|
|
26
|
-
- Structured PM questions and machine-readable role verdicts.
|
|
27
|
-
- Host-native role/subagent integration.
|
|
28
|
-
- Configurable gates or artifact directories.
|
|
29
|
-
- Claude marketplace packaging or smoke coverage.
|
|
30
|
-
- Cross-process run locking or HTTP transport.
|
|
31
|
-
|
|
32
|
-
## Workflow Model
|
|
33
|
-
|
|
34
|
-
The public gate names remain unchanged for MCP compatibility:
|
|
35
|
-
|
|
36
|
-
1. `requirements`
|
|
37
|
-
2. `architecture`
|
|
38
|
-
3. `implementation`
|
|
39
|
-
4. `testing`
|
|
40
|
-
|
|
41
|
-
The internal phase sequence becomes:
|
|
42
|
-
|
|
43
|
-
```text
|
|
44
|
-
requirements
|
|
45
|
-
-> architecture
|
|
46
|
-
-> implementation
|
|
47
|
-
-> execution (apply only)
|
|
48
|
-
-> testing
|
|
49
|
-
-> acceptance
|
|
50
|
-
-> complete
|
|
51
|
-
```
|
|
52
|
-
|
|
53
|
-
The existing `implementation` phase becomes plan-only in both execution modes. The implementer receives a read-only role prompt and writes `implementation-plan.md`. Approving the `implementation` gate advances plan mode directly to `testing`, while apply mode advances to the new nongated `execution` phase.
|
|
54
|
-
|
|
55
|
-
The `execution` phase runs the implementer in an isolated worktree, writes `implementation-review.md`, and advances to `testing` with status `ready`. The next `continue` runs the tester and verification commands in the same worktree, then opens the `testing` gate.
|
|
56
|
-
|
|
57
|
-
Approving the `testing` gate applies the captured patch to the original repository, removes the worktree, and advances to acceptance. Rejecting the testing gate leaves the worktree isolated. The rejection feedback can be answered, after which the run returns to `execution` so the implementer can revise the existing isolated changes.
|
|
58
|
-
|
|
59
|
-
## Apply Isolation
|
|
60
|
-
|
|
61
|
-
### Workspace creation
|
|
62
|
-
|
|
63
|
-
Before the first execution attempt DevCrew must:
|
|
64
|
-
|
|
65
|
-
1. Confirm the requester repository is a Git repository with a clean working tree, excluding DevCrew runtime and artifact paths.
|
|
66
|
-
2. Record the current `HEAD` as `baseCommit`.
|
|
67
|
-
3. Create a detached worktree under `.devcrew/worktrees/<run-id>`.
|
|
68
|
-
4. Persist the worktree path and base commit before invoking the SDK role.
|
|
69
|
-
|
|
70
|
-
All implementation, lint, test, and coverage commands run with the worktree as their working directory. Artifacts and state remain in the original repository.
|
|
71
|
-
|
|
72
|
-
### Capturing all changes
|
|
73
|
-
|
|
74
|
-
After the implementer returns DevCrew must normalize any commits created by the role back into worktree changes relative to `baseCommit`. This is safe because the worktree is owned by the run and has not been promoted.
|
|
75
|
-
|
|
76
|
-
DevCrew then marks untracked files as intent-to-add inside the worktree and captures:
|
|
77
|
-
|
|
78
|
-
- `git status --porcelain=v1 -z -uall` for changed paths.
|
|
79
|
-
- `git diff --binary --no-ext-diff <baseCommit> --` for the complete patch.
|
|
80
|
-
|
|
81
|
-
Using the base commit includes staged and unstaged changes. Intent-to-add makes new files visible in the patch. NUL-delimited status parsing avoids filename quoting and rename parsing bugs.
|
|
82
|
-
|
|
83
|
-
### Promotion
|
|
84
|
-
|
|
85
|
-
Before applying an approved patch DevCrew must re-check that the requester repository is clean and still points at `baseCommit`. If either condition changed, approval fails without deleting the worktree or mutating the requester repository.
|
|
86
|
-
|
|
87
|
-
Promotion writes the captured patch under the run directory, applies it to the requester repository with `git apply --binary`, verifies the resulting requester diff matches the reviewed patch, and then removes the worktree. The promoted files remain uncommitted so the requester retains normal review and commit control.
|
|
88
|
-
|
|
89
|
-
An empty apply patch is an error. Apply mode must never report successful implementation when no repository change was produced.
|
|
90
|
-
|
|
91
|
-
## State Changes
|
|
92
|
-
|
|
93
|
-
`RunState` gains optional execution workspace metadata:
|
|
94
|
-
|
|
95
|
-
```ts
|
|
96
|
-
interface ExecutionWorkspace {
|
|
97
|
-
path: string;
|
|
98
|
-
baseCommit: string;
|
|
99
|
-
}
|
|
100
|
-
```
|
|
101
|
-
|
|
102
|
-
The `execution` phase is added to `PHASES`. Older state files without execution workspace metadata continue to load.
|
|
103
|
-
|
|
104
|
-
Gate mutations use these rules:
|
|
105
|
-
|
|
106
|
-
- Approving an already approved gate returns the unchanged state and does not append another approval.
|
|
107
|
-
- Rejecting an already rejected gate returns the unchanged state and does not append duplicate feedback.
|
|
108
|
-
- A pending gate can only be approved or rejected when it is the current phase gate and status is `awaiting_approval`.
|
|
109
|
-
- `answer` is only legal while status is `awaiting_input` and the current gate is rejected.
|
|
110
|
-
- Calls against `acceptance` or `complete` cannot move the run backwards.
|
|
111
|
-
|
|
112
|
-
The service uses a new orchestrated approval entry point so testing approval can promote the patch before the core state advances.
|
|
113
|
-
|
|
114
|
-
## Backend Rules
|
|
115
|
-
|
|
116
|
-
After host/config backend resolution, workflow creation rejects this combination:
|
|
117
|
-
|
|
118
|
-
```text
|
|
119
|
-
executionMode=apply, backend=local
|
|
120
|
-
```
|
|
121
|
-
|
|
122
|
-
Plan mode keeps deterministic local fallback. Apply mode requires a real Codex or Claude SDK backend at every role phase.
|
|
123
|
-
|
|
124
|
-
The implementation-plan role is forced to read-only behavior even when the run execution mode is apply. Only the new execution phase and apply-mode tester receive write/Bash capabilities.
|
|
125
|
-
|
|
126
|
-
## Stdio Reliability
|
|
127
|
-
|
|
128
|
-
The line processor validates that parsed JSON is a non-array object with `jsonrpc: "2.0"` and a string `method`. Invalid request objects receive JSON-RPC error `-32600` with `id: null` and do not enter the request queue.
|
|
129
|
-
|
|
130
|
-
For queued requests, each returned task may reject to its caller, but the internal queue stores a recovered promise. One handler failure therefore cannot prevent later requests from executing.
|
|
131
|
-
|
|
132
|
-
Existing parse error behavior remains `-32700`. Notifications without an ID remain response-free.
|
|
133
|
-
|
|
134
|
-
## Version Discipline
|
|
135
|
-
|
|
136
|
-
The next implementation version is `0.1.2`. The following must agree:
|
|
137
|
-
|
|
138
|
-
- `package.json`
|
|
139
|
-
- `package-lock.json`
|
|
140
|
-
- `DEVCREW_VERSION`
|
|
141
|
-
- generated Codex and Claude manifests
|
|
142
|
-
- checked-in Codex manifest
|
|
143
|
-
- checked-in Codex MCP npm package specifier
|
|
144
|
-
- smoke client metadata and version assertions
|
|
145
|
-
|
|
146
|
-
CI adds a checked-in plugin drift test that generates a fresh Codex plugin in a temporary directory and compares all generated text files with the checked-in bundle. Binary assets are checked by hash. Publication order is npm `0.1.2` first, then marketplace push, so the public plugin never references an unavailable npm version.
|
|
147
|
-
|
|
148
|
-
## Error Handling
|
|
149
|
-
|
|
150
|
-
- Worktree creation failure leaves the run in `execution/ready` with no role result recorded.
|
|
151
|
-
- SDK failure leaves the isolated worktree available for diagnosis and retry.
|
|
152
|
-
- Empty implementation patch fails before testing.
|
|
153
|
-
- Verification failures remain visible in the testing artifact; automatic test verdict blocking remains P1.
|
|
154
|
-
- Promotion precondition failure leaves the worktree and state intact for manual resolution.
|
|
155
|
-
- Worktree cleanup runs only after successful promotion or explicit run rejection cleanup added in a later lifecycle feature.
|
|
156
|
-
|
|
157
|
-
## Testing Strategy
|
|
158
|
-
|
|
159
|
-
Tests are added before implementation and must demonstrate the original failures:
|
|
160
|
-
|
|
161
|
-
- Implementation-plan approval occurs before the first writable role invocation.
|
|
162
|
-
- Local apply start is rejected.
|
|
163
|
-
- An implementer-created commit is converted into a complete reviewed patch.
|
|
164
|
-
- Staged, unstaged, renamed, deleted, binary, and untracked files appear in review evidence.
|
|
165
|
-
- Rejecting testing keeps changes outside the requester repository and supports revision.
|
|
166
|
-
- Approving testing promotes exactly the reviewed patch.
|
|
167
|
-
- Changed requester `HEAD` or dirty requester worktree blocks promotion.
|
|
168
|
-
- Empty apply output fails.
|
|
169
|
-
- Duplicate approvals/rejections are idempotent.
|
|
170
|
-
- Complete runs cannot be reopened.
|
|
171
|
-
- Answer outside `awaiting_input` fails.
|
|
172
|
-
- JSON `null`, arrays, missing methods, and wrong JSON-RPC versions return `-32600`.
|
|
173
|
-
- A rejected request handler does not block the next stdio request.
|
|
174
|
-
- Checked-in plugin version and generated bundle match `DEVCREW_VERSION`.
|
|
175
|
-
|
|
176
|
-
The final verification command remains `npm run validate`, followed by the isolated Codex marketplace smoke after `@shenlee/devcrew@0.1.2` is published.
|
|
177
|
-
|
|
178
|
-
## Compatibility
|
|
179
|
-
|
|
180
|
-
MCP tool names and gate names remain stable. Existing plan-mode callers continue using the same approve/continue sequence. Apply-mode sequencing gains one additional `continue` call for the execution phase before testing.
|
|
181
|
-
|
|
182
|
-
Existing 0.1.1 run files remain loadable. Runs already in the old `implementation` phase are treated as implementation planning and cannot write code until their implementation gate is approved under the new state transition.
|
|
@@ -1,126 +0,0 @@
|
|
|
1
|
-
# DevCrew Execution Boundaries Design
|
|
2
|
-
|
|
3
|
-
## Goal
|
|
4
|
-
|
|
5
|
-
Make DevCrew's approval, verification, and role boundaries match its public
|
|
6
|
-
product claims. Interactive work must execute through the host agent's native
|
|
7
|
-
permission model. Headless work may use host SDKs only under an explicit,
|
|
8
|
-
auditable DevCrew execution policy.
|
|
9
|
-
|
|
10
|
-
## Scope
|
|
11
|
-
|
|
12
|
-
This change is delivered in three independently releasable slices:
|
|
13
|
-
|
|
14
|
-
1. Safety semantics: explicit execution policy and verification-failure
|
|
15
|
-
promotion blocking.
|
|
16
|
-
2. Workflow semantics: execution-time architecture compliance review and
|
|
17
|
-
structured role questions/results.
|
|
18
|
-
3. Productisation: effective artifact configuration and real-host integration
|
|
19
|
-
coverage.
|
|
20
|
-
|
|
21
|
-
The existing isolated Git worktree and binary patch promotion remain the sole
|
|
22
|
-
mechanism for moving apply-mode changes into the requester repository.
|
|
23
|
-
|
|
24
|
-
## Execution Planes
|
|
25
|
-
|
|
26
|
-
### Interactive host plane
|
|
27
|
-
|
|
28
|
-
Interactive Codex and Claude Code workflows do not invoke the Codex or Claude
|
|
29
|
-
SDK to modify repository files. DevCrew MCP owns durable workflow state,
|
|
30
|
-
artifacts, gate validation, execution worktree creation, patch capture, and
|
|
31
|
-
promotion. It exposes a structured execution instruction containing the role,
|
|
32
|
-
worktree path, approved context, and required result schema. The active host
|
|
33
|
-
agent or a native host subagent performs the work with the host's ordinary
|
|
34
|
-
sandbox and approval UI, then submits the result to DevCrew.
|
|
35
|
-
|
|
36
|
-
This plane must never claim that a nested SDK session inherits the interactive
|
|
37
|
-
host's current approval decisions.
|
|
38
|
-
|
|
39
|
-
### Headless SDK plane
|
|
40
|
-
|
|
41
|
-
Headless and CI workflows retain SDK orchestration, but `apply` requires an
|
|
42
|
-
explicit `executionPolicy`. The initial policy set is:
|
|
43
|
-
|
|
44
|
-
- `interactive-host`: no nested SDK execution; valid only for an interactive
|
|
45
|
-
host integration.
|
|
46
|
-
- `headless-restricted`: SDK execution in the DevCrew worktree with a declared
|
|
47
|
-
minimal tool surface and no hidden user-prompt assumption.
|
|
48
|
-
- `headless-unattended`: an explicitly opted-in unattended SDK policy for CI;
|
|
49
|
-
its audit record makes the autonomy clear.
|
|
50
|
-
|
|
51
|
-
The policy, backend, allowed capabilities, and any waiver are recorded in run
|
|
52
|
-
state and shown in review artifacts. `acceptEdits`, bare `allowedTools`, and an
|
|
53
|
-
implicit Codex approval policy are not described as inherited host approvals.
|
|
54
|
-
|
|
55
|
-
## Verification And Promotion
|
|
56
|
-
|
|
57
|
-
After isolated testing, DevCrew computes a verification status:
|
|
58
|
-
|
|
59
|
-
- `passed`: every configured or discovered verification command exited zero.
|
|
60
|
-
- `failed`: at least one command exited nonzero or timed out.
|
|
61
|
-
- `not_run`: no verification command was available.
|
|
62
|
-
|
|
63
|
-
Only `passed` can open the normal `testing` approval gate. A failed result
|
|
64
|
-
moves the run to `awaiting_input` with the failure evidence and preserves the
|
|
65
|
-
worktree. A requester may either supply feedback that returns the run to
|
|
66
|
-
`execution`, or invoke a dedicated risk-waiver operation with a non-empty
|
|
67
|
-
reason. The waiver is persistent, appears in the test report and acceptance
|
|
68
|
-
artifact, and is the only path that can open a testing approval gate after a
|
|
69
|
-
failed verification.
|
|
70
|
-
|
|
71
|
-
`not_run` remains reviewable but is visibly distinct from `passed`; it cannot
|
|
72
|
-
be silently represented as successful verification.
|
|
73
|
-
|
|
74
|
-
## Execution-Time Architecture Review
|
|
75
|
-
|
|
76
|
-
The current implementation-plan gate approves a plan and cannot approve the
|
|
77
|
-
subsequent code diff. Add an `implementation-review` gate after execution and
|
|
78
|
-
before testing. The architect role receives the approved architecture artifact,
|
|
79
|
-
captured binary diff, changed-file list, lint evidence, and structured
|
|
80
|
-
implementation result. It returns a structured compliance decision.
|
|
81
|
-
|
|
82
|
-
Only an approved implementation review advances to testing. Rejection records
|
|
83
|
-
feedback and returns to execution with the existing isolated worktree intact.
|
|
84
|
-
The existing `implementation-review.md` remains an artifact, but becomes the
|
|
85
|
-
architect's real review output rather than a rendered checklist.
|
|
86
|
-
|
|
87
|
-
## Structured Role Results And Clarification
|
|
88
|
-
|
|
89
|
-
Each role result is a validated JSON envelope with a Markdown body plus
|
|
90
|
-
role-specific fields. At minimum, PM returns `questions`, architect returns a
|
|
91
|
-
compliance decision, implementer returns changed-file and command evidence, and
|
|
92
|
-
tester returns case/evidence summaries. Markdown remains the human-facing
|
|
93
|
-
artifact format.
|
|
94
|
-
|
|
95
|
-
If PM returns one or more questions, requirements enter `awaiting_input`
|
|
96
|
-
without opening an approval gate. `devcrew_answer` records the answer and
|
|
97
|
-
re-runs PM. A requirements gate opens only when the PM result has no open
|
|
98
|
-
questions.
|
|
99
|
-
|
|
100
|
-
## Configuration
|
|
101
|
-
|
|
102
|
-
`workflow.artifactDirectory` is used by all artifact path helpers, relative to
|
|
103
|
-
the repository root and validated to remain within that root. Core safety gates
|
|
104
|
-
are not freely removable. `workflow.gates` is replaced or constrained by a
|
|
105
|
-
validated sequence that must include requirements, architecture,
|
|
106
|
-
implementation, implementation-review, and testing for apply workflows.
|
|
107
|
-
|
|
108
|
-
## Integration Coverage
|
|
109
|
-
|
|
110
|
-
Add tests for failed verification, risk waiver, no-verification status,
|
|
111
|
-
architecture-review rejection/revision, structured PM questions, and configured
|
|
112
|
-
artifact output. Preserve existing worktree-promotion coverage.
|
|
113
|
-
|
|
114
|
-
The production-like Codex marketplace smoke remains plan-mode and must verify
|
|
115
|
-
the published package version. Add isolated integration coverage for the
|
|
116
|
-
interactive execution handoff protocol and a real Claude plugin install/start
|
|
117
|
-
smoke. A real unattended apply smoke uses only a disposable fixture repository
|
|
118
|
-
and an explicitly selected headless policy.
|
|
119
|
-
|
|
120
|
-
## Non-goals
|
|
121
|
-
|
|
122
|
-
- Do not remove worktree isolation or binary patch promotion.
|
|
123
|
-
- Do not automatically approve failed verification.
|
|
124
|
-
- Do not make arbitrary workflow graph customisation part of this release.
|
|
125
|
-
- Do not use generated role files as an execution mechanism until a host-native
|
|
126
|
-
integration consumes them explicitly.
|