@easynet/agent-runtime 1.0.2 → 1.0.4

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.
Files changed (205) hide show
  1. package/.github/workflows/ci.yml +9 -24
  2. package/.github/workflows/release.yml +38 -26
  3. package/agent-runtime/.github/workflows/ci.yml +69 -0
  4. package/agent-runtime/.github/workflows/release.yml +118 -0
  5. package/agent-runtime/.releaserc.cjs +26 -0
  6. package/agent-runtime/config/agent.deep.yaml +25 -0
  7. package/agent-runtime/config/agent.react.yaml +24 -0
  8. package/agent-runtime/example/basic-usage.ts +49 -0
  9. package/agent-runtime/package-lock.json +7740 -0
  10. package/agent-runtime/package.json +49 -0
  11. package/agent-runtime/pnpm-lock.yaml +3712 -0
  12. package/agent-runtime/scripts/resolve-deps.js +54 -0
  13. package/agent-runtime/src/agents/deep-agent.ts +165 -0
  14. package/agent-runtime/src/agents/react-agent.helpers.ts +227 -0
  15. package/agent-runtime/src/agents/react-agent.ts +584 -0
  16. package/{src → agent-runtime/src/agents}/sub-agent.ts +2 -2
  17. package/agent-runtime/src/cli/args.ts +15 -0
  18. package/agent-runtime/src/cli/event-listener.ts +162 -0
  19. package/agent-runtime/src/cli/interactive.ts +144 -0
  20. package/agent-runtime/src/cli/runtime.ts +31 -0
  21. package/agent-runtime/src/cli/spinner.ts +23 -0
  22. package/agent-runtime/src/cli/terminal-render.ts +322 -0
  23. package/agent-runtime/src/cli/types.ts +33 -0
  24. package/agent-runtime/src/cli.ts +134 -0
  25. package/agent-runtime/src/config/helpers.ts +179 -0
  26. package/agent-runtime/src/config/index.ts +245 -0
  27. package/agent-runtime/src/config/types.ts +62 -0
  28. package/agent-runtime/src/core/context.ts +266 -0
  29. package/agent-runtime/src/index.ts +55 -0
  30. package/agent-runtime/tsconfig.json +18 -0
  31. package/apps/imessagebot/README.md +38 -0
  32. package/apps/imessagebot/config/.agent/cache/easynet/agent-tool-buildin/0.0.45/README.md +33 -0
  33. package/apps/imessagebot/config/.agent/cache/easynet/agent-tool-buildin/0.0.45/package-lock.json +15257 -0
  34. package/apps/imessagebot/config/.agent/cache/easynet/agent-tool-buildin/0.0.45/package.json +55 -0
  35. package/apps/imessagebot/config/agents/deep/agent.yaml +31 -0
  36. package/apps/imessagebot/config/agents/react/agent.yaml +58 -0
  37. package/apps/imessagebot/config/agents/shared/.agent/cache/easynet/agent-tool-buildin/0.0.43/README.md +33 -0
  38. package/apps/imessagebot/config/agents/shared/.agent/cache/easynet/agent-tool-buildin/0.0.43/package-lock.json +15457 -0
  39. package/apps/imessagebot/config/agents/shared/.agent/cache/easynet/agent-tool-buildin/0.0.43/package.json +55 -0
  40. package/apps/imessagebot/config/agents/shared/.agent/cache/easynet/agent-tool-buildin/0.0.46/README.md +33 -0
  41. package/apps/imessagebot/config/agents/shared/.agent/cache/easynet/agent-tool-buildin/0.0.46/package-lock.json +15257 -0
  42. package/apps/imessagebot/config/agents/shared/.agent/cache/easynet/agent-tool-buildin/0.0.46/package.json +62 -0
  43. package/apps/imessagebot/config/agents/shared/memory.yaml +31 -0
  44. package/apps/imessagebot/config/agents/shared/model.yaml +23 -0
  45. package/apps/imessagebot/config/agents/shared/tool.yaml +13 -0
  46. package/apps/imessagebot/config/app.yaml +14 -0
  47. package/apps/imessagebot/package-lock.json +53695 -0
  48. package/apps/imessagebot/package.json +41 -0
  49. package/apps/imessagebot/pnpm-lock.yaml +1589 -0
  50. package/apps/imessagebot/scripts/resolve-deps.js +41 -0
  51. package/apps/imessagebot/scripts/test-llm.mjs +27 -0
  52. package/apps/imessagebot/scripts/validate-tools-config.mjs +174 -0
  53. package/apps/imessagebot/src/config.ts +76 -0
  54. package/apps/imessagebot/src/context.ts +35 -0
  55. package/apps/imessagebot/src/index.ts +17 -0
  56. package/apps/imessagebot/tsconfig.json +18 -0
  57. package/apps/itermbot/.github/workflows/ci.yml +61 -0
  58. package/apps/itermbot/.github/workflows/release.yml +80 -0
  59. package/apps/itermbot/.releaserc.cjs +26 -0
  60. package/apps/itermbot/README.md +82 -0
  61. package/apps/itermbot/config/app.yaml +29 -0
  62. package/apps/itermbot/config/tsconfig.json +18 -0
  63. package/apps/itermbot/macos_disk_usage_agent_plan.md +244 -0
  64. package/apps/itermbot/package-lock.json +53697 -0
  65. package/apps/itermbot/package.json +57 -0
  66. package/apps/itermbot/pnpm-lock.yaml +3966 -0
  67. package/apps/itermbot/scripts/patch-buildin-cache.sh +25 -0
  68. package/apps/itermbot/scripts/resolve-deps.js +41 -0
  69. package/apps/itermbot/scripts/test-llm.mjs +32 -0
  70. package/apps/itermbot/skills/command-explain-and-guard/SKILL.md +39 -0
  71. package/apps/itermbot/skills/command-explain-and-guard/handler.js +86 -0
  72. package/apps/itermbot/skills/disk-usage-investigate/SKILL.md +44 -0
  73. package/apps/itermbot/skills/disk-usage-investigate/handler.js +12 -0
  74. package/apps/itermbot/skills/gpu-ssh-monitor/SKILL.md +64 -0
  75. package/apps/itermbot/skills/repo-triage/SKILL.md +40 -0
  76. package/apps/itermbot/skills/repo-triage/handler.js +56 -0
  77. package/apps/itermbot/skills/test-failure-diagnose/SKILL.md +43 -0
  78. package/apps/itermbot/skills/test-failure-diagnose/handler.js +107 -0
  79. package/apps/itermbot/src/config.ts +95 -0
  80. package/apps/itermbot/src/context.ts +35 -0
  81. package/apps/itermbot/src/index.ts +223 -0
  82. package/apps/itermbot/src/iterm/session-hint.ts +40 -0
  83. package/apps/itermbot/src/iterm/target-routing.ts +419 -0
  84. package/apps/itermbot/src/startup/colors.ts +317 -0
  85. package/apps/itermbot/src/startup/diagnostics.ts +97 -0
  86. package/apps/itermbot/src/startup/ui.ts +141 -0
  87. package/config/agent.deep.yaml +25 -0
  88. package/config/agent.react.yaml +24 -0
  89. package/dist/agents/deep-agent.d.ts +37 -0
  90. package/dist/agents/deep-agent.d.ts.map +1 -0
  91. package/dist/agents/deep-agent.js +115 -0
  92. package/dist/agents/deep-agent.js.map +1 -0
  93. package/dist/agents/react-agent.d.ts +40 -0
  94. package/dist/agents/react-agent.d.ts.map +1 -0
  95. package/dist/agents/react-agent.helpers.d.ts +40 -0
  96. package/dist/agents/react-agent.helpers.d.ts.map +1 -0
  97. package/dist/agents/react-agent.helpers.js +196 -0
  98. package/dist/agents/react-agent.helpers.js.map +1 -0
  99. package/dist/agents/react-agent.js +400 -0
  100. package/dist/agents/react-agent.js.map +1 -0
  101. package/dist/agents/sub-agent.d.ts +34 -0
  102. package/dist/agents/sub-agent.d.ts.map +1 -0
  103. package/dist/agents/sub-agent.js +53 -0
  104. package/dist/agents/sub-agent.js.map +1 -0
  105. package/dist/cli/args.d.ts +8 -0
  106. package/dist/cli/args.d.ts.map +1 -0
  107. package/dist/cli/args.js +9 -0
  108. package/dist/cli/args.js.map +1 -0
  109. package/dist/cli/event-listener.d.ts +3 -0
  110. package/dist/cli/event-listener.d.ts.map +1 -0
  111. package/dist/cli/event-listener.js +131 -0
  112. package/dist/cli/event-listener.js.map +1 -0
  113. package/dist/cli/interactive.d.ts +4 -0
  114. package/dist/cli/interactive.d.ts.map +1 -0
  115. package/dist/cli/interactive.js +118 -0
  116. package/dist/cli/interactive.js.map +1 -0
  117. package/dist/cli/runtime.d.ts +8 -0
  118. package/dist/cli/runtime.d.ts.map +1 -0
  119. package/dist/cli/runtime.js +27 -0
  120. package/dist/cli/runtime.js.map +1 -0
  121. package/dist/cli/spinner.d.ts +2 -0
  122. package/dist/cli/spinner.d.ts.map +1 -0
  123. package/dist/cli/spinner.js +22 -0
  124. package/dist/cli/spinner.js.map +1 -0
  125. package/dist/cli/terminal-render.d.ts +7 -0
  126. package/dist/cli/terminal-render.d.ts.map +1 -0
  127. package/dist/cli/terminal-render.js +282 -0
  128. package/dist/cli/terminal-render.js.map +1 -0
  129. package/dist/cli/types.d.ts +29 -0
  130. package/dist/cli/types.d.ts.map +1 -0
  131. package/dist/cli/types.js +3 -0
  132. package/dist/cli/types.js.map +1 -0
  133. package/dist/cli.d.ts +4 -41
  134. package/dist/cli.d.ts.map +1 -1
  135. package/dist/cli.js +84 -588
  136. package/dist/cli.js.map +1 -1
  137. package/dist/config/helpers.d.ts +6 -0
  138. package/dist/config/helpers.d.ts.map +1 -0
  139. package/dist/config/helpers.js +164 -0
  140. package/dist/config/helpers.js.map +1 -0
  141. package/dist/config/index.d.ts +15 -0
  142. package/dist/config/index.d.ts.map +1 -0
  143. package/dist/config/index.js +160 -0
  144. package/dist/config/index.js.map +1 -0
  145. package/dist/config/types.d.ts +57 -0
  146. package/dist/config/types.d.ts.map +1 -0
  147. package/dist/config/types.js +2 -0
  148. package/dist/config/types.js.map +1 -0
  149. package/dist/context.d.ts +8 -69
  150. package/dist/context.d.ts.map +1 -1
  151. package/dist/context.js +44 -24
  152. package/dist/context.js.map +1 -1
  153. package/dist/core/context.d.ts +66 -0
  154. package/dist/core/context.d.ts.map +1 -0
  155. package/dist/core/context.js +149 -0
  156. package/dist/core/context.js.map +1 -0
  157. package/dist/deep-agent.d.ts +5 -2
  158. package/dist/deep-agent.d.ts.map +1 -1
  159. package/dist/deep-agent.js +44 -11
  160. package/dist/deep-agent.js.map +1 -1
  161. package/dist/index.d.ts +6 -6
  162. package/dist/index.d.ts.map +1 -1
  163. package/dist/index.js +6 -6
  164. package/dist/index.js.map +1 -1
  165. package/dist/middleware/malformed-tool-call-middleware.d.ts +8 -0
  166. package/dist/middleware/malformed-tool-call-middleware.d.ts.map +1 -0
  167. package/dist/middleware/malformed-tool-call-middleware.js +191 -0
  168. package/dist/middleware/malformed-tool-call-middleware.js.map +1 -0
  169. package/dist/react-agent.d.ts +2 -2
  170. package/dist/react-agent.d.ts.map +1 -1
  171. package/dist/react-agent.js +28 -9
  172. package/dist/react-agent.js.map +1 -1
  173. package/package.json +1 -1
  174. package/scripts/resolve-deps.js +54 -0
  175. package/src/agents/deep-agent.ts +165 -0
  176. package/src/agents/react-agent.helpers.ts +227 -0
  177. package/src/agents/react-agent.ts +584 -0
  178. package/src/agents/sub-agent.ts +82 -0
  179. package/src/cli/args.ts +15 -0
  180. package/src/cli/event-listener.ts +162 -0
  181. package/src/cli/interactive.ts +144 -0
  182. package/src/cli/runtime.ts +31 -0
  183. package/src/cli/spinner.ts +23 -0
  184. package/src/cli/terminal-render.ts +322 -0
  185. package/src/cli/types.ts +33 -0
  186. package/src/cli.ts +91 -702
  187. package/src/config/helpers.ts +179 -0
  188. package/src/config/index.ts +245 -0
  189. package/src/config/types.ts +62 -0
  190. package/src/core/context.ts +266 -0
  191. package/src/index.ts +13 -11
  192. package/src/middleware/malformed-tool-call-middleware.ts +239 -0
  193. package/src/types/markdown-it-terminal.d.ts +4 -0
  194. package/src/types/marked-terminal.d.ts +16 -0
  195. package/dist/config.d.ts +0 -86
  196. package/dist/config.d.ts.map +0 -1
  197. package/dist/config.js +0 -84
  198. package/dist/config.js.map +0 -1
  199. package/src/config.ts +0 -177
  200. package/src/context.ts +0 -247
  201. package/src/deep-agent.ts +0 -104
  202. package/src/react-agent.ts +0 -576
  203. /package/{src → agent-runtime/src/middleware}/malformed-tool-call-middleware.ts +0 -0
  204. /package/{src → agent-runtime/src/types}/markdown-it-terminal.d.ts +0 -0
  205. /package/{src → agent-runtime/src/types}/marked-terminal.d.ts +0 -0
