@oh-my-pi/pi-coding-agent 15.7.3 → 15.7.6
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 +69 -1
- package/dist/types/config/settings-schema.d.ts +12 -22
- package/dist/types/eval/__tests__/heartbeat.test.d.ts +1 -0
- package/dist/types/eval/heartbeat.d.ts +45 -0
- package/dist/types/extensibility/custom-tools/types.d.ts +2 -2
- package/dist/types/extensibility/extensions/loader.d.ts +2 -2
- package/dist/types/extensibility/extensions/runner.d.ts +2 -1
- package/dist/types/extensibility/extensions/types.d.ts +24 -5
- package/dist/types/extensibility/shared-events.d.ts +2 -2
- package/dist/types/internal-urls/local-protocol.d.ts +19 -9
- package/dist/types/internal-urls/types.d.ts +14 -0
- package/dist/types/lsp/client.d.ts +3 -0
- package/dist/types/lsp/diagnostics-ledger.d.ts +10 -0
- package/dist/types/lsp/index.d.ts +2 -0
- package/dist/types/lsp/utils.d.ts +4 -0
- package/dist/types/mcp/manager.d.ts +14 -5
- package/dist/types/modes/acp/acp-agent.d.ts +1 -1
- package/dist/types/modes/components/assistant-message.d.ts +3 -1
- package/dist/types/modes/components/custom-editor.d.ts +0 -1
- package/dist/types/modes/components/hook-selector.d.ts +7 -1
- package/dist/types/modes/controllers/command-controller.d.ts +2 -3
- package/dist/types/modes/controllers/extension-ui-controller.d.ts +2 -2
- package/dist/types/modes/interactive-mode.d.ts +2 -2
- package/dist/types/modes/rpc/rpc-mode.d.ts +1 -1
- package/dist/types/modes/theme/theme.d.ts +1 -1
- package/dist/types/modes/types.d.ts +2 -2
- package/dist/types/session/agent-session.d.ts +10 -7
- package/dist/types/session/shake-types.d.ts +3 -3
- package/dist/types/task/repair-args.d.ts +52 -0
- package/dist/types/tiny/models.d.ts +0 -14
- package/dist/types/tiny/title-client.d.ts +28 -2
- package/dist/types/tiny/title-protocol.d.ts +8 -9
- package/dist/types/tools/ask.d.ts +8 -6
- package/dist/types/tools/eval-backends.d.ts +12 -0
- package/dist/types/tools/eval-render.d.ts +52 -0
- package/dist/types/tools/eval.d.ts +2 -35
- package/dist/types/tools/find.d.ts +1 -1
- package/dist/types/tools/index.d.ts +4 -11
- package/dist/types/tools/path-utils.d.ts +7 -0
- package/dist/types/tui/output-block.d.ts +11 -10
- package/examples/extensions/README.md +1 -0
- package/examples/extensions/thinking-note.ts +13 -0
- package/package.json +9 -9
- package/scripts/build-binary.ts +0 -1
- package/src/cli.ts +59 -0
- package/src/config/model-registry.ts +33 -4
- package/src/config/settings-schema.ts +13 -24
- package/src/config/settings.ts +10 -0
- package/src/discovery/claude.ts +41 -22
- package/src/edit/index.ts +23 -3
- package/src/eval/__tests__/agent-bridge.test.ts +90 -0
- package/src/eval/__tests__/heartbeat.test.ts +84 -0
- package/src/eval/__tests__/llm-bridge.test.ts +30 -0
- package/src/eval/agent-bridge.ts +44 -38
- package/src/eval/heartbeat.ts +74 -0
- package/src/eval/js/executor.ts +13 -9
- package/src/eval/llm-bridge.ts +20 -14
- package/src/eval/py/executor.ts +14 -18
- package/src/exec/bash-executor.ts +31 -5
- package/src/extensibility/custom-tools/types.ts +2 -2
- package/src/extensibility/extensions/loader.ts +16 -18
- package/src/extensibility/extensions/runner.ts +22 -17
- package/src/extensibility/extensions/types.ts +39 -5
- package/src/extensibility/shared-events.ts +2 -2
- package/src/internal-urls/docs-index.generated.ts +5 -5
- package/src/internal-urls/local-protocol.ts +23 -11
- package/src/internal-urls/types.ts +15 -0
- package/src/lsp/client.ts +28 -5
- package/src/lsp/diagnostics-ledger.ts +51 -0
- package/src/lsp/index.ts +9 -22
- package/src/lsp/utils.ts +21 -0
- package/src/mcp/manager.ts +87 -4
- package/src/modes/acp/acp-agent.ts +8 -4
- package/src/modes/components/assistant-message.ts +28 -1
- package/src/modes/components/custom-editor.ts +9 -7
- package/src/modes/components/hook-selector.ts +159 -32
- package/src/modes/components/tool-execution.ts +20 -4
- package/src/modes/controllers/command-controller.ts +7 -39
- package/src/modes/controllers/event-controller.ts +38 -28
- package/src/modes/controllers/extension-ui-controller.ts +3 -2
- package/src/modes/controllers/input-controller.ts +0 -15
- package/src/modes/controllers/mcp-command-controller.ts +1 -1
- package/src/modes/interactive-mode.ts +2 -1
- package/src/modes/rpc/rpc-mode.ts +17 -6
- package/src/modes/theme/theme-schema.json +30 -0
- package/src/modes/theme/theme.ts +39 -2
- package/src/modes/types.ts +2 -1
- package/src/modes/utils/ui-helpers.ts +5 -2
- package/src/prompts/system/project-prompt.md +3 -2
- package/src/prompts/system/subagent-system-prompt.md +12 -8
- package/src/prompts/system/system-prompt.md +8 -6
- package/src/prompts/tools/ask.md +2 -1
- package/src/prompts/tools/eval.md +1 -1
- package/src/session/agent-session.ts +75 -103
- package/src/session/shake-types.ts +4 -5
- package/src/slash-commands/builtin-registry.ts +2 -4
- package/src/task/executor.ts +14 -4
- package/src/task/index.ts +3 -2
- package/src/task/repair-args.ts +117 -0
- package/src/tiny/models.ts +0 -28
- package/src/tiny/title-client.ts +133 -43
- package/src/tiny/title-protocol.ts +11 -16
- package/src/tiny/worker.ts +6 -61
- package/src/tools/ask.ts +74 -32
- package/src/tools/ast-edit.ts +3 -0
- package/src/tools/ast-grep.ts +3 -0
- package/src/tools/eval-backends.ts +38 -0
- package/src/tools/eval-render.ts +750 -0
- package/src/tools/eval.ts +27 -754
- package/src/tools/find.ts +20 -6
- package/src/tools/gh.ts +1 -0
- package/src/tools/index.ts +7 -37
- package/src/tools/path-utils.ts +13 -2
- package/src/tools/read.ts +1 -0
- package/src/tools/renderers.ts +1 -1
- package/src/tools/search.ts +12 -1
- package/src/tools/write.ts +9 -1
- package/src/tui/output-block.ts +42 -79
- package/src/utils/git.ts +9 -3
|
@@ -17,7 +17,7 @@ export declare class Theme {
|
|
|
17
17
|
#private;
|
|
18
18
|
private readonly mode;
|
|
19
19
|
private readonly symbolPreset;
|
|
20
|
-
constructor(fgColors: Record<ThemeColor, string | number>, bgColors: Record<ThemeBg, string | number>, mode: ColorMode, symbolPreset: SymbolPreset, symbolOverrides: Partial<Record<SymbolKey, string>>);
|
|
20
|
+
constructor(fgColors: Record<ThemeColor, string | number>, bgColors: Record<ThemeBg, string | number>, mode: ColorMode, symbolPreset: SymbolPreset, symbolOverrides: Partial<Record<SymbolKey, string>>, spinnerFramesOverrides?: Partial<Record<SpinnerType, string[]>>);
|
|
21
21
|
fg(color: ThemeColor, text: string): string;
|
|
22
22
|
bg(color: ThemeBg, text: string): string;
|
|
23
23
|
bold(text: string): string;
|
|
@@ -4,7 +4,7 @@ import type { AssistantMessage, ImageContent, Message, UsageReport } from "@oh-m
|
|
|
4
4
|
import type { Component, Container, EditorTheme, Loader, Spacer, Text, TUI } from "@oh-my-pi/pi-tui";
|
|
5
5
|
import type { KeybindingsManager } from "../config/keybindings";
|
|
6
6
|
import type { Settings } from "../config/settings";
|
|
7
|
-
import type { ExtensionUIContext, ExtensionUIDialogOptions, ExtensionWidgetContent, ExtensionWidgetOptions } from "../extensibility/extensions";
|
|
7
|
+
import type { ExtensionUIContext, ExtensionUIDialogOptions, ExtensionUISelectItem, ExtensionWidgetContent, ExtensionWidgetOptions } from "../extensibility/extensions";
|
|
8
8
|
import type { CompactOptions } from "../extensibility/extensions/types";
|
|
9
9
|
import type { MCPManager } from "../mcp";
|
|
10
10
|
import type { PlanApprovalDetails } from "../plan-mode/approved-plan";
|
|
@@ -264,7 +264,7 @@ export interface InteractiveModeContext {
|
|
|
264
264
|
emitCustomToolSessionEvent(reason: "start" | "switch" | "branch" | "tree" | "shutdown", previousSessionFile?: string): Promise<void>;
|
|
265
265
|
setHookWidget(key: string, content: ExtensionWidgetContent, options?: ExtensionWidgetOptions): void;
|
|
266
266
|
setHookStatus(key: string, text: string | undefined): void;
|
|
267
|
-
showHookSelector(title: string, options:
|
|
267
|
+
showHookSelector(title: string, options: ExtensionUISelectItem[], dialogOptions?: ExtensionUIDialogOptions): Promise<string | undefined>;
|
|
268
268
|
hideHookSelector(): void;
|
|
269
269
|
showHookInput(title: string, placeholder?: string): Promise<string | undefined>;
|
|
270
270
|
hideHookInput(): void;
|
|
@@ -54,10 +54,10 @@ import { YieldQueue } from "./yield-queue";
|
|
|
54
54
|
export type AgentSessionEvent = AgentEvent | {
|
|
55
55
|
type: "auto_compaction_start";
|
|
56
56
|
reason: "threshold" | "overflow" | "idle" | "incomplete";
|
|
57
|
-
action: "context-full" | "handoff" | "shake"
|
|
57
|
+
action: "context-full" | "handoff" | "shake";
|
|
58
58
|
} | {
|
|
59
59
|
type: "auto_compaction_end";
|
|
60
|
-
action: "context-full" | "handoff" | "shake"
|
|
60
|
+
action: "context-full" | "handoff" | "shake";
|
|
61
61
|
result: CompactionResult | undefined;
|
|
62
62
|
aborted: boolean;
|
|
63
63
|
willRetry: boolean;
|
|
@@ -438,8 +438,15 @@ export declare class AgentSession {
|
|
|
438
438
|
/**
|
|
439
439
|
* Replace MCP tools in the registry and recompute the visible MCP tool set immediately.
|
|
440
440
|
* This allows /mcp add/remove/reauth to take effect without restarting the session.
|
|
441
|
+
*
|
|
442
|
+
* @param mcpTools The new MCP tools to register.
|
|
443
|
+
* @param options.activateAll When true, force-activates every newly registered MCP tool
|
|
444
|
+
* regardless of prior selection state. Used when an ACP client provisions MCP servers
|
|
445
|
+
* for a session where MCP discovery is disabled.
|
|
441
446
|
*/
|
|
442
|
-
refreshMCPTools(mcpTools: CustomTool[]
|
|
447
|
+
refreshMCPTools(mcpTools: CustomTool[], options?: {
|
|
448
|
+
activateAll?: boolean;
|
|
449
|
+
}): Promise<void>;
|
|
443
450
|
/**
|
|
444
451
|
* Replace RPC host-owned tools and refresh the active tool set before the next model call.
|
|
445
452
|
*/
|
|
@@ -737,10 +744,6 @@ export declare class AgentSession {
|
|
|
737
744
|
* - `images` delegates to {@link dropImages}.
|
|
738
745
|
* - `elide` replaces whole tool-call results and large fenced/XML blocks
|
|
739
746
|
* with short placeholders that embed an `artifact://` recovery link.
|
|
740
|
-
* - `summary` extractively compresses the same regions with the configured
|
|
741
|
-
* local on-device model (`providers.shakeSummaryModel`), falling back to
|
|
742
|
-
* the elide placeholder per region (or wholesale when the local model is
|
|
743
|
-
* unavailable). Never calls a remote/cloud LLM.
|
|
744
747
|
*
|
|
745
748
|
* Mutates the branch in place, persists via `rewriteEntries`, replays the
|
|
746
749
|
* rebuilt context through the agent, and tears down provider sessions that
|
|
@@ -5,13 +5,13 @@
|
|
|
5
5
|
* an import cycle through the slash-command registry).
|
|
6
6
|
*/
|
|
7
7
|
/** Mode selector for `AgentSession.shake`. */
|
|
8
|
-
export type ShakeMode = "elide" | "
|
|
8
|
+
export type ShakeMode = "elide" | "images";
|
|
9
9
|
/** Outcome of an `AgentSession.shake` run. */
|
|
10
10
|
export interface ShakeResult {
|
|
11
11
|
mode: ShakeMode;
|
|
12
|
-
/** Whole tool-call results dropped
|
|
12
|
+
/** Whole tool-call results dropped. */
|
|
13
13
|
toolResultsDropped: number;
|
|
14
|
-
/** Large fenced/XML blocks dropped
|
|
14
|
+
/** Large fenced/XML blocks dropped. */
|
|
15
15
|
blocksDropped: number;
|
|
16
16
|
/** Image blocks removed (images mode only). */
|
|
17
17
|
imagesDropped?: number;
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Repair double-encoded JSON string arguments for the task tool.
|
|
3
|
+
*
|
|
4
|
+
* Models occasionally JSON-escape a string value twice when emitting a
|
|
5
|
+
* `task` tool call, so a `context`/`assignment` that should read
|
|
6
|
+
*
|
|
7
|
+
* # Role
|
|
8
|
+
* You are a judge … "describe this" … return —
|
|
9
|
+
*
|
|
10
|
+
* arrives — after the one JSON decode the provider already applied — as the
|
|
11
|
+
* literal text
|
|
12
|
+
*
|
|
13
|
+
* # Role\nYou are a judge … \"describe this\" … return \u2014
|
|
14
|
+
*
|
|
15
|
+
* i.e. every newline, quote, and unicode character is still backslash-escaped.
|
|
16
|
+
* The subagent then receives that garbled prompt, and the call preview renders
|
|
17
|
+
* one long blob with visible `\n` / `\"` / `\uXXXX`.
|
|
18
|
+
*
|
|
19
|
+
* The *whole-arguments* form of this quirk (the entire `arguments` blob is a
|
|
20
|
+
* JSON string) is already auto-corrected by the validator's JSON-string
|
|
21
|
+
* coercion. This module handles the *per-field* form, where the object parses
|
|
22
|
+
* fine but an individual string value is double-encoded — the validator never
|
|
23
|
+
* fires there because a double-encoded string is still a structurally valid
|
|
24
|
+
* string.
|
|
25
|
+
*
|
|
26
|
+
* This is deliberately scoped to the task tool's natural-language fields
|
|
27
|
+
* (`context`, `assignment`, `description`). It is NOT applied to code-bearing
|
|
28
|
+
* tools (write/edit/bash/search), where a backslash or quote is load-bearing
|
|
29
|
+
* and a false-positive unescape would silently corrupt a file or command.
|
|
30
|
+
*/
|
|
31
|
+
import type { TaskParams } from "./types";
|
|
32
|
+
/**
|
|
33
|
+
* Return the once-unescaped string when `value` is uniformly double-encoded
|
|
34
|
+
* JSON (a well-formed JSON string body that decodes to a different string);
|
|
35
|
+
* otherwise return `value` unchanged.
|
|
36
|
+
*
|
|
37
|
+
* The `JSON.parse(\`"${value}"\`)` round-trip is the safety net: it only
|
|
38
|
+
* succeeds when *every* backslash begins a valid JSON escape and no bare
|
|
39
|
+
* double-quote exists — exactly the signature of double-encoding. Genuine
|
|
40
|
+
* prose with a Windows path (`C:\Users`), a regex (`\d+`), an embedded quote,
|
|
41
|
+
* or a real (already-decoded) newline makes the parse throw, so the value is
|
|
42
|
+
* returned untouched.
|
|
43
|
+
*/
|
|
44
|
+
export declare function repairDoubleEncodedJsonString(value: string): string;
|
|
45
|
+
/**
|
|
46
|
+
* Repair double-encoded prose in task-tool params (`context` and each task's
|
|
47
|
+
* `assignment`/`description`). Returns the same reference when nothing changed
|
|
48
|
+
* so callers can cheaply skip work. Defensive against partially-streamed args
|
|
49
|
+
* (missing/undefined fields, partial task arrays) so it is safe on the render
|
|
50
|
+
* path as well as on execution.
|
|
51
|
+
*/
|
|
52
|
+
export declare function repairTaskParams(params: TaskParams): TaskParams;
|
|
@@ -113,20 +113,6 @@ export declare const TINY_MEMORY_MODEL_OPTIONS: ({
|
|
|
113
113
|
})[];
|
|
114
114
|
export declare function isTinyMemoryLocalModelKey(value: string): value is TinyMemoryLocalModelKey;
|
|
115
115
|
export declare function getTinyMemoryModelSpec(key: TinyMemoryLocalModelKey): (typeof TINY_MEMORY_LOCAL_MODELS)[number];
|
|
116
|
-
/**
|
|
117
|
-
* Shake-summary models. Shake's `summary` mode (and the `shake-summary`
|
|
118
|
-
* compaction strategy) compress heavy regions strictly on-device — there is no
|
|
119
|
-
* online/remote option, so this registry reuses the local memory models only.
|
|
120
|
-
*/
|
|
121
|
-
export declare const SHAKE_SUMMARY_MODEL_VALUES: readonly ["qwen3-1.7b", "gemma-3-1b", "qwen2.5-1.5b", "lfm2-1.2b"];
|
|
122
|
-
export type ShakeSummaryModelKey = (typeof SHAKE_SUMMARY_MODEL_VALUES)[number];
|
|
123
|
-
export declare const SHAKE_SUMMARY_MODEL_OPTIONS: {
|
|
124
|
-
value: "gemma-3-1b" | "lfm2-1.2b" | "qwen2.5-1.5b" | "qwen3-1.7b";
|
|
125
|
-
label: "Gemma 3 1B" | "LFM2 1.2B" | "Qwen2.5 1.5B" | "Qwen3 1.7B";
|
|
126
|
-
description: "Best consolidation/dedup; lighter footprint, but leaks small talk during extraction." | "Best extraction granularity (atomic facts); weaker consolidation." | "Fastest load; solid all-rounder, slightly noisier extraction labels." | "Recommended; most disciplined extraction (ignores chit-chat), good consolidation, about 1.1 GB cached.";
|
|
127
|
-
}[];
|
|
128
|
-
/** Default shake-summary local model when none is named. */
|
|
129
|
-
export declare const DEFAULT_SHAKE_SUMMARY_MODEL_KEY: ShakeSummaryModelKey;
|
|
130
116
|
/** Any local model key (title or memory), used by the shared inference worker. */
|
|
131
117
|
export type TinyLocalModelKey = TinyTitleLocalModelKey | TinyMemoryLocalModelKey;
|
|
132
118
|
/** Resolve a local model spec by key across both the title and memory registries. */
|
|
@@ -1,8 +1,14 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { Subprocess } from "bun";
|
|
2
|
+
import type { TinyTitleProgressEvent, TinyTitleWorkerOutbound } from "./title-protocol";
|
|
2
3
|
export interface TinyTitleDownloadOptions {
|
|
3
4
|
signal?: AbortSignal;
|
|
4
5
|
onProgress?: (event: TinyTitleProgressEvent) => void;
|
|
5
6
|
}
|
|
7
|
+
/**
|
|
8
|
+
* Hidden subcommand on the main CLI that boots the tiny-model worker in the
|
|
9
|
+
* spawned subprocess. Kept in sync with the dispatch in `cli.ts`.
|
|
10
|
+
*/
|
|
11
|
+
export declare const TINY_WORKER_ARG = "--tiny-worker";
|
|
6
12
|
/**
|
|
7
13
|
* Decide which `PI_TINY_DEVICE` / `PI_TINY_DTYPE` vars to overlay onto the worker
|
|
8
14
|
* env. A present env var wins (left untouched); otherwise the mapped persisted
|
|
@@ -11,7 +17,26 @@ export interface TinyTitleDownloadOptions {
|
|
|
11
17
|
* @internal
|
|
12
18
|
*/
|
|
13
19
|
export declare function tinyWorkerEnvOverlay(env: Record<string, string | undefined>, deviceSetting: string | undefined, dtypeSetting: string | undefined): Record<string, string>;
|
|
14
|
-
|
|
20
|
+
interface SpawnedSubprocess {
|
|
21
|
+
proc: Subprocess<"ignore", "inherit", "inherit">;
|
|
22
|
+
inbound: Set<(message: TinyTitleWorkerOutbound) => void>;
|
|
23
|
+
errors: Set<(error: Error) => void>;
|
|
24
|
+
/**
|
|
25
|
+
* Flipped to `true` by {@link wrapSubprocess}'s `terminate()` right
|
|
26
|
+
* before it SIGKILLs the child so `onExit` can distinguish the
|
|
27
|
+
* expected hard-kill from a crash/OOM/external signal. Only the
|
|
28
|
+
* latter is surfaced as a worker error.
|
|
29
|
+
*/
|
|
30
|
+
intentionalExit: {
|
|
31
|
+
value: boolean;
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
/**
|
|
35
|
+
* Spawn the tiny-model worker as a subprocess. Exported for tests and the
|
|
36
|
+
* smoke probe; production callers go through {@link spawnTinyTitleWorker}
|
|
37
|
+
* which wraps the result in a {@link WorkerHandle}.
|
|
38
|
+
*/
|
|
39
|
+
export declare function createTinyTitleSubprocess(): SpawnedSubprocess;
|
|
15
40
|
export declare class TinyTitleClient {
|
|
16
41
|
#private;
|
|
17
42
|
onProgress(listener: (event: TinyTitleProgressEvent) => void): () => void;
|
|
@@ -30,3 +55,4 @@ export declare function shutdownTinyTitleClient(): Promise<void>;
|
|
|
30
55
|
export declare function smokeTestTinyTitleWorker({ timeoutMs, }?: {
|
|
31
56
|
timeoutMs?: number;
|
|
32
57
|
}): Promise<void>;
|
|
58
|
+
export {};
|
|
@@ -30,16 +30,10 @@ export type TinyTitleWorkerInbound = {
|
|
|
30
30
|
modelKey: TinyLocalModelKey;
|
|
31
31
|
prompt: string;
|
|
32
32
|
maxTokens?: number;
|
|
33
|
-
/** Optional assistant-turn prefix appended after the generation prompt to pin output format. */
|
|
34
|
-
prefill?: string;
|
|
35
|
-
/** Optional literal stop string; generation halts once it appears in the decoded tail. */
|
|
36
|
-
stop?: string;
|
|
37
33
|
} | {
|
|
38
34
|
type: "download";
|
|
39
35
|
id: string;
|
|
40
36
|
modelKey: TinyLocalModelKey;
|
|
41
|
-
} | {
|
|
42
|
-
type: "close";
|
|
43
37
|
};
|
|
44
38
|
export type TinyTitleWorkerOutbound = {
|
|
45
39
|
type: "pong";
|
|
@@ -68,11 +62,16 @@ export type TinyTitleWorkerOutbound = {
|
|
|
68
62
|
level: "debug" | "warn" | "error";
|
|
69
63
|
msg: string;
|
|
70
64
|
meta?: Record<string, unknown>;
|
|
71
|
-
} | {
|
|
72
|
-
type: "closed";
|
|
73
65
|
};
|
|
66
|
+
/**
|
|
67
|
+
* Wire transport between the parent (`TinyTitleClient`) and the tiny-model
|
|
68
|
+
* subprocess. The parent owns the subprocess lifecycle (graceful work, hard
|
|
69
|
+
* kill on shutdown); the protocol therefore carries no explicit close
|
|
70
|
+
* handshake — once the parent decides to terminate, it signals the OS to
|
|
71
|
+
* reap the child so `onnxruntime-node`'s NAPI finalizer never runs in any
|
|
72
|
+
* shared address space. See `title-client.ts` for the spawn/kill glue.
|
|
73
|
+
*/
|
|
74
74
|
export interface TinyTitleTransport {
|
|
75
75
|
send(message: TinyTitleWorkerOutbound): void;
|
|
76
76
|
onMessage(handler: (message: TinyTitleWorkerInbound) => void): () => void;
|
|
77
|
-
close(): void;
|
|
78
77
|
}
|
|
@@ -26,6 +26,7 @@ declare const askSchema: z.ZodObject<{
|
|
|
26
26
|
question: z.ZodString;
|
|
27
27
|
options: z.ZodArray<z.ZodObject<{
|
|
28
28
|
label: z.ZodString;
|
|
29
|
+
description: z.ZodOptional<z.ZodString>;
|
|
29
30
|
}, z.core.$strip>>;
|
|
30
31
|
multi: z.ZodOptional<z.ZodBoolean>;
|
|
31
32
|
recommended: z.ZodOptional<z.ZodNumber>;
|
|
@@ -71,6 +72,7 @@ export declare class AskTool implements AgentTool<typeof askSchema, AskToolDetai
|
|
|
71
72
|
question: z.ZodString;
|
|
72
73
|
options: z.ZodArray<z.ZodObject<{
|
|
73
74
|
label: z.ZodString;
|
|
75
|
+
description: z.ZodOptional<z.ZodString>;
|
|
74
76
|
}, z.core.$strip>>;
|
|
75
77
|
multi: z.ZodOptional<z.ZodBoolean>;
|
|
76
78
|
recommended: z.ZodOptional<z.ZodNumber>;
|
|
@@ -82,18 +84,18 @@ export declare class AskTool implements AgentTool<typeof askSchema, AskToolDetai
|
|
|
82
84
|
static createIf(session: ToolSession): AskTool | null;
|
|
83
85
|
execute(_toolCallId: string, params: AskParams, signal?: AbortSignal, _onUpdate?: AgentToolUpdateCallback<AskToolDetails>, context?: AgentToolContext): Promise<AgentToolResult<AskToolDetails>>;
|
|
84
86
|
}
|
|
87
|
+
interface AskRenderOption {
|
|
88
|
+
label: string;
|
|
89
|
+
description?: string;
|
|
90
|
+
}
|
|
85
91
|
interface AskRenderArgs {
|
|
86
92
|
question?: string;
|
|
87
|
-
options?:
|
|
88
|
-
label: string;
|
|
89
|
-
}>;
|
|
93
|
+
options?: AskRenderOption[];
|
|
90
94
|
multi?: boolean;
|
|
91
95
|
questions?: Array<{
|
|
92
96
|
id: string;
|
|
93
97
|
question: string;
|
|
94
|
-
options:
|
|
95
|
-
label: string;
|
|
96
|
-
}>;
|
|
98
|
+
options: AskRenderOption[];
|
|
97
99
|
multi?: boolean;
|
|
98
100
|
}>;
|
|
99
101
|
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { ToolSession } from ".";
|
|
2
|
+
export interface EvalBackendsAllowance {
|
|
3
|
+
python: boolean;
|
|
4
|
+
js: boolean;
|
|
5
|
+
}
|
|
6
|
+
/** Read per-backend allowance from settings (defaults true). */
|
|
7
|
+
export declare function readEvalBackendsAllowance(session: ToolSession): EvalBackendsAllowance;
|
|
8
|
+
/**
|
|
9
|
+
* Materialize the active eval backend allowance: PI_PY / PI_JS env flags
|
|
10
|
+
* override the per-key settings; otherwise settings (defaults true) win.
|
|
11
|
+
*/
|
|
12
|
+
export declare function resolveEvalBackends(session: ToolSession): EvalBackendsAllowance;
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* TUI rendering for the eval tool.
|
|
3
|
+
*
|
|
4
|
+
* Split out from `eval.ts` so the renderer can be imported by `renderers.ts`
|
|
5
|
+
* without dragging the eval *runtime* (JS/Python backends -> agent bridge ->
|
|
6
|
+
* task executor -> sdk -> extension loader -> root barrel) into the renderer
|
|
7
|
+
* module graph. That transitive chain re-enters `renderers.ts` while `eval.ts`
|
|
8
|
+
* is still initializing, which previously crashed module load with a TDZ
|
|
9
|
+
* `Cannot access 'evalToolRenderer' before initialization`.
|
|
10
|
+
*/
|
|
11
|
+
import type { Component } from "@oh-my-pi/pi-tui";
|
|
12
|
+
import type { EvalStatusEvent, EvalToolDetails } from "../eval/types";
|
|
13
|
+
import type { RenderResultOptions } from "../extensibility/custom-tools/types";
|
|
14
|
+
import { type Theme } from "../modes/theme/theme";
|
|
15
|
+
export declare const EVAL_DEFAULT_PREVIEW_LINES = 10;
|
|
16
|
+
interface EvalRenderCellArg {
|
|
17
|
+
language?: string;
|
|
18
|
+
code?: string;
|
|
19
|
+
title?: string;
|
|
20
|
+
}
|
|
21
|
+
interface EvalRenderArgs {
|
|
22
|
+
cells?: EvalRenderCellArg[];
|
|
23
|
+
__partialJson?: string;
|
|
24
|
+
}
|
|
25
|
+
interface EvalRenderContext {
|
|
26
|
+
output?: string;
|
|
27
|
+
expanded?: boolean;
|
|
28
|
+
previewLines?: number;
|
|
29
|
+
timeout?: number;
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Append or replace a status event. `agent` events are progress snapshots keyed
|
|
33
|
+
* by `id`, so they coalesce in place (preserving first-seen order); every other
|
|
34
|
+
* op is a discrete action and simply appends. Keeps the persisted event list
|
|
35
|
+
* bounded even when a subagent emits hundreds of throttled progress ticks.
|
|
36
|
+
*/
|
|
37
|
+
export declare function upsertStatusEvent(events: EvalStatusEvent[], event: EvalStatusEvent): void;
|
|
38
|
+
export declare const evalToolRenderer: {
|
|
39
|
+
renderCall(args: EvalRenderArgs, options: RenderResultOptions, uiTheme: Theme): Component;
|
|
40
|
+
renderResult(result: {
|
|
41
|
+
content: Array<{
|
|
42
|
+
type: string;
|
|
43
|
+
text?: string;
|
|
44
|
+
}>;
|
|
45
|
+
details?: EvalToolDetails;
|
|
46
|
+
}, options: RenderResultOptions & {
|
|
47
|
+
renderContext?: EvalRenderContext;
|
|
48
|
+
}, uiTheme: Theme, _args?: EvalRenderArgs): Component;
|
|
49
|
+
mergeCallAndResult: boolean;
|
|
50
|
+
inline: boolean;
|
|
51
|
+
};
|
|
52
|
+
export {};
|
|
@@ -1,11 +1,8 @@
|
|
|
1
1
|
import type { AgentTool, AgentToolContext, AgentToolResult, AgentToolUpdateCallback } from "@oh-my-pi/pi-agent-core";
|
|
2
|
-
import type { Component } from "@oh-my-pi/pi-tui";
|
|
3
2
|
import * as z from "zod/v4";
|
|
4
3
|
import type { EvalToolDetails } from "../eval/types";
|
|
5
|
-
import type {
|
|
6
|
-
|
|
7
|
-
import { type ToolSession } from ".";
|
|
8
|
-
export declare const EVAL_DEFAULT_PREVIEW_LINES = 10;
|
|
4
|
+
import type { ToolSession } from ".";
|
|
5
|
+
export { EVAL_DEFAULT_PREVIEW_LINES, evalToolRenderer } from "./eval-render";
|
|
9
6
|
/**
|
|
10
7
|
* Per-cell input. Each cell runs in order; state persists within a language
|
|
11
8
|
* across cells and across tool calls.
|
|
@@ -78,33 +75,3 @@ export declare class EvalTool implements AgentTool<typeof evalSchema> {
|
|
|
78
75
|
constructor(session: ToolSession | null, options?: EvalToolOptions);
|
|
79
76
|
execute(_toolCallId: string, params: z.infer<typeof evalSchema>, signal?: AbortSignal, onUpdate?: AgentToolUpdateCallback, _ctx?: AgentToolContext): Promise<AgentToolResult<EvalToolDetails | undefined>>;
|
|
80
77
|
}
|
|
81
|
-
interface EvalRenderCellArg {
|
|
82
|
-
language?: string;
|
|
83
|
-
code?: string;
|
|
84
|
-
title?: string;
|
|
85
|
-
}
|
|
86
|
-
interface EvalRenderArgs {
|
|
87
|
-
cells?: EvalRenderCellArg[];
|
|
88
|
-
__partialJson?: string;
|
|
89
|
-
}
|
|
90
|
-
interface EvalRenderContext {
|
|
91
|
-
output?: string;
|
|
92
|
-
expanded?: boolean;
|
|
93
|
-
previewLines?: number;
|
|
94
|
-
timeout?: number;
|
|
95
|
-
}
|
|
96
|
-
export declare const evalToolRenderer: {
|
|
97
|
-
renderCall(args: EvalRenderArgs, options: RenderResultOptions, uiTheme: Theme): Component;
|
|
98
|
-
renderResult(result: {
|
|
99
|
-
content: Array<{
|
|
100
|
-
type: string;
|
|
101
|
-
text?: string;
|
|
102
|
-
}>;
|
|
103
|
-
details?: EvalToolDetails;
|
|
104
|
-
}, options: RenderResultOptions & {
|
|
105
|
-
renderContext?: EvalRenderContext;
|
|
106
|
-
}, uiTheme: Theme, _args?: EvalRenderArgs): Component;
|
|
107
|
-
mergeCallAndResult: boolean;
|
|
108
|
-
inline: boolean;
|
|
109
|
-
};
|
|
110
|
-
export {};
|
|
@@ -93,7 +93,7 @@ export declare class FindTool implements AgentTool<typeof findSchema, FindToolDe
|
|
|
93
93
|
execute(_toolCallId: string, params: z.infer<typeof findSchema>, signal?: AbortSignal, onUpdate?: AgentToolUpdateCallback<FindToolDetails>, _context?: AgentToolContext): Promise<AgentToolResult<FindToolDetails>>;
|
|
94
94
|
}
|
|
95
95
|
interface FindRenderArgs {
|
|
96
|
-
paths?: string[];
|
|
96
|
+
paths?: string | string[];
|
|
97
97
|
limit?: number;
|
|
98
98
|
}
|
|
99
99
|
export declare const findToolRenderer: {
|
|
@@ -37,6 +37,7 @@ export * from "./browser";
|
|
|
37
37
|
export * from "./checkpoint";
|
|
38
38
|
export * from "./debug";
|
|
39
39
|
export * from "./eval";
|
|
40
|
+
export * from "./eval-backends";
|
|
40
41
|
export * from "./find";
|
|
41
42
|
export * from "./gh";
|
|
42
43
|
export * from "./image-gen";
|
|
@@ -218,6 +219,9 @@ export interface ToolSession {
|
|
|
218
219
|
* to splice the recorded region with replacement content. Lazily initialized
|
|
219
220
|
* by `getConflictHistory`. */
|
|
220
221
|
conflictHistory?: import("./conflict-detect").ConflictHistory;
|
|
222
|
+
/** Per-session ledger of post-edit LSP diagnostics already surfaced to the
|
|
223
|
+
* model for each file. Lazily initialized by `getDiagnosticsLedger`. */
|
|
224
|
+
diagnosticsLedger?: import("../lsp/diagnostics-ledger").DiagnosticsLedger;
|
|
221
225
|
/** Queue a hidden message to be injected at the next agent turn. */
|
|
222
226
|
queueDeferredMessage?(message: CustomMessage): void;
|
|
223
227
|
/** Get the active OpenTelemetry config so subagent dispatch can forward
|
|
@@ -241,17 +245,6 @@ export declare function computeEssentialBuiltinNames(settings: Settings): string
|
|
|
241
245
|
export declare const BUILTIN_TOOLS: Record<string, ToolFactory>;
|
|
242
246
|
export declare const HIDDEN_TOOLS: Record<string, ToolFactory>;
|
|
243
247
|
export type ToolName = keyof typeof BUILTIN_TOOLS;
|
|
244
|
-
export interface EvalBackendsAllowance {
|
|
245
|
-
python: boolean;
|
|
246
|
-
js: boolean;
|
|
247
|
-
}
|
|
248
|
-
/** Read per-backend allowance from settings (defaults true). */
|
|
249
|
-
export declare function readEvalBackendsAllowance(session: ToolSession): EvalBackendsAllowance;
|
|
250
|
-
/**
|
|
251
|
-
* Materialize the active eval backend allowance: PI_PY / PI_JS env flags
|
|
252
|
-
* override the per-key settings; otherwise settings (defaults true) win.
|
|
253
|
-
*/
|
|
254
|
-
export declare function resolveEvalBackends(session: ToolSession): EvalBackendsAllowance;
|
|
255
248
|
/**
|
|
256
249
|
* Create tools from BUILTIN_TOOLS registry.
|
|
257
250
|
*/
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { type LocalProtocolOptions } from "../internal-urls";
|
|
1
2
|
export declare function expandTilde(filePath: string, home?: string): string;
|
|
2
3
|
export declare function expandPath(filePath: string): string;
|
|
3
4
|
/**
|
|
@@ -143,6 +144,12 @@ export interface ToolScopeOptions {
|
|
|
143
144
|
surfaceExactFilePaths?: boolean;
|
|
144
145
|
/** Extra hint appended to "Path not found" when stat fails and the user supplied multiple paths. */
|
|
145
146
|
multipathStatHint?: string;
|
|
147
|
+
/** Calling session's settings — forwarded to the internal-URL router so caller-aware handlers (issue://, pr://) honor it. */
|
|
148
|
+
settings?: unknown;
|
|
149
|
+
/** Caller's abort signal — forwarded to the internal-URL router. */
|
|
150
|
+
signal?: AbortSignal;
|
|
151
|
+
/** Calling session's `local://` root mapping — pins resolutions to the calling session. */
|
|
152
|
+
localProtocolOptions?: LocalProtocolOptions;
|
|
146
153
|
}
|
|
147
154
|
export interface ToolScopeResolution {
|
|
148
155
|
searchPath: string;
|
|
@@ -14,20 +14,21 @@ export interface OutputBlockOptions {
|
|
|
14
14
|
animate?: boolean;
|
|
15
15
|
}
|
|
16
16
|
/**
|
|
17
|
-
* Monotonic frame counter for animated borders
|
|
18
|
-
*
|
|
19
|
-
*
|
|
17
|
+
* Monotonic frame counter for animated borders, quantized to the TUI's ~16ms
|
|
18
|
+
* render cap so the cache key advances once per ~60fps frame — fine enough for a
|
|
19
|
+
* smooth segment sweep, coarse enough to coalesce multiple render passes that
|
|
20
|
+
* land inside the same frame.
|
|
20
21
|
*/
|
|
21
22
|
export declare function borderShimmerTick(): number;
|
|
22
23
|
/**
|
|
23
|
-
*
|
|
24
|
-
*
|
|
25
|
-
*
|
|
26
|
-
*
|
|
27
|
-
* from the wall clock against a fixed
|
|
28
|
-
*
|
|
24
|
+
* Column of the travelling segment's center on the bottom edge for a box of
|
|
25
|
+
* inner width `W` at time `now`. The segment bounces left → right → left across
|
|
26
|
+
* the bottom border: a triangle wave over one full there-and-back cycle, eased
|
|
27
|
+
* per leg so it slows as it nears each wall before reversing. Position is
|
|
28
|
+
* derived from the wall clock against a fixed cycle, so a resize shifts the
|
|
29
|
+
* center proportionally — no reset.
|
|
29
30
|
*/
|
|
30
|
-
export declare function
|
|
31
|
+
export declare function borderSegmentHeadCol(W: number, now: number): number;
|
|
31
32
|
export declare function renderOutputBlock(options: OutputBlockOptions, theme: Theme): string[];
|
|
32
33
|
/**
|
|
33
34
|
* Cached wrapper around `renderOutputBlock`.
|
|
@@ -41,6 +41,7 @@ cp permission-gate.ts ~/.omp/agent/extensions/
|
|
|
41
41
|
| `handoff.ts` | Transfer context to a new focused session via `/handoff <goal>` |
|
|
42
42
|
| `qna.ts` | Extracts questions from last response into editor via `ctx.ui.setEditorText()` |
|
|
43
43
|
| `status-line.ts` | Shows turn progress in footer via `ctx.ui.setStatus()` with themed colors |
|
|
44
|
+
| `thinking-note.ts` | Adds display-only supplemental UI below assistant thinking blocks |
|
|
44
45
|
| `snake.ts` | Snake game with custom UI, keyboard handling, and session persistence |
|
|
45
46
|
|
|
46
47
|
### Git Integration
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { ExtensionFactory } from "@oh-my-pi/pi-coding-agent";
|
|
2
|
+
import { Container, Text } from "@oh-my-pi/pi-tui";
|
|
3
|
+
|
|
4
|
+
const extension: ExtensionFactory = pi => {
|
|
5
|
+
pi.setLabel("Thinking note");
|
|
6
|
+
pi.registerAssistantThinkingRenderer((context, theme) => {
|
|
7
|
+
const container = new Container();
|
|
8
|
+
container.addChild(new Text(theme.fg("dim", `thinking chars: ${context.text.length}`), 1, 0));
|
|
9
|
+
return container;
|
|
10
|
+
});
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
export default extension;
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"type": "module",
|
|
3
3
|
"name": "@oh-my-pi/pi-coding-agent",
|
|
4
|
-
"version": "15.7.
|
|
4
|
+
"version": "15.7.6",
|
|
5
5
|
"description": "Coding agent CLI with read, bash, edit, write tools and session management",
|
|
6
6
|
"homepage": "https://omp.sh",
|
|
7
7
|
"author": "Can Boluk",
|
|
@@ -47,14 +47,14 @@
|
|
|
47
47
|
"@agentclientprotocol/sdk": "0.22.1",
|
|
48
48
|
"@babel/parser": "^7.29.7",
|
|
49
49
|
"@mozilla/readability": "^0.6.0",
|
|
50
|
-
"@oh-my-pi/hashline": "15.7.
|
|
51
|
-
"@oh-my-pi/omp-stats": "15.7.
|
|
52
|
-
"@oh-my-pi/pi-agent-core": "15.7.
|
|
53
|
-
"@oh-my-pi/pi-ai": "15.7.
|
|
54
|
-
"@oh-my-pi/pi-mnemopi": "15.7.
|
|
55
|
-
"@oh-my-pi/pi-natives": "15.7.
|
|
56
|
-
"@oh-my-pi/pi-tui": "15.7.
|
|
57
|
-
"@oh-my-pi/pi-utils": "15.7.
|
|
50
|
+
"@oh-my-pi/hashline": "15.7.6",
|
|
51
|
+
"@oh-my-pi/omp-stats": "15.7.6",
|
|
52
|
+
"@oh-my-pi/pi-agent-core": "15.7.6",
|
|
53
|
+
"@oh-my-pi/pi-ai": "15.7.6",
|
|
54
|
+
"@oh-my-pi/pi-mnemopi": "15.7.6",
|
|
55
|
+
"@oh-my-pi/pi-natives": "15.7.6",
|
|
56
|
+
"@oh-my-pi/pi-tui": "15.7.6",
|
|
57
|
+
"@oh-my-pi/pi-utils": "15.7.6",
|
|
58
58
|
"@puppeteer/browsers": "^3.0.4",
|
|
59
59
|
"@types/turndown": "5.0.6",
|
|
60
60
|
"@xterm/headless": "^6.0.0",
|
package/scripts/build-binary.ts
CHANGED
|
@@ -56,7 +56,6 @@ async function main(): Promise<void> {
|
|
|
56
56
|
"../stats/src/sync-worker.ts",
|
|
57
57
|
"./src/tools/browser/tab-worker-entry.ts",
|
|
58
58
|
"./src/eval/js/worker-entry.ts",
|
|
59
|
-
"./src/tiny/worker.ts",
|
|
60
59
|
// Legacy pi-* extension compat entrypoints served by
|
|
61
60
|
// `legacy-pi-compat.ts`. These are reached via computed bunfs paths
|
|
62
61
|
// (which `--compile`'s static analyzer cannot trace), so each must be
|
package/src/cli.ts
CHANGED
|
@@ -1,4 +1,15 @@
|
|
|
1
1
|
#!/usr/bin/env bun
|
|
2
|
+
// Strip macOS malloc-stack-logging vars in the parent entrypoint, before any
|
|
3
|
+
// subprocess/worker spawn. libmalloc reads MallocStackLogging /
|
|
4
|
+
// MallocStackLoggingNoCompact during malloc bootstrap (pre-main) in every child
|
|
5
|
+
// and warns when they're present but set to "off"; a child cannot suppress its
|
|
6
|
+
// own warning, so the only fix is to keep them out of the inherited env here.
|
|
7
|
+
// (They must be unset, not set — presence is the trigger.)
|
|
8
|
+
try {
|
|
9
|
+
delete process.env.MallocStackLogging;
|
|
10
|
+
delete process.env.MallocStackLoggingNoCompact;
|
|
11
|
+
} catch {}
|
|
12
|
+
|
|
2
13
|
/**
|
|
3
14
|
* CLI entry point — registers all commands explicitly and delegates to the
|
|
4
15
|
* lightweight CLI runner from pi-utils.
|
|
@@ -43,12 +54,60 @@ async function runSmokeTest(): Promise<void> {
|
|
|
43
54
|
process.stdout.write("smoke-test: ok\n");
|
|
44
55
|
}
|
|
45
56
|
|
|
57
|
+
/**
|
|
58
|
+
* Hidden subcommand that boots the tiny-model worker inside this process
|
|
59
|
+
* over the parent's IPC channel. The agent's main process spawns the same
|
|
60
|
+
* binary with this flag so `onnxruntime-node` (loaded transitively by
|
|
61
|
+
* `@huggingface/transformers`) lives in a child address space. The parent
|
|
62
|
+
* `SIGKILL`s the child on shutdown so the NAPI finalizer never runs in
|
|
63
|
+
* either process — that finalizer segfaults Bun on Windows (issue #1606).
|
|
64
|
+
*/
|
|
65
|
+
async function runTinyWorker(): Promise<void> {
|
|
66
|
+
const { startTinyTitleWorker } = await import("./tiny/worker");
|
|
67
|
+
const { promise: shuttingDown, resolve: shutdown } = Promise.withResolvers<void>();
|
|
68
|
+
const send = (message: unknown): void => {
|
|
69
|
+
// `process.send` only exists when spawned with an IPC channel; the
|
|
70
|
+
// parent always spawns us that way. If it's missing, the parent
|
|
71
|
+
// vanished and there's no one to talk to.
|
|
72
|
+
const sender = (process as NodeJS.Process & { send?: (m: unknown) => boolean }).send;
|
|
73
|
+
if (!sender) {
|
|
74
|
+
shutdown();
|
|
75
|
+
return;
|
|
76
|
+
}
|
|
77
|
+
try {
|
|
78
|
+
sender.call(process, message);
|
|
79
|
+
} catch {
|
|
80
|
+
shutdown();
|
|
81
|
+
}
|
|
82
|
+
};
|
|
83
|
+
startTinyTitleWorker({
|
|
84
|
+
send,
|
|
85
|
+
onMessage(handler) {
|
|
86
|
+
const wrap = (data: unknown): void => handler(data as never);
|
|
87
|
+
process.on("message", wrap);
|
|
88
|
+
return () => {
|
|
89
|
+
process.off("message", wrap);
|
|
90
|
+
};
|
|
91
|
+
},
|
|
92
|
+
});
|
|
93
|
+
// Parent went away (crashed, SIGKILL, etc.) — commit suicide so we don't
|
|
94
|
+
// linger as an orphan. SIGKILL via `process.kill` keeps us symmetrical
|
|
95
|
+
// with the parent's hard-kill on shutdown: skip every JS/native finalizer.
|
|
96
|
+
process.on("disconnect", () => shutdown());
|
|
97
|
+
await shuttingDown;
|
|
98
|
+
process.kill(process.pid, "SIGKILL");
|
|
99
|
+
}
|
|
100
|
+
|
|
46
101
|
/** Run the CLI with the given argv (no `process.argv` prefix). */
|
|
47
102
|
export async function runCli(argv: string[]): Promise<void> {
|
|
48
103
|
if (argv[0] === "--smoke-test") {
|
|
49
104
|
await runSmokeTest();
|
|
50
105
|
return;
|
|
51
106
|
}
|
|
107
|
+
if (argv[0] === "--tiny-worker") {
|
|
108
|
+
await runTinyWorker();
|
|
109
|
+
return;
|
|
110
|
+
}
|
|
52
111
|
// --help and --version are handled by run() directly, don't rewrite those.
|
|
53
112
|
// Everything else that isn't a known subcommand routes to "launch".
|
|
54
113
|
const first = argv[0];
|