@esso0428/pi-subagents 0.17.6 → 0.17.8
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 +14 -0
- package/CONTRIBUTING.md +4 -0
- package/dist/abortable.d.ts +13 -0
- package/dist/abortable.d.ts.map +1 -0
- package/dist/abortable.js +43 -0
- package/dist/abortable.js.map +1 -0
- package/dist/agent-color.d.ts +36 -0
- package/dist/agent-color.d.ts.map +1 -0
- package/dist/agent-color.js +124 -0
- package/dist/agent-color.js.map +1 -0
- package/dist/agent-file-toggle.d.ts +126 -0
- package/dist/agent-file-toggle.d.ts.map +1 -0
- package/dist/agent-file-toggle.js +259 -0
- package/dist/agent-file-toggle.js.map +1 -0
- package/dist/agent-history.d.ts +4 -0
- package/dist/agent-history.d.ts.map +1 -1
- package/dist/agent-history.js +47 -1
- package/dist/agent-history.js.map +1 -1
- package/dist/agent-manager.d.ts +370 -56
- package/dist/agent-manager.d.ts.map +1 -1
- package/dist/agent-manager.js +1123 -409
- package/dist/agent-manager.js.map +1 -1
- package/dist/agent-runner.d.ts +100 -10
- package/dist/agent-runner.d.ts.map +1 -1
- package/dist/agent-runner.js +166 -21
- package/dist/agent-runner.js.map +1 -1
- package/dist/agent-types.d.ts +57 -5
- package/dist/agent-types.d.ts.map +1 -1
- package/dist/agent-types.js +164 -32
- package/dist/agent-types.js.map +1 -1
- package/dist/child-context.d.ts +3 -0
- package/dist/child-context.d.ts.map +1 -0
- package/dist/child-context.js +13 -0
- package/dist/child-context.js.map +1 -0
- package/dist/cross-extension-rpc.d.ts +23 -3
- package/dist/cross-extension-rpc.d.ts.map +1 -1
- package/dist/cross-extension-rpc.js +79 -17
- package/dist/cross-extension-rpc.js.map +1 -1
- package/dist/custom-agents.d.ts +38 -1
- package/dist/custom-agents.d.ts.map +1 -1
- package/dist/custom-agents.js +164 -12
- package/dist/custom-agents.js.map +1 -1
- package/dist/index.d.ts +34 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1912 -492
- package/dist/index.js.map +1 -1
- package/dist/invocation-config.d.ts +87 -2
- package/dist/invocation-config.d.ts.map +1 -1
- package/dist/invocation-config.js +71 -3
- package/dist/invocation-config.js.map +1 -1
- package/dist/mention-clone.d.ts +88 -0
- package/dist/mention-clone.d.ts.map +1 -0
- package/dist/mention-clone.js +154 -0
- package/dist/mention-clone.js.map +1 -0
- package/dist/mention.d.ts +82 -0
- package/dist/mention.d.ts.map +1 -0
- package/dist/mention.js +132 -0
- package/dist/mention.js.map +1 -0
- package/dist/model-resolver.d.ts +17 -0
- package/dist/model-resolver.d.ts.map +1 -1
- package/dist/model-resolver.js +15 -0
- package/dist/model-resolver.js.map +1 -1
- package/dist/model-scope.d.ts +50 -0
- package/dist/model-scope.d.ts.map +1 -0
- package/dist/model-scope.js +49 -0
- package/dist/model-scope.js.map +1 -0
- package/dist/nested-tools.d.ts +57 -0
- package/dist/nested-tools.d.ts.map +1 -0
- package/dist/nested-tools.js +301 -0
- package/dist/nested-tools.js.map +1 -0
- package/dist/output-file.d.ts +22 -3
- package/dist/output-file.d.ts.map +1 -1
- package/dist/output-file.js +58 -7
- package/dist/output-file.js.map +1 -1
- package/dist/prompts.d.ts +23 -0
- package/dist/prompts.d.ts.map +1 -1
- package/dist/prompts.js +20 -2
- package/dist/prompts.js.map +1 -1
- package/dist/schedule.d.ts.map +1 -1
- package/dist/schedule.js +36 -15
- package/dist/schedule.js.map +1 -1
- package/dist/settings.d.ts +228 -2
- package/dist/settings.d.ts.map +1 -1
- package/dist/settings.js +94 -0
- package/dist/settings.js.map +1 -1
- package/dist/status-note.d.ts +49 -1
- package/dist/status-note.d.ts.map +1 -1
- package/dist/status-note.js +62 -1
- package/dist/status-note.js.map +1 -1
- package/dist/structured-output.d.ts +62 -0
- package/dist/structured-output.d.ts.map +1 -0
- package/dist/structured-output.js +113 -0
- package/dist/structured-output.js.map +1 -0
- package/dist/types.d.ts +176 -10
- package/dist/types.d.ts.map +1 -1
- package/dist/ui/agent-mention.d.ts +83 -0
- package/dist/ui/agent-mention.d.ts.map +1 -0
- package/dist/ui/agent-mention.js +188 -0
- package/dist/ui/agent-mention.js.map +1 -0
- package/dist/ui/agent-widget.d.ts +97 -75
- package/dist/ui/agent-widget.d.ts.map +1 -1
- package/dist/ui/agent-widget.js +398 -420
- package/dist/ui/agent-widget.js.map +1 -1
- package/dist/ui/conversation-blocks.d.ts.map +1 -1
- package/dist/ui/conversation-blocks.js +6 -0
- package/dist/ui/conversation-blocks.js.map +1 -1
- package/dist/ui/conversation-timeline.d.ts +10 -2
- package/dist/ui/conversation-timeline.d.ts.map +1 -1
- package/dist/ui/conversation-timeline.js +130 -23
- package/dist/ui/conversation-timeline.js.map +1 -1
- package/dist/ui/conversation-viewer.d.ts +15 -5
- package/dist/ui/conversation-viewer.d.ts.map +1 -1
- package/dist/ui/conversation-viewer.js +202 -50
- package/dist/ui/conversation-viewer.js.map +1 -1
- package/dist/ui/fleet-list.d.ts +198 -0
- package/dist/ui/fleet-list.d.ts.map +1 -0
- package/dist/ui/fleet-list.js +487 -0
- package/dist/ui/fleet-list.js.map +1 -0
- package/dist/ui/schedule-menu.d.ts.map +1 -1
- package/dist/ui/schedule-menu.js +6 -7
- package/dist/ui/schedule-menu.js.map +1 -1
- package/dist/ui/select-item.d.ts +28 -0
- package/dist/ui/select-item.d.ts.map +1 -0
- package/dist/ui/select-item.js +35 -0
- package/dist/ui/select-item.js.map +1 -0
- package/dist/ui/workflow-card.d.ts +176 -0
- package/dist/ui/workflow-card.d.ts.map +1 -0
- package/dist/ui/workflow-card.js +333 -0
- package/dist/ui/workflow-card.js.map +1 -0
- package/dist/ui/workflow-dialog.d.ts +306 -0
- package/dist/ui/workflow-dialog.d.ts.map +1 -0
- package/dist/ui/workflow-dialog.js +844 -0
- package/dist/ui/workflow-dialog.js.map +1 -0
- package/dist/ui/workflow-menu.d.ts +61 -0
- package/dist/ui/workflow-menu.d.ts.map +1 -0
- package/dist/ui/workflow-menu.js +148 -0
- package/dist/ui/workflow-menu.js.map +1 -0
- package/dist/usage.d.ts +86 -1
- package/dist/usage.d.ts.map +1 -1
- package/dist/usage.js +72 -1
- package/dist/usage.js.map +1 -1
- package/dist/workflow/collisions.d.ts +96 -0
- package/dist/workflow/collisions.d.ts.map +1 -0
- package/dist/workflow/collisions.js +89 -0
- package/dist/workflow/collisions.js.map +1 -0
- package/dist/workflow/entry.d.ts +33 -0
- package/dist/workflow/entry.d.ts.map +1 -0
- package/dist/workflow/entry.js +30 -0
- package/dist/workflow/entry.js.map +1 -0
- package/dist/workflow/host.d.ts +63 -0
- package/dist/workflow/host.d.ts.map +1 -0
- package/dist/workflow/host.js +363 -0
- package/dist/workflow/host.js.map +1 -0
- package/dist/workflow/journal.d.ts +98 -0
- package/dist/workflow/journal.d.ts.map +1 -0
- package/dist/workflow/journal.js +121 -0
- package/dist/workflow/journal.js.map +1 -0
- package/dist/workflow/json-schema.d.ts +52 -0
- package/dist/workflow/json-schema.d.ts.map +1 -0
- package/dist/workflow/json-schema.js +112 -0
- package/dist/workflow/json-schema.js.map +1 -0
- package/dist/workflow/meta.d.ts +68 -0
- package/dist/workflow/meta.d.ts.map +1 -0
- package/dist/workflow/meta.js +318 -0
- package/dist/workflow/meta.js.map +1 -0
- package/dist/workflow/progress.d.ts +225 -0
- package/dist/workflow/progress.d.ts.map +1 -0
- package/dist/workflow/progress.js +362 -0
- package/dist/workflow/progress.js.map +1 -0
- package/dist/workflow/runtime.d.ts +335 -0
- package/dist/workflow/runtime.d.ts.map +1 -0
- package/dist/workflow/runtime.js +831 -0
- package/dist/workflow/runtime.js.map +1 -0
- package/dist/workflow/saved.d.ts +91 -0
- package/dist/workflow/saved.d.ts.map +1 -0
- package/dist/workflow/saved.js +204 -0
- package/dist/workflow/saved.js.map +1 -0
- package/dist/workflow/task.d.ts +137 -0
- package/dist/workflow/task.d.ts.map +1 -0
- package/dist/workflow/task.js +208 -0
- package/dist/workflow/task.js.map +1 -0
- package/dist/workflow/tool-description.d.ts +39 -0
- package/dist/workflow/tool-description.d.ts.map +1 -0
- package/dist/workflow/tool-description.js +200 -0
- package/dist/workflow/tool-description.js.map +1 -0
- package/dist/workflow/worker-source.d.ts +48 -0
- package/dist/workflow/worker-source.d.ts.map +1 -0
- package/dist/workflow/worker-source.js +779 -0
- package/dist/workflow/worker-source.js.map +1 -0
- package/dist/worktree.d.ts +10 -3
- package/dist/worktree.d.ts.map +1 -1
- package/dist/worktree.js +58 -54
- package/dist/worktree.js.map +1 -1
- package/dist/xml.d.ts +11 -0
- package/dist/xml.d.ts.map +1 -0
- package/dist/xml.js +13 -0
- package/dist/xml.js.map +1 -0
- package/docs/rpc.md +183 -0
- package/docs/superpowers/plans/2026-09-30-upstream-event-workflow-partial-history.md +195 -0
- package/docs/superpowers/specs/2026-09-30-upstream-event-workflow-partial-history-design.md +49 -0
- package/docs/workflows.md +437 -0
- package/examples/agent-tool-description.md +7 -7
- package/examples/workflows/compose.js +51 -0
- package/examples/workflows/fan-out-audit.js +47 -0
- package/examples/workflows/gated-fix.js +60 -0
- package/examples/workflows/lib/count-child.js +27 -0
- package/examples/workflows/review-panel.js +63 -0
- package/examples/workflows/structured-findings.js +78 -0
- package/package.json +1 -1
- package/src/abortable.ts +43 -0
- package/src/agent-color.ts +161 -0
- package/src/agent-file-toggle.ts +269 -0
- package/src/agent-history.ts +54 -2
- package/src/agent-manager.ts +1263 -402
- package/src/agent-runner.ts +251 -27
- package/src/agent-types.ts +188 -32
- package/src/child-context.ts +15 -0
- package/src/cross-extension-rpc.ts +96 -20
- package/src/custom-agents.ts +170 -13
- package/src/index.ts +2029 -536
- package/src/invocation-config.ts +118 -3
- package/src/mention-clone.ts +196 -0
- package/src/mention.ts +141 -0
- package/src/model-resolver.ts +18 -0
- package/src/model-scope.ts +70 -0
- package/src/nested-tools.ts +424 -0
- package/src/output-file.ts +61 -6
- package/src/prompts.ts +45 -2
- package/src/schedule.ts +35 -14
- package/src/settings.ts +312 -2
- package/src/status-note.ts +66 -1
- package/src/structured-output.ts +130 -0
- package/src/types.ts +177 -10
- package/src/ui/agent-mention.ts +216 -0
- package/src/ui/agent-widget.ts +393 -441
- package/src/ui/conversation-blocks.ts +6 -0
- package/src/ui/conversation-timeline.ts +139 -25
- package/src/ui/conversation-viewer.ts +212 -48
- package/src/ui/fleet-list.ts +558 -0
- package/src/ui/schedule-menu.ts +9 -8
- package/src/ui/select-item.ts +45 -0
- package/src/ui/workflow-card.ts +470 -0
- package/src/ui/workflow-dialog.ts +1115 -0
- package/src/ui/workflow-menu.ts +193 -0
- package/src/usage.ts +109 -2
- package/src/workflow/collisions.ts +123 -0
- package/src/workflow/entry.ts +47 -0
- package/src/workflow/host.ts +403 -0
- package/src/workflow/journal.ts +164 -0
- package/src/workflow/json-schema.ts +128 -0
- package/src/workflow/meta.ts +325 -0
- package/src/workflow/progress.ts +550 -0
- package/src/workflow/runtime.ts +1219 -0
- package/src/workflow/saved.ts +217 -0
- package/src/workflow/task.ts +302 -0
- package/src/workflow/tool-description.ts +200 -0
- package/src/workflow/worker-source.ts +781 -0
- package/src/worktree.ts +69 -55
- package/src/xml.ts +13 -0
- package/vitest.config.ts +0 -18
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* structured-output.ts — the synthetic tool behind `agent(prompt, { schema })`.
|
|
3
|
+
*
|
|
4
|
+
* A workflow script that passes a `schema` wants an *object* back, not prose it
|
|
5
|
+
* has to parse. Claude Code does this by giving the child a `StructuredOutput`
|
|
6
|
+
* tool whose input schema is the caller's schema, so the provider fills the
|
|
7
|
+
* fields, and returning the validated payload as the agent's result.
|
|
8
|
+
*
|
|
9
|
+
* We do the same, with one gap named up front: Claude Code *forces* the call,
|
|
10
|
+
* and we cannot. `toolChoice` exists in pi-ai's provider layer but is not
|
|
11
|
+
* plumbed through `AgentSession`, so an extension has no way to require a
|
|
12
|
+
* particular tool. What we have instead is three softer pressures —
|
|
13
|
+
*
|
|
14
|
+
* 1. `constrainedSampling`, so providers that support it hold the payload to
|
|
15
|
+
* the schema at sampling time;
|
|
16
|
+
* 2. the tool's description, snippet and guideline, which say the answer must
|
|
17
|
+
* come through this call;
|
|
18
|
+
* 3. validation here, answering a bad payload with `isError` so the model
|
|
19
|
+
* sees what was wrong and calls again inside the same run.
|
|
20
|
+
*
|
|
21
|
+
* — and, when all three fail, one more prompt from `runAgent`. See
|
|
22
|
+
* {@link structuredRetryPrompt}.
|
|
23
|
+
*
|
|
24
|
+
* The name matches Claude Code's exactly, so a ported prompt that mentions
|
|
25
|
+
* `StructuredOutput` is still telling the truth.
|
|
26
|
+
*/
|
|
27
|
+
import { type ToolDefinition } from "@earendil-works/pi-coding-agent";
|
|
28
|
+
import type { CompiledSchema } from "./workflow/json-schema.js";
|
|
29
|
+
/**
|
|
30
|
+
* Deliberately NOT added to `SUBAGENT_TOOL_NAMES`: that list becomes
|
|
31
|
+
* `EXCLUDED_TOOL_NAMES`, which is exactly the denial this tool has to avoid.
|
|
32
|
+
* Nor to `BUILTIN_TOOL_NAMES` — it is ours to inject, never a name a user may
|
|
33
|
+
* ask for in an agent's `tools:` frontmatter.
|
|
34
|
+
*/
|
|
35
|
+
export declare const STRUCTURED_OUTPUT_TOOL_NAME = "StructuredOutput";
|
|
36
|
+
/** What the child produced, filled in as the tool is called. */
|
|
37
|
+
export interface StructuredCapture {
|
|
38
|
+
/** The last payload that validated, canonicalised. Absent until one does. */
|
|
39
|
+
json?: string;
|
|
40
|
+
/** Why the most recent attempt was rejected, for the retry prompt. */
|
|
41
|
+
lastError?: string;
|
|
42
|
+
/** Whether the tool was called at all — "never tried" reads differently. */
|
|
43
|
+
called: boolean;
|
|
44
|
+
}
|
|
45
|
+
export declare function createStructuredCapture(): StructuredCapture;
|
|
46
|
+
/**
|
|
47
|
+
* Build the tool for one child.
|
|
48
|
+
*
|
|
49
|
+
* `capture` is the box the caller reads afterwards. It is passed in rather than
|
|
50
|
+
* returned so `runAgent` owns its lifetime and can consult it on every exit
|
|
51
|
+
* path, including the ones where the tool was never reached.
|
|
52
|
+
*/
|
|
53
|
+
export declare function createStructuredOutputTool(compiled: CompiledSchema, capture: StructuredCapture): ToolDefinition;
|
|
54
|
+
/**
|
|
55
|
+
* The one extra prompt sent when a run ended with nothing captured.
|
|
56
|
+
*
|
|
57
|
+
* Distinguishes "never called it" from "called it wrongly" — the two need
|
|
58
|
+
* different corrections, and telling a model it got the shape wrong when it
|
|
59
|
+
* never answered at all sends it looking for a mistake it did not make.
|
|
60
|
+
*/
|
|
61
|
+
export declare function structuredRetryPrompt(capture: StructuredCapture): string;
|
|
62
|
+
//# sourceMappingURL=structured-output.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"structured-output.d.ts","sourceRoot":"","sources":["../src/structured-output.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AAEH,OAAO,EAAc,KAAK,cAAc,EAAE,MAAM,iCAAiC,CAAC;AAClF,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,2BAA2B,CAAC;AAEhE;;;;;GAKG;AACH,eAAO,MAAM,2BAA2B,qBAAqB,CAAC;AAE9D,gEAAgE;AAChE,MAAM,WAAW,iBAAiB;IAChC,6EAA6E;IAC7E,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,sEAAsE;IACtE,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,4EAA4E;IAC5E,MAAM,EAAE,OAAO,CAAC;CACjB;AAED,wBAAgB,uBAAuB,IAAI,iBAAiB,CAE3D;AAED;;;;;;GAMG;AACH,wBAAgB,0BAA0B,CACxC,QAAQ,EAAE,cAAc,EACxB,OAAO,EAAE,iBAAiB,GACzB,cAAc,CAqDhB;AAED;;;;;;GAMG;AACH,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,iBAAiB,GAAG,MAAM,CAKxE"}
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* structured-output.ts — the synthetic tool behind `agent(prompt, { schema })`.
|
|
3
|
+
*
|
|
4
|
+
* A workflow script that passes a `schema` wants an *object* back, not prose it
|
|
5
|
+
* has to parse. Claude Code does this by giving the child a `StructuredOutput`
|
|
6
|
+
* tool whose input schema is the caller's schema, so the provider fills the
|
|
7
|
+
* fields, and returning the validated payload as the agent's result.
|
|
8
|
+
*
|
|
9
|
+
* We do the same, with one gap named up front: Claude Code *forces* the call,
|
|
10
|
+
* and we cannot. `toolChoice` exists in pi-ai's provider layer but is not
|
|
11
|
+
* plumbed through `AgentSession`, so an extension has no way to require a
|
|
12
|
+
* particular tool. What we have instead is three softer pressures —
|
|
13
|
+
*
|
|
14
|
+
* 1. `constrainedSampling`, so providers that support it hold the payload to
|
|
15
|
+
* the schema at sampling time;
|
|
16
|
+
* 2. the tool's description, snippet and guideline, which say the answer must
|
|
17
|
+
* come through this call;
|
|
18
|
+
* 3. validation here, answering a bad payload with `isError` so the model
|
|
19
|
+
* sees what was wrong and calls again inside the same run.
|
|
20
|
+
*
|
|
21
|
+
* — and, when all three fail, one more prompt from `runAgent`. See
|
|
22
|
+
* {@link structuredRetryPrompt}.
|
|
23
|
+
*
|
|
24
|
+
* The name matches Claude Code's exactly, so a ported prompt that mentions
|
|
25
|
+
* `StructuredOutput` is still telling the truth.
|
|
26
|
+
*/
|
|
27
|
+
import { defineTool } from "@earendil-works/pi-coding-agent";
|
|
28
|
+
/**
|
|
29
|
+
* Deliberately NOT added to `SUBAGENT_TOOL_NAMES`: that list becomes
|
|
30
|
+
* `EXCLUDED_TOOL_NAMES`, which is exactly the denial this tool has to avoid.
|
|
31
|
+
* Nor to `BUILTIN_TOOL_NAMES` — it is ours to inject, never a name a user may
|
|
32
|
+
* ask for in an agent's `tools:` frontmatter.
|
|
33
|
+
*/
|
|
34
|
+
export const STRUCTURED_OUTPUT_TOOL_NAME = "StructuredOutput";
|
|
35
|
+
export function createStructuredCapture() {
|
|
36
|
+
return { called: false };
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Build the tool for one child.
|
|
40
|
+
*
|
|
41
|
+
* `capture` is the box the caller reads afterwards. It is passed in rather than
|
|
42
|
+
* returned so `runAgent` owns its lifetime and can consult it on every exit
|
|
43
|
+
* path, including the ones where the tool was never reached.
|
|
44
|
+
*/
|
|
45
|
+
export function createStructuredOutputTool(compiled, capture) {
|
|
46
|
+
return defineTool({
|
|
47
|
+
name: STRUCTURED_OUTPUT_TOOL_NAME,
|
|
48
|
+
label: "Structured Output",
|
|
49
|
+
description: "Report your final answer. Call this exactly once, with the complete result, and put everything the "
|
|
50
|
+
+ "caller needs inside the arguments — text written outside this call is discarded. If a call is "
|
|
51
|
+
+ "rejected for not matching the schema, fix the reported fields and call it again.",
|
|
52
|
+
promptSnippet: "Report your final answer as structured data",
|
|
53
|
+
promptGuidelines: [
|
|
54
|
+
"Your final answer MUST be reported by calling StructuredOutput. Prose outside that call is discarded.",
|
|
55
|
+
],
|
|
56
|
+
// The caller's schema *is* the tool's input schema, verbatim — that is what
|
|
57
|
+
// makes the provider fill the fields. pi types this as TypeBox's `TSchema`,
|
|
58
|
+
// which v1 defines as an open interface, so a plain JSON Schema satisfies
|
|
59
|
+
// it without a cast at runtime or a conversion at author time.
|
|
60
|
+
parameters: compiled.schema,
|
|
61
|
+
// "prefer", not "require": a provider that cannot constrain sampling should
|
|
62
|
+
// fall through to validation-and-retry rather than fail the call outright.
|
|
63
|
+
constrainedSampling: { type: "json_schema", strict: "prefer" },
|
|
64
|
+
// Models occasionally send the whole payload as one JSON string instead of
|
|
65
|
+
// an object. Recovering that costs nothing and saves a whole retry.
|
|
66
|
+
prepareArguments: (args) => {
|
|
67
|
+
if (typeof args !== "string")
|
|
68
|
+
return args;
|
|
69
|
+
try {
|
|
70
|
+
return JSON.parse(args);
|
|
71
|
+
}
|
|
72
|
+
catch {
|
|
73
|
+
return args;
|
|
74
|
+
}
|
|
75
|
+
},
|
|
76
|
+
execute: async (_toolCallId, params) => {
|
|
77
|
+
capture.called = true;
|
|
78
|
+
const verdict = compiled.check(params);
|
|
79
|
+
if (verdict !== true) {
|
|
80
|
+
capture.lastError = verdict;
|
|
81
|
+
// `isError` puts the reason in front of the model as a tool result, so
|
|
82
|
+
// it can correct itself inside this same run. This is where most
|
|
83
|
+
// mismatches are resolved; the prompt-level retry is the backstop.
|
|
84
|
+
return {
|
|
85
|
+
content: [{
|
|
86
|
+
type: "text",
|
|
87
|
+
text: `StructuredOutput did not match the required schema:\n${verdict}\nCall it again with a corrected value.`,
|
|
88
|
+
}],
|
|
89
|
+
isError: true,
|
|
90
|
+
details: {},
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
// Last valid call wins: a model that calls twice meant the second one.
|
|
94
|
+
capture.json = JSON.stringify(params);
|
|
95
|
+
capture.lastError = undefined;
|
|
96
|
+
return { content: [{ type: "text", text: "Recorded." }], details: {} };
|
|
97
|
+
},
|
|
98
|
+
});
|
|
99
|
+
}
|
|
100
|
+
/**
|
|
101
|
+
* The one extra prompt sent when a run ended with nothing captured.
|
|
102
|
+
*
|
|
103
|
+
* Distinguishes "never called it" from "called it wrongly" — the two need
|
|
104
|
+
* different corrections, and telling a model it got the shape wrong when it
|
|
105
|
+
* never answered at all sends it looking for a mistake it did not make.
|
|
106
|
+
*/
|
|
107
|
+
export function structuredRetryPrompt(capture) {
|
|
108
|
+
const reason = capture.called && capture.lastError !== undefined
|
|
109
|
+
? `Your last ${STRUCTURED_OUTPUT_TOOL_NAME} call did not match the required schema: ${capture.lastError}`
|
|
110
|
+
: `You did not call ${STRUCTURED_OUTPUT_TOOL_NAME}, so your answer was not recorded.`;
|
|
111
|
+
return `${reason}\n\nCall ${STRUCTURED_OUTPUT_TOOL_NAME} now with your complete final answer. Do not reply with prose.`;
|
|
112
|
+
}
|
|
113
|
+
//# sourceMappingURL=structured-output.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"structured-output.js","sourceRoot":"","sources":["../src/structured-output.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AAEH,OAAO,EAAE,UAAU,EAAuB,MAAM,iCAAiC,CAAC;AAGlF;;;;;GAKG;AACH,MAAM,CAAC,MAAM,2BAA2B,GAAG,kBAAkB,CAAC;AAY9D,MAAM,UAAU,uBAAuB;IACrC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,CAAC;AAC3B,CAAC;AAED;;;;;;GAMG;AACH,MAAM,UAAU,0BAA0B,CACxC,QAAwB,EACxB,OAA0B;IAE1B,OAAO,UAAU,CAAC;QAChB,IAAI,EAAE,2BAA2B;QACjC,KAAK,EAAE,mBAAmB;QAC1B,WAAW,EACT,qGAAqG;cACnG,gGAAgG;cAChG,kFAAkF;QACtF,aAAa,EAAE,6CAA6C;QAC5D,gBAAgB,EAAE;YAChB,uGAAuG;SACxG;QACD,4EAA4E;QAC5E,4EAA4E;QAC5E,0EAA0E;QAC1E,+DAA+D;QAC/D,UAAU,EAAE,QAAQ,CAAC,MAAe;QACpC,4EAA4E;QAC5E,2EAA2E;QAC3E,mBAAmB,EAAE,EAAE,IAAI,EAAE,aAAa,EAAE,MAAM,EAAE,QAAQ,EAAE;QAC9D,2EAA2E;QAC3E,oEAAoE;QACpE,gBAAgB,EAAE,CAAC,IAAa,EAAE,EAAE;YAClC,IAAI,OAAO,IAAI,KAAK,QAAQ;gBAAE,OAAO,IAAa,CAAC;YACnD,IAAI,CAAC;gBACH,OAAO,IAAI,CAAC,KAAK,CAAC,IAAI,CAAU,CAAC;YACnC,CAAC;YAAC,MAAM,CAAC;gBACP,OAAO,IAAa,CAAC;YACvB,CAAC;QACH,CAAC;QACD,OAAO,EAAE,KAAK,EAAE,WAAW,EAAE,MAAM,EAAE,EAAE;YACrC,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC;YACtB,MAAM,OAAO,GAAG,QAAQ,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;YACvC,IAAI,OAAO,KAAK,IAAI,EAAE,CAAC;gBACrB,OAAO,CAAC,SAAS,GAAG,OAAO,CAAC;gBAC5B,uEAAuE;gBACvE,iEAAiE;gBACjE,mEAAmE;gBACnE,OAAO;oBACL,OAAO,EAAE,CAAC;4BACR,IAAI,EAAE,MAAM;4BACZ,IAAI,EAAE,wDAAwD,OAAO,yCAAyC;yBAC/G,CAAC;oBACF,OAAO,EAAE,IAAI;oBACb,OAAO,EAAE,EAAE;iBACZ,CAAC;YACJ,CAAC;YACD,uEAAuE;YACvE,OAAO,CAAC,IAAI,GAAG,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC;YACtC,OAAO,CAAC,SAAS,GAAG,SAAS,CAAC;YAC9B,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,WAAW,EAAE,CAAC,EAAE,OAAO,EAAE,EAAE,EAAE,CAAC;QACzE,CAAC;KACF,CAAmB,CAAC;AACvB,CAAC;AAED;;;;;;GAMG;AACH,MAAM,UAAU,qBAAqB,CAAC,OAA0B;IAC9D,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,IAAI,OAAO,CAAC,SAAS,KAAK,SAAS;QAC9D,CAAC,CAAC,aAAa,2BAA2B,4CAA4C,OAAO,CAAC,SAAS,EAAE;QACzG,CAAC,CAAC,oBAAoB,2BAA2B,oCAAoC,CAAC;IACxF,OAAO,GAAG,MAAM,YAAY,2BAA2B,gEAAgE,CAAC;AAC1H,CAAC"}
|
package/dist/types.d.ts
CHANGED
|
@@ -11,12 +11,25 @@ export type SubagentType = string;
|
|
|
11
11
|
export declare const DEFAULT_AGENT_NAMES: readonly ["general-purpose", "Explore", "Plan"];
|
|
12
12
|
/** Memory scope for persistent agent memory. */
|
|
13
13
|
export type MemoryScope = "user" | "project" | "local";
|
|
14
|
-
/**
|
|
15
|
-
|
|
14
|
+
/**
|
|
15
|
+
* Isolation mode for agent execution.
|
|
16
|
+
*
|
|
17
|
+
* `"off"` exists for the caller's benefit, not the runtime's: models that fill
|
|
18
|
+
* every optional parameter had no legal way to decline a single-value
|
|
19
|
+
* `isolation` field and kept spawning worktrees they had just reasoned their
|
|
20
|
+
* way out of (#231, #184). It is an input spelling only —
|
|
21
|
+
* `resolveAgentInvocationConfig` collapses it to `undefined`, so nothing
|
|
22
|
+
* downstream sees a value other than `"worktree"`. In an agent file it is a
|
|
23
|
+
* genuine veto, since agent config outranks tool-call params.
|
|
24
|
+
*/
|
|
25
|
+
export type IsolationMode = "worktree" | "off";
|
|
16
26
|
/** Unified agent configuration — used for both default and user-defined agents. */
|
|
17
27
|
export interface AgentConfig {
|
|
18
28
|
name: string;
|
|
29
|
+
/** UI name. `display_name` wins; Claude Code's `name` is accepted as a fallback. */
|
|
19
30
|
displayName?: string;
|
|
31
|
+
/** Claude Code-compatible name color (named color or #RRGGBB). */
|
|
32
|
+
color?: string;
|
|
20
33
|
description: string;
|
|
21
34
|
builtinToolNames?: string[];
|
|
22
35
|
/** Raw `ext:` selector entries from the `tools:` CSV, e.g. ["ext:foo", "ext:bar/x"].
|
|
@@ -40,6 +53,11 @@ export interface AgentConfig {
|
|
|
40
53
|
outputTranscript?: boolean;
|
|
41
54
|
/** Optional session directory used when persistSession is true. Omitted = pi's normal session location. */
|
|
42
55
|
sessionDir?: string;
|
|
56
|
+
/**
|
|
57
|
+
* Nested delegation, off by default: undefined = no nested tools;
|
|
58
|
+
* "all" = any enabled agent; string[] = only those agent types.
|
|
59
|
+
*/
|
|
60
|
+
allowedSubagents?: "all" | string[];
|
|
43
61
|
systemPrompt: string;
|
|
44
62
|
promptMode: "replace" | "append";
|
|
45
63
|
/** Default for spawn: fork parent conversation. undefined = caller decides. */
|
|
@@ -50,7 +68,10 @@ export interface AgentConfig {
|
|
|
50
68
|
isolated?: boolean;
|
|
51
69
|
/** Persistent memory scope — agents with memory get a persistent directory and MEMORY.md */
|
|
52
70
|
memory?: MemoryScope;
|
|
53
|
-
/**
|
|
71
|
+
/**
|
|
72
|
+
* Isolation mode — "worktree" runs the agent in a temporary git worktree,
|
|
73
|
+
* "off" refuses one even when the caller asks (frontmatter outranks params).
|
|
74
|
+
*/
|
|
54
75
|
isolation?: IsolationMode;
|
|
55
76
|
/** true = this is an embedded default agent (informational) */
|
|
56
77
|
isDefault?: boolean;
|
|
@@ -58,6 +79,8 @@ export interface AgentConfig {
|
|
|
58
79
|
enabled?: boolean;
|
|
59
80
|
/** Where this agent was loaded from */
|
|
60
81
|
source?: "default" | "project" | "global";
|
|
82
|
+
/** Path of the .md it was loaded from. Unset for embedded defaults. */
|
|
83
|
+
sourcePath?: string;
|
|
61
84
|
}
|
|
62
85
|
export type JoinMode = 'async' | 'group' | 'smart';
|
|
63
86
|
/**
|
|
@@ -68,9 +91,75 @@ export type JoinMode = 'async' | 'group' | 'smart';
|
|
|
68
91
|
* - `off`: hide the widget entirely.
|
|
69
92
|
*/
|
|
70
93
|
export type WidgetMode = 'all' | 'background' | 'off';
|
|
94
|
+
/**
|
|
95
|
+
* How much of the conversation viewer's transcript is rendered as Markdown.
|
|
96
|
+
* - `off`: every line wraps as literal text, as it did before the mode existed.
|
|
97
|
+
* - `assistant`: assistant text renders as Markdown; tool results stay verbatim
|
|
98
|
+
* and dim. The default, because assistant text *is* Markdown by contract
|
|
99
|
+
* while a tool result is arbitrary bytes — a Markdown pass over a log or a
|
|
100
|
+
* diff eats `#` from shell comments, swallows a `---` line into a setext
|
|
101
|
+
* heading, re-fences indented output and redraws `| a | b |` as a table.
|
|
102
|
+
* (Ordered-list renumbering is the one such rewrite actively suppressed —
|
|
103
|
+
* see `MARKDOWN_OPTIONS` — because it silently changes data, not layout.)
|
|
104
|
+
* - `all`: tool results render as Markdown too, for tools that genuinely emit
|
|
105
|
+
* it (#210's `ctx_execute`), accepting the rewrites above on ones that don't.
|
|
106
|
+
*/
|
|
107
|
+
export type ViewerMarkdownMode = 'off' | 'assistant' | 'all';
|
|
108
|
+
/**
|
|
109
|
+
* How `@handle message` starts an agent that is not already running.
|
|
110
|
+
* - `model`: inject Claude Code's `agent_mention` reminder and let the main
|
|
111
|
+
* model spawn it with the `Agent` tool, which is what Claude Code does.
|
|
112
|
+
* - `direct`: spawn it here, immediately, with the typed message as its prompt
|
|
113
|
+
* and no main-model turn spent.
|
|
114
|
+
* - `off`: `@` means only "attach a file" again.
|
|
115
|
+
*
|
|
116
|
+
* Messaging a running agent and resuming a finished one are direct in every
|
|
117
|
+
* mode — Claude Code only differs from us on the *new* invocation.
|
|
118
|
+
*/
|
|
119
|
+
export type AgentMentionMode = 'model' | 'direct' | 'off';
|
|
120
|
+
/**
|
|
121
|
+
* What survives a record's eviction so `@handle` keeps working. The live record
|
|
122
|
+
* is discarded after ~10 minutes, but the pi session it wrote is still on disk,
|
|
123
|
+
* and this is the little that is needed to find and describe it again.
|
|
124
|
+
*/
|
|
125
|
+
export interface AgentTombstone {
|
|
126
|
+
handle: string;
|
|
127
|
+
alias?: string;
|
|
128
|
+
id: string;
|
|
129
|
+
type: SubagentType;
|
|
130
|
+
description: string;
|
|
131
|
+
/** Always set — a record with no session file is never tombstoned. */
|
|
132
|
+
sessionFile: string;
|
|
133
|
+
completedAt: number;
|
|
134
|
+
}
|
|
135
|
+
/**
|
|
136
|
+
* What `@handle` resolved to: an agent still in memory, or the remains of one
|
|
137
|
+
* whose conversation can be reopened from disk.
|
|
138
|
+
*/
|
|
139
|
+
export type MentionResolution = {
|
|
140
|
+
kind: "live";
|
|
141
|
+
record: AgentRecord;
|
|
142
|
+
} | {
|
|
143
|
+
kind: "tombstone";
|
|
144
|
+
entry: AgentTombstone;
|
|
145
|
+
};
|
|
71
146
|
export interface AgentRecord {
|
|
72
147
|
id: string;
|
|
73
148
|
type: SubagentType;
|
|
149
|
+
/**
|
|
150
|
+
* Typeable name for the `@handle message` prompt mention, derived from the
|
|
151
|
+
* agent type and numbered when siblings collide (`explore`, `explore-2`).
|
|
152
|
+
* Top-level agents only — nested children are hidden from every top-level
|
|
153
|
+
* surface, so nothing can address them.
|
|
154
|
+
*/
|
|
155
|
+
handle?: string;
|
|
156
|
+
/**
|
|
157
|
+
* A second, memorable handle from the spawner's `name` (`@auth-audit`), drawn
|
|
158
|
+
* from the same namespace as `handle` so the two can never collide. Purely
|
|
159
|
+
* additive: `handle` is assigned regardless, so a named agent stays reachable
|
|
160
|
+
* by its type and `@explore` never comes to mean "start another one".
|
|
161
|
+
*/
|
|
162
|
+
alias?: string;
|
|
74
163
|
description: string;
|
|
75
164
|
status: "queued" | "running" | "completed" | "steered" | "aborted" | "stopped" | "error";
|
|
76
165
|
result?: string;
|
|
@@ -81,6 +170,22 @@ export interface AgentRecord {
|
|
|
81
170
|
session?: AgentSession;
|
|
82
171
|
abortController?: AbortController;
|
|
83
172
|
promise?: Promise<string>;
|
|
173
|
+
/**
|
|
174
|
+
* A caller is awaiting this agent inline (`spawnAndWait`) — what
|
|
175
|
+
* `maxConcurrentForeground` bounds. Distinct from `isBackground === false`,
|
|
176
|
+
* which says only that the agent has an inline result surface: a detached
|
|
177
|
+
* cross-extension RPC spawn is foreground by that measure and yet blocks
|
|
178
|
+
* nobody, so it takes no slot.
|
|
179
|
+
*/
|
|
180
|
+
blocking?: boolean;
|
|
181
|
+
/**
|
|
182
|
+
* Present only while the record is "queued": resolves when it leaves the
|
|
183
|
+
* queue, started or aborted. `spawnAndWait` waits on this because a queued
|
|
184
|
+
* record has no `promise` yet. Always resolves, never rejects — a rejection
|
|
185
|
+
* would escape into the caller's tool `execute` and take down pi's whole
|
|
186
|
+
* Promise.all tool batch.
|
|
187
|
+
*/
|
|
188
|
+
startGate?: Promise<void>;
|
|
84
189
|
groupId?: string;
|
|
85
190
|
joinMode?: JoinMode;
|
|
86
191
|
/** Set when result was already consumed via get_subagent_result — suppresses completion notification. */
|
|
@@ -107,8 +212,17 @@ export interface AgentRecord {
|
|
|
107
212
|
historyFile?: string;
|
|
108
213
|
/** Project-relative durable transcript path persisted in the parent session. */
|
|
109
214
|
transcriptPath?: string;
|
|
110
|
-
/**
|
|
215
|
+
/**
|
|
216
|
+
* The agent's pi session file, when it was persisted (`persist_session`, or
|
|
217
|
+
* the `rememberAgents` default). Captured so a mention can reopen the
|
|
218
|
+
* conversation after the record itself has been evicted; undefined for an
|
|
219
|
+
* in-memory session, which leaves nothing to reopen.
|
|
220
|
+
*/
|
|
221
|
+
sessionFile?: string;
|
|
222
|
+
/** Cleanup function for the optional `.output` stream subscription. */
|
|
111
223
|
outputCleanup?: () => void;
|
|
224
|
+
/** Cleanup function for the mandatory durable `.pi-subagents` history stream. */
|
|
225
|
+
historyCleanup?: () => void;
|
|
112
226
|
/**
|
|
113
227
|
* Lifetime usage breakdown, accumulated via `message_end` events. Survives
|
|
114
228
|
* compaction. Total = input + output + cacheWrite (cacheRead deliberately
|
|
@@ -130,15 +244,61 @@ export interface AgentRecord {
|
|
|
130
244
|
isBackground?: boolean;
|
|
131
245
|
/** Resolved spawn params, captured for UI display. Fixed at spawn time. */
|
|
132
246
|
invocation?: AgentInvocation;
|
|
247
|
+
/** Nesting depth: top-level subagent = 1. */
|
|
248
|
+
depth?: number;
|
|
249
|
+
/**
|
|
250
|
+
* The validated `StructuredOutput` payload, as canonical JSON.
|
|
251
|
+
*
|
|
252
|
+
* Set only when the spawn asked for a schema. Separate from `result` because
|
|
253
|
+
* `result` is prose for a reader — previewed in the widget, written to the
|
|
254
|
+
* transcript, and appended to with the worktree branch note — and JSON that
|
|
255
|
+
* has been appended to no longer parses.
|
|
256
|
+
*/
|
|
257
|
+
structuredJson?: string;
|
|
258
|
+
/** Whether the child needed the extra structured-output prompt. */
|
|
259
|
+
structuredRetried?: boolean;
|
|
260
|
+
/** Parent agent ID for ownership-scoped nested controls. */
|
|
261
|
+
parentAgentId?: string;
|
|
262
|
+
/**
|
|
263
|
+
* The workflow run that owns this child, when a workflow spawned it.
|
|
264
|
+
*
|
|
265
|
+
* Owned the same way a nested child is owned by its parent: filtered out of
|
|
266
|
+
* every top-level surface, and outside the `maxConcurrent` pool. See
|
|
267
|
+
* `isTopLevelAgent`.
|
|
268
|
+
*/
|
|
269
|
+
workflowId?: string;
|
|
270
|
+
/** Effective inherited nesting cap for this branch. */
|
|
271
|
+
maxSubagentDepth?: number;
|
|
272
|
+
/**
|
|
273
|
+
* Session id of the root (main) session this branch descends from. Nested
|
|
274
|
+
* spawns inherit it so their transcripts file under the same session
|
|
275
|
+
* directory as their ancestors' instead of the child session's own id.
|
|
276
|
+
*/
|
|
277
|
+
rootSessionId?: string;
|
|
133
278
|
}
|
|
279
|
+
/**
|
|
280
|
+
* What a session reports as its level: pi's `ThinkingLevel` plus the `"off"` a
|
|
281
|
+
* model with thinking disabled reports. Display-only — spawning still takes a
|
|
282
|
+
* `ThinkingLevel`, so this widening cannot leak into an invocation.
|
|
283
|
+
*/
|
|
284
|
+
export type EffectiveThinkingLevel = ThinkingLevel | "off";
|
|
134
285
|
export interface AgentInvocation {
|
|
135
|
-
/** Short display name, e.g. "haiku"
|
|
286
|
+
/** Short display name for tight rows, e.g. "haiku 4.5". Always set once known. */
|
|
136
287
|
modelName?: string;
|
|
137
|
-
/**
|
|
138
|
-
|
|
139
|
-
/**
|
|
140
|
-
|
|
141
|
-
|
|
288
|
+
/** Canonical `provider/id`, for surfaces with room to disambiguate providers. */
|
|
289
|
+
modelId?: string;
|
|
290
|
+
/** The level actually in effect, once a session exists to report one. */
|
|
291
|
+
thinking?: EffectiveThinkingLevel;
|
|
292
|
+
/**
|
|
293
|
+
* What the caller asked for, kept only when they did not get it — pi clamped
|
|
294
|
+
* the level to the model's capabilities, or an agent file's frontmatter
|
|
295
|
+
* outranked the parameter (#182). The snapshot exists to answer "did the spawn
|
|
296
|
+
* honor my instructions?" (#62), which it cannot do if the request is lost, so
|
|
297
|
+
* neither `requested*` field is overwritten once set.
|
|
298
|
+
*/
|
|
299
|
+
requestedThinking?: EffectiveThinkingLevel;
|
|
300
|
+
/** The caller's `model` parameter, as written, when an agent file's pin won. */
|
|
301
|
+
requestedModel?: string;
|
|
142
302
|
maxTurns?: number;
|
|
143
303
|
isolated?: boolean;
|
|
144
304
|
inheritContext?: boolean;
|
|
@@ -154,6 +314,12 @@ export interface NotificationDetails {
|
|
|
154
314
|
turnCount: number;
|
|
155
315
|
maxTurns?: number;
|
|
156
316
|
totalTokens: number;
|
|
317
|
+
/**
|
|
318
|
+
* Estimated cost in USD, from pi's per-message `usage.cost.total`. Always
|
|
319
|
+
* populated (0 when the model has no pricing); the renderer decides whether
|
|
320
|
+
* to show it, per the `showCost` setting.
|
|
321
|
+
*/
|
|
322
|
+
totalCost?: number;
|
|
157
323
|
durationMs: number;
|
|
158
324
|
outputFile?: string;
|
|
159
325
|
error?: string;
|
package/dist/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,uBAAuB,CAAC;AAC3D,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,iCAAiC,CAAC;AACpE,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,YAAY,CAAC;AAEhD,YAAY,EAAE,aAAa,EAAE,CAAC;AAE9B,uEAAuE;AACvE,MAAM,MAAM,YAAY,GAAG,MAAM,CAAC;AAElC,kDAAkD;AAClD,eAAO,MAAM,mBAAmB,iDAAkD,CAAC;AAEnF,gDAAgD;AAChD,MAAM,MAAM,WAAW,GAAG,MAAM,GAAG,SAAS,GAAG,OAAO,CAAC;AAEvD
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* agent-mention.ts — what `@` can address, and the suggestions pi renders for it.
|
|
3
|
+
*
|
|
4
|
+
* A subagent is addressable whether or not it is currently running: a live
|
|
5
|
+
* record is messaged or resumed, an evicted one whose session is still on disk
|
|
6
|
+
* is reopened, and an agent *type* with no instance at all is started. That is
|
|
7
|
+
* the point of the handle — `@explore` means the Explore agent, not "the
|
|
8
|
+
* Explore process that happens to exist right now" — so the roster below unions
|
|
9
|
+
* all three, and the dispatcher and the popup read the same list.
|
|
10
|
+
*
|
|
11
|
+
* Rows are per *agent*, not per handle. An agent given a `name` holds two names
|
|
12
|
+
* (its alias and its type-derived handle) and both resolve, but it lists once,
|
|
13
|
+
* under the alias, with its type moved into the description so the row still
|
|
14
|
+
* says what it is.
|
|
15
|
+
*
|
|
16
|
+
* pi's `CombinedAutocompleteProvider` already owns `@`, where it means "attach a
|
|
17
|
+
* file". Extensions can wrap it (`ctx.ui.addAutocompleteProvider`), so this
|
|
18
|
+
* provider adds the `@` tokens that name an agent and delegates everything else
|
|
19
|
+
* — including all of `applyCompletion`, whose `@`-branch already inserts
|
|
20
|
+
* `item.value` plus a trailing space, which is exactly what a handle needs.
|
|
21
|
+
*
|
|
22
|
+
* Matching mirrors Claude Code: case-insensitive prefix, not fuzzy. What it does
|
|
23
|
+
* NOT mirror is Claude Code dropping files whenever an agent matches. Here `@` is
|
|
24
|
+
* pi's file picker first, and the handles are additive, so a token matching both
|
|
25
|
+
* lists both — agents first. Suppressing on any match sounds narrow and is not:
|
|
26
|
+
* an empty token prefix-matches every handle, so a bare `@` — the gesture people
|
|
27
|
+
* use to browse files — would offer no files at all, and a single letter
|
|
28
|
+
* beginning any handle would do the same.
|
|
29
|
+
*
|
|
30
|
+
* Both halves ship under ONE `prefix`, which is sound because wherever BOTH sides
|
|
31
|
+
* produce rows they measured the same span. pi's `extractAtPrefix` takes the
|
|
32
|
+
* token after the last of `{space, tab, ", ', =}` and keeps it only if it starts
|
|
33
|
+
* with `@`; `MENTION_TRIGGER` matches `@[\w-]*` at the cursor, after start-of-line
|
|
34
|
+
* or `[\s。、?!]`. Where those two disagree, exactly one side answers and there
|
|
35
|
+
* is nothing to merge: `@src/index.ts` and `@"my file` are pi's alone (no handle
|
|
36
|
+
* matches), `=@ex` is pi's alone (`=` is a delimiter to pi, not a boundary to us),
|
|
37
|
+
* and `。@ex` is ours alone (the reverse). A merged response therefore never
|
|
38
|
+
* carries a prefix from one side and an item from the other.
|
|
39
|
+
*
|
|
40
|
+
* Offering never-started types is a deliberate step beyond Claude Code, whose
|
|
41
|
+
* registry holds only live tasks, so an agent you had not launched yet was
|
|
42
|
+
* unaddressable.
|
|
43
|
+
*/
|
|
44
|
+
import type { AutocompleteProvider } from "@earendil-works/pi-tui";
|
|
45
|
+
import type { AgentManager } from "../agent-manager.js";
|
|
46
|
+
import type { AgentRecord, AgentTombstone } from "../types.js";
|
|
47
|
+
/**
|
|
48
|
+
* One thing `@` can address, and what sending to it will do. `typeLabel` is the
|
|
49
|
+
* agent's `display_name`, resolved by the caller: this module stays independent
|
|
50
|
+
* of the type registry, but the popup must agree with FleetView and the widget,
|
|
51
|
+
* which both render the label rather than the raw type.
|
|
52
|
+
*/
|
|
53
|
+
export type MentionTarget = {
|
|
54
|
+
kind: "record";
|
|
55
|
+
handle: string;
|
|
56
|
+
record: AgentRecord;
|
|
57
|
+
typeLabel: string;
|
|
58
|
+
} | {
|
|
59
|
+
kind: "tombstone";
|
|
60
|
+
handle: string;
|
|
61
|
+
entry: AgentTombstone;
|
|
62
|
+
typeLabel: string;
|
|
63
|
+
} | {
|
|
64
|
+
kind: "type";
|
|
65
|
+
handle: string;
|
|
66
|
+
type: string;
|
|
67
|
+
description: string;
|
|
68
|
+
};
|
|
69
|
+
/** The registry facts the roster needs, so it stays independent of agent-types. */
|
|
70
|
+
export type TypeInfo = {
|
|
71
|
+
name: string;
|
|
72
|
+
description: string;
|
|
73
|
+
};
|
|
74
|
+
/**
|
|
75
|
+
* Everything `@` can reach, in the order the popup lists it: steerable agents
|
|
76
|
+
* first, then the other live ones earliest-launched, then agent types with no
|
|
77
|
+
* live instance. A type whose handle a record already holds is omitted — that
|
|
78
|
+
* name addresses the existing agent, which is what makes `@explore` mean
|
|
79
|
+
* "message the one that's running" and only otherwise "start one".
|
|
80
|
+
*/
|
|
81
|
+
export declare function mentionRoster(manager: AgentManager, types: readonly TypeInfo[], displayNameOf?: (type: string) => string): MentionTarget[];
|
|
82
|
+
export declare function createMentionProvider(current: AutocompleteProvider, roster: () => MentionTarget[], isEnabled: () => boolean): AutocompleteProvider;
|
|
83
|
+
//# sourceMappingURL=agent-mention.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"agent-mention.d.ts","sourceRoot":"","sources":["../../src/ui/agent-mention.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA0CG;AAEH,OAAO,KAAK,EAAoB,oBAAoB,EAA2B,MAAM,wBAAwB,CAAC;AAC9G,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AAExD,OAAO,KAAK,EAAE,WAAW,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAE/D;;;;;GAKG;AACH,MAAM,MAAM,aAAa,GACrB;IAAE,IAAI,EAAE,QAAQ,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,WAAW,CAAC;IAAC,SAAS,EAAE,MAAM,CAAA;CAAE,GAC1E;IAAE,IAAI,EAAE,WAAW,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,cAAc,CAAC;IAAC,SAAS,EAAE,MAAM,CAAA;CAAE,GAC/E;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,WAAW,EAAE,MAAM,CAAA;CAAE,CAAC;AAExE,mFAAmF;AACnF,MAAM,MAAM,QAAQ,GAAG;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,WAAW,EAAE,MAAM,CAAA;CAAE,CAAC;AAE7D;;;;;;GAMG;AACH,wBAAgB,aAAa,CAC3B,OAAO,EAAE,YAAY,EACrB,KAAK,EAAE,SAAS,QAAQ,EAAE,EAG1B,aAAa,GAAE,CAAC,IAAI,EAAE,MAAM,KAAK,MAAqB,GACrD,aAAa,EAAE,CAsCjB;AAED,wBAAgB,qBAAqB,CACnC,OAAO,EAAE,oBAAoB,EAC7B,MAAM,EAAE,MAAM,aAAa,EAAE,EAC7B,SAAS,EAAE,MAAM,OAAO,GACvB,oBAAoB,CA0DtB"}
|