mixdog 0.7.18 → 0.8.0

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 (844) hide show
  1. package/README.md +37 -331
  2. package/package.json +67 -99
  3. package/scripts/boot-smoke.mjs +94 -0
  4. package/scripts/build-tui.mjs +52 -0
  5. package/scripts/compact-smoke.mjs +199 -0
  6. package/scripts/lead-workflow-smoke.mjs +598 -0
  7. package/scripts/live-worker-smoke.mjs +239 -0
  8. package/scripts/output-style-smoke.mjs +101 -0
  9. package/scripts/smoke-loop-report.mjs +221 -0
  10. package/scripts/smoke-loop.mjs +201 -0
  11. package/scripts/smoke.mjs +113 -0
  12. package/scripts/tool-failures.mjs +143 -0
  13. package/scripts/tool-smoke.mjs +456 -0
  14. package/src/agents/debugger/AGENT.md +3 -0
  15. package/src/agents/debugger/agent.json +6 -0
  16. package/src/agents/explore/AGENT.md +4 -0
  17. package/src/agents/explore/agent.json +6 -0
  18. package/src/agents/heavy-worker/AGENT.md +3 -0
  19. package/src/agents/heavy-worker/agent.json +6 -0
  20. package/src/agents/maintainer/AGENT.md +3 -0
  21. package/src/agents/maintainer/agent.json +6 -0
  22. package/src/agents/reviewer/AGENT.md +3 -0
  23. package/src/agents/reviewer/agent.json +6 -0
  24. package/src/agents/scheduler-task.md +3 -0
  25. package/src/agents/web-researcher/AGENT.md +3 -0
  26. package/src/agents/web-researcher/agent.json +6 -0
  27. package/src/agents/webhook-handler.md +3 -0
  28. package/src/agents/worker/AGENT.md +3 -0
  29. package/src/agents/worker/agent.json +6 -0
  30. package/src/app.mjs +90 -0
  31. package/src/cli.mjs +11 -0
  32. package/src/defaults/hidden-roles.json +72 -0
  33. package/src/defaults/mixdog-config.template.json +15 -0
  34. package/src/hooks/lib/permission-evaluator.cjs +488 -0
  35. package/src/hooks/lib/settings-loader.cjs +112 -0
  36. package/src/lib/keychain-cjs.cjs +332 -0
  37. package/src/lib/plugin-paths.cjs +28 -0
  38. package/src/lib/rules-builder.cjs +315 -0
  39. package/src/mixdog-session-runtime.mjs +3704 -0
  40. package/src/output-styles/default.md +38 -0
  41. package/src/output-styles/extreme-simple.md +17 -0
  42. package/src/output-styles/simple.md +17 -0
  43. package/src/repl.mjs +322 -0
  44. package/src/rules/bridge/00-common.md +5 -0
  45. package/src/rules/bridge/20-skip-protocol.md +11 -0
  46. package/src/rules/bridge/30-explorer.md +4 -0
  47. package/src/rules/bridge/40-cycle1-agent.md +28 -0
  48. package/src/rules/bridge/41-cycle2-agent.md +59 -0
  49. package/src/rules/lead/00-tool-lead.md +5 -0
  50. package/src/rules/lead/01-general.md +5 -0
  51. package/src/rules/lead/02-channels.md +3 -0
  52. package/src/rules/lead/04-workflow.md +12 -0
  53. package/src/rules/shared/00-language.md +3 -0
  54. package/src/rules/shared/01-tool.md +3 -0
  55. package/src/runtime/agent/orchestrator/bridge-trace.mjs +814 -0
  56. package/src/runtime/agent/orchestrator/cache-mtime.mjs +60 -0
  57. package/src/runtime/agent/orchestrator/config.mjs +446 -0
  58. package/src/runtime/agent/orchestrator/context/collect.mjs +796 -0
  59. package/src/runtime/agent/orchestrator/dispatch-persist.mjs +417 -0
  60. package/src/runtime/agent/orchestrator/internal-roles.mjs +188 -0
  61. package/src/runtime/agent/orchestrator/internal-tools.mjs +88 -0
  62. package/src/runtime/agent/orchestrator/mcp/client.mjs +345 -0
  63. package/src/runtime/agent/orchestrator/providers/anthropic-oauth.mjs +2104 -0
  64. package/src/runtime/agent/orchestrator/providers/anthropic.mjs +784 -0
  65. package/src/runtime/agent/orchestrator/providers/api-usage.mjs +341 -0
  66. package/src/runtime/agent/orchestrator/providers/gemini.mjs +1679 -0
  67. package/src/runtime/agent/orchestrator/providers/grok-oauth.mjs +959 -0
  68. package/src/runtime/agent/orchestrator/providers/media-normalization.mjs +213 -0
  69. package/src/runtime/agent/orchestrator/providers/model-cache.mjs +38 -0
  70. package/src/runtime/agent/orchestrator/providers/model-catalog.mjs +471 -0
  71. package/src/runtime/agent/orchestrator/providers/oauth-usage.mjs +615 -0
  72. package/src/runtime/agent/orchestrator/providers/openai-compat-stream.mjs +808 -0
  73. package/src/runtime/agent/orchestrator/providers/openai-compat.mjs +1719 -0
  74. package/src/runtime/agent/orchestrator/providers/openai-oauth-ws.mjs +2587 -0
  75. package/src/runtime/agent/orchestrator/providers/openai-oauth.mjs +1953 -0
  76. package/src/runtime/agent/orchestrator/providers/openai-ws.mjs +136 -0
  77. package/src/runtime/agent/orchestrator/providers/opencode-go-usage.mjs +317 -0
  78. package/src/runtime/agent/orchestrator/providers/opencode-go.mjs +109 -0
  79. package/src/runtime/agent/orchestrator/providers/registry.mjs +247 -0
  80. package/src/runtime/agent/orchestrator/providers/retry-classifier.mjs +332 -0
  81. package/src/runtime/agent/orchestrator/providers/statusline-route-meta.mjs +11 -0
  82. package/src/runtime/agent/orchestrator/providers/trace-utils.mjs +50 -0
  83. package/src/runtime/agent/orchestrator/session/cache/prefetch-cache.mjs +142 -0
  84. package/src/runtime/agent/orchestrator/session/cache/read-cache.mjs +318 -0
  85. package/src/runtime/agent/orchestrator/session/cache/scoped-cache.mjs +367 -0
  86. package/src/runtime/agent/orchestrator/session/compact.mjs +882 -0
  87. package/src/runtime/agent/orchestrator/session/context-utils.mjs +233 -0
  88. package/src/runtime/agent/orchestrator/session/loop.mjs +2320 -0
  89. package/src/runtime/agent/orchestrator/session/manager.mjs +2960 -0
  90. package/src/runtime/agent/orchestrator/session/result-classification.mjs +65 -0
  91. package/src/runtime/agent/orchestrator/session/store.mjs +663 -0
  92. package/src/runtime/agent/orchestrator/session/tool-result-offload.mjs +166 -0
  93. package/src/runtime/agent/orchestrator/smart-bridge/bridge-llm.mjs +339 -0
  94. package/src/runtime/agent/orchestrator/smart-bridge/cache-strategy.mjs +419 -0
  95. package/src/runtime/agent/orchestrator/stall-policy.mjs +227 -0
  96. package/src/runtime/agent/orchestrator/tool-loop-guard.mjs +235 -0
  97. package/src/runtime/agent/orchestrator/tools/bash-session.mjs +723 -0
  98. package/src/runtime/agent/orchestrator/tools/builtin/arg-guard.mjs +389 -0
  99. package/src/runtime/agent/orchestrator/tools/builtin/bash-tool.mjs +637 -0
  100. package/src/runtime/agent/orchestrator/tools/builtin/builtin-tools.mjs +165 -0
  101. package/src/runtime/agent/orchestrator/tools/builtin/fuzzy-match.mjs +104 -0
  102. package/src/runtime/agent/orchestrator/tools/builtin/glob-walk.mjs +194 -0
  103. package/src/runtime/agent/orchestrator/tools/builtin/list-tool.mjs +596 -0
  104. package/src/runtime/agent/orchestrator/tools/builtin/native-edit-runner.mjs +110 -0
  105. package/src/runtime/agent/orchestrator/tools/builtin/path-diagnostics.mjs +153 -0
  106. package/src/runtime/agent/orchestrator/tools/builtin/read-formatting.mjs +118 -0
  107. package/src/runtime/agent/orchestrator/tools/builtin/read-open.mjs +189 -0
  108. package/src/runtime/agent/orchestrator/tools/builtin/read-single-tool.mjs +731 -0
  109. package/src/runtime/agent/orchestrator/tools/builtin/read-snapshot-runtime.mjs +168 -0
  110. package/src/runtime/agent/orchestrator/tools/builtin/read-streaming.mjs +602 -0
  111. package/src/runtime/agent/orchestrator/tools/builtin/rg-runner.mjs +465 -0
  112. package/src/runtime/agent/orchestrator/tools/builtin/search-builders.mjs +160 -0
  113. package/src/runtime/agent/orchestrator/tools/builtin/search-tool.mjs +982 -0
  114. package/src/runtime/agent/orchestrator/tools/builtin/shell-jobs.mjs +1087 -0
  115. package/src/runtime/agent/orchestrator/tools/builtin/shell-runtime.mjs +231 -0
  116. package/src/runtime/agent/orchestrator/tools/builtin/snapshot-store.mjs +223 -0
  117. package/src/runtime/agent/orchestrator/tools/builtin.mjs +478 -0
  118. package/src/runtime/agent/orchestrator/tools/code-graph-tool-defs.mjs +24 -0
  119. package/src/runtime/agent/orchestrator/tools/code-graph.mjs +4102 -0
  120. package/src/runtime/agent/orchestrator/tools/destructive-warning.mjs +323 -0
  121. package/src/runtime/agent/orchestrator/tools/graph-binary-fetcher.mjs +154 -0
  122. package/src/runtime/agent/orchestrator/tools/graph-manifest.json +26 -0
  123. package/src/runtime/agent/orchestrator/tools/patch-binary-fetcher.mjs +143 -0
  124. package/src/runtime/agent/orchestrator/tools/patch-tool-defs.mjs +18 -0
  125. package/src/runtime/agent/orchestrator/tools/patch.mjs +2772 -0
  126. package/src/runtime/agent/orchestrator/tools/progress-message.mjs +114 -0
  127. package/src/runtime/agent/orchestrator/tools/shell-command.mjs +880 -0
  128. package/src/runtime/agent/orchestrator/tools/shell-snapshot.mjs +312 -0
  129. package/src/runtime/channels/backends/discord.mjs +781 -0
  130. package/src/runtime/channels/data/voice-runtime-manifest.json +138 -0
  131. package/src/runtime/channels/index.mjs +3309 -0
  132. package/src/runtime/channels/lib/config.mjs +285 -0
  133. package/src/runtime/channels/lib/drop-trace.mjs +71 -0
  134. package/src/runtime/channels/lib/event-pipeline.mjs +81 -0
  135. package/src/runtime/channels/lib/holidays.mjs +138 -0
  136. package/src/runtime/channels/lib/hook-pipe-server.mjs +671 -0
  137. package/src/runtime/channels/lib/output-forwarder.mjs +765 -0
  138. package/src/runtime/channels/lib/runtime-paths.mjs +497 -0
  139. package/src/runtime/channels/lib/scheduler.mjs +710 -0
  140. package/src/runtime/channels/lib/session-discovery.mjs +102 -0
  141. package/src/runtime/channels/lib/state-file.mjs +68 -0
  142. package/src/runtime/channels/lib/status-snapshot.mjs +224 -0
  143. package/src/runtime/channels/lib/tool-format.mjs +124 -0
  144. package/src/runtime/channels/lib/transcript-discovery.mjs +195 -0
  145. package/src/runtime/channels/lib/voice-runtime-fetcher.mjs +734 -0
  146. package/src/runtime/channels/lib/webhook.mjs +1288 -0
  147. package/src/runtime/channels/tool-defs.mjs +177 -0
  148. package/src/runtime/lib/keychain-cjs.cjs +289 -0
  149. package/src/runtime/memory/data/runtime-manifest.json +40 -0
  150. package/src/runtime/memory/index.mjs +3600 -0
  151. package/src/runtime/memory/lib/core-memory-store.mjs +336 -0
  152. package/src/runtime/memory/lib/embedding-provider.mjs +275 -0
  153. package/src/runtime/memory/lib/embedding-worker.mjs +331 -0
  154. package/src/runtime/memory/lib/memory-cycle-requests.mjs +276 -0
  155. package/src/runtime/memory/lib/memory-cycle1.mjs +783 -0
  156. package/src/runtime/memory/lib/memory-cycle2.mjs +1389 -0
  157. package/src/runtime/memory/lib/memory-cycle3.mjs +646 -0
  158. package/src/runtime/memory/lib/memory-embed.mjs +300 -0
  159. package/src/runtime/memory/lib/memory-ops-policy.mjs +149 -0
  160. package/src/runtime/memory/lib/memory-recall-store.mjs +644 -0
  161. package/src/runtime/memory/lib/memory.mjs +418 -0
  162. package/src/runtime/memory/lib/pg/adapter.mjs +314 -0
  163. package/src/runtime/memory/lib/pg/process.mjs +366 -0
  164. package/src/runtime/memory/lib/pg/supervisor.mjs +495 -0
  165. package/src/runtime/memory/lib/runtime-fetcher.mjs +464 -0
  166. package/src/runtime/memory/lib/trace-store.mjs +734 -0
  167. package/src/runtime/memory/tool-defs.mjs +79 -0
  168. package/src/runtime/search/index.mjs +925 -0
  169. package/src/runtime/search/lib/config.mjs +61 -0
  170. package/src/runtime/search/lib/web-tools.mjs +1278 -0
  171. package/src/runtime/search/tool-defs.mjs +64 -0
  172. package/src/runtime/shared/atomic-file.mjs +435 -0
  173. package/src/runtime/shared/background-tasks.mjs +376 -0
  174. package/src/runtime/shared/child-guardian.mjs +98 -0
  175. package/src/runtime/shared/config.mjs +393 -0
  176. package/src/runtime/shared/err-text.mjs +121 -0
  177. package/src/runtime/shared/launcher-control.mjs +259 -0
  178. package/src/runtime/shared/llm/http-agent.mjs +129 -0
  179. package/src/runtime/shared/open-url.mjs +37 -0
  180. package/src/runtime/shared/plugin-paths.mjs +25 -0
  181. package/src/runtime/shared/process-shutdown.mjs +147 -0
  182. package/src/runtime/shared/schedules-store.mjs +70 -0
  183. package/src/runtime/shared/tool-execution-contract.mjs +104 -0
  184. package/src/runtime/shared/tool-surface.mjs +950 -0
  185. package/src/runtime/shared/user-cwd.mjs +221 -0
  186. package/src/runtime/shared/user-data-guard.mjs +232 -0
  187. package/src/runtime/shared/workspace-router.mjs +259 -0
  188. package/src/standalone/bridge-tool.mjs +1414 -0
  189. package/src/standalone/channel-admin.mjs +366 -0
  190. package/src/standalone/channel-worker-preload.cjs +3 -0
  191. package/src/standalone/channel-worker.mjs +353 -0
  192. package/src/standalone/explore-tool.mjs +233 -0
  193. package/src/standalone/hook-bus.mjs +246 -0
  194. package/src/standalone/plugin-admin.mjs +247 -0
  195. package/src/standalone/provider-admin.mjs +338 -0
  196. package/src/standalone/seeds.mjs +94 -0
  197. package/src/standalone/usage-dashboard.mjs +510 -0
  198. package/src/tui/App.jsx +5438 -0
  199. package/src/tui/components/AnsiText.jsx +199 -0
  200. package/src/tui/components/ContextPanel.jsx +217 -0
  201. package/src/tui/components/Markdown.jsx +205 -0
  202. package/src/tui/components/MarkdownTable.jsx +204 -0
  203. package/src/tui/components/Message.jsx +103 -0
  204. package/src/tui/components/Picker.jsx +317 -0
  205. package/src/tui/components/PromptInput.jsx +584 -0
  206. package/src/tui/components/QueuedCommands.jsx +47 -0
  207. package/src/tui/components/SlashCommandPalette.jsx +114 -0
  208. package/src/tui/components/Spinner.jsx +317 -0
  209. package/src/tui/components/StatusLine.jsx +87 -0
  210. package/src/tui/components/TextEntryPanel.jsx +323 -0
  211. package/src/tui/components/ToolExecution.jsx +772 -0
  212. package/src/tui/components/TurnDone.jsx +78 -0
  213. package/src/tui/components/UsagePanel.jsx +331 -0
  214. package/src/tui/dist/index.mjs +12359 -0
  215. package/src/tui/engine.mjs +2410 -0
  216. package/src/tui/figures.mjs +50 -0
  217. package/src/tui/hooks/useEngine.mjs +16 -0
  218. package/src/tui/index.jsx +254 -0
  219. package/src/tui/input-editing.mjs +242 -0
  220. package/src/tui/markdown/format-token.mjs +194 -0
  221. package/src/tui/paste-attachments.mjs +198 -0
  222. package/src/tui/runtime/shared/process-shutdown.mjs +1 -0
  223. package/src/tui/spinner-verbs.mjs +45 -0
  224. package/src/tui/theme.mjs +67 -0
  225. package/src/tui/time-format.mjs +53 -0
  226. package/src/ui/ansi.mjs +115 -0
  227. package/src/ui/markdown.mjs +195 -0
  228. package/src/ui/statusline.mjs +730 -0
  229. package/src/ui/tool-card.mjs +101 -0
  230. package/src/vendor/statusline/bin/statusline-lib.mjs +805 -0
  231. package/src/vendor/statusline/bin/statusline-route.mjs +596 -0
  232. package/src/vendor/statusline/scripts/lib/gateway-settings.mjs +285 -0
  233. package/src/vendor/statusline/src/gateway/claude-current.mjs +320 -0
  234. package/src/vendor/statusline/src/gateway/route-meta.mjs +753 -0
  235. package/src/vendor/statusline/src/gateway/session-routes.mjs +244 -0
  236. package/src/workflows/default/WORKFLOW.md +7 -0
  237. package/src/workflows/default/workflow.json +14 -0
  238. package/vendor/ink/build/ansi-tokenizer.d.ts +38 -0
  239. package/vendor/ink/build/ansi-tokenizer.js +316 -0
  240. package/vendor/ink/build/ansi-tokenizer.js.map +1 -0
  241. package/vendor/ink/build/colorize.d.ts +3 -0
  242. package/vendor/ink/build/colorize.js +48 -0
  243. package/vendor/ink/build/colorize.js.map +1 -0
  244. package/vendor/ink/build/components/AccessibilityContext.d.ts +3 -0
  245. package/vendor/ink/build/components/AccessibilityContext.js +5 -0
  246. package/vendor/ink/build/components/AccessibilityContext.js.map +1 -0
  247. package/vendor/ink/build/components/AnimationContext.d.ts +9 -0
  248. package/vendor/ink/build/components/AnimationContext.js +13 -0
  249. package/vendor/ink/build/components/AnimationContext.js.map +1 -0
  250. package/vendor/ink/build/components/App.d.ts +24 -0
  251. package/vendor/ink/build/components/App.js +554 -0
  252. package/vendor/ink/build/components/App.js.map +1 -0
  253. package/vendor/ink/build/components/AppContext.d.ts +80 -0
  254. package/vendor/ink/build/components/AppContext.js +25 -0
  255. package/vendor/ink/build/components/AppContext.js.map +1 -0
  256. package/vendor/ink/build/components/BackgroundContext.d.ts +4 -0
  257. package/vendor/ink/build/components/BackgroundContext.js +3 -0
  258. package/vendor/ink/build/components/BackgroundContext.js.map +1 -0
  259. package/vendor/ink/build/components/Box.d.ts +130 -0
  260. package/vendor/ink/build/components/Box.js +34 -0
  261. package/vendor/ink/build/components/Box.js.map +1 -0
  262. package/vendor/ink/build/components/CursorContext.d.ts +11 -0
  263. package/vendor/ink/build/components/CursorContext.js +8 -0
  264. package/vendor/ink/build/components/CursorContext.js.map +1 -0
  265. package/vendor/ink/build/components/ErrorBoundary.d.ts +18 -0
  266. package/vendor/ink/build/components/ErrorBoundary.js +23 -0
  267. package/vendor/ink/build/components/ErrorBoundary.js.map +1 -0
  268. package/vendor/ink/build/components/ErrorOverview.d.ts +6 -0
  269. package/vendor/ink/build/components/ErrorOverview.js +90 -0
  270. package/vendor/ink/build/components/ErrorOverview.js.map +1 -0
  271. package/vendor/ink/build/components/FocusContext.d.ts +16 -0
  272. package/vendor/ink/build/components/FocusContext.js +17 -0
  273. package/vendor/ink/build/components/FocusContext.js.map +1 -0
  274. package/vendor/ink/build/components/Newline.d.ts +13 -0
  275. package/vendor/ink/build/components/Newline.js +8 -0
  276. package/vendor/ink/build/components/Newline.js.map +1 -0
  277. package/vendor/ink/build/components/Spacer.d.ts +7 -0
  278. package/vendor/ink/build/components/Spacer.js +11 -0
  279. package/vendor/ink/build/components/Spacer.js.map +1 -0
  280. package/vendor/ink/build/components/Static.d.ts +24 -0
  281. package/vendor/ink/build/components/Static.js +28 -0
  282. package/vendor/ink/build/components/Static.js.map +1 -0
  283. package/vendor/ink/build/components/StderrContext.d.ts +15 -0
  284. package/vendor/ink/build/components/StderrContext.js +13 -0
  285. package/vendor/ink/build/components/StderrContext.js.map +1 -0
  286. package/vendor/ink/build/components/StdinContext.d.ts +28 -0
  287. package/vendor/ink/build/components/StdinContext.js +20 -0
  288. package/vendor/ink/build/components/StdinContext.js.map +1 -0
  289. package/vendor/ink/build/components/StdoutContext.d.ts +15 -0
  290. package/vendor/ink/build/components/StdoutContext.js +13 -0
  291. package/vendor/ink/build/components/StdoutContext.js.map +1 -0
  292. package/vendor/ink/build/components/Text.d.ts +55 -0
  293. package/vendor/ink/build/components/Text.js +50 -0
  294. package/vendor/ink/build/components/Text.js.map +1 -0
  295. package/vendor/ink/build/components/Transform.d.ts +16 -0
  296. package/vendor/ink/build/components/Transform.js +15 -0
  297. package/vendor/ink/build/components/Transform.js.map +1 -0
  298. package/vendor/ink/build/cursor-helpers.d.ts +39 -0
  299. package/vendor/ink/build/cursor-helpers.js +62 -0
  300. package/vendor/ink/build/cursor-helpers.js.map +1 -0
  301. package/vendor/ink/build/devtools-window-polyfill.d.ts +1 -0
  302. package/vendor/ink/build/devtools-window-polyfill.js +68 -0
  303. package/vendor/ink/build/devtools-window-polyfill.js.map +1 -0
  304. package/vendor/ink/build/devtools.d.ts +1 -0
  305. package/vendor/ink/build/devtools.js +36 -0
  306. package/vendor/ink/build/devtools.js.map +1 -0
  307. package/vendor/ink/build/dom.d.ts +62 -0
  308. package/vendor/ink/build/dom.js +143 -0
  309. package/vendor/ink/build/dom.js.map +1 -0
  310. package/vendor/ink/build/get-max-width.d.ts +3 -0
  311. package/vendor/ink/build/get-max-width.js +10 -0
  312. package/vendor/ink/build/get-max-width.js.map +1 -0
  313. package/vendor/ink/build/hooks/use-animation.d.ts +49 -0
  314. package/vendor/ink/build/hooks/use-animation.js +87 -0
  315. package/vendor/ink/build/hooks/use-animation.js.map +1 -0
  316. package/vendor/ink/build/hooks/use-app.d.ts +5 -0
  317. package/vendor/ink/build/hooks/use-app.js +8 -0
  318. package/vendor/ink/build/hooks/use-app.js.map +1 -0
  319. package/vendor/ink/build/hooks/use-box-metrics.d.ts +59 -0
  320. package/vendor/ink/build/hooks/use-box-metrics.js +81 -0
  321. package/vendor/ink/build/hooks/use-box-metrics.js.map +1 -0
  322. package/vendor/ink/build/hooks/use-cursor.d.ts +12 -0
  323. package/vendor/ink/build/hooks/use-cursor.js +29 -0
  324. package/vendor/ink/build/hooks/use-cursor.js.map +1 -0
  325. package/vendor/ink/build/hooks/use-focus-manager.d.ts +43 -0
  326. package/vendor/ink/build/hooks/use-focus-manager.js +18 -0
  327. package/vendor/ink/build/hooks/use-focus-manager.js.map +1 -0
  328. package/vendor/ink/build/hooks/use-focus.d.ts +30 -0
  329. package/vendor/ink/build/hooks/use-focus.js +43 -0
  330. package/vendor/ink/build/hooks/use-focus.js.map +1 -0
  331. package/vendor/ink/build/hooks/use-input.d.ts +132 -0
  332. package/vendor/ink/build/hooks/use-input.js +126 -0
  333. package/vendor/ink/build/hooks/use-input.js.map +1 -0
  334. package/vendor/ink/build/hooks/use-is-screen-reader-enabled.d.ts +6 -0
  335. package/vendor/ink/build/hooks/use-is-screen-reader-enabled.js +12 -0
  336. package/vendor/ink/build/hooks/use-is-screen-reader-enabled.js.map +1 -0
  337. package/vendor/ink/build/hooks/use-paste.d.ts +35 -0
  338. package/vendor/ink/build/hooks/use-paste.js +62 -0
  339. package/vendor/ink/build/hooks/use-paste.js.map +1 -0
  340. package/vendor/ink/build/hooks/use-stderr.d.ts +5 -0
  341. package/vendor/ink/build/hooks/use-stderr.js +8 -0
  342. package/vendor/ink/build/hooks/use-stderr.js.map +1 -0
  343. package/vendor/ink/build/hooks/use-stdin.d.ts +7 -0
  344. package/vendor/ink/build/hooks/use-stdin.js +9 -0
  345. package/vendor/ink/build/hooks/use-stdin.js.map +1 -0
  346. package/vendor/ink/build/hooks/use-stdout.d.ts +5 -0
  347. package/vendor/ink/build/hooks/use-stdout.js +8 -0
  348. package/vendor/ink/build/hooks/use-stdout.js.map +1 -0
  349. package/vendor/ink/build/hooks/use-window-size.d.ts +18 -0
  350. package/vendor/ink/build/hooks/use-window-size.js +22 -0
  351. package/vendor/ink/build/hooks/use-window-size.js.map +1 -0
  352. package/vendor/ink/build/index.d.ts +42 -0
  353. package/vendor/ink/build/index.js +24 -0
  354. package/vendor/ink/build/index.js.map +1 -0
  355. package/vendor/ink/build/ink.d.ts +146 -0
  356. package/vendor/ink/build/ink.js +1022 -0
  357. package/vendor/ink/build/ink.js.map +1 -0
  358. package/vendor/ink/build/input-parser.d.ts +10 -0
  359. package/vendor/ink/build/input-parser.js +194 -0
  360. package/vendor/ink/build/input-parser.js.map +1 -0
  361. package/vendor/ink/build/instances.d.ts +3 -0
  362. package/vendor/ink/build/instances.js +8 -0
  363. package/vendor/ink/build/instances.js.map +1 -0
  364. package/vendor/ink/build/kitty-keyboard.d.ts +23 -0
  365. package/vendor/ink/build/kitty-keyboard.js +32 -0
  366. package/vendor/ink/build/kitty-keyboard.js.map +1 -0
  367. package/vendor/ink/build/log-update.d.ts +20 -0
  368. package/vendor/ink/build/log-update.js +261 -0
  369. package/vendor/ink/build/log-update.js.map +1 -0
  370. package/vendor/ink/build/measure-element.d.ts +20 -0
  371. package/vendor/ink/build/measure-element.js +13 -0
  372. package/vendor/ink/build/measure-element.js.map +1 -0
  373. package/vendor/ink/build/measure-text.d.ts +6 -0
  374. package/vendor/ink/build/measure-text.js +21 -0
  375. package/vendor/ink/build/measure-text.js.map +1 -0
  376. package/vendor/ink/build/output.d.ts +35 -0
  377. package/vendor/ink/build/output.js +328 -0
  378. package/vendor/ink/build/output.js.map +1 -0
  379. package/vendor/ink/build/parse-keypress.d.ts +20 -0
  380. package/vendor/ink/build/parse-keypress.js +495 -0
  381. package/vendor/ink/build/parse-keypress.js.map +1 -0
  382. package/vendor/ink/build/reconciler.d.ts +4 -0
  383. package/vendor/ink/build/reconciler.js +306 -0
  384. package/vendor/ink/build/reconciler.js.map +1 -0
  385. package/vendor/ink/build/render-background.d.ts +4 -0
  386. package/vendor/ink/build/render-background.js +25 -0
  387. package/vendor/ink/build/render-background.js.map +1 -0
  388. package/vendor/ink/build/render-border.d.ts +4 -0
  389. package/vendor/ink/build/render-border.js +84 -0
  390. package/vendor/ink/build/render-border.js.map +1 -0
  391. package/vendor/ink/build/render-node-to-output.d.ts +14 -0
  392. package/vendor/ink/build/render-node-to-output.js +162 -0
  393. package/vendor/ink/build/render-node-to-output.js.map +1 -0
  394. package/vendor/ink/build/render-to-string.d.ts +38 -0
  395. package/vendor/ink/build/render-to-string.js +116 -0
  396. package/vendor/ink/build/render-to-string.js.map +1 -0
  397. package/vendor/ink/build/render.d.ts +176 -0
  398. package/vendor/ink/build/render.js +71 -0
  399. package/vendor/ink/build/render.js.map +1 -0
  400. package/vendor/ink/build/renderer.d.ts +8 -0
  401. package/vendor/ink/build/renderer.js +64 -0
  402. package/vendor/ink/build/renderer.js.map +1 -0
  403. package/vendor/ink/build/sanitize-ansi.d.ts +2 -0
  404. package/vendor/ink/build/sanitize-ansi.js +27 -0
  405. package/vendor/ink/build/sanitize-ansi.js.map +1 -0
  406. package/vendor/ink/build/squash-text-nodes.d.ts +3 -0
  407. package/vendor/ink/build/squash-text-nodes.js +36 -0
  408. package/vendor/ink/build/squash-text-nodes.js.map +1 -0
  409. package/vendor/ink/build/styles.d.ts +302 -0
  410. package/vendor/ink/build/styles.js +303 -0
  411. package/vendor/ink/build/styles.js.map +1 -0
  412. package/vendor/ink/build/utils.d.ts +9 -0
  413. package/vendor/ink/build/utils.js +19 -0
  414. package/vendor/ink/build/utils.js.map +1 -0
  415. package/vendor/ink/build/wrap-text.d.ts +3 -0
  416. package/vendor/ink/build/wrap-text.js +38 -0
  417. package/vendor/ink/build/wrap-text.js.map +1 -0
  418. package/vendor/ink/build/write-synchronized.d.ts +4 -0
  419. package/vendor/ink/build/write-synchronized.js +9 -0
  420. package/vendor/ink/build/write-synchronized.js.map +1 -0
  421. package/vendor/ink/license +10 -0
  422. package/vendor/ink/package.json +137 -0
  423. package/.claude-plugin/marketplace.json +0 -34
  424. package/.claude-plugin/plugin.json +0 -20
  425. package/.gitattributes +0 -34
  426. package/.mcp.json +0 -14
  427. package/ARCHITECTURE.md +0 -77
  428. package/CHANGELOG.md +0 -30
  429. package/CONTRIBUTING.md +0 -45
  430. package/DATA-FLOW.md +0 -79
  431. package/LICENSE +0 -21
  432. package/SECURITY.md +0 -138
  433. package/UNINSTALL.md +0 -115
  434. package/agents/maintenance.md +0 -5
  435. package/agents/memory-classification.md +0 -30
  436. package/agents/scheduler-task.md +0 -18
  437. package/agents/webhook-handler.md +0 -27
  438. package/agents/worker.md +0 -24
  439. package/bin/bridge +0 -133
  440. package/bin/statusline-launcher.mjs +0 -82
  441. package/bin/statusline-lib.mjs +0 -581
  442. package/bin/statusline-route.mjs +0 -273
  443. package/bin/statusline.mjs +0 -638
  444. package/bun.lock +0 -927
  445. package/commands/config.md +0 -16
  446. package/commands/doctor.md +0 -13
  447. package/commands/model.md +0 -61
  448. package/commands/setup.md +0 -17
  449. package/defaults/hidden-roles.json +0 -68
  450. package/defaults/memory-chunk-prompt.md +0 -63
  451. package/defaults/mixdog-config.template.json +0 -27
  452. package/defaults/user-workflow.json +0 -8
  453. package/defaults/user-workflow.md +0 -17
  454. package/hooks/hooks.json +0 -73
  455. package/hooks/lib/active-instance.cjs +0 -77
  456. package/hooks/lib/permission-evaluator.cjs +0 -411
  457. package/hooks/lib/permission-route.cjs +0 -63
  458. package/hooks/lib/settings-loader.cjs +0 -117
  459. package/hooks/post-tool-use.cjs +0 -84
  460. package/hooks/pre-mcp-sandbox.cjs +0 -158
  461. package/hooks/pre-tool-subagent.cjs +0 -258
  462. package/hooks/session-start.cjs +0 -1493
  463. package/hooks/shim-launcher.cjs +0 -65
  464. package/hooks/turn-timer.cjs +0 -82
  465. package/lib/claude-md-writer.cjs +0 -386
  466. package/lib/keychain-cjs.cjs +0 -290
  467. package/lib/plugin-paths.cjs +0 -69
  468. package/lib/rules-builder.cjs +0 -241
  469. package/native/README.md +0 -117
  470. package/native/prebuilt/linux-aarch64/mixdog-shim +0 -0
  471. package/native/prebuilt/linux-x86_64/mixdog-shim +0 -0
  472. package/native/prebuilt/macos-aarch64/mixdog-shim +0 -0
  473. package/native/prebuilt/macos-x86_64/mixdog-shim +0 -0
  474. package/native/prebuilt/windows-x86_64/mixdog-shim.exe +0 -0
  475. package/prompts/code-review.txt +0 -16
  476. package/prompts/security-audit.txt +0 -17
  477. package/rules/bridge/00-common.md +0 -39
  478. package/rules/bridge/20-skip-protocol.md +0 -18
  479. package/rules/bridge/30-explorer.md +0 -33
  480. package/rules/bridge/40-cycle1-agent.md +0 -52
  481. package/rules/bridge/41-cycle2-agent.md +0 -62
  482. package/rules/lead/00-tool-lead.md +0 -61
  483. package/rules/lead/01-general.md +0 -26
  484. package/rules/lead/02-channels.md +0 -49
  485. package/rules/lead/03-team.md +0 -27
  486. package/rules/lead/04-workflow.md +0 -20
  487. package/rules/shared/00-language.md +0 -14
  488. package/rules/shared/01-tool.md +0 -138
  489. package/scripts/bootstrap.mjs +0 -130
  490. package/scripts/bridge-unify-smoke.mjs +0 -308
  491. package/scripts/build-runtime-linux.sh +0 -348
  492. package/scripts/build-runtime-macos.sh +0 -217
  493. package/scripts/build-runtime-windows.ps1 +0 -242
  494. package/scripts/builtin-utils-smoke.mjs +0 -398
  495. package/scripts/bump.mjs +0 -80
  496. package/scripts/check-json.mjs +0 -45
  497. package/scripts/check-syntax-changed.mjs +0 -102
  498. package/scripts/check-syntax.mjs +0 -58
  499. package/scripts/code-graph-batch.test.mjs +0 -33
  500. package/scripts/config-preserve-smoke.mjs +0 -180
  501. package/scripts/doctor.mjs +0 -489
  502. package/scripts/edit-normalize-fuzz.mjs +0 -130
  503. package/scripts/edit-normalize-smoke.mjs +0 -401
  504. package/scripts/edit-operation-smoke.mjs +0 -369
  505. package/scripts/edit2-smoke.mjs +0 -63
  506. package/scripts/ensure-deps.mjs +0 -259
  507. package/scripts/fuzzy-e2e.mjs +0 -28
  508. package/scripts/fuzzy-smoke.mjs +0 -26
  509. package/scripts/gateway-model.mjs +0 -596
  510. package/scripts/generate-runtime-manifest.mjs +0 -166
  511. package/scripts/guard-smoke.mjs +0 -66
  512. package/scripts/hidden-role-schema-smoke.mjs +0 -162
  513. package/scripts/hook-routing-smoke.mjs +0 -29
  514. package/scripts/inject-input.ps1 +0 -204
  515. package/scripts/io-complex-smoke.mjs +0 -667
  516. package/scripts/io-explore-bench.mjs +0 -424
  517. package/scripts/io-guardrails-smoke.mjs +0 -205
  518. package/scripts/io-mini-bench-baseline.json +0 -11
  519. package/scripts/io-mini-bench.mjs +0 -216
  520. package/scripts/io-route-harness.mjs +0 -933
  521. package/scripts/io-telemetry-report.mjs +0 -691
  522. package/scripts/lib/gateway-inventory.mjs +0 -178
  523. package/scripts/lib/gateway-settings.mjs +0 -78
  524. package/scripts/mutation-bench.mjs +0 -564
  525. package/scripts/mutation-io-smoke.mjs +0 -1097
  526. package/scripts/native-patch-bridge-smoke.mjs +0 -288
  527. package/scripts/native-patch-smoke.mjs +0 -304
  528. package/scripts/openai-oauth-catalog-smoke.mjs +0 -53
  529. package/scripts/patch-interior-context-smoke.mjs +0 -49
  530. package/scripts/patch-newline-utf8-smoke.mjs +0 -157
  531. package/scripts/perf-hook-smoke.mjs +0 -71
  532. package/scripts/permission-eval-smoke.mjs +0 -443
  533. package/scripts/prep-patch.mjs +0 -53
  534. package/scripts/prep-shim.mjs +0 -96
  535. package/scripts/provider-cache-smoke.mjs +0 -687
  536. package/scripts/report-runtime-health.mjs +0 -132
  537. package/scripts/resolve-bun.mjs +0 -60
  538. package/scripts/run-mcp.mjs +0 -1473
  539. package/scripts/salvage-v4a-shatter.test.mjs +0 -58
  540. package/scripts/scoped-cache-io-smoke.mjs +0 -103
  541. package/scripts/shell-policy-round3-smoke.mjs +0 -46
  542. package/scripts/smoke-runtime-negative.ps1 +0 -100
  543. package/scripts/smoke-runtime-negative.sh +0 -95
  544. package/scripts/stall-policy-smoke.mjs +0 -50
  545. package/scripts/start-memory-worker.mjs +0 -23
  546. package/scripts/statusline-launcher-smoke.mjs +0 -235
  547. package/scripts/stress-atomic-write.mjs +0 -1028
  548. package/scripts/test-fault-inject.mjs +0 -164
  549. package/scripts/test-large-file.mjs +0 -174
  550. package/scripts/tool-edge-smoke.mjs +0 -209
  551. package/scripts/uninstall.mjs +0 -238
  552. package/scripts/webhook-selfheal-smoke.mjs +0 -27
  553. package/scripts/write-overwrite-guard-smoke.mjs +0 -56
  554. package/server-main.mjs +0 -3350
  555. package/server.mjs +0 -468
  556. package/setup/config-merge.mjs +0 -246
  557. package/setup/install.mjs +0 -574
  558. package/setup/launch-core.mjs +0 -617
  559. package/setup/launch.mjs +0 -101
  560. package/setup/locate-claude.mjs +0 -56
  561. package/setup/mixdog-cli.mjs +0 -122
  562. package/setup/setup-server.mjs +0 -3305
  563. package/setup/setup.html +0 -3740
  564. package/setup/tui.mjs +0 -325
  565. package/skills/retro-skill-proposer/SKILL.md +0 -92
  566. package/skills/schedule-add/SKILL.md +0 -77
  567. package/skills/setup/SKILL.md +0 -356
  568. package/skills/webhook-add/SKILL.md +0 -81
  569. package/src/agent/bridge-stall-watchdog.mjs +0 -337
  570. package/src/agent/index.mjs +0 -2229
  571. package/src/agent/orchestrator/ai-wrapped-dispatch.mjs +0 -1010
  572. package/src/agent/orchestrator/bridge-retry.mjs +0 -220
  573. package/src/agent/orchestrator/bridge-trace.mjs +0 -601
  574. package/src/agent/orchestrator/cache-mtime.mjs +0 -58
  575. package/src/agent/orchestrator/config.mjs +0 -405
  576. package/src/agent/orchestrator/context/collect.mjs +0 -651
  577. package/src/agent/orchestrator/dispatch-persist.mjs +0 -549
  578. package/src/agent/orchestrator/drain-registry.mjs +0 -50
  579. package/src/agent/orchestrator/explore-validator.mjs +0 -8
  580. package/src/agent/orchestrator/internal-roles.mjs +0 -118
  581. package/src/agent/orchestrator/internal-tools.mjs +0 -88
  582. package/src/agent/orchestrator/jobs.mjs +0 -116
  583. package/src/agent/orchestrator/mcp/client.mjs +0 -364
  584. package/src/agent/orchestrator/providers/anthropic-oauth.mjs +0 -1884
  585. package/src/agent/orchestrator/providers/anthropic.mjs +0 -598
  586. package/src/agent/orchestrator/providers/gemini.mjs +0 -1530
  587. package/src/agent/orchestrator/providers/grok-oauth.mjs +0 -779
  588. package/src/agent/orchestrator/providers/model-catalog.mjs +0 -374
  589. package/src/agent/orchestrator/providers/openai-compat-stream.mjs +0 -366
  590. package/src/agent/orchestrator/providers/openai-compat.mjs +0 -1511
  591. package/src/agent/orchestrator/providers/openai-oauth-ws.mjs +0 -1891
  592. package/src/agent/orchestrator/providers/openai-oauth.mjs +0 -1456
  593. package/src/agent/orchestrator/providers/openai-ws.mjs +0 -127
  594. package/src/agent/orchestrator/providers/registry.mjs +0 -192
  595. package/src/agent/orchestrator/providers/retry-classifier.mjs +0 -325
  596. package/src/agent/orchestrator/session/cache/prefetch-cache.mjs +0 -142
  597. package/src/agent/orchestrator/session/cache/read-cache.mjs +0 -319
  598. package/src/agent/orchestrator/session/cache/scoped-cache.mjs +0 -361
  599. package/src/agent/orchestrator/session/loop.mjs +0 -1619
  600. package/src/agent/orchestrator/session/manager.mjs +0 -1991
  601. package/src/agent/orchestrator/session/result-classification.mjs +0 -65
  602. package/src/agent/orchestrator/session/store.mjs +0 -632
  603. package/src/agent/orchestrator/session/stream-watchdog.mjs +0 -130
  604. package/src/agent/orchestrator/session/tool-result-offload.mjs +0 -166
  605. package/src/agent/orchestrator/session/trim.mjs +0 -491
  606. package/src/agent/orchestrator/smart-bridge/CACHE-SHARD.md +0 -115
  607. package/src/agent/orchestrator/smart-bridge/bridge-llm.mjs +0 -331
  608. package/src/agent/orchestrator/smart-bridge/cache-obs.mjs +0 -150
  609. package/src/agent/orchestrator/smart-bridge/cache-strategy.mjs +0 -228
  610. package/src/agent/orchestrator/smart-bridge/index.mjs +0 -215
  611. package/src/agent/orchestrator/smart-bridge/profiles.mjs +0 -37
  612. package/src/agent/orchestrator/smart-bridge/registry.mjs +0 -348
  613. package/src/agent/orchestrator/stall-policy.mjs +0 -201
  614. package/src/agent/orchestrator/tool-loop-guard.mjs +0 -75
  615. package/src/agent/orchestrator/tools/bash-session.mjs +0 -722
  616. package/src/agent/orchestrator/tools/builtin/arg-guard.mjs +0 -511
  617. package/src/agent/orchestrator/tools/builtin/bash-tool.mjs +0 -480
  618. package/src/agent/orchestrator/tools/builtin/builtin-tools.mjs +0 -256
  619. package/src/agent/orchestrator/tools/builtin/edit-base-guard.mjs +0 -58
  620. package/src/agent/orchestrator/tools/builtin/edit-byte-plan.mjs +0 -240
  621. package/src/agent/orchestrator/tools/builtin/edit-byte-utils.mjs +0 -113
  622. package/src/agent/orchestrator/tools/builtin/edit-commit.mjs +0 -74
  623. package/src/agent/orchestrator/tools/builtin/edit-context-utils.mjs +0 -242
  624. package/src/agent/orchestrator/tools/builtin/edit-diagnostics.mjs +0 -211
  625. package/src/agent/orchestrator/tools/builtin/edit-engine.mjs +0 -1364
  626. package/src/agent/orchestrator/tools/builtin/edit-failure-context.mjs +0 -126
  627. package/src/agent/orchestrator/tools/builtin/edit-hint.mjs +0 -141
  628. package/src/agent/orchestrator/tools/builtin/edit-match-utils.mjs +0 -194
  629. package/src/agent/orchestrator/tools/builtin/edit-partial-write.mjs +0 -60
  630. package/src/agent/orchestrator/tools/builtin/edit-stale-refresh.mjs +0 -168
  631. package/src/agent/orchestrator/tools/builtin/edit-tool.mjs +0 -173
  632. package/src/agent/orchestrator/tools/builtin/edit-utf8-guard.mjs +0 -48
  633. package/src/agent/orchestrator/tools/builtin/fuzzy-match.mjs +0 -99
  634. package/src/agent/orchestrator/tools/builtin/glob-walk.mjs +0 -193
  635. package/src/agent/orchestrator/tools/builtin/list-tool.mjs +0 -597
  636. package/src/agent/orchestrator/tools/builtin/native-edit-runner.mjs +0 -110
  637. package/src/agent/orchestrator/tools/builtin/notebook-edit-tool.mjs +0 -300
  638. package/src/agent/orchestrator/tools/builtin/path-diagnostics.mjs +0 -152
  639. package/src/agent/orchestrator/tools/builtin/read-formatting.mjs +0 -118
  640. package/src/agent/orchestrator/tools/builtin/read-open.mjs +0 -190
  641. package/src/agent/orchestrator/tools/builtin/read-single-tool.mjs +0 -728
  642. package/src/agent/orchestrator/tools/builtin/read-snapshot-runtime.mjs +0 -173
  643. package/src/agent/orchestrator/tools/builtin/read-streaming.mjs +0 -602
  644. package/src/agent/orchestrator/tools/builtin/rename-tool.mjs +0 -196
  645. package/src/agent/orchestrator/tools/builtin/rg-runner.mjs +0 -422
  646. package/src/agent/orchestrator/tools/builtin/search-builders.mjs +0 -158
  647. package/src/agent/orchestrator/tools/builtin/search-tool.mjs +0 -869
  648. package/src/agent/orchestrator/tools/builtin/shell-jobs.mjs +0 -962
  649. package/src/agent/orchestrator/tools/builtin/shell-runtime.mjs +0 -223
  650. package/src/agent/orchestrator/tools/builtin/snapshot-store.mjs +0 -206
  651. package/src/agent/orchestrator/tools/builtin/write-tool.mjs +0 -401
  652. package/src/agent/orchestrator/tools/builtin.mjs +0 -503
  653. package/src/agent/orchestrator/tools/code-graph-tool-defs.mjs +0 -24
  654. package/src/agent/orchestrator/tools/code-graph.mjs +0 -4095
  655. package/src/agent/orchestrator/tools/cwd-tool.mjs +0 -298
  656. package/src/agent/orchestrator/tools/destructive-warning.mjs +0 -323
  657. package/src/agent/orchestrator/tools/edit-normalize.mjs +0 -603
  658. package/src/agent/orchestrator/tools/graph-binary-fetcher.mjs +0 -154
  659. package/src/agent/orchestrator/tools/graph-manifest.json +0 -26
  660. package/src/agent/orchestrator/tools/host-input.mjs +0 -204
  661. package/src/agent/orchestrator/tools/patch-binary-fetcher.mjs +0 -143
  662. package/src/agent/orchestrator/tools/patch-manifest.json +0 -26
  663. package/src/agent/orchestrator/tools/patch-tool-defs.mjs +0 -20
  664. package/src/agent/orchestrator/tools/patch.mjs +0 -2754
  665. package/src/agent/orchestrator/tools/progress-message.mjs +0 -118
  666. package/src/agent/orchestrator/tools/shell-command.mjs +0 -865
  667. package/src/agent/orchestrator/tools/shell-policy-imports.mjs +0 -7
  668. package/src/agent/orchestrator/tools/shell-snapshot.mjs +0 -313
  669. package/src/agent/orchestrator/workflow-store.mjs +0 -93
  670. package/src/agent/tool-defs.mjs +0 -110
  671. package/src/channels/backends/discord.mjs +0 -784
  672. package/src/channels/data/voice-runtime-manifest.json +0 -138
  673. package/src/channels/index.mjs +0 -3268
  674. package/src/channels/lib/config.mjs +0 -292
  675. package/src/channels/lib/drop-trace.mjs +0 -71
  676. package/src/channels/lib/event-pipeline.mjs +0 -81
  677. package/src/channels/lib/holidays.mjs +0 -138
  678. package/src/channels/lib/hook-pipe-server.mjs +0 -822
  679. package/src/channels/lib/output-forwarder.mjs +0 -765
  680. package/src/channels/lib/runtime-paths.mjs +0 -552
  681. package/src/channels/lib/scheduler.mjs +0 -723
  682. package/src/channels/lib/session-discovery.mjs +0 -103
  683. package/src/channels/lib/state-file.mjs +0 -68
  684. package/src/channels/lib/status-snapshot.mjs +0 -219
  685. package/src/channels/lib/tool-format.mjs +0 -140
  686. package/src/channels/lib/transcript-discovery.mjs +0 -195
  687. package/src/channels/lib/voice-runtime-fetcher.mjs +0 -734
  688. package/src/channels/lib/webhook.mjs +0 -1318
  689. package/src/channels/tool-defs.mjs +0 -170
  690. package/src/daemon/host.mjs +0 -118
  691. package/src/daemon/mcp-transport.mjs +0 -47
  692. package/src/daemon/session.mjs +0 -100
  693. package/src/daemon/thin-client.mjs +0 -71
  694. package/src/daemon/transport.mjs +0 -163
  695. package/src/gateway/claude-current.mjs +0 -255
  696. package/src/gateway/oauth-usage.mjs +0 -598
  697. package/src/gateway/route-meta.mjs +0 -629
  698. package/src/gateway/server.mjs +0 -713
  699. package/src/memory/data/runtime-manifest.json +0 -40
  700. package/src/memory/index.mjs +0 -3332
  701. package/src/memory/lib/core-memory-store.mjs +0 -330
  702. package/src/memory/lib/embedding-provider.mjs +0 -269
  703. package/src/memory/lib/embedding-worker.mjs +0 -323
  704. package/src/memory/lib/memory-cycle1.mjs +0 -645
  705. package/src/memory/lib/memory-cycle2.mjs +0 -1284
  706. package/src/memory/lib/memory-cycle3.mjs +0 -540
  707. package/src/memory/lib/memory-embed.mjs +0 -299
  708. package/src/memory/lib/memory-ops-policy.mjs +0 -190
  709. package/src/memory/lib/memory-recall-store.mjs +0 -638
  710. package/src/memory/lib/memory.mjs +0 -412
  711. package/src/memory/lib/pg/adapter.mjs +0 -308
  712. package/src/memory/lib/pg/process.mjs +0 -360
  713. package/src/memory/lib/pg/supervisor.mjs +0 -396
  714. package/src/memory/lib/runtime-fetcher.mjs +0 -458
  715. package/src/memory/lib/trace-store.mjs +0 -728
  716. package/src/memory/tool-defs.mjs +0 -79
  717. package/src/search/index.mjs +0 -1173
  718. package/src/search/lib/backends/anthropic-oauth.mjs +0 -98
  719. package/src/search/lib/backends/exa.mjs +0 -50
  720. package/src/search/lib/backends/firecrawl.mjs +0 -61
  721. package/src/search/lib/backends/gemini-api.mjs +0 -83
  722. package/src/search/lib/backends/grok-oauth.mjs +0 -86
  723. package/src/search/lib/backends/index.mjs +0 -150
  724. package/src/search/lib/backends/openai-api.mjs +0 -144
  725. package/src/search/lib/backends/openai-oauth.mjs +0 -102
  726. package/src/search/lib/backends/openai-web-search.mjs +0 -76
  727. package/src/search/lib/backends/tavily.mjs +0 -55
  728. package/src/search/lib/backends/xai-api.mjs +0 -113
  729. package/src/search/lib/config.mjs +0 -192
  730. package/src/search/lib/provider-usage.mjs +0 -67
  731. package/src/search/lib/providers.mjs +0 -47
  732. package/src/search/lib/search-intent.mjs +0 -109
  733. package/src/search/lib/setup-handler.mjs +0 -261
  734. package/src/search/lib/web-tools.mjs +0 -1219
  735. package/src/search/tool-defs.mjs +0 -83
  736. package/src/setup/defender-exclusion.mjs +0 -183
  737. package/src/shared/atomic-file.mjs +0 -436
  738. package/src/shared/config.mjs +0 -372
  739. package/src/shared/daemon-recycle.mjs +0 -108
  740. package/src/shared/disable-claude-builtins.mjs +0 -91
  741. package/src/shared/err-text.mjs +0 -12
  742. package/src/shared/llm/http-agent.mjs +0 -123
  743. package/src/shared/open-url.mjs +0 -62
  744. package/src/shared/plugin-paths.mjs +0 -58
  745. package/src/shared/schedules-store.mjs +0 -70
  746. package/src/shared/seed.mjs +0 -161
  747. package/src/shared/user-cwd.mjs +0 -225
  748. package/src/shared/user-data-guard.mjs +0 -244
  749. package/src/status/aggregator.mjs +0 -584
  750. package/src/status/server.mjs +0 -413
  751. package/tools.json +0 -1671
  752. /package/{defaults → src/defaults}/cycle3-review-prompt.md +0 -0
  753. /package/{defaults → src/defaults}/memory-promote-prompt.md +0 -0
  754. /package/{hooks → src/hooks}/lib/permission-rules.cjs +0 -0
  755. /package/{lib → src/lib}/config-cjs.cjs +0 -0
  756. /package/{lib → src/lib}/hook-pipe-path.cjs +0 -0
  757. /package/{lib → src/lib}/mixdog-debug.cjs +0 -0
  758. /package/{lib → src/lib}/text-utils.cjs +0 -0
  759. /package/{rules → src/rules}/bridge/42-cycle3-agent.md +0 -0
  760. /package/src/{agent → runtime/agent}/orchestrator/activity-bus.mjs +0 -0
  761. /package/src/{agent → runtime/agent}/orchestrator/providers/anthropic-betas.mjs +0 -0
  762. /package/src/{agent → runtime/agent}/orchestrator/session/abort-lookup.mjs +0 -0
  763. /package/src/{agent → runtime/agent}/orchestrator/session/cache/post-edit-marks.mjs +0 -0
  764. /package/src/{agent → runtime/agent}/orchestrator/session/cache/scoped-cache-outcome.mjs +0 -0
  765. /package/src/{agent → runtime/agent}/orchestrator/session/cache/util.mjs +0 -0
  766. /package/src/{agent → runtime/agent}/orchestrator/session/read-dedup.mjs +0 -0
  767. /package/src/{agent → runtime/agent}/orchestrator/session/save-session-worker.mjs +0 -0
  768. /package/src/{agent → runtime/agent}/orchestrator/smart-bridge/session-builder.mjs +0 -0
  769. /package/src/{agent → runtime/agent}/orchestrator/tools/bash-policy-scan.mjs +0 -0
  770. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/advisory-lock.mjs +0 -0
  771. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/atomic-write.mjs +0 -0
  772. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/binary-file.mjs +0 -0
  773. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/cache-layers.mjs +0 -0
  774. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/cwd-utils.mjs +0 -0
  775. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/device-paths.mjs +0 -0
  776. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/diagnostics-tool.mjs +0 -0
  777. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/diff-utils.mjs +0 -0
  778. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/fs-reachability.mjs +0 -0
  779. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/grep-formatting.mjs +0 -0
  780. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/hash-utils.mjs +0 -0
  781. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/list-formatting.mjs +0 -0
  782. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/open-config-tool.mjs +0 -0
  783. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/path-locks.mjs +0 -0
  784. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/path-utils.mjs +0 -0
  785. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-args.mjs +0 -0
  786. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-batch.mjs +0 -0
  787. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-constants.mjs +0 -0
  788. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-image-resize.mjs +0 -0
  789. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-image.mjs +0 -0
  790. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-lines.mjs +0 -0
  791. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-mode-tool.mjs +0 -0
  792. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-range-index.mjs +0 -0
  793. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-ranges.mjs +0 -0
  794. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-special-files.mjs +0 -0
  795. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-tool.mjs +0 -0
  796. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/read-windows.mjs +0 -0
  797. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/shell-analysis.mjs +0 -0
  798. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/shell-output.mjs +0 -0
  799. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/snapshot-helpers.mjs +0 -0
  800. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/snapshot-validation.mjs +0 -0
  801. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/text-stats.mjs +0 -0
  802. /package/src/{agent → runtime/agent}/orchestrator/tools/builtin/windows-roots.mjs +0 -0
  803. /package/src/{agent → runtime/agent}/orchestrator/tools/code-graph-prewarm-worker.mjs +0 -0
  804. /package/src/{agent → runtime/agent}/orchestrator/tools/env-scrub.mjs +0 -0
  805. /package/src/{agent → runtime/agent}/orchestrator/tools/mutation-content-cache.mjs +0 -0
  806. /package/src/{agent → runtime/agent}/orchestrator/tools/mutation-planner.mjs +0 -0
  807. /package/src/{agent → runtime/agent}/orchestrator/tools/next-call-utils.mjs +0 -0
  808. /package/src/{agent → runtime/agent}/orchestrator/tools/result-compression.mjs +0 -0
  809. /package/src/{agent → runtime/agent}/orchestrator/tools/shell-exec-policy.mjs +0 -0
  810. /package/src/{agent → runtime/agent}/orchestrator/tools/shell-policy-danger-target.mjs +0 -0
  811. /package/src/{agent → runtime/agent}/orchestrator/tools/shell-policy.mjs +0 -0
  812. /package/src/{channels → runtime/channels}/lib/cli-worker-host.mjs +0 -0
  813. /package/src/{channels → runtime/channels}/lib/config-lock.mjs +0 -0
  814. /package/src/{channels → runtime/channels}/lib/event-queue.mjs +0 -0
  815. /package/src/{channels → runtime/channels}/lib/executor.mjs +0 -0
  816. /package/src/{channels → runtime/channels}/lib/format.mjs +0 -0
  817. /package/src/{channels → runtime/channels}/lib/interaction-workflows.mjs +0 -0
  818. /package/src/{channels → runtime/channels}/lib/memory-client.mjs +0 -0
  819. /package/src/{channels → runtime/channels}/lib/session-control.mjs +0 -0
  820. /package/src/{channels → runtime/channels}/lib/settings.mjs +0 -0
  821. /package/src/{channels → runtime/channels}/lib/whisper-server.mjs +0 -0
  822. /package/src/{memory → runtime/memory}/lib/agent-ipc.mjs +0 -0
  823. /package/src/{memory → runtime/memory}/lib/bridge-trace-queries.mjs +0 -0
  824. /package/src/{memory → runtime/memory}/lib/llm-worker-host.mjs +0 -0
  825. /package/src/{memory → runtime/memory}/lib/memory-cycle.mjs +0 -0
  826. /package/src/{memory → runtime/memory}/lib/memory-extraction.mjs +0 -0
  827. /package/src/{memory → runtime/memory}/lib/memory-maintenance-store.mjs +0 -0
  828. /package/src/{memory → runtime/memory}/lib/memory-recall-id-patch.mjs +0 -0
  829. /package/src/{memory → runtime/memory}/lib/memory-recall-read-query.mjs +0 -0
  830. /package/src/{memory → runtime/memory}/lib/memory-recall-scope-filter.mjs +0 -0
  831. /package/src/{memory → runtime/memory}/lib/memory-retrievers.mjs +0 -0
  832. /package/src/{memory → runtime/memory}/lib/memory-score.mjs +0 -0
  833. /package/src/{memory → runtime/memory}/lib/memory-text-utils.mjs +0 -0
  834. /package/src/{memory → runtime/memory}/lib/model-profile.mjs +0 -0
  835. /package/src/{memory → runtime/memory}/lib/project-id-resolver.mjs +0 -0
  836. /package/src/{search → runtime/search}/lib/cache.mjs +0 -0
  837. /package/src/{search → runtime/search}/lib/formatter.mjs +0 -0
  838. /package/src/{search → runtime/search}/lib/state.mjs +0 -0
  839. /package/src/{shared → runtime/shared}/abort-controller.mjs +0 -0
  840. /package/src/{shared → runtime/shared}/llm/cost.mjs +0 -0
  841. /package/src/{shared → runtime/shared}/llm/index.mjs +0 -0
  842. /package/src/{shared → runtime/shared}/llm/pid-cleanup.mjs +0 -0
  843. /package/src/{shared → runtime/shared}/llm/usage-log.mjs +0 -0
  844. /package/src/{shared → runtime/shared}/wsl.mjs +0 -0
