@capybara-hq/kernel 0.1.0-rc.2 → 0.1.0-rc.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agents/agent-lookup.js +10 -2
- package/dist/agents/agents.service.js +19 -6
- package/dist/agents/definition.d.ts +31 -8
- package/dist/agents/definition.js +193 -17
- package/dist/agents/templates.js +19 -4
- package/dist/catalog/catalog-content.js +4 -1
- package/dist/catalog/claude/agents.js +13 -10
- package/dist/catalog/marketplaces.service.d.ts +1 -1
- package/dist/channels/cards.d.ts +8 -2
- package/dist/channels/cards.js +16 -8
- package/dist/config/schema.js +2 -2
- package/dist/conversations/artifacts.d.ts +1 -1
- package/dist/conversations/artifacts.js +1 -1
- package/dist/conversations/event-log.d.ts +11 -0
- package/dist/conversations/event-log.js +19 -0
- package/dist/conversations/events.d.ts +23 -3
- package/dist/conversations/events.js +26 -14
- package/dist/db/kernel-schema.d.ts +2 -2
- package/dist/evals/recorded-tools.d.ts +27 -1
- package/dist/evals/recorded-tools.js +85 -10
- package/dist/evals/run-replay.d.ts +5 -0
- package/dist/evals/run-replay.js +19 -5
- package/dist/evals/trajectory.d.ts +2 -2
- package/dist/identity/settings.js +1 -1
- package/dist/lifecycle/kernel-lifecycle.js +5 -0
- package/dist/orgs/settings.service.d.ts +2 -2
- package/dist/orgs/settings.service.js +2 -2
- package/dist/runtime/context/build.d.ts +6 -6
- package/dist/runtime/context/build.js +18 -8
- package/dist/runtime/context/claude-tools.d.ts +2 -1
- package/dist/runtime/context/claude-tools.js +9 -10
- package/dist/runtime/context/legacy-text.d.ts +22 -0
- package/dist/runtime/context/legacy-text.js +37 -0
- package/dist/runtime/context/skills.d.ts +29 -11
- package/dist/runtime/context/skills.js +37 -30
- package/dist/runtime/loop.d.ts +1 -1
- package/dist/runtime/model-call.js +1 -1
- package/dist/runtime/run-finish.d.ts +1 -1
- package/dist/runtime/run-queue.d.ts +3 -3
- package/dist/runtime/run-queue.js +2 -2
- package/dist/runtime/run-worker.d.ts +2 -2
- package/dist/runtime/run-worker.js +4 -4
- package/dist/runtime/subagents/definition.d.ts +1 -6
- package/dist/runtime/subagents/definition.js +11 -12
- package/dist/runtime/subagents/dispatch.d.ts +2 -2
- package/dist/runtime/subagents/dispatch.js +2 -2
- package/dist/runtime/subagents/org-agents.js +2 -1
- package/dist/runtime/subagents/roster.d.ts +1 -1
- package/dist/runtime/subagents/roster.js +1 -1
- package/dist/runtime/subagents/skill-fork.d.ts +2 -2
- package/dist/runtime/subagents/skill-fork.js +2 -2
- package/dist/runtime/subagents/subagents.service.d.ts +3 -3
- package/dist/runtime/subagents/subagents.service.js +3 -3
- package/dist/runtime/waits.d.ts +5 -5
- package/dist/runtime/waits.js +5 -5
- package/dist/skills/catalog.d.ts +4 -4
- package/dist/skills/catalog.js +4 -4
- package/dist/skills/changes.service.d.ts +2 -2
- package/dist/skills/changes.service.js +5 -4
- package/dist/skills/invocation-keys.d.ts +1 -1
- package/dist/skills/invocation-keys.js +1 -1
- package/dist/skills/invoke.d.ts +1 -1
- package/dist/skills/invoke.js +5 -4
- package/dist/tools/approvals.service.d.ts +6 -0
- package/dist/tools/approvals.service.js +19 -1
- package/dist/tools/builtin-names.d.ts +73 -0
- package/dist/tools/builtin-names.js +116 -0
- package/dist/tools/builtins/agent.d.ts +7 -7
- package/dist/tools/builtins/agent.js +7 -11
- package/dist/tools/builtins/ask-user.d.ts +1 -1
- package/dist/tools/builtins/ask-user.js +2 -2
- package/dist/tools/builtins/builtin-tools.d.ts +2 -2
- package/dist/tools/builtins/builtin-tools.js +2 -2
- package/dist/tools/builtins/read-tool-output.d.ts +1 -1
- package/dist/tools/builtins/read-tool-output.js +2 -2
- package/dist/tools/builtins/sandbox/bash.d.ts +5 -5
- package/dist/tools/builtins/sandbox/bash.js +31 -28
- package/dist/tools/builtins/sandbox/common.d.ts +3 -3
- package/dist/tools/builtins/sandbox/common.js +2 -2
- package/dist/tools/builtins/sandbox/deliver.d.ts +1 -1
- package/dist/tools/builtins/sandbox/deliver.js +11 -11
- package/dist/tools/builtins/sandbox/edit.d.ts +1 -1
- package/dist/tools/builtins/sandbox/edit.js +41 -30
- package/dist/tools/builtins/sandbox/file-state.d.ts +34 -0
- package/dist/tools/builtins/sandbox/file-state.js +34 -0
- package/dist/tools/builtins/sandbox/glob-match.d.ts +1 -1
- package/dist/tools/builtins/sandbox/glob-match.js +1 -1
- package/dist/tools/builtins/sandbox/glob.d.ts +1 -1
- package/dist/tools/builtins/sandbox/glob.js +4 -4
- package/dist/tools/builtins/sandbox/grep.d.ts +7 -4
- package/dist/tools/builtins/sandbox/grep.js +147 -30
- package/dist/tools/builtins/sandbox/index.d.ts +1 -1
- package/dist/tools/builtins/sandbox/index.js +1 -1
- package/dist/tools/builtins/sandbox/read.d.ts +2 -2
- package/dist/tools/builtins/sandbox/read.js +21 -14
- package/dist/tools/builtins/sandbox/write.d.ts +1 -1
- package/dist/tools/builtins/sandbox/write.js +37 -33
- package/dist/tools/builtins/skill-load.d.ts +3 -3
- package/dist/tools/builtins/skill-load.js +32 -16
- package/dist/tools/builtins/skill-write.d.ts +4 -4
- package/dist/tools/builtins/skill-write.js +10 -10
- package/dist/tools/builtins/tool-search.d.ts +13 -9
- package/dist/tools/builtins/tool-search.js +25 -14
- package/dist/tools/connectors.service.js +4 -4
- package/dist/tools/display-names.d.ts +9 -0
- package/dist/tools/display-names.js +24 -0
- package/dist/tools/drift.js +5 -5
- package/dist/tools/elicitation.js +1 -1
- package/dist/tools/info.d.ts +20 -4
- package/dist/tools/info.js +55 -32
- package/dist/tools/legacy-data.d.ts +34 -0
- package/dist/tools/legacy-data.js +76 -0
- package/dist/tools/legacy-keys.d.ts +51 -0
- package/dist/tools/legacy-keys.js +115 -0
- package/dist/tools/naming.d.ts +1 -5
- package/dist/tools/naming.js +1 -7
- package/dist/tools/outputs.js +1 -1
- package/dist/tools/pipeline.d.ts +13 -7
- package/dist/tools/pipeline.js +97 -39
- package/dist/tools/policy.d.ts +1 -14
- package/dist/tools/policy.js +13 -19
- package/dist/tools/questions.controller.d.ts +1 -1
- package/dist/tools/questions.controller.js +1 -1
- package/dist/tools/questions.service.d.ts +1 -1
- package/dist/tools/registry.d.ts +16 -21
- package/dist/tools/registry.js +29 -37
- package/dist/tools/resources.d.ts +1 -1
- package/dist/tools/resources.js +1 -1
- package/dist/tools/tools.module.js +1 -1
- package/package.json +2 -2
- package/src/migrations/0063_tool_keys_claude_code.sql +220 -0
- package/dist/tools/builtins/sandbox/names.d.ts +0 -7
- package/dist/tools/builtins/sandbox/names.js +0 -20
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import { createHash } from "node:crypto";
|
|
2
2
|
import { MEDIA_LIMITS, } from "@capybara-hq/plugin-sdk";
|
|
3
3
|
import { catalogText, isAlwaysLoaded } from "../../tools/builtins/tool-search.js";
|
|
4
|
-
import {
|
|
4
|
+
import { LEGACY_CATALOG_HEADER, LEGACY_SKILL_TEXTS, usesLegacyToolNames } from "./legacy-text.js";
|
|
5
|
+
import { invokedSkillNames, invokedSkillsText, SKILL_TEXTS, skillsCatalogEvents, snapshotChangeText, snapshotCurrentText, snapshotSystemText, systemSkillsCatalog, } from "./skills.js";
|
|
5
6
|
/**
|
|
6
7
|
* 平台行为规范(模型可见,英文)。短而通用(spec 6 原则 5);不放时间戳、会话 ID 等会变化的内容,
|
|
7
8
|
* 保证同一 agent 版本在所有会话中 system 前缀一致、可命中提示词缓存。改动它会让所有缓存失效。
|
|
@@ -322,7 +323,7 @@ export function summaryText(summary) {
|
|
|
322
323
|
* 由会话事件日志 + agent 定义构建模型请求(纯函数,不做 I/O)。
|
|
323
324
|
* - system:`BEHAVIOR_RULES + "\n\n" + agent.instructions` 一个块,打缓存断点(a sub-agent's log:
|
|
324
325
|
* `BEHAVIOR_RULES`, its preamble and its instructions, all from its `subagent_started`);日志里第一份 `skills_catalog`
|
|
325
|
-
* 快照在任何 `model_call` 之前时,技能目录接在这个块末尾(Ruling M17,见 ./skills.ts);启用
|
|
326
|
+
* 快照在任何 `model_call` 之前时,技能目录接在这个块末尾(Ruling M17,见 ./skills.ts);启用 ToolSearch 时
|
|
326
327
|
* 第二个块是工具目录(见 {@link BuildModelRequestInput.toolSearch});
|
|
327
328
|
* - 之后的 `skills_catalog` 在所在位置渲染为 system 变更提醒;被压缩摘要覆盖的,若摘要时生效的目录与 system 里的
|
|
328
329
|
* 不同,紧随摘要补一条完整的当前目录;
|
|
@@ -488,6 +489,10 @@ export function buildModelRequest(input) {
|
|
|
488
489
|
if (!results.has(k))
|
|
489
490
|
results.set(k, e.payload);
|
|
490
491
|
}
|
|
492
|
+
// System texts naming a builtin: a request whose tools were recorded before the tool rename
|
|
493
|
+
// renders the frozen pre-rename wording, so it rebuilds exactly (tool naming spec §10)
|
|
494
|
+
const legacyNames = usesLegacyToolNames(input.tools ?? []);
|
|
495
|
+
const skillTexts = legacyNames ? LEGACY_SKILL_TEXTS : SKILL_TEXTS;
|
|
491
496
|
// 技能目录(Ruling M17):第一份快照进 system;之后的每份在所在位置追加变更提醒(相对上一份快照)。
|
|
492
497
|
const skillSnaps = skillsCatalogEvents(events);
|
|
493
498
|
const systemSkills = systemSkillsCatalog(events);
|
|
@@ -504,12 +509,12 @@ export function buildModelRequest(input) {
|
|
|
504
509
|
const covered = skillSnaps.filter((e) => e.seq <= after).at(-1);
|
|
505
510
|
// (phase B: plus the current pinned skills and tool-name map when they differ from system's)
|
|
506
511
|
if (covered && covered !== systemSkills) {
|
|
507
|
-
const text = snapshotCurrentText(systemSkills?.payload, covered.payload);
|
|
512
|
+
const text = snapshotCurrentText(systemSkills?.payload, covered.payload, skillTexts);
|
|
508
513
|
if (text !== "")
|
|
509
514
|
messages.push({ role: "system", content: text });
|
|
510
515
|
}
|
|
511
516
|
// phase D: the skills a person invoked in the summarised range, by name (from the log only)
|
|
512
|
-
const invoked = invokedSkillsText(invokedSkillNames(events, after));
|
|
517
|
+
const invoked = invokedSkillsText(invokedSkillNames(events, after), skillTexts);
|
|
513
518
|
if (invoked !== "")
|
|
514
519
|
messages.push({ role: "system", content: invoked });
|
|
515
520
|
}
|
|
@@ -588,7 +593,7 @@ export function buildModelRequest(input) {
|
|
|
588
593
|
break;
|
|
589
594
|
case "skills_catalog":
|
|
590
595
|
if (e !== systemSkills) {
|
|
591
|
-
const text = snapshotChangeText(prevSnapshot.get(e.seq), e.payload);
|
|
596
|
+
const text = snapshotChangeText(prevSnapshot.get(e.seq), e.payload, skillTexts);
|
|
592
597
|
if (text !== "")
|
|
593
598
|
messages.push({ role: "system", content: text });
|
|
594
599
|
}
|
|
@@ -608,7 +613,9 @@ export function buildModelRequest(input) {
|
|
|
608
613
|
: `${BEHAVIOR_RULES}\n\n${agent.instructions}`;
|
|
609
614
|
const system = [
|
|
610
615
|
{
|
|
611
|
-
text: systemSkills
|
|
616
|
+
text: systemSkills
|
|
617
|
+
? `${base}\n\n${snapshotSystemText(systemSkills.payload, skillTexts)}`
|
|
618
|
+
: base,
|
|
612
619
|
cache: true,
|
|
613
620
|
},
|
|
614
621
|
];
|
|
@@ -622,7 +629,10 @@ export function buildModelRequest(input) {
|
|
|
622
629
|
tools = [...sorted.filter((t) => isAlwaysLoaded(t.key)), ...loaded];
|
|
623
630
|
if (deferred.length > 0) {
|
|
624
631
|
catalog = deferred;
|
|
625
|
-
system.push({
|
|
632
|
+
system.push({
|
|
633
|
+
text: catalogText(deferred, legacyNames ? LEGACY_CATALOG_HEADER : undefined),
|
|
634
|
+
cache: true,
|
|
635
|
+
});
|
|
626
636
|
}
|
|
627
637
|
}
|
|
628
638
|
const request = {
|
|
@@ -664,7 +674,7 @@ export function buildModelRequest(input) {
|
|
|
664
674
|
return { request, meta, mediaTokens };
|
|
665
675
|
}
|
|
666
676
|
/**
|
|
667
|
-
* 日志里 `
|
|
677
|
+
* 日志里 `ToolSearch` 加载过的工具 key(全部 `tool_result.loadedTools` 的并集,按首次出现顺序)。
|
|
668
678
|
* 不看压缩摘要的边界:加载过的工具在摘要之后仍保持加载(模型可能凭摘要继续使用它们,且已发送的工具列表只追加)。
|
|
669
679
|
*/
|
|
670
680
|
export function loadedToolKeys(events) {
|
|
@@ -6,6 +6,7 @@
|
|
|
6
6
|
* English, fixed (Decision 15: not tailored to the agent's tools; it says "when it is in your
|
|
7
7
|
* tools" instead). Changing it only affects snapshots written afterwards: a conversation's next
|
|
8
8
|
* run writes a new snapshot announcing the new map, and old snapshots keep their text (phase C
|
|
9
|
-
* changed the Task / Agent line, sub-agents spec §16.5
|
|
9
|
+
* changed the Task / Agent line, sub-agents spec §16.5; the tool-naming change shortened it to the
|
|
10
|
+
* Claude Code names, spec 2026-10-29 §6).
|
|
10
11
|
*/
|
|
11
12
|
export declare const CLAUDE_CODE_TOOL_MAP: string;
|
|
@@ -6,19 +6,18 @@
|
|
|
6
6
|
* English, fixed (Decision 15: not tailored to the agent's tools; it says "when it is in your
|
|
7
7
|
* tools" instead). Changing it only affects snapshots written afterwards: a conversation's next
|
|
8
8
|
* run writes a new snapshot announcing the new map, and old snapshots keep their text (phase C
|
|
9
|
-
* changed the Task / Agent line, sub-agents spec §16.5
|
|
9
|
+
* changed the Task / Agent line, sub-agents spec §16.5; the tool-naming change shortened it to the
|
|
10
|
+
* Claude Code names, spec 2026-10-29 §6).
|
|
10
11
|
*/
|
|
11
12
|
export const CLAUDE_CODE_TOOL_MAP = [
|
|
12
|
-
"Some skills in this conversation were written for Claude Code
|
|
13
|
-
"
|
|
14
|
-
"
|
|
15
|
-
|
|
16
|
-
"- TodoWrite ->
|
|
17
|
-
"-
|
|
18
|
-
"- ToolSearch -> tool_search when it is in your tools",
|
|
19
|
-
"- Task and Agent (sub-agents) -> agent when it is in your tools (subagent_type names one of the types its description lists; model names haiku / sonnet / opus -> fast / standard / capable; SendMessage to a sub-agent -> agent with resume); otherwise not available: do the steps yourself, in order",
|
|
13
|
+
"Some skills in this conversation were written for Claude Code. Its tools Bash, Read, Write, Edit,",
|
|
14
|
+
"Glob, Grep, Skill, AskUserQuestion, ToolSearch and Agent have the same names here, when they are",
|
|
15
|
+
"in your tools. For the others:",
|
|
16
|
+
"- MultiEdit -> several Edit calls",
|
|
17
|
+
"- TodoWrite -> plugin__todo__write when it is in your tools; otherwise keep the task list in your replies",
|
|
18
|
+
"- Task -> Agent; SendMessage to a sub-agent -> Agent with resume; model names haiku / sonnet / opus -> fast / standard / capable",
|
|
20
19
|
"- TaskOutput, TaskStop -> not available",
|
|
21
20
|
"- Any other tool a skill names (for example WebFetch, WebSearch, NotebookEdit, EnterWorktree) -> not available unless one of your tools does the same job",
|
|
22
21
|
// biome-ignore lint/suspicious/noTemplateCurlyInString: the literal Claude Code variable the model reads
|
|
23
|
-
"The sandbox tools exist only when this agent has a sandbox; without them a skill's scripts cannot run. A path such as ${CLAUDE_PLUGIN_ROOT}/skills/<name>/... means /skills/<name>/... after
|
|
22
|
+
"The sandbox tools exist only when this agent has a sandbox; without them a skill's scripts cannot run. A path such as ${CLAUDE_PLUGIN_ROOT}/skills/<name>/... means /skills/<name>/... after Skill has copied that skill into the sandbox.",
|
|
24
23
|
].join("\n");
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import type { SkillTexts } from "./skills.js";
|
|
2
|
+
/**
|
|
3
|
+
* The system texts of a request as the release candidates rendered them, naming the old builtins
|
|
4
|
+
* (`skill_load`, `tool_search`). FROZEN: verbatim copies from `main` at 02b9634b
|
|
5
|
+
* (`runtime/context/skills.ts`, `tools/builtins/tool-search.ts`); never edit them. A request whose
|
|
6
|
+
* tools hold an old builtin key (a recording made before the rename) is rebuilt with these, so it
|
|
7
|
+
* reconstructs with no `system_hash` drift (tool naming spec §10). `check:terms` exempts this file.
|
|
8
|
+
*
|
|
9
|
+
* The skills texts (`skills.ts`) naming `skill_load`.
|
|
10
|
+
*/
|
|
11
|
+
export declare const LEGACY_SKILL_TEXTS: SkillTexts;
|
|
12
|
+
/** The tool catalog header (`tools/builtins/tool-search.ts` `CATALOG_HEADER`) naming `tool_search`. */
|
|
13
|
+
export declare const LEGACY_CATALOG_HEADER: string;
|
|
14
|
+
/**
|
|
15
|
+
* Was this request's tool list recorded before the rename? True when one of its tool keys is a
|
|
16
|
+
* release-candidate builtin name (the run's tools, as the request carries them). Every request
|
|
17
|
+
* that renders one of these texts offers the tool it names (`skill_load` whenever the log has a
|
|
18
|
+
* skills catalog or an invocation, `tool_search` with a tool catalog), so the tools decide it.
|
|
19
|
+
*/
|
|
20
|
+
export declare function usesLegacyToolNames(tools: readonly {
|
|
21
|
+
key: string;
|
|
22
|
+
}[]): boolean;
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import { isLegacyBuiltinKey } from "../../tools/legacy-keys.js";
|
|
2
|
+
/**
|
|
3
|
+
* The system texts of a request as the release candidates rendered them, naming the old builtins
|
|
4
|
+
* (`skill_load`, `tool_search`). FROZEN: verbatim copies from `main` at 02b9634b
|
|
5
|
+
* (`runtime/context/skills.ts`, `tools/builtins/tool-search.ts`); never edit them. A request whose
|
|
6
|
+
* tools hold an old builtin key (a recording made before the rename) is rebuilt with these, so it
|
|
7
|
+
* reconstructs with no `system_hash` drift (tool naming spec §10). `check:terms` exempts this file.
|
|
8
|
+
*
|
|
9
|
+
* The skills texts (`skills.ts`) naming `skill_load`.
|
|
10
|
+
*/
|
|
11
|
+
export const LEGACY_SKILL_TEXTS = Object.freeze({
|
|
12
|
+
skillsCatalogHeader: "Skills are available in this conversation. A skill is a set of instructions, sometimes with " +
|
|
13
|
+
"scripts or other files, for a specific kind of task. When a task matches a skill's description, " +
|
|
14
|
+
"call skill_load with the skill's name to read its instructions before you start; do not guess " +
|
|
15
|
+
"what a skill says. Available skills:",
|
|
16
|
+
newSkills: "New skills (call skill_load with the name to use one):",
|
|
17
|
+
updatedSkills: "Updated skills (call skill_load again before relying on earlier instructions):",
|
|
18
|
+
currentSkills: "Skills available in this conversation now (this replaces any earlier list of skills; call " +
|
|
19
|
+
"skill_load with a name to read a skill's instructions):",
|
|
20
|
+
invokedSkills: (names) => `Skills the user invoked earlier in this conversation: ${names.join(", ")}. Call skill_load with a name to read its instructions again.`,
|
|
21
|
+
pinnedSkillsHeader: "Pinned skills: the owner of this agent pinned these skills, so their instructions apply " +
|
|
22
|
+
"throughout this conversation. Follow them without calling skill_load; call skill_load " +
|
|
23
|
+
"only to copy a pinned skill's files into the sandbox.",
|
|
24
|
+
});
|
|
25
|
+
/** The tool catalog header (`tools/builtins/tool-search.ts` `CATALOG_HEADER`) naming `tool_search`. */
|
|
26
|
+
export const LEGACY_CATALOG_HEADER = "More tools are available but not loaded. To use one, first call tool_search with keywords; " +
|
|
27
|
+
"it returns the full definitions and loads the matching tools for your next step. " +
|
|
28
|
+
"Calling a tool that is not loaded returns an error. Tool catalog:";
|
|
29
|
+
/**
|
|
30
|
+
* Was this request's tool list recorded before the rename? True when one of its tool keys is a
|
|
31
|
+
* release-candidate builtin name (the run's tools, as the request carries them). Every request
|
|
32
|
+
* that renders one of these texts offers the tool it names (`skill_load` whenever the log has a
|
|
33
|
+
* skills catalog or an invocation, `tool_search` with a tool catalog), so the tools decide it.
|
|
34
|
+
*/
|
|
35
|
+
export function usesLegacyToolNames(tools) {
|
|
36
|
+
return tools.some((t) => isLegacyBuiltinKey(t.key));
|
|
37
|
+
}
|
|
@@ -13,14 +13,32 @@ export type PinnedSkill = NonNullable<SkillsSnapshot["pinned"]>[number];
|
|
|
13
13
|
export type SkillsCatalogEvent = Extract<ConversationEvent, {
|
|
14
14
|
type: "skills_catalog";
|
|
15
15
|
}>;
|
|
16
|
-
/**
|
|
17
|
-
|
|
16
|
+
/**
|
|
17
|
+
* The model-visible skills texts that name the skill-loading builtin. A request recorded before the
|
|
18
|
+
* tool rename renders {@link LEGACY_SKILL_TEXTS} instead (`./legacy-text.ts`, chosen from the
|
|
19
|
+
* request's tools by `usesLegacyToolNames`), so its system text stays as it was sent.
|
|
20
|
+
*/
|
|
21
|
+
export interface SkillTexts {
|
|
22
|
+
/** The header of the first catalog (in the system cache segment). */
|
|
23
|
+
skillsCatalogHeader: string;
|
|
24
|
+
/** The heading of the added skills in a change notice. */
|
|
25
|
+
newSkills: string;
|
|
26
|
+
/** The heading of the updated skills in a change notice. */
|
|
27
|
+
updatedSkills: string;
|
|
28
|
+
/** The heading of the current catalog after a compaction summary. */
|
|
29
|
+
currentSkills: string;
|
|
30
|
+
/** The line restored after a compaction summary for the invoked skills (`names` non-empty). */
|
|
31
|
+
invokedSkills: (names: readonly string[]) => string;
|
|
32
|
+
/** The header of the pinned skills in the system cache segment. */
|
|
33
|
+
pinnedSkillsHeader: string;
|
|
34
|
+
}
|
|
35
|
+
export declare const SKILL_TEXTS: SkillTexts;
|
|
18
36
|
/** 目录开头的说明(system 缓存段里的第一份目录)。 */
|
|
19
37
|
export declare const SKILLS_CATALOG_HEADER: string;
|
|
20
|
-
/** 目录里每个技能描述最多的码点数(超出确定地截断;`
|
|
38
|
+
/** 目录里每个技能描述最多的码点数(超出确定地截断;`Skill` 仍返回完整正文)。 */
|
|
21
39
|
export declare const CATALOG_DESCRIPTION_MAX_CHARS = 300;
|
|
22
40
|
/** 第一份目录(进 system 缓存段),按名字排序。 */
|
|
23
|
-
export declare function skillsCatalogText(skills: readonly CatalogSkill[]): string;
|
|
41
|
+
export declare function skillsCatalogText(skills: readonly CatalogSkill[], texts?: SkillTexts): string;
|
|
24
42
|
/** 两份快照是否相同(按 id、版本、名字、描述与来源)。顺序无关。 */
|
|
25
43
|
export declare function sameSkills(a: readonly CatalogSkill[], b: readonly CatalogSkill[]): boolean;
|
|
26
44
|
/**
|
|
@@ -41,14 +59,14 @@ export declare function sameSnapshot(a: SkillsSnapshot, b: SkillsSnapshot): bool
|
|
|
41
59
|
* 试用草稿被拒绝 / 批准了别人的同号版本时,内容变了而版本号可能不变)。
|
|
42
60
|
* `prev` 为上一份快照(没有为空)。
|
|
43
61
|
*/
|
|
44
|
-
export declare function skillsChangeText(prev: readonly CatalogSkill[], next: readonly CatalogSkill[], pinnedIds?: ReadonlySet<string
|
|
62
|
+
export declare function skillsChangeText(prev: readonly CatalogSkill[], next: readonly CatalogSkill[], pinnedIds?: ReadonlySet<string>, texts?: SkillTexts): string;
|
|
45
63
|
/** 压缩摘要之后补上的「当前目录」(与 system 里的第一份不同时):完整列出,替代之前的目录与提醒。 */
|
|
46
|
-
export declare function skillsCurrentText(skills: readonly CatalogSkill[]): string;
|
|
64
|
+
export declare function skillsCurrentText(skills: readonly CatalogSkill[], texts?: SkillTexts): string;
|
|
47
65
|
/**
|
|
48
66
|
* The line restored after a compaction summary whose range holds inline skill invocations
|
|
49
67
|
* (`names`: distinct, code point order); empty for none. Bodies are not re-injected.
|
|
50
68
|
*/
|
|
51
|
-
export declare function invokedSkillsText(names: readonly string[]): string;
|
|
69
|
+
export declare function invokedSkillsText(names: readonly string[], texts?: SkillTexts): string;
|
|
52
70
|
/** The distinct names (code point order) of the inline invocations in `events` up to `upToSeq`. */
|
|
53
71
|
export declare function invokedSkillNames(events: readonly ConversationEvent[], upToSeq: number): string[];
|
|
54
72
|
/** A skill a person invoked: the version recorded in their message. */
|
|
@@ -78,7 +96,7 @@ export declare const PINNED_SKILLS_HEADER: string;
|
|
|
78
96
|
/** One pinned skill with its body. */
|
|
79
97
|
export declare function pinnedBlock(p: PinnedSkill): string;
|
|
80
98
|
/** The pinned skills of the system snapshot (non-empty), after the catalog. */
|
|
81
|
-
export declare function pinnedSystemText(pinned: readonly PinnedSkill[]): string;
|
|
99
|
+
export declare function pinnedSystemText(pinned: readonly PinnedSkill[], texts?: SkillTexts): string;
|
|
82
100
|
/**
|
|
83
101
|
* The pinned change notice between two snapshots ({@link samePinned} false): each entry that is new
|
|
84
102
|
* or has another version or source, with its whole body; then the names of the removed ones.
|
|
@@ -94,12 +112,12 @@ export declare function toolMapChangeText(next: string | undefined): string;
|
|
|
94
112
|
* nothing else differs: logs before phase B render exactly as before), the pinned change, the
|
|
95
113
|
* tool-name map change; joined by blank lines.
|
|
96
114
|
*/
|
|
97
|
-
export declare function snapshotChangeText(prev: SkillsSnapshot | undefined, next: SkillsSnapshot): string;
|
|
115
|
+
export declare function snapshotChangeText(prev: SkillsSnapshot | undefined, next: SkillsSnapshot, texts?: SkillTexts): string;
|
|
98
116
|
/**
|
|
99
117
|
* What follows a compaction summary when the covered snapshot is not the system one: today's
|
|
100
118
|
* current catalog (when the skills differ from the system snapshot's), the current pinned skills
|
|
101
119
|
* (when they differ), the tool-name map (when it differs); joined by blank lines, "" for nothing.
|
|
102
120
|
*/
|
|
103
|
-
export declare function snapshotCurrentText(system: SkillsSnapshot | undefined, covered: SkillsSnapshot): string;
|
|
121
|
+
export declare function snapshotCurrentText(system: SkillsSnapshot | undefined, covered: SkillsSnapshot, texts?: SkillTexts): string;
|
|
104
122
|
/** The system snapshot's text after the agent's instructions: catalog, pinned skills, tool map. */
|
|
105
|
-
export declare function snapshotSystemText(s: SkillsSnapshot): string;
|
|
123
|
+
export declare function snapshotSystemText(s: SkillsSnapshot, texts?: SkillTexts): string;
|
|
@@ -1,13 +1,23 @@
|
|
|
1
|
-
|
|
2
|
-
export const
|
|
1
|
+
import { SKILL_LOAD } from "../../tools/builtin-names.js";
|
|
2
|
+
export const SKILL_TEXTS = Object.freeze({
|
|
3
|
+
skillsCatalogHeader: "Skills are available in this conversation. A skill is a set of instructions, sometimes with " +
|
|
4
|
+
"scripts or other files, for a specific kind of task. When a task matches a skill's description, " +
|
|
5
|
+
`call ${SKILL_LOAD} with the skill's name to read its instructions before you start; do not guess ` +
|
|
6
|
+
"what a skill says. Available skills:",
|
|
7
|
+
newSkills: `New skills (call ${SKILL_LOAD} with the name to use one):`,
|
|
8
|
+
updatedSkills: `Updated skills (call ${SKILL_LOAD} again before relying on earlier instructions):`,
|
|
9
|
+
currentSkills: "Skills available in this conversation now (this replaces any earlier list of skills; call " +
|
|
10
|
+
`${SKILL_LOAD} with a name to read a skill's instructions):`,
|
|
11
|
+
invokedSkills: (names) => `Skills the user invoked earlier in this conversation: ${names.join(", ")}. Call ${SKILL_LOAD} with a name to read its instructions again.`,
|
|
12
|
+
pinnedSkillsHeader: "Pinned skills: the owner of this agent pinned these skills, so their instructions apply " +
|
|
13
|
+
`throughout this conversation. Follow them without calling ${SKILL_LOAD}; call ${SKILL_LOAD} ` +
|
|
14
|
+
"only to copy a pinned skill's files into the sandbox.",
|
|
15
|
+
});
|
|
3
16
|
/** 目录开头的说明(system 缓存段里的第一份目录)。 */
|
|
4
|
-
export const SKILLS_CATALOG_HEADER =
|
|
5
|
-
"scripts or other files, for a specific kind of task. When a task matches a skill's description, " +
|
|
6
|
-
`call ${SKILL_LOAD} with the skill's name to read its instructions before you start; do not guess ` +
|
|
7
|
-
"what a skill says. Available skills:";
|
|
17
|
+
export const SKILLS_CATALOG_HEADER = SKILL_TEXTS.skillsCatalogHeader;
|
|
8
18
|
/** 按码点比较名字(与区域设置无关,结果确定)。 */
|
|
9
19
|
const byName = (a, b) => a.name < b.name ? -1 : a.name > b.name ? 1 : 0;
|
|
10
|
-
/** 目录里每个技能描述最多的码点数(超出确定地截断;`
|
|
20
|
+
/** 目录里每个技能描述最多的码点数(超出确定地截断;`Skill` 仍返回完整正文)。 */
|
|
11
21
|
export const CATALOG_DESCRIPTION_MAX_CHARS = 300;
|
|
12
22
|
/** 折叠成一行,按码点截到 {@link CATALOG_DESCRIPTION_MAX_CHARS}。 */
|
|
13
23
|
function shortDescription(d) {
|
|
@@ -21,8 +31,8 @@ function shortDescription(d) {
|
|
|
21
31
|
const line = (s) => `- ${s.name}: ${shortDescription(s.description)}`;
|
|
22
32
|
const lines = (skills) => [...skills].sort(byName).map(line).join("\n");
|
|
23
33
|
/** 第一份目录(进 system 缓存段),按名字排序。 */
|
|
24
|
-
export function skillsCatalogText(skills) {
|
|
25
|
-
return `${
|
|
34
|
+
export function skillsCatalogText(skills, texts = SKILL_TEXTS) {
|
|
35
|
+
return `${texts.skillsCatalogHeader}\n${lines(skills)}`;
|
|
26
36
|
}
|
|
27
37
|
/** 两份快照是否相同(按 id、版本、名字、描述与来源)。顺序无关。 */
|
|
28
38
|
export function sameSkills(a, b) {
|
|
@@ -66,7 +76,7 @@ export function sameSnapshot(a, b) {
|
|
|
66
76
|
/**
|
|
67
77
|
* The catalog differences between two snapshots. `pinnedIds` (the next snapshot's pinned ids, phase
|
|
68
78
|
* B) are left out of `updated`: a pinned skill's new body is rendered by {@link pinnedChangeText},
|
|
69
|
-
* and the pinned header says not to call `
|
|
79
|
+
* and the pinned header says not to call `Skill` for it.
|
|
70
80
|
*/
|
|
71
81
|
function catalogChanges(prev, next, pinnedIds) {
|
|
72
82
|
const before = new Map(prev.map((s) => [s.id, s]));
|
|
@@ -86,14 +96,14 @@ function catalogChanges(prev, next, pinnedIds) {
|
|
|
86
96
|
* 试用草稿被拒绝 / 批准了别人的同号版本时,内容变了而版本号可能不变)。
|
|
87
97
|
* `prev` 为上一份快照(没有为空)。
|
|
88
98
|
*/
|
|
89
|
-
export function skillsChangeText(prev, next, pinnedIds) {
|
|
99
|
+
export function skillsChangeText(prev, next, pinnedIds, texts = SKILL_TEXTS) {
|
|
90
100
|
const { added, updated, removed } = catalogChanges(prev, next, pinnedIds);
|
|
91
101
|
const parts = ["The skills available in this conversation have changed."];
|
|
92
102
|
if (added.length > 0) {
|
|
93
|
-
parts.push(
|
|
103
|
+
parts.push(`${texts.newSkills}\n${lines(added)}`);
|
|
94
104
|
}
|
|
95
105
|
if (updated.length > 0) {
|
|
96
|
-
parts.push(
|
|
106
|
+
parts.push(`${texts.updatedSkills}\n${lines(updated)}`);
|
|
97
107
|
}
|
|
98
108
|
if (removed.length > 0) {
|
|
99
109
|
parts.push(`Removed skills (no longer available; do not use them): ${[...removed]
|
|
@@ -106,22 +116,21 @@ export function skillsChangeText(prev, next, pinnedIds) {
|
|
|
106
116
|
return parts.join("\n\n");
|
|
107
117
|
}
|
|
108
118
|
/** 压缩摘要之后补上的「当前目录」(与 system 里的第一份不同时):完整列出,替代之前的目录与提醒。 */
|
|
109
|
-
export function skillsCurrentText(skills) {
|
|
119
|
+
export function skillsCurrentText(skills, texts = SKILL_TEXTS) {
|
|
110
120
|
if (skills.length === 0) {
|
|
111
121
|
return "No skills are available in this conversation now (this replaces any earlier list of skills).";
|
|
112
122
|
}
|
|
113
|
-
return (
|
|
114
|
-
`${SKILL_LOAD} with a name to read a skill's instructions):\n${lines(skills)}`);
|
|
123
|
+
return `${texts.currentSkills}\n${lines(skills)}`;
|
|
115
124
|
}
|
|
116
125
|
// ---- Skills a person invoked (phase D spec §4.4; model-visible, English) ----
|
|
117
126
|
/**
|
|
118
127
|
* The line restored after a compaction summary whose range holds inline skill invocations
|
|
119
128
|
* (`names`: distinct, code point order); empty for none. Bodies are not re-injected.
|
|
120
129
|
*/
|
|
121
|
-
export function invokedSkillsText(names) {
|
|
130
|
+
export function invokedSkillsText(names, texts = SKILL_TEXTS) {
|
|
122
131
|
if (names.length === 0)
|
|
123
132
|
return "";
|
|
124
|
-
return
|
|
133
|
+
return texts.invokedSkills(names);
|
|
125
134
|
}
|
|
126
135
|
/** The distinct names (code point order) of the inline invocations in `events` up to `upToSeq`. */
|
|
127
136
|
export function invokedSkillNames(events, upToSeq) {
|
|
@@ -180,16 +189,14 @@ export function systemSkillsCatalog(events) {
|
|
|
180
189
|
}
|
|
181
190
|
// ---- Pinned skills and the tool-name map (phase B, spec §9.1, §9.4; model-visible, English) ----
|
|
182
191
|
/** The header of the pinned skills in the system cache segment. */
|
|
183
|
-
export const PINNED_SKILLS_HEADER =
|
|
184
|
-
`throughout this conversation. Follow them without calling ${SKILL_LOAD}; call ${SKILL_LOAD} ` +
|
|
185
|
-
"only to copy a pinned skill's files into the sandbox.";
|
|
192
|
+
export const PINNED_SKILLS_HEADER = SKILL_TEXTS.pinnedSkillsHeader;
|
|
186
193
|
/** One pinned skill with its body. */
|
|
187
194
|
export function pinnedBlock(p) {
|
|
188
195
|
return `<pinned_skill name="${p.name}" version="${p.version}">\n${p.body.trim()}\n</pinned_skill>`;
|
|
189
196
|
}
|
|
190
197
|
/** The pinned skills of the system snapshot (non-empty), after the catalog. */
|
|
191
|
-
export function pinnedSystemText(pinned) {
|
|
192
|
-
return `${
|
|
198
|
+
export function pinnedSystemText(pinned, texts = SKILL_TEXTS) {
|
|
199
|
+
return `${texts.pinnedSkillsHeader}\n\n${pinned.map(pinnedBlock).join("\n\n")}`;
|
|
193
200
|
}
|
|
194
201
|
/**
|
|
195
202
|
* The pinned change notice between two snapshots ({@link samePinned} false): each entry that is new
|
|
@@ -233,7 +240,7 @@ export function toolMapChangeText(next) {
|
|
|
233
240
|
* nothing else differs: logs before phase B render exactly as before), the pinned change, the
|
|
234
241
|
* tool-name map change; joined by blank lines.
|
|
235
242
|
*/
|
|
236
|
-
export function snapshotChangeText(prev, next) {
|
|
243
|
+
export function snapshotChangeText(prev, next, texts = SKILL_TEXTS) {
|
|
237
244
|
const prevSkills = prev?.skills ?? [];
|
|
238
245
|
const pinnedDiff = !samePinned(prev?.pinned, next.pinned);
|
|
239
246
|
const mapDiff = prev?.toolMap !== next.toolMap;
|
|
@@ -247,7 +254,7 @@ export function snapshotChangeText(prev, next) {
|
|
|
247
254
|
: !sameSkills(prevSkills, next.skills);
|
|
248
255
|
const parts = [];
|
|
249
256
|
if (catalogDiff || (!pinnedDiff && !mapDiff)) {
|
|
250
|
-
parts.push(skillsChangeText(prevSkills, next.skills, pinnedIds));
|
|
257
|
+
parts.push(skillsChangeText(prevSkills, next.skills, pinnedIds, texts));
|
|
251
258
|
}
|
|
252
259
|
if (pinnedDiff)
|
|
253
260
|
parts.push(pinnedChangeText(prev?.pinned, next.pinned));
|
|
@@ -260,10 +267,10 @@ export function snapshotChangeText(prev, next) {
|
|
|
260
267
|
* current catalog (when the skills differ from the system snapshot's), the current pinned skills
|
|
261
268
|
* (when they differ), the tool-name map (when it differs); joined by blank lines, "" for nothing.
|
|
262
269
|
*/
|
|
263
|
-
export function snapshotCurrentText(system, covered) {
|
|
270
|
+
export function snapshotCurrentText(system, covered, texts = SKILL_TEXTS) {
|
|
264
271
|
const parts = [];
|
|
265
272
|
if (!sameSkills(system?.skills ?? [], covered.skills)) {
|
|
266
|
-
parts.push(skillsCurrentText(covered.skills));
|
|
273
|
+
parts.push(skillsCurrentText(covered.skills, texts));
|
|
267
274
|
}
|
|
268
275
|
if (!samePinned(system?.pinned, covered.pinned))
|
|
269
276
|
parts.push(pinnedCurrentText(covered.pinned));
|
|
@@ -273,10 +280,10 @@ export function snapshotCurrentText(system, covered) {
|
|
|
273
280
|
return parts.join("\n\n");
|
|
274
281
|
}
|
|
275
282
|
/** The system snapshot's text after the agent's instructions: catalog, pinned skills, tool map. */
|
|
276
|
-
export function snapshotSystemText(s) {
|
|
277
|
-
let text = skillsCatalogText(s.skills);
|
|
283
|
+
export function snapshotSystemText(s, texts = SKILL_TEXTS) {
|
|
284
|
+
let text = skillsCatalogText(s.skills, texts);
|
|
278
285
|
if (s.pinned && s.pinned.length > 0)
|
|
279
|
-
text += `\n\n${pinnedSystemText(s.pinned)}`;
|
|
286
|
+
text += `\n\n${pinnedSystemText(s.pinned, texts)}`;
|
|
280
287
|
if (s.toolMap !== undefined)
|
|
281
288
|
text += `\n\n${s.toolMap}`;
|
|
282
289
|
return text;
|
package/dist/runtime/loop.d.ts
CHANGED
|
@@ -53,7 +53,7 @@ export interface SubagentParent {
|
|
|
53
53
|
otherAgent?: boolean;
|
|
54
54
|
}
|
|
55
55
|
/**
|
|
56
|
-
* 运行在等什么人处理:审批(`approvals` 行)或输入请求(`questions` 行,统一承载 `
|
|
56
|
+
* 运行在等什么人处理:审批(`approvals` 行)或输入请求(`questions` 行,统一承载 `AskUserQuestion`、
|
|
57
57
|
* 插件工具的 `input_required` 与 MCP elicitation)。`expiresAt` 为 ISO 时间。
|
|
58
58
|
* `subagents` (phase C, spec §7.2): sub-agents dispatched in a step are still running; the id is
|
|
59
59
|
* `sa-<runId>-<step>` (no `:`, it is part of BullMQ job ids).
|
|
@@ -128,7 +128,7 @@ async function runStep(deps, input, wrapUp) {
|
|
|
128
128
|
}
|
|
129
129
|
// 每步实时解析(连接器 / 插件状态可能在步骤之间变化),解析结果记在 model_call;收尾调用同样带工具
|
|
130
130
|
// a skills catalog snapshot (Ruling M17; an empty one too) or a person's skill invocation in the
|
|
131
|
-
// log →
|
|
131
|
+
// log → Skill is offered (see skillLoadOffered)
|
|
132
132
|
const resolved = await deps.tools.forAgent(input.orgId, {
|
|
133
133
|
tools: input.agent.tools ?? [],
|
|
134
134
|
subagents: input.agent.subagents,
|
|
@@ -19,7 +19,7 @@ export interface FinishRunArgs {
|
|
|
19
19
|
floorToTrigger?: boolean;
|
|
20
20
|
/**
|
|
21
21
|
* Runs in the transaction once the run is known not to be terminal, before the terminal event:
|
|
22
|
-
* a parent's open `
|
|
22
|
+
* a parent's open `Agent` calls get their results here (sub-agents spec §12, review m1).
|
|
23
23
|
*/
|
|
24
24
|
beforeTerminal?: () => Promise<void>;
|
|
25
25
|
}
|
|
@@ -24,7 +24,7 @@ export declare class RunQueue {
|
|
|
24
24
|
private readonly finisher;
|
|
25
25
|
/** 运行以孤儿结束(标记失败 / 直接中止)后删除它的 checkpoint thread(thread_id = runId)。 */
|
|
26
26
|
private readonly checkpoints;
|
|
27
|
-
/** The run's open `
|
|
27
|
+
/** The run's open `Agent` call results, in the orphan repair's transaction (sub-agents spec §12). */
|
|
28
28
|
private readonly pipeline;
|
|
29
29
|
private readonly events;
|
|
30
30
|
private readonly log;
|
|
@@ -32,11 +32,11 @@ export declare class RunQueue {
|
|
|
32
32
|
constructor(kdb: KernelDb, eventLog: EventLog, lock: Pick<ConversationLock, "holder">, jobs: RunJobs, finisher: Pick<RunFinish, "finishIn">,
|
|
33
33
|
/** 运行以孤儿结束(标记失败 / 直接中止)后删除它的 checkpoint thread(thread_id = runId)。 */
|
|
34
34
|
checkpoints: Pick<KyselyCheckpointSaver, "deleteThread">,
|
|
35
|
-
/** The run's open `
|
|
35
|
+
/** The run's open `Agent` call results, in the orphan repair's transaction (sub-agents spec §12). */
|
|
36
36
|
pipeline: Pick<ToolPipeline, "stopOpenAgentCalls">, events: KernelEvents, log: Pick<Logger, "error" | "warn">, txHost: TransactionHost);
|
|
37
37
|
private get db();
|
|
38
38
|
/**
|
|
39
|
-
* The `beforeTerminal` of an orphan repair: writes the run's open `
|
|
39
|
+
* The `beforeTerminal` of an orphan repair: writes the run's open `Agent` call results in the
|
|
40
40
|
* repair's transaction; `fire()` runs their observe hooks after the commit (review m1).
|
|
41
41
|
*/
|
|
42
42
|
private stopOpenCalls;
|
|
@@ -48,7 +48,7 @@ let RunQueue = class RunQueue {
|
|
|
48
48
|
constructor(kdb, eventLog, lock, jobs, finisher,
|
|
49
49
|
/** 运行以孤儿结束(标记失败 / 直接中止)后删除它的 checkpoint thread(thread_id = runId)。 */
|
|
50
50
|
checkpoints,
|
|
51
|
-
/** The run's open `
|
|
51
|
+
/** The run's open `Agent` call results, in the orphan repair's transaction (sub-agents spec §12). */
|
|
52
52
|
pipeline, events, log, txHost) {
|
|
53
53
|
this.kdb = kdb;
|
|
54
54
|
this.eventLog = eventLog;
|
|
@@ -65,7 +65,7 @@ let RunQueue = class RunQueue {
|
|
|
65
65
|
return this.kdb.db;
|
|
66
66
|
}
|
|
67
67
|
/**
|
|
68
|
-
* The `beforeTerminal` of an orphan repair: writes the run's open `
|
|
68
|
+
* The `beforeTerminal` of an orphan repair: writes the run's open `Agent` call results in the
|
|
69
69
|
* repair's transaction; `fire()` runs their observe hooks after the commit (review m1).
|
|
70
70
|
*/
|
|
71
71
|
stopOpenCalls(runId) {
|
|
@@ -63,7 +63,7 @@ export declare class RunWorker {
|
|
|
63
63
|
/** Run start's skills catalog snapshot (reads the pinned skills' bodies, phase B). */
|
|
64
64
|
private readonly skillsCatalog;
|
|
65
65
|
/**
|
|
66
|
-
* In the terminal transaction of every run: writes its open `
|
|
66
|
+
* In the terminal transaction of every run: writes its open `Agent` call results
|
|
67
67
|
* (`stopOpenAgentCalls`; a no-op without dispatches); `fire` runs their observe hooks after the
|
|
68
68
|
* commit (sub-agents spec §12, review m1: a failed or stalled parent too).
|
|
69
69
|
*/
|
|
@@ -94,7 +94,7 @@ export declare class RunWorker {
|
|
|
94
94
|
/** Run start's skills catalog snapshot (reads the pinned skills' bodies, phase B). */
|
|
95
95
|
skillsCatalog: Pick<SkillsCatalogService, "record">,
|
|
96
96
|
/**
|
|
97
|
-
* In the terminal transaction of every run: writes its open `
|
|
97
|
+
* In the terminal transaction of every run: writes its open `Agent` call results
|
|
98
98
|
* (`stopOpenAgentCalls`; a no-op without dispatches); `fire` runs their observe hooks after the
|
|
99
99
|
* commit (sub-agents spec §12, review m1: a failed or stalled parent too).
|
|
100
100
|
*/
|
|
@@ -10,7 +10,6 @@ var __param = (this && this.__param) || function (paramIndex, decorator) {
|
|
|
10
10
|
import { Inject, Injectable, Optional } from "@nestjs/common";
|
|
11
11
|
import { DelayedError } from "bullmq";
|
|
12
12
|
import { sql } from "kysely";
|
|
13
|
-
import { normalizeStoredDefinition } from "../agents/definition.js";
|
|
14
13
|
import { conversationTopic, EventLog, } from "../conversations/event-log.js";
|
|
15
14
|
import { effectiveDefinition, NO_SELECTION, readSelection, sameModel, sameSelection, } from "../conversations/selection.js";
|
|
16
15
|
import { TitleQueue } from "../conversations/titles.js";
|
|
@@ -24,6 +23,7 @@ import { Transactional } from "../infra/database/transactional.decorator.js";
|
|
|
24
23
|
import { KernelEvents } from "../infra/events/kernel-events.js";
|
|
25
24
|
import { KERNEL_BUS, KERNEL_LOGGER } from "../infra/tokens.js";
|
|
26
25
|
import { pinnedFailureText, SkillsCatalogService } from "../skills/catalog.js";
|
|
26
|
+
import { normalizeStoredDefinitionIn } from "../tools/legacy-data.js";
|
|
27
27
|
import { ToolPipeline } from "../tools/pipeline.js";
|
|
28
28
|
import { RunAbort } from "./abort.js";
|
|
29
29
|
import { KyselyCheckpointSaver } from "./checkpointer.js";
|
|
@@ -109,7 +109,7 @@ let RunWorker = class RunWorker {
|
|
|
109
109
|
/** Run start's skills catalog snapshot (reads the pinned skills' bodies, phase B). */
|
|
110
110
|
skillsCatalog,
|
|
111
111
|
/**
|
|
112
|
-
* In the terminal transaction of every run: writes its open `
|
|
112
|
+
* In the terminal transaction of every run: writes its open `Agent` call results
|
|
113
113
|
* (`stopOpenAgentCalls`; a no-op without dispatches); `fire` runs their observe hooks after the
|
|
114
114
|
* commit (sub-agents spec §12, review m1: a failed or stalled parent too).
|
|
115
115
|
*/
|
|
@@ -525,7 +525,7 @@ let RunWorker = class RunWorker {
|
|
|
525
525
|
// a follow-up runs with its task message's narrowing (final review I1): the frozen tools
|
|
526
526
|
// and org skills the current version still allows, recorded at its dispatch
|
|
527
527
|
const trigger = (await this.eventLog.readAfter(conversationId, Number(run.trigger_seq) - 1, 1))[0];
|
|
528
|
-
agent = childRunDefinition(
|
|
528
|
+
agent = childRunDefinition(await normalizeStoredDefinitionIn(this.db, conv.org_id, started.payload.definition), trigger?.type === "user_message" && trigger.seq === Number(run.trigger_seq)
|
|
529
529
|
? trigger.payload.dispatch?.narrowed
|
|
530
530
|
: undefined);
|
|
531
531
|
maxSteps = Math.min(started.payload.maxSteps, runtime.maxSteps);
|
|
@@ -552,7 +552,7 @@ let RunWorker = class RunWorker {
|
|
|
552
552
|
.where("agent_id", "=", conv.agent_id)
|
|
553
553
|
.where("version", "=", run.agent_version)
|
|
554
554
|
.executeTakeFirstOrThrow();
|
|
555
|
-
saved =
|
|
555
|
+
saved = await normalizeStoredDefinitionIn(this.db, conv.org_id, version.definition);
|
|
556
556
|
agent = saved;
|
|
557
557
|
}
|
|
558
558
|
let startedAt = run.started_at;
|
|
@@ -6,11 +6,7 @@ import type { KernelConfigService } from "../../infra/config/kernel-config.servi
|
|
|
6
6
|
import type { ModelPurposesService } from "../../models/purposes.js";
|
|
7
7
|
import type { ProviderRegistry } from "../providers.js";
|
|
8
8
|
import type { RosterEntry } from "./roster.js";
|
|
9
|
-
|
|
10
|
-
* Tools a sub-agent never gets (spec §5.3, §5.5): `agent` (depth 1), `ask_user` (the person does not
|
|
11
|
-
* see the child), `sandbox_deliver` (delivering files is the parent's job) and `skill_write`.
|
|
12
|
-
*/
|
|
13
|
-
export declare const CHILD_REMOVED_TOOLS: readonly ["agent", "ask_user", "sandbox_deliver", "skill_write"];
|
|
9
|
+
export { CHILD_REMOVED_TOOLS } from "../../tools/builtin-names.js";
|
|
14
10
|
/**
|
|
15
11
|
* The roster entry's template is gone (an inline template edited away, a plugin template
|
|
16
12
|
* uninstalled) between resolving the roster and reading it. The dispatch refuses the call as an
|
|
@@ -100,4 +96,3 @@ export declare function intersectTools(frozen: readonly AgentToolRef[], current:
|
|
|
100
96
|
export declare function narrowFollowUp(frozen: Pick<AgentDefinition, "tools" | "skills">, current: Pick<AgentDefinition, "tools" | "skills">): FollowUpNarrowing;
|
|
101
97
|
/** The definition a child run uses: the frozen one with its trigger's follow-up narrowing. */
|
|
102
98
|
export declare function childRunDefinition(frozen: AgentDefinition, narrowed: FollowUpNarrowing | undefined): AgentDefinition;
|
|
103
|
-
export {};
|