@di-code/coding-agent 0.1.7 → 0.1.9

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 (333) hide show
  1. package/README.md +54 -567
  2. package/compositions/base.yml +54 -0
  3. package/compositions/interactive.yml +14 -0
  4. package/compositions/json.yml +6 -0
  5. package/compositions/print.yml +5 -0
  6. package/compositions/rpc.yml +12 -0
  7. package/compositions/webui.yml +9 -0
  8. package/dist/cli.d.ts +22 -1
  9. package/dist/cli.d.ts.map +1 -1
  10. package/dist/cli.js +97 -3
  11. package/dist/cli.js.map +1 -1
  12. package/dist/composition-loader-entry.d.ts +11 -0
  13. package/dist/composition-loader-entry.d.ts.map +1 -0
  14. package/dist/composition-loader-entry.js +12 -0
  15. package/dist/composition-loader-entry.js.map +1 -0
  16. package/dist/compositions.d.ts +32 -0
  17. package/dist/compositions.d.ts.map +1 -0
  18. package/dist/compositions.js +173 -0
  19. package/dist/compositions.js.map +1 -0
  20. package/dist/core/session/session-manager.d.ts +9 -2
  21. package/dist/core/session/session-manager.d.ts.map +1 -1
  22. package/dist/core/session/session-manager.js +28 -0
  23. package/dist/core/session/session-manager.js.map +1 -1
  24. package/dist/core/session/session-storage.d.ts.map +1 -1
  25. package/dist/core/session/session-storage.js +20 -3
  26. package/dist/core/session/session-storage.js.map +1 -1
  27. package/dist/core/session/types.d.ts +11 -2
  28. package/dist/core/session/types.d.ts.map +1 -1
  29. package/dist/core/session/types.js.map +1 -1
  30. package/dist/core/session-tools.d.ts +5 -0
  31. package/dist/core/session-tools.d.ts.map +1 -0
  32. package/dist/core/session-tools.js +17 -0
  33. package/dist/core/session-tools.js.map +1 -0
  34. package/dist/core/session.d.ts +19 -7
  35. package/dist/core/session.d.ts.map +1 -1
  36. package/dist/core/session.js +71 -39
  37. package/dist/core/session.js.map +1 -1
  38. package/dist/core/tools/bash.d.ts +1 -38
  39. package/dist/core/tools/bash.d.ts.map +1 -1
  40. package/dist/core/tools/bash.js +1 -207
  41. package/dist/core/tools/bash.js.map +1 -1
  42. package/dist/core/tools/edit-diff.d.ts +1 -24
  43. package/dist/core/tools/edit-diff.d.ts.map +1 -1
  44. package/dist/core/tools/edit-diff.js +1 -135
  45. package/dist/core/tools/edit-diff.js.map +1 -1
  46. package/dist/core/tools/edit.d.ts +1 -26
  47. package/dist/core/tools/edit.d.ts.map +1 -1
  48. package/dist/core/tools/edit.js +1 -140
  49. package/dist/core/tools/edit.js.map +1 -1
  50. package/dist/core/tools/file-mutation-queue.d.ts +1 -1
  51. package/dist/core/tools/file-mutation-queue.d.ts.map +1 -1
  52. package/dist/core/tools/file-mutation-queue.js +1 -23
  53. package/dist/core/tools/file-mutation-queue.js.map +1 -1
  54. package/dist/core/tools/file-search.d.ts +1 -13
  55. package/dist/core/tools/file-search.d.ts.map +1 -1
  56. package/dist/core/tools/file-search.js +1 -98
  57. package/dist/core/tools/file-search.js.map +1 -1
  58. package/dist/core/tools/glob.d.ts +1 -10
  59. package/dist/core/tools/glob.d.ts.map +1 -1
  60. package/dist/core/tools/glob.js +1 -43
  61. package/dist/core/tools/glob.js.map +1 -1
  62. package/dist/core/tools/grep.d.ts +1 -12
  63. package/dist/core/tools/grep.d.ts.map +1 -1
  64. package/dist/core/tools/grep.js +1 -66
  65. package/dist/core/tools/grep.js.map +1 -1
  66. package/dist/core/tools/load-skill.d.ts +1 -9
  67. package/dist/core/tools/load-skill.d.ts.map +1 -1
  68. package/dist/core/tools/load-skill.js +1 -21
  69. package/dist/core/tools/load-skill.js.map +1 -1
  70. package/dist/core/tools/path-boundary.d.ts +1 -4
  71. package/dist/core/tools/path-boundary.d.ts.map +1 -1
  72. package/dist/core/tools/path-boundary.js +1 -65
  73. package/dist/core/tools/path-boundary.js.map +1 -1
  74. package/dist/core/tools/read.d.ts +1 -16
  75. package/dist/core/tools/read.d.ts.map +1 -1
  76. package/dist/core/tools/read.js +1 -131
  77. package/dist/core/tools/read.js.map +1 -1
  78. package/dist/core/tools/write.d.ts +1 -16
  79. package/dist/core/tools/write.d.ts.map +1 -1
  80. package/dist/core/tools/write.js +1 -44
  81. package/dist/core/tools/write.js.map +1 -1
  82. package/dist/entry.js +30 -28
  83. package/dist/entry.js.map +1 -1
  84. package/dist/index.d.ts +6 -3
  85. package/dist/index.d.ts.map +1 -1
  86. package/dist/index.js +6 -3
  87. package/dist/index.js.map +1 -1
  88. package/dist/interactive/builtin.d.ts +17 -0
  89. package/dist/interactive/builtin.d.ts.map +1 -0
  90. package/dist/interactive/builtin.js +47 -0
  91. package/dist/interactive/builtin.js.map +1 -0
  92. package/dist/interactive/controller.d.ts +85 -0
  93. package/dist/interactive/controller.d.ts.map +1 -0
  94. package/dist/interactive/controller.js +211 -0
  95. package/dist/interactive/controller.js.map +1 -0
  96. package/dist/interactive/index.d.ts +3 -0
  97. package/dist/interactive/index.d.ts.map +1 -0
  98. package/dist/interactive/index.js +3 -0
  99. package/dist/interactive/index.js.map +1 -0
  100. package/dist/interactive-host-entry.d.ts +7 -0
  101. package/dist/interactive-host-entry.d.ts.map +1 -0
  102. package/dist/interactive-host-entry.js +123 -0
  103. package/dist/interactive-host-entry.js.map +1 -0
  104. package/dist/interactive-profile.d.ts +18 -0
  105. package/dist/interactive-profile.d.ts.map +1 -0
  106. package/dist/interactive-profile.js +290 -0
  107. package/dist/interactive-profile.js.map +1 -0
  108. package/dist/interactive-resources-entry.d.ts +7 -0
  109. package/dist/interactive-resources-entry.d.ts.map +1 -0
  110. package/dist/interactive-resources-entry.js +42 -0
  111. package/dist/interactive-resources-entry.js.map +1 -0
  112. package/dist/legacy-main.d.ts +39 -0
  113. package/dist/legacy-main.d.ts.map +1 -0
  114. package/dist/legacy-main.js +611 -0
  115. package/dist/legacy-main.js.map +1 -0
  116. package/dist/main.d.ts +15 -34
  117. package/dist/main.d.ts.map +1 -1
  118. package/dist/main.js +130 -518
  119. package/dist/main.js.map +1 -1
  120. package/dist/mcp/entries.d.ts +42 -0
  121. package/dist/mcp/entries.d.ts.map +1 -0
  122. package/dist/mcp/entries.js +98 -0
  123. package/dist/mcp/entries.js.map +1 -0
  124. package/dist/mcp-client-entry.d.ts +5 -0
  125. package/dist/mcp-client-entry.d.ts.map +1 -0
  126. package/dist/mcp-client-entry.js +6 -0
  127. package/dist/mcp-client-entry.js.map +1 -0
  128. package/dist/mcp-config-entry.d.ts +5 -0
  129. package/dist/mcp-config-entry.d.ts.map +1 -0
  130. package/dist/mcp-config-entry.js +6 -0
  131. package/dist/mcp-config-entry.js.map +1 -0
  132. package/dist/mcp-tools-entry.d.ts +5 -0
  133. package/dist/mcp-tools-entry.d.ts.map +1 -0
  134. package/dist/mcp-tools-entry.js +6 -0
  135. package/dist/mcp-tools-entry.js.map +1 -0
  136. package/dist/mcp-transport-entry.d.ts +5 -0
  137. package/dist/mcp-transport-entry.d.ts.map +1 -0
  138. package/dist/mcp-transport-entry.js +6 -0
  139. package/dist/mcp-transport-entry.js.map +1 -0
  140. package/dist/modes/interactive-entry.d.ts +18 -0
  141. package/dist/modes/interactive-entry.d.ts.map +1 -0
  142. package/dist/modes/interactive-entry.js +21 -0
  143. package/dist/modes/interactive-entry.js.map +1 -0
  144. package/dist/modes/interactive.d.ts +16 -6
  145. package/dist/modes/interactive.d.ts.map +1 -1
  146. package/dist/modes/interactive.js +81 -32
  147. package/dist/modes/interactive.js.map +1 -1
  148. package/dist/modes/json-entry.d.ts +13 -0
  149. package/dist/modes/json-entry.d.ts.map +1 -0
  150. package/dist/modes/json-entry.js +14 -0
  151. package/dist/modes/json-entry.js.map +1 -0
  152. package/dist/modes/json.d.ts +4 -1
  153. package/dist/modes/json.d.ts.map +1 -1
  154. package/dist/modes/json.js +3 -3
  155. package/dist/modes/json.js.map +1 -1
  156. package/dist/modes/print-entry.d.ts +10 -0
  157. package/dist/modes/print-entry.d.ts.map +1 -0
  158. package/dist/modes/print-entry.js +11 -0
  159. package/dist/modes/print-entry.js.map +1 -0
  160. package/dist/modes/tree-selector.d.ts.map +1 -1
  161. package/dist/modes/tree-selector.js +4 -0
  162. package/dist/modes/tree-selector.js.map +1 -1
  163. package/dist/plugin-dump-composition.d.ts +6 -0
  164. package/dist/plugin-dump-composition.d.ts.map +1 -0
  165. package/dist/plugin-dump-composition.js +7 -0
  166. package/dist/plugin-dump-composition.js.map +1 -0
  167. package/dist/plugin-inventory.d.ts +7 -0
  168. package/dist/plugin-inventory.d.ts.map +1 -0
  169. package/dist/plugin-inventory.js +8 -0
  170. package/dist/plugin-inventory.js.map +1 -0
  171. package/dist/plugin-manager.d.ts +6 -0
  172. package/dist/plugin-manager.d.ts.map +1 -0
  173. package/dist/plugin-manager.js +7 -0
  174. package/dist/plugin-manager.js.map +1 -0
  175. package/dist/plugin-trace.d.ts +6 -0
  176. package/dist/plugin-trace.d.ts.map +1 -0
  177. package/dist/plugin-trace.js +7 -0
  178. package/dist/plugin-trace.js.map +1 -0
  179. package/dist/plugins/dynamic-broker.d.ts +76 -0
  180. package/dist/plugins/dynamic-broker.d.ts.map +1 -0
  181. package/dist/plugins/dynamic-broker.js +852 -0
  182. package/dist/plugins/dynamic-broker.js.map +1 -0
  183. package/dist/plugins/profile.d.ts +15 -0
  184. package/dist/plugins/profile.d.ts.map +1 -0
  185. package/dist/plugins/profile.js +34 -0
  186. package/dist/plugins/profile.js.map +1 -0
  187. package/dist/plugins/runtime-host.d.ts +37 -0
  188. package/dist/plugins/runtime-host.d.ts.map +1 -0
  189. package/dist/plugins/runtime-host.js +95 -0
  190. package/dist/plugins/runtime-host.js.map +1 -0
  191. package/dist/plugins/trust.d.ts +8 -0
  192. package/dist/plugins/trust.d.ts.map +1 -0
  193. package/dist/plugins/trust.js +59 -0
  194. package/dist/plugins/trust.js.map +1 -0
  195. package/dist/project-trust-entry.d.ts +15 -0
  196. package/dist/project-trust-entry.d.ts.map +1 -0
  197. package/dist/project-trust-entry.js +15 -0
  198. package/dist/project-trust-entry.js.map +1 -0
  199. package/dist/rpc/client.d.ts +78 -6
  200. package/dist/rpc/client.d.ts.map +1 -1
  201. package/dist/rpc/client.js +172 -4
  202. package/dist/rpc/client.js.map +1 -1
  203. package/dist/rpc/dispatcher.d.ts +121 -0
  204. package/dist/rpc/dispatcher.d.ts.map +1 -0
  205. package/dist/rpc/dispatcher.js +994 -0
  206. package/dist/rpc/dispatcher.js.map +1 -0
  207. package/dist/rpc/index.d.ts +2 -0
  208. package/dist/rpc/index.d.ts.map +1 -1
  209. package/dist/rpc/index.js +2 -0
  210. package/dist/rpc/index.js.map +1 -1
  211. package/dist/rpc/lifecycle.d.ts +6 -0
  212. package/dist/rpc/lifecycle.d.ts.map +1 -0
  213. package/dist/rpc/lifecycle.js +24 -0
  214. package/dist/rpc/lifecycle.js.map +1 -0
  215. package/dist/rpc/protocol.d.ts +112 -31
  216. package/dist/rpc/protocol.d.ts.map +1 -1
  217. package/dist/rpc/protocol.js +569 -117
  218. package/dist/rpc/protocol.js.map +1 -1
  219. package/dist/rpc/server-service.d.ts +7 -0
  220. package/dist/rpc/server-service.d.ts.map +1 -0
  221. package/dist/rpc/server-service.js +3 -0
  222. package/dist/rpc/server-service.js.map +1 -0
  223. package/dist/rpc/server.d.ts +16 -19
  224. package/dist/rpc/server.d.ts.map +1 -1
  225. package/dist/rpc/server.js +59 -115
  226. package/dist/rpc/server.js.map +1 -1
  227. package/dist/rpc-client-sdk-entry.d.ts +12 -0
  228. package/dist/rpc-client-sdk-entry.d.ts.map +1 -0
  229. package/dist/rpc-client-sdk-entry.js +11 -0
  230. package/dist/rpc-client-sdk-entry.js.map +1 -0
  231. package/dist/rpc-entry.js +50 -18
  232. package/dist/rpc-entry.js.map +1 -1
  233. package/dist/rpc-server-entry.d.ts +8 -0
  234. package/dist/rpc-server-entry.d.ts.map +1 -0
  235. package/dist/rpc-server-entry.js +67 -0
  236. package/dist/rpc-server-entry.js.map +1 -0
  237. package/dist/runtime/attachment-store.d.ts +13 -0
  238. package/dist/runtime/attachment-store.d.ts.map +1 -0
  239. package/dist/runtime/attachment-store.js +93 -0
  240. package/dist/runtime/attachment-store.js.map +1 -0
  241. package/dist/runtime/bootstrap.d.ts +14 -0
  242. package/dist/runtime/bootstrap.d.ts.map +1 -0
  243. package/dist/runtime/bootstrap.js +29 -0
  244. package/dist/runtime/bootstrap.js.map +1 -0
  245. package/dist/runtime/interactive-host-service.d.ts +22 -0
  246. package/dist/runtime/interactive-host-service.d.ts.map +1 -0
  247. package/dist/runtime/interactive-host-service.js +2 -0
  248. package/dist/runtime/interactive-host-service.js.map +1 -0
  249. package/dist/runtime/interactive-resource-service.d.ts +11 -0
  250. package/dist/runtime/interactive-resource-service.d.ts.map +1 -0
  251. package/dist/runtime/interactive-resource-service.js +3 -0
  252. package/dist/runtime/interactive-resource-service.js.map +1 -0
  253. package/dist/runtime/plugin-inventory-entry.d.ts +5 -0
  254. package/dist/runtime/plugin-inventory-entry.d.ts.map +1 -0
  255. package/dist/runtime/plugin-inventory-entry.js +18 -0
  256. package/dist/runtime/plugin-inventory-entry.js.map +1 -0
  257. package/dist/runtime/plugin-inventory-service.d.ts +8 -0
  258. package/dist/runtime/plugin-inventory-service.d.ts.map +1 -0
  259. package/dist/runtime/plugin-inventory-service.js +3 -0
  260. package/dist/runtime/plugin-inventory-service.js.map +1 -0
  261. package/dist/runtime/plugin-manager-entry.d.ts +20 -0
  262. package/dist/runtime/plugin-manager-entry.d.ts.map +1 -0
  263. package/dist/runtime/plugin-manager-entry.js +96 -0
  264. package/dist/runtime/plugin-manager-entry.js.map +1 -0
  265. package/dist/runtime/plugin-observability-entry.d.ts +12 -0
  266. package/dist/runtime/plugin-observability-entry.d.ts.map +1 -0
  267. package/dist/runtime/plugin-observability-entry.js +73 -0
  268. package/dist/runtime/plugin-observability-entry.js.map +1 -0
  269. package/dist/runtime/product-host.d.ts +91 -0
  270. package/dist/runtime/product-host.d.ts.map +1 -0
  271. package/dist/runtime/product-host.js +529 -0
  272. package/dist/runtime/product-host.js.map +1 -0
  273. package/dist/runtime/session-factory.d.ts +17 -0
  274. package/dist/runtime/session-factory.d.ts.map +1 -0
  275. package/dist/runtime/session-factory.js +75 -0
  276. package/dist/runtime/session-factory.js.map +1 -0
  277. package/dist/runtime/session-host.d.ts +152 -0
  278. package/dist/runtime/session-host.d.ts.map +1 -0
  279. package/dist/runtime/session-host.js +895 -0
  280. package/dist/runtime/session-host.js.map +1 -0
  281. package/dist/runtime-core-entry.d.ts +11 -0
  282. package/dist/runtime-core-entry.d.ts.map +1 -0
  283. package/dist/runtime-core-entry.js +9 -0
  284. package/dist/runtime-core-entry.js.map +1 -0
  285. package/dist/session-factory-entry.d.ts +7 -0
  286. package/dist/session-factory-entry.d.ts.map +1 -0
  287. package/dist/session-factory-entry.js +9 -0
  288. package/dist/session-factory-entry.js.map +1 -0
  289. package/dist/session-store-jsonl-entry.d.ts +7 -0
  290. package/dist/session-store-jsonl-entry.d.ts.map +1 -0
  291. package/dist/session-store-jsonl-entry.js +33 -0
  292. package/dist/session-store-jsonl-entry.js.map +1 -0
  293. package/dist/startup.d.ts +12 -1
  294. package/dist/startup.d.ts.map +1 -1
  295. package/dist/startup.js +106 -15
  296. package/dist/startup.js.map +1 -1
  297. package/dist/subagents/index.d.ts +2 -0
  298. package/dist/subagents/index.d.ts.map +1 -0
  299. package/dist/subagents/index.js +2 -0
  300. package/dist/subagents/index.js.map +1 -0
  301. package/dist/subagents/service.d.ts +50 -0
  302. package/dist/subagents/service.d.ts.map +1 -0
  303. package/dist/subagents/service.js +521 -0
  304. package/dist/subagents/service.js.map +1 -0
  305. package/dist/ui-host.d.ts +125 -0
  306. package/dist/ui-host.d.ts.map +1 -0
  307. package/dist/ui-host.js +275 -0
  308. package/dist/ui-host.js.map +1 -0
  309. package/dist/web/assets/index-BwfuGMvv.css +1 -0
  310. package/dist/web/assets/index-DPUaJqFJ.js +41 -0
  311. package/dist/web/assets/index-DPUaJqFJ.js.map +1 -0
  312. package/dist/web/index.html +14 -0
  313. package/dist/web-command.d.ts +11 -0
  314. package/dist/web-command.d.ts.map +1 -0
  315. package/dist/web-command.js +114 -0
  316. package/dist/web-command.js.map +1 -0
  317. package/dist/web-frontend.d.ts +73 -0
  318. package/dist/web-frontend.d.ts.map +1 -0
  319. package/dist/web-frontend.js +249 -0
  320. package/dist/web-frontend.js.map +1 -0
  321. package/dist/web.d.ts +254 -0
  322. package/dist/web.d.ts.map +1 -0
  323. package/dist/web.js +740 -0
  324. package/dist/web.js.map +1 -0
  325. package/dist/webui-entry.d.ts +3 -0
  326. package/dist/webui-entry.d.ts.map +1 -0
  327. package/dist/webui-entry.js +73 -0
  328. package/dist/webui-entry.js.map +1 -0
  329. package/dist/webui.d.ts +91 -0
  330. package/dist/webui.d.ts.map +1 -0
  331. package/dist/webui.js +882 -0
  332. package/dist/webui.js.map +1 -0
  333. package/package.json +89 -8
