mindweave 0.0.1 → 2.1.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 (481) hide show
  1. package/LICENSE +190 -0
  2. package/README.md +171 -14
  3. package/dist/alternator/chassis/cache.js +47 -0
  4. package/dist/alternator/chassis/cache.js.map +1 -0
  5. package/dist/alternator/chassis/domRefs.js +53 -0
  6. package/dist/alternator/chassis/domRefs.js.map +1 -0
  7. package/dist/alternator/chassis/extractWorker.js +65 -0
  8. package/dist/alternator/chassis/extractWorker.js.map +1 -0
  9. package/dist/alternator/chassis/graph.js +221 -0
  10. package/dist/alternator/chassis/graph.js.map +1 -0
  11. package/dist/alternator/chassis/index.js +463 -0
  12. package/dist/alternator/chassis/index.js.map +1 -0
  13. package/dist/alternator/chassis/isolation.js +336 -0
  14. package/dist/alternator/chassis/isolation.js.map +1 -0
  15. package/dist/alternator/chassis/langCases.js +69 -0
  16. package/dist/alternator/chassis/langCases.js.map +1 -0
  17. package/dist/alternator/chassis/lsp.js +469 -0
  18. package/dist/alternator/chassis/lsp.js.map +1 -0
  19. package/dist/alternator/chassis/markup.js +262 -0
  20. package/dist/alternator/chassis/markup.js.map +1 -0
  21. package/dist/alternator/chassis/provision.js +198 -0
  22. package/dist/alternator/chassis/provision.js.map +1 -0
  23. package/dist/alternator/chassis/rank.js +72 -0
  24. package/dist/alternator/chassis/rank.js.map +1 -0
  25. package/dist/alternator/chassis/servers.js +215 -0
  26. package/dist/alternator/chassis/servers.js.map +1 -0
  27. package/dist/alternator/chassis/treesitter.js +608 -0
  28. package/dist/alternator/chassis/treesitter.js.map +1 -0
  29. package/dist/alternator/chassis/types.js +24 -0
  30. package/dist/alternator/chassis/types.js.map +1 -0
  31. package/dist/alternator/lane.js +67 -0
  32. package/dist/alternator/lane.js.map +1 -0
  33. package/dist/cli/App.js +2586 -0
  34. package/dist/cli/App.js.map +1 -0
  35. package/dist/cli/altScreen.js +67 -0
  36. package/dist/cli/altScreen.js.map +1 -0
  37. package/dist/cli/approvalChannel.js +72 -0
  38. package/dist/cli/approvalChannel.js.map +1 -0
  39. package/dist/cli/attachments.js +188 -0
  40. package/dist/cli/attachments.js.map +1 -0
  41. package/dist/cli/bootstrap.js +279 -0
  42. package/dist/cli/bootstrap.js.map +1 -0
  43. package/dist/cli/chatAnchor.js +94 -0
  44. package/dist/cli/chatAnchor.js.map +1 -0
  45. package/dist/cli/commandArgs.js +79 -0
  46. package/dist/cli/commandArgs.js.map +1 -0
  47. package/dist/cli/commandRoute.js +78 -0
  48. package/dist/cli/commandRoute.js.map +1 -0
  49. package/dist/cli/compaction.js +69 -0
  50. package/dist/cli/compaction.js.map +1 -0
  51. package/dist/cli/components/ApprovalBox.js +100 -0
  52. package/dist/cli/components/ApprovalBox.js.map +1 -0
  53. package/dist/cli/components/BlockView.js +128 -0
  54. package/dist/cli/components/BlockView.js.map +1 -0
  55. package/dist/cli/components/FirstRunFrame.js +41 -0
  56. package/dist/cli/components/FirstRunFrame.js.map +1 -0
  57. package/dist/cli/components/KeyManager.js +197 -0
  58. package/dist/cli/components/KeyManager.js.map +1 -0
  59. package/dist/cli/components/KeySetup.js +125 -0
  60. package/dist/cli/components/KeySetup.js.map +1 -0
  61. package/dist/cli/components/MenuFrame.js +24 -0
  62. package/dist/cli/components/MenuFrame.js.map +1 -0
  63. package/dist/cli/components/Picker.js +82 -0
  64. package/dist/cli/components/Picker.js.map +1 -0
  65. package/dist/cli/components/PromptInput.js +509 -0
  66. package/dist/cli/components/PromptInput.js.map +1 -0
  67. package/dist/cli/components/SubagentView.js +86 -0
  68. package/dist/cli/components/SubagentView.js.map +1 -0
  69. package/dist/cli/components/ToolGroup.js +60 -0
  70. package/dist/cli/components/ToolGroup.js.map +1 -0
  71. package/dist/cli/components/ToolLine.js +123 -0
  72. package/dist/cli/components/ToolLine.js.map +1 -0
  73. package/dist/cli/components/TrustGate.js +37 -0
  74. package/dist/cli/components/TrustGate.js.map +1 -0
  75. package/dist/cli/costView.js +40 -0
  76. package/dist/cli/costView.js.map +1 -0
  77. package/dist/cli/frameRate.js +30 -0
  78. package/dist/cli/frameRate.js.map +1 -0
  79. package/dist/cli/framebuffer/paint.js +165 -0
  80. package/dist/cli/framebuffer/paint.js.map +1 -0
  81. package/dist/cli/framebuffer/parse.js +266 -0
  82. package/dist/cli/framebuffer/parse.js.map +1 -0
  83. package/dist/cli/framebuffer/screen.js +196 -0
  84. package/dist/cli/framebuffer/screen.js.map +1 -0
  85. package/dist/cli/framebuffer/writer.js +139 -0
  86. package/dist/cli/framebuffer/writer.js.map +1 -0
  87. package/dist/cli/groupReveal.js +51 -0
  88. package/dist/cli/groupReveal.js.map +1 -0
  89. package/dist/cli/help.js +55 -0
  90. package/dist/cli/help.js.map +1 -0
  91. package/dist/cli/inputView.js +105 -0
  92. package/dist/cli/inputView.js.map +1 -0
  93. package/dist/cli/keyManager.js +65 -0
  94. package/dist/cli/keyManager.js.map +1 -0
  95. package/dist/cli/keySetup.js +35 -0
  96. package/dist/cli/keySetup.js.map +1 -0
  97. package/dist/cli/keyStore.js +73 -0
  98. package/dist/cli/keyStore.js.map +1 -0
  99. package/dist/cli/markdown.js +460 -0
  100. package/dist/cli/markdown.js.map +1 -0
  101. package/dist/cli/messageQueue.js +96 -0
  102. package/dist/cli/messageQueue.js.map +1 -0
  103. package/dist/cli/modes.js +90 -0
  104. package/dist/cli/modes.js.map +1 -0
  105. package/dist/cli/mouse.js +78 -0
  106. package/dist/cli/mouse.js.map +1 -0
  107. package/dist/cli/pasteAssembler.js +44 -0
  108. package/dist/cli/pasteAssembler.js.map +1 -0
  109. package/dist/cli/pathComplete.js +39 -0
  110. package/dist/cli/pathComplete.js.map +1 -0
  111. package/dist/cli/perfLog.js +90 -0
  112. package/dist/cli/perfLog.js.map +1 -0
  113. package/dist/cli/reveal.js +32 -0
  114. package/dist/cli/reveal.js.map +1 -0
  115. package/dist/cli/revealPace.js +59 -0
  116. package/dist/cli/revealPace.js.map +1 -0
  117. package/dist/cli/sessionCarry.js +19 -0
  118. package/dist/cli/sessionCarry.js.map +1 -0
  119. package/dist/cli/smoothScroll.js +74 -0
  120. package/dist/cli/smoothScroll.js.map +1 -0
  121. package/dist/cli/startupArgs.js +96 -0
  122. package/dist/cli/startupArgs.js.map +1 -0
  123. package/dist/cli/terminalRestore.js +34 -0
  124. package/dist/cli/terminalRestore.js.map +1 -0
  125. package/dist/cli/toolDisplay.js +219 -0
  126. package/dist/cli/toolDisplay.js.map +1 -0
  127. package/dist/cli/toolItems.js +65 -0
  128. package/dist/cli/toolItems.js.map +1 -0
  129. package/dist/cli/transcript.js +351 -0
  130. package/dist/cli/transcript.js.map +1 -0
  131. package/dist/cli/trust.js +79 -0
  132. package/dist/cli/trust.js.map +1 -0
  133. package/dist/cli/updateCheck.js +107 -0
  134. package/dist/cli/updateCheck.js.map +1 -0
  135. package/dist/cli/version.js +39 -0
  136. package/dist/cli/version.js.map +1 -0
  137. package/dist/cli/viewport.js +179 -0
  138. package/dist/cli/viewport.js.map +1 -0
  139. package/dist/cli/virtualWindow.js +103 -0
  140. package/dist/cli/virtualWindow.js.map +1 -0
  141. package/dist/cli/workingVerb.js +37 -0
  142. package/dist/cli/workingVerb.js.map +1 -0
  143. package/dist/cli/wrap.js +145 -0
  144. package/dist/cli/wrap.js.map +1 -0
  145. package/dist/drivers/anthropic/cachePoints.js +77 -0
  146. package/dist/drivers/anthropic/cachePoints.js.map +1 -0
  147. package/dist/drivers/anthropic/client.js +432 -0
  148. package/dist/drivers/anthropic/client.js.map +1 -0
  149. package/dist/drivers/anthropic/index.js +10 -0
  150. package/dist/drivers/anthropic/index.js.map +1 -0
  151. package/dist/drivers/anthropic/manifest.js +221 -0
  152. package/dist/drivers/anthropic/manifest.js.map +1 -0
  153. package/dist/drivers/cerebras/client.js +69 -0
  154. package/dist/drivers/cerebras/client.js.map +1 -0
  155. package/dist/drivers/cerebras/index.js +5 -0
  156. package/dist/drivers/cerebras/index.js.map +1 -0
  157. package/dist/drivers/cerebras/manifest.js +140 -0
  158. package/dist/drivers/cerebras/manifest.js.map +1 -0
  159. package/dist/drivers/clientId.js +41 -0
  160. package/dist/drivers/clientId.js.map +1 -0
  161. package/dist/drivers/contextOverflow.js +77 -0
  162. package/dist/drivers/contextOverflow.js.map +1 -0
  163. package/dist/drivers/deepseek/client.js +168 -0
  164. package/dist/drivers/deepseek/client.js.map +1 -0
  165. package/dist/drivers/deepseek/index.js +16 -0
  166. package/dist/drivers/deepseek/index.js.map +1 -0
  167. package/dist/drivers/deepseek/inlineTools.js +46 -0
  168. package/dist/drivers/deepseek/inlineTools.js.map +1 -0
  169. package/dist/drivers/deepseek/manifest.js +166 -0
  170. package/dist/drivers/deepseek/manifest.js.map +1 -0
  171. package/dist/drivers/gemini/client.js +38 -0
  172. package/dist/drivers/gemini/client.js.map +1 -0
  173. package/dist/drivers/gemini/index.js +5 -0
  174. package/dist/drivers/gemini/index.js.map +1 -0
  175. package/dist/drivers/gemini/manifest.js +150 -0
  176. package/dist/drivers/gemini/manifest.js.map +1 -0
  177. package/dist/drivers/glm/client.js +90 -0
  178. package/dist/drivers/glm/client.js.map +1 -0
  179. package/dist/drivers/glm/index.js +9 -0
  180. package/dist/drivers/glm/index.js.map +1 -0
  181. package/dist/drivers/glm/manifest.js +183 -0
  182. package/dist/drivers/glm/manifest.js.map +1 -0
  183. package/dist/drivers/groq/client.js +80 -0
  184. package/dist/drivers/groq/client.js.map +1 -0
  185. package/dist/drivers/groq/index.js +5 -0
  186. package/dist/drivers/groq/index.js.map +1 -0
  187. package/dist/drivers/groq/manifest.js +160 -0
  188. package/dist/drivers/groq/manifest.js.map +1 -0
  189. package/dist/drivers/kimi/client.js +82 -0
  190. package/dist/drivers/kimi/client.js.map +1 -0
  191. package/dist/drivers/kimi/index.js +9 -0
  192. package/dist/drivers/kimi/index.js.map +1 -0
  193. package/dist/drivers/kimi/manifest.js +168 -0
  194. package/dist/drivers/kimi/manifest.js.map +1 -0
  195. package/dist/drivers/meta/client.js +30 -0
  196. package/dist/drivers/meta/client.js.map +1 -0
  197. package/dist/drivers/meta/index.js +5 -0
  198. package/dist/drivers/meta/index.js.map +1 -0
  199. package/dist/drivers/meta/manifest.js +101 -0
  200. package/dist/drivers/meta/manifest.js.map +1 -0
  201. package/dist/drivers/minimax/client.js +36 -0
  202. package/dist/drivers/minimax/client.js.map +1 -0
  203. package/dist/drivers/minimax/index.js +5 -0
  204. package/dist/drivers/minimax/index.js.map +1 -0
  205. package/dist/drivers/minimax/manifest.js +120 -0
  206. package/dist/drivers/minimax/manifest.js.map +1 -0
  207. package/dist/drivers/mistral/client.js +54 -0
  208. package/dist/drivers/mistral/client.js.map +1 -0
  209. package/dist/drivers/mistral/index.js +5 -0
  210. package/dist/drivers/mistral/index.js.map +1 -0
  211. package/dist/drivers/mistral/manifest.js +118 -0
  212. package/dist/drivers/mistral/manifest.js.map +1 -0
  213. package/dist/drivers/openai/client.js +290 -0
  214. package/dist/drivers/openai/client.js.map +1 -0
  215. package/dist/drivers/openai/index.js +9 -0
  216. package/dist/drivers/openai/index.js.map +1 -0
  217. package/dist/drivers/openai/manifest.js +133 -0
  218. package/dist/drivers/openai/manifest.js.map +1 -0
  219. package/dist/drivers/openaiCompat/wire.js +493 -0
  220. package/dist/drivers/openaiCompat/wire.js.map +1 -0
  221. package/dist/drivers/partialTurn.js +23 -0
  222. package/dist/drivers/partialTurn.js.map +1 -0
  223. package/dist/drivers/providerError.js +181 -0
  224. package/dist/drivers/providerError.js.map +1 -0
  225. package/dist/drivers/qwen/client.js +93 -0
  226. package/dist/drivers/qwen/client.js.map +1 -0
  227. package/dist/drivers/qwen/index.js +9 -0
  228. package/dist/drivers/qwen/index.js.map +1 -0
  229. package/dist/drivers/qwen/manifest.js +146 -0
  230. package/dist/drivers/qwen/manifest.js.map +1 -0
  231. package/dist/drivers/registry.js +177 -0
  232. package/dist/drivers/registry.js.map +1 -0
  233. package/dist/drivers/retryPolicy.js +129 -0
  234. package/dist/drivers/retryPolicy.js.map +1 -0
  235. package/dist/drivers/searchBlocks.js +61 -0
  236. package/dist/drivers/searchBlocks.js.map +1 -0
  237. package/dist/drivers/types.js +2 -0
  238. package/dist/drivers/types.js.map +1 -0
  239. package/dist/drivers/xai/client.js +63 -0
  240. package/dist/drivers/xai/client.js.map +1 -0
  241. package/dist/drivers/xai/index.js +5 -0
  242. package/dist/drivers/xai/index.js.map +1 -0
  243. package/dist/drivers/xai/manifest.js +137 -0
  244. package/dist/drivers/xai/manifest.js.map +1 -0
  245. package/dist/dynamo/_probe.tmp.js +20 -0
  246. package/dist/dynamo/_probe.tmp.js.map +1 -0
  247. package/dist/dynamo/cacheBreak.js +88 -0
  248. package/dist/dynamo/cacheBreak.js.map +1 -0
  249. package/dist/dynamo/contextWindow.js +243 -0
  250. package/dist/dynamo/contextWindow.js.map +1 -0
  251. package/dist/dynamo/engine.js +2011 -0
  252. package/dist/dynamo/engine.js.map +1 -0
  253. package/dist/dynamo/guard.js +132 -0
  254. package/dist/dynamo/guard.js.map +1 -0
  255. package/dist/dynamo/liveMeter.js +58 -0
  256. package/dist/dynamo/liveMeter.js.map +1 -0
  257. package/dist/dynamo/model.js +172 -0
  258. package/dist/dynamo/model.js.map +1 -0
  259. package/dist/dynamo/planArtifact.js +125 -0
  260. package/dist/dynamo/planArtifact.js.map +1 -0
  261. package/dist/dynamo/pricing.js +140 -0
  262. package/dist/dynamo/pricing.js.map +1 -0
  263. package/dist/dynamo/prompt.js +264 -0
  264. package/dist/dynamo/prompt.js.map +1 -0
  265. package/dist/dynamo/spend.js +45 -0
  266. package/dist/dynamo/spend.js.map +1 -0
  267. package/dist/dynamo/verify.js +483 -0
  268. package/dist/dynamo/verify.js.map +1 -0
  269. package/dist/governor/forbidden.js +181 -0
  270. package/dist/governor/forbidden.js.map +1 -0
  271. package/dist/governor/freshness.js +83 -0
  272. package/dist/governor/freshness.js.map +1 -0
  273. package/dist/governor/frontmatter.js +38 -0
  274. package/dist/governor/frontmatter.js.map +1 -0
  275. package/dist/governor/glob.js +75 -0
  276. package/dist/governor/glob.js.map +1 -0
  277. package/dist/governor/index.js +87 -0
  278. package/dist/governor/index.js.map +1 -0
  279. package/dist/governor/rules.js +80 -0
  280. package/dist/governor/rules.js.map +1 -0
  281. package/dist/governor/scope.js +91 -0
  282. package/dist/governor/scope.js.map +1 -0
  283. package/dist/governor/skills.js +176 -0
  284. package/dist/governor/skills.js.map +1 -0
  285. package/dist/governor/types.js +16 -0
  286. package/dist/governor/types.js.map +1 -0
  287. package/dist/governor/write.js +182 -0
  288. package/dist/governor/write.js.map +1 -0
  289. package/dist/index.js +89 -0
  290. package/dist/index.js.map +1 -0
  291. package/dist/mcp/catalog.js +232 -0
  292. package/dist/mcp/catalog.js.map +1 -0
  293. package/dist/mcp/config.js +116 -0
  294. package/dist/mcp/config.js.map +1 -0
  295. package/dist/mcp/configWrite.js +254 -0
  296. package/dist/mcp/configWrite.js.map +1 -0
  297. package/dist/mcp/connection.js +504 -0
  298. package/dist/mcp/connection.js.map +1 -0
  299. package/dist/mcp/deferred.js +104 -0
  300. package/dist/mcp/deferred.js.map +1 -0
  301. package/dist/mcp/discover.js +128 -0
  302. package/dist/mcp/discover.js.map +1 -0
  303. package/dist/mcp/manager.js +679 -0
  304. package/dist/mcp/manager.js.map +1 -0
  305. package/dist/mcp/paramHeaders.js +163 -0
  306. package/dist/mcp/paramHeaders.js.map +1 -0
  307. package/dist/mcp/prompts.js +136 -0
  308. package/dist/mcp/prompts.js.map +1 -0
  309. package/dist/mcp/protocol.js +171 -0
  310. package/dist/mcp/protocol.js.map +1 -0
  311. package/dist/mcp/resources.js +119 -0
  312. package/dist/mcp/resources.js.map +1 -0
  313. package/dist/mcp/resultStore.js +180 -0
  314. package/dist/mcp/resultStore.js.map +1 -0
  315. package/dist/mcp/subscriptions.js +74 -0
  316. package/dist/mcp/subscriptions.js.map +1 -0
  317. package/dist/mcp/transport/headerValue.js +40 -0
  318. package/dist/mcp/transport/headerValue.js.map +1 -0
  319. package/dist/mcp/transport/http.js +321 -0
  320. package/dist/mcp/transport/http.js.map +1 -0
  321. package/dist/mcp/transport/stdio.js +234 -0
  322. package/dist/mcp/transport/stdio.js.map +1 -0
  323. package/dist/mcp/transport/types.js +27 -0
  324. package/dist/mcp/transport/types.js.map +1 -0
  325. package/dist/mcp/trust.js +98 -0
  326. package/dist/mcp/trust.js.map +1 -0
  327. package/dist/mcp/trustStore.js +55 -0
  328. package/dist/mcp/trustStore.js.map +1 -0
  329. package/dist/memory/autoMemory.js +340 -0
  330. package/dist/memory/autoMemory.js.map +1 -0
  331. package/dist/memory/compaction.js +513 -0
  332. package/dist/memory/compaction.js.map +1 -0
  333. package/dist/memory/images.js +173 -0
  334. package/dist/memory/images.js.map +1 -0
  335. package/dist/memory/presence.js +59 -0
  336. package/dist/memory/presence.js.map +1 -0
  337. package/dist/memory/projectNotes.js +247 -0
  338. package/dist/memory/projectNotes.js.map +1 -0
  339. package/dist/memory/restore.js +72 -0
  340. package/dist/memory/restore.js.map +1 -0
  341. package/dist/memory/session.js +472 -0
  342. package/dist/memory/session.js.map +1 -0
  343. package/dist/memory/sessionMemory.js +142 -0
  344. package/dist/memory/sessionMemory.js.map +1 -0
  345. package/dist/memory/sessionMemoryCompact.js +136 -0
  346. package/dist/memory/sessionMemoryCompact.js.map +1 -0
  347. package/dist/memory/store.js +217 -0
  348. package/dist/memory/store.js.map +1 -0
  349. package/dist/memory/types.js +14 -0
  350. package/dist/memory/types.js.map +1 -0
  351. package/dist/memory/workingSet.js +383 -0
  352. package/dist/memory/workingSet.js.map +1 -0
  353. package/dist/project/context.js +425 -0
  354. package/dist/project/context.js.map +1 -0
  355. package/dist/tools/approval.js +189 -0
  356. package/dist/tools/approval.js.map +1 -0
  357. package/dist/tools/askUser.js +103 -0
  358. package/dist/tools/askUser.js.map +1 -0
  359. package/dist/tools/atomicWrite.js +151 -0
  360. package/dist/tools/atomicWrite.js.map +1 -0
  361. package/dist/tools/backgroundShells.js +468 -0
  362. package/dist/tools/backgroundShells.js.map +1 -0
  363. package/dist/tools/captureSweep.js +77 -0
  364. package/dist/tools/captureSweep.js.map +1 -0
  365. package/dist/tools/chassisMux.js +92 -0
  366. package/dist/tools/chassisMux.js.map +1 -0
  367. package/dist/tools/checkpoints.js +328 -0
  368. package/dist/tools/checkpoints.js.map +1 -0
  369. package/dist/tools/codeIntel.js +267 -0
  370. package/dist/tools/codeIntel.js.map +1 -0
  371. package/dist/tools/deferredNative.js +121 -0
  372. package/dist/tools/deferredNative.js.map +1 -0
  373. package/dist/tools/detail.js +135 -0
  374. package/dist/tools/detail.js.map +1 -0
  375. package/dist/tools/diagnostics.js +174 -0
  376. package/dist/tools/diagnostics.js.map +1 -0
  377. package/dist/tools/edit.js +167 -0
  378. package/dist/tools/edit.js.map +1 -0
  379. package/dist/tools/editCore.js +283 -0
  380. package/dist/tools/editCore.js.map +1 -0
  381. package/dist/tools/editFile.js +183 -0
  382. package/dist/tools/editFile.js.map +1 -0
  383. package/dist/tools/editRipple.js +126 -0
  384. package/dist/tools/editRipple.js.map +1 -0
  385. package/dist/tools/editTarget.js +131 -0
  386. package/dist/tools/editTarget.js.map +1 -0
  387. package/dist/tools/editWindow.js +49 -0
  388. package/dist/tools/editWindow.js.map +1 -0
  389. package/dist/tools/eol.js +56 -0
  390. package/dist/tools/eol.js.map +1 -0
  391. package/dist/tools/exitPlan.js +175 -0
  392. package/dist/tools/exitPlan.js.map +1 -0
  393. package/dist/tools/focus.js +42 -0
  394. package/dist/tools/focus.js.map +1 -0
  395. package/dist/tools/gitignore.js +148 -0
  396. package/dist/tools/gitignore.js.map +1 -0
  397. package/dist/tools/glob.js +134 -0
  398. package/dist/tools/glob.js.map +1 -0
  399. package/dist/tools/governorTools.js +258 -0
  400. package/dist/tools/governorTools.js.map +1 -0
  401. package/dist/tools/grep.js +450 -0
  402. package/dist/tools/grep.js.map +1 -0
  403. package/dist/tools/guard.js +220 -0
  404. package/dist/tools/guard.js.map +1 -0
  405. package/dist/tools/killTree.js +215 -0
  406. package/dist/tools/killTree.js.map +1 -0
  407. package/dist/tools/listDir.js +143 -0
  408. package/dist/tools/listDir.js.map +1 -0
  409. package/dist/tools/mcpAdd.js +176 -0
  410. package/dist/tools/mcpAdd.js.map +1 -0
  411. package/dist/tools/mcpResources.js +116 -0
  412. package/dist/tools/mcpResources.js.map +1 -0
  413. package/dist/tools/mcpSearch.js +123 -0
  414. package/dist/tools/mcpSearch.js.map +1 -0
  415. package/dist/tools/multiEdit.js +168 -0
  416. package/dist/tools/multiEdit.js.map +1 -0
  417. package/dist/tools/paths.js +225 -0
  418. package/dist/tools/paths.js.map +1 -0
  419. package/dist/tools/posixShell.js +123 -0
  420. package/dist/tools/posixShell.js.map +1 -0
  421. package/dist/tools/readFile.js +371 -0
  422. package/dist/tools/readFile.js.map +1 -0
  423. package/dist/tools/readSymbol.js +145 -0
  424. package/dist/tools/readSymbol.js.map +1 -0
  425. package/dist/tools/registry.js +120 -0
  426. package/dist/tools/registry.js.map +1 -0
  427. package/dist/tools/replaceSymbol.js +141 -0
  428. package/dist/tools/replaceSymbol.js.map +1 -0
  429. package/dist/tools/results.js +15 -0
  430. package/dist/tools/results.js.map +1 -0
  431. package/dist/tools/ripgrep.js +145 -0
  432. package/dist/tools/ripgrep.js.map +1 -0
  433. package/dist/tools/runCommand.js +633 -0
  434. package/dist/tools/runCommand.js.map +1 -0
  435. package/dist/tools/saveMemory.js +102 -0
  436. package/dist/tools/saveMemory.js.map +1 -0
  437. package/dist/tools/screenshot.js +200 -0
  438. package/dist/tools/screenshot.js.map +1 -0
  439. package/dist/tools/screenshotWin.js +227 -0
  440. package/dist/tools/screenshotWin.js.map +1 -0
  441. package/dist/tools/search.js +121 -0
  442. package/dist/tools/search.js.map +1 -0
  443. package/dist/tools/sessionTools.js +187 -0
  444. package/dist/tools/sessionTools.js.map +1 -0
  445. package/dist/tools/shellCheckpoint.js +123 -0
  446. package/dist/tools/shellCheckpoint.js.map +1 -0
  447. package/dist/tools/shellLint.js +102 -0
  448. package/dist/tools/shellLint.js.map +1 -0
  449. package/dist/tools/shellTools.js +203 -0
  450. package/dist/tools/shellTools.js.map +1 -0
  451. package/dist/tools/spanCore.js +78 -0
  452. package/dist/tools/spanCore.js.map +1 -0
  453. package/dist/tools/subagent.js +224 -0
  454. package/dist/tools/subagent.js.map +1 -0
  455. package/dist/tools/subagentReport.js +114 -0
  456. package/dist/tools/subagentReport.js.map +1 -0
  457. package/dist/tools/tempSweep.js +118 -0
  458. package/dist/tools/tempSweep.js.map +1 -0
  459. package/dist/tools/todo.js +117 -0
  460. package/dist/tools/todo.js.map +1 -0
  461. package/dist/tools/types.js +2 -0
  462. package/dist/tools/types.js.map +1 -0
  463. package/dist/tools/untrusted.js +46 -0
  464. package/dist/tools/untrusted.js.map +1 -0
  465. package/dist/tools/useSkill.js +62 -0
  466. package/dist/tools/useSkill.js.map +1 -0
  467. package/dist/tools/walk.js +152 -0
  468. package/dist/tools/walk.js.map +1 -0
  469. package/dist/tools/web.js +61 -0
  470. package/dist/tools/web.js.map +1 -0
  471. package/dist/tools/webFetch.js +444 -0
  472. package/dist/tools/webFetch.js.map +1 -0
  473. package/dist/tools/webSearch.js +130 -0
  474. package/dist/tools/webSearch.js.map +1 -0
  475. package/dist/tools/workspace.js +212 -0
  476. package/dist/tools/workspace.js.map +1 -0
  477. package/dist/tools/workspaceDiscover.js +216 -0
  478. package/dist/tools/workspaceDiscover.js.map +1 -0
  479. package/dist/tools/writeFile.js +162 -0
  480. package/dist/tools/writeFile.js.map +1 -0
  481. package/package.json +74 -28
