@astrosheep/keiyaku 4.0.2 → 4.0.4
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/build/integrations/marketplace/plugins/keiyaku/.claude-plugin/plugin.json +1 -1
- package/build/integrations/marketplace/plugins/keiyaku/.codex-plugin/plugin.json +1 -1
- package/build/integrations/marketplace/plugins/keiyaku/package.json +1 -1
- package/build/integrations/marketplace/plugins/keiyaku/skills/keiyaku/SKILL.md +1 -1
- package/build/integrations/marketplace/plugins/keiyaku/skills/keiyaku-akuma/SKILL.md +1 -1
- package/build/integrations/marketplace/plugins/keiyaku/skills/keiyaku-bind/SKILL.md +5 -0
- package/build/integrations/marketplace/plugins/keiyaku/skills/keiyaku-task/SKILL.md +3 -1
- package/build/integrations/marketplace/plugins/keiyaku/skills/keiyaku-workflow/SKILL.md +9 -8
- package/build/src/akuma/akuma.d.ts +34 -11
- package/build/src/akuma/akuma.js +121 -61
- package/build/src/akuma/allowed.d.ts +7 -0
- package/build/src/akuma/allowed.js +40 -0
- package/build/src/akuma/archetype.d.ts +7 -4
- package/build/src/akuma/archetype.js +15 -16
- package/build/src/akuma/body.d.ts +3 -1
- package/build/src/akuma/body.js +19 -8
- package/build/src/akuma/heart/facts.d.ts +49 -7
- package/build/src/akuma/heart/index.d.ts +4 -8
- package/build/src/akuma/heart/index.js +76 -15
- package/build/src/akuma/heart/rows.d.ts +7 -5
- package/build/src/akuma/heart/rows.js +98 -11
- package/build/src/akuma/heart/schema.d.ts +1 -1
- package/build/src/akuma/heart/schema.js +15 -10
- package/build/src/akuma/heart/soul.js +3 -1
- package/build/src/akuma/heart/storage.d.ts +2 -0
- package/build/src/akuma/heart/storage.js +20 -0
- package/build/src/akuma/heart/timeline.d.ts +1 -5
- package/build/src/akuma/heart/timeline.js +8 -17
- package/build/src/akuma/index.d.ts +4 -1
- package/build/src/akuma/index.js +1 -0
- package/build/src/akuma/projection.d.ts +17 -3
- package/build/src/akuma/projection.js +40 -3
- package/build/src/akuma/provider.d.ts +1 -1
- package/build/src/akuma/provider.js +2 -1
- package/build/src/akuma/providers/acp/core.d.ts +3 -1
- package/build/src/akuma/providers/acp/core.js +4 -4
- package/build/src/akuma/providers/acp/events.d.ts +11 -3
- package/build/src/akuma/providers/acp/events.js +78 -4
- package/build/src/akuma/providers/claude/events.js +62 -3
- package/build/src/akuma/providers/codex-app-server/events.js +1 -13
- package/build/src/akuma/providers/grok-build/index.d.ts +2 -1
- package/build/src/akuma/providers/grok-build/index.js +72 -2
- package/build/src/akuma/providers/opencode-sdk/events.js +71 -6
- package/build/src/akuma/providers/pi/events.js +17 -3
- package/build/src/akuma/providers/unified-patch.d.ts +4 -0
- package/build/src/akuma/providers/unified-patch.js +14 -0
- package/build/src/akuma/publication.d.ts +1 -1
- package/build/src/akuma/publication.js +36 -7
- package/build/src/akuma/requests.d.ts +70 -4
- package/build/src/akuma/requests.js +288 -77
- package/build/src/akuma-body.d.ts +1 -0
- package/build/src/akuma-body.js +31 -0
- package/build/src/cli/accepted.d.ts +4 -1
- package/build/src/cli/accepted.js +26 -4
- package/build/src/cli/commands/akuma-invoke.d.ts +8 -7
- package/build/src/cli/commands/akuma-invoke.js +18 -10
- package/build/src/cli/commands/akuma.d.ts +11 -2
- package/build/src/cli/commands/akuma.js +67 -28
- package/build/src/cli/commands/amend.d.ts +1 -1
- package/build/src/cli/commands/amend.js +1 -1
- package/build/src/cli/commands/contract.d.ts +3 -3
- package/build/src/cli/commands/contract.js +1 -1
- package/build/src/cli/commands/install.js +4 -4
- package/build/src/cli/commands/task-query.d.ts +1 -1
- package/build/src/cli/commands/task-query.js +11 -5
- package/build/src/cli/commands/task.js +4 -4
- package/build/src/cli/coordinates.d.ts +1 -0
- package/build/src/cli/coordinates.js +5 -1
- package/build/src/cli/invoke.d.ts +1 -0
- package/build/src/cli/invoke.js +90 -73
- package/build/src/cli/main.d.ts +2 -0
- package/build/src/cli/main.js +29 -4
- package/build/src/cli/parse.d.ts +1 -0
- package/build/src/cli/parse.js +8 -4
- package/build/src/cli/render/akuma.d.ts +2 -2
- package/build/src/cli/render/akuma.js +84 -13
- package/build/src/cli/render/audit.js +16 -2
- package/build/src/cli/render/contract.d.ts +2 -0
- package/build/src/cli/render/contract.js +203 -36
- package/build/src/cli/render/kanshi.js +64 -29
- package/build/src/cli/render/receipt.d.ts +2 -1
- package/build/src/cli/render/receipt.js +9 -1
- package/build/src/cli/render/text.js +3 -1
- package/build/src/cli/result.d.ts +38 -3
- package/build/src/cli/selectors.d.ts +1 -0
- package/build/src/cli/selectors.js +9 -6
- package/build/src/cli/usage.d.ts +2 -0
- package/build/src/cli/usage.js +4 -0
- package/build/src/contract-worktree.js +3 -0
- package/build/src/dispatch/index.js +50 -39
- package/build/src/git/hooks.d.ts +0 -4
- package/build/src/git/hooks.js +0 -36
- package/build/src/git/integration.d.ts +2 -6
- package/build/src/git/integration.js +8 -8
- package/build/src/git/read-observation.js +1 -0
- package/build/src/git/reconcile.d.ts +6 -1
- package/build/src/git/reconcile.js +55 -9
- package/build/src/git/tender.d.ts +19 -4
- package/build/src/git/tender.js +44 -13
- package/build/src/git/terminal-seal.d.ts +14 -0
- package/build/src/git/terminal-seal.js +15 -2
- package/build/src/git/workspace.d.ts +1 -0
- package/build/src/git/workspace.js +12 -4
- package/build/src/index.d.ts +1 -1
- package/build/src/kanshi/index.d.ts +1 -1
- package/build/src/kanshi/index.js +1 -1
- package/build/src/kanshi/read.d.ts +9 -1
- package/build/src/kanshi/read.js +91 -37
- package/build/src/kanshi/report.d.ts +1 -0
- package/build/src/library/address.d.ts +5 -14
- package/build/src/library/address.js +20 -22
- package/build/src/library/akuma-creation.d.ts +4 -2
- package/build/src/library/akuma-creation.js +43 -26
- package/build/src/library/bind.js +3 -3
- package/build/src/library/catalog.d.ts +1 -2
- package/build/src/library/catalog.js +11 -6
- package/build/src/library/configuration.d.ts +4 -0
- package/build/src/library/configuration.js +19 -0
- package/build/src/library/contract.d.ts +15 -1
- package/build/src/library/contract.js +51 -4
- package/build/src/library/fleet.d.ts +47 -9
- package/build/src/library/fleet.js +184 -44
- package/build/src/library/input.js +1 -0
- package/build/src/library/keiyaku.d.ts +4 -4
- package/build/src/library/keiyaku.js +1 -2
- package/build/src/protocol/bind.d.ts +1 -2
- package/build/src/protocol/bind.js +2 -16
- package/build/src/protocol/operations.d.ts +4 -1
- package/build/src/protocol/operations.js +33 -27
- package/build/src/protocol/read/status.d.ts +3 -1
- package/build/src/protocol/read/status.js +24 -14
- package/build/src/runtime/proc/run.d.ts +1 -0
- package/build/src/runtime/proc/run.js +9 -2
- package/build/src/settlement/settle.d.ts +1 -0
- package/build/src/settlement/settle.js +4 -1
- package/build/src/task/board.d.ts +18 -3
- package/build/src/task/board.js +73 -26
- package/build/src/task/index.d.ts +3 -3
- package/build/src/task/index.js +7 -5
- package/build/src/task/operations.d.ts +2 -19
- package/build/src/task/operations.js +29 -7
- package/build/src/task/query.d.ts +9 -2
- package/build/src/task/query.js +32 -64
- package/build/src/verification/execution.js +2 -1
- package/package.json +3 -1
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { renderAcceptedAudit } from "./audit.js";
|
|
2
|
-
import { appendHookPayload, cleanupLines, hookFailureSummary, leakLines, outcomeLines, receiptPayload, receiptRow, reuseLines, stopLines, } from "./receipt.js";
|
|
2
|
+
import { appendHookPayload, cleanupLines, hookFailureSummary, leakLines, outcomeLines, receiptPayload, receiptRow, reuseLines, stopLines, titleLines, } from "./receipt.js";
|
|
3
3
|
import { gitShortStat, renderOpaqueBlock } from "./terminal.js";
|
|
4
4
|
const HANG = " ";
|
|
5
5
|
function isRecord(value) {
|
|
@@ -30,6 +30,13 @@ function effectRows(effect, columns) {
|
|
|
30
30
|
{ text: effect.path, opaque: true },
|
|
31
31
|
], columns);
|
|
32
32
|
}
|
|
33
|
+
else if (effect.kind === "recovery-snapshot") {
|
|
34
|
+
receiptRow(lines, mark, "recovery-snapshot", [
|
|
35
|
+
{ text: effect.action },
|
|
36
|
+
{ text: effect.snapshot, opaque: true },
|
|
37
|
+
{ text: effect.retention },
|
|
38
|
+
], columns);
|
|
39
|
+
}
|
|
33
40
|
else {
|
|
34
41
|
receiptRow(lines, mark, "ref", [
|
|
35
42
|
{ text: effect.action },
|
|
@@ -104,7 +111,6 @@ function pushBlock(lines, block) {
|
|
|
104
111
|
}
|
|
105
112
|
function acceptedRecord(result, columns) {
|
|
106
113
|
const record = [];
|
|
107
|
-
receiptRow(record, " ", "head", [{ text: result.head, opaque: true }], columns);
|
|
108
114
|
for (const fact of result.facts) {
|
|
109
115
|
const contract = fact.contract === result.contract ? [] : [{ text: fact.contract, opaque: true }];
|
|
110
116
|
receiptRow(record, " ", "journal", [
|
|
@@ -113,15 +119,10 @@ function acceptedRecord(result, columns) {
|
|
|
113
119
|
{ text: `· ${fact.kind}` },
|
|
114
120
|
], columns);
|
|
115
121
|
}
|
|
116
|
-
|
|
117
|
-
receiptRow(record, " ", "target", [{ text: result.target ?? "null", opaque: true }], columns);
|
|
118
|
-
}
|
|
122
|
+
receiptRow(record, " ", "head", [{ text: result.head, opaque: true }], columns);
|
|
119
123
|
if (result.verb === "deliver") {
|
|
120
124
|
pushBlock(record, reuseLines(result.verificationReuse, columns));
|
|
121
125
|
}
|
|
122
|
-
if (result.verb === "amend") {
|
|
123
|
-
receiptPayload(record, "diff", result.diff);
|
|
124
|
-
}
|
|
125
126
|
const changed = result.effects.filter(changedEffect);
|
|
126
127
|
const unchanged = result.effects.filter((effect) => !changedEffect(effect));
|
|
127
128
|
for (const effect of [...changed, ...unchanged])
|
|
@@ -146,22 +147,15 @@ function acceptedLagRows(result, columns) {
|
|
|
146
147
|
}
|
|
147
148
|
return obligations;
|
|
148
149
|
}
|
|
149
|
-
function
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
if (result.cleanup !== undefined)
|
|
159
|
-
pushBlock(obligations, cleanupLines(result.cleanup, columns));
|
|
160
|
-
if (result.leak !== undefined)
|
|
161
|
-
pushBlock(obligations, leakLines(result.leak, columns));
|
|
162
|
-
}
|
|
163
|
-
obligations.push(...acceptedLagRows(result, columns));
|
|
164
|
-
return obligations;
|
|
150
|
+
function indentRecord(lines) {
|
|
151
|
+
let payload = false;
|
|
152
|
+
return lines.map((line) => {
|
|
153
|
+
if (line.length === 0) {
|
|
154
|
+
payload = !payload;
|
|
155
|
+
return line;
|
|
156
|
+
}
|
|
157
|
+
return payload ? line : ` ${line}`;
|
|
158
|
+
});
|
|
165
159
|
}
|
|
166
160
|
function acceptedDeviations(result, columns) {
|
|
167
161
|
const deviations = [];
|
|
@@ -178,32 +172,120 @@ function acceptedDeviations(result, columns) {
|
|
|
178
172
|
}
|
|
179
173
|
return deviations;
|
|
180
174
|
}
|
|
181
|
-
function
|
|
182
|
-
const
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
175
|
+
function recordBlock(result, columns) {
|
|
176
|
+
const rows = [...acceptedRecord(result, columns), ...acceptedLagRows(result, columns)];
|
|
177
|
+
return [" record", ...indentRecord(rows)];
|
|
178
|
+
}
|
|
179
|
+
function verificationVerdictLine(verdict, columns) {
|
|
180
|
+
const lines = [];
|
|
181
|
+
receiptRow(lines, verdict === "satisfied" ? "✓" : "!", "verification", [
|
|
182
|
+
{ text: verdict === "satisfied" ? "passed" : "failed" },
|
|
183
|
+
], columns);
|
|
184
|
+
return lines;
|
|
185
|
+
}
|
|
186
|
+
function renderAcceptedBind(result, columns) {
|
|
187
|
+
const lines = titleLines("✓", "bound", result.contract, columns);
|
|
188
|
+
receiptRow(lines, " ", "workspace", [
|
|
189
|
+
{ text: result.workspace === "worktree" ? "managed worktree" : "here" },
|
|
190
|
+
], columns);
|
|
191
|
+
if (result.target === null)
|
|
192
|
+
receiptRow(lines, " ", "no target", [], columns);
|
|
193
|
+
else
|
|
194
|
+
receiptRow(lines, " ", "target", [{ text: result.target, opaque: true }], columns);
|
|
195
|
+
lines.push(...acceptedDeviations(result, columns), ...recordBlock(result, columns));
|
|
196
|
+
return lines.join("\n");
|
|
197
|
+
}
|
|
198
|
+
function renderAcceptedAmend(result, columns) {
|
|
199
|
+
const lines = titleLines("✓", "terms replaced", result.contract, columns);
|
|
200
|
+
receiptPayload(lines, " terms diff", result.diff);
|
|
201
|
+
lines.push(...acceptedDeviations(result, columns), ...recordBlock(result, columns));
|
|
202
|
+
return lines.join("\n");
|
|
203
|
+
}
|
|
204
|
+
function renderAcceptedDeliver(result, columns) {
|
|
205
|
+
const complete = result.facts.some((fact) => fact.kind === "claimed");
|
|
206
|
+
const title = complete ? "delivered" : "deliver — not complete";
|
|
207
|
+
const lines = titleLines("✓", title, result.contract, columns);
|
|
208
|
+
if (!complete)
|
|
209
|
+
receiptRow(lines, " ", "candidate", [{ text: "kept" }], columns);
|
|
210
|
+
if (result.verification !== undefined) {
|
|
211
|
+
lines.push(...stopLines("verification", result.verification, columns, result.contract));
|
|
186
212
|
}
|
|
187
|
-
else {
|
|
188
|
-
lines.push(...
|
|
213
|
+
else if (result.verificationVerdict !== undefined) {
|
|
214
|
+
lines.push(...verificationVerdictLine(result.verificationVerdict, columns));
|
|
215
|
+
}
|
|
216
|
+
if (!complete && result.placement !== undefined) {
|
|
217
|
+
lines.push(...stopLines("completion", result.placement, columns, result.contract));
|
|
218
|
+
}
|
|
219
|
+
else if (!complete && (result.verification !== undefined || result.verificationVerdict === "unsatisfied")) {
|
|
220
|
+
receiptRow(lines, "·", "completion", [{ text: "not attempted" }], columns);
|
|
221
|
+
}
|
|
222
|
+
if (result.cleanup !== undefined)
|
|
223
|
+
pushBlock(lines, cleanupLines(result.cleanup, columns));
|
|
224
|
+
if (result.leak !== undefined)
|
|
225
|
+
pushBlock(lines, leakLines(result.leak, columns));
|
|
226
|
+
lines.push(...recordBlock(result, columns));
|
|
227
|
+
return lines.join("\n");
|
|
228
|
+
}
|
|
229
|
+
function renderAcceptedReview(result, columns) {
|
|
230
|
+
const complete = result.facts.some((fact) => fact.kind === "claimed");
|
|
231
|
+
const lines = titleLines("✓", `review ${result.verdict}`, result.contract, columns);
|
|
232
|
+
receiptRow(lines, complete ? "✓" : "!", "contract", [
|
|
233
|
+
{ text: complete ? "complete" : "not complete" },
|
|
234
|
+
], columns);
|
|
235
|
+
if (result.placement !== undefined) {
|
|
236
|
+
lines.push(...stopLines("completion", result.placement, columns, result.contract));
|
|
189
237
|
}
|
|
190
|
-
|
|
191
|
-
|
|
238
|
+
lines.push(...acceptedDeviations(result, columns), ...recordBlock(result, columns));
|
|
239
|
+
return lines.join("\n");
|
|
240
|
+
}
|
|
241
|
+
function renderAcceptedArc(result, columns) {
|
|
242
|
+
const lines = titleLines("✓", "chapter recorded", result.contract, columns);
|
|
243
|
+
receiptRow(lines, " ", "chapter", [
|
|
244
|
+
{ text: String(result.chapter.seq) },
|
|
245
|
+
{ text: "·" },
|
|
246
|
+
{ text: result.chapter.title },
|
|
247
|
+
], columns);
|
|
248
|
+
lines.push(...recordBlock(result, columns));
|
|
249
|
+
return lines.join("\n");
|
|
250
|
+
}
|
|
251
|
+
function renderAcceptedAbandon(result, columns) {
|
|
252
|
+
const lines = titleLines("✓", "abandoned", result.contract, columns);
|
|
253
|
+
if (result.note !== undefined)
|
|
254
|
+
receiptRow(lines, " ", "note", [{ text: result.note }], columns);
|
|
255
|
+
for (const effect of result.effects) {
|
|
256
|
+
if (effect.kind === "worktree") {
|
|
257
|
+
receiptRow(lines, " ", "workspace", [
|
|
258
|
+
{ text: effect.action },
|
|
259
|
+
{ text: effect.path, opaque: true },
|
|
260
|
+
], columns);
|
|
261
|
+
}
|
|
262
|
+
else if (effect.kind === "recovery-snapshot") {
|
|
263
|
+
receiptRow(lines, " ", "recovery snapshot", [
|
|
264
|
+
{ text: effect.snapshot, opaque: true },
|
|
265
|
+
{ text: `· ${effect.retention}` },
|
|
266
|
+
], columns);
|
|
267
|
+
}
|
|
192
268
|
}
|
|
193
|
-
lines.push(...
|
|
269
|
+
lines.push(...recordBlock(result, columns));
|
|
194
270
|
return lines.join("\n");
|
|
195
271
|
}
|
|
196
272
|
export function renderAccepted(result, context) {
|
|
273
|
+
const columns = context?.columns ?? 80;
|
|
197
274
|
switch (result.verb) {
|
|
198
275
|
case "audit":
|
|
199
276
|
return renderAcceptedAudit(result, context);
|
|
200
277
|
case "bind":
|
|
278
|
+
return renderAcceptedBind(result, columns);
|
|
201
279
|
case "amend":
|
|
202
|
-
|
|
280
|
+
return renderAcceptedAmend(result, columns);
|
|
203
281
|
case "review":
|
|
282
|
+
return renderAcceptedReview(result, columns);
|
|
204
283
|
case "arc":
|
|
284
|
+
return renderAcceptedArc(result, columns);
|
|
205
285
|
case "abandon":
|
|
206
|
-
return
|
|
286
|
+
return renderAcceptedAbandon(result, columns);
|
|
287
|
+
case "deliver":
|
|
288
|
+
return renderAcceptedDeliver(result, columns);
|
|
207
289
|
}
|
|
208
290
|
}
|
|
209
291
|
export function renderRetry(result, context) {
|
|
@@ -213,3 +295,88 @@ export function renderRetry(result, context) {
|
|
|
213
295
|
: [];
|
|
214
296
|
return [...outcomeLines("?", result.verb, "retry", result.contract, columns), ...detail].join("\n");
|
|
215
297
|
}
|
|
298
|
+
function journalCount(events, source) {
|
|
299
|
+
return events.filter((event) => event.source === source).length;
|
|
300
|
+
}
|
|
301
|
+
function journalHead(fact) {
|
|
302
|
+
return fact.actor === undefined
|
|
303
|
+
? `${fact.at} ${fact.kind} · ${fact.entry}`
|
|
304
|
+
: `${fact.at} ${fact.kind} · ${fact.entry} · ${fact.actor}`;
|
|
305
|
+
}
|
|
306
|
+
function listFact(label, values) {
|
|
307
|
+
return values.length === 0 ? [` ${label} 0`] : [` ${label} ${values.join(" · ")}`];
|
|
308
|
+
}
|
|
309
|
+
function journalBody(fact) {
|
|
310
|
+
switch (fact.kind) {
|
|
311
|
+
case "bind": {
|
|
312
|
+
const { coordinates, terms } = fact.data;
|
|
313
|
+
return [
|
|
314
|
+
` start ${coordinates.start}`,
|
|
315
|
+
...(coordinates.target === undefined ? [] : [` target ${coordinates.target}`]),
|
|
316
|
+
` workspace ${coordinates.workspace}`,
|
|
317
|
+
` document ${terms.document.key}`,
|
|
318
|
+
...listFact("gates", terms.gates),
|
|
319
|
+
...listFact("after", terms.after),
|
|
320
|
+
];
|
|
321
|
+
}
|
|
322
|
+
case "amend":
|
|
323
|
+
return [
|
|
324
|
+
` document ${fact.data.document.key}`,
|
|
325
|
+
...listFact("gates", fact.data.gates),
|
|
326
|
+
...listFact("after", fact.data.after),
|
|
327
|
+
];
|
|
328
|
+
case "bound":
|
|
329
|
+
return [];
|
|
330
|
+
case "deliver": {
|
|
331
|
+
const { tenderSnapshot, integration, method, policy } = fact.data;
|
|
332
|
+
return [
|
|
333
|
+
` tender ${tenderSnapshot}`,
|
|
334
|
+
` predecessor ${integration.predecessor}`,
|
|
335
|
+
` snapshot ${integration.snapshot}`,
|
|
336
|
+
` change ${integration.changeId}`,
|
|
337
|
+
` method ${method}`,
|
|
338
|
+
` require-branches-to-be-up-to-date ${String(policy.requireBranchesToBeUpToDate)}`,
|
|
339
|
+
];
|
|
340
|
+
}
|
|
341
|
+
case "attestation": {
|
|
342
|
+
const lines = [
|
|
343
|
+
` gate ${fact.data.gate}`,
|
|
344
|
+
` verdict ${fact.data.verdict}`,
|
|
345
|
+
` subject ${fact.data.subject}`,
|
|
346
|
+
];
|
|
347
|
+
if (fact.data.summary !== undefined)
|
|
348
|
+
receiptPayload(lines, "summary", fact.data.summary);
|
|
349
|
+
return lines;
|
|
350
|
+
}
|
|
351
|
+
case "claimed":
|
|
352
|
+
return [` delivery ${fact.data.delivery}`];
|
|
353
|
+
case "arc": {
|
|
354
|
+
const lines = [` sequence ${String(fact.data.seq)}`, ` title ${fact.data.title}`];
|
|
355
|
+
receiptPayload(lines, "objective", fact.data.objective);
|
|
356
|
+
receiptPayload(lines, "brief", fact.data.brief);
|
|
357
|
+
return lines;
|
|
358
|
+
}
|
|
359
|
+
case "abandoned": {
|
|
360
|
+
if (fact.data.note === undefined)
|
|
361
|
+
return [];
|
|
362
|
+
const lines = [];
|
|
363
|
+
receiptPayload(lines, "note", fact.data.note);
|
|
364
|
+
return lines;
|
|
365
|
+
}
|
|
366
|
+
}
|
|
367
|
+
}
|
|
368
|
+
function contractHistoryEventLines(event) {
|
|
369
|
+
if (event.source === "dispatch") {
|
|
370
|
+
return [`${event.dispatch.dispatchedAt} dispatch · ${event.dispatch.akuId}`];
|
|
371
|
+
}
|
|
372
|
+
return [journalHead(event.fact), ...journalBody(event.fact)];
|
|
373
|
+
}
|
|
374
|
+
export function renderContractHistory(history) {
|
|
375
|
+
const journals = journalCount(history.events, "journal");
|
|
376
|
+
const dispatches = journalCount(history.events, "dispatch");
|
|
377
|
+
return [
|
|
378
|
+
`history ${history.id} · ${journals} journal · ${dispatches} dispatch`,
|
|
379
|
+
"",
|
|
380
|
+
...history.events.flatMap(contractHistoryEventLines),
|
|
381
|
+
].join("\n");
|
|
382
|
+
}
|
|
@@ -193,7 +193,56 @@ function endpointFact(id, observed) {
|
|
|
193
193
|
return `-> ${id} (unavailable)`;
|
|
194
194
|
return `-> ${id}`;
|
|
195
195
|
}
|
|
196
|
-
function
|
|
196
|
+
function renderNamespaceTasks(row, context) {
|
|
197
|
+
if (row.namespaceTasks.kind === "absent")
|
|
198
|
+
return plumbFacts(["namespace tasks absent"], context.columns);
|
|
199
|
+
if (row.namespaceTasks.kind === "failed") {
|
|
200
|
+
return plumbFacts([`namespace tasks failed ${row.namespaceTasks.failure.message}`], context.columns);
|
|
201
|
+
}
|
|
202
|
+
const lines = [...plumbFacts([`namespace tasks ${row.namespaceTasks.value.length}`], context.columns)];
|
|
203
|
+
for (const task of row.namespaceTasks.value) {
|
|
204
|
+
const scan = `${taskMark(task)} ${task.id} · P${task.priority} ${task.disposition}`;
|
|
205
|
+
const title = safeText(task.title);
|
|
206
|
+
const inline = `${scan} — ${title}`;
|
|
207
|
+
if (displayColumns(inline) <= context.columns - displayColumns(PLUMB)) {
|
|
208
|
+
lines.push(...plumbFacts([inline], context.columns));
|
|
209
|
+
}
|
|
210
|
+
else {
|
|
211
|
+
lines.push(...plumbFacts([`${scan} —`], context.columns));
|
|
212
|
+
lines.push(...plumbBlock(title, context.columns));
|
|
213
|
+
}
|
|
214
|
+
}
|
|
215
|
+
return lines;
|
|
216
|
+
}
|
|
217
|
+
function renderContractRow(row, report, context, selection) {
|
|
218
|
+
const hot = contractHot(row);
|
|
219
|
+
const compact = !hot && selection !== "contract";
|
|
220
|
+
const title = row.title ?? "title unavailable";
|
|
221
|
+
const phase = `${row.phase} · ${formatAge(row.phaseAt, report.observedAt)}`;
|
|
222
|
+
const lines = [identityLine(contractMark(row), row.id)];
|
|
223
|
+
lines.push(...plumbFacts(compact ? [title, phase, ...targetFacts(row)] : [title], context.columns));
|
|
224
|
+
if (!compact)
|
|
225
|
+
lines.push(...plumbFacts([phase, ...targetFacts(row)], context.columns));
|
|
226
|
+
lines.push(...plumbFacts([workspaceState(row)], context.columns));
|
|
227
|
+
if (showWorkspacePath(row, hot || selection === "contract")
|
|
228
|
+
&& row.workspaceObservation.kind !== "unappointed"
|
|
229
|
+
&& row.workspaceObservation.location.kind === "worktree") {
|
|
230
|
+
lines.push(plumbPath(row.workspaceObservation.location.path));
|
|
231
|
+
}
|
|
232
|
+
lines.push(...renderGates(row.gates.reports, report.observedAt, context.columns, selection === "contract"));
|
|
233
|
+
if (row.holder.kind === "held")
|
|
234
|
+
lines.push(...plumbFacts([`task ${row.holder.taskId}`], context.columns));
|
|
235
|
+
if (row.holder.kind === "unavailable")
|
|
236
|
+
lines.push(...plumbFacts(["holder unavailable"], context.columns));
|
|
237
|
+
for (const attached of row.fleet) {
|
|
238
|
+
const aliases = attached.aliases.length === 0 ? "" : ` (${attached.aliases.join(" ")})`;
|
|
239
|
+
lines.push(...plumbFacts([`akuma ${attached.id}${aliases}`], context.columns));
|
|
240
|
+
}
|
|
241
|
+
if (selection === "contract")
|
|
242
|
+
lines.push(...renderNamespaceTasks(row, context));
|
|
243
|
+
return lines;
|
|
244
|
+
}
|
|
245
|
+
function renderContracts(report, context) {
|
|
197
246
|
const section = report.contracts;
|
|
198
247
|
if (section.kind === "absent")
|
|
199
248
|
return sectionAbsent("KEIYAKU", context.columns);
|
|
@@ -204,37 +253,21 @@ function renderContracts(report, context, selection) {
|
|
|
204
253
|
...section.value.rows.filter((row) => !contractHot(row)),
|
|
205
254
|
];
|
|
206
255
|
const lines = [aperture("KEIYAKU", context.columns)];
|
|
207
|
-
for (const row of rows)
|
|
208
|
-
|
|
209
|
-
const compact = !hot && selection !== "contract";
|
|
210
|
-
const title = row.title ?? "title unavailable";
|
|
211
|
-
const phase = `${row.phase} · ${formatAge(row.phaseAt, report.observedAt)}`;
|
|
212
|
-
lines.push(identityLine(contractMark(row), row.id));
|
|
213
|
-
lines.push(...plumbFacts(compact
|
|
214
|
-
? [title, phase, ...targetFacts(row)]
|
|
215
|
-
: [title], context.columns));
|
|
216
|
-
if (!compact)
|
|
217
|
-
lines.push(...plumbFacts([phase, ...targetFacts(row)], context.columns));
|
|
218
|
-
lines.push(...plumbFacts([workspaceState(row)], context.columns));
|
|
219
|
-
if (showWorkspacePath(row, hot || selection === "contract")
|
|
220
|
-
&& row.workspaceObservation.kind !== "unappointed"
|
|
221
|
-
&& row.workspaceObservation.location.kind === "worktree") {
|
|
222
|
-
lines.push(plumbPath(row.workspaceObservation.location.path));
|
|
223
|
-
}
|
|
224
|
-
lines.push(...renderGates(row.gates.reports, report.observedAt, context.columns, selection === "contract"));
|
|
225
|
-
if (row.holder.kind === "held")
|
|
226
|
-
lines.push(...plumbFacts([`task ${row.holder.taskId}`], context.columns));
|
|
227
|
-
if (row.holder.kind === "unavailable")
|
|
228
|
-
lines.push(...plumbFacts(["holder unavailable"], context.columns));
|
|
229
|
-
for (const attached of row.fleet) {
|
|
230
|
-
const aliases = attached.aliases.length === 0 ? "" : ` (${attached.aliases.join(" ")})`;
|
|
231
|
-
lines.push(...plumbFacts([`akuma ${attached.id}${aliases}`], context.columns));
|
|
232
|
-
}
|
|
233
|
-
}
|
|
256
|
+
for (const row of rows)
|
|
257
|
+
lines.push(...renderContractRow(row, report, context, "world"));
|
|
234
258
|
const attention = rows.filter(contractHot).length;
|
|
235
259
|
lines.push(aperture(`${rows.length} keiyaku · ${attention} attention`, context.columns));
|
|
236
260
|
return lines;
|
|
237
261
|
}
|
|
262
|
+
function renderSelectedContract(report, context) {
|
|
263
|
+
const section = report.contracts;
|
|
264
|
+
if (section.kind === "absent")
|
|
265
|
+
return [`${PLUMB}keiyaku absent`];
|
|
266
|
+
if (section.kind === "failed")
|
|
267
|
+
return [tone(`! ${safeText(section.failure.message)}`, "alert", context.color)];
|
|
268
|
+
const row = section.value.rows[0];
|
|
269
|
+
return row === undefined ? [`${PLUMB}keiyaku absent`] : renderContractRow(row, report, context, "contract");
|
|
270
|
+
}
|
|
238
271
|
function renderTasks(report, context) {
|
|
239
272
|
const section = report.tasks;
|
|
240
273
|
if (section.kind === "absent")
|
|
@@ -335,10 +368,12 @@ function splitHorizon(report, columns) {
|
|
|
335
368
|
return [`kanshi ${HORIZON}${RULE.repeat(left)} ${aggregate} ${HORIZON}${RULE.repeat(right)} ${world}`];
|
|
336
369
|
}
|
|
337
370
|
export function renderKanshiText(report, context = { columns: 80, color: false }, selection = "world") {
|
|
371
|
+
if (selection === "contract")
|
|
372
|
+
return renderSelectedContract(report, context).join("\n");
|
|
338
373
|
return [
|
|
339
374
|
...splitHorizon(report, context.columns),
|
|
340
375
|
"",
|
|
341
|
-
...renderContracts(report, context
|
|
376
|
+
...renderContracts(report, context),
|
|
342
377
|
"",
|
|
343
378
|
...renderTasks(report, context),
|
|
344
379
|
"",
|
|
@@ -10,10 +10,11 @@ type HookFailure = Extract<Lag, {
|
|
|
10
10
|
export declare function receiptRow(lines: string[], mark: string, label: string, segments: readonly ReceiptSegment[], columns: number): void;
|
|
11
11
|
export declare function receiptPayload(lines: string[], label: string, payload: string): void;
|
|
12
12
|
export declare function outcomeLines(mark: "✓" | "!" | "?", verb: string, word: "accepted" | "refused" | "retry", contract: string | undefined, columns?: number): string[];
|
|
13
|
+
export declare function titleLines(mark: string, title: string, contract: string, columns?: number): string[];
|
|
13
14
|
export declare function hookFailureSummary(failure: HookFailure): string;
|
|
14
15
|
export declare function appendHookPayload(lines: string[], failure: HookFailure): void;
|
|
15
16
|
export declare function reuseLines(reuse: VerificationReuse | undefined, columns: number): readonly string[];
|
|
16
|
-
export declare function stopLines(label: "verification" | "
|
|
17
|
+
export declare function stopLines(label: "verification" | "completion", stop: VerificationStop | PlacementStop, columns: number, addressed: string): readonly string[];
|
|
17
18
|
export declare function cleanupLines(cleanup: NonNullable<AcceptedDeliverResult["cleanup"]>, columns: number): readonly string[];
|
|
18
19
|
export declare function leakLines(leak: NonNullable<AcceptedDeliverResult["leak"]>, columns: number): readonly string[];
|
|
19
20
|
export {};
|
|
@@ -30,6 +30,13 @@ export function outcomeLines(mark, verb, word, contract, columns = 80) {
|
|
|
30
30
|
return [inline];
|
|
31
31
|
return [`${base} —`, ` ${safeText(contract)}`];
|
|
32
32
|
}
|
|
33
|
+
export function titleLines(mark, title, contract, columns = 80) {
|
|
34
|
+
const base = `${mark} ${title}`;
|
|
35
|
+
const inline = `${base} — ${contract}`;
|
|
36
|
+
if (displayColumns(inline) <= columns)
|
|
37
|
+
return [inline];
|
|
38
|
+
return [`${base} —`, ` ${safeText(contract)}`];
|
|
39
|
+
}
|
|
33
40
|
export function hookFailureSummary(failure) {
|
|
34
41
|
if (failure.kind === "timeout" || failure.kind === "unknown-exit")
|
|
35
42
|
return failure.kind;
|
|
@@ -73,7 +80,8 @@ export function stopLines(label, stop, columns, addressed) {
|
|
|
73
80
|
}
|
|
74
81
|
}
|
|
75
82
|
const lines = [];
|
|
76
|
-
|
|
83
|
+
const state = label === "verification" ? "failed" : "blocked";
|
|
84
|
+
receiptRow(lines, "!", label, [{ text: state }, { text: "·" }, ...detail], columns);
|
|
77
85
|
if ("failure" in stop && stop.failure === "environment-failure" && "command" in stop) {
|
|
78
86
|
appendHookPayload(lines, stop.detail);
|
|
79
87
|
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { renderObservation } from "./board.js";
|
|
2
|
-
import { renderAccepted, renderRetry } from "./contract.js";
|
|
2
|
+
import { renderAccepted, renderContractHistory, renderRetry } from "./contract.js";
|
|
3
3
|
import { renderKanshiText } from "./kanshi.js";
|
|
4
4
|
import { renderRefusal } from "./refusal.js";
|
|
5
5
|
import { renderCatalogText } from "./catalog.js";
|
|
@@ -11,6 +11,8 @@ export function renderText(result, context) {
|
|
|
11
11
|
return renderKanshiText(result.report, context, result.selection);
|
|
12
12
|
if (result.kind === "catalog")
|
|
13
13
|
return renderCatalogText(result.catalog);
|
|
14
|
+
if (result.kind === "contract-history")
|
|
15
|
+
return renderContractHistory(result.history);
|
|
14
16
|
if (result.kind === "region")
|
|
15
17
|
return renderRegionText(result.region);
|
|
16
18
|
if (result.kind === "accepted")
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { AuditReport, ContractId, Fact, MutationResult, PlacementStop, ReconcileReport, Review, VerificationReuse, VerificationStop } from "../index.js";
|
|
1
|
+
import type { AuditReport, ContractHistory, ContractId, Fact, MutationResult, PlacementStop, ReconcileReport, Review, VerificationReuse, VerificationStop } from "../index.js";
|
|
2
2
|
import type { KanshiReport } from "../kanshi/index.js";
|
|
3
3
|
import type { RegionRead, Section } from "../kanshi/index.js";
|
|
4
4
|
import type { Catalog } from "../index.js";
|
|
@@ -29,6 +29,7 @@ export type AcceptedEnvelope = Readonly<{
|
|
|
29
29
|
}>;
|
|
30
30
|
export type AcceptedBindResult = AcceptedEnvelope & Readonly<{
|
|
31
31
|
verb: "bind";
|
|
32
|
+
workspace: "worktree" | "here";
|
|
32
33
|
target: string | null;
|
|
33
34
|
verification?: never;
|
|
34
35
|
verificationReuse?: never;
|
|
@@ -36,8 +37,11 @@ export type AcceptedBindResult = AcceptedEnvelope & Readonly<{
|
|
|
36
37
|
cleanup?: never;
|
|
37
38
|
leak?: never;
|
|
38
39
|
report?: never;
|
|
39
|
-
workspace?: never;
|
|
40
40
|
diff?: never;
|
|
41
|
+
verificationVerdict?: never;
|
|
42
|
+
verdict?: never;
|
|
43
|
+
chapter?: never;
|
|
44
|
+
note?: never;
|
|
41
45
|
}> & RegionObservation;
|
|
42
46
|
export type AcceptedAmendResult = AcceptedEnvelope & Readonly<{
|
|
43
47
|
verb: "amend";
|
|
@@ -50,9 +54,14 @@ export type AcceptedAmendResult = AcceptedEnvelope & Readonly<{
|
|
|
50
54
|
leak?: never;
|
|
51
55
|
report?: never;
|
|
52
56
|
workspace?: never;
|
|
57
|
+
verificationVerdict?: never;
|
|
58
|
+
verdict?: never;
|
|
59
|
+
chapter?: never;
|
|
60
|
+
note?: never;
|
|
53
61
|
}> & RegionObservation;
|
|
54
62
|
export type AcceptedDeliverResult = AcceptedEnvelope & Readonly<{
|
|
55
63
|
verb: "deliver";
|
|
64
|
+
verificationVerdict?: "satisfied" | "unsatisfied";
|
|
56
65
|
verification?: VerificationStop;
|
|
57
66
|
verificationReuse?: VerificationReuse;
|
|
58
67
|
placement?: PlacementStop;
|
|
@@ -64,9 +73,13 @@ export type AcceptedDeliverResult = AcceptedEnvelope & Readonly<{
|
|
|
64
73
|
report?: never;
|
|
65
74
|
workspace?: never;
|
|
66
75
|
diff?: never;
|
|
76
|
+
verdict?: never;
|
|
77
|
+
chapter?: never;
|
|
78
|
+
note?: never;
|
|
67
79
|
}>;
|
|
68
80
|
export type AcceptedReviewResult = AcceptedEnvelope & Readonly<{
|
|
69
81
|
verb: "review";
|
|
82
|
+
verdict: "satisfied" | "unsatisfied";
|
|
70
83
|
placement?: PlacementStop;
|
|
71
84
|
workspace?: Review["workspace"];
|
|
72
85
|
target?: never;
|
|
@@ -78,9 +91,16 @@ export type AcceptedReviewResult = AcceptedEnvelope & Readonly<{
|
|
|
78
91
|
overlapFailure?: never;
|
|
79
92
|
report?: never;
|
|
80
93
|
diff?: never;
|
|
94
|
+
verificationVerdict?: never;
|
|
95
|
+
chapter?: never;
|
|
96
|
+
note?: never;
|
|
81
97
|
}>;
|
|
82
98
|
export type AcceptedArcResult = AcceptedEnvelope & Readonly<{
|
|
83
99
|
verb: "arc";
|
|
100
|
+
chapter: Readonly<{
|
|
101
|
+
seq: number;
|
|
102
|
+
title: string;
|
|
103
|
+
}>;
|
|
84
104
|
target?: never;
|
|
85
105
|
verification?: never;
|
|
86
106
|
verificationReuse?: never;
|
|
@@ -92,9 +112,13 @@ export type AcceptedArcResult = AcceptedEnvelope & Readonly<{
|
|
|
92
112
|
report?: never;
|
|
93
113
|
workspace?: never;
|
|
94
114
|
diff?: never;
|
|
115
|
+
verificationVerdict?: never;
|
|
116
|
+
verdict?: never;
|
|
117
|
+
note?: never;
|
|
95
118
|
}>;
|
|
96
119
|
export type AcceptedAbandonResult = AcceptedEnvelope & Readonly<{
|
|
97
120
|
verb: "abandon";
|
|
121
|
+
note?: string;
|
|
98
122
|
target?: never;
|
|
99
123
|
verification?: never;
|
|
100
124
|
verificationReuse?: never;
|
|
@@ -106,6 +130,9 @@ export type AcceptedAbandonResult = AcceptedEnvelope & Readonly<{
|
|
|
106
130
|
report?: never;
|
|
107
131
|
workspace?: never;
|
|
108
132
|
diff?: never;
|
|
133
|
+
verificationVerdict?: never;
|
|
134
|
+
verdict?: never;
|
|
135
|
+
chapter?: never;
|
|
109
136
|
}>;
|
|
110
137
|
export type AcceptedAuditResult = AcceptedEnvelope & Readonly<{
|
|
111
138
|
verb: "audit";
|
|
@@ -120,6 +147,10 @@ export type AcceptedAuditResult = AcceptedEnvelope & Readonly<{
|
|
|
120
147
|
overlapFailure?: never;
|
|
121
148
|
workspace?: never;
|
|
122
149
|
diff?: never;
|
|
150
|
+
verificationVerdict?: never;
|
|
151
|
+
verdict?: never;
|
|
152
|
+
chapter?: never;
|
|
153
|
+
note?: never;
|
|
123
154
|
}>;
|
|
124
155
|
export type AcceptedResult = AcceptedBindResult | AcceptedAmendResult | AcceptedDeliverResult | AcceptedReviewResult | AcceptedArcResult | AcceptedAbandonResult | AcceptedAuditResult;
|
|
125
156
|
export type RefusedResult = Readonly<{
|
|
@@ -158,5 +189,9 @@ export type CatalogResult = Readonly<{
|
|
|
158
189
|
kind: "catalog";
|
|
159
190
|
catalog: Catalog;
|
|
160
191
|
}>;
|
|
161
|
-
export type
|
|
192
|
+
export type ContractHistoryResult = Readonly<{
|
|
193
|
+
kind: "contract-history";
|
|
194
|
+
history: ContractHistory;
|
|
195
|
+
}>;
|
|
196
|
+
export type InvocationResult = AcceptedResult | RefusedResult | RetryResult | ObservationResult | GuidanceResult | StatusResult | RegionResult | CatalogResult | ContractHistoryResult;
|
|
162
197
|
export {};
|
|
@@ -6,4 +6,5 @@ export type SelectedContract = Readonly<{
|
|
|
6
6
|
}>;
|
|
7
7
|
export declare function contractFromInput(repo: Repo, value: string): SelectedContract;
|
|
8
8
|
export declare function resolveContextualContract(board: ContractBoard, selector: string | undefined, scope: string): ContractId;
|
|
9
|
+
export declare function canonicalContractSelector(selector: string): ContractId;
|
|
9
10
|
export declare function resolveKanshiContract(report: KanshiReport, selector: string): string;
|
|
@@ -50,12 +50,7 @@ export function resolveContextualContract(board, selector, scope) {
|
|
|
50
50
|
return resolveShortContract(board.rows, selector);
|
|
51
51
|
return selectorError(`contract selector must be kei/<contract-segment> or @<contract-segment>: ${selector}`);
|
|
52
52
|
}
|
|
53
|
-
export function
|
|
54
|
-
if (report.contracts.kind !== "present") {
|
|
55
|
-
return selectorError(`cannot select a contract while the Contract world is ${report.contracts.kind}`);
|
|
56
|
-
}
|
|
57
|
-
if (selector.startsWith("@"))
|
|
58
|
-
return resolveShortContract(report.contracts.value.rows, selector);
|
|
53
|
+
export function canonicalContractSelector(selector) {
|
|
59
54
|
try {
|
|
60
55
|
identitySegments({ family: "kei", value: selector });
|
|
61
56
|
}
|
|
@@ -64,3 +59,11 @@ export function resolveKanshiContract(report, selector) {
|
|
|
64
59
|
}
|
|
65
60
|
return selector;
|
|
66
61
|
}
|
|
62
|
+
export function resolveKanshiContract(report, selector) {
|
|
63
|
+
if (report.contracts.kind !== "present") {
|
|
64
|
+
return selectorError(`cannot select a contract while the Contract world is ${report.contracts.kind}`);
|
|
65
|
+
}
|
|
66
|
+
if (selector.startsWith("@"))
|
|
67
|
+
return resolveShortContract(report.contracts.value.rows, selector);
|
|
68
|
+
return canonicalContractSelector(selector);
|
|
69
|
+
}
|
package/build/src/cli/usage.d.ts
CHANGED
|
@@ -3,5 +3,7 @@ export declare class CliUsageError extends Error {
|
|
|
3
3
|
readonly projection?: string | undefined;
|
|
4
4
|
constructor(diagnostic: string, projection?: string | undefined);
|
|
5
5
|
}
|
|
6
|
+
export declare const JSON_AUTOMATION_HELP = "--json is only for automation script input/output and should not be used for daily interactive use.";
|
|
7
|
+
export declare function withJsonAutomationHelp(help: string): string;
|
|
6
8
|
export declare function isBlankInput(value: string): boolean;
|
|
7
9
|
export declare function usageLine(usage: string): string;
|
package/build/src/cli/usage.js
CHANGED
|
@@ -8,6 +8,10 @@ export class CliUsageError extends Error {
|
|
|
8
8
|
this.name = "CliUsageError";
|
|
9
9
|
}
|
|
10
10
|
}
|
|
11
|
+
export const JSON_AUTOMATION_HELP = "--json is only for automation script input/output and should not be used for daily interactive use.";
|
|
12
|
+
export function withJsonAutomationHelp(help) {
|
|
13
|
+
return help.includes("--json") ? `${help}\n\n${JSON_AUTOMATION_HELP}` : help;
|
|
14
|
+
}
|
|
11
15
|
export function isBlankInput(value) {
|
|
12
16
|
return value.trim().length === 0;
|
|
13
17
|
}
|
|
@@ -48,6 +48,9 @@ const FULFILLMENT = [
|
|
|
48
48
|
"### Deliverer", "",
|
|
49
49
|
"Implement and verify the Objective under the Design, Region, and Criteria in this Contract.",
|
|
50
50
|
"When an Arc is active, stay within that current chapter.",
|
|
51
|
+
"For work requiring three or more steps, prefer `keiyaku task -C <worktree>` "
|
|
52
|
+
+ "to organize and manage Tasks.",
|
|
53
|
+
"Promptly update progress for Tasks already present in the current worktree.",
|
|
51
54
|
"Leave lifecycle decisions to the caller; report the candidate, verification performed, and any unmet term.", "",
|
|
52
55
|
"### Reviewer", "",
|
|
53
56
|
"Review this Contract worktree against the complete Contract.",
|