@janvitos/pi-plan-build 0.1.33 → 0.1.34
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 +2 -3
- package/index.ts +33 -34
- package/package.json +1 -1
- package/plan-execution.ts +36 -35
- package/plan-panel.ts +1 -3
- package/prompts.ts +3 -3
package/README.md
CHANGED
|
@@ -19,7 +19,7 @@ A global [Pi coding agent](https://github.com/badlogic/pi-mono) extension that a
|
|
|
19
19
|
- **Switch to Build and implement here**
|
|
20
20
|
- **Start fresh and implement**
|
|
21
21
|
- **Stay in Plan mode**
|
|
22
|
-
- **Experimental:** In fullscreen TUI, valid checklist plans also offer **Implement step by step**: a passive, non-overlapping docked right panel keeps the plan visible while natural-language prompts gate steps and
|
|
22
|
+
- **Experimental:** In fullscreen TUI, valid checklist plans also offer **Implement step by step**: a passive, non-overlapping docked right panel keeps the plan visible while natural-language prompts gate steps and report completed work. The panel is visual-only and never captures keyboard input. This feature is still under active development.
|
|
23
23
|
- Staying in Plan mode—or pressing Escape in the approval dialog—produces a durable acknowledgement and stops the run until the user responds.
|
|
24
24
|
- Mode state survives reloads, resumes, and forks.
|
|
25
25
|
- When Pi recreates the custom editor, the latest 100 user prompts from the active session branch are restored for Up/Down history navigation.
|
|
@@ -96,11 +96,10 @@ The passive 64-column right panel reserves terminal columns, so the transcript a
|
|
|
96
96
|
- “Implement the next step” or “Start step 2.”
|
|
97
97
|
- “Step 1 is complete,” “I verified that one,” or “I already handled this.”
|
|
98
98
|
- “Change step 3 to …” or “Skip this step.”
|
|
99
|
-
- “Accept this result” or “Correct it by …”
|
|
100
99
|
- “Pause the plan,” “hide the plan,” or “show the plan.”
|
|
101
100
|
- “Cancel this plan” at any point to end step-by-step execution immediately.
|
|
102
101
|
|
|
103
|
-
The extension exposes these actions to the agent through `plan_step_control`; project mutations remain blocked until the user clearly approves a ready step or explicitly indicates that it is already complete. A ready step may be marked complete without implementation when the user says they already handled or verified it.
|
|
102
|
+
The extension exposes these actions to the agent through `plan_step_control`; project mutations remain blocked until the user clearly approves a ready step or explicitly indicates that it is already complete. A ready step may be marked complete without implementation when the user says they already handled or verified it. An implemented step is marked completed immediately after verification, and the next step becomes ready without a review or acceptance phase. The agent interprets intent contextually rather than requiring exact phrases, while the extension validates every resulting state transition. Step tool results identify the affected step, for example `Step 2: complete`, rather than presenting a plan-wide completion label. When the final step is completed or skipped, the panel and execution guards are removed immediately and the main window receives a completion confirmation with a concise plan summary. Cancelling removes the panel and execution guards immediately, restores the full-width layout, and preserves the saved plan file for reference. The agent implements only that step, calls `plan_step_complete`, and waits for the user's next prompt. Progress, revisions, summaries, and panel visibility survive reload/resume. If such a session is opened in regular mode, progress is retained but cannot advance until fullscreen mode is restored; no overlay fallback is used.
|
|
104
103
|
|
|
105
104
|
Enable fullscreen in `~/.pi/agent/settings.json` and restart Pi:
|
|
106
105
|
|
package/index.ts
CHANGED
|
@@ -15,17 +15,15 @@ import {
|
|
|
15
15
|
PLAN_TO_BUILD_REMINDER,
|
|
16
16
|
} from "./prompts.ts";
|
|
17
17
|
import {
|
|
18
|
-
acceptPlanStep,
|
|
19
18
|
activePlanStep,
|
|
20
19
|
completePlanStep,
|
|
21
20
|
createPlanExecution,
|
|
22
21
|
decodePlanExecution,
|
|
22
|
+
formatPlanCompletionSummary,
|
|
23
23
|
pausePlanExecution,
|
|
24
|
-
requestPlanStepCorrections,
|
|
25
24
|
revisePlanStep,
|
|
26
25
|
skipPlanStep,
|
|
27
26
|
startPlanStep,
|
|
28
|
-
submitPlanStepForReview,
|
|
29
27
|
updatePlanChecklistStep,
|
|
30
28
|
type PlanExecutionState,
|
|
31
29
|
} from "./plan-execution.ts";
|
|
@@ -155,6 +153,19 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
155
153
|
applyTools("build");
|
|
156
154
|
}
|
|
157
155
|
|
|
156
|
+
function applyExecutionTransition(next: PlanExecutionState): string | undefined {
|
|
157
|
+
if (next.status !== "completed") {
|
|
158
|
+
updateExecution(next);
|
|
159
|
+
return undefined;
|
|
160
|
+
}
|
|
161
|
+
const summary = formatPlanCompletionSummary(next);
|
|
162
|
+
execution = undefined;
|
|
163
|
+
removePanelLayout();
|
|
164
|
+
persist();
|
|
165
|
+
applyTools("build");
|
|
166
|
+
return summary;
|
|
167
|
+
}
|
|
168
|
+
|
|
158
169
|
function ensurePanelLayout(): boolean {
|
|
159
170
|
if (!execution || !fullscreenPanelCapable || !panelTui || !originalLayoutRoot || !currentContext) return false;
|
|
160
171
|
if (!panel) panel = new PlanPanel(execution, currentContext.ui.theme);
|
|
@@ -199,7 +210,7 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
199
210
|
...base,
|
|
200
211
|
"question",
|
|
201
212
|
"plan_enter",
|
|
202
|
-
...(execution ? ["plan_step_control"] : []),
|
|
213
|
+
...(execution && execution.status !== "completed" ? ["plan_step_control"] : []),
|
|
203
214
|
...(activePlanStep(execution) ? ["plan_step_complete"] : []),
|
|
204
215
|
]));
|
|
205
216
|
}
|
|
@@ -379,13 +390,11 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
379
390
|
pi.registerTool({
|
|
380
391
|
name: "plan_step_control",
|
|
381
392
|
label: "Control Plan Execution",
|
|
382
|
-
description: `Use this tool to translate the user's natural-language instructions into one step-by-step plan action. Available actions: start a ready step, complete a clearly finished ready
|
|
393
|
+
description: `Use this tool to translate the user's natural-language instructions into one step-by-step plan action. Available actions: start a ready step, complete a clearly finished ready step, skip a ready step, revise an unimplemented instruction, pause/resume or cancel execution, or hide/show the visual plan panel. Interpret clear user intent semantically, including direct completion statements, but do not advance based on hypothetical, uncertain, or unrelated conversation.`,
|
|
383
394
|
parameters: Type.Object({
|
|
384
395
|
action: Type.Union([
|
|
385
396
|
Type.Literal("start"),
|
|
386
397
|
Type.Literal("complete"),
|
|
387
|
-
Type.Literal("accept"),
|
|
388
|
-
Type.Literal("correct"),
|
|
389
398
|
Type.Literal("skip"),
|
|
390
399
|
Type.Literal("revise"),
|
|
391
400
|
Type.Literal("pause"),
|
|
@@ -394,14 +403,14 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
394
403
|
Type.Literal("hide"),
|
|
395
404
|
Type.Literal("show"),
|
|
396
405
|
]),
|
|
397
|
-
step: Type.Optional(Type.Number({ description: "One-based step number; defaults to the current ready
|
|
406
|
+
step: Type.Optional(Type.Number({ description: "One-based step number; defaults to the current ready step", minimum: 1 })),
|
|
398
407
|
instruction: Type.Optional(Type.String({ description: "Replacement instruction required for revise" })),
|
|
399
408
|
}),
|
|
400
409
|
executionMode: "sequential",
|
|
401
410
|
async execute(_toolCallId, params) {
|
|
402
411
|
if (!execution) throw new Error("No step-by-step plan is active");
|
|
403
412
|
const target = params.step === undefined
|
|
404
|
-
? execution.steps.find((step) => step.status === "ready"
|
|
413
|
+
? execution.steps.find((step) => step.status === "ready")
|
|
405
414
|
: execution.steps[Math.floor(params.step) - 1];
|
|
406
415
|
const finish = (message: string) => ({
|
|
407
416
|
content: [{ type: "text" as const, text: message }],
|
|
@@ -418,7 +427,7 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
418
427
|
if (params.action === "show") ensurePanelLayout();
|
|
419
428
|
return finish(`The visual plan panel is now ${params.action === "show" ? "visible" : "hidden"}. Progress is unchanged.`);
|
|
420
429
|
}
|
|
421
|
-
if (execution.status === "completed") throw new Error("The plan is complete
|
|
430
|
+
if (execution.status === "completed") throw new Error("The plan is already complete");
|
|
422
431
|
if (params.action === "pause" || params.action === "resume") {
|
|
423
432
|
if ((params.action === "pause") === (execution.status === "paused")) return finish(`Plan execution is already ${params.action === "pause" ? "paused" : "running"}.`);
|
|
424
433
|
updateExecution(pausePlanExecution(execution));
|
|
@@ -433,22 +442,12 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
433
442
|
return finish("The requested step is approved. Its implementation is starting in a follow-up turn.");
|
|
434
443
|
}
|
|
435
444
|
if (params.action === "complete") {
|
|
436
|
-
|
|
437
|
-
return finish(
|
|
438
|
-
}
|
|
439
|
-
if (params.action === "accept") {
|
|
440
|
-
updateExecution(acceptPlanStep(execution, target.id));
|
|
441
|
-
return finish(execution.status === "completed" ? "The reviewed step was accepted and the plan is complete." : "The reviewed step was accepted. The next step is ready and awaits user instruction.");
|
|
442
|
-
}
|
|
443
|
-
if (params.action === "correct") {
|
|
444
|
-
updateExecution(requestPlanStepCorrections(execution, target.id));
|
|
445
|
-
applyTools("build");
|
|
446
|
-
pi.sendUserMessage(`Apply the corrections requested in the user's preceding message to plan step ${execution.steps.findIndex((step) => step.id === target.id) + 1}.`, { deliverAs: "followUp" });
|
|
447
|
-
return finish("The reviewed step was reopened. The requested corrections are starting in a follow-up turn.");
|
|
445
|
+
const completion = applyExecutionTransition(completePlanStep(execution, target.id));
|
|
446
|
+
return finish(completion ?? "The step was marked complete. The next step is ready and awaits user instruction.");
|
|
448
447
|
}
|
|
449
448
|
if (params.action === "skip") {
|
|
450
|
-
|
|
451
|
-
return finish(
|
|
449
|
+
const completion = applyExecutionTransition(skipPlanStep(execution, target.id));
|
|
450
|
+
return finish(completion ?? "The step was skipped. The next step awaits user instruction.");
|
|
452
451
|
}
|
|
453
452
|
if (!params.instruction?.trim()) throw new Error("Revising a step requires a replacement instruction");
|
|
454
453
|
const plan = await fs.promises.readFile(planPath, "utf8");
|
|
@@ -460,7 +459,7 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
460
459
|
renderCall(args, theme) {
|
|
461
460
|
const requestedStep = typeof args.step === "number" && Number.isFinite(args.step) ? Math.max(1, Math.floor(args.step)) : undefined;
|
|
462
461
|
const inferredStep = requestedStep ?? (execution
|
|
463
|
-
? execution.steps.findIndex((step) => step.status === "ready"
|
|
462
|
+
? execution.steps.findIndex((step) => step.status === "ready") + 1
|
|
464
463
|
: 0);
|
|
465
464
|
const label = inferredStep > 0 ? `Step ${inferredStep}: ${args.action}` : `Plan: ${args.action}`;
|
|
466
465
|
return new Text(theme.fg("toolTitle", theme.bold(label)), 0, 0);
|
|
@@ -482,19 +481,19 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
482
481
|
async execute(_toolCallId, params) {
|
|
483
482
|
const step = activePlanStep(execution);
|
|
484
483
|
if (!execution || !step) throw new Error("No plan step is currently active");
|
|
485
|
-
|
|
486
|
-
applyTools("build");
|
|
484
|
+
const completion = applyExecutionTransition(completePlanStep(execution, step.id, params.summary));
|
|
487
485
|
return {
|
|
488
|
-
content: [{ type: "text", text: "The
|
|
489
|
-
details: { stepId: step.id,
|
|
486
|
+
content: [{ type: "text", text: completion ?? "The step was completed. The next step is ready and awaits user instruction." }],
|
|
487
|
+
details: { stepId: step.id, completed: true },
|
|
490
488
|
terminate: true,
|
|
491
489
|
};
|
|
492
490
|
},
|
|
493
491
|
renderCall(_args, theme) {
|
|
494
|
-
return new Text(theme.fg("toolTitle", theme.bold("
|
|
492
|
+
return new Text(theme.fg("toolTitle", theme.bold("Complete plan step")), 0, 0);
|
|
495
493
|
},
|
|
496
|
-
renderResult(
|
|
497
|
-
|
|
494
|
+
renderResult(result, _options, theme, context) {
|
|
495
|
+
const text = result.content.find((item) => item.type === "text")?.text ?? "Plan step completed";
|
|
496
|
+
return new Text(theme.fg(context.isError ? "error" : "success", text), 0, 0);
|
|
498
497
|
},
|
|
499
498
|
});
|
|
500
499
|
|
|
@@ -647,7 +646,7 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
647
646
|
runMode = undefined;
|
|
648
647
|
applyTools(selectedMode);
|
|
649
648
|
updateModeIndicator(ctx);
|
|
650
|
-
if (execution) ensurePanelLayout();
|
|
649
|
+
if (execution && execution.status !== "completed") ensurePanelLayout();
|
|
651
650
|
});
|
|
652
651
|
|
|
653
652
|
pi.on("session_start", async (event, ctx) => {
|
|
@@ -826,7 +825,7 @@ export default function planBuildModes(pi: ExtensionAPI): void {
|
|
|
826
825
|
originalLayoutRoot = (tui as TUI & { layoutRoot?: Component }).layoutRoot;
|
|
827
826
|
fullscreenPanelCapable = originalLayoutRoot !== undefined;
|
|
828
827
|
}
|
|
829
|
-
if (execution) ensurePanelLayout();
|
|
828
|
+
if (execution && execution.status !== "completed") ensurePanelLayout();
|
|
830
829
|
editor.onCycle = () => {
|
|
831
830
|
if (currentContext) void selectMode(nextMode(selectedMode), currentContext, "manual");
|
|
832
831
|
};
|
package/package.json
CHANGED
package/plan-execution.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export type PlanStepStatus = "pending" | "ready" | "active" | "
|
|
1
|
+
export type PlanStepStatus = "pending" | "ready" | "active" | "completed" | "skipped";
|
|
2
2
|
|
|
3
3
|
export interface PlanStep {
|
|
4
4
|
id: string;
|
|
@@ -55,21 +55,36 @@ export function decodePlanExecution(value: unknown): PlanExecutionState | undefi
|
|
|
55
55
|
const candidate = value as Partial<PlanExecutionState>;
|
|
56
56
|
if (candidate.version !== 1 || !["running", "paused", "completed"].includes(candidate.status ?? "")) return undefined;
|
|
57
57
|
if (!Array.isArray(candidate.steps) || candidate.steps.length === 0 || typeof candidate.planMarkdown !== "string") return undefined;
|
|
58
|
-
const validStatuses = new Set<PlanStepStatus>(["pending", "ready", "active", "
|
|
58
|
+
const validStatuses = new Set<PlanStepStatus>(["pending", "ready", "active", "completed", "skipped"]);
|
|
59
59
|
const steps: PlanStep[] = [];
|
|
60
|
+
let legacyReviewIndex = -1;
|
|
60
61
|
for (const raw of candidate.steps) {
|
|
61
62
|
if (!raw || typeof raw !== "object") return undefined;
|
|
62
|
-
const step = raw as Partial<PlanStep
|
|
63
|
-
|
|
63
|
+
const step = raw as Partial<PlanStep> & { status?: string };
|
|
64
|
+
const status = step.status === "review" ? "completed" : step.status;
|
|
65
|
+
if (step.status === "review") legacyReviewIndex = steps.length;
|
|
66
|
+
if (typeof step.id !== "string" || typeof step.text !== "string" || !validStatuses.has(status as PlanStepStatus)) return undefined;
|
|
64
67
|
if (!Number.isInteger(step.sourceLine) || (step.sourceLine ?? -1) < 0) return undefined;
|
|
65
|
-
steps.push({ id: step.id, text: step.text, status:
|
|
68
|
+
steps.push({ id: step.id, text: step.text, status: status as PlanStepStatus, sourceLine: step.sourceLine!, ...(typeof step.summary === "string" ? { summary: step.summary } : {}) });
|
|
69
|
+
}
|
|
70
|
+
let selectedStepId = typeof candidate.selectedStepId === "string" ? candidate.selectedStepId : undefined;
|
|
71
|
+
let status = candidate.status!;
|
|
72
|
+
if (legacyReviewIndex >= 0) {
|
|
73
|
+
const next = steps.slice(legacyReviewIndex + 1).find((step) => step.status === "pending");
|
|
74
|
+
if (next) {
|
|
75
|
+
next.status = "ready";
|
|
76
|
+
selectedStepId = next.id;
|
|
77
|
+
} else if (steps.every((step) => step.status === "completed" || step.status === "skipped")) {
|
|
78
|
+
status = "completed";
|
|
79
|
+
selectedStepId = undefined;
|
|
80
|
+
}
|
|
66
81
|
}
|
|
67
82
|
return {
|
|
68
83
|
version: 1,
|
|
69
|
-
status
|
|
84
|
+
status,
|
|
70
85
|
steps,
|
|
71
86
|
planMarkdown: candidate.planMarkdown,
|
|
72
|
-
selectedStepId
|
|
87
|
+
selectedStepId,
|
|
73
88
|
panelVisible: candidate.panelVisible !== false,
|
|
74
89
|
};
|
|
75
90
|
}
|
|
@@ -98,6 +113,16 @@ function makeNextReady(state: PlanExecutionState, afterId: string): void {
|
|
|
98
113
|
}
|
|
99
114
|
}
|
|
100
115
|
|
|
116
|
+
export function formatPlanCompletionSummary(state: PlanExecutionState): string {
|
|
117
|
+
const lines = ["Plan complete.", "", "Summary:"];
|
|
118
|
+
for (const [index, step] of state.steps.entries()) {
|
|
119
|
+
const outcome = step.status === "skipped" ? "Skipped" : "Completed";
|
|
120
|
+
lines.push(`${index + 1}. ${outcome}: ${step.text}`);
|
|
121
|
+
if (step.summary?.trim()) lines.push(` ${step.summary.trim()}`);
|
|
122
|
+
}
|
|
123
|
+
return lines.join("\n");
|
|
124
|
+
}
|
|
125
|
+
|
|
101
126
|
export function startPlanStep(state: PlanExecutionState, id: string): PlanExecutionState {
|
|
102
127
|
const next = clone(state);
|
|
103
128
|
if (next.status === "completed") throw new Error("The plan is already complete");
|
|
@@ -109,42 +134,18 @@ export function startPlanStep(state: PlanExecutionState, id: string): PlanExecut
|
|
|
109
134
|
return next;
|
|
110
135
|
}
|
|
111
136
|
|
|
112
|
-
export function
|
|
113
|
-
const next = clone(state);
|
|
114
|
-
const step = findStep(next, id);
|
|
115
|
-
if (step.status !== "active") throw new Error("Only the active step can be submitted for review");
|
|
116
|
-
step.status = "review";
|
|
117
|
-
step.summary = summary.trim();
|
|
118
|
-
next.selectedStepId = id;
|
|
119
|
-
return next;
|
|
120
|
-
}
|
|
121
|
-
|
|
122
|
-
export function completePlanStep(state: PlanExecutionState, id: string): PlanExecutionState {
|
|
137
|
+
export function completePlanStep(state: PlanExecutionState, id: string, summary?: string): PlanExecutionState {
|
|
123
138
|
const next = clone(state);
|
|
124
139
|
const step = findStep(next, id);
|
|
125
|
-
if (step.status !== "ready" && step.status !== "
|
|
126
|
-
throw new Error("Only a ready or
|
|
140
|
+
if (step.status !== "ready" && step.status !== "active") {
|
|
141
|
+
throw new Error("Only a ready or active step can be marked complete");
|
|
127
142
|
}
|
|
143
|
+
if (summary?.trim()) step.summary = summary.trim();
|
|
128
144
|
step.status = "completed";
|
|
129
145
|
makeNextReady(next, id);
|
|
130
146
|
return next;
|
|
131
147
|
}
|
|
132
148
|
|
|
133
|
-
export function acceptPlanStep(state: PlanExecutionState, id: string): PlanExecutionState {
|
|
134
|
-
const step = findStep(state, id);
|
|
135
|
-
if (step.status !== "review") throw new Error("Only a step awaiting review can be accepted");
|
|
136
|
-
return completePlanStep(state, id);
|
|
137
|
-
}
|
|
138
|
-
|
|
139
|
-
export function requestPlanStepCorrections(state: PlanExecutionState, id: string): PlanExecutionState {
|
|
140
|
-
const next = clone(state);
|
|
141
|
-
const step = findStep(next, id);
|
|
142
|
-
if (step.status !== "review") throw new Error("Only a step awaiting review can receive corrections");
|
|
143
|
-
step.status = "active";
|
|
144
|
-
next.selectedStepId = id;
|
|
145
|
-
return next;
|
|
146
|
-
}
|
|
147
|
-
|
|
148
149
|
export function skipPlanStep(state: PlanExecutionState, id: string): PlanExecutionState {
|
|
149
150
|
const next = clone(state);
|
|
150
151
|
const step = findStep(next, id);
|
package/plan-panel.ts
CHANGED
|
@@ -6,7 +6,6 @@ const GLYPHS = {
|
|
|
6
6
|
pending: "○",
|
|
7
7
|
ready: "▷",
|
|
8
8
|
active: "▶",
|
|
9
|
-
review: "◆",
|
|
10
9
|
completed: "✓",
|
|
11
10
|
skipped: "–",
|
|
12
11
|
} as const;
|
|
@@ -46,7 +45,7 @@ export class PlanPanel implements Component {
|
|
|
46
45
|
];
|
|
47
46
|
for (let index = 0; index < this.state.steps.length; index++) {
|
|
48
47
|
const step = this.state.steps[index]!;
|
|
49
|
-
const glyphColor = step.status === "completed" ? "success" : step.status === "
|
|
48
|
+
const glyphColor = step.status === "completed" ? "success" : step.status === "active" || step.status === "ready" ? "accent" : "muted";
|
|
50
49
|
const prefix = `${this.theme.fg(glyphColor, GLYPHS[step.status])} ${index + 1}. `;
|
|
51
50
|
const text = step.status === "completed" || step.status === "skipped" ? this.theme.fg("muted", step.text) : step.text;
|
|
52
51
|
const wrapped = wrapTextWithAnsi(text, Math.max(1, contentWidth - visibleWidth(prefix)));
|
|
@@ -68,7 +67,6 @@ export class PlanPanel implements Component {
|
|
|
68
67
|
if (this.state.status === "completed") lines.push(pad(this.theme.fg("success", "Plan complete")));
|
|
69
68
|
else if (this.state.status === "paused") lines.push(pad("Tell the agent to resume, cancel, or hide the plan."));
|
|
70
69
|
else if (current?.status === "ready") lines.push(pad("Tell the agent to implement, complete, edit, skip, cancel, or hide this step."));
|
|
71
|
-
else if (current?.status === "review") lines.push(pad("Tell the agent to accept, correct, or cancel the plan."));
|
|
72
70
|
else lines.push(pad("Plan progress updates automatically from your prompts."));
|
|
73
71
|
lines.push(border(`╰${"─".repeat(inner)}╯`));
|
|
74
72
|
return lines.map((line) => truncateToWidth(line, safeWidth, ""));
|
package/prompts.ts
CHANGED
|
@@ -60,7 +60,7 @@ The approved plan is at ${planPath}. Implement only step ${stepNumber} of ${tota
|
|
|
60
60
|
|
|
61
61
|
${step}
|
|
62
62
|
|
|
63
|
-
Do not begin any later plan step. Complete and verify this step, then call plan_step_complete with a concise result summary.
|
|
63
|
+
Do not begin any later plan step. Complete and verify this step, then call plan_step_complete with a concise result summary. The step will be marked completed immediately; do not ask the user to review or accept it.
|
|
64
64
|
</system-reminder>`;
|
|
65
65
|
}
|
|
66
66
|
|
|
@@ -71,11 +71,11 @@ Step-by-step execution is waiting for the user's natural-language instruction. N
|
|
|
71
71
|
Current progress:
|
|
72
72
|
${progress}
|
|
73
73
|
|
|
74
|
-
Interpret the user's intent contextually rather than requiring exact phrases. Clear statements, confirmations, and feedback may request a state transition even when phrased non-imperatively. For example, a statement that a ready step is finished can use the complete action
|
|
74
|
+
Interpret the user's intent contextually rather than requiring exact phrases. Clear statements, confirmations, and feedback may request a state transition even when phrased non-imperatively. For example, a statement that a ready step is finished can use the complete action. If multiple materially different actions are plausible, ask a brief clarification. Cancellation is always available when the user clearly wants to stop. Do not advance based on hypothetical, uncertain, or unrelated discussion. The sidebar is a passive visual aid and cannot receive input.
|
|
75
75
|
</system-reminder>`;
|
|
76
76
|
}
|
|
77
77
|
|
|
78
|
-
export const PLAN_STEP_COMPLETE_DESCRIPTION = `Call this tool after implementing and verifying the currently active plan step. It
|
|
78
|
+
export const PLAN_STEP_COMPLETE_DESCRIPTION = `Call this tool after implementing and verifying the currently active plan step. It marks the step completed immediately and returns control to the user before any next step begins. Do not call it before the active step is complete, and never begin the next step yourself.`;
|
|
79
79
|
|
|
80
80
|
export const PLAN_EXIT_DESCRIPTION = `Use this tool when you have completed the planning phase and are ready to exit plan agent.
|
|
81
81
|
|