@@ -0,0 +1,468 @@
1
+ /**
2
+ * backgroundShells.ts — long-running commands that outlive a turn.
3
+ *
4
+ * When a command crosses its timeout (or the model asks for `run_in_background`),
5
+ * run_command hands the LIVE process to this manager instead of killing it. The
6
+ * manager owns the registry of background shells per session, buffers their output
7
+ * (capped, so a chatty dev server never floods memory or the model's context), and
8
+ * exposes:
9
+ *
10
+ * - `read(id)` — only the NEW output since the last read (incremental).
11
+ * - `kill(id)` — whole-tree kill.
12
+ * - `list()` — running + finished shells (for the UI and /shells).
13
+ *
14
+ * Two ONE-SHOT, self-cleaning event channels keep notifications from leaking
15
+ * (avoiding the common footgun where finished jobs re-inject into the model forever):
16
+ * - `takeUiEvents()` — shells that came up or stopped, not yet shown in the chat.
17
+ * - `drainEvents()` — the same for the MODEL, each with a tail of output, so it is
18
+ * told once and then never again.
19
+ *
20
+ * Every event is delivered. What varies is whether it INTERRUPTS the session: a stop
21
+ * the user caused arrives as background fact on the next turn rather than waking the
22
+ * model, which is what stops it reopening an app somebody just closed.
23
+ *
24
+ * Client-side, like the alternator lanes: it holds live process handles, never
25
+ * crosses the engine↔brain wire. All children are killed on process exit.
26
+ */
27
+ import { promises as fs } from "node:fs";
28
+ import { killTree, killTreeSync } from "./killTree.js";
29
+ const MAX_BUFFER_CHARS = 5_000_000; // cap one shell's retained output (runaway server)
30
+ export const MAX_READ_CHARS = 30_000; // cap a single `shells` read
31
+ const TAIL_CHARS = 2_000; // how much trailing output rides on a completion note
32
+ /**
33
+ * How long a server has to stay up before we treat its death as "someone stopped it"
34
+ * rather than "it failed to start".
35
+ *
36
+ * This is the one honest way to tell the two apart, because the exit status cannot:
37
+ * measured on Windows, a user closing an app reports `code 1`, and so does a server
38
+ * that crashed because its port was taken. Duration separates them cleanly — a port
39
+ * conflict dies in under a second, a session you close has been up for minutes.
40
+ *
41
+ * Borrowed from process supervisors, which hit this decades ago: supervisord counts a
42
+ * program as failed-to-start if it exits before `startsecs` (default 1s) regardless of
43
+ * its exit code. 10s is deliberately generous, since a dev server can take several
44
+ * seconds to bind a port and fail.
45
+ */
46
+ const STARTUP_GRACE_MS = 10_000;
47
+ /**
48
+ * How long to wait after `exit` for `close` before finalizing anyway.
49
+ *
50
+ * `close` fires only once every stdio stream is closed, and a surviving grandchild can
51
+ * hold the pipe open forever, which strands the entry as permanently "running".
52
+ * `exit` fires when the process itself goes, so it is the backstop; the delay lets
53
+ * `close` win normally so buffered output is not lost.
54
+ */
55
+ const EXIT_GRACE_MS = 2_000;
56
+ /**
57
+ * Guess a notify policy from the command, for callers that did not declare one.
58
+ *
59
+ * This is a FALLBACK, not the decision. The policy is declared at call time; this only
60
+ * picks a default when nothing was said, so a caller that forgets does not regress to
61
+ * "reopen the app the user just closed". Being a list of names, it is wrong for
62
+ * everything nobody thought of (`cargo run`, `docker compose up`, `flask run`, a plain
63
+ * path to a binary) — which is exactly why it is no longer the authority.
64
+ */
65
+ export function guessNotifyPolicy(command) {
66
+ return isInteractiveServerCommand(command) ? "on_failure" : "on_finish";
67
+ }
68
+ /**
69
+ * Is this command a dev server / interactive app — something that runs until stopped,
70
+ * where "it exited" means the USER closed it, NOT that a task finished? (pure/tested)
71
+ *
72
+ * Only used now to pick a default (see `guessNotifyPolicy`). A finite task (build,
73
+ * test, lint) that finishes IS a result worth surfacing, but a dev server exiting is
74
+ * just the user closing their app, and reacting to it makes the model reopen the thing
75
+ * they just closed. `build` variants are finite tasks, so they're excluded even though
76
+ * they share a runner name.
77
+ */
78
+ export function isInteractiveServerCommand(command) {
79
+ const c = command.toLowerCase();
80
+ if (/\bbuild\b/.test(c))
81
+ return false; // `next build`, `tauri build`, `vite build` — finite
82
+ // Package-runner dev/serve/start/preview scripts: `npm run dev`, `pnpm start`, `yarn serve`.
83
+ if (/\b(npm|pnpm|yarn|bun)\b[^\n]*\b(dev|serve|start|preview)\b/.test(c))
84
+ return true;
85
+ // Dev servers / desktop-app runners invoked directly.
86
+ return /\b(tauri|vite|next|nuxt|remix|astro|nodemon|electron|expo|ng|http-server|live-server|serve|webpack-dev-server|watchexec)\b/.test(c);
87
+ }
88
+ /**
89
+ * Should a finished shell INTERRUPT the user with a turn? (pure/tested)
90
+ *
91
+ * Note the narrow question. This does NOT decide whether the model is told: it is
92
+ * always told (see `drainEvents`). Swallowing the event was the real defect — the
93
+ * model could not say "your app stopped", and if asked why the app was down it had
94
+ * nothing. This decides only whether the stop is worth breaking into the session for.
95
+ *
96
+ * The rule, in the user's words: don't reopen something they closed, unless it
97
+ * crashed before they ever got to see it.
98
+ *
99
+ * - `never` → nothing is ever worth interrupting for
100
+ * - somebody killed it → the agent or the user did that on purpose, so they know
101
+ * - `on_finish` → the result is the point, always interrupt
102
+ * - a signal ended it → someone stopped it deliberately
103
+ * - otherwise → interrupt ONLY if it never came up, because then the user never saw
104
+ * it running and cannot know it failed
105
+ *
106
+ * Deliberately NOT consulted: the exit code and the duration. Exit status cannot tell
107
+ * these cases apart — measured on Windows, a closed app and a port conflict both report
108
+ * code 1, and a signalled process reports none at all. `cameUp` is the fact that
109
+ * actually separates them, and it is established in ONE place (the readiness timer)
110
+ * rather than recomputed here from a second set of numbers.
111
+ */
112
+ export function shouldWakeOnEnd(end) {
113
+ if (end.notify === "never")
114
+ return false;
115
+ if (end.killed)
116
+ return false;
117
+ if (end.notify === "on_finish")
118
+ return true;
119
+ if (end.signal)
120
+ return false;
121
+ return !end.cameUp;
122
+ }
123
+ /**
124
+ * Is `command` already running as one of these shells? (pure/tested) Matches on the
125
+ * normalized command string, so launching the very same server a second time is caught
126
+ * — the failure where the model fires `npm run tauri dev` twice, the copies collide on
127
+ * the port, and it then fights the conflict it created. Distinct servers (a frontend and
128
+ * a backend) don't match each other, so running both is still fine.
129
+ */
130
+ export function findRunningDuplicate(running, command) {
131
+ const norm = (s) => s.toLowerCase().replace(/\s+/g, " ").trim();
132
+ const target = norm(command);
133
+ return running.find((s) => norm(s.command) === target);
134
+ }
135
+ /** How long after a user closes an app a re-launch of the same command is refused. Long
136
+ * enough to break the close→reopen loop that plays out over a turn or two; short enough
137
+ * that a restart the user genuinely asks for a while later is not held back. */
138
+ export const REOPEN_COOLDOWN_MS = 2 * 60 * 1000;
139
+ /**
140
+ * Was `command` an app the USER just closed? (pure/tested)
141
+ *
142
+ * The loop this breaks: the user closes their app, an agent that ignores the "do not
143
+ * reopen" note fires run_command again, the user closes it again, and round it goes. A
144
+ * match here lets the tool refuse the re-launch instead of reopening what the user shut.
145
+ *
146
+ * The signal is "it came up, then ended, and the AGENT did not kill it" — `ready` and
147
+ * `stoppedBy !== "agent"`. That is deliberately the same fact `shouldWakeOnEnd` treats as
148
+ * the user stopping their own app. It leaves the agent's OWN restart flow (kill_shell then
149
+ * relaunch) untouched, because that ending is `stoppedBy: "agent"`; and it never blocks a
150
+ * server that failed to start (`ready` is false), which the agent should be free to fix.
151
+ * Matched on the normalized command within a cooldown, so a later, deliberate restart is
152
+ * not held back.
153
+ */
154
+ export function findRecentUserClose(shells, command, now, windowMs = REOPEN_COOLDOWN_MS) {
155
+ const norm = (s) => s.toLowerCase().replace(/\s+/g, " ").trim();
156
+ const target = norm(command);
157
+ return shells.find((s) => s.status !== "running" &&
158
+ s.ready &&
159
+ s.stoppedBy !== "agent" &&
160
+ s.finishedAt !== null &&
161
+ now - s.finishedAt < windowMs &&
162
+ norm(s.command) === target);
163
+ }
164
+ const active = new Set();
165
+ let cleanupRegistered = false;
166
+ export class BackgroundShells {
167
+ startupGraceMs;
168
+ exitGraceMs;
169
+ seq = 0;
170
+ shells = new Map();
171
+ onChange = null;
172
+ /**
173
+ * The two grace periods, injectable ONLY so tests can exercise the mechanism
174
+ * without waiting out real seconds. The defaults are the shipped behaviour and no
175
+ * production caller passes anything: a suite that waits out a 10s startup grace
176
+ * per case was 73% of the whole run's wall time, and that cost lands again on
177
+ * every contributor and every CI job.
178
+ */
179
+ constructor(startupGraceMs = STARTUP_GRACE_MS, exitGraceMs = EXIT_GRACE_MS) {
180
+ this.startupGraceMs = startupGraceMs;
181
+ this.exitGraceMs = exitGraceMs;
182
+ active.add(this);
183
+ registerCleanup();
184
+ }
185
+ /** Subscribe to state changes (start / finish / kill) — the UI re-renders. */
186
+ setOnChange(cb) {
187
+ this.onChange = cb;
188
+ }
189
+ /** Take ownership of a live child process and start buffering its output. */
190
+ adopt(child, opts) {
191
+ const id = ++this.seq;
192
+ const entry = {
193
+ id,
194
+ command: opts.command,
195
+ cwd: opts.cwd,
196
+ status: "running",
197
+ exitCode: null,
198
+ startedAt: Date.now(),
199
+ finishedAt: null,
200
+ child,
201
+ buffer: "",
202
+ readOffset: 0,
203
+ truncated: false,
204
+ notify: opts.notify ?? guessNotifyPolicy(opts.command),
205
+ ready: false,
206
+ reported: false,
207
+ uiNotified: false,
208
+ wakeOnEnd: false,
209
+ readyReported: false,
210
+ readyUiNotified: false,
211
+ readyTimer: null,
212
+ cwdFile: opts.cwdFile,
213
+ tempFile: opts.tempFile,
214
+ };
215
+ this.shells.set(id, entry);
216
+ if (opts.initial)
217
+ this.append(entry, opts.initial);
218
+ // The readiness signal. A server that is still alive after the startup grace has
219
+ // come up, and that is the one positive event worth reporting for something that
220
+ // never "finishes". Without it the model was told to promise a report it could not
221
+ // give: the only event it could ever receive was the end, which for a server is
222
+ // deliberately suppressed. Tasks don't need it — their event is completion.
223
+ if (entry.notify === "on_failure") {
224
+ entry.readyTimer = setTimeout(() => {
225
+ entry.readyTimer = null;
226
+ if (entry.status !== "running")
227
+ return;
228
+ entry.ready = true;
229
+ this.emit();
230
+ }, this.startupGraceMs);
231
+ entry.readyTimer.unref?.();
232
+ }
233
+ const collect = (chunk) => this.append(entry, chunk.toString("utf8"));
234
+ child.stdout?.on("data", collect);
235
+ child.stderr?.on("data", collect);
236
+ // `signal` is captured, not dropped: a process ended by SIGTERM/SIGINT reports
237
+ // `code === null`, and without the signal there is no way to tell that from a
238
+ // crash.
239
+ child.on("close", (code, signal) => this.onClose(entry, code, signal, false));
240
+ child.on("error", () => this.onClose(entry, null, null, false));
241
+ // Backstop for a `close` that never arrives because a surviving grandchild still
242
+ // holds the stdio pipe. Without this the entry stays "running" for the rest of the
243
+ // session: the UI shows a dead shell, and `runningCount()` is permanently wrong.
244
+ child.on("exit", (code, signal) => {
245
+ const timer = setTimeout(() => this.onClose(entry, code, signal, false), this.exitGraceMs);
246
+ timer.unref?.();
247
+ });
248
+ this.emit();
249
+ return view(entry);
250
+ }
251
+ append(entry, text) {
252
+ entry.buffer += text;
253
+ if (entry.buffer.length > MAX_BUFFER_CHARS) {
254
+ // Keep the tail — the recent output is what matters for tests/errors.
255
+ entry.buffer = entry.buffer.slice(entry.buffer.length - MAX_BUFFER_CHARS);
256
+ entry.readOffset = Math.min(entry.readOffset, entry.buffer.length);
257
+ entry.truncated = true;
258
+ }
259
+ }
260
+ onClose(entry, code, signal, killed, by) {
261
+ if (entry.status !== "running")
262
+ return;
263
+ entry.status = killed ? "killed" : "exited";
264
+ entry.exitCode = code;
265
+ if (signal)
266
+ entry.signal = signal;
267
+ entry.finishedAt = Date.now();
268
+ entry.child = null;
269
+ if (by)
270
+ entry.stoppedBy = by;
271
+ if (entry.readyTimer) {
272
+ clearTimeout(entry.readyTimer);
273
+ entry.readyTimer = null;
274
+ }
275
+ // A pending "it's up" must not fire after the thing has already stopped. Note this
276
+ // clears the PENDING notice, not `entry.ready`: whether it ever came up is the fact
277
+ // the wake decision below is built on, and it has to survive.
278
+ entry.readyReported = true;
279
+ entry.readyUiNotified = true;
280
+ // Whether this ending is worth interrupting for. It is NOT marked reported here:
281
+ // the model is always told (drainEvents), it just isn't always interrupted. Marking
282
+ // it reported is what used to delete the event outright, leaving the model unable
283
+ // to say the app had stopped at all.
284
+ entry.wakeOnEnd = shouldWakeOnEnd({
285
+ notify: entry.notify,
286
+ killed,
287
+ signal,
288
+ cameUp: entry.ready,
289
+ });
290
+ if (entry.cwdFile)
291
+ void fs.rm(entry.cwdFile, { force: true }).catch(() => { });
292
+ if (entry.tempFile)
293
+ void fs.rm(entry.tempFile, { force: true }).catch(() => { });
294
+ this.emit();
295
+ }
296
+ /** New output since the last read of this shell, plus its current status. */
297
+ async read(id) {
298
+ const entry = this.shells.get(id);
299
+ if (!entry)
300
+ return null;
301
+ let chunk = entry.buffer.slice(entry.readOffset);
302
+ entry.readOffset = entry.buffer.length;
303
+ if (chunk.length > MAX_READ_CHARS) {
304
+ chunk = `… (earlier output omitted)\n${chunk.slice(chunk.length - MAX_READ_CHARS)}`;
305
+ }
306
+ return { info: view(entry), chunk };
307
+ }
308
+ /**
309
+ * Kill a running shell (whole tree). Returns false if it isn't running.
310
+ *
311
+ * `by` records WHO stopped it. Neither actor is woken about it, since both already
312
+ * know, but the difference is kept so the model can say "you stopped it" rather than
313
+ * guessing that it crashed.
314
+ */
315
+ kill(id, by = "agent") {
316
+ const entry = this.shells.get(id);
317
+ if (!entry || entry.status !== "running" || !entry.child)
318
+ return false;
319
+ killTree(entry.child.pid);
320
+ this.onClose(entry, null, null, true, by);
321
+ return true;
322
+ }
323
+ list() {
324
+ return [...this.shells.values()].map(view);
325
+ }
326
+ running() {
327
+ return this.list().filter((s) => s.status === "running");
328
+ }
329
+ runningCount() {
330
+ return this.running().length;
331
+ }
332
+ /**
333
+ * Events worth INTERRUPTING for: a shell that just came up, or one that ended in a
334
+ * way the user cannot already know about.
335
+ *
336
+ * This is deliberately narrower than "events not yet told". A stop the user caused
337
+ * still gets delivered on the next turn (see `drainEvents`); it just doesn't break
338
+ * into the session, which is what stops the agent reopening a closed app.
339
+ */
340
+ pendingCount() {
341
+ return [...this.shells.values()].filter((e) => (e.status !== "running" && !e.reported && e.wakeOnEnd) || (e.ready && !e.readyReported)).length;
342
+ }
343
+ /** One-shot for the UI: shells that came up or stopped and aren't in the chat yet. */
344
+ takeUiEvents() {
345
+ const out = [];
346
+ for (const entry of this.shells.values()) {
347
+ if (entry.ready && !entry.readyUiNotified) {
348
+ entry.readyUiNotified = true;
349
+ out.push({ info: view(entry), kind: "ready" });
350
+ }
351
+ if (entry.status !== "running" && !entry.uiNotified) {
352
+ entry.uiNotified = true;
353
+ out.push({ info: view(entry), kind: "ended" });
354
+ }
355
+ }
356
+ return out;
357
+ }
358
+ /**
359
+ * One-shot for the MODEL: EVERYTHING it hasn't been told, each with a tail of output.
360
+ *
361
+ * Every ending is delivered, including the ones not worth interrupting for. Those
362
+ * used to be deleted, which left the model unable to say an app had stopped, or to
363
+ * answer why it was down. `wake` carries whether this was the interrupting kind, so
364
+ * the caller can word it as news or as background fact.
365
+ *
366
+ * Both kinds go through this single channel, and both mark themselves so nothing is
367
+ * ever injected twice. That one-shot property is the whole reason background jobs
368
+ * don't slowly eat the context window, and it must survive any change here.
369
+ */
370
+ async drainEvents() {
371
+ const out = [];
372
+ const tailOf = (entry) => entry.buffer.slice(Math.max(0, entry.buffer.length - TAIL_CHARS));
373
+ for (const entry of this.shells.values()) {
374
+ if (entry.ready && !entry.readyReported) {
375
+ entry.readyReported = true;
376
+ out.push({ info: view(entry), kind: "ready", tail: tailOf(entry), wake: true });
377
+ }
378
+ if (entry.status !== "running" && !entry.reported) {
379
+ entry.reported = true;
380
+ out.push({ info: view(entry), kind: "ended", tail: tailOf(entry), wake: entry.wakeOnEnd });
381
+ }
382
+ }
383
+ return out;
384
+ }
385
+ /**
386
+ * Kill every running shell and drop the registry (session swap / exit).
387
+ *
388
+ * `sync` is required when disposing from a process-exit handler: the default
389
+ * kill spawns `taskkill` asynchronously, and Node runs no async work during
390
+ * exit, so the shells would outlive us. Measured, not assumed.
391
+ */
392
+ dispose(sync = false) {
393
+ for (const entry of this.shells.values()) {
394
+ // Kill by CHILD PRESENT, not by recorded status. A shell we have marked
395
+ // "ended" only means its WRAPPER exited, and on POSIX that says nothing about
396
+ // its descendants: kill the `sh -c` and the program it started is orphaned and
397
+ // keeps running, still holding the stdio pipes. MEASURED on Linux, where the
398
+ // orphan outlived the whole test process and stopped it from ever exiting.
399
+ // The group kill still reaches it, because a process group survives its leader
400
+ // as long as it has members. Signalling an already-dead pid is a harmless
401
+ // no-op, so there is nothing to lose by not consulting the status first.
402
+ if (entry.child) {
403
+ if (sync)
404
+ killTreeSync(entry.child.pid);
405
+ else
406
+ killTree(entry.child.pid);
407
+ }
408
+ if (entry.cwdFile)
409
+ void fs.rm(entry.cwdFile, { force: true }).catch(() => { });
410
+ if (entry.tempFile)
411
+ void fs.rm(entry.tempFile, { force: true }).catch(() => { });
412
+ }
413
+ this.shells.clear();
414
+ active.delete(this);
415
+ }
416
+ emit() {
417
+ this.onChange?.();
418
+ }
419
+ }
420
+ function view(e) {
421
+ return {
422
+ id: e.id,
423
+ command: e.command,
424
+ cwd: e.cwd,
425
+ status: e.status,
426
+ exitCode: e.exitCode,
427
+ startedAt: e.startedAt,
428
+ finishedAt: e.finishedAt,
429
+ notify: e.notify,
430
+ ready: e.ready,
431
+ ...(e.signal ? { signal: e.signal } : {}),
432
+ ...(e.stoppedBy ? { stoppedBy: e.stoppedBy } : {}),
433
+ ...(e.truncated ? { truncated: true } : {}),
434
+ ...(detectPort(e.buffer) !== undefined ? { port: detectPort(e.buffer) } : {}),
435
+ };
436
+ }
437
+ /** Kill any background processes still running when the process exits. */
438
+ function registerCleanup() {
439
+ if (cleanupRegistered)
440
+ return;
441
+ cleanupRegistered = true;
442
+ process.once("exit", () => {
443
+ // Synchronous kill: an async one never reaches the OS from here.
444
+ for (const mgr of active)
445
+ mgr.dispose(true);
446
+ });
447
+ }
448
+ /**
449
+ * The port a process announced in its own output.
450
+ *
451
+ * A backgrounded dev server is only useful if you know where it is listening, and the
452
+ * one thing that knows is the server itself — it prints the URL on startup. So this
453
+ * reads the buffer rather than inspecting sockets: no privileges, no platform-specific
454
+ * netstat parsing, and it cannot report a port belonging to some other process.
455
+ *
456
+ * The FIRST announcement wins. A framework often prints a local URL and then a network
457
+ * one for the same port, and some print a proxy target afterwards; the first line is
458
+ * the one describing the server that just came up.
459
+ */
460
+ export function detectPort(output) {
461
+ const m = /(?:https?:\/\/)(?:localhost|127\.0\.0\.1|0\.0\.0\.0|\[::1\]):(\d{2,5})/i.exec(output) ??
462
+ /\b(?:listening|running|started|ready)\b[^\n]*?\bport\b\s*:?\s*(\d{2,5})/i.exec(output);
463
+ if (!m)
464
+ return undefined;
465
+ const port = Number(m[1]);
466
+ return port >= 1 && port <= 65535 ? port : undefined;
467
+ }
468
+ //# sourceMappingURL=backgroundShells.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"backgroundShells.js","sourceRoot":"","sources":["../../src/tools/backgroundShells.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,77 @@
1
+ /**
2
+ * captureSweep.ts — clear out screenshots that have outlived their usefulness.
3
+ *
4
+ * `screenshot` writes each capture to its own temp directory so the model can be
5
+ * handed the file and compaction can drop and restore the reference. Nothing removed
6
+ * them, so every window ever photographed stayed on disk indefinitely — and unlike
7
+ * the rest of the agent's temp files, a capture holds whatever happened to be on
8
+ * screen at the time.
9
+ *
10
+ * Deleting immediately after sending was considered and rejected: the reference
11
+ * survives in the transcript, compaction can bring an image back, and a capture the
12
+ * model may still be asked about should not be a dangling path. So they live for a
13
+ * few days and are swept by age at startup, which also catches anything left behind
14
+ * by a crash — the case a shutdown hook would miss.
15
+ *
16
+ * Best-effort throughout. A sweep that cannot read the temp directory, or that races
17
+ * another Mindweave deleting the same folder, must never keep the CLI from starting.
18
+ */
19
+ import { readdir, rm, stat } from "node:fs/promises";
20
+ import { tmpdir } from "node:os";
21
+ import { join } from "node:path";
22
+ /** How long a capture is kept. One edit changes the policy. */
23
+ export const CAPTURE_MAX_AGE_MS = 7 * 24 * 60 * 60 * 1000; // 7 days
24
+ /** Temp directory prefixes this sweep owns. Must match what creates them. */
25
+ export const SWEPT_PREFIXES = ["mindweave-shot-"];
26
+ /** Does this directory name belong to us? (pure) */
27
+ export function isSweptName(name) {
28
+ return SWEPT_PREFIXES.some((p) => name.startsWith(p));
29
+ }
30
+ /**
31
+ * Should an entry be removed, given its age? (pure)
32
+ *
33
+ * Split out from the I/O so the policy can be tested without fabricating timestamps
34
+ * on a real filesystem, and so "how old is too old" is one comparison in one place.
35
+ */
36
+ export function isExpired(mtimeMs, now, maxAgeMs = CAPTURE_MAX_AGE_MS) {
37
+ return now - mtimeMs > maxAgeMs;
38
+ }
39
+ /**
40
+ * Remove expired capture directories. Returns how many went.
41
+ *
42
+ * `dir` and `now` are parameters so tests drive a fabricated tree rather than the
43
+ * real temp directory, where a stray match would delete a developer's actual files.
44
+ */
45
+ export async function sweepCaptures(dir = tmpdir(), now = Date.now(), maxAgeMs = CAPTURE_MAX_AGE_MS) {
46
+ let removed = 0;
47
+ let names;
48
+ try {
49
+ names = await readdir(dir);
50
+ }
51
+ catch {
52
+ return 0; // unreadable temp directory is not our problem to solve
53
+ }
54
+ for (const name of names) {
55
+ if (!isSweptName(name))
56
+ continue;
57
+ const full = join(dir, name);
58
+ try {
59
+ const info = await stat(full);
60
+ if (!info.isDirectory())
61
+ continue;
62
+ if (!isExpired(info.mtimeMs, now, maxAgeMs))
63
+ continue;
64
+ await rm(full, { recursive: true, force: true });
65
+ removed++;
66
+ }
67
+ catch {
68
+ // Vanished under us, locked, or not ours to delete. Skip it.
69
+ }
70
+ }
71
+ return removed;
72
+ }
73
+ /** Fire-and-forget sweep for startup: never awaited, never throws, never logs. */
74
+ export function sweepCapturesInBackground() {
75
+ void sweepCaptures().catch(() => { });
76
+ }
77
+ //# sourceMappingURL=captureSweep.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"captureSweep.js","sourceRoot":"","sources":["../../src/tools/captureSweep.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AACH,OAAO,EAAE,OAAO,EAAE,EAAE,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AACrD,OAAO,EAAE,MAAM,EAAE,MAAM,SAAS,CAAC;AACjC,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAEjC,+DAA+D;AAC/D,MAAM,CAAC,MAAM,kBAAkB,GAAG,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC,CAAC,SAAS;AAEpE,6EAA6E;AAC7E,MAAM,CAAC,MAAM,cAAc,GAAG,CAAC,iBAAiB,CAAU,CAAC;AAE3D,oDAAoD;AACpD,MAAM,UAAU,WAAW,CAAC,IAAY;IACtC,OAAO,cAAc,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,CAAC;AACxD,CAAC;AAED;;;;;GAKG;AACH,MAAM,UAAU,SAAS,CAAC,OAAe,EAAE,GAAW,EAAE,QAAQ,GAAG,kBAAkB;IACnF,OAAO,GAAG,GAAG,OAAO,GAAG,QAAQ,CAAC;AAClC,CAAC;AAED;;;;;GAKG;AACH,MAAM,CAAC,KAAK,UAAU,aAAa,CACjC,MAAc,MAAM,EAAE,EACtB,MAAc,IAAI,CAAC,GAAG,EAAE,EACxB,WAAmB,kBAAkB;IAErC,IAAI,OAAO,GAAG,CAAC,CAAC;IAChB,IAAI,KAAe,CAAC;IACpB,IAAI,CAAC;QACH,KAAK,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC,CAAC;IAC7B,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,CAAC,CAAC,CAAC,wDAAwD;IACpE,CAAC;IAED,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC;YAAE,SAAS;QACjC,MAAM,IAAI,GAAG,IAAI,CAAC,GAAG,EAAE,IAAI,CAAC,CAAC;QAC7B,IAAI,CAAC;YACH,MAAM,IAAI,GAAG,MAAM,IAAI,CAAC,IAAI,CAAC,CAAC;YAC9B,IAAI,CAAC,IAAI,CAAC,WAAW,EAAE;gBAAE,SAAS;YAClC,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,OAAO,EAAE,GAAG,EAAE,QAAQ,CAAC;gBAAE,SAAS;YACtD,MAAM,EAAE,CAAC,IAAI,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC;YACjD,OAAO,EAAE,CAAC;QACZ,CAAC;QAAC,MAAM,CAAC;YACP,6DAA6D;QAC/D,CAAC;IACH,CAAC;IACD,OAAO,OAAO,CAAC;AACjB,CAAC;AAED,kFAAkF;AAClF,MAAM,UAAU,yBAAyB;IACvC,KAAK,aAAa,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,GAAE,CAAC,CAAC,CAAC;AACvC,CAAC"}
@@ -0,0 +1,92 @@
1
+ /**
2
+ * chassisMux.ts — query the right code map(s) in a multi-root workspace.
3
+ *
4
+ * Each session root has its own chassis (a code map only knows its own files). The
5
+ * code-intelligence tools route through here so they stay correct across roots:
6
+ * - path queries (outline) hit the chassis that OWNS the file;
7
+ * - name queries (definition/references) MERGE across every root;
8
+ * - relevance ranks within each root, then merges by score.
9
+ * Single-root sessions fall straight through to the one chassis — no overhead.
10
+ */
11
+ import { isAbsolute, relative } from "node:path";
12
+ import { CodeGraph } from "../alternator/chassis/graph.js";
13
+ /** Every chassis in play (per-root set, or just the primary). */
14
+ export function allChassis(ctx) {
15
+ if (ctx.chassisByRoot && ctx.chassisByRoot.size > 0)
16
+ return [...ctx.chassisByRoot.values()];
17
+ return ctx.chassis ? [ctx.chassis] : [];
18
+ }
19
+ /** The chassis whose root contains `abs`, or the primary as a fallback. */
20
+ export function chassisForPath(ctx, abs) {
21
+ if (ctx.chassisByRoot) {
22
+ for (const [root, chassis] of ctx.chassisByRoot) {
23
+ const rel = relative(root, abs);
24
+ if (rel === "" || (!rel.startsWith("..") && !isAbsolute(rel)))
25
+ return chassis;
26
+ }
27
+ }
28
+ return ctx.chassis;
29
+ }
30
+ /**
31
+ * Confidence for a MERGED list, which is the confidence of its weakest part.
32
+ *
33
+ * The merged list is one list to the reader, and the caveat printed from this value
34
+ * governs all of it. So a root running a language server must not vouch for a root
35
+ * that is on the tree-sitter tier: taking the best there marks name-level entries
36
+ * `resolved` purely by association, and `resolved` is exactly what suppresses the
37
+ * "verify with grep" note those entries need. Each `Ref` still carries its own
38
+ * per-entry confidence for anyone who wants the finer answer.
39
+ */
40
+ function mergedConfidence(values) {
41
+ return values.every((c) => c === "resolved") && values.length > 0 ? "resolved" : "name-level";
42
+ }
43
+ /** Where a symbol is defined, merged across every root. */
44
+ export async function mergedDefinition(ctx, name) {
45
+ const list = allChassis(ctx);
46
+ if (list.length === 1)
47
+ return list[0].definition(name);
48
+ const symbols = [];
49
+ const confidences = [];
50
+ for (const ch of list) {
51
+ const r = await ch.definition(name);
52
+ symbols.push(...r.symbols);
53
+ if (r.symbols.length)
54
+ confidences.push(r.confidence);
55
+ }
56
+ return { symbols, confidence: mergedConfidence(confidences) };
57
+ }
58
+ /** Who references a symbol, merged across every root. */
59
+ export async function mergedReferences(ctx, name) {
60
+ const list = allChassis(ctx);
61
+ if (list.length === 1)
62
+ return list[0].references(name);
63
+ const refs = [];
64
+ const confidences = [];
65
+ for (const ch of list) {
66
+ const r = await ch.references(name);
67
+ refs.push(...r.refs);
68
+ if (r.refs.length)
69
+ confidences.push(r.confidence);
70
+ }
71
+ return { refs, confidence: mergedConfidence(confidences) };
72
+ }
73
+ /** The span(s) of a named symbol's definition, across every root. A `path` is only
74
+ * ever inside one root, so passing it naturally narrows the result to that root. */
75
+ export async function symbolSpans(ctx, name, opts = {}) {
76
+ const list = allChassis(ctx);
77
+ if (list.length === 0)
78
+ return [];
79
+ if (list.length === 1)
80
+ return list[0].span(name, opts);
81
+ const spans = [];
82
+ for (const ch of list)
83
+ spans.push(...(await ch.span(name, opts)));
84
+ return spans;
85
+ }
86
+ /** A chassis's underlying code graph, if it exposes one (CodeChassis does; the
87
+ * null/test chassis may not). */
88
+ function graphOf(chassis) {
89
+ const g = chassis.graphRef?.();
90
+ return g instanceof CodeGraph ? g : null;
91
+ }
92
+ //# sourceMappingURL=chassisMux.js.map