@within-7/minto 0.3.9 → 0.4.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 (383) hide show
  1. package/dist/Tool.js.map +2 -2
  2. package/dist/commands/agents/AgentsCommand.js +461 -657
  3. package/dist/commands/agents/AgentsCommand.js.map +2 -2
  4. package/dist/commands/agents/types.js +1 -0
  5. package/dist/commands/agents/types.js.map +2 -2
  6. package/dist/commands/agents/utils/fileOperations.js +96 -36
  7. package/dist/commands/agents/utils/fileOperations.js.map +3 -3
  8. package/dist/commands/agents/utils/index.js +3 -1
  9. package/dist/commands/agents/utils/index.js.map +2 -2
  10. package/dist/commands/context.js +54 -23
  11. package/dist/commands/context.js.map +2 -2
  12. package/dist/commands/ctx_viz.js +1 -1
  13. package/dist/commands/effort.js +87 -0
  14. package/dist/commands/effort.js.map +7 -0
  15. package/dist/commands/export.js +684 -94
  16. package/dist/commands/export.js.map +2 -2
  17. package/dist/commands/ide.js +18 -0
  18. package/dist/commands/ide.js.map +7 -0
  19. package/dist/commands/language.js +19 -46
  20. package/dist/commands/language.js.map +2 -2
  21. package/dist/commands/mcp-interactive.js +425 -217
  22. package/dist/commands/mcp-interactive.js.map +2 -2
  23. package/dist/commands/memory.js +168 -0
  24. package/dist/commands/memory.js.map +7 -0
  25. package/dist/commands/model.js +457 -65
  26. package/dist/commands/model.js.map +2 -2
  27. package/dist/commands/outputStyle.js +64 -0
  28. package/dist/commands/outputStyle.js.map +7 -0
  29. package/dist/commands/permissions.js +75 -49
  30. package/dist/commands/permissions.js.map +2 -2
  31. package/dist/commands/plugin/utils.js +33 -1
  32. package/dist/commands/plugin/utils.js.map +2 -2
  33. package/dist/commands/plugin.js +891 -185
  34. package/dist/commands/plugin.js.map +3 -3
  35. package/dist/commands/refreshCommands.js +2 -0
  36. package/dist/commands/refreshCommands.js.map +2 -2
  37. package/dist/commands/resume.js +1 -1
  38. package/dist/commands/resume.js.map +1 -1
  39. package/dist/commands/review.js +51 -0
  40. package/dist/commands/review.js.map +7 -0
  41. package/dist/commands/sandbox.js +168 -70
  42. package/dist/commands/sandbox.js.map +2 -2
  43. package/dist/commands/setup.js +593 -107
  44. package/dist/commands/setup.js.map +2 -2
  45. package/dist/commands/stats.js +188 -131
  46. package/dist/commands/stats.js.map +2 -2
  47. package/dist/commands/status.js +75 -13
  48. package/dist/commands/status.js.map +2 -2
  49. package/dist/commands/terminalSetup.js +6 -0
  50. package/dist/commands/terminalSetup.js.map +2 -2
  51. package/dist/commands/undo.js +146 -174
  52. package/dist/commands/undo.js.map +2 -2
  53. package/dist/commands/vim.js +22 -0
  54. package/dist/commands/vim.js.map +7 -0
  55. package/dist/commands.js +12 -0
  56. package/dist/commands.js.map +2 -2
  57. package/dist/components/Help.js +165 -32
  58. package/dist/components/Help.js.map +2 -2
  59. package/dist/components/HighlightedCode.js +1 -0
  60. package/dist/components/HighlightedCode.js.map +2 -2
  61. package/dist/components/InfoPanel/InfoPanel.js +123 -0
  62. package/dist/components/InfoPanel/InfoPanel.js.map +7 -0
  63. package/dist/components/InfoPanel/index.js +5 -0
  64. package/dist/components/InfoPanel/index.js.map +7 -0
  65. package/dist/components/InfoPanel/types.js +1 -0
  66. package/dist/components/InfoPanel/types.js.map +7 -0
  67. package/dist/components/ModelSelector/BrandTextInput.js +43 -0
  68. package/dist/components/ModelSelector/BrandTextInput.js.map +7 -0
  69. package/dist/components/ModelSelector/ModelSelector.js +590 -565
  70. package/dist/components/ModelSelector/ModelSelector.js.map +2 -2
  71. package/dist/components/ModelSelector/WizardContainer.js +45 -0
  72. package/dist/components/ModelSelector/WizardContainer.js.map +7 -0
  73. package/dist/components/ModelSelector/index.js +1 -3
  74. package/dist/components/ModelSelector/index.js.map +2 -2
  75. package/dist/components/PromptInput.js +26 -11
  76. package/dist/components/PromptInput.js.map +2 -2
  77. package/dist/components/PulseLabel.js +44 -0
  78. package/dist/components/PulseLabel.js.map +7 -0
  79. package/dist/components/RequestStatusIndicator.js +1 -1
  80. package/dist/components/RequestStatusIndicator.js.map +1 -1
  81. package/dist/components/SimpleSelector/SimpleSelector.js +154 -0
  82. package/dist/components/SimpleSelector/SimpleSelector.js.map +7 -0
  83. package/dist/components/SimpleSelector/index.js +5 -0
  84. package/dist/components/SimpleSelector/index.js.map +7 -0
  85. package/dist/components/SimpleSelector/types.js +1 -0
  86. package/dist/components/SimpleSelector/types.js.map +7 -0
  87. package/dist/components/Spinner.js +12 -42
  88. package/dist/components/Spinner.js.map +3 -3
  89. package/dist/components/StartupStatus.js +57 -0
  90. package/dist/components/StartupStatus.js.map +7 -0
  91. package/dist/components/StatusOverlayContent.js +21 -0
  92. package/dist/components/StatusOverlayContent.js.map +7 -0
  93. package/dist/components/SubagentBlock.js +43 -6
  94. package/dist/components/SubagentBlock.js.map +2 -2
  95. package/dist/components/TabbedListView/ScrollableList.js +31 -5
  96. package/dist/components/TabbedListView/ScrollableList.js.map +2 -2
  97. package/dist/components/TabbedListView/TabBar.js +13 -8
  98. package/dist/components/TabbedListView/TabBar.js.map +2 -2
  99. package/dist/components/TabbedListView/TabbedListView.js +123 -48
  100. package/dist/components/TabbedListView/TabbedListView.js.map +2 -2
  101. package/dist/components/TodoPanel.js +1 -1
  102. package/dist/components/TodoPanel.js.map +1 -1
  103. package/dist/components/ToolUseLoader.js +5 -0
  104. package/dist/components/ToolUseLoader.js.map +2 -2
  105. package/dist/components/TrustDialog.js +0 -2
  106. package/dist/components/TrustDialog.js.map +2 -2
  107. package/dist/components/messages/TaskInModuleView.js +1 -1
  108. package/dist/components/messages/TaskInModuleView.js.map +2 -2
  109. package/dist/components/messages/TaskToolMessage.js +1 -1
  110. package/dist/components/messages/TaskToolMessage.js.map +2 -2
  111. package/dist/components/messages/UserPromptMessage.js +6 -1
  112. package/dist/components/messages/UserPromptMessage.js.map +2 -2
  113. package/dist/constants/modelCapabilities.js +103 -18
  114. package/dist/constants/modelCapabilities.js.map +2 -2
  115. package/dist/constants/product.js +2 -0
  116. package/dist/constants/product.js.map +2 -2
  117. package/dist/constants/prompts/agentPrompt.js +30 -0
  118. package/dist/constants/prompts/agentPrompt.js.map +7 -0
  119. package/dist/constants/prompts/codeConventions.js +27 -0
  120. package/dist/constants/prompts/codeConventions.js.map +7 -0
  121. package/dist/constants/prompts/doingTasks.js +15 -0
  122. package/dist/constants/prompts/doingTasks.js.map +7 -0
  123. package/dist/constants/prompts/envInfo.js +17 -0
  124. package/dist/constants/prompts/envInfo.js.map +7 -0
  125. package/dist/constants/prompts/executingWithCare.js +17 -0
  126. package/dist/constants/prompts/executingWithCare.js.map +7 -0
  127. package/dist/constants/prompts/identity.js +10 -0
  128. package/dist/constants/prompts/identity.js.map +7 -0
  129. package/dist/constants/prompts/index.js +78 -0
  130. package/dist/constants/prompts/index.js.map +7 -0
  131. package/dist/constants/prompts/taskManagement.js +60 -0
  132. package/dist/constants/prompts/taskManagement.js.map +7 -0
  133. package/dist/constants/prompts/toneAndStyle.js +62 -0
  134. package/dist/constants/prompts/toneAndStyle.js.map +7 -0
  135. package/dist/constants/prompts/toolUsagePolicy.js +38 -0
  136. package/dist/constants/prompts/toolUsagePolicy.js.map +7 -0
  137. package/dist/constants/prompts.js +5 -176
  138. package/dist/constants/prompts.js.map +2 -2
  139. package/dist/constants/providerRegistry.js +235 -0
  140. package/dist/constants/providerRegistry.js.map +7 -0
  141. package/dist/constants/providers.js +35 -0
  142. package/dist/constants/providers.js.map +7 -0
  143. package/dist/context/PermissionContext.js +0 -1
  144. package/dist/context/PermissionContext.js.map +2 -2
  145. package/dist/context.js +87 -31
  146. package/dist/context.js.map +2 -2
  147. package/dist/core/backupHook.js +29 -0
  148. package/dist/core/backupHook.js.map +7 -0
  149. package/dist/core/config/defaults.js +11 -2
  150. package/dist/core/config/defaults.js.map +2 -2
  151. package/dist/core/config/schema.js +21 -3
  152. package/dist/core/config/schema.js.map +2 -2
  153. package/dist/core/costTracker.js +18 -16
  154. package/dist/core/costTracker.js.map +2 -2
  155. package/dist/core/index.js +0 -1
  156. package/dist/core/index.js.map +2 -2
  157. package/dist/core/tokenStatsManager.js +22 -4
  158. package/dist/core/tokenStatsManager.js.map +2 -2
  159. package/dist/cost-tracker.js +0 -16
  160. package/dist/cost-tracker.js.map +2 -2
  161. package/dist/entrypoints/bootstrap.js +3 -1
  162. package/dist/entrypoints/bootstrap.js.map +2 -2
  163. package/dist/entrypoints/cli.js +81 -68
  164. package/dist/entrypoints/cli.js.map +2 -2
  165. package/dist/hooks/useAgentTokenStats.js +1 -1
  166. package/dist/hooks/useAgentTokenStats.js.map +2 -2
  167. package/dist/hooks/useAgentTranscripts.js +2 -1
  168. package/dist/hooks/useAgentTranscripts.js.map +2 -2
  169. package/dist/hooks/useBackgroundShells.js +29 -0
  170. package/dist/hooks/useBackgroundShells.js.map +7 -0
  171. package/dist/hooks/useCanUseTool.js +1 -1
  172. package/dist/hooks/useCanUseTool.js.map +2 -2
  173. package/dist/hooks/useDeferredLoading.js +64 -0
  174. package/dist/hooks/useDeferredLoading.js.map +7 -0
  175. package/dist/hooks/useHookStatus.js +1 -1
  176. package/dist/hooks/useHookStatus.js.map +2 -2
  177. package/dist/hooks/useSessionTracking.js +55 -0
  178. package/dist/hooks/useSessionTracking.js.map +7 -0
  179. package/dist/hooks/useTerminalSize.js +21 -0
  180. package/dist/hooks/useTerminalSize.js.map +2 -2
  181. package/dist/hooks/useTextInput.js +1 -0
  182. package/dist/hooks/useTextInput.js.map +2 -2
  183. package/dist/hooks/useUnifiedCompletion.js +3 -2
  184. package/dist/hooks/useUnifiedCompletion.js.map +2 -2
  185. package/dist/i18n/locales/en.js +299 -1
  186. package/dist/i18n/locales/en.js.map +2 -2
  187. package/dist/i18n/locales/zh-CN.js +300 -2
  188. package/dist/i18n/locales/zh-CN.js.map +2 -2
  189. package/dist/i18n/types.js.map +1 -1
  190. package/dist/messages.js +41 -17
  191. package/dist/messages.js.map +2 -2
  192. package/dist/permissions.js +94 -1
  193. package/dist/permissions.js.map +2 -2
  194. package/dist/query.js +27 -19
  195. package/dist/query.js.map +2 -2
  196. package/dist/screens/REPL.js +83 -74
  197. package/dist/screens/REPL.js.map +2 -2
  198. package/dist/services/adapters/responsesAPI.js +6 -0
  199. package/dist/services/adapters/responsesAPI.js.map +2 -2
  200. package/dist/services/agentTeams/index.js +35 -0
  201. package/dist/services/agentTeams/index.js.map +7 -0
  202. package/dist/services/agentTeams/mailbox.js +114 -0
  203. package/dist/services/agentTeams/mailbox.js.map +7 -0
  204. package/dist/services/agentTeams/teamManager.js +149 -0
  205. package/dist/services/agentTeams/teamManager.js.map +7 -0
  206. package/dist/services/agentTeams/teamTaskStore.js +114 -0
  207. package/dist/services/agentTeams/teamTaskStore.js.map +7 -0
  208. package/dist/services/agentTeams/teammateSpawner.js +80 -0
  209. package/dist/services/agentTeams/teammateSpawner.js.map +7 -0
  210. package/dist/services/checkpointManager.js +16 -3
  211. package/dist/services/checkpointManager.js.map +2 -2
  212. package/dist/services/claude.js +19 -1728
  213. package/dist/services/claude.js.map +3 -3
  214. package/dist/services/customCommands.js +30 -8
  215. package/dist/services/customCommands.js.map +2 -2
  216. package/dist/services/gpt5ConnectionTest.js +4 -2
  217. package/dist/services/gpt5ConnectionTest.js.map +2 -2
  218. package/dist/services/hookExecutor.js +411 -127
  219. package/dist/services/hookExecutor.js.map +2 -2
  220. package/dist/services/llm/anthropicProvider.js +807 -0
  221. package/dist/services/llm/anthropicProvider.js.map +7 -0
  222. package/dist/services/llm/dispatch.js +218 -0
  223. package/dist/services/llm/dispatch.js.map +7 -0
  224. package/dist/services/llm/index.js +44 -0
  225. package/dist/services/llm/index.js.map +7 -0
  226. package/dist/services/llm/mintoContext.js +69 -0
  227. package/dist/services/llm/mintoContext.js.map +7 -0
  228. package/dist/services/llm/openaiProvider.js +622 -0
  229. package/dist/services/llm/openaiProvider.js.map +7 -0
  230. package/dist/services/llm/types.js +157 -0
  231. package/dist/services/llm/types.js.map +7 -0
  232. package/dist/services/mcpClient.js +183 -33
  233. package/dist/services/mcpClient.js.map +2 -2
  234. package/dist/services/notifier.js +14 -0
  235. package/dist/services/notifier.js.map +2 -2
  236. package/dist/services/oauth.js +4 -2
  237. package/dist/services/oauth.js.map +2 -2
  238. package/dist/services/openai.js +66 -56
  239. package/dist/services/openai.js.map +3 -3
  240. package/dist/services/outputStyles.js +102 -21
  241. package/dist/services/outputStyles.js.map +2 -2
  242. package/dist/services/plugins/lspServers.js +1 -1
  243. package/dist/services/plugins/lspServers.js.map +2 -2
  244. package/dist/services/plugins/pluginRuntime.js +2 -1
  245. package/dist/services/plugins/pluginRuntime.js.map +2 -2
  246. package/dist/services/plugins/pluginValidation.js +10 -3
  247. package/dist/services/plugins/pluginValidation.js.map +2 -2
  248. package/dist/services/plugins/skillMarketplace.js +20 -9
  249. package/dist/services/plugins/skillMarketplace.js.map +2 -2
  250. package/dist/services/sentry.js +1 -1
  251. package/dist/services/sentry.js.map +2 -2
  252. package/dist/services/sessionMemory.js +16 -3
  253. package/dist/services/sessionMemory.js.map +2 -2
  254. package/dist/services/systemReminder.js +367 -9
  255. package/dist/services/systemReminder.js.map +2 -2
  256. package/dist/services/taskStore.js +19 -0
  257. package/dist/services/taskStore.js.map +2 -2
  258. package/dist/tools/ArchitectTool/ArchitectTool.js.map +1 -1
  259. package/dist/tools/AskUserQuestionTool/AskUserQuestionTool.js.map +1 -1
  260. package/dist/tools/BashOutputTool/BashOutputTool.js.map +1 -1
  261. package/dist/tools/BashTool/BashTool.js +28 -0
  262. package/dist/tools/BashTool/BashTool.js.map +2 -2
  263. package/dist/tools/FileEditTool/FileEditTool.js +8 -1
  264. package/dist/tools/FileEditTool/FileEditTool.js.map +2 -2
  265. package/dist/tools/FileReadTool/FileReadTool.js +14 -0
  266. package/dist/tools/FileReadTool/FileReadTool.js.map +2 -2
  267. package/dist/tools/FileWriteTool/FileWriteTool.js +10 -1
  268. package/dist/tools/FileWriteTool/FileWriteTool.js.map +2 -2
  269. package/dist/tools/GlobTool/GlobTool.js.map +1 -1
  270. package/dist/tools/GrepTool/GrepTool.js.map +1 -1
  271. package/dist/tools/KillShellTool/KillShellTool.js.map +1 -1
  272. package/dist/tools/ListMcpResourcesTool/ListMcpResourcesTool.js.map +2 -2
  273. package/dist/tools/LspTool/LspTool.js +11 -2
  274. package/dist/tools/LspTool/LspTool.js.map +2 -2
  275. package/dist/tools/MCPTool/MCPTool.js.map +1 -1
  276. package/dist/tools/MemoryReadTool/MemoryReadTool.js +2 -1
  277. package/dist/tools/MemoryReadTool/MemoryReadTool.js.map +2 -2
  278. package/dist/tools/MemoryWriteTool/MemoryWriteTool.js +2 -1
  279. package/dist/tools/MemoryWriteTool/MemoryWriteTool.js.map +2 -2
  280. package/dist/tools/MultiEditTool/MultiEditTool.js +7 -0
  281. package/dist/tools/MultiEditTool/MultiEditTool.js.map +2 -2
  282. package/dist/tools/NotebookEditTool/NotebookEditTool.js +2 -0
  283. package/dist/tools/NotebookEditTool/NotebookEditTool.js.map +2 -2
  284. package/dist/tools/NotebookReadTool/NotebookReadTool.js.map +1 -1
  285. package/dist/tools/PlanModeTool/EnterPlanModeTool.js +8 -2
  286. package/dist/tools/PlanModeTool/EnterPlanModeTool.js.map +2 -2
  287. package/dist/tools/PlanModeTool/ExitPlanModeTool.js +2 -0
  288. package/dist/tools/PlanModeTool/ExitPlanModeTool.js.map +2 -2
  289. package/dist/tools/ReadMcpResourceTool/ReadMcpResourceTool.js.map +1 -1
  290. package/dist/tools/SlashCommandTool/SlashCommandTool.js +174 -18
  291. package/dist/tools/SlashCommandTool/SlashCommandTool.js.map +3 -3
  292. package/dist/tools/TaskCreateTool/TaskCreateTool.js.map +1 -1
  293. package/dist/tools/TaskGetTool/TaskGetTool.js.map +1 -1
  294. package/dist/tools/TaskListTool/TaskListTool.js.map +1 -1
  295. package/dist/tools/TaskOutputTool/TaskOutputTool.js.map +1 -1
  296. package/dist/tools/TaskStopTool/TaskStopTool.js.map +1 -1
  297. package/dist/tools/TaskTool/TaskTool.js +84 -11
  298. package/dist/tools/TaskTool/TaskTool.js.map +2 -2
  299. package/dist/tools/TaskTool/prompt.js +12 -6
  300. package/dist/tools/TaskTool/prompt.js.map +2 -2
  301. package/dist/tools/TaskUpdateTool/TaskUpdateTool.js.map +1 -1
  302. package/dist/tools/ThinkTool/ThinkTool.js.map +1 -1
  303. package/dist/tools/TodoWriteTool/TodoWriteTool.js.map +1 -1
  304. package/dist/tools/URLFetcherTool/URLFetcherTool.js.map +1 -1
  305. package/dist/tools/WebSearchTool/WebSearchTool.js.map +1 -1
  306. package/dist/tools/WebSearchTool/searchProviders.js +2 -1
  307. package/dist/tools/WebSearchTool/searchProviders.js.map +2 -2
  308. package/dist/tools/lsTool/lsTool.js.map +2 -2
  309. package/dist/tools/lsTool/prompt.js.map +1 -1
  310. package/dist/tools.js +14 -3
  311. package/dist/tools.js.map +2 -2
  312. package/dist/types/PermissionMode.js +21 -1
  313. package/dist/types/PermissionMode.js.map +2 -2
  314. package/dist/types/agentTeams.js +1 -0
  315. package/dist/types/agentTeams.js.map +7 -0
  316. package/dist/types/hooks.js +8 -2
  317. package/dist/types/hooks.js.map +2 -2
  318. package/dist/types/plugin.js +3 -5
  319. package/dist/types/plugin.js.map +2 -2
  320. package/dist/utils/agentHookExecutor.js +1 -4
  321. package/dist/utils/agentHookExecutor.js.map +2 -2
  322. package/dist/utils/agentLoader.js +91 -15
  323. package/dist/utils/agentLoader.js.map +2 -2
  324. package/dist/utils/agentMemory.js.map +2 -2
  325. package/dist/utils/animationManager.js +1 -1
  326. package/dist/utils/animationManager.js.map +2 -2
  327. package/dist/utils/ask.js +1 -1
  328. package/dist/utils/async.js +5 -1
  329. package/dist/utils/async.js.map +2 -2
  330. package/dist/utils/autoCompactCore.js +60 -0
  331. package/dist/utils/autoCompactCore.js.map +2 -2
  332. package/dist/utils/claudeCodeSync.js +439 -0
  333. package/dist/utils/claudeCodeSync.js.map +7 -0
  334. package/dist/utils/config.js +27 -151
  335. package/dist/utils/config.js.map +2 -2
  336. package/dist/utils/configSchema.js +227 -0
  337. package/dist/utils/configSchema.js.map +7 -0
  338. package/dist/utils/debugLogger.js.map +2 -2
  339. package/dist/utils/env.js +4 -3
  340. package/dist/utils/env.js.map +2 -2
  341. package/dist/utils/envConfig.js +34 -0
  342. package/dist/utils/envConfig.js.map +3 -3
  343. package/dist/utils/execFileNoThrow.js +2 -1
  344. package/dist/utils/execFileNoThrow.js.map +2 -2
  345. package/dist/utils/gpt5.js +146 -0
  346. package/dist/utils/gpt5.js.map +7 -0
  347. package/dist/utils/hookManager.js +374 -140
  348. package/dist/utils/hookManager.js.map +2 -2
  349. package/dist/utils/markdown.js +47 -0
  350. package/dist/utils/markdown.js.map +2 -2
  351. package/dist/utils/marketplaceManager.js +80 -43
  352. package/dist/utils/marketplaceManager.js.map +2 -2
  353. package/dist/utils/memoizeWithTTL.js +25 -0
  354. package/dist/utils/memoizeWithTTL.js.map +7 -0
  355. package/dist/utils/messages.js +2 -2
  356. package/dist/utils/messages.js.map +2 -2
  357. package/dist/utils/model.js +34 -9
  358. package/dist/utils/model.js.map +2 -2
  359. package/dist/utils/pluginInstaller.js +68 -29
  360. package/dist/utils/pluginInstaller.js.map +2 -2
  361. package/dist/utils/pluginLoader.js +249 -57
  362. package/dist/utils/pluginLoader.js.map +2 -2
  363. package/dist/utils/repoFetcher.js +110 -0
  364. package/dist/utils/repoFetcher.js.map +7 -0
  365. package/dist/utils/safeFetch.js +45 -0
  366. package/dist/utils/safeFetch.js.map +7 -0
  367. package/dist/utils/skillLoader.js +77 -12
  368. package/dist/utils/skillLoader.js.map +2 -2
  369. package/dist/utils/streamingState.js +52 -0
  370. package/dist/utils/streamingState.js.map +7 -0
  371. package/dist/utils/stringSubstitution.js +4 -5
  372. package/dist/utils/stringSubstitution.js.map +2 -2
  373. package/dist/utils/style.js +6 -3
  374. package/dist/utils/style.js.map +2 -2
  375. package/dist/utils/teamConfig.js +162 -16
  376. package/dist/utils/teamConfig.js.map +2 -2
  377. package/dist/utils/terminal.js +1 -1
  378. package/dist/utils/terminal.js.map +2 -2
  379. package/dist/utils/toolRiskClassification.js +0 -6
  380. package/dist/utils/toolRiskClassification.js.map +2 -2
  381. package/dist/version.js +2 -2
  382. package/dist/version.js.map +1 -1
  383. package/package.json +7 -6