package/dist/main.js CHANGED
@@ -1,547 +1,159 @@
1
- import { randomUUID } from "node:crypto";
2
- import { access, readdir, stat } from "node:fs/promises";
1
+ import { access } from "node:fs/promises";
3
2
  import { homedir } from "node:os";
4
- import { basename, dirname, extname, join, resolve } from "node:path";
5
- import { ProcessTerminal, TUI, truncateToWidth } from "@di-code/tui";
6
- import { runCli } from "./cli.js";
7
- import { loadImageInputs } from "./core/image-input.js";
8
- import { loadResources } from "./core/resources/loader.js";
9
- import { SessionManager } from "./core/session/session-manager.js";
10
- import { AgentSession } from "./core/session.js";
11
- import { buildSystemPrompt } from "./core/system-prompt.js";
12
- import { workspaceStorageKey } from "./core/user-data.js";
13
- import { ProjectTrustManager } from "./extensions/trust.js";
14
- import { DEFAULT_LOCALE, translate } from "./i18n.js";
15
- import { addMcpConfig, getMcpConfig, listMcpConfig, removeMcpConfig } from "./mcp/config.js";
16
- import { loadProjectMcp } from "./mcp/loader.js";
17
- import { InteractiveMode } from "./modes/interactive.js";
18
- import { runJsonMode } from "./modes/json.js";
19
- import { runPrintMode } from "./modes/print.js";
20
- import { loadPlugins } from "./plugins/loader.js";
21
- import { PluginManager } from "./plugins/manager.js";
22
- import { resolveThinkingLevelPreference } from "./startup.js";
23
- const MAX_SESSION_QUESTION_LENGTH = 72;
24
- function defaultSessionDirectory(agentDir, cwd) {
25
- return join(agentDir, "sessions", workspaceStorageKey(cwd));
26
- }
27
- const STARTUP_STATUS_COLORS = {
28
- error: "\x1b[31m",
29
- success: "\x1b[32m",
30
- warning: "\x1b[33m",
31
- reset: "\x1b[0m",
32
- };
33
- function formatMcpStatus(status) {
34
- switch (status.state) {
35
- case "connecting":
36
- return `${STARTUP_STATUS_COLORS.warning}MCP [loading]${STARTUP_STATUS_COLORS.reset} ${status.serverId}`;
37
- case "connected":
38
- return `${STARTUP_STATUS_COLORS.success}MCP [ok]${STARTUP_STATUS_COLORS.reset} ${status.serverId} (${status.tools} tools, ${status.resources} resources, ${status.prompts} prompts)`;
39
- case "failed":
40
- return `${STARTUP_STATUS_COLORS.error}MCP [error]${STARTUP_STATUS_COLORS.reset} ${status.serverId} (${status.stage}): ${status.message}`;
41
- }
42
- }
43
- function formatMcpDiagnostic(serverId, stage, message) {
44
- return `${STARTUP_STATUS_COLORS.error}MCP [error]${STARTUP_STATUS_COLORS.reset} ${serverId ?? "configuration"} (${stage}): ${message}\n`;
45
- }
46
- function formatPluginStatus(status) {
47
- switch (status.state) {
48
- case "loading":
49
- return `${STARTUP_STATUS_COLORS.warning}Plugin [loading]${STARTUP_STATUS_COLORS.reset} ${status.pluginId}`;
50
- case "loaded":
51
- return `${STARTUP_STATUS_COLORS.success}Plugin [ok]${STARTUP_STATUS_COLORS.reset} ${status.pluginId} (${status.tools} tools, ${status.commands} commands)`;
52
- case "failed":
53
- return `${STARTUP_STATUS_COLORS.error}Plugin [error]${STARTUP_STATUS_COLORS.reset} ${status.pluginId ?? "plugin"} (${status.stage}): ${status.message}`;
54
- }
55
- }
56
- function formatPluginDiagnostic(pluginId, stage, message) {
57
- return `${STARTUP_STATUS_COLORS.error}Plugin [error]${STARTUP_STATUS_COLORS.reset} ${pluginId ?? "plugin"} (${stage}): ${message}\n`;
58
- }
59
- function pluginStatusKey(status) {
60
- if (status.state === "failed" && status.pluginId === undefined)
61
- return `plugin:${status.sourcePath}`;
62
- return `plugin:${status.pluginId}`;
63
- }
64
- /** Renders startup states in place so terminal history retains only their final outcome. */
65
- export class StartupStatusRenderer {
66
- lines = [];
67
- indexes = new Map();
68
- write;
69
- replaceInPlace;
70
- width;
71
- constructor(write, replaceInPlace, width = 80) {
72
- this.write = write;
73
- this.replaceInPlace = replaceInPlace;
74
- this.width = width;
75
- }
76
- update(key, text) {
77
- const line = truncateToWidth(text.replace(/[\r\n]+/g, " "), Math.max(1, this.width), "...");
78
- const index = this.indexes.get(key);
79
- if (index === undefined || !this.replaceInPlace) {
80
- this.indexes.set(key, this.lines.length);
81
- this.lines.push(line);
82
- this.write(`${line}\n`);
83
- return;
84
- }
85
- this.lines[index] = line;
86
- const offset = this.lines.length - index;
87
- this.write(`\x1b[${offset}A\r\x1b[2K${line}\x1b[${offset}B\r`);
88
- }
89
- }
90
- function startupStatusRenderer(write, interactive) {
91
- const width = typeof process.stderr.columns === "number" && process.stderr.columns > 0 ? process.stderr.columns : 80;
92
- return new StartupStatusRenderer(write, interactive && process.stderr.isTTY === true, width);
93
- }
94
- async function openOrCreateSession(filePath, cwd, now) {
95
- try {
96
- await access(filePath);
97
- return await SessionManager.open(filePath, { now });
98
- }
99
- catch (cause) {
100
- if (!(cause instanceof Error && "code" in cause && cause.code === "ENOENT"))
101
- throw cause;
102
- return SessionManager.create({ filePath, cwd, now, deferCreate: true });
103
- }
104
- }
105
- function newSessionPath(sessionDirectory, now) {
106
- return join(sessionDirectory, `session-${now()}-${randomUUID().slice(0, 8)}.jsonl`);
107
- }
108
- async function mostRecentSessionPath(sessionDirectory) {
109
- let names;
110
- try {
111
- names = (await readdir(sessionDirectory, { withFileTypes: true }))
112
- .filter((entry) => entry.isFile() && extname(entry.name) === ".jsonl")
113
- .map((entry) => entry.name);
114
- }
115
- catch (cause) {
116
- if (cause instanceof Error && "code" in cause && cause.code === "ENOENT")
117
- return undefined;
118
- throw cause;
119
- }
120
- const candidates = await Promise.all(names.map(async (name) => {
121
- const filePath = join(sessionDirectory, name);
122
- try {
123
- return { filePath, modifiedAt: (await stat(filePath)).mtimeMs };
124
- }
125
- catch (cause) {
126
- if (cause instanceof Error && "code" in cause && cause.code === "ENOENT")
127
- return undefined;
128
- throw cause;
129
- }
130
- }));
131
- return candidates
132
- .filter((candidate) => candidate !== undefined)
133
- .sort((left, right) => right.modifiedAt - left.modifiedAt || right.filePath.localeCompare(left.filePath))[0]
134
- ?.filePath;
135
- }
136
- async function hasProjectLocalCapabilities(cwd) {
137
- const directories = [
3
+ import { join, resolve } from "node:path";
4
+ import { hostCommandRegistryKey, processExitKey, sessionStoreKey } from "@di-code/builtins";
5
+ import { createCompositionLoader } from "@di-code/plugin-loader";
6
+ import { createRootContext, redactSensitiveText } from "@di-code/plugin-runtime";
7
+ import { createCliParser } from "./cli.js";
8
+ import { importCompositionModule, resolveCompositionEntries, resolveManagedCompositionEntries, } from "./compositions.js";
9
+ import { createProjectTrustStore } from "./project-trust-entry.js";
10
+ import { pluginInventoryKey } from "./runtime/plugin-inventory-service.js";
11
+ function errorMessage(cause) {
12
+ return redactSensitiveText(cause instanceof Error ? cause.message : String(cause));
13
+ }
14
+ function isRun(command) {
15
+ return command.kind === "run";
16
+ }
17
+ function isMinimalCommand(command) {
18
+ return command.kind === "run" || command.kind === "plugin" || command.kind === "observe";
19
+ }
20
+ async function hasTrustedProjectContent(cwd) {
21
+ for (const path of [
138
22
  join(cwd, ".di-code", "skills"),
139
23
  join(cwd, ".agents", "skills"),
140
- join(cwd, ".di-code", "extensions"),
141
- join(cwd, ".di-code", "plugins"),
142
24
  join(cwd, ".di-code", "mcp.local.json"),
143
25
  join(cwd, ".mcp.json"),
144
- ];
145
- const results = await Promise.all(directories.map(async (directory) => {
26
+ ]) {
146
27
  try {
147
- const metadata = await stat(directory);
148
- return metadata.isDirectory() || metadata.isFile();
28
+ await access(path);
29
+ return true;
149
30
  }
150
31
  catch (cause) {
151
- if (cause instanceof Error && "code" in cause && cause.code === "ENOENT")
152
- return false;
153
- return false;
32
+ if (!(cause instanceof Error && "code" in cause && cause.code === "ENOENT"))
33
+ throw cause;
154
34
  }
155
- }));
156
- return results.some(Boolean);
157
- }
158
- async function selectStartupSession(command, allowedRoot, agentDir, now) {
159
- const sessionDirectory = defaultSessionDirectory(agentDir, allowedRoot);
160
- if (command.sessionPath !== undefined) {
161
- return openOrCreateSession(resolve(allowedRoot, command.sessionPath), allowedRoot, now);
162
- }
163
- if (command.continueSession) {
164
- const recentPath = await mostRecentSessionPath(sessionDirectory);
165
- if (recentPath !== undefined)
166
- return SessionManager.open(recentPath, { now });
167
35
  }
168
- return SessionManager.create({
169
- filePath: newSessionPath(sessionDirectory, now),
170
- cwd: allowedRoot,
171
- now,
172
- deferCreate: true,
173
- });
36
+ return false;
174
37
  }
175
- function formatSessionTimestamp(timestamp, fallback, timeZone) {
176
- const date = new Date(timestamp);
177
- if (Number.isNaN(date.getTime()))
178
- return fallback;
38
+ /** Starts a composition profile and executes its registered host command. */
39
+ export async function runMinimalProfile(args, options) {
40
+ const parser = createCliParser();
41
+ let command;
179
42
  try {
180
- const parts = new Map(new Intl.DateTimeFormat("en-CA", {
181
- timeZone: timeZone ?? Intl.DateTimeFormat().resolvedOptions().timeZone,
182
- year: "numeric",
183
- month: "2-digit",
184
- day: "2-digit",
185
- hour: "2-digit",
186
- minute: "2-digit",
187
- hourCycle: "h23",
188
- })
189
- .formatToParts(date)
190
- .filter((part) => part.type !== "literal")
191
- .map((part) => [part.type, part.value]));
192
- const year = parts.get("year");
193
- const month = parts.get("month");
194
- const day = parts.get("day");
195
- const hour = parts.get("hour");
196
- const minute = parts.get("minute");
197
- if (!year || !month || !day || !hour || !minute)
198
- return fallback;
199
- return `${year}-${month}-${day} ${hour}:${minute}`;
43
+ command = parser.parse(args);
200
44
  }
201
- catch {
202
- return fallback;
45
+ catch (cause) {
46
+ options.stderr(`${errorMessage(cause)}\n`);
47
+ return 1;
203
48
  }
204
- }
205
- export function formatSessionLabel(manager, timeZone) {
206
- const firstUserEntry = manager.entries.find((entry) => entry.type === "message" && entry.message.role === "user");
207
- const fileName = basename(manager.filePath, extname(manager.filePath));
208
- if (firstUserEntry?.type !== "message" || firstUserEntry.message.role !== "user") {
209
- return `${fileName} (${formatSessionTimestamp(Date.parse(manager.header.timestamp), manager.header.timestamp, timeZone)})`;
49
+ if (command.kind === "help") {
50
+ options.stdout(`${parser.help("en")}\n`);
51
+ return 0;
210
52
  }
211
- const question = firstUserEntry.message.content
212
- .filter((content) => content.type === "text")
213
- .map((content) => content.text)
214
- .join(" ")
215
- .replace(/\s+/g, " ")
216
- .trim();
217
- const label = question.length > MAX_SESSION_QUESTION_LENGTH
218
- ? `${question.slice(0, MAX_SESSION_QUESTION_LENGTH - 3)}...`
219
- : question || fileName;
220
- const timestamp = formatSessionTimestamp(firstUserEntry.message.timestamp, firstUserEntry.timestamp, timeZone);
221
- return `${label} (${timestamp})`;
222
- }
223
- async function sessionChoices(sessionDirectory, currentFile, open) {
224
- let names = [];
225
- try {
226
- names = (await readdir(sessionDirectory, { withFileTypes: true }))
227
- .filter((entry) => entry.isFile() && extname(entry.name) === ".jsonl")
228
- .map((entry) => entry.name)
229
- .sort();
53
+ if (command.kind === "version") {
54
+ options.stdout(`${options.version}\n`);
55
+ return 0;
230
56
  }
231
- catch (cause) {
232
- if (!(cause instanceof Error && "code" in cause && cause.code === "ENOENT"))
233
- throw cause;
57
+ if (!isMinimalCommand(command)) {
58
+ options.stderr("MCP commands are unavailable in the minimal profile.\n");
59
+ return 1;
234
60
  }
235
- return Promise.all(names
236
- .filter((name) => resolve(sessionDirectory, name) !== resolve(currentFile))
237
- .map(async (name) => {
238
- const filePath = join(sessionDirectory, name);
239
- const id = basename(name, extname(name));
240
- let label = id;
241
- try {
242
- label = formatSessionLabel(await SessionManager.open(filePath));
61
+ if (isRun(command) && command.mode === "interactive" && !options.interactive?.isInteractiveTerminal) {
62
+ options.stderr("Interactive mode requires an interactive TTY.\n");
63
+ return 1;
64
+ }
65
+ const mode = isRun(command) ? command.mode : "print";
66
+ const observability = command.kind === "observe";
67
+ const allowedRoot = resolve(options.allowedRoot ?? process.cwd());
68
+ const agentDir = resolve(options.agentDir ?? join(homedir(), ".di-code"));
69
+ const trustStore = createProjectTrustStore(join(agentDir, "trust.json"));
70
+ if (isRun(command) && command.projectTrust !== undefined)
71
+ await trustStore.set(allowedRoot, command.projectTrust);
72
+ let projectTrusted = isRun(command) && !command.noProjectPlugins && (await trustStore.get(allowedRoot)) === true;
73
+ if (isRun(command) &&
74
+ command.mode === "interactive" &&
75
+ !projectTrusted &&
76
+ command.projectTrust === undefined &&
77
+ options.interactive?.promptProjectTrust &&
78
+ (await hasTrustedProjectContent(allowedRoot))) {
79
+ projectTrusted = await options.interactive.promptProjectTrust(allowedRoot);
80
+ await trustStore.set(allowedRoot, projectTrusted);
81
+ }
82
+ const managedEntries = await resolveManagedCompositionEntries(agentDir);
83
+ const compositionEntries = await resolveCompositionEntries(isRun(command) ? (command.profile ?? command.mode) : "base", {
84
+ cwd: allowedRoot,
85
+ agentDir,
86
+ ...(isRun(command) && command.compositionPath ? { compositionPath: command.compositionPath } : {}),
87
+ includeProjectComposition: projectTrusted,
88
+ observability,
89
+ allowedRoot,
90
+ });
91
+ const context = createRootContext({ id: "minimal-profile", mode, trustedProject: projectTrusted });
92
+ const unsubscribe = context.events.subscribe((event) => options.onRuntimeEvent?.(event));
93
+ const loader = createCompositionLoader({
94
+ context,
95
+ entries: [...compositionEntries, ...managedEntries],
96
+ importModule: options.importModule ?? importCompositionModule,
97
+ projectTrusted,
98
+ });
99
+ try {
100
+ await loader.load();
101
+ context.require(pluginInventoryKey).set(loader.tree.snapshot());
102
+ const host = context.require(hostCommandRegistryKey);
103
+ let name;
104
+ let input;
105
+ if (command.kind === "observe") {
106
+ name = command.action === "trace" ? "trace-plugins" : "dump-composition";
107
+ input = { stdout: options.stdout };
243
108
  }
244
- catch {
245
- // Keep damaged sessions selectable so opening one can report the detailed load error.
109
+ else if (command.kind === "plugin") {
110
+ name = "plugin";
111
+ input = { ...command, stdout: options.stdout, stderr: options.stderr };
246
112
  }
247
- return {
248
- id,
249
- label,
250
- description: filePath,
251
- open: () => open(filePath),
252
- };
253
- }));
254
- }
255
- export async function runMain(args, options) {
256
- const dependencies = {
257
- stdout: options.stdout,
258
- stderr: options.stderr,
259
- version: options.version,
260
- locale: options.locale ?? options.startupConfiguration?.locale ?? DEFAULT_LOCALE,
261
- plugin: async (command) => {
262
- const agentDir = resolve(options.agentDir ?? join(homedir(), ".di-code"));
263
- const manager = new PluginManager({ agentDir });
264
- try {
265
- switch (command.action) {
266
- case "list":
267
- for (const plugin of await manager.list())
268
- options.stdout(`${plugin.id}\t${plugin.enabled ? "enabled" : "disabled"}\t${plugin.manifest.version}\n`);
269
- return 0;
270
- case "install": {
271
- const plugin = await manager.install(command.argument);
272
- options.stdout(`Installed ${plugin.id}\n`);
273
- return 0;
274
- }
275
- case "enable":
276
- await manager.enable(command.argument);
277
- return 0;
278
- case "disable":
279
- await manager.disable(command.argument);
280
- return 0;
281
- case "update":
282
- await manager.update(command.argument);
283
- return 0;
284
- case "remove":
285
- await manager.remove(command.argument);
286
- return 0;
287
- }
288
- }
289
- catch (cause) {
290
- options.stderr(`${cause instanceof Error ? cause.message : String(cause)}\n`);
291
- return 1;
292
- }
293
- },
294
- mcp: async (command) => {
295
- const cwd = resolve(options.allowedRoot ?? process.cwd());
296
- const scope = command.scope;
297
- const trustManager = new ProjectTrustManager(join(options.agentDir ?? join(homedir(), ".di-code"), "trust.json"));
298
- const requireProjectTrust = async (selected) => {
299
- if ((selected === "local" || selected === "project") && (await trustManager.get(cwd)) !== true)
300
- throw new Error(`Project trust is required to modify the ${selected} MCP scope.`);
301
- };
302
- try {
303
- switch (command.action) {
304
- case "add": {
305
- const selected = scope ?? "local";
306
- await requireProjectTrust(selected);
307
- const config = command.transport === "stdio"
308
- ? {
309
- command: command.command,
310
- ...(command.args && command.args.length > 0 ? { args: command.args } : {}),
311
- }
312
- : { type: "http", url: command.url };
313
- await addMcpConfig(cwd, selected, command.serverId, config);
314
- options.stdout(`Added MCP server "${command.serverId}" to ${selected} scope.\n`);
315
- return 0;
316
- }
317
- case "list": {
318
- const scopes = scope ? [scope] : ["local", "project", "user"];
319
- for (const selected of scopes) {
320
- for (const entry of await listMcpConfig(cwd, selected))
321
- options.stdout(`${entry.id}\t${entry.scope}\t${JSON.stringify(entry.config)}\n`);
322
- }
323
- return 0;
324
- }
325
- case "get": {
326
- const entry = await getMcpConfig(cwd, command.serverId, scope);
327
- if (!entry)
328
- throw new Error(`MCP server "${command.serverId}" was not found.`);
329
- options.stdout(`${JSON.stringify({ id: entry.id, scope: entry.scope, config: entry.config })}\n`);
330
- return 0;
331
- }
332
- case "remove": {
333
- const selected = scope ?? "local";
334
- await requireProjectTrust(selected);
335
- await removeMcpConfig(cwd, selected, command.serverId);
336
- options.stdout(`Removed MCP server "${command.serverId}" from ${selected} scope.\n`);
337
- return 0;
338
- }
339
- }
340
- }
341
- catch (cause) {
342
- options.stderr(`${cause instanceof Error ? cause.message : String(cause)}\n`);
343
- return 1;
344
- }
345
- },
346
- run: async (command) => {
347
- const allowedRoot = resolve(options.allowedRoot ?? process.cwd());
348
- const now = options.now ?? Date.now;
349
- const agentDir = resolve(options.agentDir ?? join(homedir(), ".di-code"));
350
- const trustManager = new ProjectTrustManager(join(agentDir, "trust.json"));
351
- if (command.projectTrust !== undefined)
352
- await trustManager.set(allowedRoot, command.projectTrust);
353
- let persistedTrust = await trustManager.get(allowedRoot);
354
- const shouldPromptForTrust = command.mode === "interactive" &&
355
- options.isInteractiveTerminal === true &&
356
- command.projectTrust === undefined &&
357
- persistedTrust === null &&
358
- options.promptProjectTrust !== undefined &&
359
- (await hasProjectLocalCapabilities(allowedRoot));
360
- if (shouldPromptForTrust) {
361
- let decision = false;
362
- try {
363
- decision = await options.promptProjectTrust(allowedRoot);
364
- }
365
- catch {
366
- // Fail closed when the prompt is interrupted or unavailable.
367
- }
368
- await trustManager.set(allowedRoot, decision);
369
- persistedTrust = decision;
370
- }
371
- const runtime = await options.createRuntime(command);
372
- if (runtime === undefined)
373
- return 0;
374
- const resources = await loadResources({
375
- cwd: allowedRoot,
376
- agentDir,
377
- projectTrusted: persistedTrust === true,
378
- noSkills: command.noSkills,
379
- noContextFiles: command.noContextFiles,
380
- skillPaths: command.skillPaths,
381
- });
382
- for (const diagnostic of resources.diagnostics) {
383
- if (diagnostic.kind !== "skill")
384
- continue;
385
- options.stderr(`${JSON.stringify({ type: "skill_diagnostic", path: diagnostic.path, stage: diagnostic.stage, severity: diagnostic.severity, message: diagnostic.message })}\n`);
386
- }
387
- const interactivePluginStatus = command.mode === "interactive";
388
- const startupStatus = startupStatusRenderer(options.stderr, interactivePluginStatus);
389
- const pluginStatusFailures = new Set();
390
- const extensions = await loadPlugins({
113
+ else if (command.mode === "interactive") {
114
+ name = "interactive";
115
+ input = {
116
+ command,
391
117
  cwd: allowedRoot,
392
118
  agentDir,
393
- trustManager,
394
- mode: command.mode,
395
- ...(interactivePluginStatus
396
- ? {
397
- onPluginLoadStatus: (status) => {
398
- if (status.state === "failed")
399
- pluginStatusFailures.add(status.sourcePath);
400
- startupStatus.update(pluginStatusKey(status), formatPluginStatus(status));
401
- },
402
- }
403
- : {}),
404
- });
405
- for (const diagnostic of extensions.diagnostics) {
406
- if (interactivePluginStatus) {
407
- if (pluginStatusFailures.has(diagnostic.sourcePath))
408
- continue;
409
- options.stderr(formatPluginDiagnostic(diagnostic.pluginId, diagnostic.stage, diagnostic.message));
410
- continue;
411
- }
412
- options.stderr(`${JSON.stringify({ type: "plugin_diagnostic", pluginId: diagnostic.pluginId, stage: diagnostic.stage, sourcePath: diagnostic.sourcePath, severity: diagnostic.severity, message: diagnostic.message })}\n`);
413
- }
414
- const interactiveMcpStatus = command.mode === "interactive";
415
- const mcp = await loadProjectMcp({
416
- cwd: allowedRoot,
417
- projectTrusted: persistedTrust === true,
418
- homeDirectory: homedir(),
419
- reservedToolNames: [
420
- "read",
421
- "write",
422
- "edit",
423
- "bash",
424
- "load_skill",
425
- ...extensions.host.listTools().map((tool) => tool.name),
426
- ],
427
- ...(interactiveMcpStatus
428
- ? {
429
- onServerConnectionStatus: (status) => startupStatus.update(`mcp:${status.serverId}`, formatMcpStatus(status)),
430
- }
119
+ projectTrusted,
120
+ stderr: options.stderr,
121
+ ...(options.interactive?.startInteractiveMode
122
+ ? { startInteractiveMode: options.interactive.startInteractiveMode }
431
123
  : {}),
432
- });
433
- for (const diagnostic of mcp.diagnostics) {
434
- if (interactiveMcpStatus) {
435
- if (diagnostic.serverId && (diagnostic.stage === "connect" || diagnostic.stage === "list_tools"))
436
- continue;
437
- options.stderr(formatMcpDiagnostic(diagnostic.serverId, diagnostic.stage, diagnostic.message));
438
- continue;
439
- }
440
- options.stderr(`${JSON.stringify({ type: "mcp_diagnostic", serverId: diagnostic.serverId, stage: diagnostic.stage, message: diagnostic.message })}\n`);
441
- }
442
- const systemPrompt = buildSystemPrompt({ cwd: allowedRoot, ...resources });
443
- const manager = await selectStartupSession(command, allowedRoot, agentDir, now);
444
- const sessionFile = manager.filePath;
445
- const thinkingLevel = resolveThinkingLevelPreference(options.startupConfiguration, runtime);
446
- const session = new AgentSession({
447
- allowedRoot,
448
- provider: runtime.provider,
449
- model: runtime.model,
450
- ...(thinkingLevel === undefined ? {} : { thinkingLevel }),
451
- systemPrompt,
452
- skills: resources.skills,
453
- now: options.now,
454
- sessionManager: manager,
455
- extensionHost: extensions.host,
456
- externalTools: mcp.tools,
457
- });
458
- const imagePaths = command.imagePaths ?? [];
459
- const promptRunner = {
460
- prompt: async (text) => session.promptWithImages(text, await loadImageInputs(imagePaths, allowedRoot)),
461
- subscribe: session.subscribe.bind(session),
462
124
  };
463
- if (command.mode === "json") {
464
- await extensions.host.emit({ type: "session_start", cwd: allowedRoot });
465
- try {
466
- return await runJsonMode(command.prompt, promptRunner, options);
467
- }
468
- finally {
469
- await extensions.host.emit({ type: "session_shutdown", reason: "user" });
470
- await mcp.manager.close();
471
- }
472
- }
473
- if (command.mode === "interactive") {
474
- const terminal = new ProcessTerminal();
475
- const tui = new TUI(terminal);
476
- const mode = new InteractiveMode({
477
- session,
478
- tui,
479
- agentDir,
480
- locale: options.locale ?? options.startupConfiguration?.locale ?? DEFAULT_LOCALE,
481
- onExit: () => {
482
- void mcp.manager.close();
483
- },
484
- extensionHost: extensions.host,
485
- ...(options.startupConfiguration
486
- ? { providerOnboarding: { configuration: options.startupConfiguration, agentDir } }
487
- : {}),
488
- sessions: [
489
- {
490
- id: "new-session",
491
- label: translate(options.locale ?? options.startupConfiguration?.locale ?? DEFAULT_LOCALE, "newSession"),
492
- description: translate(options.locale ?? options.startupConfiguration?.locale ?? DEFAULT_LOCALE, "newSessionDescription"),
493
- open: async () => {
494
- const filePath = newSessionPath(dirname(sessionFile), now);
495
- const nextManager = await SessionManager.create({
496
- filePath,
497
- cwd: allowedRoot,
498
- now,
499
- deferCreate: true,
500
- });
501
- return new AgentSession({
502
- allowedRoot,
503
- provider: runtime.provider,
504
- model: runtime.model,
505
- ...(thinkingLevel === undefined ? {} : { thinkingLevel }),
506
- systemPrompt,
507
- skills: resources.skills,
508
- now: options.now,
509
- sessionManager: nextManager,
510
- extensionHost: extensions.host,
511
- externalTools: mcp.tools,
512
- });
513
- },
514
- },
515
- ...(await sessionChoices(dirname(sessionFile), sessionFile, async (filePath) => {
516
- const nextManager = await SessionManager.open(filePath, { now });
517
- return new AgentSession({
518
- allowedRoot,
519
- provider: runtime.provider,
520
- model: runtime.model,
521
- ...(thinkingLevel === undefined ? {} : { thinkingLevel }),
522
- systemPrompt,
523
- skills: resources.skills,
524
- now: options.now,
525
- sessionManager: nextManager,
526
- extensionHost: extensions.host,
527
- externalTools: mcp.tools,
528
- });
529
- })),
530
- ],
531
- });
532
- mode.start(command.prompt);
533
- return 0;
534
- }
535
- await extensions.host.emit({ type: "session_start", cwd: allowedRoot });
125
+ }
126
+ else {
127
+ name = command.mode;
128
+ input = { prompt: command.prompt, stdout: options.stdout };
129
+ }
130
+ const code = await host.execute(name, input, context.signal);
131
+ const processExit = context.require(processExitKey);
132
+ processExit.setCode(code);
133
+ return processExit.code();
134
+ }
135
+ catch (cause) {
136
+ options.stderr(`${errorMessage(cause).replace(/^Required entry agent-loop failed: /, "")}\n`);
137
+ return 1;
138
+ }
139
+ finally {
140
+ const memory = context.get(sessionStoreKey);
141
+ try {
536
142
  try {
537
- return await runPrintMode(command.prompt, promptRunner, options);
143
+ await loader.dispose();
538
144
  }
539
145
  finally {
540
- await extensions.host.emit({ type: "session_shutdown", reason: "user" });
541
- await mcp.manager.close();
146
+ await context.dispose();
542
147
  }
543
- },
544
- };
545
- return runCli(args, dependencies);
148
+ }
149
+ finally {
150
+ unsubscribe();
151
+ if (memory) {
152
+ memory.dispose();
153
+ if (memory.disposed())
154
+ options.onSessionDisposed?.();
155
+ }
156
+ }
157
+ }
546
158
  }
547
159
  //# sourceMappingURL=main.js.map