@@ -0,0 +1,925 @@
1
+ #!/usr/bin/env bun
2
+
3
+ import { Server } from '@modelcontextprotocol/sdk/server/index.js'
4
+ import { CallToolRequestSchema, ListToolsRequestSchema } from '@modelcontextprotocol/sdk/types.js'
5
+ import { z } from 'zod'
6
+ import fs from 'fs'
7
+ import path from 'path'
8
+ import {
9
+ ensureDataDir,
10
+ getRequestTimeoutMs,
11
+ loadConfig,
12
+ } from './lib/config.mjs'
13
+ import { normalizeErrorMessage } from '../agent/orchestrator/tools/builtin/path-diagnostics.mjs'
14
+ import { presentErrorText } from '../shared/err-text.mjs'
15
+
16
+ function readPluginVersion() {
17
+ try {
18
+ return JSON.parse(fs.readFileSync(new URL('../../../package.json', import.meta.url), 'utf8')).version || '0.0.1'
19
+ } catch { return '0.0.1' }
20
+ }
21
+ const PLUGIN_VERSION = readPluginVersion()
22
+ import {
23
+ buildCacheKey,
24
+ buildCacheMeta,
25
+ flushCacheState,
26
+ getCachedEntry,
27
+ loadCacheState,
28
+ setCachedEntry,
29
+ } from './lib/cache.mjs'
30
+ import {
31
+ flushUsageState,
32
+ loadUsageState,
33
+ noteProviderFailure,
34
+ classifyProviderError,
35
+ noteProviderSuccess,
36
+ saveUsageState,
37
+ updateProviderState,
38
+ } from './lib/state.mjs'
39
+ import { assertPublicUrl, crawlSite, getScrapeCapabilities, pinnedFetch, scrapeUrls } from './lib/web-tools.mjs'
40
+ import { formatResponse } from './lib/formatter.mjs'
41
+ import {
42
+ cancelBackgroundTask,
43
+ getBackgroundTask,
44
+ renderBackgroundTask,
45
+ renderBackgroundTaskList,
46
+ resolveExecutionMode,
47
+ startBackgroundTask,
48
+ taskIdFromArgs,
49
+ } from '../shared/background-tasks.mjs'
50
+
51
+
52
+ ensureDataDir()
53
+
54
+ const searchArgsSchema = z.object({
55
+ keywords: z.union([z.string().min(1), z.array(z.string().min(1)).min(1)]).describe('Search query string or array of queries.'),
56
+ mode: z.enum(['sync', 'async']).optional(),
57
+ action: z.enum(['run', 'list', 'status', 'read', 'cancel']).optional(),
58
+ task_id: z.string().optional(),
59
+ firstResponseTimeoutMs: z.number().int().min(0).optional(),
60
+ idleTimeoutMs: z.number().int().min(0).optional(),
61
+ site: z.string().optional().describe('Restrict results to a specific domain.'),
62
+ type: z.enum(['web', 'news', 'images']).optional().describe('Search type. Default: web.'),
63
+ maxResults: z.number().int().min(1).max(20).optional().describe('Maximum number of results to return (1-20).'),
64
+ locale: z.union([
65
+ z.string(),
66
+ z.object({
67
+ country: z.string().optional(),
68
+ language: z.string().optional(),
69
+ region: z.string().optional(),
70
+ city: z.string().optional(),
71
+ timezone: z.string().optional(),
72
+ }),
73
+ ]).optional().describe('Explicit search locale. String such as "ko-KR" or object with country/language/city/region/timezone.'),
74
+ contextSize: z.enum(['low', 'medium', 'high']).optional().describe('Search context size hint. Default: low.'),
75
+ })
76
+
77
+ const searchUrlArgsSchema = z.object({
78
+ url: z.union([z.string().url(), z.array(z.string().url()).min(1)]).describe('Single URL or array of URLs to fetch.'),
79
+ startIndex: z.number().int().min(0).optional().describe('Character offset to start the slice from (default 0). For chunked reading of large pages, pass the previous response\'s nextStartIndex.'),
80
+ maxLength: z.number().int().min(0).optional().describe('Max characters to return per call (default 50000). Pass 0 for unlimited.'),
81
+ cwd: z.string().optional(),
82
+ })
83
+
84
+ const SEARCH_EMPTY_STRING_FIELDS = ['keywords', 'site', 'type', 'locale', 'contextSize', 'mode', 'action', 'task_id', 'firstResponseTimeoutMs', 'idleTimeoutMs']
85
+
86
+ function normalizeSearchArgs(rawArgs) {
87
+ if (!rawArgs || typeof rawArgs !== 'object' || Array.isArray(rawArgs)) return rawArgs
88
+ const args = { ...rawArgs }
89
+ for (const key of SEARCH_EMPTY_STRING_FIELDS) {
90
+ const value = args[key]
91
+ if (typeof value === 'string') {
92
+ const trimmed = value.trim()
93
+ if (!trimmed) delete args[key]
94
+ else args[key] = trimmed
95
+ }
96
+ }
97
+ if (Array.isArray(args.keywords)) {
98
+ const keywords = args.keywords
99
+ .map(value => typeof value === 'string' ? value.trim() : value)
100
+ .filter(value => typeof value === 'string' ? value.length > 0 : Boolean(value))
101
+ if (keywords.length > 0) args.keywords = keywords
102
+ else delete args.keywords
103
+ }
104
+ return args
105
+ }
106
+
107
+ function normalizeSearchUrlArgs(rawArgs) {
108
+ if (!rawArgs || typeof rawArgs !== 'object' || Array.isArray(rawArgs)) return rawArgs
109
+ const args = { ...rawArgs }
110
+ if (typeof args.url === 'string') args.url = args.url.trim()
111
+ if (Array.isArray(args.url)) {
112
+ const urls = args.url
113
+ .map(value => typeof value === 'string' ? value.trim() : value)
114
+ .filter(value => typeof value === 'string' ? value.length > 0 : Boolean(value))
115
+ if (urls.length > 0) args.url = urls
116
+ else delete args.url
117
+ }
118
+ return args
119
+ }
120
+
121
+ function formattedText(tool, payload) {
122
+ const text = formatResponse(tool, tool === 'search' ? dropInvalidSearchResults(payload) : payload)
123
+ return {
124
+ content: [{ type: 'text', text }],
125
+ }
126
+ }
127
+
128
+ function toolText(response) {
129
+ if (typeof response === 'string') return response
130
+ const parts = Array.isArray(response?.content) ? response.content : []
131
+ const text = parts
132
+ .filter(part => part?.type === 'text')
133
+ .map(part => part.text)
134
+ .join('\n')
135
+ return text || JSON.stringify(response, null, 2)
136
+ }
137
+
138
+ function okText(text) {
139
+ return { content: [{ type: 'text', text }], isError: false }
140
+ }
141
+
142
+ function searchTaskControl(action, args = {}, options = {}) {
143
+ if (action === 'list') return okText(renderBackgroundTaskList({ surface: 'search', context: options }))
144
+ const taskId = taskIdFromArgs(args)
145
+ if (!taskId) return { ...okText('Error: task_id is required'), isError: true }
146
+ const task = getBackgroundTask(taskId, { surface: 'search', context: options })
147
+ if (!task) return { ...okText(`Error: search task not found: ${taskId}`), isError: true }
148
+ if (action === 'cancel') {
149
+ cancelBackgroundTask(taskId, 'cancelled by search control')
150
+ return okText(renderBackgroundTask(task, { includeResult: true }))
151
+ }
152
+ return okText(renderBackgroundTask(task, { includeResult: action === 'read' }))
153
+ }
154
+
155
+ function isInvalidSearchResult(result) {
156
+ const title = String(result?.title || '').trim()
157
+ return /\bpage not found\b|\b404\b.*\bnot found\b/i.test(title)
158
+ }
159
+
160
+ function dropInvalidSearchResults(payload) {
161
+ if (!payload || typeof payload !== 'object') return payload
162
+ const response = payload.response
163
+ if (!response || typeof response !== 'object' || !Array.isArray(response.results)) return payload
164
+ const results = response.results.filter(result => !isInvalidSearchResult(result))
165
+ if (results.length === response.results.length) return payload
166
+ return {
167
+ ...payload,
168
+ response: {
169
+ ...response,
170
+ results,
171
+ droppedInvalidResults: (response.droppedInvalidResults || 0) + (response.results.length - results.length),
172
+ },
173
+ }
174
+ }
175
+
176
+ function getSearchCacheTtlMs(type = 'web') {
177
+ switch (type) {
178
+ case 'news':
179
+ return 20 * 60 * 1000
180
+ case 'images':
181
+ return 60 * 60 * 1000
182
+ case 'web':
183
+ default:
184
+ return 30 * 60 * 1000
185
+ }
186
+ }
187
+
188
+ function getScrapeCacheTtlMs(isXRoute = false) {
189
+ return isXRoute ? 10 * 60 * 1000 : 60 * 60 * 1000
190
+ }
191
+
192
+ function normalizeCacheUrl(url) {
193
+ try {
194
+ return new URL(url).toString()
195
+ } catch {
196
+ return String(url)
197
+ }
198
+ }
199
+
200
+ const DOC_INDEX_MAX_BYTES = 2 * 1024 * 1024
201
+ const DOC_INDEX_MAX_FETCHES = 8
202
+ const DOC_INDEX_COMMON_PATHS = ['docs', 'api', 'reference', 'api/reference']
203
+ const DOC_INDEX_STOPWORDS = new Set([
204
+ 'about', 'after', 'again', 'also', 'and', 'are', 'can', 'com', 'doc', 'docs',
205
+ 'documentation', 'for', 'from', 'how', 'http', 'https', 'into', 'official',
206
+ 'page', 'pages', 'site', 'the', 'this', 'title', 'url', 'use', 'using', 'what',
207
+ 'when', 'where', 'which', 'with', 'www',
208
+ ])
209
+
210
+ function keywordsText(keywords) {
211
+ return Array.isArray(keywords) ? keywords.join(' ') : String(keywords || '')
212
+ }
213
+
214
+ function queryTokens(keywords) {
215
+ const tokens = keywordsText(keywords)
216
+ .toLowerCase()
217
+ .match(/[\p{L}\p{N}][\p{L}\p{N}._-]{1,}/gu) || []
218
+ return [...new Set(tokens
219
+ .filter(token => token.length >= 3 && !DOC_INDEX_STOPWORDS.has(token)))]
220
+ }
221
+
222
+ // Weighted scoring across title/path/url/snippet. Title hit is the strongest
223
+ // signal (8) because llms.txt entries are hand-curated; path-segment hits
224
+ // (5) and last-segment hits (3..10) catch /api/foo over /blog/foo. Url and
225
+ // snippet (2 / 1) act as tiebreakers when title misses. .md penalty -2 so
226
+ // raw markdown sources lose to rendered docs when both are listed.
227
+ function docLinkScore(link, tokens) {
228
+ if (!tokens.length) return 0
229
+ const title = String(link.title || '').toLowerCase()
230
+ const url = String(link.url || '').toLowerCase()
231
+ const snippet = String(link.snippet || '').toLowerCase()
232
+ let pathname = ''
233
+ try {
234
+ pathname = new URL(link.url).pathname.toLowerCase()
235
+ } catch {}
236
+ const segments = pathname.split('/').filter(Boolean)
237
+ let score = 0
238
+ for (const token of tokens) {
239
+ if (title.includes(token)) score += 8
240
+ if (segments.includes(token)) score += 5
241
+ if (segments.at(-1) === token) score += 3 + Math.max(0, 7 - segments.length)
242
+ if (url.includes(token)) score += 2
243
+ if (snippet.includes(token)) score += 1
244
+ }
245
+ if (/\.md$/i.test(pathname)) score -= 2
246
+ return score
247
+ }
248
+
249
+ function docIndexUrlCandidates(site, keywords) {
250
+ if (!site) return []
251
+ let parsed
252
+ try {
253
+ parsed = new URL(/^https?:\/\//i.test(site) ? site : `https://${site}`)
254
+ } catch {
255
+ return []
256
+ }
257
+ const candidates = []
258
+ const add = (url) => {
259
+ try {
260
+ const normalized = new URL(url).toString()
261
+ if (!candidates.includes(normalized)) candidates.push(normalized)
262
+ } catch {}
263
+ }
264
+ const pathParts = parsed.pathname.split('/').filter(Boolean)
265
+ for (let i = pathParts.length; i >= 0; i -= 1) {
266
+ const prefix = pathParts.slice(0, i).join('/')
267
+ add(`${parsed.origin}${prefix ? `/${prefix}` : ''}/llms.txt`)
268
+ }
269
+ // When the user asks an api/docs question on a bare-host site, also probe
270
+ // the common doc-prefix llms.txt locations the host might publish under.
271
+ const docsIntent = /\b(?:api|docs?|documentation|reference)\b/i.test(keywordsText(keywords))
272
+ if (docsIntent && pathParts.length === 0) {
273
+ for (const prefix of DOC_INDEX_COMMON_PATHS) {
274
+ add(`${parsed.origin}/${prefix}/llms.txt`)
275
+ }
276
+ }
277
+ return candidates
278
+ }
279
+
280
+
281
+ function docIndexAbortSignal(timeoutMs, parentSignal) {
282
+ const ms = Math.min(Math.max(Number(timeoutMs) || 10_000, 1000), 10_000)
283
+ if (typeof AbortSignal.any === 'function') {
284
+ const parts = [AbortSignal.timeout(ms)]
285
+ if (parentSignal) parts.push(parentSignal)
286
+ return AbortSignal.any(parts)
287
+ }
288
+ const controller = new AbortController()
289
+ let timer
290
+ let onParentAbort
291
+ const abortWith = reason => {
292
+ if (timer !== undefined) {
293
+ clearTimeout(timer)
294
+ timer = undefined
295
+ }
296
+ if (parentSignal && onParentAbort) {
297
+ parentSignal.removeEventListener('abort', onParentAbort)
298
+ onParentAbort = undefined
299
+ }
300
+ if (!controller.signal.aborted) controller.abort(reason)
301
+ }
302
+ timer = setTimeout(
303
+ () => abortWith(new DOMException('The operation was aborted due to timeout', 'TimeoutError')),
304
+ ms,
305
+ )
306
+ if (parentSignal) {
307
+ if (parentSignal.aborted) {
308
+ abortWith(parentSignal.reason)
309
+ return controller.signal
310
+ }
311
+ onParentAbort = () => abortWith(parentSignal.reason)
312
+ parentSignal.addEventListener('abort', onParentAbort, { once: true })
313
+ }
314
+ return controller.signal
315
+ }
316
+
317
+ async function fetchDocIndex(url, timeoutMs, parentSignal) {
318
+ // SSRF: reuse the guarded web_fetch path's public-URL/private-IP check so
319
+ // docs-index discovery cannot be steered into localhost / link-local /
320
+ // cloud-metadata addresses by a hostile site override. Follow redirects
321
+ // manually and re-validate each hop so a 30x Location can't steer us to
322
+ // a private/loopback address after the initial check.
323
+ const REDIRECT_STATUSES = new Set([301, 302, 303, 307, 308])
324
+ const MAX_REDIRECTS = 5
325
+ const signal = docIndexAbortSignal(timeoutMs, parentSignal)
326
+ let currentUrl = url
327
+ let response
328
+ for (let hops = 0; ; hops++) {
329
+ assertPublicUrl(currentUrl)
330
+ // pinnedFetch resolves+validates the host once and pins the connection
331
+ // to the validated IP, closing the validate-then-fetch DNS-rebinding /
332
+ // TOCTOU window that bare `fetch` left open.
333
+ response = await pinnedFetch(currentUrl, {
334
+ headers: { Accept: 'text/markdown,text/plain,text/*,*/*' },
335
+ signal,
336
+ redirect: 'manual',
337
+ })
338
+ if (!REDIRECT_STATUSES.has(response.status)) break
339
+ try { await response.body?.cancel() } catch {}
340
+ if (hops >= MAX_REDIRECTS) {
341
+ throw new Error(`docs index too many redirects (max ${MAX_REDIRECTS})`)
342
+ }
343
+ const location = response.headers.get('location')
344
+ if (!location) {
345
+ throw new Error(`docs index redirect ${response.status} without Location header`)
346
+ }
347
+ currentUrl = new URL(location, currentUrl).toString()
348
+ }
349
+ if (!response.ok) {
350
+ try { await response.body?.cancel() } catch {}
351
+ throw new Error(`docs index fetch failed: ${response.status}`)
352
+ }
353
+ const contentLength = Number(response.headers.get('content-length') || 0)
354
+ if (contentLength > DOC_INDEX_MAX_BYTES) {
355
+ try { await response.body?.cancel() } catch {}
356
+ throw new Error(`docs index too large: ${contentLength}`)
357
+ }
358
+ // Enforce DOC_INDEX_MAX_BYTES while streaming so chunked / missing-length
359
+ // responses can't blow past the 2MB cap by deferring the check until after
360
+ // the whole body is buffered.
361
+ const reader = response.body?.getReader?.()
362
+ let text
363
+ if (!reader) {
364
+ // Buffer as bytes and cap by byte length — string.length counts UTF-16
365
+ // code units, which under-counts multi-byte characters and lets the
366
+ // body blow past DOC_INDEX_MAX_BYTES.
367
+ const buf = new Uint8Array(await response.arrayBuffer())
368
+ const capped = buf.byteLength > DOC_INDEX_MAX_BYTES ? buf.subarray(0, DOC_INDEX_MAX_BYTES) : buf
369
+ text = new TextDecoder('utf-8', { fatal: false }).decode(capped)
370
+ } else {
371
+ const chunks = []
372
+ let total = 0
373
+ let capped = false
374
+ try {
375
+ while (true) {
376
+ const { done, value } = await reader.read()
377
+ if (done) break
378
+ total += value.byteLength
379
+ chunks.push(value)
380
+ if (total >= DOC_INDEX_MAX_BYTES) {
381
+ capped = true
382
+ try { await reader.cancel() } catch {}
383
+ break
384
+ }
385
+ }
386
+ } finally {
387
+ try { reader.releaseLock() } catch {}
388
+ }
389
+ const decoder = new TextDecoder('utf-8', { fatal: false })
390
+ let buf = ''
391
+ for (const chunk of chunks) buf += decoder.decode(chunk, { stream: true })
392
+ buf += decoder.decode()
393
+ text = capped || buf.length > DOC_INDEX_MAX_BYTES ? buf.slice(0, DOC_INDEX_MAX_BYTES) : buf
394
+ }
395
+ return {
396
+ text,
397
+ url: response.url || url,
398
+ }
399
+ }
400
+
401
+ function parseDocIndexLinks(text, sourceUrl) {
402
+ const links = []
403
+ const seen = new Set()
404
+ const add = (title, rawUrl, snippet = '') => {
405
+ if (!title || !rawUrl) return
406
+ let url
407
+ try {
408
+ url = new URL(rawUrl, sourceUrl).toString()
409
+ } catch {
410
+ return
411
+ }
412
+ if (!/^https?:\/\//i.test(url) || seen.has(url)) return
413
+ seen.add(url)
414
+ links.push({
415
+ title: String(title).trim(),
416
+ url,
417
+ snippet: String(snippet || '').trim(),
418
+ sourceUrl,
419
+ })
420
+ }
421
+
422
+ for (const line of String(text || '').split(/\r?\n/)) {
423
+ const item = line.match(/^\s*[-*]\s+\[([^\]]{1,180})\]\(([^)\s]+)\)\s*:?\s*(.*)$/)
424
+ if (item) add(item[1], item[2], item[3])
425
+ }
426
+ const inlineRe = /\[([^\]]{1,180})\]\((https?:\/\/[^)\s]+)\)/g
427
+ let match
428
+ while ((match = inlineRe.exec(String(text || '')))) {
429
+ add(match[1], match[2])
430
+ }
431
+ return links
432
+ }
433
+
434
+
435
+ function isDocIndexLink(url) {
436
+ try {
437
+ return /\/llms(?:-full)?\.txt$/i.test(new URL(url).pathname)
438
+ } catch {
439
+ return false
440
+ }
441
+ }
442
+
443
+ function hostFromUrl(url) {
444
+ try {
445
+ return new URL(/^https?:\/\//i.test(url) ? url : `https://${url}`).hostname.toLowerCase()
446
+ } catch {
447
+ return ''
448
+ }
449
+ }
450
+
451
+ function isBaseHost(host) {
452
+ return host.split('.').filter(Boolean).length <= 2
453
+ }
454
+
455
+ function hostMatchesScope(host, scopedHost) {
456
+ if (!host || !scopedHost) return false
457
+ if (host === scopedHost) return true
458
+ return isBaseHost(scopedHost) && host.endsWith(`.${scopedHost}`)
459
+ }
460
+
461
+ function sameDocIndexScope(url, site, requestedIndexUrl) {
462
+ const linkHost = hostFromUrl(url)
463
+ if (!linkHost) return false
464
+ // Always require the link to match the original requested site host.
465
+ const siteHost = hostFromUrl(site)
466
+ if (siteHost && !hostMatchesScope(linkHost, siteHost)) return false
467
+ const scopes = [
468
+ siteHost,
469
+ hostFromUrl(requestedIndexUrl),
470
+ ].filter(Boolean)
471
+ return scopes.some(scope => hostMatchesScope(linkHost, scope))
472
+ }
473
+
474
+ async function discoverDocsIndexResults(args, timeoutMs, parentSignal) {
475
+ if (!args?.site || (args.type && args.type !== 'web')) return []
476
+ const tokens = queryTokens(args.keywords)
477
+ if (!tokens.length) return []
478
+
479
+ const queue = docIndexUrlCandidates(args.site, args.keywords)
480
+ const seenIndexes = new Set()
481
+ const candidates = []
482
+
483
+ while (queue.length > 0 && seenIndexes.size < DOC_INDEX_MAX_FETCHES) {
484
+ if (parentSignal?.aborted) return []
485
+ const indexUrl = queue.shift()
486
+ if (!indexUrl || seenIndexes.has(indexUrl)) continue
487
+ seenIndexes.add(indexUrl)
488
+ let index = null
489
+ try {
490
+ index = await fetchDocIndex(indexUrl, timeoutMs, parentSignal)
491
+ } catch {
492
+ continue
493
+ }
494
+ const sourceUrl = index.url || indexUrl
495
+ const links = parseDocIndexLinks(index.text, sourceUrl)
496
+ for (const link of links) {
497
+ if (isDocIndexLink(link.url)) {
498
+ if (!seenIndexes.has(link.url) && queue.length + seenIndexes.size < DOC_INDEX_MAX_FETCHES) queue.push(link.url)
499
+ continue
500
+ }
501
+ if (!sameDocIndexScope(link.url, args.site, indexUrl)) continue
502
+ const score = docLinkScore(link, tokens)
503
+ if (score <= 0) continue
504
+ candidates.push({
505
+ ...link,
506
+ score,
507
+ })
508
+ }
509
+ }
510
+
511
+ const seenUrls = new Set()
512
+ return candidates
513
+ .sort((a, b) => b.score - a.score)
514
+ .filter((item) => {
515
+ if (seenUrls.has(item.url)) return false
516
+ seenUrls.add(item.url)
517
+ return true
518
+ })
519
+ .slice(0, Math.min(Number(args.maxResults) || 5, 5))
520
+ .map(item => ({
521
+ title: item.title,
522
+ url: item.url,
523
+ snippet: item.snippet || `Matched docs index: ${item.sourceUrl}`,
524
+ source: 'docs-index',
525
+ provider: 'docs-index',
526
+ publishedDate: null,
527
+ meta: { score: item.score, sourceUrl: item.sourceUrl },
528
+ }))
529
+ }
530
+
531
+ async function augmentSearchPayloadWithDocsIndex(payload, args, timeoutMs, parentSignal) {
532
+ if (!payload || typeof payload !== 'object') return payload
533
+ const response = payload.response
534
+ if (!response || typeof response !== 'object' || !Array.isArray(response.results)) return payload
535
+ const indexResults = await discoverDocsIndexResults(args, timeoutMs, parentSignal)
536
+ if (!indexResults.length) return payload
537
+ const seen = new Set()
538
+ const results = []
539
+ for (const result of [...indexResults, ...response.results]) {
540
+ const url = String(result?.url || '')
541
+ const key = url || `${result?.title || ''}\n${result?.snippet || ''}`
542
+ if (seen.has(key)) continue
543
+ seen.add(key)
544
+ results.push(result)
545
+ }
546
+ return {
547
+ ...payload,
548
+ response: {
549
+ ...response,
550
+ results: results.slice(0, Math.max(Number(args.maxResults) || results.length, indexResults.length)),
551
+ docsIndexAugmented: {
552
+ added: indexResults.length,
553
+ sources: [...new Set(indexResults.map(item => item.meta?.sourceUrl).filter(Boolean))],
554
+ },
555
+ },
556
+ }
557
+ }
558
+
559
+ async function writeStartupSnapshot() {
560
+ loadConfig()
561
+ const usageState = loadUsageState()
562
+ const scrapeCapabilities = getScrapeCapabilities()
563
+
564
+ updateProviderState(usageState, 'readability', {
565
+ available: scrapeCapabilities.readability,
566
+ connection: 'builtin',
567
+ source: 'local',
568
+ })
569
+
570
+ updateProviderState(usageState, 'puppeteer', {
571
+ available: scrapeCapabilities.puppeteer,
572
+ connection: 'local-browser',
573
+ source: 'local',
574
+ })
575
+ }
576
+
577
+ // ── Core action implementations (shared by individual and batch handlers) ──
578
+
579
+ const _searchInFlight = new Map()
580
+
581
+ function searchArgsForCacheKey(args) {
582
+ const keywords = Array.isArray(args.keywords)
583
+ ? [...new Set(args.keywords.map(v => String(v || '').trim()).filter(Boolean))]
584
+ : String(args.keywords || '').trim()
585
+ return {
586
+ keywords,
587
+ site: args.site || null,
588
+ type: args.type || 'web',
589
+ locale: args.locale || null,
590
+ contextSize: args.contextSize || 'low',
591
+ maxResults: Math.max(1, Math.min(20, Number(args.maxResults) || 10)),
592
+ }
593
+ }
594
+
595
+ function buildAgentSearchPrompt(args) {
596
+ const query = Array.isArray(args.keywords) ? args.keywords.join('\n') : String(args.keywords || '')
597
+ const lines = [
598
+ 'Perform a concise web research task for Mixdog search.',
599
+ '',
600
+ `Query: ${query}`,
601
+ args.site ? `Site/domain restriction: ${args.site}` : null,
602
+ args.type ? `Search type: ${args.type}` : null,
603
+ args.locale ? `Locale: ${typeof args.locale === 'string' ? args.locale : JSON.stringify(args.locale)}` : null,
604
+ `Max results: ${Math.max(1, Math.min(20, Number(args.maxResults) || 10))}`,
605
+ '',
606
+ 'Return a short answer first, then cite useful results as title + URL + one-line snippet.',
607
+ 'Do not edit files.',
608
+ ].filter(Boolean)
609
+ return lines.join('\n')
610
+ }
611
+
612
+ async function _searchCore(args, { cacheState, agentSearch, signal }) {
613
+ const cacheArgs = searchArgsForCacheKey(args)
614
+ const searchCacheKey = buildCacheKey('search', {
615
+ provider: 'web-researcher',
616
+ ...cacheArgs,
617
+ })
618
+ const cachedSearch = getCachedEntry(cacheState, searchCacheKey)
619
+ if (cachedSearch) return { ...cachedSearch.payload, cache: buildCacheMeta(cachedSearch, true) }
620
+
621
+ const existing = _searchInFlight.get(searchCacheKey)
622
+ if (existing) return existing
623
+
624
+ const run = (async () => {
625
+ if (signal?.aborted) throw signal.reason || new Error('search aborted')
626
+ if (typeof agentSearch !== 'function') {
627
+ throw new Error('search provider unavailable: Web Researcher agent bridge is not attached')
628
+ }
629
+ const startedAt = Date.now()
630
+ const content = await agentSearch({
631
+ ...args,
632
+ ...cacheArgs,
633
+ prompt: buildAgentSearchPrompt({ ...args, ...cacheArgs }),
634
+ })
635
+ const answer = String(content || '').trim()
636
+ const payload = {
637
+ tool: 'search',
638
+ provider: 'web-researcher',
639
+ response: {
640
+ usedProvider: 'web-researcher',
641
+ query: Array.isArray(cacheArgs.keywords) ? cacheArgs.keywords.join('\n') : cacheArgs.keywords,
642
+ rawQuery: Array.isArray(cacheArgs.keywords) ? cacheArgs.keywords.join('\n') : cacheArgs.keywords,
643
+ answer,
644
+ model: null,
645
+ durationMs: Date.now() - startedAt,
646
+ usage: null,
647
+ results: [],
648
+ warnings: [],
649
+ type: cacheArgs.type,
650
+ site: cacheArgs.site,
651
+ locale: cacheArgs.locale,
652
+ },
653
+ }
654
+ const cachedEntry = setCachedEntry(cacheState, searchCacheKey, payload, getSearchCacheTtlMs(cacheArgs.type))
655
+ flushCacheState()
656
+ return { ...payload, cache: buildCacheMeta(cachedEntry, false) }
657
+ })()
658
+
659
+ run.catch(() => {})
660
+ _searchInFlight.set(searchCacheKey, run)
661
+ try {
662
+ return await run
663
+ } finally {
664
+ if (_searchInFlight.get(searchCacheKey) === run) _searchInFlight.delete(searchCacheKey)
665
+ }
666
+ }
667
+
668
+ const DEFAULT_FETCH_MAX_LENGTH = 50000
669
+ const FETCH_CACHE_VERSION = 'auto-render-js-fallback-v1'
670
+
671
+ // Apply character-level pagination to a cached or fresh fetch payload. Mirrors
672
+ // the mcp-server-fetch reference: caller passes startIndex/maxLength and
673
+ // receives a slice plus pointers (nextStartIndex, hasMore) for the next chunk.
674
+ // totalLength is preserved so the caller can decide whether to keep paging.
675
+ function applyFetchPagination(payload, args) {
676
+ const fullContent = String(payload?.content ?? '')
677
+ const totalLength = fullContent.length
678
+ const startIndex = Math.max(0, Number.isFinite(args?.startIndex) ? args.startIndex : 0)
679
+ const rawLimit = args?.maxLength
680
+ const limit = rawLimit === 0
681
+ ? Infinity
682
+ : (rawLimit == null ? DEFAULT_FETCH_MAX_LENGTH : Math.max(0, Number(rawLimit)))
683
+ if (startIndex >= totalLength) {
684
+ return {
685
+ ...payload,
686
+ content: '',
687
+ bytes: 0,
688
+ totalLength,
689
+ range: { startIndex, endIndex: startIndex },
690
+ hasMore: false,
691
+ nextStartIndex: null,
692
+ truncated: false,
693
+ }
694
+ }
695
+ const endIndex = Math.min(totalLength, startIndex + (Number.isFinite(limit) ? limit : totalLength - startIndex))
696
+ const slice = fullContent.slice(startIndex, endIndex)
697
+ const hasMore = endIndex < totalLength
698
+ return {
699
+ ...payload,
700
+ content: slice,
701
+ bytes: Buffer.byteLength(slice, 'utf-8'),
702
+ totalLength,
703
+ range: { startIndex, endIndex },
704
+ hasMore,
705
+ nextStartIndex: hasMore ? endIndex : null,
706
+ truncated: hasMore || startIndex > 0,
707
+ }
708
+ }
709
+
710
+ async function _fetchCore(args, { usageState, cacheState, timeoutMs, signal }) {
711
+ const FETCH_URL_CAP = Math.max(1, Number(process.env.FETCH_URL_CAP) || 10)
712
+ // Bound how many URLs scrape concurrently. Each non-cached URL can launch a
713
+ // Puppeteer browser; running all FETCH_URL_CAP (default 10) at once can spawn
714
+ // up to 10 Chromium processes simultaneously and exhaust memory/file handles.
715
+ const FETCH_CONCURRENCY = Math.max(1, Number(process.env.FETCH_CONCURRENCY) || 3)
716
+ const allUrls = Array.isArray(args.url) ? args.url : [args.url]
717
+ const urls = allUrls.slice(0, FETCH_URL_CAP)
718
+
719
+ const runOne = async (url, index) => {
720
+ const normalizedUrl = normalizeCacheUrl(url)
721
+ const fetchCacheKey = buildCacheKey('fetch:url', { url: normalizedUrl, version: FETCH_CACHE_VERSION })
722
+ const cached = getCachedEntry(cacheState, fetchCacheKey)
723
+ if (cached) {
724
+ return {
725
+ index: index + 1,
726
+ status: 'success',
727
+ ...applyFetchPagination(cached.payload, args),
728
+ cache: buildCacheMeta(cached, true),
729
+ }
730
+ }
731
+
732
+ try {
733
+ const [page] = await scrapeUrls([url], timeoutMs, usageState, signal)
734
+ if (page?.error) {
735
+ return {
736
+ index: index + 1,
737
+ status: 'error',
738
+ tool: 'web_fetch',
739
+ url,
740
+ error: page.error,
741
+ }
742
+ }
743
+ const payload = { tool: 'web_fetch', ...page }
744
+ const cachedEntry = setCachedEntry(cacheState, fetchCacheKey, payload, getScrapeCacheTtlMs(false))
745
+ return {
746
+ index: index + 1,
747
+ status: 'success',
748
+ ...applyFetchPagination(payload, args),
749
+ cache: buildCacheMeta(cachedEntry, false),
750
+ }
751
+ } catch (error) {
752
+ // Pre-extractor failures (e.g. assertPublicUrl in web-tools) throw
753
+ // before scrapeUrls returns a page-shaped error. Surface the raw
754
+ // message verbatim so the caller sees the actual cause rather than
755
+ // a silenced/swallowed result.
756
+ const message = error instanceof Error
757
+ ? (error.message || error.name || 'fetch failed')
758
+ : String(error)
759
+ const code = error?.code || error?.name || null
760
+ return {
761
+ index: index + 1,
762
+ status: 'error',
763
+ tool: 'web_fetch',
764
+ url,
765
+ error: message,
766
+ ...(code ? { errorCode: code } : {}),
767
+ }
768
+ }
769
+ }
770
+
771
+ // Bounded worker pool: at most FETCH_CONCURRENCY runOne() calls in flight.
772
+ const results = new Array(urls.length)
773
+ let next = 0
774
+ const worker = async () => {
775
+ while (next < urls.length) {
776
+ const i = next++
777
+ results[i] = await runOne(urls[i], i)
778
+ }
779
+ }
780
+ await Promise.all(
781
+ Array.from({ length: Math.min(FETCH_CONCURRENCY, urls.length) }, worker),
782
+ )
783
+
784
+ return { tool: 'web_fetch', results, urlsTruncated: allUrls.length > urls.length ? allUrls.length : 0 }
785
+ }
786
+
787
+ // Only `web_fetch` remains in the direct web module. Web search is routed
788
+ // through the Web Researcher agent, so there is no standalone search provider
789
+ // configuration or search backend selection surface.
790
+ import { TOOL_DEFS as toolDefinitions } from './tool-defs.mjs'
791
+
792
+ const SEARCH_INSTRUCTIONS = '';
793
+
794
+ const server = new Server(
795
+ {
796
+ name: 'mixdog-web',
797
+ version: PLUGIN_VERSION,
798
+ },
799
+ {
800
+ capabilities: {
801
+ tools: {},
802
+ },
803
+ instructions: SEARCH_INSTRUCTIONS,
804
+ },
805
+ )
806
+
807
+ server.setRequestHandler(ListToolsRequestSchema, async () => ({
808
+ tools: toolDefinitions.filter(t => t.public !== false),
809
+ }))
810
+
811
+ async function handleToolCall(name, rawArgs, options = {}) {
812
+ const { signal, agentSearch } = options || {}
813
+ const config = loadConfig()
814
+ const usageState = loadUsageState()
815
+ const cacheState = loadCacheState()
816
+ const timeoutMs = getRequestTimeoutMs(config)
817
+
818
+ switch (name) {
819
+ case 'search': {
820
+ let args
821
+ const rawAction = String(rawArgs?.action || 'run').trim().toLowerCase()
822
+ if (['list', 'status', 'read', 'cancel'].includes(rawAction)) {
823
+ return searchTaskControl(rawAction, rawArgs || {}, options)
824
+ }
825
+ if (rawArgs && rawArgs.pattern !== undefined && rawArgs.query === undefined && rawArgs.keywords === undefined) {
826
+ return { content: [{ type: 'text', text: 'Error: web search requires query; use glob(pattern=...) for file paths.' }], isError: true }
827
+ }
828
+ if (rawArgs && rawArgs.query !== undefined && rawArgs.keywords === undefined) {
829
+ rawArgs = { ...rawArgs, keywords: rawArgs.query }
830
+ delete rawArgs.query
831
+ }
832
+ try {
833
+ args = searchArgsSchema.parse(normalizeSearchArgs(rawArgs || {}))
834
+ } catch (e) {
835
+ if (e instanceof z.ZodError) {
836
+ return { content: [{ type: 'text', text: JSON.stringify({ error: 'Invalid arguments', details: e.errors }) }], isError: true }
837
+ }
838
+ throw e
839
+ }
840
+ const runSearchNow = async () => {
841
+ if (Array.isArray(args.keywords) && args.keywords.length > 1) {
842
+ const SEARCH_FANOUT_CAP = Math.max(1, Number(process.env.SEARCH_FANOUT_CAP) || 10)
843
+ const keywords = [...new Set(args.keywords.map(kw => String(kw || '').trim()).filter(Boolean))].slice(0, SEARCH_FANOUT_CAP)
844
+ const sections = await Promise.all(keywords.map(async (kw) => {
845
+ const sub = await handleToolCall('search', { ...rawArgs, keywords: kw, mode: 'sync', action: 'run' }, { signal, agentSearch })
846
+ const text = (sub.content || []).filter(p => p.type === 'text').map(p => p.text).join('\n')
847
+ return `### Query: ${kw}\n\n${text}`
848
+ }))
849
+ return { content: [{ type: 'text', text: sections.join('\n\n---\n\n') }] }
850
+ }
851
+ try {
852
+ const result = await _searchCore(args, { cacheState, agentSearch, signal })
853
+ flushUsageState()
854
+ return formattedText('search', result)
855
+ } catch (error) {
856
+ flushUsageState()
857
+ const _rawErr = normalizeErrorMessage(error instanceof Error ? error.message : String(error))
858
+ const _cleanErr = presentErrorText(_rawErr, { surface: 'search' })
859
+ return { content: [{ type: 'text', text: `Search failed: ${_cleanErr}` }], isError: true }
860
+ }
861
+ }
862
+ if (resolveExecutionMode(args, 'sync') === 'async') {
863
+ const label = Array.isArray(args.keywords)
864
+ ? args.keywords.join(' | ')
865
+ : String(args.keywords || '')
866
+ const task = startBackgroundTask({
867
+ surface: 'search',
868
+ operation: 'search',
869
+ label: label.replace(/\s+/g, ' ').slice(0, 120),
870
+ input: { keywords: args.keywords, site: args.site || null, type: args.type || 'web' },
871
+ context: options,
872
+ resultType: 'search_task_result',
873
+ renderResult: (text) => String(text || ''),
874
+ run: async () => {
875
+ const response = await runSearchNow()
876
+ const text = toolText(response)
877
+ if (response?.isError) throw new Error(text)
878
+ return text
879
+ },
880
+ })
881
+ return okText(renderBackgroundTask(task))
882
+ }
883
+ return runSearchNow()
884
+ }
885
+ case 'web_fetch': {
886
+ let urlArgs
887
+ try {
888
+ urlArgs = searchUrlArgsSchema.parse(normalizeSearchUrlArgs(rawArgs || {}))
889
+ } catch (e) {
890
+ if (e instanceof z.ZodError) {
891
+ return { content: [{ type: 'text', text: JSON.stringify({ error: 'Invalid arguments', details: e.errors }) }], isError: true }
892
+ }
893
+ throw e
894
+ }
895
+ try {
896
+ const result = await _fetchCore(urlArgs, { config, usageState, cacheState, timeoutMs, signal })
897
+ flushCacheState()
898
+ flushUsageState()
899
+ return {
900
+ ...formattedText('fetch', result),
901
+ ...(result.results.some(item => item.status === 'success') ? {} : { isError: true }),
902
+ }
903
+ } catch (error) {
904
+ flushUsageState()
905
+ const _rawErr = normalizeErrorMessage(error instanceof Error ? error.message : String(error))
906
+ const _cleanErr = presentErrorText(_rawErr, { surface: 'web_fetch' })
907
+ return { content: [{ type: 'text', text: `Fetch failed: ${_cleanErr}` }], isError: true }
908
+ }
909
+ }
910
+ default:
911
+ throw new Error(`Unknown tool: ${name}`)
912
+ }
913
+ }
914
+
915
+ server.setRequestHandler(CallToolRequestSchema, async (request, extra) => {
916
+ return handleToolCall(request.params.name, request.params.arguments, { signal: extra?.signal })
917
+ })
918
+
919
+ /* ── Module exports (used when imported by mixdog-unified) ── */
920
+ export { toolDefinitions as TOOL_DEFS }
921
+ export { SEARCH_INSTRUCTIONS as instructions }
922
+
923
+ export { handleToolCall }
924
+ export async function start() { await writeStartupSnapshot() }
925
+ export function stop() { flushUsageState(); flushCacheState() }