@@ -0,0 +1,114 @@
1
+ import { existsSync, readFileSync, writeFileSync, mkdirSync } from "fs";
2
+ import { join } from "path";
3
+ import { homedir } from "os";
4
+ class Mailbox {
5
+ messages = [];
6
+ storePath;
7
+ listeners = /* @__PURE__ */ new Map();
8
+ constructor(teamName) {
9
+ this.storePath = join(
10
+ homedir(),
11
+ ".minto",
12
+ "teams",
13
+ teamName,
14
+ "mailbox.json"
15
+ );
16
+ }
17
+ /**
18
+ * Send a message to a specific teammate or broadcast to all
19
+ */
20
+ send(from, to, content) {
21
+ const msg = {
22
+ id: `msg-${Date.now()}-${Math.random().toString(36).slice(2, 8)}`,
23
+ from,
24
+ to,
25
+ content,
26
+ timestamp: Date.now(),
27
+ type: to === "all" ? "broadcast" : "direct"
28
+ };
29
+ this.messages.push(msg);
30
+ this.persist();
31
+ const targetListeners = to === "all" ? Array.from(this.listeners.values()).flat() : this.listeners.get(to) || [];
32
+ for (const listener of targetListeners) {
33
+ try {
34
+ listener(msg);
35
+ } catch {
36
+ }
37
+ }
38
+ return msg;
39
+ }
40
+ /**
41
+ * Get unread messages for a teammate
42
+ */
43
+ getUnread(recipientId) {
44
+ return this.messages.filter(
45
+ (m) => !m.read && (m.to === recipientId || m.to === "all") && m.from !== recipientId
46
+ );
47
+ }
48
+ /**
49
+ * Mark messages as read
50
+ */
51
+ markRead(messageIds) {
52
+ const idSet = new Set(messageIds);
53
+ for (const msg of this.messages) {
54
+ if (idSet.has(msg.id)) {
55
+ msg.read = true;
56
+ }
57
+ }
58
+ this.persist();
59
+ }
60
+ /**
61
+ * Subscribe to messages for a teammate
62
+ */
63
+ subscribe(recipientId, callback) {
64
+ const existing = this.listeners.get(recipientId) || [];
65
+ existing.push(callback);
66
+ this.listeners.set(recipientId, existing);
67
+ return () => {
68
+ const list = this.listeners.get(recipientId);
69
+ if (list) {
70
+ const idx = list.indexOf(callback);
71
+ if (idx >= 0) list.splice(idx, 1);
72
+ }
73
+ };
74
+ }
75
+ /**
76
+ * Get all messages (for debugging/display)
77
+ */
78
+ getAll() {
79
+ return [...this.messages];
80
+ }
81
+ /**
82
+ * Persist mailbox to disk (for cross-process teams)
83
+ */
84
+ persist() {
85
+ try {
86
+ const dir = join(this.storePath, "..");
87
+ if (!existsSync(dir)) {
88
+ mkdirSync(dir, { recursive: true });
89
+ }
90
+ writeFileSync(
91
+ this.storePath,
92
+ JSON.stringify(this.messages, null, 2),
93
+ "utf-8"
94
+ );
95
+ } catch {
96
+ }
97
+ }
98
+ /**
99
+ * Load mailbox from disk
100
+ */
101
+ load() {
102
+ if (!existsSync(this.storePath)) return;
103
+ try {
104
+ const content = readFileSync(this.storePath, "utf-8");
105
+ this.messages = JSON.parse(content);
106
+ } catch {
107
+ this.messages = [];
108
+ }
109
+ }
110
+ }
111
+ export {
112
+ Mailbox
113
+ };
114
+ //# sourceMappingURL=mailbox.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../src/services/agentTeams/mailbox.ts"],
4
+ "sourcesContent": ["/**\n * Agent Teams Mailbox\n *\n * Message passing system between teammates.\n * In-memory for in-process mode; file-based for cross-process (tmux).\n */\n\nimport { existsSync, readFileSync, writeFileSync, mkdirSync } from 'fs'\nimport { join } from 'path'\nimport { homedir } from 'os'\nimport type { TeamMessage } from '../../types/agentTeams'\n\n/**\n * Mailbox for a team's inter-agent messaging\n */\nexport class Mailbox {\n private messages: TeamMessage[] = []\n private storePath: string\n private listeners = new Map<string, ((msg: TeamMessage) => void)[]>()\n\n constructor(teamName: string) {\n this.storePath = join(\n homedir(),\n '.minto',\n 'teams',\n teamName,\n 'mailbox.json',\n )\n }\n\n /**\n * Send a message to a specific teammate or broadcast to all\n */\n send(from: string, to: string | 'all', content: string): TeamMessage {\n const msg: TeamMessage = {\n id: `msg-${Date.now()}-${Math.random().toString(36).slice(2, 8)}`,\n from,\n to,\n content,\n timestamp: Date.now(),\n type: to === 'all' ? 'broadcast' : 'direct',\n }\n\n this.messages.push(msg)\n this.persist()\n\n // Notify listeners\n const targetListeners =\n to === 'all'\n ? Array.from(this.listeners.values()).flat()\n : this.listeners.get(to) || []\n\n for (const listener of targetListeners) {\n try {\n listener(msg)\n } catch {\n // Don't let listener errors break sending\n }\n }\n\n return msg\n }\n\n /**\n * Get unread messages for a teammate\n */\n getUnread(recipientId: string): TeamMessage[] {\n return this.messages.filter(\n m =>\n !m.read &&\n (m.to === recipientId || m.to === 'all') &&\n m.from !== recipientId,\n )\n }\n\n /**\n * Mark messages as read\n */\n markRead(messageIds: string[]): void {\n const idSet = new Set(messageIds)\n for (const msg of this.messages) {\n if (idSet.has(msg.id)) {\n msg.read = true\n }\n }\n this.persist()\n }\n\n /**\n * Subscribe to messages for a teammate\n */\n subscribe(\n recipientId: string,\n callback: (msg: TeamMessage) => void,\n ): () => void {\n const existing = this.listeners.get(recipientId) || []\n existing.push(callback)\n this.listeners.set(recipientId, existing)\n\n return () => {\n const list = this.listeners.get(recipientId)\n if (list) {\n const idx = list.indexOf(callback)\n if (idx >= 0) list.splice(idx, 1)\n }\n }\n }\n\n /**\n * Get all messages (for debugging/display)\n */\n getAll(): TeamMessage[] {\n return [...this.messages]\n }\n\n /**\n * Persist mailbox to disk (for cross-process teams)\n */\n private persist(): void {\n try {\n const dir = join(this.storePath, '..')\n if (!existsSync(dir)) {\n mkdirSync(dir, { recursive: true })\n }\n writeFileSync(\n this.storePath,\n JSON.stringify(this.messages, null, 2),\n 'utf-8',\n )\n } catch {\n // Best-effort persistence\n }\n }\n\n /**\n * Load mailbox from disk\n */\n load(): void {\n if (!existsSync(this.storePath)) return\n\n try {\n const content = readFileSync(this.storePath, 'utf-8')\n this.messages = JSON.parse(content)\n } catch {\n // Start fresh on parse error\n this.messages = []\n }\n }\n}\n"],
5
+ "mappings": "AAOA,SAAS,YAAY,cAAc,eAAe,iBAAiB;AACnE,SAAS,YAAY;AACrB,SAAS,eAAe;AAMjB,MAAM,QAAQ;AAAA,EACX,WAA0B,CAAC;AAAA,EAC3B;AAAA,EACA,YAAY,oBAAI,IAA4C;AAAA,EAEpE,YAAY,UAAkB;AAC5B,SAAK,YAAY;AAAA,MACf,QAAQ;AAAA,MACR;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,IACF;AAAA,EACF;AAAA;AAAA;AAAA;AAAA,EAKA,KAAK,MAAc,IAAoB,SAA8B;AACnE,UAAM,MAAmB;AAAA,MACvB,IAAI,OAAO,KAAK,IAAI,CAAC,IAAI,KAAK,OAAO,EAAE,SAAS,EAAE,EAAE,MAAM,GAAG,CAAC,CAAC;AAAA,MAC/D;AAAA,MACA;AAAA,MACA;AAAA,MACA,WAAW,KAAK,IAAI;AAAA,MACpB,MAAM,OAAO,QAAQ,cAAc;AAAA,IACrC;AAEA,SAAK,SAAS,KAAK,GAAG;AACtB,SAAK,QAAQ;AAGb,UAAM,kBACJ,OAAO,QACH,MAAM,KAAK,KAAK,UAAU,OAAO,CAAC,EAAE,KAAK,IACzC,KAAK,UAAU,IAAI,EAAE,KAAK,CAAC;AAEjC,eAAW,YAAY,iBAAiB;AACtC,UAAI;AACF,iBAAS,GAAG;AAAA,MACd,QAAQ;AAAA,MAER;AAAA,IACF;AAEA,WAAO;AAAA,EACT;AAAA;AAAA;AAAA;AAAA,EAKA,UAAU,aAAoC;AAC5C,WAAO,KAAK,SAAS;AAAA,MACnB,OACE,CAAC,EAAE,SACF,EAAE,OAAO,eAAe,EAAE,OAAO,UAClC,EAAE,SAAS;AAAA,IACf;AAAA,EACF;AAAA;AAAA;AAAA;AAAA,EAKA,SAAS,YAA4B;AACnC,UAAM,QAAQ,IAAI,IAAI,UAAU;AAChC,eAAW,OAAO,KAAK,UAAU;AAC/B,UAAI,MAAM,IAAI,IAAI,EAAE,GAAG;AACrB,YAAI,OAAO;AAAA,MACb;AAAA,IACF;AACA,SAAK,QAAQ;AAAA,EACf;AAAA;AAAA;AAAA;AAAA,EAKA,UACE,aACA,UACY;AACZ,UAAM,WAAW,KAAK,UAAU,IAAI,WAAW,KAAK,CAAC;AACrD,aAAS,KAAK,QAAQ;AACtB,SAAK,UAAU,IAAI,aAAa,QAAQ;AAExC,WAAO,MAAM;AACX,YAAM,OAAO,KAAK,UAAU,IAAI,WAAW;AAC3C,UAAI,MAAM;AACR,cAAM,MAAM,KAAK,QAAQ,QAAQ;AACjC,YAAI,OAAO,EAAG,MAAK,OAAO,KAAK,CAAC;AAAA,MAClC;AAAA,IACF;AAAA,EACF;AAAA;AAAA;AAAA;AAAA,EAKA,SAAwB;AACtB,WAAO,CAAC,GAAG,KAAK,QAAQ;AAAA,EAC1B;AAAA;AAAA;AAAA;AAAA,EAKQ,UAAgB;AACtB,QAAI;AACF,YAAM,MAAM,KAAK,KAAK,WAAW,IAAI;AACrC,UAAI,CAAC,WAAW,GAAG,GAAG;AACpB,kBAAU,KAAK,EAAE,WAAW,KAAK,CAAC;AAAA,MACpC;AACA;AAAA,QACE,KAAK;AAAA,QACL,KAAK,UAAU,KAAK,UAAU,MAAM,CAAC;AAAA,QACrC;AAAA,MACF;AAAA,IACF,QAAQ;AAAA,IAER;AAAA,EACF;AAAA;AAAA;AAAA;AAAA,EAKA,OAAa;AACX,QAAI,CAAC,WAAW,KAAK,SAAS,EAAG;AAEjC,QAAI;AACF,YAAM,UAAU,aAAa,KAAK,WAAW,OAAO;AACpD,WAAK,WAAW,KAAK,MAAM,OAAO;AAAA,IACpC,QAAQ;AAEN,WAAK,WAAW,CAAC;AAAA,IACnB;AAAA,EACF;AACF;",
6
+ "names": []
7
+ }
@@ -0,0 +1,149 @@
1
+ import { existsSync, mkdirSync, writeFileSync, readFileSync } from "fs";
2
+ import { join } from "path";
3
+ import { homedir } from "os";
4
+ import { Mailbox } from "./mailbox.js";
5
+ import { TeamTaskStore } from "./teamTaskStore.js";
6
+ import { emitReminderEvent } from "../systemReminder.js";
7
+ function isAgentTeamsEnabled() {
8
+ return process.env.MINTO_EXPERIMENTAL_AGENT_TEAMS === "1";
9
+ }
10
+ const activeTeams = /* @__PURE__ */ new Map();
11
+ function getTeamsDir() {
12
+ return join(homedir(), ".minto", "teams");
13
+ }
14
+ function createTeam(config) {
15
+ if (!isAgentTeamsEnabled()) {
16
+ throw new Error(
17
+ "Agent Teams is experimental. Set MINTO_EXPERIMENTAL_AGENT_TEAMS=1 to enable."
18
+ );
19
+ }
20
+ if (activeTeams.has(config.name)) {
21
+ throw new Error(`Team "${config.name}" already exists`);
22
+ }
23
+ const team = {
24
+ name: config.name,
25
+ config,
26
+ members: [],
27
+ createdAt: Date.now()
28
+ };
29
+ const mailbox = new Mailbox(config.name);
30
+ const taskStore = new TeamTaskStore(config.name);
31
+ taskStore.load();
32
+ mailbox.load();
33
+ const teamDir = join(getTeamsDir(), config.name);
34
+ if (!existsSync(teamDir)) {
35
+ mkdirSync(teamDir, { recursive: true });
36
+ }
37
+ writeFileSync(
38
+ join(teamDir, "team.json"),
39
+ JSON.stringify(team, null, 2),
40
+ "utf-8"
41
+ );
42
+ activeTeams.set(config.name, { team, mailbox, taskStore });
43
+ emitReminderEvent("team:coordination", {
44
+ teamId: config.name,
45
+ message: `Team "${config.name}" created (max ${config.maxTeammates} teammates).`
46
+ });
47
+ return team;
48
+ }
49
+ function addTeammate(teamName, teammate) {
50
+ const entry = activeTeams.get(teamName);
51
+ if (!entry) {
52
+ throw new Error(`Team "${teamName}" not found`);
53
+ }
54
+ const fullTeammate = {
55
+ ...teammate,
56
+ lastActivity: Date.now()
57
+ };
58
+ entry.team.members.push(fullTeammate);
59
+ emitReminderEvent("team:coordination", {
60
+ teamId: teamName,
61
+ message: `Teammate "${teammate.id}" (${teammate.agentType}) joined team "${teamName}".`
62
+ });
63
+ const teamDir = join(getTeamsDir(), teamName);
64
+ writeFileSync(
65
+ join(teamDir, "team.json"),
66
+ JSON.stringify(entry.team, null, 2),
67
+ "utf-8"
68
+ );
69
+ return fullTeammate;
70
+ }
71
+ function updateTeammateStatus(teamName, teammateId, status, currentTaskId) {
72
+ const entry = activeTeams.get(teamName);
73
+ if (!entry) return;
74
+ const member = entry.team.members.find((m) => m.id === teammateId);
75
+ if (!member) return;
76
+ member.status = status;
77
+ member.lastActivity = Date.now();
78
+ if (currentTaskId !== void 0) {
79
+ member.currentTaskId = currentTaskId;
80
+ }
81
+ }
82
+ function getTeam(teamName) {
83
+ return activeTeams.get(teamName);
84
+ }
85
+ function getActiveTeams() {
86
+ return Array.from(activeTeams.values()).map((e) => e.team);
87
+ }
88
+ function disbandTeam(teamName) {
89
+ const entry = activeTeams.get(teamName);
90
+ if (!entry) return;
91
+ for (const member of entry.team.members) {
92
+ member.status = "stopped";
93
+ }
94
+ const teamDir = join(getTeamsDir(), teamName);
95
+ if (existsSync(teamDir)) {
96
+ writeFileSync(
97
+ join(teamDir, "team.json"),
98
+ JSON.stringify(entry.team, null, 2),
99
+ "utf-8"
100
+ );
101
+ }
102
+ activeTeams.delete(teamName);
103
+ emitReminderEvent("team:shutdown", {
104
+ teamId: teamName,
105
+ reason: "disbanded"
106
+ });
107
+ }
108
+ function loadTeam(teamName) {
109
+ const teamFile = join(getTeamsDir(), teamName, "team.json");
110
+ if (!existsSync(teamFile)) return null;
111
+ try {
112
+ const content = readFileSync(teamFile, "utf-8");
113
+ const team = JSON.parse(content);
114
+ const mailbox = new Mailbox(teamName);
115
+ const taskStore = new TeamTaskStore(teamName);
116
+ mailbox.load();
117
+ taskStore.load();
118
+ activeTeams.set(teamName, { team, mailbox, taskStore });
119
+ return team;
120
+ } catch {
121
+ return null;
122
+ }
123
+ }
124
+ function resolveDisplayMode(mode) {
125
+ if (mode === "tmux") return "tmux";
126
+ if (mode === "in-process") return "in-process";
127
+ try {
128
+ const { execSync } = require("child_process");
129
+ execSync("which tmux", { stdio: "pipe" });
130
+ if (process.env.TMUX) {
131
+ return "tmux";
132
+ }
133
+ return "in-process";
134
+ } catch {
135
+ return "in-process";
136
+ }
137
+ }
138
+ export {
139
+ addTeammate,
140
+ createTeam,
141
+ disbandTeam,
142
+ getActiveTeams,
143
+ getTeam,
144
+ isAgentTeamsEnabled,
145
+ loadTeam,
146
+ resolveDisplayMode,
147
+ updateTeammateStatus
148
+ };
149
+ //# sourceMappingURL=teamManager.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../src/services/agentTeams/teamManager.ts"],
4
+ "sourcesContent": ["/**\n * Team Manager\n *\n * Central coordinator for agent teams lifecycle.\n * Manages team creation, teammate spawning, and disbanding.\n *\n * Experimental: Enable with MINTO_EXPERIMENTAL_AGENT_TEAMS=1\n */\n\nimport { existsSync, mkdirSync, writeFileSync, readFileSync, rmSync } from 'fs'\nimport { join } from 'path'\nimport { homedir } from 'os'\nimport type {\n Team,\n TeamConfig,\n Teammate,\n TeamDisplayMode,\n} from '../../types/agentTeams'\nimport { Mailbox } from './mailbox'\nimport { TeamTaskStore } from './teamTaskStore'\nimport { emitReminderEvent } from '../systemReminder'\n\n/**\n * Check if Agent Teams feature is enabled\n */\nexport function isAgentTeamsEnabled(): boolean {\n return process.env.MINTO_EXPERIMENTAL_AGENT_TEAMS === '1'\n}\n\n/**\n * Active teams registry\n */\nconst activeTeams = new Map<\n string,\n {\n team: Team\n mailbox: Mailbox\n taskStore: TeamTaskStore\n }\n>()\n\n/**\n * Get the teams storage directory\n */\nfunction getTeamsDir(): string {\n return join(homedir(), '.minto', 'teams')\n}\n\n/**\n * Create a new team\n */\nexport function createTeam(config: TeamConfig): Team {\n if (!isAgentTeamsEnabled()) {\n throw new Error(\n 'Agent Teams is experimental. Set MINTO_EXPERIMENTAL_AGENT_TEAMS=1 to enable.',\n )\n }\n\n if (activeTeams.has(config.name)) {\n throw new Error(`Team \"${config.name}\" already exists`)\n }\n\n const team: Team = {\n name: config.name,\n config,\n members: [],\n createdAt: Date.now(),\n }\n\n const mailbox = new Mailbox(config.name)\n const taskStore = new TeamTaskStore(config.name)\n taskStore.load()\n mailbox.load()\n\n // Persist team config\n const teamDir = join(getTeamsDir(), config.name)\n if (!existsSync(teamDir)) {\n mkdirSync(teamDir, { recursive: true })\n }\n writeFileSync(\n join(teamDir, 'team.json'),\n JSON.stringify(team, null, 2),\n 'utf-8',\n )\n\n activeTeams.set(config.name, { team, mailbox, taskStore })\n\n emitReminderEvent('team:coordination', {\n teamId: config.name,\n message: `Team \"${config.name}\" created (max ${config.maxTeammates} teammates).`,\n })\n\n return team\n}\n\n/**\n * Add a teammate to a team\n */\nexport function addTeammate(\n teamName: string,\n teammate: Omit<Teammate, 'lastActivity'>,\n): Teammate {\n const entry = activeTeams.get(teamName)\n if (!entry) {\n throw new Error(`Team \"${teamName}\" not found`)\n }\n\n const fullTeammate: Teammate = {\n ...teammate,\n lastActivity: Date.now(),\n }\n\n entry.team.members.push(fullTeammate)\n\n emitReminderEvent('team:coordination', {\n teamId: teamName,\n message: `Teammate \"${teammate.id}\" (${teammate.agentType}) joined team \"${teamName}\".`,\n })\n\n // Persist\n const teamDir = join(getTeamsDir(), teamName)\n writeFileSync(\n join(teamDir, 'team.json'),\n JSON.stringify(entry.team, null, 2),\n 'utf-8',\n )\n\n return fullTeammate\n}\n\n/**\n * Update teammate status\n */\nexport function updateTeammateStatus(\n teamName: string,\n teammateId: string,\n status: Teammate['status'],\n currentTaskId?: string,\n): void {\n const entry = activeTeams.get(teamName)\n if (!entry) return\n\n const member = entry.team.members.find(m => m.id === teammateId)\n if (!member) return\n\n member.status = status\n member.lastActivity = Date.now()\n if (currentTaskId !== undefined) {\n member.currentTaskId = currentTaskId\n }\n}\n\n/**\n * Get a team by name\n */\nexport function getTeam(\n teamName: string,\n): { team: Team; mailbox: Mailbox; taskStore: TeamTaskStore } | undefined {\n return activeTeams.get(teamName)\n}\n\n/**\n * Get all active teams\n */\nexport function getActiveTeams(): Team[] {\n return Array.from(activeTeams.values()).map(e => e.team)\n}\n\n/**\n * Disband a team\n */\nexport function disbandTeam(teamName: string): void {\n const entry = activeTeams.get(teamName)\n if (!entry) return\n\n // Mark all members as stopped\n for (const member of entry.team.members) {\n member.status = 'stopped'\n }\n\n // Persist final state\n const teamDir = join(getTeamsDir(), teamName)\n if (existsSync(teamDir)) {\n writeFileSync(\n join(teamDir, 'team.json'),\n JSON.stringify(entry.team, null, 2),\n 'utf-8',\n )\n }\n\n activeTeams.delete(teamName)\n\n emitReminderEvent('team:shutdown', {\n teamId: teamName,\n reason: 'disbanded',\n })\n}\n\n/**\n * Load a persisted team from disk\n */\nexport function loadTeam(teamName: string): Team | null {\n const teamFile = join(getTeamsDir(), teamName, 'team.json')\n if (!existsSync(teamFile)) return null\n\n try {\n const content = readFileSync(teamFile, 'utf-8')\n const team = JSON.parse(content) as Team\n\n const mailbox = new Mailbox(teamName)\n const taskStore = new TeamTaskStore(teamName)\n mailbox.load()\n taskStore.load()\n\n activeTeams.set(teamName, { team, mailbox, taskStore })\n return team\n } catch {\n return null\n }\n}\n\n/**\n * Resolve display mode based on config and environment\n */\nexport function resolveDisplayMode(\n mode: TeamDisplayMode,\n): 'in-process' | 'tmux' {\n if (mode === 'tmux') return 'tmux'\n if (mode === 'in-process') return 'in-process'\n\n // Auto: check if tmux is available\n try {\n const { execSync } = require('child_process')\n execSync('which tmux', { stdio: 'pipe' })\n // tmux available, check if we're already in a tmux session\n if (process.env.TMUX) {\n return 'tmux'\n }\n return 'in-process' // Default to in-process even if tmux available\n } catch {\n return 'in-process'\n }\n}\n"],
5
+ "mappings": "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",
6
+ "names": []
7
+ }
@@ -0,0 +1,114 @@
1
+ import { existsSync, readFileSync, writeFileSync, mkdirSync } from "fs";
2
+ import { join } from "path";
3
+ import { homedir } from "os";
4
+ class TeamTaskStore {
5
+ storePath;
6
+ tasks = [];
7
+ constructor(teamName) {
8
+ this.storePath = join(homedir(), ".minto", "tasks", teamName, "tasks.json");
9
+ }
10
+ /**
11
+ * Load tasks from disk
12
+ */
13
+ load() {
14
+ if (!existsSync(this.storePath)) {
15
+ this.tasks = [];
16
+ return;
17
+ }
18
+ try {
19
+ const content = readFileSync(this.storePath, "utf-8");
20
+ this.tasks = JSON.parse(content);
21
+ } catch {
22
+ this.tasks = [];
23
+ }
24
+ }
25
+ /**
26
+ * Save tasks to disk (atomic write)
27
+ */
28
+ save() {
29
+ try {
30
+ const dir = join(this.storePath, "..");
31
+ if (!existsSync(dir)) {
32
+ mkdirSync(dir, { recursive: true });
33
+ }
34
+ const tmpPath = `${this.storePath}.tmp`;
35
+ writeFileSync(tmpPath, JSON.stringify(this.tasks, null, 2), "utf-8");
36
+ const { renameSync } = require("fs");
37
+ renameSync(tmpPath, this.storePath);
38
+ } catch {
39
+ writeFileSync(
40
+ this.storePath,
41
+ JSON.stringify(this.tasks, null, 2),
42
+ "utf-8"
43
+ );
44
+ }
45
+ }
46
+ /**
47
+ * Create a new task
48
+ */
49
+ create(subject, description) {
50
+ this.load();
51
+ const maxId = this.tasks.reduce(
52
+ (max, t) => Math.max(max, parseInt(t.id, 10) || 0),
53
+ 0
54
+ );
55
+ const task = {
56
+ id: String(maxId + 1),
57
+ subject,
58
+ description,
59
+ status: "pending",
60
+ createdAt: Date.now(),
61
+ updatedAt: Date.now()
62
+ };
63
+ this.tasks.push(task);
64
+ this.save();
65
+ return task;
66
+ }
67
+ /**
68
+ * Claim a task (compare-and-swap to prevent double-claiming)
69
+ */
70
+ claim(taskId, assignee) {
71
+ this.load();
72
+ const task = this.tasks.find((t) => t.id === taskId);
73
+ if (!task) return false;
74
+ if (task.status !== "pending" || task.assignee) {
75
+ return false;
76
+ }
77
+ task.assignee = assignee;
78
+ task.status = "in_progress";
79
+ task.updatedAt = Date.now();
80
+ this.save();
81
+ return true;
82
+ }
83
+ /**
84
+ * Complete a task
85
+ */
86
+ complete(taskId, assignee) {
87
+ this.load();
88
+ const task = this.tasks.find((t) => t.id === taskId);
89
+ if (!task) return false;
90
+ if (task.assignee !== assignee) return false;
91
+ task.status = "completed";
92
+ task.updatedAt = Date.now();
93
+ this.save();
94
+ return true;
95
+ }
96
+ /**
97
+ * Get all tasks
98
+ */
99
+ getAll() {
100
+ this.load();
101
+ return [...this.tasks];
102
+ }
103
+ /**
104
+ * Get unclaimed tasks
105
+ */
106
+ getUnclaimed() {
107
+ this.load();
108
+ return this.tasks.filter((t) => t.status === "pending" && !t.assignee);
109
+ }
110
+ }
111
+ export {
112
+ TeamTaskStore
113
+ };
114
+ //# sourceMappingURL=teamTaskStore.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../src/services/agentTeams/teamTaskStore.ts"],
4
+ "sourcesContent": ["/**\n * Team Task Store\n *\n * Shared task storage for agent teams.\n * File-based with atomic writes for cross-process safety.\n */\n\nimport { existsSync, readFileSync, writeFileSync, mkdirSync } from 'fs'\nimport { join } from 'path'\nimport { homedir } from 'os'\n\n/**\n * Team task (simplified version of Task for cross-process sharing)\n */\nexport interface TeamTask {\n id: string\n subject: string\n description: string\n status: 'pending' | 'in_progress' | 'completed'\n assignee?: string\n createdAt: number\n updatedAt: number\n}\n\n/**\n * Shared task store for a team\n */\nexport class TeamTaskStore {\n private storePath: string\n private tasks: TeamTask[] = []\n\n constructor(teamName: string) {\n this.storePath = join(homedir(), '.minto', 'tasks', teamName, 'tasks.json')\n }\n\n /**\n * Load tasks from disk\n */\n load(): void {\n if (!existsSync(this.storePath)) {\n this.tasks = []\n return\n }\n\n try {\n const content = readFileSync(this.storePath, 'utf-8')\n this.tasks = JSON.parse(content)\n } catch {\n this.tasks = []\n }\n }\n\n /**\n * Save tasks to disk (atomic write)\n */\n private save(): void {\n try {\n const dir = join(this.storePath, '..')\n if (!existsSync(dir)) {\n mkdirSync(dir, { recursive: true })\n }\n\n // Atomic write: write to temp file then rename\n const tmpPath = `${this.storePath}.tmp`\n writeFileSync(tmpPath, JSON.stringify(this.tasks, null, 2), 'utf-8')\n\n // On most systems, rename is atomic within the same filesystem\n const { renameSync } = require('fs')\n renameSync(tmpPath, this.storePath)\n } catch {\n // Fallback: direct write\n writeFileSync(\n this.storePath,\n JSON.stringify(this.tasks, null, 2),\n 'utf-8',\n )\n }\n }\n\n /**\n * Create a new task\n */\n create(subject: string, description: string): TeamTask {\n // Reload to get latest state (cross-process safety)\n this.load()\n\n const maxId = this.tasks.reduce(\n (max, t) => Math.max(max, parseInt(t.id, 10) || 0),\n 0,\n )\n\n const task: TeamTask = {\n id: String(maxId + 1),\n subject,\n description,\n status: 'pending',\n createdAt: Date.now(),\n updatedAt: Date.now(),\n }\n\n this.tasks.push(task)\n this.save()\n return task\n }\n\n /**\n * Claim a task (compare-and-swap to prevent double-claiming)\n */\n claim(taskId: string, assignee: string): boolean {\n // Reload to get latest state\n this.load()\n\n const task = this.tasks.find(t => t.id === taskId)\n if (!task) return false\n\n // CAS: only claim if still pending and unassigned\n if (task.status !== 'pending' || task.assignee) {\n return false\n }\n\n task.assignee = assignee\n task.status = 'in_progress'\n task.updatedAt = Date.now()\n this.save()\n return true\n }\n\n /**\n * Complete a task\n */\n complete(taskId: string, assignee: string): boolean {\n this.load()\n\n const task = this.tasks.find(t => t.id === taskId)\n if (!task) return false\n\n // Only the assignee can complete\n if (task.assignee !== assignee) return false\n\n task.status = 'completed'\n task.updatedAt = Date.now()\n this.save()\n return true\n }\n\n /**\n * Get all tasks\n */\n getAll(): TeamTask[] {\n this.load()\n return [...this.tasks]\n }\n\n /**\n * Get unclaimed tasks\n */\n getUnclaimed(): TeamTask[] {\n this.load()\n return this.tasks.filter(t => t.status === 'pending' && !t.assignee)\n }\n}\n"],
5
+ "mappings": "AAOA,SAAS,YAAY,cAAc,eAAe,iBAAiB;AACnE,SAAS,YAAY;AACrB,SAAS,eAAe;AAkBjB,MAAM,cAAc;AAAA,EACjB;AAAA,EACA,QAAoB,CAAC;AAAA,EAE7B,YAAY,UAAkB;AAC5B,SAAK,YAAY,KAAK,QAAQ,GAAG,UAAU,SAAS,UAAU,YAAY;AAAA,EAC5E;AAAA;AAAA;AAAA;AAAA,EAKA,OAAa;AACX,QAAI,CAAC,WAAW,KAAK,SAAS,GAAG;AAC/B,WAAK,QAAQ,CAAC;AACd;AAAA,IACF;AAEA,QAAI;AACF,YAAM,UAAU,aAAa,KAAK,WAAW,OAAO;AACpD,WAAK,QAAQ,KAAK,MAAM,OAAO;AAAA,IACjC,QAAQ;AACN,WAAK,QAAQ,CAAC;AAAA,IAChB;AAAA,EACF;AAAA;AAAA;AAAA;AAAA,EAKQ,OAAa;AACnB,QAAI;AACF,YAAM,MAAM,KAAK,KAAK,WAAW,IAAI;AACrC,UAAI,CAAC,WAAW,GAAG,GAAG;AACpB,kBAAU,KAAK,EAAE,WAAW,KAAK,CAAC;AAAA,MACpC;AAGA,YAAM,UAAU,GAAG,KAAK,SAAS;AACjC,oBAAc,SAAS,KAAK,UAAU,KAAK,OAAO,MAAM,CAAC,GAAG,OAAO;AAGnE,YAAM,EAAE,WAAW,IAAI,QAAQ,IAAI;AACnC,iBAAW,SAAS,KAAK,SAAS;AAAA,IACpC,QAAQ;AAEN;AAAA,QACE,KAAK;AAAA,QACL,KAAK,UAAU,KAAK,OAAO,MAAM,CAAC;AAAA,QAClC;AAAA,MACF;AAAA,IACF;AAAA,EACF;AAAA;AAAA;AAAA;AAAA,EAKA,OAAO,SAAiB,aAA+B;AAErD,SAAK,KAAK;AAEV,UAAM,QAAQ,KAAK,MAAM;AAAA,MACvB,CAAC,KAAK,MAAM,KAAK,IAAI,KAAK,SAAS,EAAE,IAAI,EAAE,KAAK,CAAC;AAAA,MACjD;AAAA,IACF;AAEA,UAAM,OAAiB;AAAA,MACrB,IAAI,OAAO,QAAQ,CAAC;AAAA,MACpB;AAAA,MACA;AAAA,MACA,QAAQ;AAAA,MACR,WAAW,KAAK,IAAI;AAAA,MACpB,WAAW,KAAK,IAAI;AAAA,IACtB;AAEA,SAAK,MAAM,KAAK,IAAI;AACpB,SAAK,KAAK;AACV,WAAO;AAAA,EACT;AAAA;AAAA;AAAA;AAAA,EAKA,MAAM,QAAgB,UAA2B;AAE/C,SAAK,KAAK;AAEV,UAAM,OAAO,KAAK,MAAM,KAAK,OAAK,EAAE,OAAO,MAAM;AACjD,QAAI,CAAC,KAAM,QAAO;AAGlB,QAAI,KAAK,WAAW,aAAa,KAAK,UAAU;AAC9C,aAAO;AAAA,IACT;AAEA,SAAK,WAAW;AAChB,SAAK,SAAS;AACd,SAAK,YAAY,KAAK,IAAI;AAC1B,SAAK,KAAK;AACV,WAAO;AAAA,EACT;AAAA;AAAA;AAAA;AAAA,EAKA,SAAS,QAAgB,UAA2B;AAClD,SAAK,KAAK;AAEV,UAAM,OAAO,KAAK,MAAM,KAAK,OAAK,EAAE,OAAO,MAAM;AACjD,QAAI,CAAC,KAAM,QAAO;AAGlB,QAAI,KAAK,aAAa,SAAU,QAAO;AAEvC,SAAK,SAAS;AACd,SAAK,YAAY,KAAK,IAAI;AAC1B,SAAK,KAAK;AACV,WAAO;AAAA,EACT;AAAA;AAAA;AAAA;AAAA,EAKA,SAAqB;AACnB,SAAK,KAAK;AACV,WAAO,CAAC,GAAG,KAAK,KAAK;AAAA,EACvB;AAAA;AAAA;AAAA;AAAA,EAKA,eAA2B;AACzB,SAAK,KAAK;AACV,WAAO,KAAK,MAAM,OAAO,OAAK,EAAE,WAAW,aAAa,CAAC,EAAE,QAAQ;AAAA,EACrE;AACF;",
6
+ "names": []
7
+ }
@@ -0,0 +1,80 @@
1
+ import { addTeammate, updateTeammateStatus, getTeam } from "./teamManager.js";
2
+ import { getHookManager } from "../../utils/hookManager.js";
3
+ let teammateCounter = 0;
4
+ function generateTeammateId() {
5
+ return `teammate-${Date.now()}-${++teammateCounter}`;
6
+ }
7
+ const TEAMMATE_COLORS = [
8
+ "cyan",
9
+ "magenta",
10
+ "yellow",
11
+ "green",
12
+ "blue",
13
+ "red",
14
+ "white"
15
+ ];
16
+ function getTeammateColor(index) {
17
+ return TEAMMATE_COLORS[index % TEAMMATE_COLORS.length];
18
+ }
19
+ async function spawnTeammate(teamName, agentType, prompt, options) {
20
+ const entry = getTeam(teamName);
21
+ if (!entry) return null;
22
+ const { team } = entry;
23
+ const mode = options?.mode || "in-process";
24
+ const teammateId = generateTeammateId();
25
+ const teammateName = options?.name || `${agentType}-${team.members.length + 1}`;
26
+ const teammate = addTeammate(teamName, {
27
+ id: teammateId,
28
+ name: teammateName,
29
+ agentType,
30
+ status: "idle",
31
+ prompt,
32
+ color: getTeammateColor(team.members.length)
33
+ });
34
+ if (mode === "tmux") {
35
+ await spawnTmuxTeammate(teamName, teammate);
36
+ }
37
+ return teammate;
38
+ }
39
+ async function spawnTmuxTeammate(teamName, teammate) {
40
+ try {
41
+ const { execSync } = await import("child_process");
42
+ const cmd = `minto --resume --prompt "${teammate.prompt.replace(/"/g, '\\"')}" --agent-type "${teammate.agentType}"`;
43
+ execSync(`tmux split-window -h -t "${teamName}" "${cmd}"`, {
44
+ stdio: "pipe"
45
+ });
46
+ updateTeammateStatus(teamName, teammate.id, "working");
47
+ } catch {
48
+ updateTeammateStatus(teamName, teammate.id, "stopped");
49
+ }
50
+ }
51
+ async function markTeammateIdle(teamName, teammateId, teammateName) {
52
+ updateTeammateStatus(teamName, teammateId, "idle");
53
+ const hookMgr = getHookManager();
54
+ if (hookMgr) {
55
+ hookMgr.executeTeammateIdle(teammateName, teamName).catch(() => {
56
+ });
57
+ }
58
+ }
59
+ function getTeamSummary(teamName) {
60
+ const entry = getTeam(teamName);
61
+ if (!entry) return null;
62
+ const { team } = entry;
63
+ const statusCounts = { idle: 0, working: 0, planning: 0, stopped: 0 };
64
+ for (const member of team.members) {
65
+ statusCounts[member.status]++;
66
+ }
67
+ const parts = [`Team: ${team.name}`];
68
+ parts.push(`Members: ${team.members.length}`);
69
+ if (statusCounts.working > 0) parts.push(`Working: ${statusCounts.working}`);
70
+ if (statusCounts.idle > 0) parts.push(`Idle: ${statusCounts.idle}`);
71
+ if (statusCounts.planning > 0)
72
+ parts.push(`Planning: ${statusCounts.planning}`);
73
+ return parts.join(" | ");
74
+ }
75
+ export {
76
+ getTeamSummary,
77
+ markTeammateIdle,
78
+ spawnTeammate
79
+ };
80
+ //# sourceMappingURL=teammateSpawner.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../src/services/agentTeams/teammateSpawner.ts"],
4
+ "sourcesContent": ["/**\n * Teammate Spawner\n *\n * Spawns teammate instances for agent teams.\n * Supports in-process (TaskTool delegation) and tmux (subprocess) modes.\n *\n * Experimental: Enable with MINTO_EXPERIMENTAL_AGENT_TEAMS=1\n */\n\nimport { addTeammate, updateTeammateStatus, getTeam } from './teamManager'\nimport type { Teammate, TeammateStatus } from '../../types/agentTeams'\nimport { getHookManager } from '../../utils/hookManager'\n\nlet teammateCounter = 0\n\n/**\n * Generate a unique teammate ID\n */\nfunction generateTeammateId(): string {\n return `teammate-${Date.now()}-${++teammateCounter}`\n}\n\n/**\n * Teammate colors for UI differentiation\n */\nconst TEAMMATE_COLORS = [\n 'cyan',\n 'magenta',\n 'yellow',\n 'green',\n 'blue',\n 'red',\n 'white',\n]\n\nfunction getTeammateColor(index: number): string {\n return TEAMMATE_COLORS[index % TEAMMATE_COLORS.length]!\n}\n\n/**\n * Spawn a teammate in the given team\n *\n * In-process mode: Creates a teammate record and returns it.\n * The caller is responsible for running the actual agent work\n * (typically via TaskTool delegation).\n *\n * tmux mode: Creates a new tmux pane with a separate CLI process.\n */\nexport async function spawnTeammate(\n teamName: string,\n agentType: string,\n prompt: string,\n options?: {\n name?: string\n mode?: 'in-process' | 'tmux'\n },\n): Promise<Teammate | null> {\n const entry = getTeam(teamName)\n if (!entry) return null\n\n const { team } = entry\n const mode = options?.mode || 'in-process'\n const teammateId = generateTeammateId()\n const teammateName =\n options?.name || `${agentType}-${team.members.length + 1}`\n\n const teammate = addTeammate(teamName, {\n id: teammateId,\n name: teammateName,\n agentType,\n status: 'idle' as TeammateStatus,\n prompt,\n color: getTeammateColor(team.members.length),\n })\n\n if (mode === 'tmux') {\n await spawnTmuxTeammate(teamName, teammate)\n }\n\n return teammate\n}\n\n/**\n * Spawn a teammate in a tmux pane\n */\nasync function spawnTmuxTeammate(\n teamName: string,\n teammate: Teammate,\n): Promise<void> {\n try {\n const { execSync } = await import('child_process')\n const cmd = `minto --resume --prompt \"${teammate.prompt.replace(/\"/g, '\\\\\"')}\" --agent-type \"${teammate.agentType}\"`\n\n // Create new tmux pane\n execSync(`tmux split-window -h -t \"${teamName}\" \"${cmd}\"`, {\n stdio: 'pipe',\n })\n\n updateTeammateStatus(teamName, teammate.id, 'working')\n } catch {\n // tmux not available or command failed\n updateTeammateStatus(teamName, teammate.id, 'stopped')\n }\n}\n\n/**\n * Mark a teammate as idle and fire TeammateIdle hook\n */\nexport async function markTeammateIdle(\n teamName: string,\n teammateId: string,\n teammateName: string,\n): Promise<void> {\n updateTeammateStatus(teamName, teammateId, 'idle')\n\n // Fire TeammateIdle hook\n const hookMgr = getHookManager()\n if (hookMgr) {\n hookMgr.executeTeammateIdle(teammateName, teamName).catch(() => {\n // Hook errors don't break teammate lifecycle\n })\n }\n}\n\n/**\n * Get team summary for display\n */\nexport function getTeamSummary(teamName: string): string | null {\n const entry = getTeam(teamName)\n if (!entry) return null\n\n const { team } = entry\n const statusCounts = { idle: 0, working: 0, planning: 0, stopped: 0 }\n for (const member of team.members) {\n statusCounts[member.status]++\n }\n\n const parts: string[] = [`Team: ${team.name}`]\n parts.push(`Members: ${team.members.length}`)\n if (statusCounts.working > 0) parts.push(`Working: ${statusCounts.working}`)\n if (statusCounts.idle > 0) parts.push(`Idle: ${statusCounts.idle}`)\n if (statusCounts.planning > 0)\n parts.push(`Planning: ${statusCounts.planning}`)\n\n return parts.join(' | ')\n}\n"],
5
+ "mappings": "AASA,SAAS,aAAa,sBAAsB,eAAe;AAE3D,SAAS,sBAAsB;AAE/B,IAAI,kBAAkB;AAKtB,SAAS,qBAA6B;AACpC,SAAO,YAAY,KAAK,IAAI,CAAC,IAAI,EAAE,eAAe;AACpD;AAKA,MAAM,kBAAkB;AAAA,EACtB;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF;AAEA,SAAS,iBAAiB,OAAuB;AAC/C,SAAO,gBAAgB,QAAQ,gBAAgB,MAAM;AACvD;AAWA,eAAsB,cACpB,UACA,WACA,QACA,SAI0B;AAC1B,QAAM,QAAQ,QAAQ,QAAQ;AAC9B,MAAI,CAAC,MAAO,QAAO;AAEnB,QAAM,EAAE,KAAK,IAAI;AACjB,QAAM,OAAO,SAAS,QAAQ;AAC9B,QAAM,aAAa,mBAAmB;AACtC,QAAM,eACJ,SAAS,QAAQ,GAAG,SAAS,IAAI,KAAK,QAAQ,SAAS,CAAC;AAE1D,QAAM,WAAW,YAAY,UAAU;AAAA,IACrC,IAAI;AAAA,IACJ,MAAM;AAAA,IACN;AAAA,IACA,QAAQ;AAAA,IACR;AAAA,IACA,OAAO,iBAAiB,KAAK,QAAQ,MAAM;AAAA,EAC7C,CAAC;AAED,MAAI,SAAS,QAAQ;AACnB,UAAM,kBAAkB,UAAU,QAAQ;AAAA,EAC5C;AAEA,SAAO;AACT;AAKA,eAAe,kBACb,UACA,UACe;AACf,MAAI;AACF,UAAM,EAAE,SAAS,IAAI,MAAM,OAAO,eAAe;AACjD,UAAM,MAAM,4BAA4B,SAAS,OAAO,QAAQ,MAAM,KAAK,CAAC,mBAAmB,SAAS,SAAS;AAGjH,aAAS,4BAA4B,QAAQ,MAAM,GAAG,KAAK;AAAA,MACzD,OAAO;AAAA,IACT,CAAC;AAED,yBAAqB,UAAU,SAAS,IAAI,SAAS;AAAA,EACvD,QAAQ;AAEN,yBAAqB,UAAU,SAAS,IAAI,SAAS;AAAA,EACvD;AACF;AAKA,eAAsB,iBACpB,UACA,YACA,cACe;AACf,uBAAqB,UAAU,YAAY,MAAM;AAGjD,QAAM,UAAU,eAAe;AAC/B,MAAI,SAAS;AACX,YAAQ,oBAAoB,cAAc,QAAQ,EAAE,MAAM,MAAM;AAAA,IAEhE,CAAC;AAAA,EACH;AACF;AAKO,SAAS,eAAe,UAAiC;AAC9D,QAAM,QAAQ,QAAQ,QAAQ;AAC9B,MAAI,CAAC,MAAO,QAAO;AAEnB,QAAM,EAAE,KAAK,IAAI;AACjB,QAAM,eAAe,EAAE,MAAM,GAAG,SAAS,GAAG,UAAU,GAAG,SAAS,EAAE;AACpE,aAAW,UAAU,KAAK,SAAS;AACjC,iBAAa,OAAO,MAAM;AAAA,EAC5B;AAEA,QAAM,QAAkB,CAAC,SAAS,KAAK,IAAI,EAAE;AAC7C,QAAM,KAAK,YAAY,KAAK,QAAQ,MAAM,EAAE;AAC5C,MAAI,aAAa,UAAU,EAAG,OAAM,KAAK,YAAY,aAAa,OAAO,EAAE;AAC3E,MAAI,aAAa,OAAO,EAAG,OAAM,KAAK,SAAS,aAAa,IAAI,EAAE;AAClE,MAAI,aAAa,WAAW;AAC1B,UAAM,KAAK,aAAa,aAAa,QAAQ,EAAE;AAEjD,SAAO,MAAM,KAAK,KAAK;AACzB;",
6
+ "names": []
7
+ }
@@ -10,6 +10,7 @@ import {
10
10
  import { join, dirname } from "path";
11
11
  import { getCwd } from "../utils/state.js";
12
12
  import { execFileNoThrow } from "../utils/execFileNoThrow.js";
13
+ import { debug as debugLogger } from "../utils/debugLogger.js";
13
14
  class CheckpointManager {
14
15
  checkpoints = /* @__PURE__ */ new Map();
15
16
  fileChangeTracker = [];
@@ -36,7 +37,11 @@ class CheckpointManager {
36
37
  try {
37
38
  gitCommit = await this.getCurrentGitCommit();
38
39
  gitBranch = await this.getCurrentGitBranch();
39
- } catch {
40
+ } catch (e) {
41
+ debugLogger.warn(
42
+ "CHECKPOINT",
43
+ `Git info unavailable: ${e instanceof Error ? e.message : String(e)}`
44
+ );
40
45
  }
41
46
  }
42
47
  const checkpoint = {
@@ -254,10 +259,18 @@ class CheckpointManager {
254
259
  const content = readFileSync(filePath, "utf-8");
255
260
  const checkpoint = JSON.parse(content);
256
261
  this.checkpoints.set(checkpoint.id, checkpoint);
257
- } catch {
262
+ } catch (e) {
263
+ debugLogger.warn(
264
+ "CHECKPOINT",
265
+ `Skip invalid checkpoint file: ${e instanceof Error ? e.message : String(e)}`
266
+ );
258
267
  }
259
268
  }
260
- } catch {
269
+ } catch (e) {
270
+ debugLogger.warn(
271
+ "CHECKPOINT",
272
+ `Cannot read checkpoint directory: ${e instanceof Error ? e.message : String(e)}`
273
+ );
261
274
  }
262
275
  }
263
276
  /**