@f5xc-salesdemos/xcsh 2.2.0 → 14.0.2

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 (1518) hide show
  1. package/CHANGELOG.md +6854 -24
  2. package/README.md +11 -610
  3. package/examples/README.md +8 -15
  4. package/examples/custom-tools/README.md +109 -0
  5. package/examples/custom-tools/hello/index.ts +20 -0
  6. package/examples/custom-tools/todo/index.ts +206 -0
  7. package/examples/extensions/README.md +78 -143
  8. package/examples/extensions/api-demo.ts +89 -0
  9. package/examples/extensions/chalk-logger.ts +25 -0
  10. package/examples/extensions/hello.ts +24 -18
  11. package/examples/extensions/pirate.ts +5 -9
  12. package/examples/extensions/plan-mode.ts +551 -0
  13. package/examples/extensions/reload-runtime.ts +1 -1
  14. package/examples/extensions/todo.ts +18 -19
  15. package/examples/extensions/tools.ts +23 -19
  16. package/examples/extensions/with-deps/index.ts +5 -1
  17. package/examples/extensions/with-deps/package-lock.json +2 -2
  18. package/examples/extensions/with-deps/package.json +2 -8
  19. package/examples/hooks/README.md +56 -0
  20. package/examples/hooks/auto-commit-on-exit.ts +48 -0
  21. package/examples/hooks/confirm-destructive.ts +58 -0
  22. package/examples/hooks/custom-compaction.ts +115 -0
  23. package/examples/hooks/dirty-repo-guard.ts +51 -0
  24. package/examples/hooks/file-trigger.ts +40 -0
  25. package/examples/hooks/git-checkpoint.ts +52 -0
  26. package/examples/hooks/handoff.ts +149 -0
  27. package/examples/hooks/permission-gate.ts +33 -0
  28. package/examples/hooks/protected-paths.ts +29 -0
  29. package/examples/hooks/qna.ts +118 -0
  30. package/examples/hooks/status-line.ts +39 -0
  31. package/examples/sdk/01-minimal.ts +3 -4
  32. package/examples/sdk/02-custom-model.ts +9 -9
  33. package/examples/sdk/03-custom-prompt.ts +11 -23
  34. package/examples/sdk/04-skills.ts +23 -32
  35. package/examples/sdk/06-extensions.ts +14 -22
  36. package/examples/sdk/06-hooks.ts +61 -0
  37. package/examples/sdk/07-context-files.ts +18 -23
  38. package/examples/sdk/08-prompt-templates.ts +14 -21
  39. package/examples/sdk/08-slash-commands.ts +46 -0
  40. package/examples/sdk/09-api-keys-and-oauth.ts +15 -9
  41. package/examples/sdk/11-sessions.ts +3 -4
  42. package/examples/sdk/README.md +117 -92
  43. package/package.json +507 -82
  44. package/scripts/format-prompts.ts +68 -0
  45. package/scripts/generate-docs-index.ts +40 -0
  46. package/scripts/generate-template.ts +32 -0
  47. package/src/async/index.ts +1 -0
  48. package/src/async/job-manager.ts +383 -0
  49. package/src/autoresearch/apply-contract-to-state.ts +24 -0
  50. package/src/autoresearch/command-resume.md +17 -0
  51. package/src/autoresearch/contract.ts +288 -0
  52. package/src/autoresearch/dashboard.ts +446 -0
  53. package/src/autoresearch/git.ts +329 -0
  54. package/src/autoresearch/helpers.ts +507 -0
  55. package/src/autoresearch/index.ts +534 -0
  56. package/src/autoresearch/prompt.md +244 -0
  57. package/src/autoresearch/resume-message.md +16 -0
  58. package/src/autoresearch/state.ts +380 -0
  59. package/src/autoresearch/tools/init-experiment.ts +395 -0
  60. package/src/autoresearch/tools/log-experiment.ts +778 -0
  61. package/src/autoresearch/tools/run-experiment.ts +678 -0
  62. package/src/autoresearch/types.ts +218 -0
  63. package/src/bun-imports.d.ts +22 -0
  64. package/src/capability/context-file.ts +44 -0
  65. package/src/capability/extension-module.ts +34 -0
  66. package/src/capability/extension.ts +47 -0
  67. package/src/capability/fs.ts +107 -0
  68. package/src/capability/hook.ts +40 -0
  69. package/src/capability/index.ts +436 -0
  70. package/src/capability/instruction.ts +37 -0
  71. package/src/capability/mcp.ts +74 -0
  72. package/src/capability/prompt.ts +35 -0
  73. package/src/capability/rule.ts +224 -0
  74. package/src/capability/settings.ts +34 -0
  75. package/src/capability/skill.ts +49 -0
  76. package/src/capability/slash-command.ts +40 -0
  77. package/src/capability/ssh.ts +41 -0
  78. package/src/capability/system-prompt.ts +34 -0
  79. package/src/capability/tool.ts +38 -0
  80. package/src/capability/types.ts +168 -0
  81. package/src/cli/agents-cli.ts +138 -0
  82. package/src/cli/args.ts +283 -0
  83. package/src/cli/classify-install-target.ts +50 -0
  84. package/src/cli/commands/init-xdg.ts +27 -0
  85. package/src/cli/config-cli.ts +418 -0
  86. package/src/cli/file-processor.ts +123 -0
  87. package/src/cli/grep-cli.ts +160 -0
  88. package/src/cli/grievances-cli.ts +78 -0
  89. package/src/cli/initial-message.ts +58 -0
  90. package/src/cli/jupyter-cli.ts +106 -0
  91. package/src/cli/list-models.ts +89 -0
  92. package/src/cli/plugin-cli.ts +964 -0
  93. package/src/cli/read-cli.ts +67 -0
  94. package/src/cli/session-picker.ts +52 -0
  95. package/src/cli/setup-cli.ts +376 -0
  96. package/src/cli/shell-cli.ts +174 -0
  97. package/src/cli/ssh-cli.ts +179 -0
  98. package/src/cli/stats-cli.ts +182 -0
  99. package/src/cli/update-cli.ts +342 -0
  100. package/src/cli/web-search-cli.ts +133 -0
  101. package/src/cli.ts +96 -0
  102. package/src/commands/agents.ts +57 -0
  103. package/src/commands/commit.ts +36 -0
  104. package/src/commands/config.ts +51 -0
  105. package/src/commands/grep.ts +48 -0
  106. package/src/commands/grievances.ts +20 -0
  107. package/src/commands/jupyter.ts +32 -0
  108. package/src/commands/launch.ts +141 -0
  109. package/src/commands/plugin.ts +78 -0
  110. package/src/commands/read.ts +33 -0
  111. package/src/commands/setup.ts +42 -0
  112. package/src/commands/shell.ts +29 -0
  113. package/src/commands/ssh.ts +60 -0
  114. package/src/commands/stats.ts +29 -0
  115. package/src/commands/update.ts +21 -0
  116. package/src/commands/web-search.ts +42 -0
  117. package/src/commit/agentic/agent.ts +314 -0
  118. package/src/commit/agentic/fallback.ts +96 -0
  119. package/src/commit/agentic/index.ts +354 -0
  120. package/src/commit/agentic/prompts/analyze-file.md +22 -0
  121. package/src/commit/agentic/prompts/session-user.md +25 -0
  122. package/src/commit/agentic/prompts/split-confirm.md +1 -0
  123. package/src/commit/agentic/prompts/system.md +38 -0
  124. package/src/commit/agentic/state.ts +60 -0
  125. package/src/commit/agentic/tools/analyze-file.ts +128 -0
  126. package/src/commit/agentic/tools/git-file-diff.ts +191 -0
  127. package/src/commit/agentic/tools/git-hunk.ts +50 -0
  128. package/src/commit/agentic/tools/git-overview.ts +81 -0
  129. package/src/commit/agentic/tools/index.ts +54 -0
  130. package/src/commit/agentic/tools/propose-changelog.ts +139 -0
  131. package/src/commit/agentic/tools/propose-commit.ts +122 -0
  132. package/src/commit/agentic/tools/recent-commits.ts +81 -0
  133. package/src/commit/agentic/tools/schemas.ts +31 -0
  134. package/src/commit/agentic/tools/split-commit.ts +251 -0
  135. package/src/commit/agentic/topo-sort.ts +44 -0
  136. package/src/commit/agentic/trivial.ts +51 -0
  137. package/src/commit/agentic/validation.ts +183 -0
  138. package/src/commit/analysis/conventional.ts +122 -0
  139. package/src/commit/analysis/index.ts +4 -0
  140. package/src/commit/analysis/scope.ts +242 -0
  141. package/src/commit/analysis/summary.ts +105 -0
  142. package/src/commit/analysis/validation.ts +66 -0
  143. package/src/commit/changelog/detect.ts +40 -0
  144. package/src/commit/changelog/generate.ts +101 -0
  145. package/src/commit/changelog/index.ts +234 -0
  146. package/src/commit/changelog/parse.ts +44 -0
  147. package/src/commit/cli.ts +85 -0
  148. package/src/commit/git/diff.ts +148 -0
  149. package/src/commit/index.ts +5 -0
  150. package/src/commit/map-reduce/index.ts +69 -0
  151. package/src/commit/map-reduce/map-phase.ts +193 -0
  152. package/src/commit/map-reduce/reduce-phase.ts +108 -0
  153. package/src/commit/map-reduce/utils.ts +9 -0
  154. package/src/commit/message.ts +11 -0
  155. package/src/commit/model-selection.ts +63 -0
  156. package/src/commit/pipeline.ts +242 -0
  157. package/src/commit/prompts/analysis-system.md +148 -0
  158. package/src/commit/prompts/analysis-user.md +38 -0
  159. package/src/commit/prompts/changelog-system.md +50 -0
  160. package/src/commit/prompts/changelog-user.md +18 -0
  161. package/src/commit/prompts/file-observer-system.md +24 -0
  162. package/src/commit/prompts/file-observer-user.md +8 -0
  163. package/src/commit/prompts/reduce-system.md +50 -0
  164. package/src/commit/prompts/reduce-user.md +17 -0
  165. package/src/commit/prompts/summary-retry.md +3 -0
  166. package/src/commit/prompts/summary-system.md +38 -0
  167. package/src/commit/prompts/summary-user.md +13 -0
  168. package/src/commit/prompts/types-description.md +2 -0
  169. package/src/commit/types.ts +118 -0
  170. package/src/commit/utils/exclusions.ts +42 -0
  171. package/src/commit/utils.ts +44 -0
  172. package/src/config/file-lock.ts +121 -0
  173. package/src/config/keybindings.ts +493 -0
  174. package/src/config/mcp-schema.json +230 -0
  175. package/src/config/model-registry.ts +1917 -0
  176. package/src/config/model-resolver.ts +1064 -0
  177. package/src/config/prompt-templates.ts +255 -0
  178. package/src/config/resolve-config-value.ts +94 -0
  179. package/src/config/settings-schema.ts +1929 -0
  180. package/src/config/settings.ts +701 -0
  181. package/src/config.ts +419 -0
  182. package/src/cursor.ts +304 -0
  183. package/src/dap/client.ts +674 -0
  184. package/src/dap/config.ts +150 -0
  185. package/src/dap/defaults.json +211 -0
  186. package/src/dap/index.ts +4 -0
  187. package/src/dap/session.ts +1255 -0
  188. package/src/dap/types.ts +600 -0
  189. package/src/debug/index.ts +438 -0
  190. package/src/debug/log-formatting.ts +58 -0
  191. package/src/debug/log-viewer.ts +908 -0
  192. package/src/debug/profiler.ts +158 -0
  193. package/src/debug/report-bundle.ts +365 -0
  194. package/src/debug/system-info.ts +107 -0
  195. package/src/discovery/agents-md.ts +67 -0
  196. package/src/discovery/agents.ts +219 -0
  197. package/src/discovery/builtin.ts +851 -0
  198. package/src/discovery/claude-plugins.ts +296 -0
  199. package/src/discovery/claude.ts +543 -0
  200. package/src/discovery/cline.ts +83 -0
  201. package/src/discovery/codex.ts +535 -0
  202. package/src/discovery/cursor.ts +220 -0
  203. package/src/discovery/gemini.ts +396 -0
  204. package/src/discovery/github.ts +118 -0
  205. package/src/discovery/helpers.ts +968 -0
  206. package/src/discovery/index.ts +79 -0
  207. package/src/discovery/mcp-json.ts +171 -0
  208. package/src/discovery/opencode.ts +393 -0
  209. package/src/discovery/plugin-dir-roots.ts +28 -0
  210. package/src/discovery/ssh.ts +153 -0
  211. package/src/discovery/substitute-plugin-root.ts +29 -0
  212. package/src/discovery/vscode.ts +105 -0
  213. package/src/discovery/windsurf.ts +147 -0
  214. package/src/edit/diff.ts +818 -0
  215. package/src/edit/index.ts +314 -0
  216. package/src/edit/line-hash.ts +67 -0
  217. package/src/edit/modes/chunk.ts +454 -0
  218. package/src/edit/modes/hashline.ts +1341 -0
  219. package/src/edit/modes/patch.ts +1785 -0
  220. package/src/edit/modes/replace.ts +1107 -0
  221. package/src/edit/normalize.ts +375 -0
  222. package/src/edit/renderer.ts +467 -0
  223. package/src/exa/factory.ts +59 -0
  224. package/src/exa/index.ts +27 -0
  225. package/src/exa/mcp-client.ts +291 -0
  226. package/src/exa/render.ts +244 -0
  227. package/src/exa/researcher.ts +47 -0
  228. package/src/exa/search.ts +86 -0
  229. package/src/exa/types.ts +166 -0
  230. package/src/exa/websets.ts +247 -0
  231. package/src/exec/bash-executor.ts +240 -0
  232. package/src/exec/exec.ts +53 -0
  233. package/src/exec/idle-timeout-watchdog.ts +126 -0
  234. package/src/exec/non-interactive-env.ts +48 -0
  235. package/src/export/custom-share.ts +65 -0
  236. package/src/export/html/index.ts +161 -0
  237. package/src/export/html/template.css +919 -0
  238. package/src/export/html/template.generated.ts +2 -0
  239. package/src/export/html/template.html +46 -0
  240. package/src/export/html/template.js +1458 -0
  241. package/src/export/html/template.macro.ts +24 -0
  242. package/src/export/ttsr.ts +434 -0
  243. package/src/extensibility/custom-commands/bundled/ci-green/index.ts +25 -0
  244. package/src/extensibility/custom-commands/bundled/review/index.ts +435 -0
  245. package/src/extensibility/custom-commands/index.ts +2 -0
  246. package/src/extensibility/custom-commands/loader.ts +236 -0
  247. package/src/extensibility/custom-commands/types.ts +111 -0
  248. package/src/extensibility/custom-tools/index.ts +7 -0
  249. package/src/extensibility/custom-tools/loader.ts +238 -0
  250. package/src/extensibility/custom-tools/types.ts +255 -0
  251. package/src/extensibility/custom-tools/wrapper.ts +47 -0
  252. package/src/extensibility/extensions/index.ts +15 -0
  253. package/src/extensibility/extensions/loader.ts +516 -0
  254. package/src/extensibility/extensions/runner.ts +841 -0
  255. package/src/extensibility/extensions/types.ts +1366 -0
  256. package/src/extensibility/extensions/wrapper.ts +191 -0
  257. package/src/extensibility/hooks/index.ts +5 -0
  258. package/src/extensibility/hooks/loader.ts +255 -0
  259. package/src/extensibility/hooks/runner.ts +425 -0
  260. package/src/extensibility/hooks/tool-wrapper.ts +108 -0
  261. package/src/extensibility/hooks/types.ts +822 -0
  262. package/src/extensibility/plugins/doctor.ts +66 -0
  263. package/src/extensibility/plugins/git-url.ts +281 -0
  264. package/src/extensibility/plugins/index.ts +9 -0
  265. package/src/extensibility/plugins/installer.ts +192 -0
  266. package/src/extensibility/plugins/loader.ts +267 -0
  267. package/src/extensibility/plugins/manager.ts +731 -0
  268. package/src/extensibility/plugins/marketplace/cache.ts +136 -0
  269. package/src/extensibility/plugins/marketplace/fetcher.ts +317 -0
  270. package/src/extensibility/plugins/marketplace/index.ts +6 -0
  271. package/src/extensibility/plugins/marketplace/manager.ts +751 -0
  272. package/src/extensibility/plugins/marketplace/registry.ts +196 -0
  273. package/src/extensibility/plugins/marketplace/source-resolver.ts +147 -0
  274. package/src/extensibility/plugins/marketplace/types.ts +191 -0
  275. package/src/extensibility/plugins/parser.ts +105 -0
  276. package/src/extensibility/plugins/types.ts +194 -0
  277. package/src/extensibility/skills.ts +252 -0
  278. package/src/extensibility/slash-commands.ts +227 -0
  279. package/src/extensibility/tool-proxy.ts +25 -0
  280. package/src/extensibility/utils.ts +38 -0
  281. package/src/index.ts +61 -0
  282. package/src/internal-urls/agent-protocol.ts +136 -0
  283. package/src/internal-urls/artifact-protocol.ts +97 -0
  284. package/src/internal-urls/docs-index.generated.ts +57 -0
  285. package/src/internal-urls/index.ts +35 -0
  286. package/src/internal-urls/jobs-protocol.ts +118 -0
  287. package/src/internal-urls/json-query.ts +126 -0
  288. package/src/internal-urls/local-protocol.ts +206 -0
  289. package/src/internal-urls/mcp-protocol.ts +156 -0
  290. package/src/internal-urls/memory-protocol.ts +133 -0
  291. package/src/internal-urls/parse.ts +72 -0
  292. package/src/internal-urls/pi-protocol.ts +84 -0
  293. package/src/internal-urls/router.ts +54 -0
  294. package/src/internal-urls/rule-protocol.ts +55 -0
  295. package/src/internal-urls/skill-protocol.ts +111 -0
  296. package/src/internal-urls/types.ts +52 -0
  297. package/src/ipy/cancellation.ts +28 -0
  298. package/src/ipy/executor.ts +762 -0
  299. package/src/ipy/gateway-coordinator.ts +424 -0
  300. package/src/ipy/kernel.ts +1065 -0
  301. package/src/ipy/modules.ts +144 -0
  302. package/src/ipy/prelude.py +849 -0
  303. package/src/ipy/prelude.ts +3 -0
  304. package/src/ipy/runtime.ts +221 -0
  305. package/src/lsp/client.ts +878 -0
  306. package/src/lsp/clients/biome-client.ts +202 -0
  307. package/src/lsp/clients/index.ts +50 -0
  308. package/src/lsp/clients/lsp-linter-client.ts +93 -0
  309. package/src/lsp/clients/swiftlint-client.ts +120 -0
  310. package/src/lsp/config.ts +402 -0
  311. package/src/lsp/defaults.json +998 -0
  312. package/src/lsp/edits.ts +109 -0
  313. package/src/lsp/index.ts +1743 -0
  314. package/src/lsp/lspmux.ts +233 -0
  315. package/src/lsp/render.ts +683 -0
  316. package/src/lsp/startup-events.ts +13 -0
  317. package/src/lsp/types.ts +438 -0
  318. package/src/lsp/utils.ts +807 -0
  319. package/src/main.ts +914 -0
  320. package/src/mcp/client.ts +482 -0
  321. package/src/mcp/config-writer.ts +225 -0
  322. package/src/mcp/config.ts +365 -0
  323. package/src/mcp/discoverable-tool-metadata.ts +202 -0
  324. package/src/mcp/index.ts +29 -0
  325. package/src/mcp/json-rpc.ts +84 -0
  326. package/src/mcp/loader.ts +124 -0
  327. package/src/mcp/manager.ts +1152 -0
  328. package/src/mcp/oauth-discovery.ts +349 -0
  329. package/src/mcp/oauth-flow.ts +387 -0
  330. package/src/mcp/render.ts +130 -0
  331. package/src/mcp/smithery-auth.ts +104 -0
  332. package/src/mcp/smithery-connect.ts +145 -0
  333. package/src/mcp/smithery-registry.ts +477 -0
  334. package/src/mcp/tool-bridge.ts +417 -0
  335. package/src/mcp/tool-cache.ts +117 -0
  336. package/src/mcp/transports/http.ts +475 -0
  337. package/src/mcp/transports/index.ts +6 -0
  338. package/src/mcp/transports/stdio.ts +325 -0
  339. package/src/mcp/types.ts +423 -0
  340. package/src/memories/index.ts +1114 -0
  341. package/src/memories/storage.ts +577 -0
  342. package/src/modes/acp/acp-agent.ts +1358 -0
  343. package/src/modes/acp/acp-event-mapper.ts +538 -0
  344. package/src/modes/acp/acp-mode.ts +15 -0
  345. package/src/modes/acp/index.ts +2 -0
  346. package/src/modes/components/agent-dashboard.ts +1120 -0
  347. package/src/modes/components/assistant-message.ts +206 -0
  348. package/src/modes/components/bash-execution.ts +247 -0
  349. package/src/modes/components/bordered-loader.ts +41 -0
  350. package/src/modes/components/branch-summary-message.ts +45 -0
  351. package/src/modes/components/btw-panel.ts +104 -0
  352. package/src/modes/components/compaction-summary-message.ts +51 -0
  353. package/src/modes/components/countdown-timer.ts +75 -0
  354. package/src/modes/components/custom-editor.ts +238 -0
  355. package/src/modes/components/custom-message.ts +91 -0
  356. package/src/modes/components/diff.ts +210 -0
  357. package/src/modes/components/dynamic-border.ts +25 -0
  358. package/src/modes/components/extensions/extension-dashboard.ts +326 -0
  359. package/src/modes/components/extensions/extension-list.ts +492 -0
  360. package/src/modes/components/extensions/index.ts +9 -0
  361. package/src/modes/components/extensions/inspector-panel.ts +317 -0
  362. package/src/modes/components/extensions/state-manager.ts +587 -0
  363. package/src/modes/components/extensions/types.ts +191 -0
  364. package/src/modes/components/footer.ts +262 -0
  365. package/src/modes/components/history-search.ts +158 -0
  366. package/src/modes/components/hook-editor.ts +151 -0
  367. package/src/modes/components/hook-input.ts +79 -0
  368. package/src/modes/components/hook-message.ts +100 -0
  369. package/src/modes/components/hook-selector.ts +190 -0
  370. package/src/modes/components/index.ts +36 -0
  371. package/src/modes/components/keybinding-hints.ts +65 -0
  372. package/src/modes/components/login-dialog.ts +164 -0
  373. package/src/modes/components/mcp-add-wizard.ts +1314 -0
  374. package/src/modes/components/model-selector.ts +789 -0
  375. package/src/modes/components/oauth-selector.ts +211 -0
  376. package/src/modes/components/plugin-selector.ts +95 -0
  377. package/src/modes/components/plugin-settings.ts +477 -0
  378. package/src/modes/components/python-execution.ts +181 -0
  379. package/src/modes/components/queue-mode-selector.ts +56 -0
  380. package/src/modes/components/read-tool-group.ts +152 -0
  381. package/src/modes/components/session-observer-overlay.ts +472 -0
  382. package/src/modes/components/session-selector.ts +343 -0
  383. package/src/modes/components/settings-defs.ts +547 -0
  384. package/src/modes/components/settings-selector.ts +624 -0
  385. package/src/modes/components/show-images-selector.ts +45 -0
  386. package/src/modes/components/skill-message.ts +90 -0
  387. package/src/modes/components/status-line/context-thresholds.ts +68 -0
  388. package/src/modes/components/status-line/git-utils.ts +42 -0
  389. package/src/modes/components/status-line/index.ts +4 -0
  390. package/src/modes/components/status-line/presets.ts +94 -0
  391. package/src/modes/components/status-line/segments.ts +392 -0
  392. package/src/modes/components/status-line/separators.ts +55 -0
  393. package/src/modes/components/status-line/token-rate.ts +66 -0
  394. package/src/modes/components/status-line/types.ts +82 -0
  395. package/src/modes/components/status-line-segment-editor.ts +358 -0
  396. package/src/modes/components/status-line.ts +499 -0
  397. package/src/modes/components/theme-selector.ts +63 -0
  398. package/src/modes/components/thinking-selector.ts +52 -0
  399. package/src/modes/components/todo-reminder.ts +47 -0
  400. package/src/modes/components/tool-execution.ts +697 -0
  401. package/src/modes/components/tree-selector.ts +908 -0
  402. package/src/modes/components/ttsr-notification.ts +80 -0
  403. package/src/modes/components/user-message-selector.ts +141 -0
  404. package/src/modes/components/user-message.ts +38 -0
  405. package/src/modes/components/visual-truncate.ts +63 -0
  406. package/src/modes/components/welcome.ts +248 -0
  407. package/src/modes/controllers/btw-controller.ts +193 -0
  408. package/src/modes/controllers/command-controller.ts +1195 -0
  409. package/src/modes/controllers/event-controller.ts +644 -0
  410. package/src/modes/controllers/extension-ui-controller.ts +960 -0
  411. package/src/modes/controllers/input-controller.ts +762 -0
  412. package/src/modes/controllers/mcp-command-controller.ts +1926 -0
  413. package/src/modes/controllers/selector-controller.ts +991 -0
  414. package/src/modes/controllers/ssh-command-controller.ts +421 -0
  415. package/src/modes/index.ts +34 -0
  416. package/src/modes/interactive-mode.ts +1664 -0
  417. package/src/modes/oauth-manual-input.ts +42 -0
  418. package/src/modes/print-mode.ts +192 -0
  419. package/src/modes/prompt-action-autocomplete.ts +233 -0
  420. package/src/modes/rpc/host-tools.ts +186 -0
  421. package/src/modes/rpc/rpc-client.ts +750 -0
  422. package/src/modes/rpc/rpc-mode.ts +825 -0
  423. package/src/modes/rpc/rpc-types.ts +297 -0
  424. package/src/modes/session-observer-registry.ts +146 -0
  425. package/src/modes/shared.ts +30 -0
  426. package/src/modes/theme/dark.json +95 -0
  427. package/src/modes/theme/defaults/alabaster.json +93 -0
  428. package/src/modes/theme/defaults/amethyst.json +96 -0
  429. package/src/modes/theme/defaults/anthracite.json +93 -0
  430. package/src/modes/theme/defaults/basalt.json +91 -0
  431. package/src/modes/theme/defaults/birch.json +95 -0
  432. package/src/modes/theme/defaults/dark-abyss.json +91 -0
  433. package/src/modes/theme/defaults/dark-arctic.json +104 -0
  434. package/src/modes/theme/defaults/dark-aurora.json +95 -0
  435. package/src/modes/theme/defaults/dark-catppuccin.json +107 -0
  436. package/src/modes/theme/defaults/dark-cavern.json +91 -0
  437. package/src/modes/theme/defaults/dark-copper.json +95 -0
  438. package/src/modes/theme/defaults/dark-cosmos.json +90 -0
  439. package/src/modes/theme/defaults/dark-cyberpunk.json +102 -0
  440. package/src/modes/theme/defaults/dark-dracula.json +98 -0
  441. package/src/modes/theme/defaults/dark-eclipse.json +91 -0
  442. package/src/modes/theme/defaults/dark-ember.json +95 -0
  443. package/src/modes/theme/defaults/dark-equinox.json +90 -0
  444. package/src/modes/theme/defaults/dark-forest.json +96 -0
  445. package/src/modes/theme/defaults/dark-github.json +105 -0
  446. package/src/modes/theme/defaults/dark-gruvbox.json +112 -0
  447. package/src/modes/theme/defaults/dark-lavender.json +95 -0
  448. package/src/modes/theme/defaults/dark-lunar.json +89 -0
  449. package/src/modes/theme/defaults/dark-midnight.json +95 -0
  450. package/src/modes/theme/defaults/dark-monochrome.json +94 -0
  451. package/src/modes/theme/defaults/dark-monokai.json +98 -0
  452. package/src/modes/theme/defaults/dark-nebula.json +90 -0
  453. package/src/modes/theme/defaults/dark-nord.json +97 -0
  454. package/src/modes/theme/defaults/dark-ocean.json +101 -0
  455. package/src/modes/theme/defaults/dark-one.json +100 -0
  456. package/src/modes/theme/defaults/dark-poimandres.json +138 -0
  457. package/src/modes/theme/defaults/dark-rainforest.json +91 -0
  458. package/src/modes/theme/defaults/dark-reef.json +91 -0
  459. package/src/modes/theme/defaults/dark-retro.json +92 -0
  460. package/src/modes/theme/defaults/dark-rose-pine.json +96 -0
  461. package/src/modes/theme/defaults/dark-sakura.json +95 -0
  462. package/src/modes/theme/defaults/dark-slate.json +95 -0
  463. package/src/modes/theme/defaults/dark-solarized.json +97 -0
  464. package/src/modes/theme/defaults/dark-solstice.json +90 -0
  465. package/src/modes/theme/defaults/dark-starfall.json +91 -0
  466. package/src/modes/theme/defaults/dark-sunset.json +99 -0
  467. package/src/modes/theme/defaults/dark-swamp.json +90 -0
  468. package/src/modes/theme/defaults/dark-synthwave.json +103 -0
  469. package/src/modes/theme/defaults/dark-taiga.json +91 -0
  470. package/src/modes/theme/defaults/dark-terminal.json +95 -0
  471. package/src/modes/theme/defaults/dark-tokyo-night.json +101 -0
  472. package/src/modes/theme/defaults/dark-tundra.json +91 -0
  473. package/src/modes/theme/defaults/dark-twilight.json +91 -0
  474. package/src/modes/theme/defaults/dark-volcanic.json +91 -0
  475. package/src/modes/theme/defaults/graphite.json +92 -0
  476. package/src/modes/theme/defaults/index.ts +203 -0
  477. package/src/modes/theme/defaults/light-arctic.json +107 -0
  478. package/src/modes/theme/defaults/light-aurora-day.json +91 -0
  479. package/src/modes/theme/defaults/light-canyon.json +91 -0
  480. package/src/modes/theme/defaults/light-catppuccin.json +106 -0
  481. package/src/modes/theme/defaults/light-cirrus.json +90 -0
  482. package/src/modes/theme/defaults/light-coral.json +95 -0
  483. package/src/modes/theme/defaults/light-cyberpunk.json +96 -0
  484. package/src/modes/theme/defaults/light-dawn.json +90 -0
  485. package/src/modes/theme/defaults/light-dunes.json +91 -0
  486. package/src/modes/theme/defaults/light-eucalyptus.json +95 -0
  487. package/src/modes/theme/defaults/light-forest.json +100 -0
  488. package/src/modes/theme/defaults/light-frost.json +95 -0
  489. package/src/modes/theme/defaults/light-github.json +115 -0
  490. package/src/modes/theme/defaults/light-glacier.json +91 -0
  491. package/src/modes/theme/defaults/light-gruvbox.json +108 -0
  492. package/src/modes/theme/defaults/light-haze.json +90 -0
  493. package/src/modes/theme/defaults/light-honeycomb.json +95 -0
  494. package/src/modes/theme/defaults/light-lagoon.json +91 -0
  495. package/src/modes/theme/defaults/light-lavender.json +95 -0
  496. package/src/modes/theme/defaults/light-meadow.json +91 -0
  497. package/src/modes/theme/defaults/light-mint.json +95 -0
  498. package/src/modes/theme/defaults/light-monochrome.json +101 -0
  499. package/src/modes/theme/defaults/light-ocean.json +99 -0
  500. package/src/modes/theme/defaults/light-one.json +99 -0
  501. package/src/modes/theme/defaults/light-opal.json +91 -0
  502. package/src/modes/theme/defaults/light-orchard.json +91 -0
  503. package/src/modes/theme/defaults/light-paper.json +95 -0
  504. package/src/modes/theme/defaults/light-poimandres.json +138 -0
  505. package/src/modes/theme/defaults/light-prism.json +90 -0
  506. package/src/modes/theme/defaults/light-retro.json +98 -0
  507. package/src/modes/theme/defaults/light-sand.json +95 -0
  508. package/src/modes/theme/defaults/light-savanna.json +91 -0
  509. package/src/modes/theme/defaults/light-solarized.json +102 -0
  510. package/src/modes/theme/defaults/light-soleil.json +90 -0
  511. package/src/modes/theme/defaults/light-sunset.json +99 -0
  512. package/src/modes/theme/defaults/light-synthwave.json +98 -0
  513. package/src/modes/theme/defaults/light-tokyo-night.json +111 -0
  514. package/src/modes/theme/defaults/light-wetland.json +91 -0
  515. package/src/modes/theme/defaults/light-zenith.json +89 -0
  516. package/src/modes/theme/defaults/limestone.json +94 -0
  517. package/src/modes/theme/defaults/mahogany.json +97 -0
  518. package/src/modes/theme/defaults/marble.json +93 -0
  519. package/src/modes/theme/defaults/obsidian.json +91 -0
  520. package/src/modes/theme/defaults/onyx.json +91 -0
  521. package/src/modes/theme/defaults/pearl.json +93 -0
  522. package/src/modes/theme/defaults/porcelain.json +91 -0
  523. package/src/modes/theme/defaults/quartz.json +96 -0
  524. package/src/modes/theme/defaults/sandstone.json +95 -0
  525. package/src/modes/theme/defaults/titanium.json +90 -0
  526. package/src/modes/theme/defaults/xcsh-dark.json +89 -0
  527. package/src/modes/theme/defaults/xcsh-light.json +91 -0
  528. package/src/modes/theme/light.json +93 -0
  529. package/src/modes/theme/mermaid-cache.ts +70 -0
  530. package/src/modes/theme/theme-schema.json +429 -0
  531. package/src/modes/theme/theme.ts +2541 -0
  532. package/src/modes/types.ts +269 -0
  533. package/src/modes/utils/hotkeys-markdown.ts +59 -0
  534. package/src/modes/utils/keybinding-matchers.ts +30 -0
  535. package/src/modes/utils/tools-markdown.ts +27 -0
  536. package/src/modes/utils/ui-helpers.ts +620 -0
  537. package/src/plan-mode/approved-plan.ts +55 -0
  538. package/src/plan-mode/state.ts +6 -0
  539. package/src/priority.json +29 -0
  540. package/src/prompts/agents/designer.md +68 -0
  541. package/src/prompts/agents/explore.md +60 -0
  542. package/src/prompts/agents/frontmatter.md +10 -0
  543. package/src/prompts/agents/init.md +36 -0
  544. package/src/prompts/agents/librarian.md +121 -0
  545. package/src/prompts/agents/plan.md +49 -0
  546. package/src/prompts/agents/reviewer.md +127 -0
  547. package/src/prompts/agents/task.md +16 -0
  548. package/src/prompts/ci-green-request.md +36 -0
  549. package/src/prompts/compaction/branch-summary-context.md +5 -0
  550. package/src/prompts/compaction/branch-summary-preamble.md +2 -0
  551. package/src/prompts/compaction/branch-summary.md +30 -0
  552. package/src/prompts/compaction/compaction-short-summary.md +9 -0
  553. package/src/prompts/compaction/compaction-summary-context.md +5 -0
  554. package/src/prompts/compaction/compaction-summary.md +38 -0
  555. package/src/prompts/compaction/compaction-turn-prefix.md +17 -0
  556. package/src/prompts/compaction/compaction-update-summary.md +45 -0
  557. package/src/prompts/memories/consolidation.md +30 -0
  558. package/src/prompts/memories/read-path.md +11 -0
  559. package/src/prompts/memories/stage_one_input.md +6 -0
  560. package/src/prompts/memories/stage_one_system.md +21 -0
  561. package/src/prompts/review-request.md +64 -0
  562. package/src/prompts/system/agent-creation-architect.md +65 -0
  563. package/src/prompts/system/agent-creation-user.md +6 -0
  564. package/src/prompts/system/auto-handoff-threshold-focus.md +1 -0
  565. package/src/prompts/system/btw-user.md +8 -0
  566. package/src/prompts/system/commit-message-system.md +2 -0
  567. package/src/prompts/system/custom-system-prompt.md +68 -0
  568. package/src/prompts/system/eager-todo.md +13 -0
  569. package/src/prompts/system/file-operations.md +10 -0
  570. package/src/prompts/system/handoff-document.md +46 -0
  571. package/src/prompts/system/plan-mode-active.md +107 -0
  572. package/src/prompts/system/plan-mode-approved.md +23 -0
  573. package/src/prompts/system/plan-mode-reference.md +14 -0
  574. package/src/prompts/system/plan-mode-subagent.md +34 -0
  575. package/src/prompts/system/plan-mode-tool-decision-reminder.md +9 -0
  576. package/src/prompts/system/subagent-submit-reminder.md +11 -0
  577. package/src/prompts/system/subagent-system-prompt.md +35 -0
  578. package/src/prompts/system/subagent-user-prompt.md +12 -0
  579. package/src/prompts/system/summarization-system.md +3 -0
  580. package/src/prompts/system/system-prompt.md +333 -0
  581. package/src/prompts/system/title-system.md +2 -0
  582. package/src/prompts/system/ttsr-interrupt.md +7 -0
  583. package/src/prompts/system/web-search.md +28 -0
  584. package/src/prompts/tools/ask.md +28 -0
  585. package/src/prompts/tools/ast-edit.md +48 -0
  586. package/src/prompts/tools/ast-grep.md +54 -0
  587. package/src/prompts/tools/async-result.md +5 -0
  588. package/src/prompts/tools/await.md +5 -0
  589. package/src/prompts/tools/bash.md +47 -0
  590. package/src/prompts/tools/browser.md +24 -0
  591. package/src/prompts/tools/calculator.md +10 -0
  592. package/src/prompts/tools/cancel-job.md +5 -0
  593. package/src/prompts/tools/checkpoint.md +16 -0
  594. package/src/prompts/tools/chunk-edit.md +219 -0
  595. package/src/prompts/tools/debug.md +43 -0
  596. package/src/prompts/tools/exit-plan-mode.md +41 -0
  597. package/src/prompts/tools/find.md +26 -0
  598. package/src/prompts/tools/gemini-image.md +7 -0
  599. package/src/prompts/tools/gh-issue-view.md +11 -0
  600. package/src/prompts/tools/gh-pr-checkout.md +12 -0
  601. package/src/prompts/tools/gh-pr-diff.md +12 -0
  602. package/src/prompts/tools/gh-pr-push.md +11 -0
  603. package/src/prompts/tools/gh-pr-view.md +11 -0
  604. package/src/prompts/tools/gh-repo-view.md +11 -0
  605. package/src/prompts/tools/gh-run-watch.md +12 -0
  606. package/src/prompts/tools/gh-search-issues.md +11 -0
  607. package/src/prompts/tools/gh-search-prs.md +11 -0
  608. package/src/prompts/tools/grep.md +29 -0
  609. package/src/prompts/tools/hashline.md +131 -0
  610. package/src/prompts/tools/inspect-image-system.md +20 -0
  611. package/src/prompts/tools/inspect-image.md +32 -0
  612. package/src/prompts/tools/lsp.md +33 -0
  613. package/src/prompts/tools/patch.md +72 -0
  614. package/src/prompts/tools/python.md +60 -0
  615. package/src/prompts/tools/read-chunk.md +17 -0
  616. package/src/prompts/tools/read.md +54 -0
  617. package/src/prompts/tools/render-mermaid.md +9 -0
  618. package/src/prompts/tools/replace.md +36 -0
  619. package/src/prompts/tools/resolve.md +8 -0
  620. package/src/prompts/tools/rewind.md +13 -0
  621. package/src/prompts/tools/search-tool-bm25.md +34 -0
  622. package/src/prompts/tools/ssh.md +44 -0
  623. package/src/prompts/tools/task-summary.md +28 -0
  624. package/src/prompts/tools/task.md +131 -0
  625. package/src/prompts/tools/todo-write.md +89 -0
  626. package/src/prompts/tools/web-search.md +10 -0
  627. package/src/prompts/tools/write.md +13 -0
  628. package/src/sdk.ts +1694 -0
  629. package/src/secrets/index.ts +116 -0
  630. package/src/secrets/obfuscator.ts +277 -0
  631. package/src/secrets/regex.ts +21 -0
  632. package/src/session/agent-session.ts +6506 -0
  633. package/src/session/agent-storage.ts +451 -0
  634. package/src/session/artifacts.ts +132 -0
  635. package/src/session/auth-storage.ts +17 -0
  636. package/src/session/blob-store.ts +135 -0
  637. package/src/session/compaction/branch-summarization.ts +322 -0
  638. package/src/session/compaction/compaction.ts +1388 -0
  639. package/src/session/compaction/index.ts +7 -0
  640. package/src/session/compaction/pruning.ts +91 -0
  641. package/src/session/compaction/utils.ts +184 -0
  642. package/src/session/history-storage.ts +253 -0
  643. package/src/session/messages.ts +373 -0
  644. package/src/session/session-dump-format.ts +203 -0
  645. package/src/session/session-manager.ts +2728 -0
  646. package/src/session/session-storage.ts +367 -0
  647. package/src/session/streaming-output.ts +752 -0
  648. package/src/session/tool-choice-queue.ts +213 -0
  649. package/src/slash-commands/builtin-registry.ts +981 -0
  650. package/src/slash-commands/marketplace-install-parser.ts +99 -0
  651. package/src/ssh/config-writer.ts +183 -0
  652. package/src/ssh/connection-manager.ts +445 -0
  653. package/src/ssh/ssh-executor.ts +128 -0
  654. package/src/ssh/sshfs-mount.ts +137 -0
  655. package/src/ssh/utils.ts +8 -0
  656. package/src/stt/downloader.ts +71 -0
  657. package/src/stt/index.ts +3 -0
  658. package/src/stt/recorder.ts +351 -0
  659. package/src/stt/setup.ts +52 -0
  660. package/src/stt/stt-controller.ts +160 -0
  661. package/src/stt/transcribe.py +70 -0
  662. package/src/stt/transcriber.ts +91 -0
  663. package/src/system-prompt.ts +620 -0
  664. package/src/task/agents.ts +166 -0
  665. package/src/task/commands.ts +131 -0
  666. package/src/task/discovery.ts +126 -0
  667. package/src/task/executor.ts +1293 -0
  668. package/src/task/index.ts +1199 -0
  669. package/src/task/isolation-backend.ts +72 -0
  670. package/src/task/name-generator.ts +1577 -0
  671. package/src/task/output-manager.ts +107 -0
  672. package/src/task/parallel.ts +116 -0
  673. package/src/task/render.ts +1021 -0
  674. package/src/task/subprocess-tool-registry.ts +88 -0
  675. package/src/task/template.ts +33 -0
  676. package/src/task/types.ts +230 -0
  677. package/src/task/worktree.ts +580 -0
  678. package/src/task/xcsh-command.ts +26 -0
  679. package/src/thinking.ts +87 -0
  680. package/src/tools/archive-reader.ts +315 -0
  681. package/src/tools/ask.ts +795 -0
  682. package/src/tools/ast-edit.ts +495 -0
  683. package/src/tools/ast-grep.ts +456 -0
  684. package/src/tools/auto-generated-guard.ts +305 -0
  685. package/src/tools/await-tool.ts +170 -0
  686. package/src/tools/bash-interactive.ts +377 -0
  687. package/src/tools/bash-interceptor.ts +67 -0
  688. package/src/tools/bash-normalize.ts +107 -0
  689. package/src/tools/bash-skill-urls.ts +246 -0
  690. package/src/tools/bash.ts +600 -0
  691. package/src/tools/browser.ts +1473 -0
  692. package/src/tools/calculator.ts +537 -0
  693. package/src/tools/cancel-job.ts +99 -0
  694. package/src/tools/checkpoint.ts +133 -0
  695. package/src/tools/context.ts +39 -0
  696. package/src/tools/debug.ts +1007 -0
  697. package/src/tools/exit-plan-mode.ts +101 -0
  698. package/src/tools/fetch.ts +1463 -0
  699. package/src/tools/find.ts +495 -0
  700. package/src/tools/fs-cache-invalidation.ts +33 -0
  701. package/src/tools/gemini-image.ts +896 -0
  702. package/src/tools/gh-renderer.ts +305 -0
  703. package/src/tools/gh.ts +2546 -0
  704. package/src/tools/grep.ts +625 -0
  705. package/src/tools/index.ts +426 -0
  706. package/src/tools/inspect-image-renderer.ts +103 -0
  707. package/src/tools/inspect-image.ts +173 -0
  708. package/src/tools/json-tree.ts +243 -0
  709. package/src/tools/jtd-to-json-schema.ts +199 -0
  710. package/src/tools/jtd-to-typescript.ts +136 -0
  711. package/src/tools/jtd-utils.ts +102 -0
  712. package/src/tools/list-limit.ts +40 -0
  713. package/src/tools/notebook.ts +288 -0
  714. package/src/tools/output-meta.ts +588 -0
  715. package/src/tools/path-utils.ts +560 -0
  716. package/src/tools/plan-mode-guard.ts +41 -0
  717. package/src/tools/puppeteer/00_stealth_tampering.txt +63 -0
  718. package/src/tools/puppeteer/01_stealth_activity.txt +20 -0
  719. package/src/tools/puppeteer/02_stealth_hairline.txt +11 -0
  720. package/src/tools/puppeteer/03_stealth_botd.txt +384 -0
  721. package/src/tools/puppeteer/04_stealth_iframe.txt +81 -0
  722. package/src/tools/puppeteer/05_stealth_webgl.txt +75 -0
  723. package/src/tools/puppeteer/06_stealth_screen.txt +72 -0
  724. package/src/tools/puppeteer/07_stealth_fonts.txt +97 -0
  725. package/src/tools/puppeteer/08_stealth_audio.txt +51 -0
  726. package/src/tools/puppeteer/09_stealth_locale.txt +46 -0
  727. package/src/tools/puppeteer/10_stealth_plugins.txt +206 -0
  728. package/src/tools/puppeteer/11_stealth_hardware.txt +8 -0
  729. package/src/tools/puppeteer/12_stealth_codecs.txt +40 -0
  730. package/src/tools/puppeteer/13_stealth_worker.txt +74 -0
  731. package/src/tools/python.ts +1135 -0
  732. package/src/tools/read.ts +1375 -0
  733. package/src/tools/render-mermaid.ts +71 -0
  734. package/src/tools/render-utils.ts +618 -0
  735. package/src/tools/renderers.ts +68 -0
  736. package/src/tools/report-tool-issue.ts +80 -0
  737. package/src/tools/resolve.ts +192 -0
  738. package/src/tools/review.ts +238 -0
  739. package/src/tools/search-tool-bm25.ts +283 -0
  740. package/src/tools/ssh.ts +320 -0
  741. package/src/tools/submit-result.ts +226 -0
  742. package/src/tools/todo-write.ts +450 -0
  743. package/src/tools/tool-errors.ts +62 -0
  744. package/src/tools/tool-result.ts +86 -0
  745. package/src/tools/tool-timeouts.ts +30 -0
  746. package/src/tools/write.ts +479 -0
  747. package/src/tui/code-cell.ts +113 -0
  748. package/src/tui/file-list.ts +47 -0
  749. package/src/tui/index.ts +11 -0
  750. package/src/tui/output-block.ts +150 -0
  751. package/src/tui/status-line.ts +39 -0
  752. package/src/tui/tree-list.ts +84 -0
  753. package/src/tui/types.ts +15 -0
  754. package/src/tui/utils.ts +103 -0
  755. package/src/utils/changelog.ts +98 -0
  756. package/src/utils/clipboard.ts +80 -0
  757. package/src/utils/command-args.ts +76 -0
  758. package/src/utils/commit-message-generator.ts +136 -0
  759. package/src/utils/edit-mode.ts +49 -0
  760. package/src/utils/event-bus.ts +33 -0
  761. package/src/utils/external-editor.ts +65 -0
  762. package/src/utils/file-display-mode.ts +37 -0
  763. package/src/utils/file-mentions.ts +376 -0
  764. package/src/utils/fuzzy.ts +108 -0
  765. package/src/utils/git.ts +1400 -0
  766. package/src/utils/image-convert.ts +27 -0
  767. package/src/utils/image-loading.ts +98 -0
  768. package/src/utils/image-resize.ts +236 -0
  769. package/src/utils/markit.ts +81 -0
  770. package/src/utils/open.ts +20 -0
  771. package/src/utils/shell-snapshot.ts +188 -0
  772. package/src/utils/sixel.ts +69 -0
  773. package/src/utils/title-generator.ts +184 -0
  774. package/src/utils/tool-choice.ts +28 -0
  775. package/src/utils/tools-manager.ts +356 -0
  776. package/src/web/kagi.ts +174 -0
  777. package/src/web/parallel.ts +346 -0
  778. package/src/web/scrapers/artifacthub.ts +207 -0
  779. package/src/web/scrapers/arxiv.ts +83 -0
  780. package/src/web/scrapers/aur.ts +162 -0
  781. package/src/web/scrapers/biorxiv.ts +133 -0
  782. package/src/web/scrapers/bluesky.ts +262 -0
  783. package/src/web/scrapers/brew.ts +172 -0
  784. package/src/web/scrapers/cheatsh.ts +68 -0
  785. package/src/web/scrapers/chocolatey.ts +196 -0
  786. package/src/web/scrapers/choosealicense.ts +95 -0
  787. package/src/web/scrapers/cisa-kev.ts +87 -0
  788. package/src/web/scrapers/clojars.ts +154 -0
  789. package/src/web/scrapers/coingecko.ts +177 -0
  790. package/src/web/scrapers/crates-io.ts +110 -0
  791. package/src/web/scrapers/crossref.ts +136 -0
  792. package/src/web/scrapers/devto.ts +147 -0
  793. package/src/web/scrapers/discogs.ts +306 -0
  794. package/src/web/scrapers/discourse.ts +197 -0
  795. package/src/web/scrapers/dockerhub.ts +138 -0
  796. package/src/web/scrapers/docs-rs.ts +653 -0
  797. package/src/web/scrapers/fdroid.ts +134 -0
  798. package/src/web/scrapers/firefox-addons.ts +191 -0
  799. package/src/web/scrapers/flathub.ts +223 -0
  800. package/src/web/scrapers/github-gist.ts +58 -0
  801. package/src/web/scrapers/github.ts +452 -0
  802. package/src/web/scrapers/gitlab.ts +401 -0
  803. package/src/web/scrapers/go-pkg.ts +266 -0
  804. package/src/web/scrapers/hackage.ts +140 -0
  805. package/src/web/scrapers/hackernews.ts +189 -0
  806. package/src/web/scrapers/hex.ts +105 -0
  807. package/src/web/scrapers/huggingface.ts +321 -0
  808. package/src/web/scrapers/iacr.ts +89 -0
  809. package/src/web/scrapers/index.ts +252 -0
  810. package/src/web/scrapers/jetbrains-marketplace.ts +159 -0
  811. package/src/web/scrapers/lemmy.ts +203 -0
  812. package/src/web/scrapers/lobsters.ts +175 -0
  813. package/src/web/scrapers/mastodon.ts +292 -0
  814. package/src/web/scrapers/maven.ts +138 -0
  815. package/src/web/scrapers/mdn.ts +169 -0
  816. package/src/web/scrapers/metacpan.ts +222 -0
  817. package/src/web/scrapers/musicbrainz.ts +250 -0
  818. package/src/web/scrapers/npm.ts +98 -0
  819. package/src/web/scrapers/nuget.ts +183 -0
  820. package/src/web/scrapers/nvd.ts +222 -0
  821. package/src/web/scrapers/ollama.ts +239 -0
  822. package/src/web/scrapers/open-vsx.ts +106 -0
  823. package/src/web/scrapers/opencorporates.ts +292 -0
  824. package/src/web/scrapers/openlibrary.ts +336 -0
  825. package/src/web/scrapers/orcid.ts +286 -0
  826. package/src/web/scrapers/osv.ts +176 -0
  827. package/src/web/scrapers/packagist.ts +160 -0
  828. package/src/web/scrapers/pub-dev.ts +143 -0
  829. package/src/web/scrapers/pubmed.ts +211 -0
  830. package/src/web/scrapers/pypi.ts +112 -0
  831. package/src/web/scrapers/rawg.ts +110 -0
  832. package/src/web/scrapers/readthedocs.ts +120 -0
  833. package/src/web/scrapers/reddit.ts +95 -0
  834. package/src/web/scrapers/repology.ts +251 -0
  835. package/src/web/scrapers/rfc.ts +201 -0
  836. package/src/web/scrapers/rubygems.ts +103 -0
  837. package/src/web/scrapers/searchcode.ts +190 -0
  838. package/src/web/scrapers/sec-edgar.ts +261 -0
  839. package/src/web/scrapers/semantic-scholar.ts +171 -0
  840. package/src/web/scrapers/snapcraft.ts +187 -0
  841. package/src/web/scrapers/sourcegraph.ts +336 -0
  842. package/src/web/scrapers/spdx.ts +108 -0
  843. package/src/web/scrapers/spotify.ts +198 -0
  844. package/src/web/scrapers/stackoverflow.ts +120 -0
  845. package/src/web/scrapers/terraform.ts +277 -0
  846. package/src/web/scrapers/tldr.ts +47 -0
  847. package/src/web/scrapers/twitter.ts +93 -0
  848. package/src/web/scrapers/types.ts +267 -0
  849. package/src/web/scrapers/utils.ts +109 -0
  850. package/src/web/scrapers/vimeo.ts +133 -0
  851. package/src/web/scrapers/vscode-marketplace.ts +187 -0
  852. package/src/web/scrapers/w3c.ts +156 -0
  853. package/src/web/scrapers/wikidata.ts +344 -0
  854. package/src/web/scrapers/wikipedia.ts +84 -0
  855. package/src/web/scrapers/youtube.ts +313 -0
  856. package/src/web/search/index.ts +268 -0
  857. package/src/web/search/provider.ts +86 -0
  858. package/src/web/search/providers/anthropic.ts +286 -0
  859. package/src/web/search/providers/base.ts +25 -0
  860. package/src/web/search/providers/brave.ts +150 -0
  861. package/src/web/search/providers/codex.ts +383 -0
  862. package/src/web/search/providers/exa.ts +264 -0
  863. package/src/web/search/providers/gemini.ts +566 -0
  864. package/src/web/search/providers/jina.ts +99 -0
  865. package/src/web/search/providers/kagi.ts +70 -0
  866. package/src/web/search/providers/kimi.ts +157 -0
  867. package/src/web/search/providers/parallel.ts +63 -0
  868. package/src/web/search/providers/perplexity.ts +546 -0
  869. package/src/web/search/providers/synthetic.ts +113 -0
  870. package/src/web/search/providers/tavily.ts +162 -0
  871. package/src/web/search/providers/utils.ts +36 -0
  872. package/src/web/search/providers/zai.ts +311 -0
  873. package/src/web/search/render.ts +299 -0
  874. package/src/web/search/types.ts +434 -0
  875. package/src/web/search/utils.ts +17 -0
  876. package/dist/bun/cli.d.ts +0 -3
  877. package/dist/bun/cli.d.ts.map +0 -1
  878. package/dist/bun/cli.js +0 -7
  879. package/dist/bun/cli.js.map +0 -1
  880. package/dist/bun/register-bedrock.d.ts +0 -2
  881. package/dist/bun/register-bedrock.d.ts.map +0 -1
  882. package/dist/bun/register-bedrock.js +0 -4
  883. package/dist/bun/register-bedrock.js.map +0 -1
  884. package/dist/cli/args.d.ts +0 -52
  885. package/dist/cli/args.d.ts.map +0 -1
  886. package/dist/cli/args.js +0 -326
  887. package/dist/cli/args.js.map +0 -1
  888. package/dist/cli/config-selector.d.ts +0 -14
  889. package/dist/cli/config-selector.d.ts.map +0 -1
  890. package/dist/cli/config-selector.js +0 -31
  891. package/dist/cli/config-selector.js.map +0 -1
  892. package/dist/cli/file-processor.d.ts +0 -15
  893. package/dist/cli/file-processor.d.ts.map +0 -1
  894. package/dist/cli/file-processor.js +0 -83
  895. package/dist/cli/file-processor.js.map +0 -1
  896. package/dist/cli/initial-message.d.ts +0 -18
  897. package/dist/cli/initial-message.d.ts.map +0 -1
  898. package/dist/cli/initial-message.js +0 -22
  899. package/dist/cli/initial-message.js.map +0 -1
  900. package/dist/cli/list-models.d.ts +0 -9
  901. package/dist/cli/list-models.d.ts.map +0 -1
  902. package/dist/cli/list-models.js +0 -92
  903. package/dist/cli/list-models.js.map +0 -1
  904. package/dist/cli/session-picker.d.ts +0 -9
  905. package/dist/cli/session-picker.d.ts.map +0 -1
  906. package/dist/cli/session-picker.js +0 -35
  907. package/dist/cli/session-picker.js.map +0 -1
  908. package/dist/cli.d.ts +0 -3
  909. package/dist/cli.d.ts.map +0 -1
  910. package/dist/cli.js +0 -14
  911. package/dist/cli.js.map +0 -1
  912. package/dist/config.d.ts +0 -68
  913. package/dist/config.d.ts.map +0 -1
  914. package/dist/config.js +0 -203
  915. package/dist/config.js.map +0 -1
  916. package/dist/core/agent-session-runtime.d.ts +0 -83
  917. package/dist/core/agent-session-runtime.d.ts.map +0 -1
  918. package/dist/core/agent-session-runtime.js +0 -236
  919. package/dist/core/agent-session-runtime.js.map +0 -1
  920. package/dist/core/agent-session-services.d.ts +0 -86
  921. package/dist/core/agent-session-services.d.ts.map +0 -1
  922. package/dist/core/agent-session-services.js +0 -116
  923. package/dist/core/agent-session-services.js.map +0 -1
  924. package/dist/core/agent-session.d.ts +0 -585
  925. package/dist/core/agent-session.d.ts.map +0 -1
  926. package/dist/core/agent-session.js +0 -2497
  927. package/dist/core/agent-session.js.map +0 -1
  928. package/dist/core/auth-storage.d.ts +0 -132
  929. package/dist/core/auth-storage.d.ts.map +0 -1
  930. package/dist/core/auth-storage.js +0 -422
  931. package/dist/core/auth-storage.js.map +0 -1
  932. package/dist/core/bash-executor.d.ts +0 -46
  933. package/dist/core/bash-executor.d.ts.map +0 -1
  934. package/dist/core/bash-executor.js +0 -125
  935. package/dist/core/bash-executor.js.map +0 -1
  936. package/dist/core/compaction/branch-summarization.d.ts +0 -88
  937. package/dist/core/compaction/branch-summarization.d.ts.map +0 -1
  938. package/dist/core/compaction/branch-summarization.js +0 -243
  939. package/dist/core/compaction/branch-summarization.js.map +0 -1
  940. package/dist/core/compaction/compaction.d.ts +0 -121
  941. package/dist/core/compaction/compaction.d.ts.map +0 -1
  942. package/dist/core/compaction/compaction.js +0 -613
  943. package/dist/core/compaction/compaction.js.map +0 -1
  944. package/dist/core/compaction/index.d.ts +0 -7
  945. package/dist/core/compaction/index.d.ts.map +0 -1
  946. package/dist/core/compaction/index.js +0 -7
  947. package/dist/core/compaction/index.js.map +0 -1
  948. package/dist/core/compaction/utils.d.ts +0 -38
  949. package/dist/core/compaction/utils.d.ts.map +0 -1
  950. package/dist/core/compaction/utils.js +0 -153
  951. package/dist/core/compaction/utils.js.map +0 -1
  952. package/dist/core/defaults.d.ts +0 -3
  953. package/dist/core/defaults.d.ts.map +0 -1
  954. package/dist/core/defaults.js +0 -2
  955. package/dist/core/defaults.js.map +0 -1
  956. package/dist/core/diagnostics.d.ts +0 -15
  957. package/dist/core/diagnostics.d.ts.map +0 -1
  958. package/dist/core/diagnostics.js +0 -2
  959. package/dist/core/diagnostics.js.map +0 -1
  960. package/dist/core/event-bus.d.ts +0 -9
  961. package/dist/core/event-bus.d.ts.map +0 -1
  962. package/dist/core/event-bus.js +0 -25
  963. package/dist/core/event-bus.js.map +0 -1
  964. package/dist/core/exec.d.ts +0 -29
  965. package/dist/core/exec.d.ts.map +0 -1
  966. package/dist/core/exec.js +0 -75
  967. package/dist/core/exec.js.map +0 -1
  968. package/dist/core/export-html/ansi-to-html.d.ts +0 -22
  969. package/dist/core/export-html/ansi-to-html.d.ts.map +0 -1
  970. package/dist/core/export-html/ansi-to-html.js +0 -249
  971. package/dist/core/export-html/ansi-to-html.js.map +0 -1
  972. package/dist/core/export-html/index.d.ts +0 -37
  973. package/dist/core/export-html/index.d.ts.map +0 -1
  974. package/dist/core/export-html/index.js +0 -224
  975. package/dist/core/export-html/index.js.map +0 -1
  976. package/dist/core/export-html/template.css +0 -1001
  977. package/dist/core/export-html/template.html +0 -55
  978. package/dist/core/export-html/template.js +0 -1690
  979. package/dist/core/export-html/tool-renderer.d.ts +0 -40
  980. package/dist/core/export-html/tool-renderer.d.ts.map +0 -1
  981. package/dist/core/export-html/tool-renderer.js +0 -95
  982. package/dist/core/export-html/tool-renderer.js.map +0 -1
  983. package/dist/core/extensions/index.d.ts +0 -12
  984. package/dist/core/extensions/index.d.ts.map +0 -1
  985. package/dist/core/extensions/index.js +0 -9
  986. package/dist/core/extensions/index.js.map +0 -1
  987. package/dist/core/extensions/loader.d.ts +0 -25
  988. package/dist/core/extensions/loader.d.ts.map +0 -1
  989. package/dist/core/extensions/loader.js +0 -436
  990. package/dist/core/extensions/loader.js.map +0 -1
  991. package/dist/core/extensions/runner.d.ts +0 -148
  992. package/dist/core/extensions/runner.d.ts.map +0 -1
  993. package/dist/core/extensions/runner.js +0 -700
  994. package/dist/core/extensions/runner.js.map +0 -1
  995. package/dist/core/extensions/types.d.ts +0 -1073
  996. package/dist/core/extensions/types.d.ts.map +0 -1
  997. package/dist/core/extensions/types.js +0 -45
  998. package/dist/core/extensions/types.js.map +0 -1
  999. package/dist/core/extensions/wrapper.d.ts +0 -20
  1000. package/dist/core/extensions/wrapper.d.ts.map +0 -1
  1001. package/dist/core/extensions/wrapper.js +0 -22
  1002. package/dist/core/extensions/wrapper.js.map +0 -1
  1003. package/dist/core/footer-data-provider.d.ts +0 -48
  1004. package/dist/core/footer-data-provider.d.ts.map +0 -1
  1005. package/dist/core/footer-data-provider.js +0 -314
  1006. package/dist/core/footer-data-provider.js.map +0 -1
  1007. package/dist/core/index.d.ts +0 -12
  1008. package/dist/core/index.d.ts.map +0 -1
  1009. package/dist/core/index.js +0 -12
  1010. package/dist/core/index.js.map +0 -1
  1011. package/dist/core/keybindings.d.ts +0 -288
  1012. package/dist/core/keybindings.d.ts.map +0 -1
  1013. package/dist/core/keybindings.js +0 -240
  1014. package/dist/core/keybindings.js.map +0 -1
  1015. package/dist/core/messages.d.ts +0 -77
  1016. package/dist/core/messages.d.ts.map +0 -1
  1017. package/dist/core/messages.js +0 -123
  1018. package/dist/core/messages.js.map +0 -1
  1019. package/dist/core/model-registry.d.ts +0 -132
  1020. package/dist/core/model-registry.d.ts.map +0 -1
  1021. package/dist/core/model-registry.js +0 -583
  1022. package/dist/core/model-registry.js.map +0 -1
  1023. package/dist/core/model-resolver.d.ts +0 -110
  1024. package/dist/core/model-resolver.d.ts.map +0 -1
  1025. package/dist/core/model-resolver.js +0 -486
  1026. package/dist/core/model-resolver.js.map +0 -1
  1027. package/dist/core/output-guard.d.ts +0 -6
  1028. package/dist/core/output-guard.d.ts.map +0 -1
  1029. package/dist/core/output-guard.js +0 -59
  1030. package/dist/core/output-guard.js.map +0 -1
  1031. package/dist/core/package-manager.d.ts +0 -192
  1032. package/dist/core/package-manager.d.ts.map +0 -1
  1033. package/dist/core/package-manager.js +0 -1832
  1034. package/dist/core/package-manager.js.map +0 -1
  1035. package/dist/core/prompt-templates.d.ts +0 -51
  1036. package/dist/core/prompt-templates.d.ts.map +0 -1
  1037. package/dist/core/prompt-templates.js +0 -249
  1038. package/dist/core/prompt-templates.js.map +0 -1
  1039. package/dist/core/resolve-config-value.d.ts +0 -23
  1040. package/dist/core/resolve-config-value.d.ts.map +0 -1
  1041. package/dist/core/resolve-config-value.js +0 -126
  1042. package/dist/core/resolve-config-value.js.map +0 -1
  1043. package/dist/core/resource-loader.d.ts +0 -185
  1044. package/dist/core/resource-loader.d.ts.map +0 -1
  1045. package/dist/core/resource-loader.js +0 -720
  1046. package/dist/core/resource-loader.js.map +0 -1
  1047. package/dist/core/sdk.d.ts +0 -93
  1048. package/dist/core/sdk.d.ts.map +0 -1
  1049. package/dist/core/sdk.js +0 -236
  1050. package/dist/core/sdk.js.map +0 -1
  1051. package/dist/core/session-cwd.d.ts +0 -19
  1052. package/dist/core/session-cwd.d.ts.map +0 -1
  1053. package/dist/core/session-cwd.js +0 -38
  1054. package/dist/core/session-cwd.js.map +0 -1
  1055. package/dist/core/session-manager.d.ts +0 -333
  1056. package/dist/core/session-manager.d.ts.map +0 -1
  1057. package/dist/core/session-manager.js +0 -1105
  1058. package/dist/core/session-manager.js.map +0 -1
  1059. package/dist/core/settings-manager.d.ts +0 -237
  1060. package/dist/core/settings-manager.d.ts.map +0 -1
  1061. package/dist/core/settings-manager.js +0 -703
  1062. package/dist/core/settings-manager.js.map +0 -1
  1063. package/dist/core/skills.d.ts +0 -60
  1064. package/dist/core/skills.d.ts.map +0 -1
  1065. package/dist/core/skills.js +0 -409
  1066. package/dist/core/skills.js.map +0 -1
  1067. package/dist/core/slash-commands.d.ts +0 -14
  1068. package/dist/core/slash-commands.d.ts.map +0 -1
  1069. package/dist/core/slash-commands.js +0 -23
  1070. package/dist/core/slash-commands.js.map +0 -1
  1071. package/dist/core/source-info.d.ts +0 -18
  1072. package/dist/core/source-info.d.ts.map +0 -1
  1073. package/dist/core/source-info.js +0 -19
  1074. package/dist/core/source-info.js.map +0 -1
  1075. package/dist/core/system-prompt.d.ts +0 -28
  1076. package/dist/core/system-prompt.d.ts.map +0 -1
  1077. package/dist/core/system-prompt.js +0 -116
  1078. package/dist/core/system-prompt.js.map +0 -1
  1079. package/dist/core/timings.d.ts +0 -8
  1080. package/dist/core/timings.d.ts.map +0 -1
  1081. package/dist/core/timings.js +0 -31
  1082. package/dist/core/timings.js.map +0 -1
  1083. package/dist/core/tools/bash.d.ts +0 -73
  1084. package/dist/core/tools/bash.d.ts.map +0 -1
  1085. package/dist/core/tools/bash.js +0 -352
  1086. package/dist/core/tools/bash.js.map +0 -1
  1087. package/dist/core/tools/edit-diff.d.ts +0 -85
  1088. package/dist/core/tools/edit-diff.d.ts.map +0 -1
  1089. package/dist/core/tools/edit-diff.js +0 -337
  1090. package/dist/core/tools/edit-diff.js.map +0 -1
  1091. package/dist/core/tools/edit.d.ts +0 -53
  1092. package/dist/core/tools/edit.d.ts.map +0 -1
  1093. package/dist/core/tools/edit.js +0 -196
  1094. package/dist/core/tools/edit.js.map +0 -1
  1095. package/dist/core/tools/file-mutation-queue.d.ts +0 -6
  1096. package/dist/core/tools/file-mutation-queue.d.ts.map +0 -1
  1097. package/dist/core/tools/file-mutation-queue.js +0 -37
  1098. package/dist/core/tools/file-mutation-queue.js.map +0 -1
  1099. package/dist/core/tools/find.d.ts +0 -46
  1100. package/dist/core/tools/find.d.ts.map +0 -1
  1101. package/dist/core/tools/find.js +0 -258
  1102. package/dist/core/tools/find.js.map +0 -1
  1103. package/dist/core/tools/grep.d.ts +0 -56
  1104. package/dist/core/tools/grep.d.ts.map +0 -1
  1105. package/dist/core/tools/grep.js +0 -293
  1106. package/dist/core/tools/grep.js.map +0 -1
  1107. package/dist/core/tools/index.d.ts +0 -115
  1108. package/dist/core/tools/index.d.ts.map +0 -1
  1109. package/dist/core/tools/index.js +0 -86
  1110. package/dist/core/tools/index.js.map +0 -1
  1111. package/dist/core/tools/ls.d.ts +0 -46
  1112. package/dist/core/tools/ls.d.ts.map +0 -1
  1113. package/dist/core/tools/ls.js +0 -172
  1114. package/dist/core/tools/ls.js.map +0 -1
  1115. package/dist/core/tools/path-utils.d.ts +0 -8
  1116. package/dist/core/tools/path-utils.d.ts.map +0 -1
  1117. package/dist/core/tools/path-utils.js +0 -81
  1118. package/dist/core/tools/path-utils.js.map +0 -1
  1119. package/dist/core/tools/read.d.ts +0 -46
  1120. package/dist/core/tools/read.d.ts.map +0 -1
  1121. package/dist/core/tools/read.js +0 -225
  1122. package/dist/core/tools/read.js.map +0 -1
  1123. package/dist/core/tools/render-utils.d.ts +0 -21
  1124. package/dist/core/tools/render-utils.d.ts.map +0 -1
  1125. package/dist/core/tools/render-utils.js +0 -49
  1126. package/dist/core/tools/render-utils.js.map +0 -1
  1127. package/dist/core/tools/tool-definition-wrapper.d.ts +0 -14
  1128. package/dist/core/tools/tool-definition-wrapper.d.ts.map +0 -1
  1129. package/dist/core/tools/tool-definition-wrapper.js +0 -32
  1130. package/dist/core/tools/tool-definition-wrapper.js.map +0 -1
  1131. package/dist/core/tools/truncate.d.ts +0 -70
  1132. package/dist/core/tools/truncate.d.ts.map +0 -1
  1133. package/dist/core/tools/truncate.js +0 -205
  1134. package/dist/core/tools/truncate.js.map +0 -1
  1135. package/dist/core/tools/write.d.ts +0 -35
  1136. package/dist/core/tools/write.d.ts.map +0 -1
  1137. package/dist/core/tools/write.js +0 -216
  1138. package/dist/core/tools/write.js.map +0 -1
  1139. package/dist/index.d.ts +0 -28
  1140. package/dist/index.d.ts.map +0 -1
  1141. package/dist/index.js +0 -43
  1142. package/dist/index.js.map +0 -1
  1143. package/dist/main.d.ts +0 -8
  1144. package/dist/main.d.ts.map +0 -1
  1145. package/dist/main.js +0 -593
  1146. package/dist/main.js.map +0 -1
  1147. package/dist/migrations.d.ts +0 -33
  1148. package/dist/migrations.d.ts.map +0 -1
  1149. package/dist/migrations.js +0 -281
  1150. package/dist/migrations.js.map +0 -1
  1151. package/dist/modes/index.d.ts +0 -9
  1152. package/dist/modes/index.d.ts.map +0 -1
  1153. package/dist/modes/index.js +0 -8
  1154. package/dist/modes/index.js.map +0 -1
  1155. package/dist/modes/interactive/components/armin.d.ts +0 -34
  1156. package/dist/modes/interactive/components/armin.d.ts.map +0 -1
  1157. package/dist/modes/interactive/components/armin.js +0 -333
  1158. package/dist/modes/interactive/components/armin.js.map +0 -1
  1159. package/dist/modes/interactive/components/assistant-message.d.ts +0 -18
  1160. package/dist/modes/interactive/components/assistant-message.d.ts.map +0 -1
  1161. package/dist/modes/interactive/components/assistant-message.js +0 -107
  1162. package/dist/modes/interactive/components/assistant-message.js.map +0 -1
  1163. package/dist/modes/interactive/components/bash-execution.d.ts +0 -34
  1164. package/dist/modes/interactive/components/bash-execution.d.ts.map +0 -1
  1165. package/dist/modes/interactive/components/bash-execution.js +0 -175
  1166. package/dist/modes/interactive/components/bash-execution.js.map +0 -1
  1167. package/dist/modes/interactive/components/bordered-loader.d.ts +0 -16
  1168. package/dist/modes/interactive/components/bordered-loader.d.ts.map +0 -1
  1169. package/dist/modes/interactive/components/bordered-loader.js +0 -51
  1170. package/dist/modes/interactive/components/bordered-loader.js.map +0 -1
  1171. package/dist/modes/interactive/components/branch-summary-message.d.ts +0 -16
  1172. package/dist/modes/interactive/components/branch-summary-message.d.ts.map +0 -1
  1173. package/dist/modes/interactive/components/branch-summary-message.js +0 -44
  1174. package/dist/modes/interactive/components/branch-summary-message.js.map +0 -1
  1175. package/dist/modes/interactive/components/compaction-summary-message.d.ts +0 -16
  1176. package/dist/modes/interactive/components/compaction-summary-message.d.ts.map +0 -1
  1177. package/dist/modes/interactive/components/compaction-summary-message.js +0 -45
  1178. package/dist/modes/interactive/components/compaction-summary-message.js.map +0 -1
  1179. package/dist/modes/interactive/components/config-selector.d.ts +0 -71
  1180. package/dist/modes/interactive/components/config-selector.d.ts.map +0 -1
  1181. package/dist/modes/interactive/components/config-selector.js +0 -479
  1182. package/dist/modes/interactive/components/config-selector.js.map +0 -1
  1183. package/dist/modes/interactive/components/countdown-timer.d.ts +0 -14
  1184. package/dist/modes/interactive/components/countdown-timer.d.ts.map +0 -1
  1185. package/dist/modes/interactive/components/countdown-timer.js +0 -33
  1186. package/dist/modes/interactive/components/countdown-timer.js.map +0 -1
  1187. package/dist/modes/interactive/components/custom-editor.d.ts +0 -21
  1188. package/dist/modes/interactive/components/custom-editor.d.ts.map +0 -1
  1189. package/dist/modes/interactive/components/custom-editor.js +0 -70
  1190. package/dist/modes/interactive/components/custom-editor.js.map +0 -1
  1191. package/dist/modes/interactive/components/custom-message.d.ts +0 -20
  1192. package/dist/modes/interactive/components/custom-message.d.ts.map +0 -1
  1193. package/dist/modes/interactive/components/custom-message.js +0 -79
  1194. package/dist/modes/interactive/components/custom-message.js.map +0 -1
  1195. package/dist/modes/interactive/components/daxnuts.d.ts +0 -23
  1196. package/dist/modes/interactive/components/daxnuts.d.ts.map +0 -1
  1197. package/dist/modes/interactive/components/daxnuts.js +0 -140
  1198. package/dist/modes/interactive/components/daxnuts.js.map +0 -1
  1199. package/dist/modes/interactive/components/diff.d.ts +0 -12
  1200. package/dist/modes/interactive/components/diff.d.ts.map +0 -1
  1201. package/dist/modes/interactive/components/diff.js +0 -133
  1202. package/dist/modes/interactive/components/diff.js.map +0 -1
  1203. package/dist/modes/interactive/components/dynamic-border.d.ts +0 -15
  1204. package/dist/modes/interactive/components/dynamic-border.d.ts.map +0 -1
  1205. package/dist/modes/interactive/components/dynamic-border.js +0 -21
  1206. package/dist/modes/interactive/components/dynamic-border.js.map +0 -1
  1207. package/dist/modes/interactive/components/extension-editor.d.ts +0 -20
  1208. package/dist/modes/interactive/components/extension-editor.d.ts.map +0 -1
  1209. package/dist/modes/interactive/components/extension-editor.js +0 -111
  1210. package/dist/modes/interactive/components/extension-editor.js.map +0 -1
  1211. package/dist/modes/interactive/components/extension-input.d.ts +0 -23
  1212. package/dist/modes/interactive/components/extension-input.d.ts.map +0 -1
  1213. package/dist/modes/interactive/components/extension-input.js +0 -61
  1214. package/dist/modes/interactive/components/extension-input.js.map +0 -1
  1215. package/dist/modes/interactive/components/extension-selector.d.ts +0 -24
  1216. package/dist/modes/interactive/components/extension-selector.d.ts.map +0 -1
  1217. package/dist/modes/interactive/components/extension-selector.js +0 -78
  1218. package/dist/modes/interactive/components/extension-selector.js.map +0 -1
  1219. package/dist/modes/interactive/components/footer.d.ts +0 -27
  1220. package/dist/modes/interactive/components/footer.d.ts.map +0 -1
  1221. package/dist/modes/interactive/components/footer.js +0 -201
  1222. package/dist/modes/interactive/components/footer.js.map +0 -1
  1223. package/dist/modes/interactive/components/index.d.ts +0 -32
  1224. package/dist/modes/interactive/components/index.d.ts.map +0 -1
  1225. package/dist/modes/interactive/components/index.js +0 -33
  1226. package/dist/modes/interactive/components/index.js.map +0 -1
  1227. package/dist/modes/interactive/components/keybinding-hints.d.ts +0 -8
  1228. package/dist/modes/interactive/components/keybinding-hints.d.ts.map +0 -1
  1229. package/dist/modes/interactive/components/keybinding-hints.js +0 -22
  1230. package/dist/modes/interactive/components/keybinding-hints.js.map +0 -1
  1231. package/dist/modes/interactive/components/login-dialog.d.ts +0 -42
  1232. package/dist/modes/interactive/components/login-dialog.d.ts.map +0 -1
  1233. package/dist/modes/interactive/components/login-dialog.js +0 -145
  1234. package/dist/modes/interactive/components/login-dialog.js.map +0 -1
  1235. package/dist/modes/interactive/components/model-selector.d.ts +0 -47
  1236. package/dist/modes/interactive/components/model-selector.d.ts.map +0 -1
  1237. package/dist/modes/interactive/components/model-selector.js +0 -275
  1238. package/dist/modes/interactive/components/model-selector.js.map +0 -1
  1239. package/dist/modes/interactive/components/oauth-selector.d.ts +0 -19
  1240. package/dist/modes/interactive/components/oauth-selector.d.ts.map +0 -1
  1241. package/dist/modes/interactive/components/oauth-selector.js +0 -97
  1242. package/dist/modes/interactive/components/oauth-selector.js.map +0 -1
  1243. package/dist/modes/interactive/components/scoped-models-selector.d.ts +0 -49
  1244. package/dist/modes/interactive/components/scoped-models-selector.d.ts.map +0 -1
  1245. package/dist/modes/interactive/components/scoped-models-selector.js +0 -275
  1246. package/dist/modes/interactive/components/scoped-models-selector.js.map +0 -1
  1247. package/dist/modes/interactive/components/session-selector-search.d.ts +0 -23
  1248. package/dist/modes/interactive/components/session-selector-search.d.ts.map +0 -1
  1249. package/dist/modes/interactive/components/session-selector-search.js +0 -155
  1250. package/dist/modes/interactive/components/session-selector-search.js.map +0 -1
  1251. package/dist/modes/interactive/components/session-selector.d.ts +0 -95
  1252. package/dist/modes/interactive/components/session-selector.d.ts.map +0 -1
  1253. package/dist/modes/interactive/components/session-selector.js +0 -848
  1254. package/dist/modes/interactive/components/session-selector.js.map +0 -1
  1255. package/dist/modes/interactive/components/settings-selector.d.ts +0 -58
  1256. package/dist/modes/interactive/components/settings-selector.d.ts.map +0 -1
  1257. package/dist/modes/interactive/components/settings-selector.js +0 -301
  1258. package/dist/modes/interactive/components/settings-selector.js.map +0 -1
  1259. package/dist/modes/interactive/components/show-images-selector.d.ts +0 -10
  1260. package/dist/modes/interactive/components/show-images-selector.d.ts.map +0 -1
  1261. package/dist/modes/interactive/components/show-images-selector.js +0 -39
  1262. package/dist/modes/interactive/components/show-images-selector.js.map +0 -1
  1263. package/dist/modes/interactive/components/skill-invocation-message.d.ts +0 -17
  1264. package/dist/modes/interactive/components/skill-invocation-message.d.ts.map +0 -1
  1265. package/dist/modes/interactive/components/skill-invocation-message.js +0 -47
  1266. package/dist/modes/interactive/components/skill-invocation-message.js.map +0 -1
  1267. package/dist/modes/interactive/components/theme-selector.d.ts +0 -11
  1268. package/dist/modes/interactive/components/theme-selector.d.ts.map +0 -1
  1269. package/dist/modes/interactive/components/theme-selector.js +0 -50
  1270. package/dist/modes/interactive/components/theme-selector.js.map +0 -1
  1271. package/dist/modes/interactive/components/thinking-selector.d.ts +0 -11
  1272. package/dist/modes/interactive/components/thinking-selector.d.ts.map +0 -1
  1273. package/dist/modes/interactive/components/thinking-selector.js +0 -51
  1274. package/dist/modes/interactive/components/thinking-selector.js.map +0 -1
  1275. package/dist/modes/interactive/components/tool-execution.d.ts +0 -58
  1276. package/dist/modes/interactive/components/tool-execution.d.ts.map +0 -1
  1277. package/dist/modes/interactive/components/tool-execution.js +0 -274
  1278. package/dist/modes/interactive/components/tool-execution.js.map +0 -1
  1279. package/dist/modes/interactive/components/tree-selector.d.ts +0 -89
  1280. package/dist/modes/interactive/components/tree-selector.d.ts.map +0 -1
  1281. package/dist/modes/interactive/components/tree-selector.js +0 -1084
  1282. package/dist/modes/interactive/components/tree-selector.js.map +0 -1
  1283. package/dist/modes/interactive/components/user-message-selector.d.ts +0 -30
  1284. package/dist/modes/interactive/components/user-message-selector.d.ts.map +0 -1
  1285. package/dist/modes/interactive/components/user-message-selector.js +0 -113
  1286. package/dist/modes/interactive/components/user-message-selector.js.map +0 -1
  1287. package/dist/modes/interactive/components/user-message.d.ts +0 -9
  1288. package/dist/modes/interactive/components/user-message.d.ts.map +0 -1
  1289. package/dist/modes/interactive/components/user-message.js +0 -28
  1290. package/dist/modes/interactive/components/user-message.js.map +0 -1
  1291. package/dist/modes/interactive/components/visual-truncate.d.ts +0 -24
  1292. package/dist/modes/interactive/components/visual-truncate.d.ts.map +0 -1
  1293. package/dist/modes/interactive/components/visual-truncate.js +0 -33
  1294. package/dist/modes/interactive/components/visual-truncate.js.map +0 -1
  1295. package/dist/modes/interactive/interactive-mode.d.ts +0 -320
  1296. package/dist/modes/interactive/interactive-mode.d.ts.map +0 -1
  1297. package/dist/modes/interactive/interactive-mode.js +0 -3970
  1298. package/dist/modes/interactive/interactive-mode.js.map +0 -1
  1299. package/dist/modes/interactive/theme/dark.json +0 -85
  1300. package/dist/modes/interactive/theme/light.json +0 -84
  1301. package/dist/modes/interactive/theme/theme-schema.json +0 -335
  1302. package/dist/modes/interactive/theme/theme.d.ts +0 -81
  1303. package/dist/modes/interactive/theme/theme.d.ts.map +0 -1
  1304. package/dist/modes/interactive/theme/theme.js +0 -979
  1305. package/dist/modes/interactive/theme/theme.js.map +0 -1
  1306. package/dist/modes/print-mode.d.ts +0 -28
  1307. package/dist/modes/print-mode.d.ts.map +0 -1
  1308. package/dist/modes/print-mode.js +0 -112
  1309. package/dist/modes/print-mode.js.map +0 -1
  1310. package/dist/modes/rpc/jsonl.d.ts +0 -17
  1311. package/dist/modes/rpc/jsonl.d.ts.map +0 -1
  1312. package/dist/modes/rpc/jsonl.js +0 -49
  1313. package/dist/modes/rpc/jsonl.js.map +0 -1
  1314. package/dist/modes/rpc/rpc-client.d.ts +0 -217
  1315. package/dist/modes/rpc/rpc-client.d.ts.map +0 -1
  1316. package/dist/modes/rpc/rpc-client.js +0 -402
  1317. package/dist/modes/rpc/rpc-client.js.map +0 -1
  1318. package/dist/modes/rpc/rpc-mode.d.ts +0 -20
  1319. package/dist/modes/rpc/rpc-mode.d.ts.map +0 -1
  1320. package/dist/modes/rpc/rpc-mode.js +0 -550
  1321. package/dist/modes/rpc/rpc-mode.js.map +0 -1
  1322. package/dist/modes/rpc/rpc-types.d.ts +0 -408
  1323. package/dist/modes/rpc/rpc-types.d.ts.map +0 -1
  1324. package/dist/modes/rpc/rpc-types.js +0 -8
  1325. package/dist/modes/rpc/rpc-types.js.map +0 -1
  1326. package/dist/package-manager-cli.d.ts +0 -4
  1327. package/dist/package-manager-cli.d.ts.map +0 -1
  1328. package/dist/package-manager-cli.js +0 -234
  1329. package/dist/package-manager-cli.js.map +0 -1
  1330. package/dist/utils/changelog.d.ts +0 -21
  1331. package/dist/utils/changelog.d.ts.map +0 -1
  1332. package/dist/utils/changelog.js +0 -87
  1333. package/dist/utils/changelog.js.map +0 -1
  1334. package/dist/utils/child-process.d.ts +0 -11
  1335. package/dist/utils/child-process.d.ts.map +0 -1
  1336. package/dist/utils/child-process.js +0 -78
  1337. package/dist/utils/child-process.js.map +0 -1
  1338. package/dist/utils/clipboard-image.d.ts +0 -11
  1339. package/dist/utils/clipboard-image.d.ts.map +0 -1
  1340. package/dist/utils/clipboard-image.js +0 -245
  1341. package/dist/utils/clipboard-image.js.map +0 -1
  1342. package/dist/utils/clipboard-native.d.ts +0 -8
  1343. package/dist/utils/clipboard-native.d.ts.map +0 -1
  1344. package/dist/utils/clipboard-native.js +0 -14
  1345. package/dist/utils/clipboard-native.js.map +0 -1
  1346. package/dist/utils/clipboard.d.ts +0 -2
  1347. package/dist/utils/clipboard.d.ts.map +0 -1
  1348. package/dist/utils/clipboard.js +0 -78
  1349. package/dist/utils/clipboard.js.map +0 -1
  1350. package/dist/utils/exif-orientation.d.ts +0 -5
  1351. package/dist/utils/exif-orientation.d.ts.map +0 -1
  1352. package/dist/utils/exif-orientation.js +0 -158
  1353. package/dist/utils/exif-orientation.js.map +0 -1
  1354. package/dist/utils/frontmatter.d.ts +0 -8
  1355. package/dist/utils/frontmatter.d.ts.map +0 -1
  1356. package/dist/utils/frontmatter.js +0 -26
  1357. package/dist/utils/frontmatter.js.map +0 -1
  1358. package/dist/utils/git.d.ts +0 -26
  1359. package/dist/utils/git.d.ts.map +0 -1
  1360. package/dist/utils/git.js +0 -163
  1361. package/dist/utils/git.js.map +0 -1
  1362. package/dist/utils/image-convert.d.ts +0 -9
  1363. package/dist/utils/image-convert.d.ts.map +0 -1
  1364. package/dist/utils/image-convert.js +0 -39
  1365. package/dist/utils/image-convert.js.map +0 -1
  1366. package/dist/utils/image-resize.d.ts +0 -36
  1367. package/dist/utils/image-resize.d.ts.map +0 -1
  1368. package/dist/utils/image-resize.js +0 -137
  1369. package/dist/utils/image-resize.js.map +0 -1
  1370. package/dist/utils/mime.d.ts +0 -2
  1371. package/dist/utils/mime.d.ts.map +0 -1
  1372. package/dist/utils/mime.js +0 -26
  1373. package/dist/utils/mime.js.map +0 -1
  1374. package/dist/utils/paths.d.ts +0 -7
  1375. package/dist/utils/paths.d.ts.map +0 -1
  1376. package/dist/utils/paths.js +0 -19
  1377. package/dist/utils/paths.js.map +0 -1
  1378. package/dist/utils/photon.d.ts +0 -21
  1379. package/dist/utils/photon.d.ts.map +0 -1
  1380. package/dist/utils/photon.js +0 -121
  1381. package/dist/utils/photon.js.map +0 -1
  1382. package/dist/utils/shell.d.ts +0 -26
  1383. package/dist/utils/shell.d.ts.map +0 -1
  1384. package/dist/utils/shell.js +0 -186
  1385. package/dist/utils/shell.js.map +0 -1
  1386. package/dist/utils/sleep.d.ts +0 -5
  1387. package/dist/utils/sleep.d.ts.map +0 -1
  1388. package/dist/utils/sleep.js +0 -17
  1389. package/dist/utils/sleep.js.map +0 -1
  1390. package/dist/utils/tools-manager.d.ts +0 -3
  1391. package/dist/utils/tools-manager.d.ts.map +0 -1
  1392. package/dist/utils/tools-manager.js +0 -252
  1393. package/dist/utils/tools-manager.js.map +0 -1
  1394. package/docs/compaction.md +0 -398
  1395. package/docs/custom-provider.md +0 -597
  1396. package/docs/development.md +0 -72
  1397. package/docs/extensions.md +0 -2288
  1398. package/docs/images/doom-extension.png +0 -0
  1399. package/docs/images/exy.png +0 -0
  1400. package/docs/images/interactive-mode.png +0 -0
  1401. package/docs/images/tree-view.png +0 -0
  1402. package/docs/json.md +0 -84
  1403. package/docs/keybindings.md +0 -175
  1404. package/docs/models.md +0 -349
  1405. package/docs/packages.md +0 -219
  1406. package/docs/prompt-templates.md +0 -67
  1407. package/docs/providers.md +0 -200
  1408. package/docs/rpc.md +0 -1425
  1409. package/docs/sdk.md +0 -1136
  1410. package/docs/session.md +0 -423
  1411. package/docs/settings.md +0 -246
  1412. package/docs/shell-aliases.md +0 -13
  1413. package/docs/skills.md +0 -236
  1414. package/docs/terminal-setup.md +0 -108
  1415. package/docs/termux.md +0 -137
  1416. package/docs/themes.md +0 -296
  1417. package/docs/tmux.md +0 -61
  1418. package/docs/tree.md +0 -239
  1419. package/docs/tui.md +0 -890
  1420. package/docs/windows.md +0 -17
  1421. package/examples/extensions/antigravity-image-gen.ts +0 -418
  1422. package/examples/extensions/auto-commit-on-exit.ts +0 -49
  1423. package/examples/extensions/bash-spawn-hook.ts +0 -30
  1424. package/examples/extensions/bookmark.ts +0 -50
  1425. package/examples/extensions/built-in-tool-renderer.ts +0 -246
  1426. package/examples/extensions/claude-rules.ts +0 -86
  1427. package/examples/extensions/commands.ts +0 -72
  1428. package/examples/extensions/confirm-destructive.ts +0 -59
  1429. package/examples/extensions/custom-compaction.ts +0 -127
  1430. package/examples/extensions/custom-footer.ts +0 -64
  1431. package/examples/extensions/custom-header.ts +0 -73
  1432. package/examples/extensions/custom-provider-anthropic/index.ts +0 -604
  1433. package/examples/extensions/custom-provider-anthropic/package-lock.json +0 -24
  1434. package/examples/extensions/custom-provider-anthropic/package.json +0 -19
  1435. package/examples/extensions/custom-provider-gitlab-duo/index.ts +0 -349
  1436. package/examples/extensions/custom-provider-gitlab-duo/package.json +0 -16
  1437. package/examples/extensions/custom-provider-gitlab-duo/test.ts +0 -82
  1438. package/examples/extensions/custom-provider-qwen-cli/index.ts +0 -345
  1439. package/examples/extensions/custom-provider-qwen-cli/package.json +0 -16
  1440. package/examples/extensions/dirty-repo-guard.ts +0 -56
  1441. package/examples/extensions/doom-overlay/README.md +0 -48
  1442. package/examples/extensions/doom-overlay/doom/build/doom.js +0 -21
  1443. package/examples/extensions/doom-overlay/doom/build/doom.wasm +0 -0
  1444. package/examples/extensions/doom-overlay/doom/build.sh +0 -152
  1445. package/examples/extensions/doom-overlay/doom/doomgeneric_pi.c +0 -72
  1446. package/examples/extensions/doom-overlay/doom-component.ts +0 -132
  1447. package/examples/extensions/doom-overlay/doom-engine.ts +0 -173
  1448. package/examples/extensions/doom-overlay/doom-keys.ts +0 -104
  1449. package/examples/extensions/doom-overlay/index.ts +0 -74
  1450. package/examples/extensions/doom-overlay/wad-finder.ts +0 -51
  1451. package/examples/extensions/dynamic-resources/SKILL.md +0 -8
  1452. package/examples/extensions/dynamic-resources/dynamic.json +0 -79
  1453. package/examples/extensions/dynamic-resources/dynamic.md +0 -5
  1454. package/examples/extensions/dynamic-resources/index.ts +0 -15
  1455. package/examples/extensions/dynamic-tools.ts +0 -74
  1456. package/examples/extensions/event-bus.ts +0 -43
  1457. package/examples/extensions/file-trigger.ts +0 -41
  1458. package/examples/extensions/git-checkpoint.ts +0 -53
  1459. package/examples/extensions/handoff.ts +0 -153
  1460. package/examples/extensions/hidden-thinking-label.ts +0 -53
  1461. package/examples/extensions/inline-bash.ts +0 -94
  1462. package/examples/extensions/input-transform.ts +0 -43
  1463. package/examples/extensions/interactive-shell.ts +0 -196
  1464. package/examples/extensions/mac-system-theme.ts +0 -47
  1465. package/examples/extensions/message-renderer.ts +0 -59
  1466. package/examples/extensions/minimal-mode.ts +0 -426
  1467. package/examples/extensions/modal-editor.ts +0 -85
  1468. package/examples/extensions/model-status.ts +0 -31
  1469. package/examples/extensions/notify.ts +0 -55
  1470. package/examples/extensions/overlay-qa-tests.ts +0 -1348
  1471. package/examples/extensions/overlay-test.ts +0 -150
  1472. package/examples/extensions/permission-gate.ts +0 -34
  1473. package/examples/extensions/plan-mode/README.md +0 -69
  1474. package/examples/extensions/plan-mode/index.ts +0 -340
  1475. package/examples/extensions/plan-mode/utils.ts +0 -168
  1476. package/examples/extensions/preset.ts +0 -403
  1477. package/examples/extensions/protected-paths.ts +0 -30
  1478. package/examples/extensions/provider-payload.ts +0 -14
  1479. package/examples/extensions/qna.ts +0 -122
  1480. package/examples/extensions/question.ts +0 -264
  1481. package/examples/extensions/questionnaire.ts +0 -427
  1482. package/examples/extensions/rainbow-editor.ts +0 -88
  1483. package/examples/extensions/rpc-demo.ts +0 -118
  1484. package/examples/extensions/sandbox/index.ts +0 -321
  1485. package/examples/extensions/sandbox/package-lock.json +0 -92
  1486. package/examples/extensions/sandbox/package.json +0 -19
  1487. package/examples/extensions/send-user-message.ts +0 -97
  1488. package/examples/extensions/session-name.ts +0 -27
  1489. package/examples/extensions/shutdown-command.ts +0 -63
  1490. package/examples/extensions/snake.ts +0 -343
  1491. package/examples/extensions/space-invaders.ts +0 -560
  1492. package/examples/extensions/ssh.ts +0 -220
  1493. package/examples/extensions/status-line.ts +0 -32
  1494. package/examples/extensions/subagent/README.md +0 -181
  1495. package/examples/extensions/subagent/agents/planner.md +0 -37
  1496. package/examples/extensions/subagent/agents/reviewer.md +0 -35
  1497. package/examples/extensions/subagent/agents/scout.md +0 -50
  1498. package/examples/extensions/subagent/agents/worker.md +0 -24
  1499. package/examples/extensions/subagent/agents.ts +0 -126
  1500. package/examples/extensions/subagent/index.ts +0 -986
  1501. package/examples/extensions/subagent/prompts/implement-and-review.md +0 -10
  1502. package/examples/extensions/subagent/prompts/implement.md +0 -10
  1503. package/examples/extensions/subagent/prompts/scout-and-plan.md +0 -9
  1504. package/examples/extensions/summarize.ts +0 -206
  1505. package/examples/extensions/system-prompt-header.ts +0 -17
  1506. package/examples/extensions/timed-confirm.ts +0 -70
  1507. package/examples/extensions/titlebar-spinner.ts +0 -58
  1508. package/examples/extensions/tool-override.ts +0 -144
  1509. package/examples/extensions/trigger-compact.ts +0 -50
  1510. package/examples/extensions/truncated-tool.ts +0 -195
  1511. package/examples/extensions/widget-placement.ts +0 -9
  1512. package/examples/rpc-extension-ui.ts +0 -640
  1513. package/examples/sdk/05-tools.ts +0 -56
  1514. package/examples/sdk/10-settings.ts +0 -51
  1515. package/examples/sdk/12-full-control.ts +0 -81
  1516. package/examples/sdk/13-session-runtime.ts +0 -67
  1517. /package/{dist/core/export-html → src/export/html}/vendor/highlight.min.js +0 -0
  1518. /package/{dist/core/export-html → src/export/html}/vendor/marked.min.js +0 -0
