@oh-my-pi/pi-coding-agent 14.1.1 → 14.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +47 -2
- package/package.json +8 -8
- package/scripts/build-binary.ts +61 -0
- package/src/autoresearch/helpers.ts +10 -0
- package/src/autoresearch/index.ts +1 -11
- package/src/autoresearch/tools/init-experiment.ts +1 -10
- package/src/autoresearch/tools/log-experiment.ts +1 -11
- package/src/autoresearch/tools/run-experiment.ts +1 -10
- package/src/bun-imports.d.ts +6 -0
- package/src/cli/plugin-cli.ts +23 -45
- package/src/commit/agentic/tools/propose-commit.ts +1 -14
- package/src/commit/agentic/tools/split-commit.ts +1 -15
- package/src/commit/utils.ts +15 -1
- package/src/config/model-registry.ts +3 -3
- package/src/config/prompt-templates.ts +4 -12
- package/src/config/settings-schema.ts +27 -2
- package/src/config/settings.ts +1 -1
- package/src/discovery/claude-plugins.ts +61 -6
- package/src/discovery/codex.ts +2 -15
- package/src/discovery/gemini.ts +2 -15
- package/src/discovery/helpers.ts +40 -1
- package/src/discovery/opencode.ts +2 -15
- package/src/edit/apply-patch/index.ts +87 -0
- package/src/edit/apply-patch/parser.ts +174 -0
- package/src/edit/diff.ts +3 -14
- package/src/edit/index.ts +65 -2
- package/src/edit/modes/apply-patch.lark +19 -0
- package/src/edit/modes/apply-patch.ts +63 -0
- package/src/edit/modes/hashline.ts +3 -3
- package/src/edit/modes/replace.ts +2 -13
- package/src/edit/read-file.ts +18 -0
- package/src/edit/renderer.ts +61 -33
- package/src/extensibility/extensions/compact-handler.ts +40 -0
- package/src/extensibility/extensions/runner.ts +11 -29
- package/src/extensibility/utils.ts +7 -1
- package/src/internal-urls/docs-index.generated.ts +9 -2
- package/src/lsp/render.ts +14 -2
- package/src/main.ts +1 -0
- package/src/mcp/manager.ts +29 -48
- package/src/memories/index.ts +7 -1
- package/src/modes/acp/acp-agent.ts +3 -16
- package/src/modes/components/model-selector.ts +15 -24
- package/src/modes/components/plugin-settings.ts +16 -5
- package/src/modes/components/read-tool-group.ts +92 -9
- package/src/modes/components/settings-defs.ts +18 -0
- package/src/modes/components/settings-selector.ts +2 -6
- package/src/modes/components/tool-execution.ts +61 -28
- package/src/modes/controllers/event-controller.ts +3 -1
- package/src/modes/controllers/extension-ui-controller.ts +99 -150
- package/src/modes/controllers/selector-controller.ts +3 -12
- package/src/modes/interactive-mode.ts +4 -2
- package/src/modes/print-mode.ts +4 -22
- package/src/modes/rpc/rpc-mode.ts +18 -38
- package/src/modes/shared.ts +10 -1
- package/src/modes/utils/ui-helpers.ts +6 -2
- package/src/plan-mode/approved-plan.ts +5 -4
- package/src/prompts/system/subagent-system-prompt.md +4 -4
- package/src/prompts/system/subagent-user-prompt.md +2 -2
- package/src/prompts/system/system-prompt.md +208 -243
- package/src/prompts/tools/apply-patch.md +67 -0
- package/src/prompts/tools/ast-edit.md +18 -23
- package/src/prompts/tools/ast-grep.md +24 -32
- package/src/prompts/tools/bash.md +11 -23
- package/src/prompts/tools/debug.md +8 -22
- package/src/prompts/tools/find.md +0 -4
- package/src/prompts/tools/grep.md +3 -5
- package/src/prompts/tools/hashline.md +16 -10
- package/src/prompts/tools/python.md +10 -14
- package/src/prompts/tools/read.md +17 -24
- package/src/prompts/tools/task.md +57 -21
- package/src/prompts/tools/todo-write.md +45 -67
- package/src/session/agent-session.ts +4 -4
- package/src/session/session-manager.ts +15 -7
- package/src/session/streaming-output.ts +24 -0
- package/src/slash-commands/builtin-registry.ts +3 -14
- package/src/task/executor.ts +13 -34
- package/src/task/index.ts +82 -18
- package/src/task/simple-mode.ts +27 -0
- package/src/task/template.ts +17 -3
- package/src/task/types.ts +77 -30
- package/src/tools/ask.ts +2 -4
- package/src/tools/ast-edit.ts +4 -15
- package/src/tools/ast-grep.ts +8 -27
- package/src/tools/bash-skill-urls.ts +9 -7
- package/src/tools/bash.ts +4 -12
- package/src/tools/browser.ts +1 -1
- package/src/tools/fetch.ts +1 -14
- package/src/tools/file-recorder.ts +35 -0
- package/src/tools/find.ts +6 -3
- package/src/tools/gh-format.ts +12 -0
- package/src/tools/gh-renderer.ts +1 -8
- package/src/tools/gh.ts +6 -13
- package/src/tools/grep.ts +9 -22
- package/src/tools/jtd-to-json-schema.ts +16 -0
- package/src/tools/match-line-format.ts +20 -0
- package/src/tools/path-utils.ts +30 -2
- package/src/tools/plan-mode-guard.ts +6 -5
- package/src/tools/python.ts +1 -1
- package/src/tools/read.ts +1 -1
- package/src/tools/render-utils.ts +38 -6
- package/src/tools/renderers.ts +1 -0
- package/src/tools/ssh.ts +3 -11
- package/src/tools/submit-result.ts +1 -13
- package/src/tools/todo-write.ts +137 -103
- package/src/tools/write.ts +2 -23
- package/src/tui/code-cell.ts +12 -7
- package/src/utils/edit-mode.ts +3 -2
- package/src/utils/git.ts +1 -1
- package/src/vim/engine.ts +41 -58
- package/src/web/scrapers/crates-io.ts +1 -14
- package/src/web/scrapers/types.ts +13 -0
- package/src/web/search/providers/base.ts +13 -0
- package/src/web/search/providers/brave.ts +2 -5
- package/src/web/search/providers/codex.ts +20 -24
- package/src/web/search/providers/gemini.ts +39 -1
- package/src/web/search/providers/jina.ts +2 -5
- package/src/web/search/providers/kagi.ts +3 -8
- package/src/web/search/providers/kimi.ts +3 -7
- package/src/web/search/providers/parallel.ts +3 -8
- package/src/web/search/providers/synthetic.ts +3 -7
- package/src/web/search/providers/tavily.ts +15 -11
- package/src/web/search/providers/utils.ts +36 -0
- package/src/web/search/providers/zai.ts +3 -7
|
@@ -16,6 +16,7 @@ import type {
|
|
|
16
16
|
ExtensionUIDialogOptions,
|
|
17
17
|
ExtensionWidgetOptions,
|
|
18
18
|
} from "../../extensibility/extensions";
|
|
19
|
+
import { runExtensionCompact, runExtensionSetModel } from "../../extensibility/extensions/compact-handler";
|
|
19
20
|
import { type Theme, theme } from "../../modes/theme/theme";
|
|
20
21
|
import type { AgentSession } from "../../session/agent-session";
|
|
21
22
|
import { isRpcHostToolResult, isRpcHostToolUpdate, RpcHostToolBridge } from "./host-tools";
|
|
@@ -66,6 +67,18 @@ function normalizeHostToolDefinitions(tools: RpcHostToolDefinition[]): RpcHostTo
|
|
|
66
67
|
});
|
|
67
68
|
}
|
|
68
69
|
|
|
70
|
+
function parseValueDialogResponse(
|
|
71
|
+
response: RpcExtensionUIResponse,
|
|
72
|
+
dialogOptions: ExtensionUIDialogOptions | undefined,
|
|
73
|
+
): string | undefined {
|
|
74
|
+
if ("cancelled" in response && response.cancelled) {
|
|
75
|
+
if (response.timedOut) dialogOptions?.onTimeout?.();
|
|
76
|
+
return undefined;
|
|
77
|
+
}
|
|
78
|
+
if ("value" in response) return response.value;
|
|
79
|
+
return undefined;
|
|
80
|
+
}
|
|
81
|
+
|
|
69
82
|
function shouldEmitRpcTitles(): boolean {
|
|
70
83
|
const raw = $env.PI_RPC_EMIT_TITLE;
|
|
71
84
|
if (!raw) return false;
|
|
@@ -228,14 +241,7 @@ export async function runRpcMode(session: AgentSession): Promise<never> {
|
|
|
228
241
|
dialogOptions,
|
|
229
242
|
undefined,
|
|
230
243
|
{ method: "select", title, options, timeout: dialogOptions?.timeout },
|
|
231
|
-
response =>
|
|
232
|
-
if ("cancelled" in response && response.cancelled) {
|
|
233
|
-
if (response.timedOut) dialogOptions?.onTimeout?.();
|
|
234
|
-
return undefined;
|
|
235
|
-
}
|
|
236
|
-
if ("value" in response) return response.value;
|
|
237
|
-
return undefined;
|
|
238
|
-
},
|
|
244
|
+
response => parseValueDialogResponse(response, dialogOptions),
|
|
239
245
|
);
|
|
240
246
|
}
|
|
241
247
|
|
|
@@ -264,14 +270,7 @@ export async function runRpcMode(session: AgentSession): Promise<never> {
|
|
|
264
270
|
dialogOptions,
|
|
265
271
|
undefined,
|
|
266
272
|
{ method: "input", title, placeholder, timeout: dialogOptions?.timeout },
|
|
267
|
-
response =>
|
|
268
|
-
if ("cancelled" in response && response.cancelled) {
|
|
269
|
-
if (response.timedOut) dialogOptions?.onTimeout?.();
|
|
270
|
-
return undefined;
|
|
271
|
-
}
|
|
272
|
-
if ("value" in response) return response.value;
|
|
273
|
-
return undefined;
|
|
274
|
-
},
|
|
273
|
+
response => parseValueDialogResponse(response, dialogOptions),
|
|
275
274
|
);
|
|
276
275
|
}
|
|
277
276
|
|
|
@@ -432,12 +431,7 @@ export async function runRpcMode(session: AgentSession): Promise<never> {
|
|
|
432
431
|
getAllTools: () => session.getAllToolNames(),
|
|
433
432
|
setActiveTools: (toolNames: string[]) => session.setActiveToolsByName(toolNames),
|
|
434
433
|
getCommands: () => [],
|
|
435
|
-
setModel:
|
|
436
|
-
const key = await session.modelRegistry.getApiKey(model);
|
|
437
|
-
if (!key) return false;
|
|
438
|
-
await session.setModel(model);
|
|
439
|
-
return true;
|
|
440
|
-
},
|
|
434
|
+
setModel: model => runExtensionSetModel(session, model),
|
|
441
435
|
getThinkingLevel: () => session.thinkingLevel,
|
|
442
436
|
setThinkingLevel: level => session.setThinkingLevel(level),
|
|
443
437
|
getSessionName: () => session.sessionManager.getSessionName(),
|
|
@@ -456,14 +450,7 @@ export async function runRpcMode(session: AgentSession): Promise<never> {
|
|
|
456
450
|
},
|
|
457
451
|
getContextUsage: () => session.getContextUsage(),
|
|
458
452
|
getSystemPrompt: () => session.systemPrompt,
|
|
459
|
-
compact:
|
|
460
|
-
const instructions = typeof instructionsOrOptions === "string" ? instructionsOrOptions : undefined;
|
|
461
|
-
const options =
|
|
462
|
-
instructionsOrOptions && typeof instructionsOrOptions === "object"
|
|
463
|
-
? instructionsOrOptions
|
|
464
|
-
: undefined;
|
|
465
|
-
await session.compact(instructions, options);
|
|
466
|
-
},
|
|
453
|
+
compact: instructionsOrOptions => runExtensionCompact(session, instructionsOrOptions),
|
|
467
454
|
},
|
|
468
455
|
// ExtensionCommandContextActions - commands invokable via prompt("/command")
|
|
469
456
|
{
|
|
@@ -492,14 +479,7 @@ export async function runRpcMode(session: AgentSession): Promise<never> {
|
|
|
492
479
|
reload: async () => {
|
|
493
480
|
await session.reload();
|
|
494
481
|
},
|
|
495
|
-
compact:
|
|
496
|
-
const instructions = typeof instructionsOrOptions === "string" ? instructionsOrOptions : undefined;
|
|
497
|
-
const options =
|
|
498
|
-
instructionsOrOptions && typeof instructionsOrOptions === "object"
|
|
499
|
-
? instructionsOrOptions
|
|
500
|
-
: undefined;
|
|
501
|
-
await session.compact(instructions, options);
|
|
502
|
-
},
|
|
482
|
+
compact: instructionsOrOptions => runExtensionCompact(session, instructionsOrOptions),
|
|
503
483
|
},
|
|
504
484
|
new RpcExtensionUIContext(pendingExtensionRequests, output),
|
|
505
485
|
);
|
package/src/modes/shared.ts
CHANGED
|
@@ -5,9 +5,18 @@ import { theme } from "./theme/theme";
|
|
|
5
5
|
// Text Sanitization
|
|
6
6
|
// ═══════════════════════════════════════════════════════════════════════════
|
|
7
7
|
|
|
8
|
-
|
|
8
|
+
const ANSI_OSC_RE = /\x1b\][^\x07\x1b]*(?:\x07|\x1b\\)|\x9d[^\x07\x9c]*(?:\x07|\x9c)/g;
|
|
9
|
+
const ANSI_STRING_RE = /\x1b(?:P|_|\^)[\s\S]*?\x1b\\|[\x90\x9e\x9f][\s\S]*?\x9c/g;
|
|
10
|
+
const ANSI_CSI_RE = /\x1b\[[0-?]*[ -/]*[@-~]|\x9b[0-?]*[ -/]*[@-~]/g;
|
|
11
|
+
const ANSI_SINGLE_RE = /\x1b[@-Z\\-_]/g;
|
|
12
|
+
|
|
13
|
+
/** Sanitize text for display in a single-line status. Strips ANSI escape sequences, C0/C1 control characters, collapses whitespace, trims. */
|
|
9
14
|
export function sanitizeStatusText(text: string): string {
|
|
10
15
|
return text
|
|
16
|
+
.replace(ANSI_OSC_RE, "")
|
|
17
|
+
.replace(ANSI_STRING_RE, "")
|
|
18
|
+
.replace(ANSI_CSI_RE, "")
|
|
19
|
+
.replace(ANSI_SINGLE_RE, "")
|
|
11
20
|
.replace(/[\u0000-\u001f\u007f-\u009f]/g, " ")
|
|
12
21
|
.replace(/ +/g, " ")
|
|
13
22
|
.trim();
|
|
@@ -257,7 +257,9 @@ export class UiHelpers {
|
|
|
257
257
|
if (content.name === "read") {
|
|
258
258
|
if (hasErrorStop && errorMessage) {
|
|
259
259
|
if (!readGroup) {
|
|
260
|
-
readGroup = new ReadToolGroupComponent(
|
|
260
|
+
readGroup = new ReadToolGroupComponent({
|
|
261
|
+
showContentPreview: this.ctx.settings.get("read.toolResultPreview"),
|
|
262
|
+
});
|
|
261
263
|
readGroup.setExpanded(this.ctx.toolOutputExpanded);
|
|
262
264
|
this.ctx.chatContainer.addChild(readGroup);
|
|
263
265
|
}
|
|
@@ -330,7 +332,9 @@ export class UiHelpers {
|
|
|
330
332
|
let component = this.ctx.pendingTools.get(message.toolCallId);
|
|
331
333
|
if (!component) {
|
|
332
334
|
if (!readGroup) {
|
|
333
|
-
readGroup = new ReadToolGroupComponent(
|
|
335
|
+
readGroup = new ReadToolGroupComponent({
|
|
336
|
+
showContentPreview: this.ctx.settings.get("read.toolResultPreview"),
|
|
337
|
+
});
|
|
334
338
|
readGroup.setExpanded(this.ctx.toolOutputExpanded);
|
|
335
339
|
this.ctx.chatContainer.addChild(readGroup);
|
|
336
340
|
}
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import * as fs from "node:fs/promises";
|
|
2
2
|
import { isEnoent } from "@oh-my-pi/pi-utils";
|
|
3
3
|
import { resolveLocalUrlToPath } from "../internal-urls";
|
|
4
|
+
import { normalizeLocalScheme } from "../tools/path-utils";
|
|
4
5
|
|
|
5
6
|
interface RenameApprovedPlanFileOptions {
|
|
6
7
|
planFilePath: string;
|
|
@@ -10,8 +11,8 @@ interface RenameApprovedPlanFileOptions {
|
|
|
10
11
|
}
|
|
11
12
|
|
|
12
13
|
function assertLocalUrl(path: string, label: "source" | "destination"): void {
|
|
13
|
-
if (!path.startsWith("local://")) {
|
|
14
|
-
throw new Error(`Approved plan ${label} path must use local
|
|
14
|
+
if (!path.startsWith("local:/") && !path.startsWith("local://")) {
|
|
15
|
+
throw new Error(`Approved plan ${label} path must use local: scheme with / or // (received ${path}).`);
|
|
15
16
|
}
|
|
16
17
|
}
|
|
17
18
|
|
|
@@ -24,8 +25,8 @@ export async function renameApprovedPlanFile(options: RenameApprovedPlanFileOpti
|
|
|
24
25
|
getArtifactsDir: () => getArtifactsDir(),
|
|
25
26
|
getSessionId: () => getSessionId(),
|
|
26
27
|
};
|
|
27
|
-
const resolvedSource = resolveLocalUrlToPath(planFilePath, resolveOptions);
|
|
28
|
-
const resolvedDestination = resolveLocalUrlToPath(finalPlanFilePath, resolveOptions);
|
|
28
|
+
const resolvedSource = resolveLocalUrlToPath(normalizeLocalScheme(planFilePath), resolveOptions);
|
|
29
|
+
const resolvedDestination = resolveLocalUrlToPath(normalizeLocalScheme(finalPlanFilePath), resolveOptions);
|
|
29
30
|
|
|
30
31
|
if (resolvedSource === resolvedDestination) {
|
|
31
32
|
return;
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
{{base}}
|
|
2
2
|
|
|
3
|
-
{{
|
|
3
|
+
{{SECTION_SEPARATOR "Acting as"}}
|
|
4
4
|
{{agent}}
|
|
5
5
|
|
|
6
|
-
{{
|
|
6
|
+
{{SECTION_SEPARATOR "Job"}}
|
|
7
7
|
You are operating on a delegated sub-task.
|
|
8
8
|
{{#if worktree}}
|
|
9
9
|
You are working in an isolated working tree at `{{worktree}}` for this sub-task.
|
|
@@ -14,7 +14,7 @@ You **MUST NOT** modify files outside this tree or in the original repository.
|
|
|
14
14
|
If you need additional information, you can find your conversation with the user in {{contextFile}} (`tail` or `grep` relevant terms).
|
|
15
15
|
{{/if}}
|
|
16
16
|
|
|
17
|
-
{{
|
|
17
|
+
{{SECTION_SEPARATOR "Closure"}}
|
|
18
18
|
No TODO tracking, no progress updates. Execute, call `submit_result`, done.
|
|
19
19
|
|
|
20
20
|
When finished, you **MUST** call `submit_result` exactly once. This is like writing to a ticket, provide what is required, and close it.
|
|
@@ -28,7 +28,7 @@ Your result **MUST** match this TypeScript interface:
|
|
|
28
28
|
```
|
|
29
29
|
{{/if}}
|
|
30
30
|
|
|
31
|
-
{{
|
|
31
|
+
{{SECTION_SEPARATOR "Giving Up"}}
|
|
32
32
|
Giving up is a last resort. If truly blocked, you **MUST** call `submit_result` exactly once with `result.error` describing what you tried and the exact blocker.
|
|
33
33
|
You **MUST NOT** give up due to uncertainty, missing information obtainable via tools or repo context, or needing a design decision you can derive yourself.
|
|
34
34
|
|
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
{{#if context}}
|
|
2
|
-
{{
|
|
2
|
+
{{SECTION_SEPARATOR "Background"}}
|
|
3
3
|
<context>
|
|
4
4
|
{{context}}
|
|
5
5
|
</context>
|
|
6
6
|
{{/if}}
|
|
7
7
|
|
|
8
|
-
{{
|
|
8
|
+
{{SECTION_SEPARATOR "Task"}}
|
|
9
9
|
Your assignment is below. Your work begins now.
|
|
10
10
|
<goal>
|
|
11
11
|
{{assignment}}
|