@@ -0,0 +1,35 @@
1
+ /**
2
+ * Shared runtime context: LLM, memory, tools.
3
+ * Built once and passed to both ReAct and Deep agents.
4
+ */
5
+ import {
6
+ createContextBuilders,
7
+ type AppContextBuilders,
8
+ type BotContext,
9
+ type BotTool,
10
+ type CreateContextOptions,
11
+ } from "@easynet/agent-runtime";
12
+ import {
13
+ loadAppConfig,
14
+ getModelsConfigPath,
15
+ getMemoryConfigPath,
16
+ getToolConfigPath,
17
+ type AppConfig,
18
+ } from "./config.js";
19
+
20
+ export type { BotContext, BotTool, CreateContextOptions };
21
+
22
+ const builders: AppContextBuilders = createContextBuilders<AppConfig>({
23
+ configApi: {
24
+ loadAgentConfig: loadAppConfig,
25
+ getModelsConfigPath: (config: AppConfig, agentName?: string) => getModelsConfigPath(config, agentName),
26
+ getMemoryConfigPath: (config: AppConfig, agentName?: string) => getMemoryConfigPath(config, agentName),
27
+ getToolConfigPath: (config: AppConfig, agentName?: string) => getToolConfigPath(config, agentName),
28
+ },
29
+ });
30
+
31
+ export const createAgentLlm: AppContextBuilders["createAgentLlm"] = builders.createAgentLlm;
32
+ export const createAgentMemory: AppContextBuilders["createAgentMemory"] = builders.createAgentMemory;
33
+ export const createAgentTools: AppContextBuilders["createAgentTools"] = builders.createAgentTools;
34
+ export const createAgent: AppContextBuilders["createAgent"] = builders.createAgent;
35
+ export const createBotContext: AppContextBuilders["createBotContext"] = builders.createBotContext;
@@ -0,0 +1,223 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * iTermBot: ReAct agent (LangChain) + Deep agent (DeepAgents).
4
+ * Usage:
5
+ * npm start # interactive: choose agent then chat
6
+ * npm run react # use ReAct agent
7
+ * npm run deep # use Deep agent
8
+ * node dist/index.js react "Your question"
9
+ * node dist/index.js deep "Your question"
10
+ */
11
+ import {
12
+ runAppCli,
13
+ createStructuredRunEventListener,
14
+ resolveDefaultAgentName as resolveRuntimeDefaultAgentName,
15
+ } from "@easynet/agent-runtime";
16
+ import { createAgentEventBus } from "@easynet/agent-common";
17
+ import type { TargetRoutingState } from "./iterm/target-routing.js";
18
+ import { applyStartupPanelColors, restoreSessionColorsSync } from "./startup/colors.js";
19
+ import { injectTargetSessionHint } from "./iterm/session-hint.js";
20
+ import { enableDynamicTargetRouting } from "./iterm/target-routing.js";
21
+ import {
22
+ clearStartupNoise,
23
+ formatLogPath,
24
+ getAppVersion,
25
+ printStartupBanner,
26
+ printStartupSummary,
27
+ resolveConfigPath,
28
+ runStartupStep,
29
+ StartupProgressRenderer,
30
+ } from "./startup/ui.js";
31
+ import {
32
+ getLlmSelectionLabel,
33
+ getSkillsPathLabel,
34
+ runLlmHealthCheck,
35
+ } from "./startup/diagnostics.js";
36
+ import {
37
+ loadAppConfig,
38
+ getModelsConfigPath,
39
+ getMemoryConfigPath,
40
+ getToolConfigPath,
41
+ } from "./config.js";
42
+ import { createAgent, createAgentLlm, createAgentMemory, createAgentTools } from "./context.js";
43
+ let startupColorSnapshots: Parameters<typeof restoreSessionColorsSync>[0] = [];
44
+ let stopDynamicTargetRouting: (() => void) | null = null;
45
+
46
+ function sanitizeSessionId(input: string): string {
47
+ return input.replace(/[^a-zA-Z0-9_-]/g, "_").slice(0, 64);
48
+ }
49
+
50
+ function configureThreadMemoryNamespace(ctx: Parameters<NonNullable<Parameters<typeof runAppCli>[0]["onReady"]>>[0], args: {
51
+ chatSessionId: string | null;
52
+ }): string {
53
+ const appConfig = ctx.config.app as
54
+ | {
55
+ agent?: Record<string, { memory?: { namespace_mode?: "thread" | "fixed"; namespace?: string } }>;
56
+ }
57
+ | undefined;
58
+ const agents = appConfig?.agent;
59
+ const agentList = agents ? Object.values(agents) : [];
60
+ const firstAgent = agentList[0];
61
+ const defaultBaseNamespace = "user:itermbot";
62
+ const baseNamespace =
63
+ firstAgent?.memory?.namespace ??
64
+ defaultBaseNamespace;
65
+ const mode = firstAgent?.memory?.namespace_mode ?? "thread";
66
+ const seed = args.chatSessionId ? sanitizeSessionId(args.chatSessionId) : `local_${Date.now().toString(36)}`;
67
+ const threadNamespace = mode === "fixed" ? baseNamespace : `${baseNamespace}:thread:${seed}`;
68
+
69
+ if (!ctx.config.app) ctx.config.app = {};
70
+ if (!ctx.config.app.agent) ctx.config.app.agent = {};
71
+
72
+ for (const agentName of Object.keys(ctx.config.app.agent)) {
73
+ const current = ctx.config.app.agent[agentName] ?? {};
74
+ const currentMemory = current.memory ?? {};
75
+ ctx.config.app.agent[agentName] = {
76
+ ...current,
77
+ memory: {
78
+ ...currentMemory,
79
+ namespace: threadNamespace,
80
+ },
81
+ };
82
+ }
83
+
84
+ return threadNamespace;
85
+ }
86
+
87
+ function ensureItermEnvironmentOrExit(): void {
88
+ const termProgram = process.env.TERM_PROGRAM?.trim();
89
+ const itermSessionId = process.env.ITERM_SESSION_ID?.trim();
90
+ const isIterm = termProgram === "iTerm.app" || Boolean(itermSessionId);
91
+ if (isIterm) return;
92
+
93
+ console.error("iTermBot startup blocked: iTerm2 environment is required.");
94
+ console.error("Please run iTermBot inside iTerm2 and try again.");
95
+ process.exit(1);
96
+ }
97
+
98
+ async function createBotContextWithStartupSteps() {
99
+ const appConfigPath = resolveConfigPath("config/app.yaml");
100
+ const config = await loadAppConfig(appConfigPath);
101
+ const agentName = resolveRuntimeDefaultAgentName(
102
+ config,
103
+ (config.app as { defaultAgent?: string } | undefined)?.defaultAgent,
104
+ );
105
+ const events = createAgentEventBus();
106
+ const progress = new StartupProgressRenderer();
107
+ await runStartupStep(
108
+ progress,
109
+ "init app config",
110
+ async () => config,
111
+ () => `${formatLogPath(appConfigPath)} (agent=${agentName})`,
112
+ );
113
+ const modelsPath = getModelsConfigPath(config, agentName);
114
+ const memoryPath = getMemoryConfigPath(config, agentName);
115
+ const toolPath = getToolConfigPath(config, agentName);
116
+ const llmSelectionLabel = await getLlmSelectionLabel(modelsPath);
117
+ const skillsPathLabel = await getSkillsPathLabel(config, agentName);
118
+ const llmTask = runStartupStep(
119
+ progress,
120
+ "init llm",
121
+ () => createAgentLlm(config, events, agentName),
122
+ () => `${formatLogPath(modelsPath)} (${llmSelectionLabel})`,
123
+ ).then(async (llm) => {
124
+ await runStartupStep(
125
+ progress,
126
+ "check llm health",
127
+ () => runLlmHealthCheck(llm),
128
+ () => `${formatLogPath(modelsPath)} (${llmSelectionLabel})`,
129
+ );
130
+ return llm;
131
+ });
132
+ const memoryTask = runStartupStep(
133
+ progress,
134
+ "init memory",
135
+ () => createAgentMemory(config, events, agentName),
136
+ () => formatLogPath(memoryPath),
137
+ );
138
+ const toolsTask = runStartupStep(
139
+ progress,
140
+ "init tools",
141
+ () => createAgentTools(config, events, agentName),
142
+ (result) => `${formatLogPath(toolPath)} (count=${result.length})`,
143
+ );
144
+ const [llm, memory, tools] = await Promise.all([llmTask, memoryTask, toolsTask]);
145
+ return runStartupStep(
146
+ progress,
147
+ "init skills and context",
148
+ () => createAgent({ events, agentName, llm, memory, tools }),
149
+ (result) => `count=${result.skillSet?.list().length ?? 0} (${skillsPathLabel})`,
150
+ );
151
+ }
152
+
153
+ ensureItermEnvironmentOrExit();
154
+ clearStartupNoise();
155
+ printStartupBanner();
156
+
157
+ runAppCli({
158
+ appName: "iTermBot",
159
+ createBotContext: createBotContextWithStartupSteps,
160
+ ui: {
161
+ assistantLabel: "iTermBot",
162
+ useColor: true,
163
+ echoUserQuestion: false,
164
+ processingSpinner: true,
165
+ processingText: false,
166
+ loadingText: false,
167
+ loadingSpinner: false,
168
+ readyText: false,
169
+ interactiveIntro: false,
170
+ },
171
+ eventListener: createStructuredRunEventListener((line) => console.log(line)),
172
+ onShutdown: () => {
173
+ if (stopDynamicTargetRouting) {
174
+ stopDynamicTargetRouting();
175
+ stopDynamicTargetRouting = null;
176
+ }
177
+ if (startupColorSnapshots.length > 0) {
178
+ restoreSessionColorsSync(startupColorSnapshots);
179
+ }
180
+ },
181
+ onReady: async (ctx) => {
182
+ const progress = new StartupProgressRenderer();
183
+ const startup = await runStartupStep(
184
+ progress,
185
+ "init iTerm panels",
186
+ () => applyStartupPanelColors(),
187
+ );
188
+ const routingState: TargetRoutingState = {
189
+ chatSessionId: startup.chatSessionId,
190
+ chatWindowId: startup.windowId,
191
+ chatTabIndex: startup.tabIndex,
192
+ targetSessionId: startup.targetSessionId,
193
+ windowId: startup.windowId,
194
+ tabIndex: startup.tabIndex,
195
+ };
196
+ stopDynamicTargetRouting = await runStartupStep(
197
+ progress,
198
+ "init target routing",
199
+ () => enableDynamicTargetRouting(ctx, routingState),
200
+ );
201
+ await runStartupStep(
202
+ progress,
203
+ "init memory namespace",
204
+ () =>
205
+ configureThreadMemoryNamespace(ctx, {
206
+ chatSessionId: startup.chatSessionId,
207
+ }),
208
+ (result) => result,
209
+ );
210
+
211
+ startupColorSnapshots = startup.colorSnapshots;
212
+
213
+ printStartupSummary({
214
+ version: getAppVersion(),
215
+ });
216
+ injectTargetSessionHint(ctx, {
217
+ ...startup,
218
+ targetSessionId: routingState.targetSessionId,
219
+ windowId: routingState.windowId,
220
+ tabIndex: routingState.tabIndex,
221
+ });
222
+ },
223
+ });
@@ -0,0 +1,40 @@
1
+ import type { BotContext } from "@easynet/agent-runtime";
2
+ import type { StartupResult } from "../startup/colors.js";
3
+
4
+ type PromptTemplates = {
5
+ itermPolicy?: string;
6
+ targetSession?: string;
7
+ };
8
+
9
+ function formatTargetSessionHint(template: string, startup: StartupResult): string {
10
+ return template
11
+ .replaceAll("{{sessionId}}", startup.targetSessionId ?? "")
12
+ .replaceAll("{{windowId}}", String(startup.windowId))
13
+ .replaceAll("{{tabIndex}}", String(startup.tabIndex));
14
+ }
15
+
16
+ function getPromptTemplates(ctx: BotContext): PromptTemplates | undefined {
17
+ const appConfig = ctx.config.app as { promptTemplates?: PromptTemplates } | undefined;
18
+ return appConfig?.promptTemplates;
19
+ }
20
+
21
+ export function injectTargetSessionHint(ctx: BotContext, startup: StartupResult): void {
22
+ const templates = getPromptTemplates(ctx);
23
+ const policyTemplate = templates?.itermPolicy?.trim() ?? "";
24
+ const targetTemplate = templates?.targetSession?.trim() ?? "";
25
+ const sessionRendered = startup.targetSessionId && targetTemplate
26
+ ? formatTargetSessionHint(targetTemplate, startup)
27
+ : "";
28
+
29
+ const agents = ctx.config.app?.agent as Record<string, { systemPrompt?: string } | undefined> | undefined;
30
+ if (!agents) return;
31
+ for (const agentCfg of Object.values(agents)) {
32
+ if (!agentCfg) continue;
33
+ const base = (agentCfg.systemPrompt ?? "").trim();
34
+ const parts: string[] = [];
35
+ if (policyTemplate && !base.includes(policyTemplate)) parts.push(policyTemplate);
36
+ if (sessionRendered && !base.includes(sessionRendered)) parts.push(sessionRendered);
37
+ if (base) parts.push(base);
38
+ agentCfg.systemPrompt = parts.join("\n\n");
39
+ }
40
+ }