@@ -0,0 +1,1743 @@
1
+ import * as fs from "node:fs";
2
+ import path from "node:path";
3
+ import type {
4
+ AgentTool,
5
+ AgentToolContext,
6
+ AgentToolResult,
7
+ AgentToolUpdateCallback,
8
+ } from "@f5xc-salesdemos/pi-agent-core";
9
+ import { logger, once, prompt, untilAborted } from "@f5xc-salesdemos/pi-utils";
10
+ import type { BunFile } from "bun";
11
+ import { type Theme, theme } from "../modes/theme/theme";
12
+ import lspDescription from "../prompts/tools/lsp.md" with { type: "text" };
13
+ import type { ToolSession } from "../tools";
14
+ import { resolveToCwd } from "../tools/path-utils";
15
+ import { ToolAbortError, throwIfAborted } from "../tools/tool-errors";
16
+ import { clampTimeout } from "../tools/tool-timeouts";
17
+ import {
18
+ ensureFileOpen,
19
+ getActiveClients,
20
+ getOrCreateClient,
21
+ type LspServerStatus,
22
+ notifySaved,
23
+ refreshFile,
24
+ sendRequest,
25
+ setIdleTimeout,
26
+ syncContent,
27
+ WARMUP_TIMEOUT_MS,
28
+ } from "./client";
29
+ import { getLinterClient } from "./clients";
30
+ import { getServersForFile, type LspConfig, loadConfig } from "./config";
31
+ import { applyTextEditsToString, applyWorkspaceEdit } from "./edits";
32
+ import { detectLspmux } from "./lspmux";
33
+ import { renderCall, renderResult } from "./render";
34
+ import {
35
+ type CodeAction,
36
+ type CodeActionContext,
37
+ type Command,
38
+ type Diagnostic,
39
+ type DocumentSymbol,
40
+ type Hover,
41
+ type Location,
42
+ type LocationLink,
43
+ type LspClient,
44
+ type LspParams,
45
+ type LspToolDetails,
46
+ lspSchema,
47
+ type PublishedDiagnostics,
48
+ type ServerConfig,
49
+ type SymbolInformation,
50
+ type TextEdit,
51
+ type WorkspaceEdit,
52
+ } from "./types";
53
+ import {
54
+ applyCodeAction,
55
+ collectGlobMatches,
56
+ dedupeWorkspaceSymbols,
57
+ extractHoverText,
58
+ fileToUri,
59
+ filterWorkspaceSymbols,
60
+ formatCodeAction,
61
+ formatDiagnostic,
62
+ formatDiagnosticsSummary,
63
+ formatDocumentSymbol,
64
+ formatGroupedDiagnosticMessages,
65
+ formatLocation,
66
+ formatSymbolInformation,
67
+ formatWorkspaceEdit,
68
+ hasGlobPattern,
69
+ readLocationContext,
70
+ resolveSymbolColumn,
71
+ sortDiagnostics,
72
+ symbolKindToIcon,
73
+ uriToFile,
74
+ } from "./utils";
75
+
76
+ export type { LspServerStatus } from "./client";
77
+ export type { LspToolDetails } from "./types";
78
+
79
+ export interface LspStartupServerInfo {
80
+ name: string;
81
+ status: "connecting" | "ready" | "error";
82
+ fileTypes: string[];
83
+ error?: string;
84
+ }
85
+
86
+ /** Result from warming up LSP servers */
87
+ export interface LspWarmupResult {
88
+ servers: Array<LspStartupServerInfo & { status: "ready" | "error" }>;
89
+ }
90
+
91
+ /** Options for warming up LSP servers */
92
+ export interface LspWarmupOptions {
93
+ /** Called when starting to connect to servers */
94
+ onConnecting?: (serverNames: string[]) => void;
95
+ }
96
+
97
+ export function discoverStartupLspServers(cwd: string): LspStartupServerInfo[] {
98
+ const config = loadConfig(cwd);
99
+ return getLspServers(config).map(([name, serverConfig]) => ({
100
+ name,
101
+ status: "connecting",
102
+ fileTypes: serverConfig.fileTypes,
103
+ }));
104
+ }
105
+
106
+ /**
107
+ * Warm up LSP servers for a directory by connecting to all detected servers.
108
+ * This should be called at startup to avoid cold-start delays.
109
+ *
110
+ * @param cwd - Working directory to detect and start servers for
111
+ * @param options - Optional callbacks for progress reporting
112
+ * @returns Status of each server that was started
113
+ */
114
+ export async function warmupLspServers(cwd: string, options?: LspWarmupOptions): Promise<LspWarmupResult> {
115
+ const config = loadConfig(cwd);
116
+ setIdleTimeout(config.idleTimeoutMs);
117
+ const servers: LspWarmupResult["servers"] = [];
118
+ const lspServers = getLspServers(config);
119
+
120
+ // Notify caller which servers we're connecting to
121
+ if (lspServers.length > 0 && options?.onConnecting) {
122
+ options.onConnecting(lspServers.map(([name]) => name));
123
+ }
124
+
125
+ // Start all detected servers in parallel with a short timeout
126
+ // Servers that don't respond quickly will be initialized lazily on first use
127
+ const results = await Promise.allSettled(
128
+ lspServers.map(async ([name, serverConfig]) => {
129
+ const client = await getOrCreateClient(serverConfig, cwd, serverConfig.warmupTimeoutMs ?? WARMUP_TIMEOUT_MS);
130
+ return { name, client, fileTypes: serverConfig.fileTypes };
131
+ }),
132
+ );
133
+
134
+ for (let i = 0; i < results.length; i++) {
135
+ const result = results[i];
136
+ const [name, serverConfig] = lspServers[i];
137
+ if (result.status === "fulfilled") {
138
+ servers.push({
139
+ name: result.value.name,
140
+ status: "ready",
141
+ fileTypes: result.value.fileTypes,
142
+ });
143
+ } else {
144
+ const errorMsg = result.reason?.message ?? String(result.reason);
145
+ logger.warn("LSP server failed to start", { server: name, error: errorMsg });
146
+ servers.push({
147
+ name,
148
+ status: "error",
149
+ fileTypes: serverConfig.fileTypes,
150
+ error: errorMsg,
151
+ });
152
+ }
153
+ }
154
+
155
+ return { servers };
156
+ }
157
+
158
+ /**
159
+ * Get status of currently active LSP servers.
160
+ */
161
+ export function getLspStatus(): LspServerStatus[] {
162
+ return getActiveClients();
163
+ }
164
+
165
+ /**
166
+ * Sync in-memory file content to all applicable LSP servers.
167
+ * Sends didOpen (if new) or didChange (if already open).
168
+ *
169
+ * @param absolutePath - Absolute path to the file
170
+ * @param content - The new file content
171
+ * @param cwd - Working directory for LSP config resolution
172
+ * @param servers - Servers to sync to
173
+ */
174
+ async function syncFileContent(
175
+ absolutePath: string,
176
+ content: string,
177
+ cwd: string,
178
+ servers: Array<[string, ServerConfig]>,
179
+ signal?: AbortSignal,
180
+ ): Promise<void> {
181
+ throwIfAborted(signal);
182
+ await Promise.allSettled(
183
+ servers.map(async ([_serverName, serverConfig]) => {
184
+ throwIfAborted(signal);
185
+ if (serverConfig.createClient) {
186
+ return;
187
+ }
188
+ const client = await getOrCreateClient(serverConfig, cwd);
189
+ throwIfAborted(signal);
190
+ await syncContent(client, absolutePath, content, signal);
191
+ }),
192
+ );
193
+ }
194
+
195
+ /**
196
+ * Notify all LSP servers that a file was saved.
197
+ * Assumes content was already synced via syncFileContent.
198
+ *
199
+ * @param absolutePath - Absolute path to the file
200
+ * @param cwd - Working directory for LSP config resolution
201
+ * @param servers - Servers to notify
202
+ */
203
+ async function notifyFileSaved(
204
+ absolutePath: string,
205
+ cwd: string,
206
+ servers: Array<[string, ServerConfig]>,
207
+ signal?: AbortSignal,
208
+ ): Promise<void> {
209
+ throwIfAborted(signal);
210
+ await Promise.allSettled(
211
+ servers.map(async ([_serverName, serverConfig]) => {
212
+ throwIfAborted(signal);
213
+ if (serverConfig.createClient) {
214
+ return;
215
+ }
216
+ const client = await getOrCreateClient(serverConfig, cwd);
217
+ await notifySaved(client, absolutePath, signal);
218
+ }),
219
+ );
220
+ }
221
+
222
+ // Cache config per cwd to avoid repeated file I/O
223
+ const configCache = new Map<string, LspConfig>();
224
+
225
+ function getConfig(cwd: string): LspConfig {
226
+ let config = configCache.get(cwd);
227
+ if (!config) {
228
+ config = loadConfig(cwd);
229
+ setIdleTimeout(config.idleTimeoutMs);
230
+ configCache.set(cwd, config);
231
+ }
232
+ return config;
233
+ }
234
+
235
+ function isCustomLinter(serverConfig: ServerConfig): boolean {
236
+ return Boolean(serverConfig.createClient);
237
+ }
238
+
239
+ function splitServers(servers: Array<[string, ServerConfig]>): {
240
+ lspServers: Array<[string, ServerConfig]>;
241
+ customLinterServers: Array<[string, ServerConfig]>;
242
+ } {
243
+ const lspServers: Array<[string, ServerConfig]> = [];
244
+ const customLinterServers: Array<[string, ServerConfig]> = [];
245
+ for (const entry of servers) {
246
+ if (isCustomLinter(entry[1])) {
247
+ customLinterServers.push(entry);
248
+ } else {
249
+ lspServers.push(entry);
250
+ }
251
+ }
252
+ return { lspServers, customLinterServers };
253
+ }
254
+
255
+ function getLspServers(config: LspConfig): Array<[string, ServerConfig]> {
256
+ return (Object.entries(config.servers) as Array<[string, ServerConfig]>).filter(
257
+ ([, serverConfig]) => !isCustomLinter(serverConfig),
258
+ );
259
+ }
260
+
261
+ function getLspServersForFile(config: LspConfig, filePath: string): Array<[string, ServerConfig]> {
262
+ return getServersForFile(config, filePath).filter(([, serverConfig]) => !isCustomLinter(serverConfig));
263
+ }
264
+
265
+ function getLspServerForFile(config: LspConfig, filePath: string): [string, ServerConfig] | null {
266
+ const servers = getLspServersForFile(config, filePath);
267
+ return servers.length > 0 ? servers[0] : null;
268
+ }
269
+
270
+ const DIAGNOSTIC_MESSAGE_LIMIT = 50;
271
+ const SINGLE_DIAGNOSTICS_WAIT_TIMEOUT_MS = 3000;
272
+ const BATCH_DIAGNOSTICS_WAIT_TIMEOUT_MS = 400;
273
+ const MAX_GLOB_DIAGNOSTIC_TARGETS = 20;
274
+ const WORKSPACE_SYMBOL_LIMIT = 200;
275
+
276
+ function limitDiagnosticMessages(messages: string[]): string[] {
277
+ if (messages.length <= DIAGNOSTIC_MESSAGE_LIMIT) {
278
+ return messages;
279
+ }
280
+ return messages.slice(0, DIAGNOSTIC_MESSAGE_LIMIT);
281
+ }
282
+
283
+ const LOCATION_CONTEXT_LINES = 1;
284
+ const REFERENCE_CONTEXT_LIMIT = 50;
285
+
286
+ function normalizeLocationResult(result: Location | Location[] | LocationLink | LocationLink[] | null): Location[] {
287
+ if (!result) return [];
288
+ const raw = Array.isArray(result) ? result : [result];
289
+ return raw.flatMap(loc => {
290
+ if ("uri" in loc) {
291
+ return [loc as Location];
292
+ }
293
+ if ("targetUri" in loc) {
294
+ const link = loc as LocationLink;
295
+ return [{ uri: link.targetUri, range: link.targetSelectionRange ?? link.targetRange }];
296
+ }
297
+ return [];
298
+ });
299
+ }
300
+
301
+ async function formatLocationWithContext(location: Location, cwd: string): Promise<string> {
302
+ const header = ` ${formatLocation(location, cwd)}`;
303
+ const context = await readLocationContext(
304
+ uriToFile(location.uri),
305
+ location.range.start.line + 1,
306
+ LOCATION_CONTEXT_LINES,
307
+ );
308
+ if (context.length === 0) {
309
+ return header;
310
+ }
311
+ return `${header}\n${context.map(lineText => ` ${lineText}`).join("\n")}`;
312
+ }
313
+ async function reloadServer(client: LspClient, serverName: string, signal?: AbortSignal): Promise<string> {
314
+ let output = `Restarted ${serverName}`;
315
+ const reloadMethods = ["rust-analyzer/reloadWorkspace", "workspace/didChangeConfiguration"];
316
+ for (const method of reloadMethods) {
317
+ try {
318
+ await sendRequest(client, method, method.includes("Configuration") ? { settings: {} } : null, signal);
319
+ output = `Reloaded ${serverName}`;
320
+ break;
321
+ } catch {
322
+ // Method not supported, try next
323
+ }
324
+ }
325
+ if (output.startsWith("Restarted")) {
326
+ client.proc.kill();
327
+ }
328
+ return output;
329
+ }
330
+
331
+ interface WaitForDiagnosticsOptions {
332
+ timeoutMs?: number;
333
+ signal?: AbortSignal;
334
+ minVersion?: number;
335
+ expectedDocumentVersion?: number;
336
+ allowUnversioned?: boolean;
337
+ }
338
+
339
+ function getAcceptedDiagnostics(
340
+ publishedDiagnostics: PublishedDiagnostics | undefined,
341
+ expectedDocumentVersion?: number,
342
+ allowUnversioned = true,
343
+ ): Diagnostic[] | undefined {
344
+ if (!publishedDiagnostics) {
345
+ return undefined;
346
+ }
347
+ if (expectedDocumentVersion === undefined) {
348
+ return publishedDiagnostics.diagnostics;
349
+ }
350
+ if (publishedDiagnostics.version === expectedDocumentVersion) {
351
+ return publishedDiagnostics.diagnostics;
352
+ }
353
+ if (allowUnversioned && publishedDiagnostics.version == null) {
354
+ return publishedDiagnostics.diagnostics;
355
+ }
356
+ return undefined;
357
+ }
358
+
359
+ async function waitForDiagnostics(
360
+ client: LspClient,
361
+ uri: string,
362
+ options: WaitForDiagnosticsOptions = {},
363
+ ): Promise<Diagnostic[]> {
364
+ const { timeoutMs = 3000, signal, minVersion, expectedDocumentVersion, allowUnversioned = true } = options;
365
+ const start = Date.now();
366
+ while (Date.now() - start < timeoutMs) {
367
+ throwIfAborted(signal);
368
+ const versionOk = minVersion === undefined || client.diagnosticsVersion > minVersion;
369
+ const diagnostics = getAcceptedDiagnostics(
370
+ client.diagnostics.get(uri),
371
+ expectedDocumentVersion,
372
+ allowUnversioned,
373
+ );
374
+ if (diagnostics !== undefined && versionOk) {
375
+ return diagnostics;
376
+ }
377
+ await Bun.sleep(100);
378
+ }
379
+ const versionOk = minVersion === undefined || client.diagnosticsVersion > minVersion;
380
+ if (!versionOk) {
381
+ return [];
382
+ }
383
+ return getAcceptedDiagnostics(client.diagnostics.get(uri), expectedDocumentVersion, allowUnversioned) ?? [];
384
+ }
385
+
386
+ /** Project type detection result */
387
+ interface ProjectType {
388
+ type: "rust" | "typescript" | "go" | "python" | "unknown";
389
+ command?: string[];
390
+ description: string;
391
+ }
392
+
393
+ /** Detect project type from root markers */
394
+ function detectProjectType(cwd: string): ProjectType {
395
+ // Check for Rust (Cargo.toml)
396
+ if (fs.existsSync(path.join(cwd, "Cargo.toml"))) {
397
+ return { type: "rust", command: ["cargo", "check", "--message-format=short"], description: "Rust (cargo check)" };
398
+ }
399
+
400
+ // Check for TypeScript (tsconfig.json)
401
+ if (fs.existsSync(path.join(cwd, "tsconfig.json"))) {
402
+ return { type: "typescript", command: ["npx", "tsc", "--noEmit"], description: "TypeScript (tsc --noEmit)" };
403
+ }
404
+
405
+ // Check for Go (go.mod)
406
+ if (fs.existsSync(path.join(cwd, "go.mod"))) {
407
+ return { type: "go", command: ["go", "build", "./..."], description: "Go (go build)" };
408
+ }
409
+
410
+ // Check for Python (pyproject.toml or pyrightconfig.json)
411
+ if (fs.existsSync(path.join(cwd, "pyproject.toml")) || fs.existsSync(path.join(cwd, "pyrightconfig.json"))) {
412
+ return { type: "python", command: ["pyright"], description: "Python (pyright)" };
413
+ }
414
+
415
+ return { type: "unknown", description: "Unknown project type" };
416
+ }
417
+
418
+ /** Run workspace diagnostics command and parse output */
419
+ async function runWorkspaceDiagnostics(
420
+ cwd: string,
421
+ signal?: AbortSignal,
422
+ ): Promise<{ output: string; projectType: ProjectType }> {
423
+ throwIfAborted(signal);
424
+ const projectType = detectProjectType(cwd);
425
+ if (!projectType.command) {
426
+ return {
427
+ output: `Cannot detect project type. Supported: Rust (Cargo.toml), TypeScript (tsconfig.json), Go (go.mod), Python (pyproject.toml)`,
428
+ projectType,
429
+ };
430
+ }
431
+ const proc = Bun.spawn(projectType.command, {
432
+ cwd,
433
+ stdout: "pipe",
434
+ stderr: "pipe",
435
+ windowsHide: true,
436
+ });
437
+ const abortHandler = () => {
438
+ proc.kill();
439
+ };
440
+ if (signal) {
441
+ signal.addEventListener("abort", abortHandler, { once: true });
442
+ }
443
+
444
+ try {
445
+ const [stdout, stderr] = await Promise.all([new Response(proc.stdout).text(), new Response(proc.stderr).text()]);
446
+ await proc.exited;
447
+ throwIfAborted(signal);
448
+ const combined = (stdout + stderr).trim();
449
+ if (!combined) {
450
+ return { output: "No issues found", projectType };
451
+ }
452
+ // Limit output length
453
+ const lines = combined.split("\n");
454
+ if (lines.length > 50) {
455
+ return { output: `${lines.slice(0, 50).join("\n")}\n... and ${lines.length - 50} more lines`, projectType };
456
+ }
457
+ return { output: combined, projectType };
458
+ } catch (e) {
459
+ if (signal?.aborted) {
460
+ throw new ToolAbortError();
461
+ }
462
+ return { output: `Failed to run ${projectType.command.join(" ")}: ${e}`, projectType };
463
+ } finally {
464
+ signal?.removeEventListener("abort", abortHandler);
465
+ }
466
+ }
467
+
468
+ /** Result from getDiagnosticsForFile */
469
+ export interface FileDiagnosticsResult {
470
+ /** Name of the LSP server used (if available) */
471
+ server?: string;
472
+ /** Formatted diagnostic messages */
473
+ messages: string[];
474
+ /** Summary string (e.g., "2 error(s), 1 warning(s)") */
475
+ summary: string;
476
+ /** Whether there are any errors (severity 1) */
477
+ errored: boolean;
478
+ /** Whether the file was formatted */
479
+ formatter?: FileFormatResult;
480
+ }
481
+
482
+ type ServerVersionMap = Map<string, number>;
483
+
484
+ interface GetDiagnosticsForFileOptions {
485
+ signal?: AbortSignal;
486
+ minVersions?: ServerVersionMap;
487
+ expectedDocumentVersions?: ServerVersionMap;
488
+ allowUnversionedLspDiagnostics?: boolean;
489
+ }
490
+
491
+ /**
492
+ * Capture current diagnostic versions for all LSP servers.
493
+ * Call this BEFORE syncing content to detect stale diagnostics later.
494
+ */
495
+ async function captureDiagnosticVersions(
496
+ cwd: string,
497
+ servers: Array<[string, ServerConfig]>,
498
+ ): Promise<ServerVersionMap> {
499
+ const versions = new Map<string, number>();
500
+ await Promise.allSettled(
501
+ servers.map(async ([serverName, serverConfig]) => {
502
+ if (serverConfig.createClient) return;
503
+ const client = await getOrCreateClient(serverConfig, cwd);
504
+ versions.set(serverName, client.diagnosticsVersion);
505
+ }),
506
+ );
507
+ return versions;
508
+ }
509
+
510
+ async function captureOpenFileVersions(
511
+ absolutePath: string,
512
+ cwd: string,
513
+ servers: Array<[string, ServerConfig]>,
514
+ ): Promise<ServerVersionMap> {
515
+ const uri = fileToUri(absolutePath);
516
+ const versions = new Map<string, number>();
517
+ await Promise.allSettled(
518
+ servers.map(async ([serverName, serverConfig]) => {
519
+ const client = await getOrCreateClient(serverConfig, cwd);
520
+ const version = client.openFiles.get(uri)?.version;
521
+ if (version !== undefined) {
522
+ versions.set(serverName, version);
523
+ }
524
+ }),
525
+ );
526
+ return versions;
527
+ }
528
+
529
+ /**
530
+ * Get diagnostics for a file using LSP or custom linter client.
531
+ *
532
+ * @param absolutePath - Absolute path to the file
533
+ * @param cwd - Working directory for LSP config resolution
534
+ * @param servers - Servers to query diagnostics for
535
+ * @param minVersions - Minimum diagnostic versions per server (to detect stale results)
536
+ * @returns Diagnostic results or undefined if no servers
537
+ */
538
+ async function getDiagnosticsForFile(
539
+ absolutePath: string,
540
+ cwd: string,
541
+ servers: Array<[string, ServerConfig]>,
542
+ options: GetDiagnosticsForFileOptions = {},
543
+ ): Promise<FileDiagnosticsResult | undefined> {
544
+ const { signal, minVersions, expectedDocumentVersions, allowUnversionedLspDiagnostics = true } = options;
545
+ if (servers.length === 0) {
546
+ return undefined;
547
+ }
548
+
549
+ const uri = fileToUri(absolutePath);
550
+ const relPath = path.relative(cwd, absolutePath);
551
+ const allDiagnostics: Diagnostic[] = [];
552
+ const serverNames: string[] = [];
553
+
554
+ // Wait for diagnostics from all servers in parallel
555
+ const results = await Promise.allSettled(
556
+ servers.map(async ([serverName, serverConfig]) => {
557
+ throwIfAborted(signal);
558
+ // Use custom linter client if configured
559
+ if (serverConfig.createClient) {
560
+ const linterClient = getLinterClient(serverName, serverConfig, cwd);
561
+ const diagnostics = await linterClient.lint(absolutePath);
562
+ return { serverName, diagnostics };
563
+ }
564
+
565
+ // Default: use LSP
566
+ const client = await getOrCreateClient(serverConfig, cwd);
567
+ throwIfAborted(signal);
568
+ // Content already synced + didSave sent, wait for fresh diagnostics
569
+ const minVersion = minVersions?.get(serverName);
570
+ const expectedDocumentVersion = expectedDocumentVersions?.get(serverName);
571
+ const diagnostics = await waitForDiagnostics(client, uri, {
572
+ timeoutMs: 3000,
573
+ signal,
574
+ minVersion,
575
+ expectedDocumentVersion,
576
+ allowUnversioned: allowUnversionedLspDiagnostics,
577
+ });
578
+ return { serverName, diagnostics };
579
+ }),
580
+ );
581
+
582
+ for (const result of results) {
583
+ if (result.status === "fulfilled") {
584
+ serverNames.push(result.value.serverName);
585
+ allDiagnostics.push(...result.value.diagnostics);
586
+ }
587
+ }
588
+
589
+ if (serverNames.length === 0) {
590
+ return undefined;
591
+ }
592
+
593
+ if (allDiagnostics.length === 0) {
594
+ return {
595
+ server: serverNames.join(", "),
596
+ messages: [],
597
+ summary: "OK",
598
+ errored: false,
599
+ };
600
+ }
601
+
602
+ // Deduplicate diagnostics by range + message (different servers might report similar issues)
603
+ const seen = new Set<string>();
604
+ const uniqueDiagnostics: Diagnostic[] = [];
605
+ for (const d of allDiagnostics) {
606
+ const key = `${d.range.start.line}:${d.range.start.character}:${d.range.end.line}:${d.range.end.character}:${d.message}`;
607
+ if (!seen.has(key)) {
608
+ seen.add(key);
609
+ uniqueDiagnostics.push(d);
610
+ }
611
+ }
612
+
613
+ sortDiagnostics(uniqueDiagnostics);
614
+ const formatted = uniqueDiagnostics.map(d => formatDiagnostic(d, relPath));
615
+ const limited = limitDiagnosticMessages(formatted);
616
+ const summary = formatDiagnosticsSummary(uniqueDiagnostics);
617
+ const hasErrors = uniqueDiagnostics.some(d => d.severity === 1);
618
+
619
+ return {
620
+ server: serverNames.join(", "),
621
+ messages: limited,
622
+ summary,
623
+ errored: hasErrors,
624
+ };
625
+ }
626
+
627
+ export enum FileFormatResult {
628
+ UNCHANGED = "unchanged",
629
+ FORMATTED = "formatted",
630
+ }
631
+
632
+ /** Default formatting options for LSP */
633
+ const DEFAULT_FORMAT_OPTIONS = {
634
+ tabSize: 3,
635
+ insertSpaces: true,
636
+ trimTrailingWhitespace: true,
637
+ insertFinalNewline: true,
638
+ trimFinalNewlines: true,
639
+ };
640
+
641
+ /**
642
+ * Format content using LSP or custom linter client.
643
+ *
644
+ * @param absolutePath - Absolute path (for URI)
645
+ * @param content - Content to format
646
+ * @param cwd - Working directory for LSP config resolution
647
+ * @param servers - Servers to try formatting with
648
+ * @returns Formatted content, or original if no formatter available
649
+ */
650
+ async function formatContent(
651
+ absolutePath: string,
652
+ content: string,
653
+ cwd: string,
654
+ servers: Array<[string, ServerConfig]>,
655
+ signal?: AbortSignal,
656
+ ): Promise<string> {
657
+ if (servers.length === 0) {
658
+ return content;
659
+ }
660
+
661
+ const uri = fileToUri(absolutePath);
662
+
663
+ for (const [serverName, serverConfig] of servers) {
664
+ try {
665
+ throwIfAborted(signal);
666
+ // Use custom linter client if configured
667
+ if (serverConfig.createClient) {
668
+ const linterClient = getLinterClient(serverName, serverConfig, cwd);
669
+ return await linterClient.format(absolutePath, content);
670
+ }
671
+
672
+ // Default: use LSP
673
+ const client = await getOrCreateClient(serverConfig, cwd);
674
+ throwIfAborted(signal);
675
+
676
+ const caps = client.serverCapabilities;
677
+ if (!caps?.documentFormattingProvider) {
678
+ continue;
679
+ }
680
+
681
+ // Request formatting (content already synced)
682
+ const edits = (await sendRequest(
683
+ client,
684
+ "textDocument/formatting",
685
+ {
686
+ textDocument: { uri },
687
+ options: DEFAULT_FORMAT_OPTIONS,
688
+ },
689
+ signal,
690
+ )) as TextEdit[] | null;
691
+
692
+ if (!edits || edits.length === 0) {
693
+ return content;
694
+ }
695
+
696
+ // Apply edits in-memory and return
697
+ return applyTextEditsToString(content, edits);
698
+ } catch {}
699
+ }
700
+
701
+ return content;
702
+ }
703
+
704
+ /** Options for creating the LSP writethrough callback */
705
+ export interface WritethroughOptions {
706
+ /** Whether to format the file using LSP after writing */
707
+ enableFormat?: boolean;
708
+ /** Whether to get LSP diagnostics after writing */
709
+ enableDiagnostics?: boolean;
710
+ /** Called when diagnostics arrive after the main timeout. */
711
+ onDeferredDiagnostics?: (diagnostics: FileDiagnosticsResult) => void;
712
+ /** Signal to cancel a pending deferred diagnostics fetch. */
713
+ deferredSignal?: AbortSignal;
714
+ }
715
+
716
+ /** Internal resolved form of {@link WritethroughOptions} that the writethrough machinery operates on. */
717
+ type ResolvedWritethroughOptions = {
718
+ enableFormat: boolean;
719
+ enableDiagnostics: boolean;
720
+ };
721
+
722
+ /** Per-file deferred LSP diagnostics wiring for {@link WritethroughCallback}. */
723
+ export type WritethroughDeferredHandle = {
724
+ onDeferredDiagnostics: (diagnostics: FileDiagnosticsResult) => void;
725
+ signal: AbortSignal;
726
+ finalize: (diagnostics: FileDiagnosticsResult | undefined) => void;
727
+ };
728
+
729
+ /** Callback type for the LSP writethrough */
730
+ export type WritethroughCallback = (
731
+ dst: string,
732
+ content: string,
733
+ signal?: AbortSignal,
734
+ file?: BunFile,
735
+ batch?: LspWritethroughBatchRequest,
736
+ getDeferred?: (dst: string) => WritethroughDeferredHandle | undefined,
737
+ ) => Promise<FileDiagnosticsResult | undefined>;
738
+
739
+ /** No-op writethrough callback */
740
+ export async function writethroughNoop(
741
+ dst: string,
742
+ content: string,
743
+ _signal?: AbortSignal,
744
+ file?: BunFile,
745
+ _batch?: LspWritethroughBatchRequest,
746
+ _getDeferred?: (dst: string) => WritethroughDeferredHandle | undefined,
747
+ ): Promise<FileDiagnosticsResult | undefined> {
748
+ if (file) {
749
+ await file.write(content);
750
+ } else {
751
+ await Bun.write(dst, content);
752
+ }
753
+ return undefined;
754
+ }
755
+
756
+ interface PendingWritethrough {
757
+ dst: string;
758
+ content: string;
759
+ file?: BunFile;
760
+ }
761
+
762
+ interface LspWritethroughBatchRequest {
763
+ id: string;
764
+ flush: boolean;
765
+ }
766
+
767
+ interface LspWritethroughBatchState {
768
+ entries: Map<string, PendingWritethrough>;
769
+ options: ResolvedWritethroughOptions;
770
+ }
771
+
772
+ const writethroughBatches = new Map<string, LspWritethroughBatchState>();
773
+
774
+ function getOrCreateWritethroughBatch(id: string, options: ResolvedWritethroughOptions): LspWritethroughBatchState {
775
+ const existing = writethroughBatches.get(id);
776
+ if (existing) {
777
+ existing.options.enableFormat ||= options.enableFormat;
778
+ existing.options.enableDiagnostics ||= options.enableDiagnostics;
779
+ return existing;
780
+ }
781
+ const batch: LspWritethroughBatchState = {
782
+ entries: new Map<string, PendingWritethrough>(),
783
+ options: { ...options },
784
+ };
785
+ writethroughBatches.set(id, batch);
786
+ return batch;
787
+ }
788
+
789
+ export async function flushLspWritethroughBatch(
790
+ id: string,
791
+ cwd: string,
792
+ signal?: AbortSignal,
793
+ ): Promise<FileDiagnosticsResult | undefined> {
794
+ const state = writethroughBatches.get(id);
795
+ if (!state) {
796
+ return undefined;
797
+ }
798
+ writethroughBatches.delete(id);
799
+ return flushWritethroughBatch(Array.from(state.entries.values()), cwd, state.options, signal);
800
+ }
801
+
802
+ function summarizeDiagnosticMessages(messages: string[]): { summary: string; errored: boolean } {
803
+ const counts = { error: 0, warning: 0, info: 0, hint: 0 };
804
+ for (const message of messages) {
805
+ const match = message.match(/\[(error|warning|info|hint)\]/i);
806
+ if (!match) continue;
807
+ const key = match[1].toLowerCase() as keyof typeof counts;
808
+ counts[key] += 1;
809
+ }
810
+
811
+ const parts: string[] = [];
812
+ if (counts.error > 0) parts.push(`${counts.error} error(s)`);
813
+ if (counts.warning > 0) parts.push(`${counts.warning} warning(s)`);
814
+ if (counts.info > 0) parts.push(`${counts.info} info(s)`);
815
+ if (counts.hint > 0) parts.push(`${counts.hint} hint(s)`);
816
+
817
+ return {
818
+ summary: parts.length > 0 ? parts.join(", ") : "no issues",
819
+ errored: counts.error > 0,
820
+ };
821
+ }
822
+
823
+ function mergeDiagnostics(
824
+ results: Array<FileDiagnosticsResult | undefined>,
825
+ options: ResolvedWritethroughOptions,
826
+ ): FileDiagnosticsResult | undefined {
827
+ const messages: string[] = [];
828
+ const servers = new Set<string>();
829
+ let hasResults = false;
830
+ let hasFormatter = false;
831
+ let formatted = false;
832
+
833
+ for (const result of results) {
834
+ if (!result) continue;
835
+ hasResults = true;
836
+ if (result.server) {
837
+ for (const server of result.server.split(",")) {
838
+ const trimmed = server.trim();
839
+ if (trimmed) {
840
+ servers.add(trimmed);
841
+ }
842
+ }
843
+ }
844
+ if (result.messages.length > 0) {
845
+ messages.push(...result.messages);
846
+ }
847
+ if (result.formatter !== undefined) {
848
+ hasFormatter = true;
849
+ if (result.formatter === FileFormatResult.FORMATTED) {
850
+ formatted = true;
851
+ }
852
+ }
853
+ }
854
+
855
+ if (!hasResults && !hasFormatter) {
856
+ return undefined;
857
+ }
858
+
859
+ let summary = options.enableDiagnostics ? "no issues" : "OK";
860
+ let errored = false;
861
+ let limitedMessages = messages;
862
+ if (messages.length > 0) {
863
+ const summaryInfo = summarizeDiagnosticMessages(messages);
864
+ summary = summaryInfo.summary;
865
+ errored = summaryInfo.errored;
866
+ limitedMessages = limitDiagnosticMessages(messages);
867
+ }
868
+ const formatter = hasFormatter ? (formatted ? FileFormatResult.FORMATTED : FileFormatResult.UNCHANGED) : undefined;
869
+
870
+ return {
871
+ server: servers.size > 0 ? Array.from(servers).join(", ") : undefined,
872
+ messages: limitedMessages,
873
+ summary,
874
+ errored,
875
+ formatter,
876
+ };
877
+ }
878
+
879
+ async function scheduleDeferredDiagnosticsFetch(args: {
880
+ dst: string;
881
+ cwd: string;
882
+ servers: Array<[string, ServerConfig]>;
883
+ minVersions: ServerVersionMap | undefined;
884
+ expectedDocumentVersions: ServerVersionMap | undefined;
885
+ signal: AbortSignal;
886
+ callback: (diagnostics: FileDiagnosticsResult) => void;
887
+ }): Promise<void> {
888
+ try {
889
+ const deferredTimeout = AbortSignal.timeout(25_000);
890
+ const combined = AbortSignal.any([args.signal, deferredTimeout]);
891
+ const diagnostics = await getDiagnosticsForFile(args.dst, args.cwd, args.servers, {
892
+ signal: combined,
893
+ minVersions: args.minVersions,
894
+ expectedDocumentVersions: args.expectedDocumentVersions,
895
+ });
896
+ if (args.signal.aborted || diagnostics === undefined) return;
897
+ args.callback(diagnostics);
898
+ } catch {
899
+ // Cancelled or LSP gave up; silently discard.
900
+ }
901
+ }
902
+
903
+ async function runLspWritethrough(
904
+ dst: string,
905
+ content: string,
906
+ cwd: string,
907
+ options: ResolvedWritethroughOptions,
908
+ signal?: AbortSignal,
909
+ file?: BunFile,
910
+ deferred?: {
911
+ onDeferredDiagnostics: (diagnostics: FileDiagnosticsResult) => void;
912
+ signal: AbortSignal;
913
+ },
914
+ ): Promise<FileDiagnosticsResult | undefined> {
915
+ const { enableFormat, enableDiagnostics } = options;
916
+ const config = getConfig(cwd);
917
+ const servers = getServersForFile(config, dst);
918
+ if (servers.length === 0) {
919
+ return writethroughNoop(dst, content, signal, file);
920
+ }
921
+ const { lspServers, customLinterServers } = splitServers(servers);
922
+
923
+ let finalContent = content;
924
+ const writeContent = async (value: string) => (file ? file.write(value) : Bun.write(dst, value));
925
+ const getWritePromise = once(() => writeContent(finalContent));
926
+ const useCustomFormatter = enableFormat && customLinterServers.length > 0;
927
+
928
+ // Capture diagnostic versions BEFORE syncing to detect stale diagnostics
929
+ const minVersions = enableDiagnostics ? await captureDiagnosticVersions(cwd, servers) : undefined;
930
+ let expectedDocumentVersions: ServerVersionMap | undefined;
931
+
932
+ let formatter: FileFormatResult | undefined;
933
+ let diagnostics: FileDiagnosticsResult | undefined;
934
+ let timedOut = false;
935
+ try {
936
+ const timeoutSignal = AbortSignal.timeout(5_000);
937
+ timeoutSignal.addEventListener(
938
+ "abort",
939
+ () => {
940
+ timedOut = true;
941
+ },
942
+ { once: true },
943
+ );
944
+ const operationSignal = signal ? AbortSignal.any([signal, timeoutSignal]) : timeoutSignal;
945
+ await untilAborted(operationSignal, async () => {
946
+ if (useCustomFormatter) {
947
+ // Custom linters (e.g. Biome CLI) require on-disk input.
948
+ await writeContent(content);
949
+ finalContent = await formatContent(dst, content, cwd, customLinterServers, operationSignal);
950
+ formatter = finalContent !== content ? FileFormatResult.FORMATTED : FileFormatResult.UNCHANGED;
951
+ await writeContent(finalContent);
952
+ await syncFileContent(dst, finalContent, cwd, lspServers, operationSignal);
953
+ } else {
954
+ // 1. Sync original content to LSP servers
955
+ await syncFileContent(dst, content, cwd, lspServers, operationSignal);
956
+
957
+ // 2. Format in-memory via LSP
958
+ if (enableFormat) {
959
+ finalContent = await formatContent(dst, content, cwd, lspServers, operationSignal);
960
+ formatter = finalContent !== content ? FileFormatResult.FORMATTED : FileFormatResult.UNCHANGED;
961
+ }
962
+
963
+ // 3. If formatted, sync formatted content to LSP servers
964
+ if (finalContent !== content) {
965
+ await syncFileContent(dst, finalContent, cwd, lspServers, operationSignal);
966
+ }
967
+
968
+ // 4. Write to disk
969
+ await getWritePromise();
970
+ }
971
+
972
+ if (enableDiagnostics) {
973
+ expectedDocumentVersions = await captureOpenFileVersions(dst, cwd, lspServers);
974
+ }
975
+
976
+ // 5. Notify saved to LSP servers
977
+ await notifyFileSaved(dst, cwd, lspServers, operationSignal);
978
+
979
+ // 6. Get diagnostics from all servers (wait for fresh results)
980
+ if (enableDiagnostics) {
981
+ diagnostics = await getDiagnosticsForFile(dst, cwd, servers, {
982
+ signal: operationSignal,
983
+ minVersions,
984
+ expectedDocumentVersions,
985
+ allowUnversionedLspDiagnostics: false,
986
+ });
987
+ }
988
+ });
989
+ } catch {
990
+ if (timedOut) {
991
+ formatter = undefined;
992
+ diagnostics = undefined;
993
+ // Schedule background diagnostic fetch if caller wants deferred results
994
+ if (deferred && !deferred.signal.aborted && enableDiagnostics) {
995
+ void scheduleDeferredDiagnosticsFetch({
996
+ dst,
997
+ cwd,
998
+ servers,
999
+ minVersions,
1000
+ expectedDocumentVersions,
1001
+ signal: deferred.signal,
1002
+ callback: deferred.onDeferredDiagnostics,
1003
+ });
1004
+ }
1005
+ }
1006
+ await getWritePromise();
1007
+ }
1008
+
1009
+ if (formatter !== undefined) {
1010
+ diagnostics ??= {
1011
+ server: servers.map(([name]) => name).join(", "),
1012
+ messages: [],
1013
+ summary: "OK",
1014
+ errored: false,
1015
+ };
1016
+ diagnostics.formatter = formatter;
1017
+ }
1018
+
1019
+ return diagnostics;
1020
+ }
1021
+
1022
+ async function flushWritethroughBatch(
1023
+ batch: PendingWritethrough[],
1024
+ cwd: string,
1025
+ options: ResolvedWritethroughOptions,
1026
+ signal?: AbortSignal,
1027
+ getDeferred?: (dst: string) => WritethroughDeferredHandle | undefined,
1028
+ ): Promise<FileDiagnosticsResult | undefined> {
1029
+ if (batch.length === 0) {
1030
+ return undefined;
1031
+ }
1032
+ const results: Array<FileDiagnosticsResult | undefined> = [];
1033
+ for (const entry of batch) {
1034
+ const bundle = getDeferred?.(entry.dst);
1035
+ const deferredInner =
1036
+ bundle &&
1037
+ ({
1038
+ onDeferredDiagnostics: bundle.onDeferredDiagnostics,
1039
+ signal: bundle.signal,
1040
+ } as const);
1041
+ const diag = await runLspWritethrough(entry.dst, entry.content, cwd, options, signal, entry.file, deferredInner);
1042
+ bundle?.finalize(diag);
1043
+ results.push(diag);
1044
+ }
1045
+ return mergeDiagnostics(results, options);
1046
+ }
1047
+
1048
+ /** Create a writethrough callback for LSP aware write operations */
1049
+ export function createLspWritethrough(cwd: string, options?: WritethroughOptions): WritethroughCallback {
1050
+ const resolvedOptions: ResolvedWritethroughOptions = {
1051
+ enableFormat: options?.enableFormat ?? false,
1052
+ enableDiagnostics: options?.enableDiagnostics ?? false,
1053
+ };
1054
+ if (!resolvedOptions.enableFormat && !resolvedOptions.enableDiagnostics) {
1055
+ return writethroughNoop;
1056
+ }
1057
+ return async (
1058
+ dst: string,
1059
+ content: string,
1060
+ signal?: AbortSignal,
1061
+ file?: BunFile,
1062
+ batch?: LspWritethroughBatchRequest,
1063
+ getDeferred?: (dst: string) => WritethroughDeferredHandle | undefined,
1064
+ ) => {
1065
+ if (!batch) {
1066
+ const bundle = getDeferred?.(dst);
1067
+ const deferredInner =
1068
+ bundle &&
1069
+ ({
1070
+ onDeferredDiagnostics: bundle.onDeferredDiagnostics,
1071
+ signal: bundle.signal,
1072
+ } as const);
1073
+ const diagnostics = await runLspWritethrough(dst, content, cwd, resolvedOptions, signal, file, deferredInner);
1074
+ bundle?.finalize(diagnostics);
1075
+ return diagnostics;
1076
+ }
1077
+
1078
+ const state = getOrCreateWritethroughBatch(batch.id, resolvedOptions);
1079
+ state.entries.set(dst, { dst, content, file });
1080
+
1081
+ if (!batch.flush) {
1082
+ await writethroughNoop(dst, content, signal, file);
1083
+ return undefined;
1084
+ }
1085
+
1086
+ writethroughBatches.delete(batch.id);
1087
+ return flushWritethroughBatch(Array.from(state.entries.values()), cwd, state.options, signal, getDeferred);
1088
+ };
1089
+ }
1090
+
1091
+ /**
1092
+ * LSP tool for language server protocol operations.
1093
+ */
1094
+ export class LspTool implements AgentTool<typeof lspSchema, LspToolDetails, Theme> {
1095
+ readonly name = "lsp";
1096
+ readonly label = "LSP";
1097
+ readonly description: string;
1098
+ readonly parameters = lspSchema;
1099
+ readonly strict = true;
1100
+ readonly renderCall = renderCall;
1101
+ readonly renderResult = renderResult;
1102
+ readonly mergeCallAndResult = true;
1103
+ readonly inline = true;
1104
+
1105
+ constructor(private readonly session: ToolSession) {
1106
+ this.description = prompt.render(lspDescription);
1107
+ }
1108
+
1109
+ static createIf(session: ToolSession): LspTool | null {
1110
+ return session.enableLsp === false ? null : new LspTool(session);
1111
+ }
1112
+
1113
+ async execute(
1114
+ _toolCallId: string,
1115
+ params: LspParams,
1116
+ signal?: AbortSignal,
1117
+ _onUpdate?: AgentToolUpdateCallback<LspToolDetails>,
1118
+ _context?: AgentToolContext,
1119
+ ): Promise<AgentToolResult<LspToolDetails>> {
1120
+ const { action, file, line, symbol, occurrence, query, new_name, apply, timeout } = params;
1121
+ const timeoutSec = clampTimeout("lsp", timeout);
1122
+ const timeoutSignal = AbortSignal.timeout(timeoutSec * 1000);
1123
+ signal = signal ? AbortSignal.any([signal, timeoutSignal]) : timeoutSignal;
1124
+ throwIfAborted(signal);
1125
+
1126
+ const config = getConfig(this.session.cwd);
1127
+
1128
+ // Status action doesn't need a file
1129
+ if (action === "status") {
1130
+ const servers = Object.keys(config.servers);
1131
+ const lspmuxState = await detectLspmux();
1132
+ const lspmuxStatus = lspmuxState.available
1133
+ ? lspmuxState.running
1134
+ ? "lspmux: active (multiplexing enabled)"
1135
+ : "lspmux: installed but server not running"
1136
+ : "";
1137
+
1138
+ const serverStatus =
1139
+ servers.length > 0
1140
+ ? `Active language servers: ${servers.join(", ")}`
1141
+ : "No language servers configured for this project";
1142
+
1143
+ const output = lspmuxStatus ? `${serverStatus}\n${lspmuxStatus}` : serverStatus;
1144
+ return {
1145
+ content: [{ type: "text", text: output }],
1146
+ details: { action, success: true, request: params },
1147
+ };
1148
+ }
1149
+
1150
+ // Diagnostics can be batch or single-file - queries all applicable servers
1151
+ if (action === "diagnostics") {
1152
+ if (file === "*") {
1153
+ // `*` => run workspace diagnostics across all configured servers
1154
+ const result = await runWorkspaceDiagnostics(this.session.cwd, signal);
1155
+ return {
1156
+ content: [
1157
+ {
1158
+ type: "text",
1159
+ text: `Workspace diagnostics (${result.projectType.description}):\n${result.output}`,
1160
+ },
1161
+ ],
1162
+ details: { action, success: true, request: params },
1163
+ };
1164
+ }
1165
+
1166
+ if (!file) {
1167
+ return {
1168
+ content: [
1169
+ {
1170
+ type: "text",
1171
+ text: "Error: file parameter required. Use `*` for workspace-wide diagnostics or a path/glob for specific files.",
1172
+ },
1173
+ ],
1174
+ details: { action, success: false, request: params },
1175
+ };
1176
+ }
1177
+
1178
+ let targets: string[];
1179
+ let truncatedGlobTargets = false;
1180
+ if (hasGlobPattern(file)) {
1181
+ const globMatches = await collectGlobMatches(file, this.session.cwd, MAX_GLOB_DIAGNOSTIC_TARGETS);
1182
+ targets = globMatches.matches;
1183
+ truncatedGlobTargets = globMatches.truncated;
1184
+ } else {
1185
+ targets = [file];
1186
+ }
1187
+
1188
+ if (targets.length === 0) {
1189
+ return {
1190
+ content: [{ type: "text", text: `No files matched pattern: ${file}` }],
1191
+ details: { action, success: true, request: params },
1192
+ };
1193
+ }
1194
+
1195
+ const detailed = targets.length > 1 || truncatedGlobTargets;
1196
+ const diagnosticsWaitTimeoutMs = detailed
1197
+ ? Math.min(BATCH_DIAGNOSTICS_WAIT_TIMEOUT_MS, timeoutSec * 1000)
1198
+ : Math.min(SINGLE_DIAGNOSTICS_WAIT_TIMEOUT_MS, timeoutSec * 1000);
1199
+ const results: string[] = [];
1200
+ const allServerNames = new Set<string>();
1201
+ if (truncatedGlobTargets) {
1202
+ results.push(
1203
+ `${theme.status.warning} Pattern matched more than ${MAX_GLOB_DIAGNOSTIC_TARGETS} files; showing first ${MAX_GLOB_DIAGNOSTIC_TARGETS}. Narrow the glob or use workspace diagnostics.`,
1204
+ );
1205
+ }
1206
+
1207
+ for (const target of targets) {
1208
+ throwIfAborted(signal);
1209
+ const resolved = resolveToCwd(target, this.session.cwd);
1210
+ const servers = getServersForFile(config, resolved);
1211
+ if (servers.length === 0) {
1212
+ results.push(`${theme.status.error} ${target}: No language server found`);
1213
+ continue;
1214
+ }
1215
+
1216
+ const uri = fileToUri(resolved);
1217
+ const relPath = path.relative(this.session.cwd, resolved);
1218
+ const allDiagnostics: Diagnostic[] = [];
1219
+
1220
+ // Query all applicable servers for this file
1221
+ for (const [serverName, serverConfig] of servers) {
1222
+ allServerNames.add(serverName);
1223
+ try {
1224
+ throwIfAborted(signal);
1225
+ if (serverConfig.createClient) {
1226
+ const linterClient = getLinterClient(serverName, serverConfig, this.session.cwd);
1227
+ const diagnostics = await linterClient.lint(resolved);
1228
+ allDiagnostics.push(...diagnostics);
1229
+ continue;
1230
+ }
1231
+ const client = await getOrCreateClient(serverConfig, this.session.cwd);
1232
+ const minVersion = client.diagnosticsVersion;
1233
+ await refreshFile(client, resolved, signal);
1234
+ const expectedDocumentVersion = client.openFiles.get(uri)?.version;
1235
+ const diagnostics = await waitForDiagnostics(client, uri, {
1236
+ timeoutMs: diagnosticsWaitTimeoutMs,
1237
+ signal,
1238
+ minVersion,
1239
+ expectedDocumentVersion,
1240
+ });
1241
+ allDiagnostics.push(...diagnostics);
1242
+ } catch (err) {
1243
+ if (err instanceof ToolAbortError || signal?.aborted) {
1244
+ throw err;
1245
+ }
1246
+ // Server failed, continue with others
1247
+ }
1248
+ }
1249
+
1250
+ // Deduplicate diagnostics
1251
+ const seen = new Set<string>();
1252
+ const uniqueDiagnostics: Diagnostic[] = [];
1253
+ for (const d of allDiagnostics) {
1254
+ const key = `${d.range.start.line}:${d.range.start.character}:${d.range.end.line}:${d.range.end.character}:${d.message}`;
1255
+ if (!seen.has(key)) {
1256
+ seen.add(key);
1257
+ uniqueDiagnostics.push(d);
1258
+ }
1259
+ }
1260
+
1261
+ sortDiagnostics(uniqueDiagnostics);
1262
+
1263
+ if (!detailed && targets.length === 1) {
1264
+ if (uniqueDiagnostics.length === 0) {
1265
+ return {
1266
+ content: [{ type: "text", text: "No diagnostics" }],
1267
+ details: { action, serverName: Array.from(allServerNames).join(", "), success: true },
1268
+ };
1269
+ }
1270
+
1271
+ const summary = formatDiagnosticsSummary(uniqueDiagnostics);
1272
+ const formatted = uniqueDiagnostics.map(d => formatDiagnostic(d, relPath));
1273
+ const output = `${summary}:\n${formatGroupedDiagnosticMessages(formatted)}`;
1274
+ return {
1275
+ content: [{ type: "text", text: output }],
1276
+ details: { action, serverName: Array.from(allServerNames).join(", "), success: true },
1277
+ };
1278
+ }
1279
+
1280
+ if (uniqueDiagnostics.length === 0) {
1281
+ results.push(`${theme.status.success} ${relPath}: no issues`);
1282
+ } else {
1283
+ const summary = formatDiagnosticsSummary(uniqueDiagnostics);
1284
+ results.push(`${theme.status.error} ${relPath}: ${summary}`);
1285
+ const formatted = uniqueDiagnostics.map(d => formatDiagnostic(d, relPath));
1286
+ results.push(formatGroupedDiagnosticMessages(formatted));
1287
+ }
1288
+ }
1289
+
1290
+ return {
1291
+ content: [{ type: "text", text: results.join("\n") }],
1292
+ details: { action, serverName: Array.from(allServerNames).join(", "), success: true },
1293
+ };
1294
+ }
1295
+
1296
+ // `*` means workspace scope for symbols/reload; other actions need a concrete file.
1297
+ const isWorkspace = file === "*";
1298
+ const requiresFile = !file && action !== "reload";
1299
+
1300
+ if (requiresFile) {
1301
+ return {
1302
+ content: [
1303
+ {
1304
+ type: "text",
1305
+ text: "Error: file parameter required. Use `*` for workspace scope where supported.",
1306
+ },
1307
+ ],
1308
+ details: { action, success: false },
1309
+ };
1310
+ }
1311
+
1312
+ const resolvedFile = file && !isWorkspace ? resolveToCwd(file, this.session.cwd) : null;
1313
+ if (action === "symbols" && (isWorkspace || !resolvedFile)) {
1314
+ const normalizedQuery = query?.trim();
1315
+ if (!normalizedQuery) {
1316
+ return {
1317
+ content: [{ type: "text", text: "Error: query parameter required for workspace symbol search" }],
1318
+ details: { action, success: false, request: params },
1319
+ };
1320
+ }
1321
+ const servers = getLspServers(config);
1322
+ if (servers.length === 0) {
1323
+ return {
1324
+ content: [{ type: "text", text: "No language server found for this action" }],
1325
+ details: { action, success: false, request: params },
1326
+ };
1327
+ }
1328
+ const aggregatedSymbols: SymbolInformation[] = [];
1329
+ const respondingServers = new Set<string>();
1330
+ for (const [workspaceServerName, workspaceServerConfig] of servers) {
1331
+ throwIfAborted(signal);
1332
+ try {
1333
+ const workspaceClient = await getOrCreateClient(workspaceServerConfig, this.session.cwd);
1334
+ const workspaceResult = (await sendRequest(
1335
+ workspaceClient,
1336
+ "workspace/symbol",
1337
+ { query: normalizedQuery },
1338
+ signal,
1339
+ )) as SymbolInformation[] | null;
1340
+ if (!workspaceResult || workspaceResult.length === 0) {
1341
+ continue;
1342
+ }
1343
+ respondingServers.add(workspaceServerName);
1344
+ aggregatedSymbols.push(...filterWorkspaceSymbols(workspaceResult, normalizedQuery));
1345
+ } catch (err) {
1346
+ if (err instanceof ToolAbortError || signal?.aborted) {
1347
+ throw err;
1348
+ }
1349
+ }
1350
+ }
1351
+ const dedupedSymbols = dedupeWorkspaceSymbols(aggregatedSymbols);
1352
+ if (dedupedSymbols.length === 0) {
1353
+ return {
1354
+ content: [{ type: "text", text: `No symbols matching "${normalizedQuery}"` }],
1355
+ details: {
1356
+ action,
1357
+ serverName: Array.from(respondingServers).join(", "),
1358
+ success: true,
1359
+ request: params,
1360
+ },
1361
+ };
1362
+ }
1363
+ const limitedSymbols = dedupedSymbols.slice(0, WORKSPACE_SYMBOL_LIMIT);
1364
+ const lines = limitedSymbols.map(s => formatSymbolInformation(s, this.session.cwd));
1365
+ const truncationLine =
1366
+ dedupedSymbols.length > WORKSPACE_SYMBOL_LIMIT
1367
+ ? `\n... ${dedupedSymbols.length - WORKSPACE_SYMBOL_LIMIT} additional symbol(s) omitted`
1368
+ : "";
1369
+ return {
1370
+ content: [
1371
+ {
1372
+ type: "text",
1373
+ text: `Found ${dedupedSymbols.length} symbol(s) matching "${normalizedQuery}":\n${lines.map(l => ` ${l}`).join("\n")}${truncationLine}`,
1374
+ },
1375
+ ],
1376
+ details: {
1377
+ action,
1378
+ serverName: Array.from(respondingServers).join(", "),
1379
+ success: true,
1380
+ request: params,
1381
+ },
1382
+ };
1383
+ }
1384
+
1385
+ if (action === "reload" && (isWorkspace || !resolvedFile)) {
1386
+ const servers = getLspServers(config);
1387
+ if (servers.length === 0) {
1388
+ return {
1389
+ content: [{ type: "text", text: "No language server found for this action" }],
1390
+ details: { action, success: false, request: params },
1391
+ };
1392
+ }
1393
+ const outputs: string[] = [];
1394
+ for (const [workspaceServerName, workspaceServerConfig] of servers) {
1395
+ throwIfAborted(signal);
1396
+ try {
1397
+ const workspaceClient = await getOrCreateClient(workspaceServerConfig, this.session.cwd);
1398
+ outputs.push(await reloadServer(workspaceClient, workspaceServerName, signal));
1399
+ } catch (err) {
1400
+ if (err instanceof ToolAbortError || signal?.aborted) {
1401
+ throw err;
1402
+ }
1403
+ const errorMessage = err instanceof Error ? err.message : String(err);
1404
+ outputs.push(`Failed to reload ${workspaceServerName}: ${errorMessage}`);
1405
+ }
1406
+ }
1407
+ return {
1408
+ content: [{ type: "text", text: outputs.join("\n") }],
1409
+ details: { action, serverName: servers.map(([name]) => name).join(", "), success: true, request: params },
1410
+ };
1411
+ }
1412
+
1413
+ const serverInfo = resolvedFile ? getLspServerForFile(config, resolvedFile) : null;
1414
+ if (!serverInfo) {
1415
+ return {
1416
+ content: [{ type: "text", text: "No language server found for this action" }],
1417
+ details: { action, success: false },
1418
+ };
1419
+ }
1420
+
1421
+ const [serverName, serverConfig] = serverInfo;
1422
+
1423
+ try {
1424
+ const client = await getOrCreateClient(serverConfig, this.session.cwd);
1425
+ const targetFile = resolvedFile;
1426
+
1427
+ if (targetFile) {
1428
+ await ensureFileOpen(client, targetFile, signal);
1429
+ }
1430
+
1431
+ const uri = targetFile ? fileToUri(targetFile) : "";
1432
+ const resolvedLine = line ?? 1;
1433
+ const resolvedCharacter = targetFile
1434
+ ? await resolveSymbolColumn(targetFile, resolvedLine, symbol, occurrence)
1435
+ : 0;
1436
+ const position = { line: resolvedLine - 1, character: resolvedCharacter };
1437
+
1438
+ let output: string;
1439
+
1440
+ switch (action) {
1441
+ // =====================================================================
1442
+ // Standard LSP Operations
1443
+ // =====================================================================
1444
+
1445
+ case "definition": {
1446
+ const result = (await sendRequest(
1447
+ client,
1448
+ "textDocument/definition",
1449
+ {
1450
+ textDocument: { uri },
1451
+ position,
1452
+ },
1453
+ signal,
1454
+ )) as Location | Location[] | LocationLink | LocationLink[] | null;
1455
+
1456
+ const locations = normalizeLocationResult(result);
1457
+
1458
+ if (locations.length === 0) {
1459
+ output = "No definition found";
1460
+ } else {
1461
+ const lines = await Promise.all(
1462
+ locations.map(location => formatLocationWithContext(location, this.session.cwd)),
1463
+ );
1464
+ output = `Found ${locations.length} definition(s):\n${lines.join("\n")}`;
1465
+ }
1466
+ break;
1467
+ }
1468
+
1469
+ case "type_definition": {
1470
+ const result = (await sendRequest(
1471
+ client,
1472
+ "textDocument/typeDefinition",
1473
+ {
1474
+ textDocument: { uri },
1475
+ position,
1476
+ },
1477
+ signal,
1478
+ )) as Location | Location[] | LocationLink | LocationLink[] | null;
1479
+
1480
+ const locations = normalizeLocationResult(result);
1481
+
1482
+ if (locations.length === 0) {
1483
+ output = "No type definition found";
1484
+ } else {
1485
+ const lines = await Promise.all(
1486
+ locations.map(location => formatLocationWithContext(location, this.session.cwd)),
1487
+ );
1488
+ output = `Found ${locations.length} type definition(s):\n${lines.join("\n")}`;
1489
+ }
1490
+ break;
1491
+ }
1492
+
1493
+ case "implementation": {
1494
+ const result = (await sendRequest(
1495
+ client,
1496
+ "textDocument/implementation",
1497
+ {
1498
+ textDocument: { uri },
1499
+ position,
1500
+ },
1501
+ signal,
1502
+ )) as Location | Location[] | LocationLink | LocationLink[] | null;
1503
+
1504
+ const locations = normalizeLocationResult(result);
1505
+
1506
+ if (locations.length === 0) {
1507
+ output = "No implementation found";
1508
+ } else {
1509
+ const lines = await Promise.all(
1510
+ locations.map(location => formatLocationWithContext(location, this.session.cwd)),
1511
+ );
1512
+ output = `Found ${locations.length} implementation(s):\n${lines.join("\n")}`;
1513
+ }
1514
+ break;
1515
+ }
1516
+ case "references": {
1517
+ const result = (await sendRequest(
1518
+ client,
1519
+ "textDocument/references",
1520
+ {
1521
+ textDocument: { uri },
1522
+ position,
1523
+ context: { includeDeclaration: true },
1524
+ },
1525
+ signal,
1526
+ )) as Location[] | null;
1527
+
1528
+ if (!result || result.length === 0) {
1529
+ output = "No references found";
1530
+ } else {
1531
+ const contextualReferences = result.slice(0, REFERENCE_CONTEXT_LIMIT);
1532
+ const plainReferences = result.slice(REFERENCE_CONTEXT_LIMIT);
1533
+ const contextualLines = await Promise.all(
1534
+ contextualReferences.map(location => formatLocationWithContext(location, this.session.cwd)),
1535
+ );
1536
+ const plainLines = plainReferences.map(location => ` ${formatLocation(location, this.session.cwd)}`);
1537
+ const lines = plainLines.length
1538
+ ? [
1539
+ ...contextualLines,
1540
+ ` ... ${plainLines.length} additional reference(s) shown without context`,
1541
+ ...plainLines,
1542
+ ]
1543
+ : contextualLines;
1544
+ output = `Found ${result.length} reference(s):\n${lines.join("\n")}`;
1545
+ }
1546
+ break;
1547
+ }
1548
+
1549
+ case "hover": {
1550
+ const result = (await sendRequest(
1551
+ client,
1552
+ "textDocument/hover",
1553
+ {
1554
+ textDocument: { uri },
1555
+ position,
1556
+ },
1557
+ signal,
1558
+ )) as Hover | null;
1559
+
1560
+ if (!result?.contents) {
1561
+ output = "No hover information";
1562
+ } else {
1563
+ output = extractHoverText(result.contents);
1564
+ }
1565
+ break;
1566
+ }
1567
+
1568
+ case "code_actions": {
1569
+ const diagnostics = client.diagnostics.get(uri)?.diagnostics ?? [];
1570
+ const context: CodeActionContext = {
1571
+ diagnostics,
1572
+ only: !apply && query ? [query] : undefined,
1573
+ triggerKind: 1,
1574
+ };
1575
+
1576
+ const result = (await sendRequest(
1577
+ client,
1578
+ "textDocument/codeAction",
1579
+ {
1580
+ textDocument: { uri },
1581
+ range: { start: position, end: position },
1582
+ context,
1583
+ },
1584
+ signal,
1585
+ )) as (CodeAction | Command)[] | null;
1586
+
1587
+ if (!result || result.length === 0) {
1588
+ output = "No code actions available";
1589
+ break;
1590
+ }
1591
+
1592
+ if (apply === true && query) {
1593
+ const normalizedQuery = query.trim();
1594
+ if (normalizedQuery.length === 0) {
1595
+ output = "Error: query parameter required when apply=true for code_actions";
1596
+ break;
1597
+ }
1598
+ const parsedIndex = /^\d+$/.test(normalizedQuery) ? Number.parseInt(normalizedQuery, 10) : null;
1599
+ const selectedAction = result.find(
1600
+ (actionItem, index) =>
1601
+ (parsedIndex !== null && index === parsedIndex) ||
1602
+ actionItem.title.toLowerCase().includes(normalizedQuery.toLowerCase()),
1603
+ );
1604
+
1605
+ if (!selectedAction) {
1606
+ const actionLines = result.map((actionItem, index) => ` ${formatCodeAction(actionItem, index)}`);
1607
+ output = `No code action matches "${normalizedQuery}". Available actions:\n${actionLines.join("\n")}`;
1608
+ break;
1609
+ }
1610
+
1611
+ const appliedAction = await applyCodeAction(selectedAction, {
1612
+ resolveCodeAction: async actionItem =>
1613
+ (await sendRequest(client, "codeAction/resolve", actionItem, signal)) as CodeAction,
1614
+ applyWorkspaceEdit: async edit => applyWorkspaceEdit(edit, this.session.cwd),
1615
+ executeCommand: async commandItem => {
1616
+ await sendRequest(
1617
+ client,
1618
+ "workspace/executeCommand",
1619
+ {
1620
+ command: commandItem.command,
1621
+ arguments: commandItem.arguments ?? [],
1622
+ },
1623
+ signal,
1624
+ );
1625
+ },
1626
+ });
1627
+
1628
+ if (!appliedAction) {
1629
+ output = `Action "${selectedAction.title}" has no workspace edit or command to apply`;
1630
+ break;
1631
+ }
1632
+
1633
+ const summaryLines: string[] = [];
1634
+ if (appliedAction.edits.length > 0) {
1635
+ summaryLines.push(" Workspace edit:");
1636
+ summaryLines.push(...appliedAction.edits.map(item => ` ${item}`));
1637
+ }
1638
+ if (appliedAction.executedCommands.length > 0) {
1639
+ summaryLines.push(" Executed command(s):");
1640
+ summaryLines.push(...appliedAction.executedCommands.map(commandName => ` ${commandName}`));
1641
+ }
1642
+
1643
+ output = `Applied "${appliedAction.title}":\n${summaryLines.join("\n")}`;
1644
+ break;
1645
+ }
1646
+
1647
+ const actionLines = result.map((actionItem, index) => ` ${formatCodeAction(actionItem, index)}`);
1648
+ output = `${result.length} code action(s):\n${actionLines.join("\n")}`;
1649
+ break;
1650
+ }
1651
+ case "symbols": {
1652
+ if (!targetFile) {
1653
+ output = "Error: file parameter required for document symbols";
1654
+ break;
1655
+ }
1656
+ // File-based document symbols
1657
+ const result = (await sendRequest(
1658
+ client,
1659
+ "textDocument/documentSymbol",
1660
+ {
1661
+ textDocument: { uri },
1662
+ },
1663
+ signal,
1664
+ )) as (DocumentSymbol | SymbolInformation)[] | null;
1665
+
1666
+ if (!result || result.length === 0) {
1667
+ output = "No symbols found";
1668
+ } else {
1669
+ const relPath = path.relative(this.session.cwd, targetFile);
1670
+ if ("selectionRange" in result[0]) {
1671
+ const lines = (result as DocumentSymbol[]).flatMap(s => formatDocumentSymbol(s));
1672
+ output = `Symbols in ${relPath}:\n${lines.join("\n")}`;
1673
+ } else {
1674
+ const lines = (result as SymbolInformation[]).map(s => {
1675
+ const line = s.location.range.start.line + 1;
1676
+ const icon = symbolKindToIcon(s.kind);
1677
+ return `${icon} ${s.name} @ line ${line}`;
1678
+ });
1679
+ output = `Symbols in ${relPath}:\n${lines.join("\n")}`;
1680
+ }
1681
+ }
1682
+ break;
1683
+ }
1684
+
1685
+ case "rename": {
1686
+ if (!new_name) {
1687
+ return {
1688
+ content: [{ type: "text", text: "Error: new_name parameter required for rename" }],
1689
+ details: { action, serverName, success: false },
1690
+ };
1691
+ }
1692
+
1693
+ const result = (await sendRequest(
1694
+ client,
1695
+ "textDocument/rename",
1696
+ {
1697
+ textDocument: { uri },
1698
+ position,
1699
+ newName: new_name,
1700
+ },
1701
+ signal,
1702
+ )) as WorkspaceEdit | null;
1703
+
1704
+ if (!result) {
1705
+ output = "Rename returned no edits";
1706
+ } else {
1707
+ const shouldApply = apply !== false;
1708
+ if (shouldApply) {
1709
+ const applied = await applyWorkspaceEdit(result, this.session.cwd);
1710
+ output = `Applied rename:\n${applied.map(a => ` ${a}`).join("\n")}`;
1711
+ } else {
1712
+ const preview = formatWorkspaceEdit(result, this.session.cwd);
1713
+ output = `Rename preview:\n${preview.map(p => ` ${p}`).join("\n")}`;
1714
+ }
1715
+ }
1716
+ break;
1717
+ }
1718
+
1719
+ case "reload": {
1720
+ output = await reloadServer(client, serverName, signal);
1721
+ break;
1722
+ }
1723
+
1724
+ default:
1725
+ output = `Unknown action: ${action}`;
1726
+ }
1727
+
1728
+ return {
1729
+ content: [{ type: "text", text: output }],
1730
+ details: { serverName, action, success: true, request: params },
1731
+ };
1732
+ } catch (err) {
1733
+ if (err instanceof ToolAbortError || signal?.aborted) {
1734
+ throw new ToolAbortError();
1735
+ }
1736
+ const errorMessage = err instanceof Error ? err.message : String(err);
1737
+ return {
1738
+ content: [{ type: "text", text: `LSP error: ${errorMessage}` }],
1739
+ details: { serverName, action, success: false, request: params },
1740
+ };
1741
+ }
1742
+ }
1743
+ }