@oh-my-pi/pi-coding-agent 16.2.2 → 16.2.3
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 +49 -0
- package/dist/cli.js +3624 -3568
- package/dist/types/advisor/__tests__/config.test.d.ts +1 -0
- package/dist/types/advisor/advise-tool.d.ts +8 -4
- package/dist/types/advisor/config.d.ts +88 -0
- package/dist/types/advisor/index.d.ts +1 -0
- package/dist/types/advisor/transcript-recorder.d.ts +13 -2
- package/dist/types/advisor/watchdog.d.ts +20 -0
- package/dist/types/collab/guest.d.ts +29 -0
- package/dist/types/config/settings-schema.d.ts +81 -0
- package/dist/types/debug/log-viewer.d.ts +1 -0
- package/dist/types/debug/raw-sse.d.ts +1 -0
- package/dist/types/edit/hashline/diff.d.ts +0 -11
- package/dist/types/extensibility/tool-event-input.d.ts +7 -0
- package/dist/types/extensibility/utils.d.ts +12 -0
- package/dist/types/mcp/transports/index.d.ts +1 -0
- package/dist/types/mcp/transports/sse.d.ts +20 -0
- package/dist/types/modes/components/advisor-config.d.ts +59 -0
- package/dist/types/modes/components/index.d.ts +1 -0
- package/dist/types/modes/components/model-selector.d.ts +9 -1
- package/dist/types/modes/components/settings-selector.d.ts +1 -0
- package/dist/types/modes/components/status-line/component.d.ts +30 -1
- package/dist/types/modes/components/status-line/types.d.ts +13 -1
- package/dist/types/modes/controllers/selector-controller.d.ts +1 -0
- package/dist/types/modes/interactive-mode.d.ts +10 -4
- package/dist/types/modes/skill-command.d.ts +32 -0
- package/dist/types/modes/types.d.ts +7 -2
- package/dist/types/session/agent-session.d.ts +58 -10
- package/dist/types/session/indexed-session-storage.d.ts +7 -1
- package/dist/types/session/messages.d.ts +26 -0
- package/dist/types/session/messages.test.d.ts +1 -0
- package/dist/types/session/session-entries.d.ts +31 -3
- package/dist/types/session/session-history-format.d.ts +6 -0
- package/dist/types/session/session-loader.d.ts +9 -1
- package/dist/types/session/session-manager.d.ts +6 -4
- package/dist/types/session/session-storage.d.ts +11 -0
- package/dist/types/session/session-title-slot.d.ts +19 -0
- package/dist/types/ssh/connection-manager.d.ts +47 -0
- package/dist/types/ssh/utils.d.ts +16 -0
- package/dist/types/task/executor.d.ts +3 -16
- package/dist/types/task/render.d.ts +0 -5
- package/dist/types/task/renderer.d.ts +13 -0
- package/dist/types/task/types.d.ts +16 -0
- package/dist/types/task/yield-assembly.d.ts +28 -0
- package/dist/types/tiny/text.d.ts +8 -0
- package/dist/types/tools/render-utils.d.ts +2 -0
- package/dist/types/tools/review.d.ts +6 -4
- package/dist/types/tools/ssh.d.ts +1 -1
- package/dist/types/tools/todo.d.ts +6 -0
- package/dist/types/tools/yield.d.ts +8 -3
- package/dist/types/utils/thinking-display.d.ts +4 -0
- package/package.json +12 -12
- package/src/advisor/__tests__/advisor.test.ts +242 -10
- package/src/advisor/__tests__/config.test.ts +173 -0
- package/src/advisor/advise-tool.ts +11 -6
- package/src/advisor/config.ts +256 -0
- package/src/advisor/index.ts +1 -0
- package/src/advisor/runtime.ts +12 -2
- package/src/advisor/transcript-recorder.ts +25 -2
- package/src/advisor/watchdog.ts +57 -31
- package/src/autoresearch/index.ts +7 -2
- package/src/cli/gc-cli.ts +17 -10
- package/src/collab/guest.ts +43 -7
- package/src/config/model-registry.ts +80 -18
- package/src/config/settings-schema.ts +77 -0
- package/src/debug/index.ts +32 -7
- package/src/debug/log-viewer.ts +111 -53
- package/src/debug/raw-sse.ts +68 -48
- package/src/discovery/codex.ts +13 -5
- package/src/edit/hashline/diff.ts +57 -4
- package/src/eval/js/shared/local-module-loader.ts +23 -1
- package/src/export/html/template.js +13 -7
- package/src/extensibility/extensions/loader.ts +5 -3
- package/src/extensibility/extensions/wrapper.ts +9 -3
- package/src/extensibility/hooks/loader.ts +3 -3
- package/src/extensibility/hooks/tool-wrapper.ts +13 -4
- package/src/extensibility/plugins/manager.ts +2 -1
- package/src/extensibility/tool-event-input.ts +23 -0
- package/src/extensibility/utils.ts +74 -0
- package/src/internal-urls/docs-index.generated.txt +1 -1
- package/src/mcp/client.ts +3 -1
- package/src/mcp/manager.ts +12 -5
- package/src/mcp/transports/index.ts +1 -0
- package/src/mcp/transports/sse.ts +377 -0
- package/src/memories/index.ts +15 -6
- package/src/modes/components/advisor-config.ts +555 -0
- package/src/modes/components/advisor-message.ts +9 -2
- package/src/modes/components/agent-hub.ts +9 -4
- package/src/modes/components/index.ts +2 -0
- package/src/modes/components/model-selector.ts +79 -48
- package/src/modes/components/settings-selector.ts +1 -0
- package/src/modes/components/status-line/component.ts +144 -5
- package/src/modes/components/status-line/segments.ts +46 -21
- package/src/modes/components/status-line/types.ts +13 -1
- package/src/modes/components/tool-execution.ts +47 -6
- package/src/modes/controllers/command-controller.ts +23 -2
- package/src/modes/controllers/event-controller.ts +106 -0
- package/src/modes/controllers/extension-ui-controller.ts +1 -1
- package/src/modes/controllers/input-controller.ts +61 -61
- package/src/modes/controllers/selector-controller.ts +100 -9
- package/src/modes/interactive-mode.ts +65 -5
- package/src/modes/skill-command.ts +116 -0
- package/src/modes/types.ts +7 -2
- package/src/modes/utils/ui-helpers.ts +41 -23
- package/src/prompts/agents/reviewer.md +11 -10
- package/src/prompts/review-custom-request.md +1 -2
- package/src/prompts/review-request.md +1 -2
- package/src/prompts/system/interrupted-thinking.md +7 -0
- package/src/prompts/system/recap-user.md +9 -0
- package/src/prompts/system/subagent-system-prompt.md +8 -5
- package/src/prompts/system/subagent-yield-reminder.md +6 -5
- package/src/prompts/system/system-prompt.md +0 -1
- package/src/prompts/tools/irc.md +2 -2
- package/src/prompts/tools/read.md +2 -2
- package/src/sdk.ts +28 -24
- package/src/session/agent-session.ts +867 -428
- package/src/session/indexed-session-storage.ts +86 -13
- package/src/session/messages.test.ts +125 -0
- package/src/session/messages.ts +172 -9
- package/src/session/redis-session-storage.ts +49 -2
- package/src/session/session-entries.ts +39 -2
- package/src/session/session-history-format.ts +29 -2
- package/src/session/session-listing.ts +54 -24
- package/src/session/session-loader.ts +66 -3
- package/src/session/session-manager.ts +113 -19
- package/src/session/session-persistence.ts +95 -1
- package/src/session/session-storage.ts +36 -0
- package/src/session/session-title-slot.ts +141 -0
- package/src/session/sql-session-storage.ts +71 -11
- package/src/slash-commands/builtin-registry.ts +16 -3
- package/src/ssh/__tests__/connection-manager-args.test.ts +123 -1
- package/src/ssh/__tests__/file-transfer-posix-guard.test.ts +55 -18
- package/src/ssh/connection-manager.ts +139 -12
- package/src/ssh/file-transfer.ts +23 -18
- package/src/ssh/ssh-executor.ts +2 -13
- package/src/ssh/utils.ts +19 -0
- package/src/task/executor.ts +21 -23
- package/src/task/render.ts +162 -20
- package/src/task/renderer.ts +14 -0
- package/src/task/types.ts +17 -0
- package/src/task/yield-assembly.ts +207 -0
- package/src/tiny/text.ts +23 -0
- package/src/tools/ask.ts +55 -4
- package/src/tools/render-utils.ts +2 -0
- package/src/tools/renderers.ts +8 -2
- package/src/tools/review.ts +17 -7
- package/src/tools/ssh.ts +8 -4
- package/src/tools/todo.ts +17 -1
- package/src/tools/yield.ts +140 -31
- package/src/utils/thinking-display.ts +15 -0
|
@@ -109,11 +109,16 @@ export declare class InteractiveMode implements InteractiveModeContext {
|
|
|
109
109
|
loopLimit: LoopLimitRuntime | undefined;
|
|
110
110
|
todoPhases: TodoPhase[];
|
|
111
111
|
hideThinkingBlock: boolean;
|
|
112
|
+
/** Whether the visible session has produced thinking content the user can reveal. */
|
|
113
|
+
get hasDisplayableThinkingContent(): boolean;
|
|
114
|
+
/** Record received reasoning content so Ctrl+T can reveal it even when model metadata says thinking is off. */
|
|
115
|
+
noteDisplayableThinkingContent(message: AgentMessage): boolean;
|
|
112
116
|
/**
|
|
113
|
-
* Effective thinking-block visibility: hidden when the user's setting is on
|
|
114
|
-
*
|
|
115
|
-
*
|
|
116
|
-
*
|
|
117
|
+
* Effective thinking-block visibility: hidden when the user's setting is on,
|
|
118
|
+
* or while thinking is "off" before the session has actually produced
|
|
119
|
+
* displayable thinking content. Some providers return thinking blocks without
|
|
120
|
+
* advertising reasoning support, so observed content unlocks the visibility
|
|
121
|
+
* toggle.
|
|
117
122
|
*/
|
|
118
123
|
get effectiveHideThinkingBlock(): boolean;
|
|
119
124
|
proseOnlyThinking: boolean;
|
|
@@ -319,6 +324,7 @@ export declare class InteractiveMode implements InteractiveModeContext {
|
|
|
319
324
|
executeCompaction(customInstructionsOrOptions?: string | CompactOptions, isAuto?: boolean): Promise<CompactionOutcome>;
|
|
320
325
|
openInBrowser(urlOrPath: string): void;
|
|
321
326
|
showSettingsSelector(): void;
|
|
327
|
+
showAdvisorConfigure(): void;
|
|
322
328
|
showHistorySearch(): void;
|
|
323
329
|
showExtensionsDashboard(): void;
|
|
324
330
|
showAgentsDashboard(): void;
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import type { ImageContent, TextContent } from "@oh-my-pi/pi-ai";
|
|
2
|
+
import { type CustomMessage, SKILL_PROMPT_MESSAGE_TYPE, type SkillPromptDetails } from "../session/messages";
|
|
3
|
+
import type { InteractiveModeContext } from "./types";
|
|
4
|
+
type SkillCommandHost = Pick<InteractiveModeContext, "skillCommands" | "session" | "showError">;
|
|
5
|
+
type SkillPromptMessage = Pick<CustomMessage<SkillPromptDetails>, "customType" | "content" | "display" | "details" | "attribution"> & {
|
|
6
|
+
customType: typeof SKILL_PROMPT_MESSAGE_TYPE;
|
|
7
|
+
content: string | (TextContent | ImageContent)[];
|
|
8
|
+
display: true;
|
|
9
|
+
details: SkillPromptDetails;
|
|
10
|
+
attribution: "user";
|
|
11
|
+
};
|
|
12
|
+
type SkillPromptOptions = {
|
|
13
|
+
streamingBehavior: "steer" | "followUp";
|
|
14
|
+
queueChipText: string;
|
|
15
|
+
};
|
|
16
|
+
interface InvokeSkillCommandOptions {
|
|
17
|
+
propagateErrors?: boolean;
|
|
18
|
+
queueOnly?: boolean;
|
|
19
|
+
images?: ImageContent[];
|
|
20
|
+
}
|
|
21
|
+
/** Built custom-message payload and delivery options for a `/skill:` command. */
|
|
22
|
+
export interface BuiltSkillCommandPrompt {
|
|
23
|
+
message: SkillPromptMessage;
|
|
24
|
+
options: SkillPromptOptions;
|
|
25
|
+
}
|
|
26
|
+
/** Return true when `text` names a registered `/skill:<name>` command. */
|
|
27
|
+
export declare function isKnownSkillCommand(ctx: SkillCommandHost, text: string): boolean;
|
|
28
|
+
/** Build the user-attributed custom message for a registered `/skill:<name>` command. */
|
|
29
|
+
export declare function buildSkillCommandPrompt(ctx: SkillCommandHost, text: string, streamingBehavior: "steer" | "followUp", images?: ImageContent[]): Promise<BuiltSkillCommandPrompt | undefined>;
|
|
30
|
+
/** Invoke a registered `/skill:<name>` command as a user-attributed custom message. */
|
|
31
|
+
export declare function invokeSkillCommandFromText(ctx: SkillCommandHost, text: string, streamingBehavior: "steer" | "followUp", options?: InvokeSkillCommandOptions): Promise<boolean>;
|
|
32
|
+
export {};
|
|
@@ -142,10 +142,14 @@ export interface InteractiveModeContext {
|
|
|
142
142
|
hideThinkingBlock: boolean;
|
|
143
143
|
/**
|
|
144
144
|
* Effective thinking-block visibility: true when hidden by user setting OR
|
|
145
|
-
* thinking level is "off"
|
|
146
|
-
*
|
|
145
|
+
* thinking level is "off" before the session has produced displayable
|
|
146
|
+
* thinking content.
|
|
147
147
|
*/
|
|
148
148
|
readonly effectiveHideThinkingBlock: boolean;
|
|
149
|
+
/** Whether this visible session has produced thinking content the user can reveal. */
|
|
150
|
+
readonly hasDisplayableThinkingContent: boolean;
|
|
151
|
+
/** Record a message whose thinking content makes Ctrl+T meaningful even at thinking level "off"; returns true on first observation. */
|
|
152
|
+
noteDisplayableThinkingContent(message: AgentMessage): boolean;
|
|
149
153
|
proseOnlyThinking: boolean;
|
|
150
154
|
compactionQueuedMessages: CompactionQueuedMessage[];
|
|
151
155
|
pendingTools: Map<string, ToolExecutionHandle>;
|
|
@@ -316,6 +320,7 @@ export interface InteractiveModeContext {
|
|
|
316
320
|
refreshSlashCommandState(cwd?: string): Promise<void>;
|
|
317
321
|
applyCwdChange(newCwd: string): Promise<void>;
|
|
318
322
|
showSettingsSelector(): void;
|
|
323
|
+
showAdvisorConfigure(): void;
|
|
319
324
|
showHistorySearch(): void;
|
|
320
325
|
showExtensionsDashboard(): void;
|
|
321
326
|
showAgentsDashboard(): void;
|
|
@@ -17,6 +17,7 @@ import { Agent, type AgentEvent, type AgentMessage, type AgentState, type AgentT
|
|
|
17
17
|
import { type CompactionResult, type ShakeConfig } from "@oh-my-pi/pi-agent-core/compaction";
|
|
18
18
|
import type { AssistantMessage, Context, ImageContent, Message, MessageAttribution, Model, ProviderSessionState, ResetCreditAccountStatus, ResetCreditRedeemOutcome, ResetCreditTarget, ServiceTier, SimpleStreamOptions, TextContent, ToolChoice, UsageReport } from "@oh-my-pi/pi-ai";
|
|
19
19
|
import { Effort } from "@oh-my-pi/pi-ai";
|
|
20
|
+
import { type AdvisorConfig } from "../advisor";
|
|
20
21
|
import { type AsyncJob, type AsyncJobDeliveryState, AsyncJobManager } from "../async";
|
|
21
22
|
import type { Rule } from "../capability/rule";
|
|
22
23
|
import type { ModelRegistry } from "../config/model-registry";
|
|
@@ -247,20 +248,29 @@ export interface AgentSessionConfig {
|
|
|
247
248
|
*/
|
|
248
249
|
providerSessionId?: string;
|
|
249
250
|
/**
|
|
250
|
-
*
|
|
251
|
-
*
|
|
252
|
-
* advisor's
|
|
253
|
-
*
|
|
251
|
+
* Full advisor toolset, pre-built in `createAgentSession` against a distinct,
|
|
252
|
+
* advisor-scoped `ToolSession` (its own `-advisor` session/agent id) so the
|
|
253
|
+
* advisor's tool state stays isolated from the primary. The advisor is a full
|
|
254
|
+
* agent; its config `tools` selects a subset (default read/grep/glob). Undefined
|
|
255
|
+
* when the advisor is disabled.
|
|
254
256
|
*/
|
|
255
|
-
|
|
257
|
+
advisorTools?: AgentTool[];
|
|
256
258
|
/** Preloaded watchdog prompt content for the advisor. */
|
|
257
259
|
advisorWatchdogPrompt?: string;
|
|
260
|
+
/** Preloaded YAML top-level `instructions` shared baseline, kept separate from
|
|
261
|
+
* `advisorWatchdogPrompt` so `/advisor configure` can swap it live. */
|
|
262
|
+
advisorSharedInstructions?: string;
|
|
258
263
|
/**
|
|
259
264
|
* Preloaded project context files (AGENTS.md, etc.) rendered as a system-prompt
|
|
260
265
|
* block for the advisor — the same standing instructions the primary agent
|
|
261
266
|
* receives, so the reviewer holds the agent to them.
|
|
262
267
|
*/
|
|
263
268
|
advisorContextPrompt?: string;
|
|
269
|
+
/**
|
|
270
|
+
* Advisors discovered from `WATCHDOG.yml`. Empty/undefined runs a single
|
|
271
|
+
* legacy advisor on the `advisor` role (byte-for-byte the pre-config path).
|
|
272
|
+
*/
|
|
273
|
+
advisorConfigs?: AdvisorConfig[];
|
|
264
274
|
/**
|
|
265
275
|
* Strip tool descriptions from provider-bound tool specs on side requests
|
|
266
276
|
* (handoff). Must match the session-start value used to build the system
|
|
@@ -356,6 +366,7 @@ export interface SessionStats {
|
|
|
356
366
|
tokens: {
|
|
357
367
|
input: number;
|
|
358
368
|
output: number;
|
|
369
|
+
reasoning: number;
|
|
359
370
|
cacheRead: number;
|
|
360
371
|
cacheWrite: number;
|
|
361
372
|
total: number;
|
|
@@ -373,6 +384,7 @@ export interface AdvisorStats {
|
|
|
373
384
|
tokens: {
|
|
374
385
|
input: number;
|
|
375
386
|
output: number;
|
|
387
|
+
reasoning: number;
|
|
376
388
|
cacheRead: number;
|
|
377
389
|
cacheWrite: number;
|
|
378
390
|
total: number;
|
|
@@ -383,6 +395,18 @@ export interface AdvisorStats {
|
|
|
383
395
|
assistant: number;
|
|
384
396
|
total: number;
|
|
385
397
|
};
|
|
398
|
+
/** Per-advisor breakdown; one entry per active advisor (single-advisor sessions have one). */
|
|
399
|
+
advisors: PerAdvisorStat[];
|
|
400
|
+
}
|
|
401
|
+
/** One advisor's slice of {@link AdvisorStats}, surfaced for the multi-advisor status panel. */
|
|
402
|
+
export interface PerAdvisorStat {
|
|
403
|
+
name: string;
|
|
404
|
+
model: Model;
|
|
405
|
+
contextWindow: number;
|
|
406
|
+
contextTokens: number;
|
|
407
|
+
tokens: AdvisorStats["tokens"];
|
|
408
|
+
cost: number;
|
|
409
|
+
messages: AdvisorStats["messages"];
|
|
386
410
|
}
|
|
387
411
|
export interface FreshSessionResult {
|
|
388
412
|
previousSessionId: string;
|
|
@@ -394,6 +418,7 @@ export type RestoredQueuedMessage = {
|
|
|
394
418
|
text: string;
|
|
395
419
|
images?: ImageContent[];
|
|
396
420
|
};
|
|
421
|
+
type SessionNameTrigger = "replan";
|
|
397
422
|
export declare class AgentSession {
|
|
398
423
|
#private;
|
|
399
424
|
readonly agent: Agent;
|
|
@@ -698,6 +723,7 @@ export declare class AgentSession {
|
|
|
698
723
|
prompt(text: string, options?: PromptOptions): Promise<boolean>;
|
|
699
724
|
promptCustomMessage<T = unknown>(message: Pick<CustomMessage<T>, "customType" | "content" | "display" | "details" | "attribution">, options?: Pick<PromptOptions, "streamingBehavior" | "toolChoice"> & {
|
|
700
725
|
queueChipText?: string;
|
|
726
|
+
queueOnly?: boolean;
|
|
701
727
|
}): Promise<void>;
|
|
702
728
|
/**
|
|
703
729
|
* Queue a steering message to interrupt the agent mid-run.
|
|
@@ -797,7 +823,7 @@ export declare class AgentSession {
|
|
|
797
823
|
/**
|
|
798
824
|
* Set a display name for the current session.
|
|
799
825
|
*/
|
|
800
|
-
setSessionName(name: string, source?: "auto" | "user"): Promise<boolean>;
|
|
826
|
+
setSessionName(name: string, source?: "auto" | "user", trigger?: SessionNameTrigger): Promise<boolean>;
|
|
801
827
|
/**
|
|
802
828
|
* Fork the current session, creating a new session file with the exact same state.
|
|
803
829
|
* Copies all entries and artifacts to the new session.
|
|
@@ -808,16 +834,22 @@ export declare class AgentSession {
|
|
|
808
834
|
/**
|
|
809
835
|
* Set model directly.
|
|
810
836
|
* Validates that a credential source is configured (synchronously, without
|
|
811
|
-
* refreshing OAuth or running command-backed key programs)
|
|
812
|
-
*
|
|
813
|
-
*
|
|
837
|
+
* refreshing OAuth or running command-backed key programs). The active
|
|
838
|
+
* session switches by default; when `currentContextTokens` is provided and
|
|
839
|
+
* exceeds the refreshed candidate's context window, the live switch is
|
|
840
|
+
* skipped while role persistence still runs. Returns whether the active
|
|
841
|
+
* model actually switched, computed against the refreshed metadata so
|
|
842
|
+
* dynamic providers (e.g. llama.cpp) honor their post-load contextWindow.
|
|
814
843
|
* @throws Error if no API key available for the model
|
|
815
844
|
*/
|
|
816
845
|
setModel(model: Model, role?: string, options?: {
|
|
817
846
|
selector?: string;
|
|
818
847
|
thinkingLevel?: ThinkingLevel;
|
|
819
848
|
persist?: boolean;
|
|
820
|
-
|
|
849
|
+
currentContextTokens?: number;
|
|
850
|
+
}): Promise<{
|
|
851
|
+
switched: boolean;
|
|
852
|
+
}>;
|
|
821
853
|
/**
|
|
822
854
|
* Set model temporarily (for this session only).
|
|
823
855
|
* Validates that a credential source is configured (synchronously, without
|
|
@@ -1258,6 +1290,15 @@ export declare class AgentSession {
|
|
|
1258
1290
|
* @returns true when the advisor is actively running after the call.
|
|
1259
1291
|
*/
|
|
1260
1292
|
toggleAdvisorEnabled(): boolean;
|
|
1293
|
+
/**
|
|
1294
|
+
* Replace the live advisor roster from an edited `WATCHDOG.yml` (the `/advisor
|
|
1295
|
+
* configure` save path). Swaps the configs + shared baseline, then rebuilds the
|
|
1296
|
+
* runtimes in place so the change applies without a restart. When the advisor is
|
|
1297
|
+
* disabled the new configs are simply stored for the next enable.
|
|
1298
|
+
*
|
|
1299
|
+
* @returns the number of advisors active after the rebuild.
|
|
1300
|
+
*/
|
|
1301
|
+
applyAdvisorConfigs(advisors: AdvisorConfig[], sharedInstructions: string | undefined): number;
|
|
1261
1302
|
/**
|
|
1262
1303
|
* Whether the advisor setting is enabled for this session.
|
|
1263
1304
|
*/
|
|
@@ -1269,6 +1310,13 @@ export declare class AgentSession {
|
|
|
1269
1310
|
* not merely the setting. Drives the status-line badge and `/dump advisor`.
|
|
1270
1311
|
*/
|
|
1271
1312
|
isAdvisorActive(): boolean;
|
|
1313
|
+
/**
|
|
1314
|
+
* The names of the tools available to advisors this session (the pool a
|
|
1315
|
+
* `/advisor configure` editor lists). The advisor is a full agent, so this is the
|
|
1316
|
+
* full built tool set; a tool whose optional factory returns null (e.g. lsp with
|
|
1317
|
+
* no servers) is absent.
|
|
1318
|
+
*/
|
|
1319
|
+
getAdvisorAvailableToolNames(): string[];
|
|
1272
1320
|
/**
|
|
1273
1321
|
* The live advisor `Agent`, or `undefined` when no advisor runtime is
|
|
1274
1322
|
* attached. Surfaced for diagnostics (`/dump advisor` already serializes
|
|
@@ -1,16 +1,21 @@
|
|
|
1
1
|
import type { SessionStorage, SessionStorageStat, SessionStorageWriter } from "./session-storage";
|
|
2
|
+
import { type SessionTitleUpdate } from "./session-title-slot";
|
|
2
3
|
export interface SessionStorageIndexEntry {
|
|
3
4
|
path: string;
|
|
4
5
|
size: number;
|
|
5
6
|
mtimeMs: number;
|
|
7
|
+
title?: string;
|
|
8
|
+
titleSource?: SessionTitleUpdate["source"];
|
|
9
|
+
titleUpdatedAt?: string;
|
|
6
10
|
}
|
|
7
11
|
export interface SessionStorageBackend {
|
|
8
12
|
init(): Promise<void>;
|
|
9
13
|
loadIndex(): Promise<Iterable<SessionStorageIndexEntry>>;
|
|
10
14
|
readFull(path: string): Promise<string | null>;
|
|
11
15
|
readSlices(path: string, prefixBytes: number, suffixBytes: number): Promise<[string, string]>;
|
|
12
|
-
writeFull(path: string, content: string, mtimeMs: number): Promise<void>;
|
|
16
|
+
writeFull(path: string, content: string, mtimeMs: number, title?: SessionTitleUpdate): Promise<void>;
|
|
13
17
|
append(path: string, line: string, mtimeMs: number): Promise<void>;
|
|
18
|
+
updateSessionTitle(path: string, title: SessionTitleUpdate, mtimeMs: number): Promise<void>;
|
|
14
19
|
truncate(path: string, mtimeMs: number): Promise<void>;
|
|
15
20
|
remove(paths: string[]): Promise<void>;
|
|
16
21
|
move(src: string, dst: string, mtimeMs: number): Promise<void>;
|
|
@@ -24,6 +29,7 @@ export declare class IndexedSessionStorage implements SessionStorage {
|
|
|
24
29
|
ensureDirSync(_dir: string): void;
|
|
25
30
|
existsSync(path: string): boolean;
|
|
26
31
|
writeTextSync(path: string, content: string): void;
|
|
32
|
+
updateSessionTitle(path: string, title: SessionTitleUpdate): Promise<void>;
|
|
27
33
|
statSync(path: string): SessionStorageStat;
|
|
28
34
|
listFilesSync(dir: string, pattern: string): string[];
|
|
29
35
|
exists(path: string): Promise<boolean>;
|
|
@@ -12,6 +12,32 @@ import type { OutputMeta } from "../tools/output-meta";
|
|
|
12
12
|
export declare const SKILL_PROMPT_MESSAGE_TYPE = "skill-prompt";
|
|
13
13
|
export declare const LSP_LATE_DIAGNOSTIC_MESSAGE_TYPE = "lsp-late-diagnostic";
|
|
14
14
|
export declare const BACKGROUND_TAN_DISPATCH_MESSAGE_TYPE = "background-tan-dispatch";
|
|
15
|
+
/** Custom message type for hidden interrupted-thinking continuity context. */
|
|
16
|
+
export declare const INTERRUPTED_THINKING_MESSAGE_TYPE = "interrupted-thinking";
|
|
17
|
+
/** Metadata persisted with a hidden interrupted-thinking continuity message. */
|
|
18
|
+
export interface InterruptedThinkingDetails {
|
|
19
|
+
interruptedAt: number;
|
|
20
|
+
provider: AssistantMessage["provider"];
|
|
21
|
+
model: string;
|
|
22
|
+
blockCount: number;
|
|
23
|
+
}
|
|
24
|
+
/** Pure helper result for persisting interrupted thinking outside the assistant turn. */
|
|
25
|
+
export interface DemotedInterruptedThinking {
|
|
26
|
+
reasoning: string;
|
|
27
|
+
strippedContent: AssistantMessage["content"];
|
|
28
|
+
blockCount: number;
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Demote a trailing run of *incomplete* interrupted-thinking from an assistant
|
|
32
|
+
* message — reasoning that was still streaming when the user aborted.
|
|
33
|
+
*
|
|
34
|
+
* A block joins the run only when it is a non-empty `thinking` block with no
|
|
35
|
+
* `thinkingSignature`. A signed/complete thinking block (Anthropic signature,
|
|
36
|
+
* OpenAI reasoning item id) is safely replayable, so it ends the run and stays
|
|
37
|
+
* in place — as do `redactedThinking` encrypted blobs, text, tool calls,
|
|
38
|
+
* empty-thinking blocks, and trailing empty text placeholders.
|
|
39
|
+
*/
|
|
40
|
+
export declare function demoteInterruptedThinking(message: Pick<AssistantMessage, "content">): DemotedInterruptedThinking | undefined;
|
|
15
41
|
/** Details persisted on a `/tan` background-dispatch breadcrumb. */
|
|
16
42
|
export interface BackgroundTanDispatchDetails {
|
|
17
43
|
jobId: string;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -1,13 +1,26 @@
|
|
|
1
1
|
import type { AgentMessage } from "@oh-my-pi/pi-agent-core";
|
|
2
2
|
import type { ImageContent, MessageAttribution, ServiceTier, TextContent } from "@oh-my-pi/pi-ai";
|
|
3
3
|
export declare const CURRENT_SESSION_VERSION = 3;
|
|
4
|
+
export declare const SESSION_TITLE_SLOT_BYTES = 256;
|
|
5
|
+
export declare const SESSION_TITLE_SLOT_ENTRY_TYPE = "title";
|
|
6
|
+
export declare const TITLE_CHANGE_ENTRY_TYPE = "title_change";
|
|
7
|
+
export type SessionTitleSource = "auto" | "user";
|
|
8
|
+
/** Fixed-width first-line slot carrying the mutable current session title. */
|
|
9
|
+
export interface SessionTitleSlotEntry {
|
|
10
|
+
type: typeof SESSION_TITLE_SLOT_ENTRY_TYPE;
|
|
11
|
+
v: 1;
|
|
12
|
+
title: string;
|
|
13
|
+
source?: SessionTitleSource;
|
|
14
|
+
updatedAt: string;
|
|
15
|
+
pad: string;
|
|
16
|
+
}
|
|
4
17
|
export declare const EPHEMERAL_MODEL_CHANGE_ROLE = "fallback";
|
|
5
18
|
export interface SessionHeader {
|
|
6
19
|
type: "session";
|
|
7
20
|
version?: number;
|
|
8
21
|
id: string;
|
|
9
22
|
title?: string;
|
|
10
|
-
titleSource?:
|
|
23
|
+
titleSource?: SessionTitleSource;
|
|
11
24
|
timestamp: string;
|
|
12
25
|
cwd: string;
|
|
13
26
|
parentSession?: string;
|
|
@@ -91,6 +104,19 @@ export interface LabelEntry extends SessionEntryBase {
|
|
|
91
104
|
targetId: string;
|
|
92
105
|
label: string | undefined;
|
|
93
106
|
}
|
|
107
|
+
/** Append-only audit entry recording a session title change. */
|
|
108
|
+
export interface TitleChangeEntry extends SessionEntryBase {
|
|
109
|
+
type: typeof TITLE_CHANGE_ENTRY_TYPE;
|
|
110
|
+
title: string;
|
|
111
|
+
previousTitle?: string;
|
|
112
|
+
source: SessionTitleSource;
|
|
113
|
+
trigger?: string;
|
|
114
|
+
}
|
|
115
|
+
declare module "@oh-my-pi/pi-agent-core/compaction/entries" {
|
|
116
|
+
interface CustomCompactionSessionEntries {
|
|
117
|
+
titleChange: TitleChangeEntry;
|
|
118
|
+
}
|
|
119
|
+
}
|
|
94
120
|
/** TTSR injection entry - tracks which time-traveling rules have been injected this session. */
|
|
95
121
|
export interface TtsrInjectionEntry extends SessionEntryBase {
|
|
96
122
|
type: "ttsr_injection";
|
|
@@ -149,9 +175,11 @@ export interface CustomMessageEntry<T = unknown> extends SessionEntryBase {
|
|
|
149
175
|
attribution?: MessageAttribution;
|
|
150
176
|
}
|
|
151
177
|
/** Session entry - has id/parentId for tree structure (returned by "read" methods in SessionManager) */
|
|
152
|
-
export type SessionEntry = SessionMessageEntry | ThinkingLevelChangeEntry | ModelChangeEntry | ServiceTierChangeEntry | CompactionEntry | BranchSummaryEntry | CustomEntry | CustomMessageEntry | LabelEntry | TtsrInjectionEntry | MCPToolSelectionEntry | SessionInitEntry | ModeChangeEntry;
|
|
153
|
-
/** Raw file entry
|
|
178
|
+
export type SessionEntry = SessionMessageEntry | ThinkingLevelChangeEntry | ModelChangeEntry | ServiceTierChangeEntry | CompactionEntry | BranchSummaryEntry | CustomEntry | CustomMessageEntry | LabelEntry | TitleChangeEntry | TtsrInjectionEntry | MCPToolSelectionEntry | SessionInitEntry | ModeChangeEntry;
|
|
179
|
+
/** Raw logical file entry after loaders strip any fixed-width title slot. */
|
|
154
180
|
export type FileEntry = SessionHeader | SessionEntry;
|
|
181
|
+
/** Physical JSONL entry before slot-aware loaders fold the title slot. */
|
|
182
|
+
export type RawFileEntry = SessionTitleSlotEntry | FileEntry;
|
|
155
183
|
/** Tree node for getTree() - defensive copy of session structure */
|
|
156
184
|
export interface SessionTreeNode {
|
|
157
185
|
entry: SessionEntry;
|
|
@@ -18,6 +18,12 @@ export interface HistoryFormatOptions {
|
|
|
18
18
|
* still collapse to a one-liner.
|
|
19
19
|
*/
|
|
20
20
|
expandPrimaryContext?: boolean;
|
|
21
|
+
/**
|
|
22
|
+
* Append the full unified diff (from a tool result's `details.diff`) below
|
|
23
|
+
* edit/apply_patch tool lines, instead of just the path. The advisor sets
|
|
24
|
+
* this so it sees what changed without re-reading the file.
|
|
25
|
+
*/
|
|
26
|
+
expandEditDiffs?: boolean;
|
|
21
27
|
}
|
|
22
28
|
/**
|
|
23
29
|
* Hidden custom messages that inject the primary agent's operative *constraints*
|
|
@@ -1,7 +1,15 @@
|
|
|
1
1
|
import type { AgentMessage } from "@oh-my-pi/pi-agent-core";
|
|
2
2
|
import { BlobStore } from "./blob-store";
|
|
3
|
-
import type
|
|
3
|
+
import { type FileEntry, type SessionTitleSlotEntry } from "./session-entries";
|
|
4
4
|
import { type SessionStorage } from "./session-storage";
|
|
5
|
+
import { type SessionTitleUpdate } from "./session-title-slot";
|
|
6
|
+
/** Parse session JSONL while stripping and folding the optional fixed title slot. */
|
|
7
|
+
export declare function parseSessionContent(content: string): {
|
|
8
|
+
entries: FileEntry[];
|
|
9
|
+
titleSlot: SessionTitleUpdate | undefined;
|
|
10
|
+
};
|
|
11
|
+
/** Read only the fixed-size head window to detect a physical title slot. */
|
|
12
|
+
export declare function readTitleSlotFromFile(filePath: string, storage?: SessionStorage): Promise<SessionTitleSlotEntry | undefined>;
|
|
5
13
|
/** Exported for compaction.test.ts */
|
|
6
14
|
export declare function parseSessionEntries(content: string): FileEntry[];
|
|
7
15
|
/** Exported for testing */
|
|
@@ -3,7 +3,7 @@ import { ArtifactManager } from "./artifacts";
|
|
|
3
3
|
import { type BlobPutOptions, type BlobPutResult } from "./blob-store";
|
|
4
4
|
import { type BashExecutionMessage, type CustomMessage, type FileMentionMessage, type HookMessage, type PythonExecutionMessage } from "./messages";
|
|
5
5
|
import { type BuildSessionContextOptions, type SessionContext } from "./session-context";
|
|
6
|
-
import { type NewSessionOptions, type SessionEntry, type SessionHeader, type SessionTreeNode, type UsageStatistics } from "./session-entries";
|
|
6
|
+
import { type NewSessionOptions, type SessionEntry, type SessionHeader, type SessionTitleSource, type SessionTreeNode, type UsageStatistics } from "./session-entries";
|
|
7
7
|
import { type SessionInfo } from "./session-listing";
|
|
8
8
|
import { type SessionStorage } from "./session-storage";
|
|
9
9
|
export type ReadonlySessionManager = Pick<SessionManager, "getCwd" | "getSessionDir" | "getSessionId" | "getSessionFile" | "getSessionName" | "getArtifactsDir" | "getArtifactManager" | "allocateArtifactPath" | "saveArtifact" | "getArtifactPath" | "getLeafId" | "getLeafEntry" | "getEntry" | "getLabel" | "getBranch" | "getHeader" | "getEntries" | "getTree" | "getUsageStatistics" | "putBlob" | "putBlobSync">;
|
|
@@ -12,8 +12,10 @@ interface SessionManagerStateSnapshot {
|
|
|
12
12
|
sessionDir: string;
|
|
13
13
|
sessionId: string;
|
|
14
14
|
sessionName: string | undefined;
|
|
15
|
-
titleSource:
|
|
15
|
+
titleSource: SessionTitleSource | undefined;
|
|
16
16
|
sessionFile: string | undefined;
|
|
17
|
+
titleUpdatedAt: string;
|
|
18
|
+
hasTitleSlot: boolean;
|
|
17
19
|
onDisk: boolean;
|
|
18
20
|
needsRewrite: boolean;
|
|
19
21
|
header: SessionHeader;
|
|
@@ -109,7 +111,7 @@ export declare class SessionManager {
|
|
|
109
111
|
saveDraft(text: string): Promise<void>;
|
|
110
112
|
consumeDraft(): Promise<string | null>;
|
|
111
113
|
/** The source that set the session name: "user" (manual/RPC) or "auto" (generated title). */
|
|
112
|
-
get titleSource():
|
|
114
|
+
get titleSource(): SessionTitleSource | undefined;
|
|
113
115
|
getSessionName(): string | undefined;
|
|
114
116
|
onSessionNameChanged(cb: () => void): () => void;
|
|
115
117
|
/**
|
|
@@ -117,7 +119,7 @@ export declare class SessionManager {
|
|
|
117
119
|
* @param source "user" for explicit renames; "auto" for generated titles.
|
|
118
120
|
* Auto titles are ignored once the user has set a name.
|
|
119
121
|
*/
|
|
120
|
-
setSessionName(name: string, source?:
|
|
122
|
+
setSessionName(name: string, source?: SessionTitleSource, trigger?: string): Promise<boolean>;
|
|
121
123
|
/**
|
|
122
124
|
* Append a foreign (host-authored) entry verbatim, preserving its
|
|
123
125
|
* `id`/`parentId`. Used by collab guests to mirror the host session.
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { type SessionTitleUpdate } from "./session-title-slot";
|
|
1
2
|
export interface SessionStorageStat {
|
|
2
3
|
size: number;
|
|
3
4
|
mtimeMs: number;
|
|
@@ -22,6 +23,14 @@ export interface SessionStorage {
|
|
|
22
23
|
ensureDirSync(dir: string): void;
|
|
23
24
|
existsSync(path: string): boolean;
|
|
24
25
|
writeTextSync(path: string, content: string): void;
|
|
26
|
+
/**
|
|
27
|
+
* Update the current session title through the storage backend.
|
|
28
|
+
*
|
|
29
|
+
* File-like backends rewrite the fixed-width JSONL title slot; indexed
|
|
30
|
+
* backends can store the semantic title fields and synthesize the slot when
|
|
31
|
+
* reading.
|
|
32
|
+
*/
|
|
33
|
+
updateSessionTitle(path: string, update: SessionTitleUpdate): Promise<void>;
|
|
25
34
|
statSync(path: string): SessionStorageStat;
|
|
26
35
|
listFilesSync(dir: string, pattern: string): string[];
|
|
27
36
|
exists(path: string): Promise<boolean>;
|
|
@@ -43,6 +52,7 @@ export declare class FileSessionStorage implements SessionStorage {
|
|
|
43
52
|
ensureDirSync(dir: string): void;
|
|
44
53
|
existsSync(path: string): boolean;
|
|
45
54
|
writeTextSync(fpath: string, content: string): void;
|
|
55
|
+
updateSessionTitle(fpath: string, update: SessionTitleUpdate): Promise<void>;
|
|
46
56
|
statSync(path: string): SessionStorageStat;
|
|
47
57
|
listFilesSync(dir: string, pattern: string): string[];
|
|
48
58
|
exists(path: string): Promise<boolean>;
|
|
@@ -67,6 +77,7 @@ export declare class MemorySessionStorage implements SessionStorage {
|
|
|
67
77
|
ensureDirSync(_dir: string): void;
|
|
68
78
|
existsSync(path: string): boolean;
|
|
69
79
|
writeTextSync(path: string, content: string): void;
|
|
80
|
+
updateSessionTitle(path: string, update: SessionTitleUpdate): Promise<void>;
|
|
70
81
|
/**
|
|
71
82
|
* Internal O(1) append used by {@link MemorySessionStorageWriter}. Lazily
|
|
72
83
|
* creates the entry. External callers should go through `openWriter()`
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { type SessionTitleSlotEntry, type SessionTitleSource } from "./session-entries";
|
|
2
|
+
/** Semantic title update persisted by session storage backends. */
|
|
3
|
+
export interface SessionTitleUpdate {
|
|
4
|
+
title?: string;
|
|
5
|
+
source?: SessionTitleSource;
|
|
6
|
+
updatedAt: string;
|
|
7
|
+
}
|
|
8
|
+
/** Parse a physical title slot JSONL line. Returns undefined for legacy headers. */
|
|
9
|
+
export declare function parseTitleSlotLine(line: string): SessionTitleSlotEntry | undefined;
|
|
10
|
+
/** Parse the fixed-width title slot from a physical session body. */
|
|
11
|
+
export declare function parseTitleSlotFromContent(content: string): SessionTitleSlotEntry | undefined;
|
|
12
|
+
/** Convert a parsed title slot to the semantic storage update shape. */
|
|
13
|
+
export declare function titleUpdateFromSlot(slot: SessionTitleSlotEntry | undefined): SessionTitleUpdate | undefined;
|
|
14
|
+
/** Serialize the fixed-width first-line title slot, exactly 256 UTF-8 bytes including newline. */
|
|
15
|
+
export declare function serializeTitleSlot(options: SessionTitleUpdate): string;
|
|
16
|
+
/** Replace the physical fixed-width title slot in a full session body. */
|
|
17
|
+
export declare function overlayTitleSlotContent(content: string, update: SessionTitleUpdate): string;
|
|
18
|
+
/** Replace the physical fixed-width title slot in a prefix byte window. */
|
|
19
|
+
export declare function overlayTitleSlotPrefix(prefix: string, prefixBytes: number, update: SessionTitleUpdate): string;
|
|
@@ -14,6 +14,15 @@ export interface SSHHostInfo {
|
|
|
14
14
|
version: number;
|
|
15
15
|
os: SSHHostOs;
|
|
16
16
|
shell: SSHHostShell;
|
|
17
|
+
/**
|
|
18
|
+
* Shell name OMP verified can execute the POSIX transfer snippets
|
|
19
|
+
* (`head`/`cat`/`mv`/`test`/`ls`) `ssh://` uses. Probed by running
|
|
20
|
+
* `sh -lc` / `bash -lc` / `zsh -lc` against the remote and keeping the
|
|
21
|
+
* first one that round-trips a known marker. Independent of `shell`
|
|
22
|
+
* (the self-reported login shell), which may be noisy, exotic, or simply
|
|
23
|
+
* mis-classified — only `transferShell` gates ssh:// transfers.
|
|
24
|
+
*/
|
|
25
|
+
transferShell?: "sh" | "bash" | "zsh";
|
|
17
26
|
compatShell?: "bash" | "sh";
|
|
18
27
|
compatEnabled: boolean;
|
|
19
28
|
}
|
|
@@ -22,6 +31,44 @@ interface SSHArgsOptions {
|
|
|
22
31
|
/** When true, omit `-n` so the remote command can read from our piped stdin. */
|
|
23
32
|
allowStdin?: boolean;
|
|
24
33
|
}
|
|
34
|
+
/**
|
|
35
|
+
* Parse a raw cache-file value (or any unknown) into a normalized
|
|
36
|
+
* {@link SSHHostInfo}, dropping fields that don't pass the per-field guards.
|
|
37
|
+
* Exported so cache-layer round-tripping (incl. the new `transferShell`
|
|
38
|
+
* field, #3719) is testable without touching disk.
|
|
39
|
+
*/
|
|
40
|
+
export declare function parseHostInfo(value: unknown): SSHHostInfo | null;
|
|
41
|
+
/**
|
|
42
|
+
* Frame marker emitted by the remote OS/shell probe. The probe wraps its
|
|
43
|
+
* payload in this prefix so the parser can ignore startup-file noise (banners,
|
|
44
|
+
* `motd`, login messages, `Last login: …`) instead of trusting only the first
|
|
45
|
+
* line of stdout. See #3719.
|
|
46
|
+
*/
|
|
47
|
+
export declare const HOST_PROBE_MARKER = "PI_HOST_PROBE=";
|
|
48
|
+
/** Marker for the transfer-shell capability probe. */
|
|
49
|
+
export declare const TRANSFER_PROBE_MARKER = "PI_TRANSFER_OK|";
|
|
50
|
+
/**
|
|
51
|
+
* Find the first line of `stdout`/`stderr` that begins with `marker` and
|
|
52
|
+
* return everything after it. Used by the SSH host probe so noisy login
|
|
53
|
+
* dotfiles can't corrupt OS/shell classification by emitting text on the
|
|
54
|
+
* first line of `ssh` output.
|
|
55
|
+
*
|
|
56
|
+
* Returns `null` when no marker line is found in either stream.
|
|
57
|
+
*/
|
|
58
|
+
export declare function extractProbePayload(stdout: string, stderr: string, marker?: string): string | null;
|
|
59
|
+
/**
|
|
60
|
+
* Find `marker` anywhere in `stdout` or `stderr` and return everything that
|
|
61
|
+
* follows it, scanning stdout first. Returns `null` when the marker is in
|
|
62
|
+
* neither stream.
|
|
63
|
+
*
|
|
64
|
+
* Used by the transfer-shell capability probe. Some remotes have broken
|
|
65
|
+
* login dotfiles that swap fd 1/2, so the marker can land on stderr even
|
|
66
|
+
* though the probe ran the printf successfully (matches the host-info
|
|
67
|
+
* probe's stderr fallback). See #3719.
|
|
68
|
+
*/
|
|
69
|
+
export declare function findProbeMarker(stdout: string, stderr: string, marker: string): string | null;
|
|
70
|
+
/** Classify a POSIX-ish `uname -s` payload from the transfer-shell probe. */
|
|
71
|
+
export declare function osFromUname(value: string): SSHHostOs | undefined;
|
|
25
72
|
export declare function getHostInfo(hostName: string): Promise<SSHHostInfo | undefined>;
|
|
26
73
|
export declare function getHostInfoForHost(host: SSHConnectionTarget): Promise<SSHHostInfo | undefined>;
|
|
27
74
|
/**
|
|
@@ -6,3 +6,19 @@ export declare function buildSshTarget(username: string | undefined, host: strin
|
|
|
6
6
|
* `ssh://` file-transfer helpers.
|
|
7
7
|
*/
|
|
8
8
|
export declare function quotePosixPath(value: string): string;
|
|
9
|
+
/**
|
|
10
|
+
* Wrap a POSIX command in `<shell> -c '<command>'` so it runs under the
|
|
11
|
+
* named shell rather than whatever `$SHELL` happens to be on the remote.
|
|
12
|
+
*
|
|
13
|
+
* Used by the `ssh://` transfer helpers and the Windows compat dispatch:
|
|
14
|
+
* OpenSSH passes our snippets to `<login-shell> -c`, so a remote whose
|
|
15
|
+
* login shell is fish/csh/tcsh (or cmd/powershell on Windows compat)
|
|
16
|
+
* can't parse `if [ … ]; then …`. Wrapping forces parsing under the
|
|
17
|
+
* shell OMP actually verified can run the snippet.
|
|
18
|
+
*
|
|
19
|
+
* `-c` (not `-lc`): the transfer snippets only call absolute POSIX
|
|
20
|
+
* builtins (`head`/`cat`/`mv`/`test`/`ls`/`mkdir`/`rm`/`dirname`) and
|
|
21
|
+
* don't need login-profile setup. Capability *probing* still uses
|
|
22
|
+
* `-lc` to mirror the user's real environment.
|
|
23
|
+
*/
|
|
24
|
+
export declare function wrapInPosixShell(shell: "sh" | "bash" | "zsh", command: string): string;
|
|
@@ -23,7 +23,8 @@ import type { AuthStorage } from "../session/auth-storage";
|
|
|
23
23
|
import type { ContextFileEntry } from "../tools";
|
|
24
24
|
import type { EventBus } from "../utils/event-bus";
|
|
25
25
|
import type { WorkspaceTree } from "../workspace-tree";
|
|
26
|
-
import { type AgentDefinition, type AgentProgress, type ReviewFinding, type SingleResult } from "./types";
|
|
26
|
+
import { type AgentDefinition, type AgentProgress, type ReviewFinding, type SingleResult, type YieldItem } from "./types";
|
|
27
|
+
export type { YieldItem } from "./types";
|
|
27
28
|
/**
|
|
28
29
|
* Soft per-agent request budgets (assistant requests per run). When a subagent
|
|
29
30
|
* crosses its budget it receives ONE steering notice asking it to wrap up; at
|
|
@@ -164,20 +165,6 @@ export interface ExecutorOptions {
|
|
|
164
165
|
*/
|
|
165
166
|
keepAlive?: boolean;
|
|
166
167
|
}
|
|
167
|
-
export interface YieldItem {
|
|
168
|
-
data?: unknown;
|
|
169
|
-
status?: "success" | "aborted";
|
|
170
|
-
error?: string;
|
|
171
|
-
/**
|
|
172
|
-
* Set by the in-tool yield validator when it exhausted its retry budget
|
|
173
|
-
* (MAX_SCHEMA_RETRIES) and accepted a schema-invalid payload anyway.
|
|
174
|
-
* `finalizeSubprocessOutput` honors this by serializing the payload and
|
|
175
|
-
* surfacing a stderr warning, instead of re-emitting `schema_violation`
|
|
176
|
-
* — which would silently swap the subagent's "accepted" view for a
|
|
177
|
-
* different, opaque error blob in the parent's view of the result.
|
|
178
|
-
*/
|
|
179
|
-
schemaOverridden?: boolean;
|
|
180
|
-
}
|
|
181
168
|
interface FinalizeSubprocessOutputArgs {
|
|
182
169
|
rawOutput: string;
|
|
183
170
|
exitCode: number;
|
|
@@ -187,6 +174,7 @@ interface FinalizeSubprocessOutputArgs {
|
|
|
187
174
|
yieldItems?: YieldItem[];
|
|
188
175
|
reportFindings?: ReviewFinding[];
|
|
189
176
|
outputSchema: unknown;
|
|
177
|
+
lastAssistantText?: string;
|
|
190
178
|
}
|
|
191
179
|
interface FinalizeSubprocessOutputResult {
|
|
192
180
|
rawOutput: string;
|
|
@@ -217,4 +205,3 @@ export declare function finalizeSubagentLifecycle(args: {
|
|
|
217
205
|
* Run a single agent in-process.
|
|
218
206
|
*/
|
|
219
207
|
export declare function runSubprocess(options: ExecutorOptions): Promise<SingleResult>;
|
|
220
|
-
export {};
|
|
@@ -31,9 +31,4 @@ export declare function renderResult(result: {
|
|
|
31
31
|
details?: TaskToolDetails;
|
|
32
32
|
isError?: boolean;
|
|
33
33
|
}, options: TaskRenderOptions, theme: Theme, args?: TaskParams): Component;
|
|
34
|
-
export declare const taskToolRenderer: {
|
|
35
|
-
renderCall: typeof renderCall;
|
|
36
|
-
renderResult: typeof renderResult;
|
|
37
|
-
mergeCallAndResult: boolean;
|
|
38
|
-
};
|
|
39
34
|
export {};
|