@botbotgo/agent-harness 0.0.475 → 0.0.476
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -1234
- package/README.zh.md +3 -1191
- package/dist/acp.js +1 -1
- package/dist/api.js +1 -404
- package/dist/benchmark/checkpoint-resume-cost-benchmark.js +1 -55
- package/dist/benchmark/deepagent-local-model-benchmark.js +2 -35
- package/dist/benchmark/upstream-runtime-ab-benchmark.js +1 -179
- package/dist/cli/chat-interactive.js +25 -244
- package/dist/cli/chat-rendering.js +6 -100
- package/dist/cli/chat-stream.js +23 -512
- package/dist/cli/chat-ui.js +21 -199
- package/dist/cli/chat-workspace.js +2 -210
- package/dist/cli/main.js +21 -428
- package/dist/cli/managed-service-commands.js +9 -63
- package/dist/cli/managed-service.js +2 -137
- package/dist/cli/options-init-chat.js +1 -108
- package/dist/cli/options-runtime.js +1 -158
- package/dist/cli/options-serve.js +1 -282
- package/dist/cli/options.js +2 -19
- package/dist/cli/process-guards.js +1 -139
- package/dist/cli/request-tree.js +7 -296
- package/dist/cli/runtime-commands.js +12 -258
- package/dist/cli/runtime-output.js +16 -155
- package/dist/cli/server-commands.js +16 -270
- package/dist/cli/workspace.js +1 -67
- package/dist/cli.js +1 -7
- package/dist/client/acp.js +1 -1
- package/dist/client/in-process.js +1 -67
- package/dist/client/index.js +1 -2
- package/dist/client/types.js +0 -1
- package/dist/client.js +1 -1
- package/dist/contracts/core.js +1 -1
- package/dist/contracts/runtime-evaluation.js +0 -1
- package/dist/contracts/runtime-memory.js +0 -1
- package/dist/contracts/runtime-observability.js +0 -1
- package/dist/contracts/runtime-requests.js +0 -1
- package/dist/contracts/runtime-scheduling.js +0 -1
- package/dist/contracts/runtime.js +1 -27
- package/dist/contracts/types.js +1 -3
- package/dist/contracts/workspace.js +0 -1
- package/dist/flow/build-flow-graph.js +1 -50
- package/dist/flow/export-mermaid.js +2 -464
- package/dist/flow/export-sequence-mermaid.js +2 -325
- package/dist/flow/flow-graph-normalization.js +1 -214
- package/dist/flow/flow-graph-runtime.js +1 -107
- package/dist/flow/flow-graph-upstream.js +1 -494
- package/dist/flow/index.js +1 -3
- package/dist/flow/types.js +0 -1
- package/dist/index.js +1 -5
- package/dist/init-project.js +1 -1
- package/dist/knowledge/config.js +1 -32
- package/dist/knowledge/contracts.js +0 -1
- package/dist/knowledge/index.js +1 -2
- package/dist/knowledge/module.js +12 -909
- package/dist/knowledge/procedural/config.js +1 -125
- package/dist/knowledge/procedural/index.js +1 -2
- package/dist/knowledge/procedural/manager.js +9 -345
- package/dist/mcp.js +1 -2
- package/dist/package-version.d.ts +1 -1
- package/dist/package-version.js +1 -2
- package/dist/persistence/file-store.js +3 -758
- package/dist/persistence/sqlite-request-context-store.js +5 -54
- package/dist/persistence/sqlite-request-queue-store.js +10 -108
- package/dist/persistence/sqlite-runtime.js +1 -86
- package/dist/persistence/sqlite-store.js +62 -810
- package/dist/persistence/types.js +0 -1
- package/dist/projections/presentation.js +37 -206
- package/dist/projections/request-events.js +2 -502
- package/dist/projections/upstream-events.js +1 -201
- package/dist/protocol/a2a/http-discovery.js +1 -178
- package/dist/protocol/a2a/http-rpc.js +6 -622
- package/dist/protocol/a2a/http.js +1 -138
- package/dist/protocol/a2a/task-state.js +3 -317
- package/dist/protocol/acp/client.js +8 -294
- package/dist/protocol/acp/harness-client.js +1 -218
- package/dist/protocol/acp/http.js +5 -130
- package/dist/protocol/acp/server.js +1 -310
- package/dist/protocol/acp/stdio.js +2 -69
- package/dist/protocol/ag-ui/http.js +3 -378
- package/dist/protocol/mcp/server.js +1 -428
- package/dist/resource/backend/workspace-scoped-backend.js +1 -319
- package/dist/resource/isolation.js +1 -237
- package/dist/resource/mcp/tool-support.js +3 -296
- package/dist/resource/mcp-tool-support.js +1 -2
- package/dist/resource/providers/resource-provider.js +1 -215
- package/dist/resource/resource-impl.js +1 -3
- package/dist/resource/resource-types.js +0 -1
- package/dist/resource/resource.js +1 -1
- package/dist/resource/sources.js +1 -247
- package/dist/resource/tools/function-tool-resolver.js +2 -272
- package/dist/runtime/adapter/compat/deepagent-compat.js +1 -29
- package/dist/runtime/adapter/compat/openai-compatible.js +1 -55
- package/dist/runtime/adapter/direct-builtin-utility.js +2 -90
- package/dist/runtime/adapter/flow/execution-context.js +1 -71
- package/dist/runtime/adapter/flow/invocation-flow.js +8 -425
- package/dist/runtime/adapter/flow/invoke-runtime.js +1 -20
- package/dist/runtime/adapter/flow/stream-runtime.js +11 -1395
- package/dist/runtime/adapter/invocation-result.js +2 -473
- package/dist/runtime/adapter/local-tool-invocation.js +6 -638
- package/dist/runtime/adapter/middleware/context-hygiene.js +1 -83
- package/dist/runtime/adapter/middleware-assembly.js +5 -477
- package/dist/runtime/adapter/model/invocation-request.js +3 -183
- package/dist/runtime/adapter/model/message-assembly.js +1 -28
- package/dist/runtime/adapter/model/model-providers.js +23 -1115
- package/dist/runtime/adapter/model/prompted-json-tool-call-capture.js +1 -40
- package/dist/runtime/adapter/model/prompted-json-tool-policy.js +1 -22
- package/dist/runtime/adapter/resilience.js +1 -104
- package/dist/runtime/adapter/runtime-adapter-support.js +3 -141
- package/dist/runtime/adapter/runtime-shell.js +5 -166
- package/dist/runtime/adapter/stream-event-projection.js +2 -622
- package/dist/runtime/adapter/stream-text-consumption.js +1 -18
- package/dist/runtime/adapter/terminal-status.js +2 -67
- package/dist/runtime/adapter/tool/builtin-middleware-tools.js +6 -627
- package/dist/runtime/adapter/tool/declared-middleware.js +1 -154
- package/dist/runtime/adapter/tool/interrupt-policy.js +1 -34
- package/dist/runtime/adapter/tool/provider-tool.js +1 -25
- package/dist/runtime/adapter/tool/resolved-tool.js +1 -225
- package/dist/runtime/adapter/tool/tool-arguments.js +3 -486
- package/dist/runtime/adapter/tool/tool-hitl.js +1 -346
- package/dist/runtime/adapter/tool/tool-name-mapping.js +1 -128
- package/dist/runtime/adapter/tool/tool-output-artifacts.js +2 -88
- package/dist/runtime/adapter/tool/tool-replay.js +1 -37
- package/dist/runtime/adapter/tool-resolution.js +1 -86
- package/dist/runtime/adapter/upstream-configurable-keys.js +1 -2
- package/dist/runtime/agent-runtime-adapter.js +60 -2338
- package/dist/runtime/agent-runtime-assembly.js +7 -249
- package/dist/runtime/env/runtime-env.js +1 -62
- package/dist/runtime/harness/background-runtime.js +1 -8
- package/dist/runtime/harness/bindings.js +1 -58
- package/dist/runtime/harness/events/event-bus.js +1 -16
- package/dist/runtime/harness/events/event-sink.js +1 -61
- package/dist/runtime/harness/events/events.js +1 -80
- package/dist/runtime/harness/events/listener-runtime.js +1 -13
- package/dist/runtime/harness/events/runtime-event-operations.js +1 -9
- package/dist/runtime/harness/events/streaming.js +1 -100
- package/dist/runtime/harness/events/timeline.js +1 -52
- package/dist/runtime/harness/public-shapes.js +1 -186
- package/dist/runtime/harness/run/artifact-paths.js +1 -15
- package/dist/runtime/harness/run/governance.js +1 -295
- package/dist/runtime/harness/run/helpers.js +1 -71
- package/dist/runtime/harness/run/inspection.js +1 -409
- package/dist/runtime/harness/run/operator-overview.js +1 -80
- package/dist/runtime/harness/run/queue-diagnostics.js +1 -15
- package/dist/runtime/harness/run/recovery.js +1 -162
- package/dist/runtime/harness/run/resources.js +1 -60
- package/dist/runtime/harness/run/resume.js +1 -56
- package/dist/runtime/harness/run/routing.js +1 -48
- package/dist/runtime/harness/run/run-lifecycle.js +1 -66
- package/dist/runtime/harness/run/run-operations.js +1 -217
- package/dist/runtime/harness/run/run-queue.js +1 -43
- package/dist/runtime/harness/run/run-slot-acquisition.js +1 -157
- package/dist/runtime/harness/run/session-records.js +1 -97
- package/dist/runtime/harness/run/start-run.js +1 -120
- package/dist/runtime/harness/run/startup-runtime.js +1 -69
- package/dist/runtime/harness/run/stream-run.js +8 -1418
- package/dist/runtime/harness/run/surface-semantics.js +1 -79
- package/dist/runtime/harness/runtime-defaults.js +1 -39
- package/dist/runtime/harness/system/boundary-analysis.js +1 -234
- package/dist/runtime/harness/system/health-monitor.js +1 -258
- package/dist/runtime/harness/system/inventory.js +1 -129
- package/dist/runtime/harness/system/mem0-ingestion-sync.js +5 -345
- package/dist/runtime/harness/system/policy-engine.js +1 -175
- package/dist/runtime/harness/system/runtime-memory-candidates.js +4 -110
- package/dist/runtime/harness/system/runtime-memory-consolidation.js +1 -51
- package/dist/runtime/harness/system/runtime-memory-manager.js +10 -693
- package/dist/runtime/harness/system/runtime-memory-policy.js +1 -155
- package/dist/runtime/harness/system/runtime-memory-records.js +11 -577
- package/dist/runtime/harness/system/runtime-memory-sync.js +5 -206
- package/dist/runtime/harness/system/session-memory-sync.js +3 -113
- package/dist/runtime/harness/system/skill-requirements.js +1 -112
- package/dist/runtime/harness/system/store.js +9 -365
- package/dist/runtime/harness/tool-gateway/index.js +1 -2
- package/dist/runtime/harness/tool-gateway/policy.js +1 -45
- package/dist/runtime/harness/tool-gateway/validation.js +1 -176
- package/dist/runtime/harness/tool-schema.js +1 -3
- package/dist/runtime/harness.js +3 -1490
- package/dist/runtime/index.js +1 -3
- package/dist/runtime/layout/runtime-layout.js +1 -31
- package/dist/runtime/maintenance/checkpoint-maintenance.js +2 -178
- package/dist/runtime/maintenance/file-checkpoint-saver.js +1 -106
- package/dist/runtime/maintenance/runtime-record-maintenance.js +2 -169
- package/dist/runtime/maintenance/sqlite-checkpoint-saver.js +4 -289
- package/dist/runtime/parsing/output-content.js +10 -550
- package/dist/runtime/parsing/output-parsing.js +1 -4
- package/dist/runtime/parsing/output-recovery.js +3 -213
- package/dist/runtime/parsing/output-tool-args.js +7 -663
- package/dist/runtime/parsing/stream-event-parsing.js +3 -362
- package/dist/runtime/prompts/runtime-prompts.js +4 -73
- package/dist/runtime/scheduling/system-schedule-manager.js +11 -532
- package/dist/runtime/skills/skill-metadata.js +1 -197
- package/dist/runtime/startup-tracing.js +2 -37
- package/dist/runtime/support/compiled-binding.js +1 -290
- package/dist/runtime/support/embedding-models.js +1 -118
- package/dist/runtime/support/harness-support.js +5 -137
- package/dist/runtime/support/llamaindex.js +1 -108
- package/dist/runtime/support/runtime-adapter-options.js +1 -29
- package/dist/runtime/support/runtime-factories.js +1 -51
- package/dist/runtime/support/vector-stores.js +9 -270
- package/dist/scaffold/init-project.js +54 -233
- package/dist/tooling/extensions.js +1 -311
- package/dist/tooling/module-loader.js +1 -55
- package/dist/tools.js +1 -176
- package/dist/utils/agent-display.js +1 -18
- package/dist/utils/bundled-text.js +4 -39
- package/dist/utils/compiled-binding.js +1 -33
- package/dist/utils/fs.js +2 -45
- package/dist/utils/id.js +1 -9
- package/dist/utils/message-content.js +1 -30
- package/dist/utils/object.js +1 -6
- package/dist/workspace/agent-binding-compiler.js +3 -613
- package/dist/workspace/compile.js +1 -472
- package/dist/workspace/framework-contract-validation.js +2 -322
- package/dist/workspace/index.js +1 -1
- package/dist/workspace/object-loader-paths.js +1 -71
- package/dist/workspace/object-loader-readers.js +1 -187
- package/dist/workspace/object-loader.js +1 -754
- package/dist/workspace/resource-compilers.js +1 -374
- package/dist/workspace/support/agent-capabilities.js +1 -37
- package/dist/workspace/support/agent-execution-config.js +1 -44
- package/dist/workspace/support/discovery.js +1 -147
- package/dist/workspace/support/source-collectors.js +1 -30
- package/dist/workspace/support/source-protocols.js +2 -192
- package/dist/workspace/support/workspace-ref-utils.js +1 -362
- package/dist/workspace/tool-hydration.js +1 -280
- package/dist/workspace/validate.js +1 -99
- package/dist/workspace/yaml-object-reader.js +1 -285
- package/package.json +7 -3
package/dist/cli/chat-ui.js
CHANGED
|
@@ -1,199 +1,21 @@
|
|
|
1
|
-
import
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
const CHAT_LOGO_PRODUCT_LINE_COLORS = [136, 136, 160, 160, 160];
|
|
23
|
-
function colorizeSolidAsciiBlock(block, lineColors, enabled) {
|
|
24
|
-
const trimmed = trimAsciiBlock(block);
|
|
25
|
-
const lines = trimmed.split("\n");
|
|
26
|
-
if (!enabled) {
|
|
27
|
-
return trimmed;
|
|
28
|
-
}
|
|
29
|
-
return lines
|
|
30
|
-
.map((line, i) => {
|
|
31
|
-
const code = lineColors[Math.min(i, lineColors.length - 1)] ?? lineColors[lineColors.length - 1];
|
|
32
|
-
return `\x1b[38;5;${code}m${line}\x1b[0m`;
|
|
33
|
-
})
|
|
34
|
-
.join("\n");
|
|
35
|
-
}
|
|
36
|
-
function ellipsizeChatId(value, maxChars) {
|
|
37
|
-
if (value.length <= maxChars) {
|
|
38
|
-
return value;
|
|
39
|
-
}
|
|
40
|
-
if (maxChars <= 1) {
|
|
41
|
-
return "…";
|
|
42
|
-
}
|
|
43
|
-
return `${value.slice(0, maxChars - 1)}…`;
|
|
44
|
-
}
|
|
45
|
-
export function renderChatPromptLine(input) {
|
|
46
|
-
const agent = input.agentId ?? "—";
|
|
47
|
-
const sessionShort = input.sessionId ? ellipsizeChatId(input.sessionId, 8) : null;
|
|
48
|
-
if (!input.color) {
|
|
49
|
-
return `❯ agent:${agent}${sessionShort ? ` [${sessionShort}]` : ""} › `;
|
|
50
|
-
}
|
|
51
|
-
const labelColor = "\x1b[1;37m";
|
|
52
|
-
const valueColor = "\x1b[38;5;252m";
|
|
53
|
-
const mutedColor = "\x1b[38;5;242m";
|
|
54
|
-
const sigilColor = "\x1b[38;5;246m";
|
|
55
|
-
const reset = "\x1b[0m";
|
|
56
|
-
return `${sigilColor}❯${reset} ${labelColor}agent${reset}:${valueColor}${agent}${reset}${sessionShort ? ` ${mutedColor}[${sessionShort}]${reset}` : ""} ${sigilColor}›${reset} `;
|
|
57
|
-
}
|
|
58
|
-
export function renderChatBanner(input) {
|
|
59
|
-
const { color } = input;
|
|
60
|
-
const brandArt = colorizeSolidAsciiBlock(CHAT_ASCII_BOTBOTGO, CHAT_LOGO_BRAND_LINE_COLORS, color);
|
|
61
|
-
const productArt = colorizeSolidAsciiBlock(CHAT_ASCII_AGENT_HARNESS, CHAT_LOGO_PRODUCT_LINE_COLORS, color);
|
|
62
|
-
const logoWidth = Math.max(...CHAT_ASCII_BOTBOTGO.split("\n").map((l) => l.length), ...CHAT_ASCII_AGENT_HARNESS.split("\n").map((l) => l.length));
|
|
63
|
-
const ruleLen = Math.min(logoWidth + 4, 96);
|
|
64
|
-
const dimRule = (ch, len) => color ? `\x1b[38;5;237m${ch.repeat(len)}\x1b[0m` : ch.repeat(len);
|
|
65
|
-
const labelColor = color ? "\x1b[38;5;242m" : "";
|
|
66
|
-
const valueColor = color ? "\x1b[38;5;252m" : "";
|
|
67
|
-
const accentColor = color ? "\x1b[38;5;33m" : "";
|
|
68
|
-
const resetColor = color ? "\x1b[0m" : "";
|
|
69
|
-
const mutedColor = color ? "\x1b[38;5;238m" : "";
|
|
70
|
-
const borderColor = color ? "\x1b[38;5;237m" : "";
|
|
71
|
-
const kvRow = (label, value, labelW, accent = false) => {
|
|
72
|
-
const lPad = label.padEnd(labelW);
|
|
73
|
-
const lFormatted = `${labelColor}${lPad}${resetColor}`;
|
|
74
|
-
const vFormatted = accent
|
|
75
|
-
? `${accentColor}${value}${resetColor}`
|
|
76
|
-
: `${valueColor}${value}${resetColor}`;
|
|
77
|
-
return ` ${borderColor}│${resetColor} ${lFormatted} ${mutedColor}·${resetColor} ${vFormatted}`;
|
|
78
|
-
};
|
|
79
|
-
const rows = [
|
|
80
|
-
["workspace", input.workspacePath, false],
|
|
81
|
-
["transport", input.transport, false],
|
|
82
|
-
];
|
|
83
|
-
if (input.agentId)
|
|
84
|
-
rows.push(["agent", input.agentId, true]);
|
|
85
|
-
if (input.sessionId)
|
|
86
|
-
rows.push(["session", input.sessionId, false]);
|
|
87
|
-
const labelW = Math.max(...rows.map(([l]) => l.length));
|
|
88
|
-
const panelInner = Math.max(...rows.map(([, v]) => labelW + 4 + v.length), 44);
|
|
89
|
-
const hLine = (l, m, r) => color
|
|
90
|
-
? ` ${borderColor}${l}${resetColor}${borderColor}${m.repeat(panelInner + 2)}${r}${resetColor}`
|
|
91
|
-
: ` ${l}${m.repeat(panelInner + 2)}${r}`;
|
|
92
|
-
const versionTagText = `agent-harness v${AGENT_HARNESS_VERSION} · released ${AGENT_HARNESS_RELEASE_DATE}`;
|
|
93
|
-
const versionTag = color ? `${mutedColor}${versionTagText}${resetColor}` : versionTagText;
|
|
94
|
-
const versionDividerSpan = Math.max(36, ruleLen);
|
|
95
|
-
const versionGap = 2;
|
|
96
|
-
const versionRuleBudget = Math.max(24, versionDividerSpan - versionTagText.length - versionGap * 2);
|
|
97
|
-
const versionRuleLeftLen = Math.floor(versionRuleBudget / 2);
|
|
98
|
-
const versionRuleRightLen = versionRuleBudget - versionRuleLeftLen;
|
|
99
|
-
const hint = color
|
|
100
|
-
? ` ${mutedColor}Type \x1b[38;5;246m/help\x1b[0m${mutedColor} for commands · \x1b[38;5;246m/exit\x1b[0m${mutedColor} to quit${resetColor}`
|
|
101
|
-
: ` Type /help for commands · /exit to quit`;
|
|
102
|
-
return [
|
|
103
|
-
"",
|
|
104
|
-
brandArt,
|
|
105
|
-
"",
|
|
106
|
-
` ${dimRule("─", Math.max(36, ruleLen - 4))}`,
|
|
107
|
-
"",
|
|
108
|
-
productArt,
|
|
109
|
-
"",
|
|
110
|
-
` ${dimRule("─", versionRuleLeftLen)}${" ".repeat(versionGap)}${versionTag}${" ".repeat(versionGap)}${dimRule("─", versionRuleRightLen)}`,
|
|
111
|
-
"",
|
|
112
|
-
hLine("╭", "─", "╮"),
|
|
113
|
-
...rows.map(([l, v, accent]) => kvRow(l, v, labelW, accent)),
|
|
114
|
-
hLine("╰", "─", "╯"),
|
|
115
|
-
"",
|
|
116
|
-
hint,
|
|
117
|
-
"",
|
|
118
|
-
].join("\n");
|
|
119
|
-
}
|
|
120
|
-
export function renderRequestEvents(events) {
|
|
121
|
-
if (events.length === 0) {
|
|
122
|
-
return "No events recorded.\n";
|
|
123
|
-
}
|
|
124
|
-
return events.map((event) => {
|
|
125
|
-
const timestamp = formatTimestamp(event.timestamp) ?? "unknown-time";
|
|
126
|
-
const eventType = typeof event.eventType === "string" ? event.eventType : "unknown-event";
|
|
127
|
-
return `${timestamp} ${eventType}`;
|
|
128
|
-
}).join("\n") + "\n";
|
|
129
|
-
}
|
|
130
|
-
export function renderChatContext(input) {
|
|
131
|
-
const rows = [
|
|
132
|
-
["agent", input.agentId ?? "—"],
|
|
133
|
-
["session", input.sessionId ?? "—"],
|
|
134
|
-
["request", input.requestId ?? "—"],
|
|
135
|
-
];
|
|
136
|
-
const labelW = Math.max(...rows.map(([l]) => l.length));
|
|
137
|
-
const lines = rows.map(([label, value]) => ` ${label.padEnd(labelW)} ${value}`);
|
|
138
|
-
return ["", " Context", " ───────", ...lines, ""].join("\n");
|
|
139
|
-
}
|
|
140
|
-
export function renderChatHelp() {
|
|
141
|
-
const sections = [
|
|
142
|
-
{
|
|
143
|
-
heading: "Context & navigation",
|
|
144
|
-
rows: [
|
|
145
|
-
["/context", "Show current agent / session / request"],
|
|
146
|
-
["/new", "Clear session — start a fresh conversation"],
|
|
147
|
-
["/agent <id>", "Switch agent for new requests"],
|
|
148
|
-
["/session", "Print current session id"],
|
|
149
|
-
["/sessions", "List recent sessions"],
|
|
150
|
-
["/resume <id>", "Resume an existing session"],
|
|
151
|
-
["/request [id]", "Show or select active request"],
|
|
152
|
-
["/requests", "List requests for current session / agent"],
|
|
153
|
-
],
|
|
154
|
-
},
|
|
155
|
-
{
|
|
156
|
-
heading: "Approvals",
|
|
157
|
-
rows: [
|
|
158
|
-
["/approvals", "List pending approvals"],
|
|
159
|
-
["/approve <id>", "Approve a pending approval"],
|
|
160
|
-
["/reject <id>", "Reject a pending approval"],
|
|
161
|
-
["/cancel", "Cancel the latest active request"],
|
|
162
|
-
],
|
|
163
|
-
},
|
|
164
|
-
{
|
|
165
|
-
heading: "Diagnostics",
|
|
166
|
-
rows: [
|
|
167
|
-
["/events", "Persisted events for the latest request"],
|
|
168
|
-
["/trace", "Trace items for the latest request"],
|
|
169
|
-
["/health", "Runtime health snapshot"],
|
|
170
|
-
["/overview", "Runtime operator overview"],
|
|
171
|
-
],
|
|
172
|
-
},
|
|
173
|
-
{
|
|
174
|
-
heading: "Session",
|
|
175
|
-
rows: [
|
|
176
|
-
["/help", "Show this help"],
|
|
177
|
-
["/exit", "Quit chat"],
|
|
178
|
-
],
|
|
179
|
-
},
|
|
180
|
-
];
|
|
181
|
-
const allRows = sections.flatMap((s) => s.rows);
|
|
182
|
-
const cmdW = Math.max(...allRows.map(([cmd]) => cmd.length));
|
|
183
|
-
const out = [""];
|
|
184
|
-
for (const section of sections) {
|
|
185
|
-
out.push(` ${section.heading}`);
|
|
186
|
-
out.push(` ${"─".repeat(section.heading.length)}`);
|
|
187
|
-
for (const [cmd, desc] of section.rows) {
|
|
188
|
-
out.push(` ${cmd.padEnd(cmdW)} ${desc}`);
|
|
189
|
-
}
|
|
190
|
-
out.push("");
|
|
191
|
-
}
|
|
192
|
-
out.push(" Starter tasks:");
|
|
193
|
-
out.push(" ─────────────");
|
|
194
|
-
out.push(" Inspect this workspace and explain the main entry points.");
|
|
195
|
-
out.push(" Review this project structure before making any edits.");
|
|
196
|
-
out.push(" Find the likeliest config issue and propose the smallest fix.");
|
|
197
|
-
out.push("");
|
|
198
|
-
return out.join("\n");
|
|
199
|
-
}
|
|
1
|
+
import{AGENT_HARNESS_RELEASE_DATE as y,AGENT_HARNESS_VERSION as H}from"../package-version.js";function B(t){return typeof t=="string"&&t.trim().length>0?t.trim():null}function g(t){return t.split(`
|
|
2
|
+
`).map(e=>e.replace(/\s+$/u,"")).join(`
|
|
3
|
+
`)}const C=g(` ____ ___ _____ ____ ___ _____ ____ ___
|
|
4
|
+
| __ ) / _ \\_ _| __ ) / _ \\_ _/ ___|/ _ \\
|
|
5
|
+
| _ \\| | | || | | _ \\| | | || || | _| | | |
|
|
6
|
+
| |_) | |_| || | | |_) | |_| || || |_| | |_| |
|
|
7
|
+
|____/ \\___/ |_| |____/ \\___/ |_| \\____|\\___/`),R=g(` _ ____ _____ _ _ _____ _ _ _ ____ _ _ _____ ____ ____
|
|
8
|
+
/ \\ / ___| ____| \\ | |_ _| | | | | / \\ | _ \\| \\ | | ____/ ___/ ___|
|
|
9
|
+
/ _ \\| | _| _| | \\| | | | | |_| | / _ \\ | |_) | \\| | _| \\___ \\___ \\
|
|
10
|
+
/ ___ \\ |_| | |___| |\\ | | | | _ |/ ___ \\| _ <| |\\ | |___ ___) |__) |
|
|
11
|
+
/_/ \\_\\____|_____|_| \\_| |_| |_| |_/_/ \\_\\_| \\_\\_| \\_|_____|____/____/`),G=[25,238,160,238,160],P=[136,136,160,160,160];function A(t,e,o){const n=g(t),s=n.split(`
|
|
12
|
+
`);return o?s.map((r,a)=>`\x1B[38;5;${e[Math.min(a,e.length-1)]??e[e.length-1]}m${r}\x1B[0m`).join(`
|
|
13
|
+
`):n}function D(t,e){return t.length<=e?t:e<=1?"\u2026":`${t.slice(0,e-1)}\u2026`}function F(t){const e=t.agentId??"\u2014",o=t.sessionId?D(t.sessionId,8):null;if(!t.color)return`\u276F agent:${e}${o?` [${o}]`:""} \u203A `;const n="\x1B[1;37m",s="\x1B[38;5;252m",r="\x1B[38;5;242m",a="\x1B[38;5;246m",p="\x1B[0m";return`${a}\u276F${p} ${n}agent${p}:${s}${e}${p}${o?` ${r}[${o}]${p}`:""} ${a}\u203A${p} `}function z(t){const{color:e}=t,o=A(C,G,e),n=A(R,P,e),s=Math.max(...C.split(`
|
|
14
|
+
`).map(_=>_.length),...R.split(`
|
|
15
|
+
`).map(_=>_.length)),r=Math.min(s+4,96),a=(_,i)=>e?`\x1B[38;5;237m${_.repeat(i)}\x1B[0m`:_.repeat(i),p=e?"\x1B[38;5;242m":"",S=e?"\x1B[38;5;252m":"",T=e?"\x1B[38;5;33m":"",c=e?"\x1B[0m":"",h=e?"\x1B[38;5;238m":"",$=e?"\x1B[38;5;237m":"",I=(_,i,l,M=!1)=>{const k=_.padEnd(l),N=`${p}${k}${c}`,j=M?`${T}${i}${c}`:`${S}${i}${c}`;return` ${$}\u2502${c} ${N} ${h}\xB7${c} ${j}`},m=[["workspace",t.workspacePath,!1],["transport",t.transport,!1]];t.agentId&&m.push(["agent",t.agentId,!0]),t.sessionId&&m.push(["session",t.sessionId,!1]);const f=Math.max(...m.map(([_])=>_.length)),x=Math.max(...m.map(([,_])=>f+4+_.length),44),v=(_,i,l)=>e?` ${$}${_}${c}${$}${i.repeat(x+2)}${l}${c}`:` ${_}${i.repeat(x+2)}${l}`,d=`agent-harness v${H} \xB7 released ${y}`,E=e?`${h}${d}${c}`:d,L=Math.max(36,r),u=2,b=Math.max(24,L-d.length-u*2),w=Math.floor(b/2),q=b-w,O=e?` ${h}Type \x1B[38;5;246m/help\x1B[0m${h} for commands \xB7 \x1B[38;5;246m/exit\x1B[0m${h} to quit${c}`:" Type /help for commands \xB7 /exit to quit";return["",o,"",` ${a("\u2500",Math.max(36,r-4))}`,"",n,"",` ${a("\u2500",w)}${" ".repeat(u)}${E}${" ".repeat(u)}${a("\u2500",q)}`,"",v("\u256D","\u2500","\u256E"),...m.map(([_,i,l])=>I(_,i,f,l)),v("\u2570","\u2500","\u256F"),"",O,""].join(`
|
|
16
|
+
`)}function Q(t){return t.length===0?`No events recorded.
|
|
17
|
+
`:t.map(e=>{const o=B(e.timestamp)??"unknown-time",n=typeof e.eventType=="string"?e.eventType:"unknown-event";return`${o} ${n}`}).join(`
|
|
18
|
+
`)+`
|
|
19
|
+
`}function U(t){const e=[["agent",t.agentId??"\u2014"],["session",t.sessionId??"\u2014"],["request",t.requestId??"\u2014"]],o=Math.max(...e.map(([s])=>s.length));return[""," Context"," \u2500\u2500\u2500\u2500\u2500\u2500\u2500",...e.map(([s,r])=>` ${s.padEnd(o)} ${r}`),""].join(`
|
|
20
|
+
`)}function V(){const t=[{heading:"Context & navigation",rows:[["/context","Show current agent / session / request"],["/new","Clear session \u2014 start a fresh conversation"],["/agent <id>","Switch agent for new requests"],["/session","Print current session id"],["/sessions","List recent sessions"],["/resume <id>","Resume an existing session"],["/request [id]","Show or select active request"],["/requests","List requests for current session / agent"]]},{heading:"Approvals",rows:[["/approvals","List pending approvals"],["/approve <id>","Approve a pending approval"],["/reject <id>","Reject a pending approval"],["/cancel","Cancel the latest active request"]]},{heading:"Diagnostics",rows:[["/events","Persisted events for the latest request"],["/trace","Trace items for the latest request"],["/health","Runtime health snapshot"],["/overview","Runtime operator overview"]]},{heading:"Session",rows:[["/help","Show this help"],["/exit","Quit chat"]]}],e=t.flatMap(s=>s.rows),o=Math.max(...e.map(([s])=>s.length)),n=[""];for(const s of t){n.push(` ${s.heading}`),n.push(` ${"\u2500".repeat(s.heading.length)}`);for(const[r,a]of s.rows)n.push(` ${r.padEnd(o)} ${a}`);n.push("")}return n.push(" Starter tasks:"),n.push(" \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500"),n.push(" Inspect this workspace and explain the main entry points."),n.push(" Review this project structure before making any edits."),n.push(" Find the likeliest config issue and propose the smallest fix."),n.push(""),n.join(`
|
|
21
|
+
`)}export{z as renderChatBanner,U as renderChatContext,V as renderChatHelp,F as renderChatPromptLine,Q as renderRequestEvents};
|
|
@@ -1,210 +1,2 @@
|
|
|
1
|
-
import {
|
|
2
|
-
|
|
3
|
-
import YAML from "yaml";
|
|
4
|
-
import { interpolateEnvPlaceholders } from "../workspace/yaml-object-reader.js";
|
|
5
|
-
import { frameworkCliWorkspaceRoot, hasCliConfigYaml, resolveCliConfigRoot, } from "./workspace.js";
|
|
6
|
-
export function normalizeChatCommand(line) {
|
|
7
|
-
const trimmed = line.trim();
|
|
8
|
-
if (!trimmed.startsWith("/")) {
|
|
9
|
-
return null;
|
|
10
|
-
}
|
|
11
|
-
const [name, ...rest] = trimmed.slice(1).split(/\s+/);
|
|
12
|
-
return {
|
|
13
|
-
name,
|
|
14
|
-
arg: rest.length > 0 ? rest.join(" ") : undefined,
|
|
15
|
-
};
|
|
16
|
-
}
|
|
17
|
-
function asRecord(value) {
|
|
18
|
-
return typeof value === "object" && value !== null ? value : undefined;
|
|
19
|
-
}
|
|
20
|
-
function readCliConfigObjects(workspaceRoot) {
|
|
21
|
-
const roots = [
|
|
22
|
-
resolveCliConfigRoot(frameworkCliWorkspaceRoot()),
|
|
23
|
-
resolveCliConfigRoot(workspaceRoot),
|
|
24
|
-
];
|
|
25
|
-
const merged = new Map();
|
|
26
|
-
for (const configRoot of roots) {
|
|
27
|
-
if (!hasCliConfigYaml(configRoot)) {
|
|
28
|
-
continue;
|
|
29
|
-
}
|
|
30
|
-
const files = [];
|
|
31
|
-
const pending = [configRoot];
|
|
32
|
-
while (pending.length > 0) {
|
|
33
|
-
const current = pending.pop();
|
|
34
|
-
for (const entry of readdirSync(current, { withFileTypes: true })) {
|
|
35
|
-
const entryPath = path.join(current, entry.name);
|
|
36
|
-
if (entry.isDirectory()) {
|
|
37
|
-
if (entry.name === "node_modules") {
|
|
38
|
-
continue;
|
|
39
|
-
}
|
|
40
|
-
pending.push(entryPath);
|
|
41
|
-
continue;
|
|
42
|
-
}
|
|
43
|
-
if (entry.isFile() && /\.ya?ml$/i.test(entry.name)) {
|
|
44
|
-
files.push(entryPath);
|
|
45
|
-
}
|
|
46
|
-
}
|
|
47
|
-
}
|
|
48
|
-
for (const filePath of files.sort()) {
|
|
49
|
-
const content = readFileSync(filePath, "utf8");
|
|
50
|
-
for (const document of YAML.parseAllDocuments(content)) {
|
|
51
|
-
const resolved = interpolateEnvPlaceholders(document.toJSON(), filePath);
|
|
52
|
-
const typed = asRecord(resolved);
|
|
53
|
-
if (!typed) {
|
|
54
|
-
continue;
|
|
55
|
-
}
|
|
56
|
-
if (typed.kind === "Models" && Array.isArray(typed.spec)) {
|
|
57
|
-
for (const item of typed.spec) {
|
|
58
|
-
const record = asRecord(item);
|
|
59
|
-
if (!record) {
|
|
60
|
-
continue;
|
|
61
|
-
}
|
|
62
|
-
const id = typeof record.name === "string" ? record.name : record.id;
|
|
63
|
-
if (typeof id !== "string" || !id) {
|
|
64
|
-
continue;
|
|
65
|
-
}
|
|
66
|
-
merged.set(`Model/${id}`, {
|
|
67
|
-
...record,
|
|
68
|
-
kind: "Model",
|
|
69
|
-
id,
|
|
70
|
-
});
|
|
71
|
-
}
|
|
72
|
-
continue;
|
|
73
|
-
}
|
|
74
|
-
const metadata = asRecord(typed.metadata);
|
|
75
|
-
const spec = asRecord(typed.spec);
|
|
76
|
-
if (typeof typed.kind === "string" && spec) {
|
|
77
|
-
const id = typeof metadata?.name === "string" ? metadata.name : typed.id;
|
|
78
|
-
if (typeof id !== "string" || !id) {
|
|
79
|
-
continue;
|
|
80
|
-
}
|
|
81
|
-
merged.set(`${typed.kind}/${id}`, {
|
|
82
|
-
...spec,
|
|
83
|
-
kind: typed.kind,
|
|
84
|
-
id,
|
|
85
|
-
});
|
|
86
|
-
continue;
|
|
87
|
-
}
|
|
88
|
-
const kind = typeof typed.kind === "string" ? typed.kind : undefined;
|
|
89
|
-
const id = typeof typed.id === "string" ? typed.id : undefined;
|
|
90
|
-
if (!kind || !id) {
|
|
91
|
-
continue;
|
|
92
|
-
}
|
|
93
|
-
merged.set(`${kind}/${id}`, typed);
|
|
94
|
-
}
|
|
95
|
-
}
|
|
96
|
-
}
|
|
97
|
-
return Array.from(merged.values());
|
|
98
|
-
}
|
|
99
|
-
function getWorkspaceDefaultAgentId(workspaceRoot) {
|
|
100
|
-
const runtime = readCliConfigObjects(workspaceRoot).find((item) => item.kind === "Runtime" && item.id === "default");
|
|
101
|
-
const routing = asRecord(runtime?.routing);
|
|
102
|
-
return typeof routing?.defaultAgentId === "string" && routing.defaultAgentId.trim().length > 0 ? routing.defaultAgentId.trim() : undefined;
|
|
103
|
-
}
|
|
104
|
-
function getAgentModelRef(workspaceRoot, agentId) {
|
|
105
|
-
const agent = readCliConfigObjects(workspaceRoot).find((item) => item.kind === "Agent" && item.id === agentId);
|
|
106
|
-
return typeof agent?.modelRef === "string" && agent.modelRef.trim().length > 0 ? agent.modelRef.trim() : undefined;
|
|
107
|
-
}
|
|
108
|
-
function getModelInfo(workspaceRoot, modelRef) {
|
|
109
|
-
const modelName = modelRef.startsWith("model/") ? modelRef.slice("model/".length) : modelRef;
|
|
110
|
-
const model = readCliConfigObjects(workspaceRoot).find((item) => item.kind === "Model" && item.id === modelName);
|
|
111
|
-
if (!model) {
|
|
112
|
-
return undefined;
|
|
113
|
-
}
|
|
114
|
-
return {
|
|
115
|
-
provider: typeof model.provider === "string" ? model.provider : undefined,
|
|
116
|
-
model: typeof model.model === "string" ? model.model : undefined,
|
|
117
|
-
baseUrl: typeof model.baseUrl === "string" ? model.baseUrl : undefined,
|
|
118
|
-
};
|
|
119
|
-
}
|
|
120
|
-
export function readChatWorkspaceModelInfo(workspaceRoot, agentId) {
|
|
121
|
-
try {
|
|
122
|
-
const resolvedAgentId = agentId ?? getWorkspaceDefaultAgentId(workspaceRoot);
|
|
123
|
-
if (!resolvedAgentId) {
|
|
124
|
-
return getModelInfo(workspaceRoot, "model/default");
|
|
125
|
-
}
|
|
126
|
-
const modelRef = getAgentModelRef(workspaceRoot, resolvedAgentId) ?? "model/default";
|
|
127
|
-
return getModelInfo(workspaceRoot, modelRef);
|
|
128
|
-
}
|
|
129
|
-
catch {
|
|
130
|
-
return undefined;
|
|
131
|
-
}
|
|
132
|
-
}
|
|
133
|
-
function renderProviderFailureHint(modelInfo) {
|
|
134
|
-
if (!modelInfo?.provider) {
|
|
135
|
-
return undefined;
|
|
136
|
-
}
|
|
137
|
-
if (modelInfo.provider === "ollama") {
|
|
138
|
-
const modelText = modelInfo.model ? ` and ensure \`${modelInfo.model}\` is available` : "";
|
|
139
|
-
return `Hint: start Ollama${modelInfo.baseUrl ? ` at ${modelInfo.baseUrl}` : ""}${modelText}. Example: \`ollama serve\`${modelInfo.model ? ` and \`ollama pull ${modelInfo.model}\`` : ""}.`;
|
|
140
|
-
}
|
|
141
|
-
if (modelInfo.provider === "openai") {
|
|
142
|
-
return "Hint: verify network access and that `OPENAI_API_KEY` is set for this shell.";
|
|
143
|
-
}
|
|
144
|
-
if (modelInfo.provider === "anthropic") {
|
|
145
|
-
return "Hint: verify network access and that `ANTHROPIC_API_KEY` is set for this shell.";
|
|
146
|
-
}
|
|
147
|
-
if (modelInfo.provider === "google" || modelInfo.provider === "google-genai" || modelInfo.provider === "gemini") {
|
|
148
|
-
return "Hint: verify network access and that the configured Google API key is available in this shell.";
|
|
149
|
-
}
|
|
150
|
-
if (modelInfo.provider === "openai-compatible") {
|
|
151
|
-
return `Hint: verify the configured endpoint${modelInfo.baseUrl ? ` (${modelInfo.baseUrl})` : ""} and the required API key for that provider.`;
|
|
152
|
-
}
|
|
153
|
-
return undefined;
|
|
154
|
-
}
|
|
155
|
-
export function renderChatRuntimeFailure(output, modelInfo) {
|
|
156
|
-
const trimmed = output.trim();
|
|
157
|
-
if (!trimmed.startsWith("runtime_error=")) {
|
|
158
|
-
return output;
|
|
159
|
-
}
|
|
160
|
-
const normalized = trimmed.toLowerCase();
|
|
161
|
-
if (!normalized.includes("fetch failed") &&
|
|
162
|
-
!normalized.includes("connection error") &&
|
|
163
|
-
!normalized.includes("timed out") &&
|
|
164
|
-
!normalized.includes("error 524") &&
|
|
165
|
-
!normalized.includes("404 page not found")) {
|
|
166
|
-
return output;
|
|
167
|
-
}
|
|
168
|
-
const lines = [trimmed];
|
|
169
|
-
const isTimeoutStyleError = /(\berror 524\b|\btimeout\b|\btimed out\b)/i.test(trimmed);
|
|
170
|
-
if (modelInfo?.provider || modelInfo?.model) {
|
|
171
|
-
lines.push(`provider=${modelInfo?.provider ?? "unknown"}${modelInfo?.model ? ` model=${modelInfo.model}` : ""}`);
|
|
172
|
-
}
|
|
173
|
-
if (modelInfo?.baseUrl) {
|
|
174
|
-
lines.push(`endpoint=${modelInfo.baseUrl}`);
|
|
175
|
-
}
|
|
176
|
-
if (normalized.includes("404 page not found") && modelInfo?.provider === "ollama") {
|
|
177
|
-
lines.push("Hint: the configured endpoint responded, but it does not look like an Ollama API route. Check that `baseUrl` points at the Ollama server root and that no other service is bound to this port.");
|
|
178
|
-
}
|
|
179
|
-
const hint = renderProviderFailureHint(modelInfo);
|
|
180
|
-
if (hint) {
|
|
181
|
-
lines.push(hint);
|
|
182
|
-
}
|
|
183
|
-
if (isTimeoutStyleError) {
|
|
184
|
-
lines.push("Hint: this usually indicates the model endpoint dropped the connection before producing a full answer.");
|
|
185
|
-
}
|
|
186
|
-
return lines.join("\n");
|
|
187
|
-
}
|
|
188
|
-
export async function probeChatWorkspace(input) {
|
|
189
|
-
const modelInfo = readChatWorkspaceModelInfo(input.workspaceRoot, input.agentId);
|
|
190
|
-
if (!modelInfo?.provider || modelInfo.provider !== "ollama" || !modelInfo.baseUrl) {
|
|
191
|
-
return undefined;
|
|
192
|
-
}
|
|
193
|
-
try {
|
|
194
|
-
const response = await fetch(new URL("/api/tags", modelInfo.baseUrl), {
|
|
195
|
-
method: "GET",
|
|
196
|
-
headers: { accept: "application/json" },
|
|
197
|
-
});
|
|
198
|
-
if (response.ok) {
|
|
199
|
-
return undefined;
|
|
200
|
-
}
|
|
201
|
-
if (response.status === 404) {
|
|
202
|
-
return renderChatRuntimeFailure("runtime_error=404 page not found", modelInfo);
|
|
203
|
-
}
|
|
204
|
-
return renderChatRuntimeFailure(`runtime_error=HTTP ${response.status} ${response.statusText}`.trim(), modelInfo);
|
|
205
|
-
}
|
|
206
|
-
catch (error) {
|
|
207
|
-
const message = error instanceof Error ? error.message : String(error);
|
|
208
|
-
return renderChatRuntimeFailure(`runtime_error=${message}`, modelInfo);
|
|
209
|
-
}
|
|
210
|
-
}
|
|
1
|
+
import{readFileSync as C,readdirSync as U}from"node:fs";import P from"node:path";import w from"yaml";import{interpolateEnvPlaceholders as H}from"../workspace/yaml-object-reader.js";import{frameworkCliWorkspaceRoot as M,hasCliConfigYaml as R,resolveCliConfigRoot as k}from"./workspace.js";function N(e){const t=e.trim();if(!t.startsWith("/"))return null;const[n,...r]=t.slice(1).split(/\s+/);return{name:n,arg:r.length>0?r.join(" "):void 0}}function l(e){return typeof e=="object"&&e!==null?e:void 0}function m(e){const t=[k(M()),k(e)],n=new Map;for(const r of t){if(!R(r))continue;const o=[],u=[r];for(;u.length>0;){const s=u.pop();for(const d of U(s,{withFileTypes:!0})){const f=P.join(s,d.name);if(d.isDirectory()){if(d.name==="node_modules")continue;u.push(f);continue}d.isFile()&&/\.ya?ml$/i.test(d.name)&&o.push(f)}}for(const s of o.sort()){const d=C(s,"utf8");for(const f of w.parseAllDocuments(d)){const A=H(f.toJSON(),s),i=l(A);if(!i)continue;if(i.kind==="Models"&&Array.isArray(i.spec)){for(const a of i.spec){const c=l(a);if(!c)continue;const p=typeof c.name=="string"?c.name:c.id;typeof p!="string"||!p||n.set(`Model/${p}`,{...c,kind:"Model",id:p})}continue}const g=l(i.metadata),y=l(i.spec);if(typeof i.kind=="string"&&y){const a=typeof g?.name=="string"?g.name:i.id;if(typeof a!="string"||!a)continue;n.set(`${i.kind}/${a}`,{...y,kind:i.kind,id:a});continue}const v=typeof i.kind=="string"?i.kind:void 0,b=typeof i.id=="string"?i.id:void 0;!v||!b||n.set(`${v}/${b}`,i)}}}return Array.from(n.values())}function _(e){const t=m(e).find(r=>r.kind==="Runtime"&&r.id==="default"),n=l(t?.routing);return typeof n?.defaultAgentId=="string"&&n.defaultAgentId.trim().length>0?n.defaultAgentId.trim():void 0}function E(e,t){const n=m(e).find(r=>r.kind==="Agent"&&r.id===t);return typeof n?.modelRef=="string"&&n.modelRef.trim().length>0?n.modelRef.trim():void 0}function $(e,t){const n=t.startsWith("model/")?t.slice(6):t,r=m(e).find(o=>o.kind==="Model"&&o.id===n);if(r)return{provider:typeof r.provider=="string"?r.provider:void 0,model:typeof r.model=="string"?r.model:void 0,baseUrl:typeof r.baseUrl=="string"?r.baseUrl:void 0}}function T(e,t){try{const n=t??_(e);if(!n)return $(e,"model/default");const r=E(e,n)??"model/default";return $(e,r)}catch{return}}function x(e){if(e?.provider){if(e.provider==="ollama"){const t=e.model?` and ensure \`${e.model}\` is available`:"";return`Hint: start Ollama${e.baseUrl?` at ${e.baseUrl}`:""}${t}. Example: \`ollama serve\`${e.model?` and \`ollama pull ${e.model}\``:""}.`}if(e.provider==="openai")return"Hint: verify network access and that `OPENAI_API_KEY` is set for this shell.";if(e.provider==="anthropic")return"Hint: verify network access and that `ANTHROPIC_API_KEY` is set for this shell.";if(e.provider==="google"||e.provider==="google-genai"||e.provider==="gemini")return"Hint: verify network access and that the configured Google API key is available in this shell.";if(e.provider==="openai-compatible")return`Hint: verify the configured endpoint${e.baseUrl?` (${e.baseUrl})`:""} and the required API key for that provider.`}}function h(e,t){const n=e.trim();if(!n.startsWith("runtime_error="))return e;const r=n.toLowerCase();if(!r.includes("fetch failed")&&!r.includes("connection error")&&!r.includes("timed out")&&!r.includes("error 524")&&!r.includes("404 page not found"))return e;const o=[n],u=/(\berror 524\b|\btimeout\b|\btimed out\b)/i.test(n);(t?.provider||t?.model)&&o.push(`provider=${t?.provider??"unknown"}${t?.model?` model=${t.model}`:""}`),t?.baseUrl&&o.push(`endpoint=${t.baseUrl}`),r.includes("404 page not found")&&t?.provider==="ollama"&&o.push("Hint: the configured endpoint responded, but it does not look like an Ollama API route. Check that `baseUrl` points at the Ollama server root and that no other service is bound to this port.");const s=x(t);return s&&o.push(s),u&&o.push("Hint: this usually indicates the model endpoint dropped the connection before producing a full answer."),o.join(`
|
|
2
|
+
`)}async function Y(e){const t=T(e.workspaceRoot,e.agentId);if(!(!t?.provider||t.provider!=="ollama"||!t.baseUrl))try{const n=await fetch(new URL("/api/tags",t.baseUrl),{method:"GET",headers:{accept:"application/json"}});return n.ok?void 0:n.status===404?h("runtime_error=404 page not found",t):h(`runtime_error=HTTP ${n.status} ${n.statusText}`.trim(),t)}catch(n){const r=n instanceof Error?n.message:String(n);return h(`runtime_error=${r}`,t)}}export{N as normalizeChatCommand,Y as probeChatWorkspace,T as readChatWorkspaceModelInfo,h as renderChatRuntimeFailure};
|