@botbotgo/agent-harness 0.0.298 → 0.0.300
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 +78 -38
- package/README.zh.md +80 -31
- package/dist/acp.d.ts +3 -0
- package/dist/acp.js +10 -2
- package/dist/api.d.ts +14 -2
- package/dist/api.js +19 -3
- package/dist/cli.d.ts +18 -1
- package/dist/cli.js +1408 -319
- package/dist/client/acp.d.ts +9 -3
- package/dist/client/acp.js +55 -1
- package/dist/client/in-process.d.ts +5 -2
- package/dist/client/in-process.js +4 -6
- package/dist/client/index.d.ts +1 -1
- package/dist/client/types.d.ts +6 -5
- package/dist/config/agents/direct.yaml +7 -17
- package/dist/config/agents/orchestra.yaml +9 -65
- package/dist/config/catalogs/embedding-models.yaml +1 -1
- package/dist/config/catalogs/stores.yaml +1 -1
- package/dist/config/knowledge/knowledge-runtime.yaml +36 -2
- package/dist/config/knowledge/procedural-memory-runtime.yaml +78 -0
- package/dist/config/{catalogs/models.yaml → models.yaml} +2 -2
- package/dist/config/prompts/direct-system.md +16 -0
- package/dist/config/prompts/orchestra-system.md +62 -0
- package/dist/config/prompts/routing-system.md +14 -0
- package/dist/config/runtime/runtime-memory.yaml +39 -5
- package/dist/config/runtime/workspace.yaml +7 -16
- package/dist/contracts/runtime.d.ts +242 -1
- package/dist/contracts/workspace.d.ts +2 -0
- package/dist/index.d.ts +5 -3
- package/dist/index.js +2 -1
- package/dist/init-project.js +178 -33
- package/dist/knowledge/contracts.d.ts +5 -0
- package/dist/knowledge/module.d.ts +5 -0
- package/dist/knowledge/module.js +340 -18
- package/dist/package-version.d.ts +1 -1
- package/dist/package-version.js +1 -1
- package/dist/persistence/file-store.d.ts +5 -1
- package/dist/persistence/file-store.js +16 -0
- package/dist/persistence/sqlite-store.d.ts +4 -1
- package/dist/persistence/sqlite-store.js +88 -14
- package/dist/persistence/types.d.ts +4 -1
- package/dist/procedural/config.d.ts +63 -0
- package/dist/procedural/config.js +125 -0
- package/dist/procedural/index.d.ts +2 -0
- package/dist/procedural/index.js +1 -0
- package/dist/protocol/ag-ui/http.d.ts +3 -0
- package/dist/protocol/ag-ui/http.js +10 -0
- package/dist/request-events.d.ts +63 -0
- package/dist/request-events.js +400 -0
- package/dist/resource/isolation.js +11 -0
- package/dist/resource/resource-impl.d.ts +1 -0
- package/dist/resource/resource-impl.js +103 -12
- package/dist/resources/init-templates/agent-context/deep-research.md +5 -0
- package/dist/resources/init-templates/prompts/research-analyst-basic.md +1 -0
- package/dist/resources/init-templates/prompts/research-analyst-web-search.md +1 -0
- package/dist/resources/init-templates/prompts/research-host-deep-research-basic.md +1 -0
- package/dist/resources/init-templates/prompts/research-host-deep-research-web-search.md +1 -0
- package/dist/resources/init-templates/prompts/research-host-single-agent-basic.md +1 -0
- package/dist/resources/init-templates/prompts/research-host-single-agent-web-search.md +1 -0
- package/dist/resources/prompts/runtime/browser-capability-disclaimer-recovery.md +1 -0
- package/dist/resources/prompts/runtime/default-subagent.md +2 -0
- package/dist/resources/prompts/runtime/durable-memory-context.md +7 -0
- package/dist/resources/prompts/runtime/execution-with-tool-evidence-retry.md +1 -0
- package/dist/resources/prompts/runtime/execution-with-tool-evidence.md +1 -0
- package/dist/resources/prompts/runtime/invalid-tool-selection-recovery.md +1 -0
- package/dist/resources/prompts/runtime/memory-manager.md +31 -0
- package/dist/resources/prompts/runtime/memory-mutation-reconciliation.md +22 -0
- package/dist/resources/prompts/runtime/slash-command-skill.md +6 -0
- package/dist/resources/prompts/runtime/strict-tool-json.md +1 -0
- package/dist/resources/prompts/runtime/workspace-boundary-guidance.md +3 -0
- package/dist/resources/prompts/runtime/workspace-relative-path.md +1 -0
- package/dist/resources/prompts/runtime/write-todos-descriptive-content.md +1 -0
- package/dist/resources/prompts/runtime/write-todos-full-entry.md +1 -0
- package/dist/resources/prompts/runtime/write-todos-non-empty-initial-list.md +1 -0
- package/dist/resources/tools/_runtime_tool_helpers.mjs +152 -0
- package/dist/resources/tools/cancel_request.mjs +21 -0
- package/dist/resources/tools/fetch_url.mjs +23 -0
- package/dist/resources/tools/http_request.mjs +30 -0
- package/dist/resources/tools/inspect_approvals.mjs +27 -0
- package/dist/resources/tools/inspect_artifacts.mjs +21 -0
- package/dist/resources/tools/inspect_events.mjs +21 -0
- package/dist/resources/tools/inspect_requests.mjs +27 -0
- package/dist/resources/tools/inspect_sessions.mjs +21 -0
- package/dist/resources/tools/list_files.mjs +27 -0
- package/dist/resources/tools/read_artifact.mjs +22 -0
- package/dist/resources/tools/request_approval.mjs +27 -0
- package/dist/resources/tools/run_command.mjs +21 -0
- package/dist/resources/tools/schedule_task.mjs +76 -0
- package/dist/resources/tools/search_files.mjs +47 -0
- package/dist/resources/tools/send_message.mjs +23 -0
- package/dist/runtime/adapter/direct-builtin-utility.d.ts +1 -0
- package/dist/runtime/adapter/direct-builtin-utility.js +90 -0
- package/dist/runtime/adapter/flow/execution-context.d.ts +1 -1
- package/dist/runtime/adapter/flow/execution-context.js +1 -1
- package/dist/runtime/adapter/flow/invocation-flow.d.ts +1 -0
- package/dist/runtime/adapter/flow/invocation-flow.js +9 -1
- package/dist/runtime/adapter/flow/invoke-runtime.d.ts +1 -1
- package/dist/runtime/adapter/flow/stream-runtime.d.ts +5 -1
- package/dist/runtime/adapter/flow/stream-runtime.js +556 -35
- package/dist/runtime/adapter/invocation-result.js +3 -2
- package/dist/runtime/adapter/local-tool-invocation.d.ts +1 -1
- package/dist/runtime/adapter/local-tool-invocation.js +28 -4
- package/dist/runtime/adapter/middleware-assembly.js +3 -1
- package/dist/runtime/adapter/model/invocation-request.d.ts +4 -1
- package/dist/runtime/adapter/model/invocation-request.js +138 -16
- package/dist/runtime/adapter/model/message-assembly.js +2 -6
- package/dist/runtime/adapter/model/model-providers.js +103 -5
- package/dist/runtime/adapter/resilience.js +17 -2
- package/dist/runtime/adapter/runtime-adapter-support.d.ts +11 -7
- package/dist/runtime/adapter/runtime-adapter-support.js +39 -5
- package/dist/runtime/adapter/tool/builtin-middleware-tools.d.ts +63 -1
- package/dist/runtime/adapter/tool/builtin-middleware-tools.js +193 -21
- package/dist/runtime/adapter/tool/tool-arguments.d.ts +3 -1
- package/dist/runtime/adapter/tool/tool-arguments.js +52 -17
- package/dist/runtime/adapter/tool-resolution.d.ts +1 -0
- package/dist/runtime/adapter/tool-resolution.js +4 -2
- package/dist/runtime/agent-runtime-adapter.d.ts +27 -0
- package/dist/runtime/agent-runtime-adapter.js +163 -11
- package/dist/runtime/harness/events/event-bus.d.ts +1 -0
- package/dist/runtime/harness/events/event-bus.js +3 -0
- package/dist/runtime/harness/events/event-sink.d.ts +3 -0
- package/dist/runtime/harness/events/event-sink.js +16 -7
- package/dist/runtime/harness/events/streaming.d.ts +18 -1
- package/dist/runtime/harness/events/streaming.js +23 -10
- package/dist/runtime/harness/run/inspection.js +26 -5
- package/dist/runtime/harness/run/stream-run.d.ts +13 -4
- package/dist/runtime/harness/run/stream-run.js +448 -4
- package/dist/runtime/harness/run/surface-semantics.js +7 -34
- package/dist/runtime/harness/system/runtime-memory-manager.d.ts +3 -0
- package/dist/runtime/harness/system/runtime-memory-manager.js +384 -69
- package/dist/runtime/harness/system/runtime-memory-policy.d.ts +20 -1
- package/dist/runtime/harness/system/runtime-memory-policy.js +65 -17
- package/dist/runtime/harness/system/runtime-memory-records.js +100 -0
- package/dist/runtime/harness/system/runtime-memory-sync.js +2 -2
- package/dist/runtime/harness/system/store.d.ts +4 -0
- package/dist/runtime/harness/system/store.js +153 -0
- package/dist/runtime/harness.d.ts +9 -1
- package/dist/runtime/harness.js +141 -7
- package/dist/runtime/maintenance/sqlite-checkpoint-saver.d.ts +8 -3
- package/dist/runtime/maintenance/sqlite-checkpoint-saver.js +152 -53
- package/dist/runtime/parsing/output-parsing.d.ts +10 -2
- package/dist/runtime/parsing/output-parsing.js +223 -16
- package/dist/runtime/parsing/stream-event-parsing.d.ts +7 -0
- package/dist/runtime/parsing/stream-event-parsing.js +51 -1
- package/dist/runtime/scheduling/system-schedule-manager.d.ts +41 -0
- package/dist/runtime/scheduling/system-schedule-manager.js +532 -0
- package/dist/runtime/support/embedding-models.d.ts +1 -1
- package/dist/runtime/support/embedding-models.js +5 -2
- package/dist/runtime/support/runtime-factories.js +1 -1
- package/dist/runtime/support/runtime-layout.d.ts +3 -0
- package/dist/runtime/support/runtime-layout.js +10 -1
- package/dist/runtime/support/runtime-prompts.d.ts +30 -0
- package/dist/runtime/support/runtime-prompts.js +55 -0
- package/dist/runtime/support/vector-stores.d.ts +1 -1
- package/dist/runtime/support/vector-stores.js +5 -2
- package/dist/upstream-events.js +8 -7
- package/dist/utils/bundled-text.d.ts +3 -0
- package/dist/utils/bundled-text.js +25 -0
- package/dist/utils/id.js +3 -2
- package/dist/workspace/agent-binding-compiler.js +53 -13
- package/dist/workspace/object-loader.js +64 -2
- package/dist/workspace/support/workspace-ref-utils.d.ts +2 -1
- package/dist/workspace/support/workspace-ref-utils.js +24 -5
- package/dist/workspace/yaml-object-reader.d.ts +1 -0
- package/dist/workspace/yaml-object-reader.js +95 -17
- package/package.json +11 -5
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
import { AIMessage } from "langchain";
|
|
2
|
+
import { BROWSER_CAPABILITY_DISCLAIMER_RECOVERY_INSTRUCTION, EXECUTION_WITH_TOOL_EVIDENCE_INSTRUCTION, EXECUTION_WITH_TOOL_EVIDENCE_RETRY_INSTRUCTION, INVALID_TOOL_SELECTION_RECOVERY_INSTRUCTION, STRICT_TOOL_JSON_INSTRUCTION, WORKSPACE_RELATIVE_PATH_INSTRUCTION, WRITE_TODOS_DESCRIPTIVE_CONTENT_INSTRUCTION, WRITE_TODOS_FULL_ENTRY_INSTRUCTION, WRITE_TODOS_NON_EMPTY_INITIAL_LIST_INSTRUCTION, } from "../support/runtime-prompts.js";
|
|
3
|
+
export { BROWSER_CAPABILITY_DISCLAIMER_RECOVERY_INSTRUCTION, EXECUTION_WITH_TOOL_EVIDENCE_INSTRUCTION, EXECUTION_WITH_TOOL_EVIDENCE_RETRY_INSTRUCTION, INVALID_TOOL_SELECTION_RECOVERY_INSTRUCTION, STRICT_TOOL_JSON_INSTRUCTION, WORKSPACE_RELATIVE_PATH_INSTRUCTION, WRITE_TODOS_DESCRIPTIVE_CONTENT_INSTRUCTION, WRITE_TODOS_FULL_ENTRY_INSTRUCTION, WRITE_TODOS_NON_EMPTY_INITIAL_LIST_INSTRUCTION, };
|
|
2
4
|
export function sanitizeVisibleText(value) {
|
|
3
5
|
return value
|
|
4
6
|
.replace(/[A-Za-z0-9_]*Middleware\.after_model/g, "")
|
|
@@ -218,6 +220,13 @@ function extractAssistantTextFromMessages(messages) {
|
|
|
218
220
|
if (typeof message !== "object" || !message)
|
|
219
221
|
continue;
|
|
220
222
|
const typed = message;
|
|
223
|
+
const explicitRole = typeof typed.role === "string" ? typed.role.trim().toLowerCase() : undefined;
|
|
224
|
+
if (explicitRole === "assistant" || explicitRole === "ai") {
|
|
225
|
+
const content = extractMessageContent(message);
|
|
226
|
+
if (content)
|
|
227
|
+
return content;
|
|
228
|
+
continue;
|
|
229
|
+
}
|
|
221
230
|
const ids = Array.isArray(typed.id) ? typed.id.filter((item) => typeof item === "string") : [];
|
|
222
231
|
const typeName = ids.at(-1);
|
|
223
232
|
const runtimeType = typeof message._getType === "function"
|
|
@@ -295,11 +304,54 @@ function extractStructuredOutputText(value) {
|
|
|
295
304
|
}
|
|
296
305
|
return readTextContent(typed.content);
|
|
297
306
|
}
|
|
307
|
+
function normalizePotentialLineNumberedDocument(value) {
|
|
308
|
+
return value
|
|
309
|
+
.split("\n")
|
|
310
|
+
.map((line) => line.replace(/^\s*\d+\s+/, ""))
|
|
311
|
+
.join("\n")
|
|
312
|
+
.trim();
|
|
313
|
+
}
|
|
314
|
+
function isLikelySkillDocumentText(value) {
|
|
315
|
+
const normalized = normalizePotentialLineNumberedDocument(value);
|
|
316
|
+
if (!normalized.startsWith("---")) {
|
|
317
|
+
return false;
|
|
318
|
+
}
|
|
319
|
+
const lower = normalized.toLowerCase();
|
|
320
|
+
return (lower.includes("\nname: ") &&
|
|
321
|
+
lower.includes("\ndescription: ") &&
|
|
322
|
+
lower.includes("\n# ") &&
|
|
323
|
+
lower.includes("## workflow"));
|
|
324
|
+
}
|
|
325
|
+
export function containsLikelySkillDocument(value) {
|
|
326
|
+
if (typeof value === "string") {
|
|
327
|
+
return isLikelySkillDocumentText(value);
|
|
328
|
+
}
|
|
329
|
+
if (Array.isArray(value)) {
|
|
330
|
+
return value.some((item) => containsLikelySkillDocument(item));
|
|
331
|
+
}
|
|
332
|
+
if (typeof value === "object" && value) {
|
|
333
|
+
const typed = value;
|
|
334
|
+
if (typed.content !== undefined && containsLikelySkillDocument(typed.content)) {
|
|
335
|
+
return true;
|
|
336
|
+
}
|
|
337
|
+
if (typed.output !== undefined && containsLikelySkillDocument(typed.output)) {
|
|
338
|
+
return true;
|
|
339
|
+
}
|
|
340
|
+
if (typed.messages !== undefined && containsLikelySkillDocument(typed.messages)) {
|
|
341
|
+
return true;
|
|
342
|
+
}
|
|
343
|
+
if (typed.kwargs !== undefined && containsLikelySkillDocument(typed.kwargs)) {
|
|
344
|
+
return true;
|
|
345
|
+
}
|
|
346
|
+
return Object.values(typed).some((item) => containsLikelySkillDocument(item));
|
|
347
|
+
}
|
|
348
|
+
return false;
|
|
349
|
+
}
|
|
298
350
|
export function extractToolFallbackContext(value) {
|
|
299
351
|
if (typeof value !== "object" || !value)
|
|
300
352
|
return "";
|
|
301
353
|
const typed = value;
|
|
302
|
-
const messages = extractToolMessageContents(typed.messages);
|
|
354
|
+
const messages = extractToolMessageContents(typed.messages).filter((message) => !isLikelySkillDocumentText(message));
|
|
303
355
|
if (messages.length > 0)
|
|
304
356
|
return messages.slice(-3).join("\n\n");
|
|
305
357
|
if (typed.output && typeof typed.output === "object") {
|
|
@@ -311,7 +363,7 @@ export function extractToolFallbackContext(value) {
|
|
|
311
363
|
}
|
|
312
364
|
export function extractVisibleOutput(value) {
|
|
313
365
|
const structured = extractStructuredOutputText(value);
|
|
314
|
-
if (structured)
|
|
366
|
+
if (structured && !isLikelySkillDocumentText(structured))
|
|
315
367
|
return structured;
|
|
316
368
|
if (typeof value === "string") {
|
|
317
369
|
const parsed = tryParseJson(value);
|
|
@@ -319,11 +371,13 @@ export function extractVisibleOutput(value) {
|
|
|
319
371
|
if (isLikelyMemoryWriteArgsObject(parsed))
|
|
320
372
|
return "";
|
|
321
373
|
const parsedStructured = extractStructuredOutputText(parsed);
|
|
322
|
-
if (parsedStructured)
|
|
374
|
+
if (parsedStructured && !isLikelySkillDocumentText(parsedStructured))
|
|
323
375
|
return parsedStructured;
|
|
324
376
|
if (isLikelyToolArgsObject(parsed))
|
|
325
377
|
return "";
|
|
326
378
|
}
|
|
379
|
+
if (isLikelySkillDocumentText(value))
|
|
380
|
+
return "";
|
|
327
381
|
return value;
|
|
328
382
|
}
|
|
329
383
|
if (typeof value === "object" && value) {
|
|
@@ -515,10 +569,128 @@ export function isToolCallValidationFailure(error) {
|
|
|
515
569
|
return /Received tool input did not match expected schema/i.test(message) && /(?:→\s*at|at)\s+[\w[\].]+/i.test(message);
|
|
516
570
|
}
|
|
517
571
|
export function isToolCallRecoveryFailure(error) {
|
|
518
|
-
return isToolCallParseFailure(error) ||
|
|
572
|
+
return (isToolCallParseFailure(error) ||
|
|
573
|
+
isToolCallValidationFailure(error) ||
|
|
574
|
+
isRepairableWriteTodosEmptyFailure(error) ||
|
|
575
|
+
isRepairableWriteTodosPlaceholderFailure(error) ||
|
|
576
|
+
isWorkspacePathScopeFailure(error));
|
|
577
|
+
}
|
|
578
|
+
function collectErrorMessages(error) {
|
|
579
|
+
if (!error) {
|
|
580
|
+
return [];
|
|
581
|
+
}
|
|
582
|
+
if (error instanceof Error) {
|
|
583
|
+
const nested = Array.isArray(error.errors)
|
|
584
|
+
? (error.errors ?? []).flatMap((item) => collectErrorMessages(item))
|
|
585
|
+
: [];
|
|
586
|
+
return [error.message, ...nested].filter((value) => typeof value === "string" && value.trim().length > 0);
|
|
587
|
+
}
|
|
588
|
+
if (typeof error === "string" && error.trim().length > 0) {
|
|
589
|
+
return [error];
|
|
590
|
+
}
|
|
591
|
+
if (typeof error === "object") {
|
|
592
|
+
const record = error;
|
|
593
|
+
return [record.message, record.error, record.details].flatMap((item) => collectErrorMessages(item));
|
|
594
|
+
}
|
|
595
|
+
return [];
|
|
596
|
+
}
|
|
597
|
+
export function isWorkspacePathScopeFailure(error) {
|
|
598
|
+
return collectErrorMessages(error).some((message) => /outside the workspace root|workspace-relative path/i.test(message));
|
|
599
|
+
}
|
|
600
|
+
export function isRepairableWriteTodosPlaceholderFailure(error) {
|
|
601
|
+
if (!(error instanceof Error))
|
|
602
|
+
return false;
|
|
603
|
+
const message = error.message.trim();
|
|
604
|
+
if (!message)
|
|
605
|
+
return false;
|
|
606
|
+
return /write_todos/i.test(message) && /descriptive task content|placeholder entries/i.test(message);
|
|
607
|
+
}
|
|
608
|
+
function extractLastUserMessageText(input) {
|
|
609
|
+
if (!Array.isArray(input) && !(typeof input === "object" && input && Array.isArray(input.messages))) {
|
|
610
|
+
return "";
|
|
611
|
+
}
|
|
612
|
+
const messages = Array.isArray(input) ? input : input.messages;
|
|
613
|
+
for (let index = messages.length - 1; index >= 0; index -= 1) {
|
|
614
|
+
const message = messages[index];
|
|
615
|
+
if (typeof message !== "object" || !message)
|
|
616
|
+
continue;
|
|
617
|
+
const typed = message;
|
|
618
|
+
if (typed.role === "user") {
|
|
619
|
+
return extractMessageContent(message).trim();
|
|
620
|
+
}
|
|
621
|
+
const ids = Array.isArray(typed.id) ? typed.id.filter((item) => typeof item === "string") : [];
|
|
622
|
+
const typeName = ids.at(-1);
|
|
623
|
+
const runtimeType = typeof message._getType === "function"
|
|
624
|
+
? message._getType()
|
|
625
|
+
: typeof message.getType === "function"
|
|
626
|
+
? message.getType()
|
|
627
|
+
: undefined;
|
|
628
|
+
if (typeName === "HumanMessage" || runtimeType === "human") {
|
|
629
|
+
return extractMessageContent(message).trim();
|
|
630
|
+
}
|
|
631
|
+
if (typeof typed.kwargs === "object" && typed.kwargs && typed.kwargs.role === "user") {
|
|
632
|
+
return extractMessageContent(message).trim();
|
|
633
|
+
}
|
|
634
|
+
}
|
|
635
|
+
return "";
|
|
636
|
+
}
|
|
637
|
+
function isToolRequiredExecutionPrompt(text) {
|
|
638
|
+
if (!text)
|
|
639
|
+
return false;
|
|
640
|
+
return (/write_todos/i.test(text) ||
|
|
641
|
+
/\b(create|write|edit|read|show|display|append|run|execute|wait|sleep|repeat|loop|file|files|command)\b/i.test(text) ||
|
|
642
|
+
/(创建|写入|读取|显示|追加|执行|运行|等待|重复|文件|命令|步骤)/.test(text));
|
|
643
|
+
}
|
|
644
|
+
function isBrowserOrUrlTask(text) {
|
|
645
|
+
if (!text)
|
|
646
|
+
return false;
|
|
647
|
+
return (/https?:\/\/\S+/i.test(text) ||
|
|
648
|
+
/\b(url|urls|website|websites|web page|webpage|browser|browse|page summary|summari[sz]e.*page|open.*page)\b/i.test(text) ||
|
|
649
|
+
/(网址|链接|网页|网站|页面|浏览器|总结.*网页|总结.*页面|打开.*网页)/.test(text));
|
|
650
|
+
}
|
|
651
|
+
function claimsExecutionWithoutToolEvidence(text) {
|
|
652
|
+
if (!text)
|
|
653
|
+
return false;
|
|
654
|
+
return (/\b(completed|done|created|wrote|written|read|displayed|appended|executed|waited|result|results)\b/i.test(text) ||
|
|
655
|
+
/(已创建|已写入|已读取|已显示|已追加|已执行|已等待|执行结果|状态更新|步骤\s*\d+|文件内容)/.test(text));
|
|
656
|
+
}
|
|
657
|
+
function claimsMissingBrowserCapability(text) {
|
|
658
|
+
if (!text)
|
|
659
|
+
return false;
|
|
660
|
+
return (/\b(i do not have the capability to access external websites|i do not have access to external websites|i cannot access external websites|i can(?:not|'t) browse|i do not have (?:direct )?(?:web|browser|browsing) access|i do not have .*tool.*(?:website|url|browser)|i cannot summarize .* because .*tool.*failed|please provide (?:the )?text content.*i (?:will|can) summarize)\b/i.test(text) ||
|
|
661
|
+
/(我没有直接访问外部网站|我无法直接访问外部网站|我无法访问外部网站|我不能访问外部网站|我无法直接访问外部网站内容|我无法访问网页|请提供文本内容.*我将为您进行总结|我没有.*浏览.*工具|我没有.*网页抓取.*工具|我没有.*访问.*网站.*工具|我无法总结该网页内容,因为.*工具执行失败)/.test(text));
|
|
662
|
+
}
|
|
663
|
+
export function isRetrySafeInvalidToolSelectionError(value) {
|
|
664
|
+
const text = readTextContent(value).trim();
|
|
665
|
+
if (!text)
|
|
666
|
+
return false;
|
|
667
|
+
return /is not a valid tool, try one of \[/i.test(text);
|
|
668
|
+
}
|
|
669
|
+
export function shouldValidateExecutionWithoutToolEvidence(request) {
|
|
670
|
+
const userText = extractLastUserMessageText(request);
|
|
671
|
+
const browserOrUrlTask = isBrowserOrUrlTask(userText);
|
|
672
|
+
return browserOrUrlTask || isToolRequiredExecutionPrompt(userText);
|
|
673
|
+
}
|
|
674
|
+
export function resolveExecutionWithoutToolEvidenceInstruction(request, result) {
|
|
675
|
+
const assistantText = AIMessage.isInstance(result)
|
|
676
|
+
? readTextContent(result.content).trim()
|
|
677
|
+
: extractAssistantTextFromMessages(result?.messages).trim();
|
|
678
|
+
return resolveExecutionWithoutToolEvidenceTextInstruction(request, assistantText, hasToolCalls(result));
|
|
679
|
+
}
|
|
680
|
+
export function resolveExecutionWithoutToolEvidenceTextInstruction(request, assistantText, toolCallEvidence = false) {
|
|
681
|
+
const userText = extractLastUserMessageText(request);
|
|
682
|
+
const browserOrUrlTask = isBrowserOrUrlTask(userText);
|
|
683
|
+
if (!shouldValidateExecutionWithoutToolEvidence(request)) {
|
|
684
|
+
return null;
|
|
685
|
+
}
|
|
686
|
+
if (!assistantText || toolCallEvidence) {
|
|
687
|
+
return null;
|
|
688
|
+
}
|
|
689
|
+
if (browserOrUrlTask && claimsMissingBrowserCapability(assistantText)) {
|
|
690
|
+
return BROWSER_CAPABILITY_DISCLAIMER_RECOVERY_INSTRUCTION;
|
|
691
|
+
}
|
|
692
|
+
return claimsExecutionWithoutToolEvidence(assistantText) ? EXECUTION_WITH_TOOL_EVIDENCE_INSTRUCTION : null;
|
|
519
693
|
}
|
|
520
|
-
export const STRICT_TOOL_JSON_INSTRUCTION = "When calling tools, return only the tool call itself. The arguments must be a pure JSON object with no explanatory text before or after it.";
|
|
521
|
-
export const WRITE_TODOS_FULL_ENTRY_INSTRUCTION = "When calling write_todos, every todo item must include both content and status. Do not send status-only updates. Retry by resending the full todo entry with the original content preserved.";
|
|
522
694
|
export function isRepairableWriteTodosContentFailure(error) {
|
|
523
695
|
if (!(error instanceof Error))
|
|
524
696
|
return false;
|
|
@@ -527,10 +699,27 @@ export function isRepairableWriteTodosContentFailure(error) {
|
|
|
527
699
|
return false;
|
|
528
700
|
return /write_todos/i.test(message) && /todos\[\d+\]\.content/i.test(message);
|
|
529
701
|
}
|
|
702
|
+
export function isRepairableWriteTodosEmptyFailure(error) {
|
|
703
|
+
if (!(error instanceof Error))
|
|
704
|
+
return false;
|
|
705
|
+
const message = error.message.trim();
|
|
706
|
+
if (!message)
|
|
707
|
+
return false;
|
|
708
|
+
return /write_todos/i.test(message) && /Initial write_todos call cannot use an empty todo list/i.test(message);
|
|
709
|
+
}
|
|
530
710
|
export function resolveToolCallRecoveryInstruction(error) {
|
|
711
|
+
if (isRepairableWriteTodosEmptyFailure(error)) {
|
|
712
|
+
return WRITE_TODOS_NON_EMPTY_INITIAL_LIST_INSTRUCTION;
|
|
713
|
+
}
|
|
531
714
|
if (isRepairableWriteTodosContentFailure(error)) {
|
|
532
715
|
return WRITE_TODOS_FULL_ENTRY_INSTRUCTION;
|
|
533
716
|
}
|
|
717
|
+
if (isRepairableWriteTodosPlaceholderFailure(error)) {
|
|
718
|
+
return WRITE_TODOS_DESCRIPTIVE_CONTENT_INSTRUCTION;
|
|
719
|
+
}
|
|
720
|
+
if (isWorkspacePathScopeFailure(error)) {
|
|
721
|
+
return WORKSPACE_RELATIVE_PATH_INSTRUCTION;
|
|
722
|
+
}
|
|
534
723
|
if (isToolCallRecoveryFailure(error)) {
|
|
535
724
|
return STRICT_TOOL_JSON_INSTRUCTION;
|
|
536
725
|
}
|
|
@@ -557,18 +746,36 @@ export function wrapResolvedModel(value) {
|
|
|
557
746
|
const member = Reflect.get(currentTarget, prop, receiver);
|
|
558
747
|
if (prop === "invoke" && typeof member === "function") {
|
|
559
748
|
return async (...args) => {
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
749
|
+
let activeArgs = [...args];
|
|
750
|
+
for (let attempt = 0; attempt < 3; attempt += 1) {
|
|
751
|
+
try {
|
|
752
|
+
const normalized = normalizeAgentMessage(await member.apply(currentTarget, activeArgs));
|
|
753
|
+
const executionRecoveryInstruction = resolveExecutionWithoutToolEvidenceInstruction(activeArgs[0], normalized);
|
|
754
|
+
if (!executionRecoveryInstruction) {
|
|
755
|
+
return normalized;
|
|
756
|
+
}
|
|
757
|
+
if (attempt === 2) {
|
|
758
|
+
throw new Error("Model claimed task execution without any tool calls after repeated recovery attempts. Refusing to treat that response as a successful execution.");
|
|
759
|
+
}
|
|
760
|
+
const nextInstruction = attempt === 0
|
|
761
|
+
? executionRecoveryInstruction
|
|
762
|
+
: EXECUTION_WITH_TOOL_EVIDENCE_RETRY_INSTRUCTION;
|
|
763
|
+
activeArgs = [...activeArgs];
|
|
764
|
+
activeArgs[0] = appendToolRecoveryInstruction(activeArgs[0], nextInstruction);
|
|
765
|
+
}
|
|
766
|
+
catch (error) {
|
|
767
|
+
const recoveryInstruction = resolveToolCallRecoveryInstruction(error);
|
|
768
|
+
if (!recoveryInstruction) {
|
|
769
|
+
throw error;
|
|
770
|
+
}
|
|
771
|
+
if (attempt === 2) {
|
|
772
|
+
throw error;
|
|
773
|
+
}
|
|
774
|
+
activeArgs = [...activeArgs];
|
|
775
|
+
activeArgs[0] = appendToolRecoveryInstruction(activeArgs[0], recoveryInstruction);
|
|
567
776
|
}
|
|
568
|
-
const retryArgs = [...args];
|
|
569
|
-
retryArgs[0] = appendToolRecoveryInstruction(retryArgs[0], recoveryInstruction);
|
|
570
|
-
return normalizeAgentMessage(await member.apply(currentTarget, retryArgs));
|
|
571
777
|
}
|
|
778
|
+
throw new Error("Model invocation retry loop exited unexpectedly.");
|
|
572
779
|
};
|
|
573
780
|
}
|
|
574
781
|
if ((prop === "bindTools" || prop === "withConfig" || prop === "withStructuredOutput") && typeof member === "function") {
|
|
@@ -1,6 +1,10 @@
|
|
|
1
|
+
import type { RequestExecutionStep } from "../../contracts/types.js";
|
|
1
2
|
export type RuntimeStreamChunk = {
|
|
2
3
|
kind: "upstream-event";
|
|
3
4
|
event: unknown;
|
|
5
|
+
} | {
|
|
6
|
+
kind: "commentary";
|
|
7
|
+
content: string;
|
|
4
8
|
} | {
|
|
5
9
|
kind: "content";
|
|
6
10
|
content: string;
|
|
@@ -15,6 +19,9 @@ export type RuntimeStreamChunk = {
|
|
|
15
19
|
toolName: string;
|
|
16
20
|
output: unknown;
|
|
17
21
|
isError?: boolean;
|
|
22
|
+
} | {
|
|
23
|
+
kind: "profile";
|
|
24
|
+
step: RequestExecutionStep;
|
|
18
25
|
};
|
|
19
26
|
export declare function extractTerminalStreamOutput(event: unknown): string;
|
|
20
27
|
export declare function extractReasoningStreamOutput(event: unknown): string;
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { isLowSignalTodoContent } from "../adapter/runtime-adapter-support.js";
|
|
1
2
|
import { extractReasoningText, extractVisibleOutput, hasToolCalls, readTextContent } from "./output-parsing.js";
|
|
2
3
|
function parseMaybeJson(value) {
|
|
3
4
|
const trimmed = value.trim();
|
|
@@ -11,6 +12,22 @@ function parseMaybeJson(value) {
|
|
|
11
12
|
return value;
|
|
12
13
|
}
|
|
13
14
|
}
|
|
15
|
+
function unwrapToolMessageOutput(value) {
|
|
16
|
+
if (typeof value !== "object" || !value || Array.isArray(value)) {
|
|
17
|
+
return value;
|
|
18
|
+
}
|
|
19
|
+
const record = value;
|
|
20
|
+
if (typeof record.content === "string") {
|
|
21
|
+
return parseMaybeJson(record.content);
|
|
22
|
+
}
|
|
23
|
+
const kwargs = typeof record.kwargs === "object" && record.kwargs !== null
|
|
24
|
+
? record.kwargs
|
|
25
|
+
: undefined;
|
|
26
|
+
if (typeof kwargs?.content === "string") {
|
|
27
|
+
return parseMaybeJson(kwargs.content);
|
|
28
|
+
}
|
|
29
|
+
return value;
|
|
30
|
+
}
|
|
14
31
|
function readToolErrorText(value) {
|
|
15
32
|
if (typeof value === "string") {
|
|
16
33
|
return value;
|
|
@@ -36,6 +53,31 @@ function isErrorLikeToolOutput(value) {
|
|
|
36
53
|
}
|
|
37
54
|
return /(^|\b)(error|exception|failed|failure|denied|timed out|timeout|not permitted|eperm|eacces)(\b|:)/i.test(message);
|
|
38
55
|
}
|
|
56
|
+
function isEmptyInitialWriteTodosResult(value) {
|
|
57
|
+
if (typeof value !== "object" || !value || Array.isArray(value)) {
|
|
58
|
+
return false;
|
|
59
|
+
}
|
|
60
|
+
const typed = value;
|
|
61
|
+
if (typeof typed.summary === "object" && typed.summary && Array.isArray(typed.summary.items)) {
|
|
62
|
+
return (typed.summary.items).length === 0;
|
|
63
|
+
}
|
|
64
|
+
if (typeof typed.update === "object" && typed.update && Array.isArray(typed.update.todos)) {
|
|
65
|
+
return (typed.update.todos).length === 0;
|
|
66
|
+
}
|
|
67
|
+
return false;
|
|
68
|
+
}
|
|
69
|
+
function hasLowSignalInitialWriteTodos(value) {
|
|
70
|
+
if (typeof value !== "object" || !value || Array.isArray(value)) {
|
|
71
|
+
return false;
|
|
72
|
+
}
|
|
73
|
+
const typed = value;
|
|
74
|
+
const items = typeof typed.summary === "object" && typed.summary && Array.isArray(typed.summary.items)
|
|
75
|
+
? (typed.summary.items ?? [])
|
|
76
|
+
: typeof typed.update === "object" && typed.update && Array.isArray(typed.update.todos)
|
|
77
|
+
? (typed.update.todos ?? [])
|
|
78
|
+
: [];
|
|
79
|
+
return items.length > 0 && items.every((item) => typeof item?.content === "string" && isLowSignalTodoContent(item.content));
|
|
80
|
+
}
|
|
39
81
|
export function extractTerminalStreamOutput(event) {
|
|
40
82
|
if (typeof event !== "object" || !event)
|
|
41
83
|
return "";
|
|
@@ -93,7 +135,15 @@ export function extractToolResult(event) {
|
|
|
93
135
|
return null;
|
|
94
136
|
}
|
|
95
137
|
const rawOutput = isToolError ? typed.data?.error ?? typed.data?.output : typed.data?.output;
|
|
96
|
-
const normalizedOutput = typeof rawOutput === "string"
|
|
138
|
+
const normalizedOutput = typeof rawOutput === "string"
|
|
139
|
+
? parseMaybeJson(rawOutput)
|
|
140
|
+
: unwrapToolMessageOutput(rawOutput);
|
|
141
|
+
if (!isToolError && toolName === "write_todos" && isEmptyInitialWriteTodosResult(normalizedOutput)) {
|
|
142
|
+
throw new Error("Error invoking tool 'write_todos' with kwargs {\"todos\":[]} with error: Error: Initial write_todos call cannot use an empty todo list. Send the concrete task steps with both content and status.");
|
|
143
|
+
}
|
|
144
|
+
if (!isToolError && toolName === "write_todos" && hasLowSignalInitialWriteTodos(normalizedOutput)) {
|
|
145
|
+
throw new Error("Error invoking tool 'write_todos' with placeholder todo content with error: Error: Initial write_todos call must use descriptive task content. Do not use placeholder entries like '1', '2', or 'step 1'.");
|
|
146
|
+
}
|
|
97
147
|
return {
|
|
98
148
|
toolName,
|
|
99
149
|
output: normalizedOutput,
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import type { RuntimeScheduleManageInput, RuntimeScheduleManageResult, RuntimeScheduleManager, RuntimeScheduleRecord } from "../../contracts/types.js";
|
|
2
|
+
type CommandResult = {
|
|
3
|
+
stdout: string;
|
|
4
|
+
stderr: string;
|
|
5
|
+
exitCode: number;
|
|
6
|
+
};
|
|
7
|
+
type CommandRunner = (command: string, args: string[], options?: {
|
|
8
|
+
input?: string;
|
|
9
|
+
}) => Promise<CommandResult>;
|
|
10
|
+
type SystemScheduleManagerOptions = {
|
|
11
|
+
workspaceRoot: string;
|
|
12
|
+
runtimeRoot: string;
|
|
13
|
+
platform?: NodeJS.Platform;
|
|
14
|
+
nodePath?: string;
|
|
15
|
+
cliPath?: string;
|
|
16
|
+
runCommand?: CommandRunner;
|
|
17
|
+
};
|
|
18
|
+
export declare class SystemScheduleManager implements RuntimeScheduleManager {
|
|
19
|
+
private readonly options;
|
|
20
|
+
private readonly schedulesRoot;
|
|
21
|
+
private readonly platform;
|
|
22
|
+
private readonly nodePath;
|
|
23
|
+
private readonly cliPath;
|
|
24
|
+
private readonly adapter;
|
|
25
|
+
constructor(options: SystemScheduleManagerOptions);
|
|
26
|
+
private manifestPath;
|
|
27
|
+
private ensureSchedulesRoot;
|
|
28
|
+
private writeManifest;
|
|
29
|
+
private toPublicRecord;
|
|
30
|
+
private loadStoredRecord;
|
|
31
|
+
private resolveStatus;
|
|
32
|
+
getSchedule(scheduleId: string): Promise<RuntimeScheduleRecord | null>;
|
|
33
|
+
private listStoredRecords;
|
|
34
|
+
private createSchedule;
|
|
35
|
+
private listSchedules;
|
|
36
|
+
private updateSchedule;
|
|
37
|
+
private deleteSchedule;
|
|
38
|
+
manageSchedule(input: RuntimeScheduleManageInput): Promise<RuntimeScheduleManageResult>;
|
|
39
|
+
describeSchedule(record: RuntimeScheduleRecord): string;
|
|
40
|
+
}
|
|
41
|
+
export {};
|