@within-7/minto 0.4.1 → 0.4.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 (391) hide show
  1. package/dist/Tool.js +7 -0
  2. package/dist/Tool.js.map +2 -2
  3. package/dist/commands/agents/AgentsCommand.js +1 -1
  4. package/dist/commands/agents/AgentsCommand.js.map +2 -2
  5. package/dist/commands/agents/constants.js +2 -2
  6. package/dist/commands/agents/constants.js.map +2 -2
  7. package/dist/commands/clear.js +4 -3
  8. package/dist/commands/clear.js.map +2 -2
  9. package/dist/commands/compact.js +2 -2
  10. package/dist/commands/compact.js.map +1 -1
  11. package/dist/commands/context.js +3 -1
  12. package/dist/commands/context.js.map +2 -2
  13. package/dist/commands/login.js +128 -0
  14. package/dist/commands/login.js.map +7 -0
  15. package/dist/commands/memory.js +33 -82
  16. package/dist/commands/memory.js.map +2 -2
  17. package/dist/commands/quit.js +3 -1
  18. package/dist/commands/quit.js.map +2 -2
  19. package/dist/commands/resume.js +39 -239
  20. package/dist/commands/resume.js.map +2 -2
  21. package/dist/commands/tasks.js +1 -1
  22. package/dist/commands/tasks.js.map +2 -2
  23. package/dist/commands/terminalSetup.js +6 -2
  24. package/dist/commands/terminalSetup.js.map +2 -2
  25. package/dist/commands.js +2 -0
  26. package/dist/commands.js.map +2 -2
  27. package/dist/components/AgentDetailView.js +126 -0
  28. package/dist/components/AgentDetailView.js.map +7 -0
  29. package/dist/components/AgentThinkingBlock.js +1 -1
  30. package/dist/components/AgentThinkingBlock.js.map +2 -2
  31. package/dist/components/AgentViewBanner.js +22 -0
  32. package/dist/components/AgentViewBanner.js.map +7 -0
  33. package/dist/components/HeaderBar.js +1 -1
  34. package/dist/components/HeaderBar.js.map +2 -2
  35. package/dist/components/Help.js +8 -1
  36. package/dist/components/Help.js.map +2 -2
  37. package/dist/components/HotkeyHelpPanel.js +26 -8
  38. package/dist/components/HotkeyHelpPanel.js.map +2 -2
  39. package/dist/components/IdleNotificationBar.js +10 -0
  40. package/dist/components/IdleNotificationBar.js.map +7 -0
  41. package/dist/components/ModelSelector/ModelSelector.js +55 -20
  42. package/dist/components/ModelSelector/ModelSelector.js.map +2 -2
  43. package/dist/components/PromptInput.js +186 -115
  44. package/dist/components/PromptInput.js.map +2 -2
  45. package/dist/components/RewindPanel.js +272 -0
  46. package/dist/components/RewindPanel.js.map +7 -0
  47. package/dist/components/Spinner.js +10 -21
  48. package/dist/components/Spinner.js.map +2 -2
  49. package/dist/components/StreamingTextPreview.js +29 -0
  50. package/dist/components/StreamingTextPreview.js.map +7 -0
  51. package/dist/components/SubagentBlock.js +3 -2
  52. package/dist/components/SubagentBlock.js.map +2 -2
  53. package/dist/components/SubagentProgress.js +4 -4
  54. package/dist/components/SubagentProgress.js.map +2 -2
  55. package/dist/components/TabbedListView/SearchInput.js +1 -1
  56. package/dist/components/TabbedListView/SearchInput.js.map +2 -2
  57. package/dist/components/TabbedListView/TabbedListView.js +87 -41
  58. package/dist/components/TabbedListView/TabbedListView.js.map +2 -2
  59. package/dist/components/TaskCard.js +4 -4
  60. package/dist/components/TaskCard.js.map +2 -2
  61. package/dist/components/TeamMemberPanel.js +107 -0
  62. package/dist/components/TeamMemberPanel.js.map +7 -0
  63. package/dist/components/ThinkingSelector.js +84 -0
  64. package/dist/components/ThinkingSelector.js.map +7 -0
  65. package/dist/components/TitledDivider.js +26 -0
  66. package/dist/components/TitledDivider.js.map +7 -0
  67. package/dist/components/TodoPanel.js +31 -30
  68. package/dist/components/TodoPanel.js.map +2 -2
  69. package/dist/components/TokenWarning.js +28 -7
  70. package/dist/components/TokenWarning.js.map +2 -2
  71. package/dist/components/messages/AssistantTextMessage.js +5 -2
  72. package/dist/components/messages/AssistantTextMessage.js.map +2 -2
  73. package/dist/components/messages/AssistantToolUseMessage.js +9 -1
  74. package/dist/components/messages/AssistantToolUseMessage.js.map +2 -2
  75. package/dist/components/messages/DefaultToolResultFallback.js +11 -0
  76. package/dist/components/messages/DefaultToolResultFallback.js.map +7 -0
  77. package/dist/components/messages/ParallelTasksGroupView.js +14 -6
  78. package/dist/components/messages/ParallelTasksGroupView.js.map +2 -2
  79. package/dist/components/messages/TaskInModuleView.js +27 -27
  80. package/dist/components/messages/TaskInModuleView.js.map +2 -2
  81. package/dist/components/messages/UserGuidanceMessage.js +26 -0
  82. package/dist/components/messages/UserGuidanceMessage.js.map +7 -0
  83. package/dist/components/messages/UserPromptMessage.js +2 -1
  84. package/dist/components/messages/UserPromptMessage.js.map +2 -2
  85. package/dist/components/messages/UserTeamNotificationMessage.js +91 -0
  86. package/dist/components/messages/UserTeamNotificationMessage.js.map +7 -0
  87. package/dist/components/messages/UserTextMessage.js +8 -0
  88. package/dist/components/messages/UserTextMessage.js.map +2 -2
  89. package/dist/components/messages/UserToolResultMessage/UserToolRejectMessage.js +4 -2
  90. package/dist/components/messages/UserToolResultMessage/UserToolRejectMessage.js.map +2 -2
  91. package/dist/components/messages/UserToolResultMessage/UserToolResultMessage.js +18 -1
  92. package/dist/components/messages/UserToolResultMessage/UserToolResultMessage.js.map +2 -2
  93. package/dist/components/messages/UserToolResultMessage/UserToolSuccessMessage.js +12 -1
  94. package/dist/components/messages/UserToolResultMessage/UserToolSuccessMessage.js.map +2 -2
  95. package/dist/components/permissions/PermissionRequest.js +4 -0
  96. package/dist/components/permissions/PermissionRequest.js.map +2 -2
  97. package/dist/components/permissions/PlanApprovalRequest.js +164 -0
  98. package/dist/components/permissions/PlanApprovalRequest.js.map +7 -0
  99. package/dist/constants/agentTeams.js +17 -0
  100. package/dist/constants/agentTeams.js.map +7 -0
  101. package/dist/constants/macros.js +2 -1
  102. package/dist/constants/macros.js.map +2 -2
  103. package/dist/constants/prompts/agentPrompt.js +1 -0
  104. package/dist/constants/prompts/agentPrompt.js.map +2 -2
  105. package/dist/constants/prompts/autoMemory.js +39 -0
  106. package/dist/constants/prompts/autoMemory.js.map +7 -0
  107. package/dist/constants/prompts/codeConventions.js +1 -13
  108. package/dist/constants/prompts/codeConventions.js.map +2 -2
  109. package/dist/constants/prompts/doingTasks.js +21 -2
  110. package/dist/constants/prompts/doingTasks.js.map +2 -2
  111. package/dist/constants/prompts/envInfo.js +6 -7
  112. package/dist/constants/prompts/envInfo.js.map +2 -2
  113. package/dist/constants/prompts/index.js +27 -5
  114. package/dist/constants/prompts/index.js.map +2 -2
  115. package/dist/constants/prompts/taskManagement.js +2 -43
  116. package/dist/constants/prompts/taskManagement.js.map +2 -2
  117. package/dist/constants/prompts/teamOverlays.js +50 -0
  118. package/dist/constants/prompts/teamOverlays.js.map +7 -0
  119. package/dist/constants/prompts/toneAndStyle.js +4 -29
  120. package/dist/constants/prompts/toneAndStyle.js.map +2 -2
  121. package/dist/constants/prompts/toolUsagePolicy.js +7 -22
  122. package/dist/constants/prompts/toolUsagePolicy.js.map +2 -2
  123. package/dist/constants/toolInputExamples.js +2 -2
  124. package/dist/constants/toolInputExamples.js.map +2 -2
  125. package/dist/context.js +39 -6
  126. package/dist/context.js.map +2 -2
  127. package/dist/core/backupManager.js +1 -1
  128. package/dist/core/backupManager.js.map +2 -2
  129. package/dist/core/permissions/rules/planModeRule.js +1 -1
  130. package/dist/core/permissions/rules/planModeRule.js.map +1 -1
  131. package/dist/core/permissions/rules/safeModeRule.js +1 -1
  132. package/dist/core/permissions/rules/safeModeRule.js.map +1 -1
  133. package/dist/engine/AgentEngine.js +902 -0
  134. package/dist/engine/AgentEngine.js.map +7 -0
  135. package/dist/engine/EngineRegistry.js +89 -0
  136. package/dist/engine/EngineRegistry.js.map +7 -0
  137. package/dist/engine/foregroundAdapter.js +191 -0
  138. package/dist/engine/foregroundAdapter.js.map +7 -0
  139. package/dist/engine/index.js +15 -0
  140. package/dist/engine/index.js.map +7 -0
  141. package/dist/engine/types.js +1 -0
  142. package/dist/engine/types.js.map +7 -0
  143. package/dist/entrypoints/cli.js +410 -79
  144. package/dist/entrypoints/cli.js.map +3 -3
  145. package/dist/hooks/useAgentEngine.js +129 -0
  146. package/dist/hooks/useAgentEngine.js.map +7 -0
  147. package/dist/hooks/useAgentTokenStats.js +0 -16
  148. package/dist/hooks/useAgentTokenStats.js.map +2 -2
  149. package/dist/hooks/useCanUseTool.js +47 -2
  150. package/dist/hooks/useCanUseTool.js.map +2 -2
  151. package/dist/hooks/useDeferredLoading.js +4 -1
  152. package/dist/hooks/useDeferredLoading.js.map +2 -2
  153. package/dist/hooks/useIdleNotifications.js +66 -0
  154. package/dist/hooks/useIdleNotifications.js.map +7 -0
  155. package/dist/hooks/useSessionTracking.js +9 -7
  156. package/dist/hooks/useSessionTracking.js.map +2 -2
  157. package/dist/hooks/useTeamMembers.js +51 -0
  158. package/dist/hooks/useTeamMembers.js.map +7 -0
  159. package/dist/i18n/locales/en.js +77 -12
  160. package/dist/i18n/locales/en.js.map +2 -2
  161. package/dist/i18n/locales/zh-CN.js +77 -12
  162. package/dist/i18n/locales/zh-CN.js.map +2 -2
  163. package/dist/i18n/types.js.map +1 -1
  164. package/dist/messages.js.map +2 -2
  165. package/dist/permissions.js +113 -7
  166. package/dist/permissions.js.map +2 -2
  167. package/dist/query.js +135 -37
  168. package/dist/query.js.map +2 -2
  169. package/dist/screens/REPL.js +504 -361
  170. package/dist/screens/REPL.js.map +3 -3
  171. package/dist/screens/ResumeConversation.js +199 -14
  172. package/dist/screens/ResumeConversation.js.map +2 -2
  173. package/dist/services/adapters/base.js.map +1 -1
  174. package/dist/services/agentTeams/backends/headless.js +108 -0
  175. package/dist/services/agentTeams/backends/headless.js.map +7 -0
  176. package/dist/services/agentTeams/backends/inProcess.js +102 -0
  177. package/dist/services/agentTeams/backends/inProcess.js.map +7 -0
  178. package/dist/services/agentTeams/backends/resolver.js +18 -0
  179. package/dist/services/agentTeams/backends/resolver.js.map +7 -0
  180. package/dist/services/agentTeams/backends/tmux.js +168 -0
  181. package/dist/services/agentTeams/backends/tmux.js.map +7 -0
  182. package/dist/services/agentTeams/backends/types.js +1 -0
  183. package/dist/services/agentTeams/backends/types.js.map +7 -0
  184. package/dist/services/agentTeams/heartbeat.js +88 -0
  185. package/dist/services/agentTeams/heartbeat.js.map +7 -0
  186. package/dist/services/agentTeams/index.js +42 -2
  187. package/dist/services/agentTeams/index.js.map +2 -2
  188. package/dist/services/agentTeams/injectionChannel.js +105 -0
  189. package/dist/services/agentTeams/injectionChannel.js.map +7 -0
  190. package/dist/services/agentTeams/mailbox.js +410 -30
  191. package/dist/services/agentTeams/mailbox.js.map +2 -2
  192. package/dist/services/agentTeams/messageFormatter.js +80 -0
  193. package/dist/services/agentTeams/messageFormatter.js.map +7 -0
  194. package/dist/services/agentTeams/permissionDelegation.js +71 -0
  195. package/dist/services/agentTeams/permissionDelegation.js.map +7 -0
  196. package/dist/services/agentTeams/teamEvents.js +45 -0
  197. package/dist/services/agentTeams/teamEvents.js.map +7 -0
  198. package/dist/services/agentTeams/teamManager.js +251 -34
  199. package/dist/services/agentTeams/teamManager.js.map +2 -2
  200. package/dist/services/agentTeams/teamTaskStore.js +290 -61
  201. package/dist/services/agentTeams/teamTaskStore.js.map +2 -2
  202. package/dist/services/agentTeams/teammateSpawner.js +99 -18
  203. package/dist/services/agentTeams/teammateSpawner.js.map +2 -2
  204. package/dist/services/hookExecutor.js +51 -8
  205. package/dist/services/hookExecutor.js.map +2 -2
  206. package/dist/services/llm/anthropicProvider.js +56 -59
  207. package/dist/services/llm/anthropicProvider.js.map +2 -2
  208. package/dist/services/llm/dispatch.js +24 -5
  209. package/dist/services/llm/dispatch.js.map +2 -2
  210. package/dist/services/llm/openaiProvider.js +115 -136
  211. package/dist/services/llm/openaiProvider.js.map +3 -3
  212. package/dist/services/llm/types.js +89 -15
  213. package/dist/services/llm/types.js.map +2 -2
  214. package/dist/services/mcpClient.js +80 -4
  215. package/dist/services/mcpClient.js.map +2 -2
  216. package/dist/services/mintoAuth.js +299 -0
  217. package/dist/services/mintoAuth.js.map +7 -0
  218. package/dist/services/oauth.js +3 -3
  219. package/dist/services/oauth.js.map +2 -2
  220. package/dist/services/openai.js +91 -20
  221. package/dist/services/openai.js.map +2 -2
  222. package/dist/services/plugins/pluginRuntime.js +11 -5
  223. package/dist/services/plugins/pluginRuntime.js.map +2 -2
  224. package/dist/services/plugins/pluginValidation.js +4 -2
  225. package/dist/services/plugins/pluginValidation.js.map +2 -2
  226. package/dist/services/sandbox/sandboxController.js +11 -3
  227. package/dist/services/sandbox/sandboxController.js.map +2 -2
  228. package/dist/services/sessionMemoryInjector.js +77 -0
  229. package/dist/services/sessionMemoryInjector.js.map +7 -0
  230. package/dist/services/systemReminder.js +130 -8
  231. package/dist/services/systemReminder.js.map +2 -2
  232. package/dist/services/taskStore.js +199 -8
  233. package/dist/services/taskStore.js.map +3 -3
  234. package/dist/services/topicDetector.js +169 -0
  235. package/dist/services/topicDetector.js.map +7 -0
  236. package/dist/tools/AskExpertModelTool/AskExpertModelTool.js +0 -13
  237. package/dist/tools/AskExpertModelTool/AskExpertModelTool.js.map +2 -2
  238. package/dist/tools/BashTool/BashTool.js +51 -28
  239. package/dist/tools/BashTool/BashTool.js.map +2 -2
  240. package/dist/tools/BashTool/prompt.js +95 -118
  241. package/dist/tools/BashTool/prompt.js.map +2 -2
  242. package/dist/tools/BashTool/utils.js +39 -1
  243. package/dist/tools/BashTool/utils.js.map +2 -2
  244. package/dist/tools/EnterWorktreeTool/EnterWorktreeTool.js +121 -0
  245. package/dist/tools/EnterWorktreeTool/EnterWorktreeTool.js.map +7 -0
  246. package/dist/tools/EnterWorktreeTool/prompt.js +22 -0
  247. package/dist/tools/EnterWorktreeTool/prompt.js.map +7 -0
  248. package/dist/tools/FileEditTool/FileEditTool.js +9 -4
  249. package/dist/tools/FileEditTool/FileEditTool.js.map +2 -2
  250. package/dist/tools/FileEditTool/prompt.js +3 -7
  251. package/dist/tools/FileEditTool/prompt.js.map +2 -2
  252. package/dist/tools/FileReadTool/FileReadTool.js +125 -3
  253. package/dist/tools/FileReadTool/FileReadTool.js.map +2 -2
  254. package/dist/tools/FileReadTool/prompt.js +1 -2
  255. package/dist/tools/FileReadTool/prompt.js.map +2 -2
  256. package/dist/tools/FileWriteTool/prompt.js +3 -5
  257. package/dist/tools/FileWriteTool/prompt.js.map +2 -2
  258. package/dist/tools/GlobTool/GlobTool.js +3 -2
  259. package/dist/tools/GlobTool/GlobTool.js.map +2 -2
  260. package/dist/tools/GrepTool/GrepTool.js +16 -5
  261. package/dist/tools/GrepTool/GrepTool.js.map +2 -2
  262. package/dist/tools/ListMcpResourcesTool/ListMcpResourcesTool.js.map +2 -2
  263. package/dist/tools/MCPSearchTool/MCPSearchTool.js +172 -0
  264. package/dist/tools/MCPSearchTool/MCPSearchTool.js.map +7 -0
  265. package/dist/tools/MCPSearchTool/prompt.js +77 -0
  266. package/dist/tools/MCPSearchTool/prompt.js.map +7 -0
  267. package/dist/tools/MultiEditTool/prompt.js +4 -7
  268. package/dist/tools/MultiEditTool/prompt.js.map +2 -2
  269. package/dist/tools/PlanModeTool/EnterPlanModeTool.js +12 -8
  270. package/dist/tools/PlanModeTool/EnterPlanModeTool.js.map +2 -2
  271. package/dist/tools/PlanModeTool/ExitPlanModeTool.js +54 -1
  272. package/dist/tools/PlanModeTool/ExitPlanModeTool.js.map +2 -2
  273. package/dist/tools/PlanModeTool/prompt.js +23 -74
  274. package/dist/tools/PlanModeTool/prompt.js.map +2 -2
  275. package/dist/tools/SendMessageTool/SendMessageTool.js +341 -0
  276. package/dist/tools/SendMessageTool/SendMessageTool.js.map +7 -0
  277. package/dist/tools/SendMessageTool/prompt.js +44 -0
  278. package/dist/tools/SendMessageTool/prompt.js.map +7 -0
  279. package/dist/tools/TaskCreateTool/prompt.js +15 -4
  280. package/dist/tools/TaskCreateTool/prompt.js.map +2 -2
  281. package/dist/tools/TaskListTool/prompt.js +18 -3
  282. package/dist/tools/TaskListTool/prompt.js.map +2 -2
  283. package/dist/tools/TaskOutputTool/prompt.js +4 -3
  284. package/dist/tools/TaskOutputTool/prompt.js.map +2 -2
  285. package/dist/tools/TaskTool/TaskTool.js +762 -98
  286. package/dist/tools/TaskTool/TaskTool.js.map +3 -3
  287. package/dist/tools/TaskTool/constants.js +8 -2
  288. package/dist/tools/TaskTool/constants.js.map +2 -2
  289. package/dist/tools/TaskTool/prompt.js +74 -70
  290. package/dist/tools/TaskTool/prompt.js.map +2 -2
  291. package/dist/tools/TaskUpdateTool/TaskUpdateTool.js +15 -1
  292. package/dist/tools/TaskUpdateTool/TaskUpdateTool.js.map +2 -2
  293. package/dist/tools/TeamCreateTool/TeamCreateTool.js +129 -0
  294. package/dist/tools/TeamCreateTool/TeamCreateTool.js.map +7 -0
  295. package/dist/tools/TeamCreateTool/prompt.js +58 -0
  296. package/dist/tools/TeamCreateTool/prompt.js.map +7 -0
  297. package/dist/tools/TeamDeleteTool/TeamDeleteTool.js +151 -0
  298. package/dist/tools/TeamDeleteTool/TeamDeleteTool.js.map +7 -0
  299. package/dist/tools/TeamDeleteTool/prompt.js +16 -0
  300. package/dist/tools/TeamDeleteTool/prompt.js.map +7 -0
  301. package/dist/tools/URLFetcherTool/URLFetcherTool.js +106 -15
  302. package/dist/tools/URLFetcherTool/URLFetcherTool.js.map +2 -2
  303. package/dist/tools/URLFetcherTool/prompt.js +3 -2
  304. package/dist/tools/URLFetcherTool/prompt.js.map +2 -2
  305. package/dist/tools/WebSearchTool/WebSearchTool.js +2 -1
  306. package/dist/tools/WebSearchTool/WebSearchTool.js.map +2 -2
  307. package/dist/tools/WebSearchTool/prompt.js +5 -4
  308. package/dist/tools/WebSearchTool/prompt.js.map +2 -2
  309. package/dist/tools.js +100 -20
  310. package/dist/tools.js.map +2 -2
  311. package/dist/types/PermissionMode.js +35 -6
  312. package/dist/types/PermissionMode.js.map +2 -2
  313. package/dist/types/hooks.js +2 -0
  314. package/dist/types/hooks.js.map +2 -2
  315. package/dist/types/plugin.js +2 -0
  316. package/dist/types/plugin.js.map +3 -3
  317. package/dist/utils/CircuitBreaker.js +15 -9
  318. package/dist/utils/CircuitBreaker.js.map +2 -2
  319. package/dist/utils/agentLoader.js +249 -112
  320. package/dist/utils/agentLoader.js.map +2 -2
  321. package/dist/utils/animationManager.js +40 -3
  322. package/dist/utils/animationManager.js.map +2 -2
  323. package/dist/utils/ask.js +7 -6
  324. package/dist/utils/ask.js.map +2 -2
  325. package/dist/utils/atomicWrite.js +23 -0
  326. package/dist/utils/atomicWrite.js.map +7 -0
  327. package/dist/utils/autoCompactCore.js +73 -56
  328. package/dist/utils/autoCompactCore.js.map +2 -2
  329. package/dist/utils/autoMemoryPaths.js +89 -0
  330. package/dist/utils/autoMemoryPaths.js.map +7 -0
  331. package/dist/utils/config.js +63 -38
  332. package/dist/utils/config.js.map +2 -2
  333. package/dist/utils/configSchema.js +13 -8
  334. package/dist/utils/configSchema.js.map +2 -2
  335. package/dist/utils/credentials/index.js +14 -0
  336. package/dist/utils/credentials/index.js.map +2 -2
  337. package/dist/utils/dualPath.js +24 -0
  338. package/dist/utils/dualPath.js.map +7 -0
  339. package/dist/utils/exit.js +66 -7
  340. package/dist/utils/exit.js.map +2 -2
  341. package/dist/utils/externalEditor.js +155 -0
  342. package/dist/utils/externalEditor.js.map +7 -0
  343. package/dist/utils/fileLock.js +67 -0
  344. package/dist/utils/fileLock.js.map +7 -0
  345. package/dist/utils/format.js +24 -14
  346. package/dist/utils/format.js.map +2 -2
  347. package/dist/utils/globalErrorHandler.js +5 -96
  348. package/dist/utils/globalErrorHandler.js.map +3 -3
  349. package/dist/utils/groupHandlers/parallelTasksHandler.js +5 -3
  350. package/dist/utils/groupHandlers/parallelTasksHandler.js.map +2 -2
  351. package/dist/utils/groupHandlers/taskHandler.js +2 -2
  352. package/dist/utils/groupHandlers/taskHandler.js.map +2 -2
  353. package/dist/utils/hookManager.js +64 -6
  354. package/dist/utils/hookManager.js.map +2 -2
  355. package/dist/utils/log.js +6 -2
  356. package/dist/utils/log.js.map +2 -2
  357. package/dist/utils/markdown.js +237 -19
  358. package/dist/utils/markdown.js.map +2 -2
  359. package/dist/utils/messageContextManager.js +18 -5
  360. package/dist/utils/messageContextManager.js.map +2 -2
  361. package/dist/utils/messageGroupManager.js +1 -1
  362. package/dist/utils/messageGroupManager.js.map +2 -2
  363. package/dist/utils/messages.js +104 -46
  364. package/dist/utils/messages.js.map +2 -2
  365. package/dist/utils/model.js +2 -2
  366. package/dist/utils/model.js.map +2 -2
  367. package/dist/utils/pasteCache.js +8 -4
  368. package/dist/utils/pasteCache.js.map +2 -2
  369. package/dist/utils/pluginLoader.js +18 -0
  370. package/dist/utils/pluginLoader.js.map +2 -2
  371. package/dist/utils/secureKeyStorage.js +36 -7
  372. package/dist/utils/secureKeyStorage.js.map +2 -2
  373. package/dist/utils/simpleMode.js +7 -0
  374. package/dist/utils/simpleMode.js.map +7 -0
  375. package/dist/utils/streamingState.js +11 -1
  376. package/dist/utils/streamingState.js.map +2 -2
  377. package/dist/utils/taskDisplayUtils.js +2 -1
  378. package/dist/utils/taskDisplayUtils.js.map +2 -2
  379. package/dist/utils/teamConfig.js +2 -2
  380. package/dist/utils/teamConfig.js.map +2 -2
  381. package/dist/utils/thinking.js +6 -2
  382. package/dist/utils/thinking.js.map +3 -3
  383. package/dist/utils/tokenProgress.js +55 -0
  384. package/dist/utils/tokenProgress.js.map +7 -0
  385. package/dist/utils/toolRiskClassification.js +26 -17
  386. package/dist/utils/toolRiskClassification.js.map +2 -2
  387. package/dist/utils/tooling/toolError.js +12 -0
  388. package/dist/utils/tooling/toolError.js.map +7 -0
  389. package/dist/version.js +2 -2
  390. package/dist/version.js.map +1 -1
  391. package/package.json +10 -8
@@ -1,231 +1,13 @@
1
- import React, { useState, useMemo } from "react";
1
+ import React from "react";
2
2
  import { render } from "ink";
3
- import path from "path";
4
3
  import { t } from "../i18n/index.js";
5
- import { getCwd } from "../utils/state.js";
6
4
  import { CACHE_PATHS, loadLogList } from "../utils/log.js";
7
5
  import { deserializeMessages } from "../utils/conversationRecovery.js";
8
6
  import { getNextAvailableLogForkNumber, logError } from "../utils/log.js";
9
7
  import { isDefaultSlowAndCapableModel } from "../utils/model.js";
10
8
  import { prepareTerminalForREPL } from "../utils/terminal.js";
11
9
  import { REPL } from "../screens/REPL.js";
12
- import {
13
- TabbedListView
14
- } from "../components/TabbedListView/index.js";
15
- function formatDate(date) {
16
- const now = /* @__PURE__ */ new Date();
17
- const hours = date.getHours().toString().padStart(2, "0");
18
- const minutes = date.getMinutes().toString().padStart(2, "0");
19
- const timeStr = `${hours}:${minutes}`;
20
- const isToday = date.getDate() === now.getDate() && date.getMonth() === now.getMonth() && date.getFullYear() === now.getFullYear();
21
- if (isToday) {
22
- return `${t("commands.sessions.today")} ${timeStr}`;
23
- }
24
- const yesterday = new Date(now);
25
- yesterday.setDate(yesterday.getDate() - 1);
26
- const isYesterday = date.getDate() === yesterday.getDate() && date.getMonth() === yesterday.getMonth() && date.getFullYear() === yesterday.getFullYear();
27
- if (isYesterday) {
28
- return `${t("commands.sessions.yesterday")} ${timeStr}`;
29
- }
30
- const month = (date.getMonth() + 1).toString().padStart(2, "0");
31
- const day = date.getDate().toString().padStart(2, "0");
32
- return `${month}-${day} ${timeStr}`;
33
- }
34
- function truncate(str, maxLength) {
35
- if (str.length <= maxLength) return str;
36
- return str.slice(0, maxLength - 3) + "...";
37
- }
38
- function wasCleared(log) {
39
- for (let i = log.messages.length - 1; i >= 0; i--) {
40
- const msg = log.messages[i];
41
- if (msg.type === "user") {
42
- const content = typeof msg.message?.content === "string" ? msg.message.content : Array.isArray(msg.message?.content) ? msg.message.content.filter((c) => c.type === "text").map((c) => c.text).join("") : "";
43
- return content.includes("<command-name>clear</command-name>");
44
- }
45
- }
46
- return false;
47
- }
48
- function deduplicateLogForks(logs) {
49
- const groupedByDate = /* @__PURE__ */ new Map();
50
- for (const log of logs) {
51
- const existing = groupedByDate.get(log.date) || [];
52
- existing.push(log);
53
- groupedByDate.set(log.date, existing);
54
- }
55
- const deduped = [];
56
- for (const [, group] of groupedByDate) {
57
- const sorted = group.sort((a, b) => {
58
- const forkDiff = (b.forkNumber ?? 0) - (a.forkNumber ?? 0);
59
- if (forkDiff !== 0) return forkDiff;
60
- return b.modified.getTime() - a.modified.getTime();
61
- });
62
- if (sorted[0]) {
63
- deduped.push(sorted[0]);
64
- }
65
- }
66
- return deduped.sort((a, b) => b.modified.getTime() - a.modified.getTime());
67
- }
68
- function getLogProjectPath(log) {
69
- const firstMessage = log.messages[0];
70
- return firstMessage?.cwd || null;
71
- }
72
- function getProjectName(projectPath) {
73
- return path.basename(projectPath) || projectPath;
74
- }
75
- function extractFirstPrompt(log) {
76
- for (const msg of log.messages) {
77
- if (msg.type === "user") {
78
- let content = "";
79
- if (typeof msg.message?.content === "string") {
80
- content = msg.message.content;
81
- } else if (Array.isArray(msg.message?.content)) {
82
- content = msg.message.content.filter((c) => c.type === "text").map((c) => c.text).join("");
83
- }
84
- const trimmed = content.trim();
85
- if (trimmed.startsWith("<system-reminder>") || trimmed.startsWith("<command-name>") || trimmed.startsWith("<") && trimmed.includes("</")) {
86
- continue;
87
- }
88
- const firstLine = content.split("\n")[0]?.trim() || "";
89
- if (firstLine) {
90
- return firstLine;
91
- }
92
- }
93
- }
94
- return log.firstPrompt || "No prompt";
95
- }
96
- function countToolCalls(log) {
97
- let count = 0;
98
- for (const msg of log.messages) {
99
- if (msg.type === "assistant" && Array.isArray(msg.message?.content)) {
100
- for (const block of msg.message.content) {
101
- if (block.type === "tool_use") {
102
- count++;
103
- }
104
- }
105
- }
106
- }
107
- return count;
108
- }
109
- function logToListItem(log) {
110
- const dateStr = formatDate(log.modified);
111
- const projectPath = getLogProjectPath(log) || "";
112
- const projectName = projectPath ? truncate(getProjectName(projectPath), 15) : "";
113
- const msgCount = log.messageCount;
114
- const toolCount = countToolCalls(log);
115
- const firstPrompt = extractFirstPrompt(log);
116
- return {
117
- id: log.fullPath,
118
- // Use fullPath as unique id (date can be duplicated for forks)
119
- label: truncate(firstPrompt, 45),
120
- description: projectName || void 0,
121
- metadata: `${dateStr} \xB7 ${msgCount} msgs \xB7 ${toolCount} tools`,
122
- category: projectName || "Unknown",
123
- data: log
124
- };
125
- }
126
- function ResumeDisplay({
127
- recentLogs,
128
- projectLogs,
129
- allLogs,
130
- tools,
131
- commands,
132
- verbose,
133
- onClose,
134
- unmount
135
- }) {
136
- const [activeTab, setActiveTab] = useState("recent");
137
- const [searchQuery, setSearchQuery] = useState("");
138
- const tabs = useMemo(
139
- () => [
140
- {
141
- id: "recent",
142
- label: t("commands.sessions.title"),
143
- badge: recentLogs.length
144
- },
145
- {
146
- id: "project",
147
- label: t("commands.sessions.headerProject"),
148
- badge: projectLogs.length
149
- },
150
- {
151
- id: "all",
152
- label: t("common.all"),
153
- badge: allLogs.length
154
- }
155
- ],
156
- [recentLogs.length, projectLogs.length, allLogs.length]
157
- );
158
- const items = useMemo(() => {
159
- let logs;
160
- switch (activeTab) {
161
- case "project":
162
- logs = projectLogs;
163
- break;
164
- case "all":
165
- logs = allLogs;
166
- break;
167
- case "recent":
168
- default:
169
- logs = recentLogs;
170
- }
171
- return logs.map(logToListItem);
172
- }, [activeTab, recentLogs, projectLogs, allLogs]);
173
- const handleSelect = async (item) => {
174
- const log = item.data;
175
- try {
176
- onClose();
177
- const isDefaultModel = await isDefaultSlowAndCapableModel();
178
- unmount();
179
- await prepareTerminalForREPL();
180
- render(
181
- /* @__PURE__ */ React.createElement(
182
- REPL,
183
- {
184
- messageLogName: log.date,
185
- initialPrompt: "",
186
- shouldShowPromptInput: true,
187
- verbose,
188
- commands,
189
- tools,
190
- initialMessages: deserializeMessages(log.messages, tools),
191
- initialForkNumber: getNextAvailableLogForkNumber(
192
- log.date,
193
- log.forkNumber ?? 1,
194
- 0
195
- ),
196
- isDefaultModel,
197
- isResumedConversation: true
198
- }
199
- ),
200
- {
201
- exitOnCtrlC: false
202
- }
203
- );
204
- } catch (e) {
205
- logError(`Failed to load conversation: ${e}`);
206
- throw e;
207
- }
208
- };
209
- return /* @__PURE__ */ React.createElement(
210
- TabbedListView,
211
- {
212
- title: t("commands.resume.title"),
213
- tabs,
214
- activeTab,
215
- onTabChange: setActiveTab,
216
- items,
217
- searchEnabled: true,
218
- searchPlaceholder: t("ui.tabbedList.search"),
219
- searchQuery,
220
- onSearchChange: setSearchQuery,
221
- onSelect: handleSelect,
222
- onClose,
223
- emptyText: t("commands.resume.noSessions"),
224
- footerHint: t("commands.resume.navigationHint"),
225
- groupByCategory: activeTab === "all"
226
- }
227
- );
228
- }
10
+ import { SessionPicker } from "../screens/ResumeConversation.js";
229
11
  var resume_default = {
230
12
  type: "local-jsx",
231
13
  name: "resume",
@@ -239,28 +21,46 @@ var resume_default = {
239
21
  },
240
22
  async call(onDone, context) {
241
23
  const { commands = [], tools = [], verbose = false } = context.options || {};
242
- const cwd = getCwd();
243
24
  const allRawLogs = await loadLogList(CACHE_PATHS.messages());
244
- const validLogs = deduplicateLogForks(
245
- allRawLogs.filter((log) => !wasCleared(log))
246
- );
247
- const recentLogs = validLogs.slice(0, 20);
248
- const projectLogs = validLogs.filter((log) => {
249
- const logPath = getLogProjectPath(log);
250
- return logPath === cwd;
251
- });
252
- const allLogs = validLogs.slice(0, 100);
25
+ const handleSelect = async (log) => {
26
+ try {
27
+ onDone();
28
+ const isDefaultModel = await isDefaultSlowAndCapableModel();
29
+ context.unmount();
30
+ await prepareTerminalForREPL();
31
+ render(
32
+ /* @__PURE__ */ React.createElement(
33
+ REPL,
34
+ {
35
+ messageLogName: log.date,
36
+ initialPrompt: "",
37
+ shouldShowPromptInput: true,
38
+ verbose,
39
+ commands,
40
+ tools,
41
+ initialMessages: deserializeMessages(log.messages, tools),
42
+ initialForkNumber: getNextAvailableLogForkNumber(
43
+ log.date,
44
+ log.forkNumber ?? 1,
45
+ 0
46
+ ),
47
+ isDefaultModel,
48
+ isResumedConversation: true
49
+ }
50
+ ),
51
+ { exitOnCtrlC: false }
52
+ );
53
+ } catch (e) {
54
+ logError(`Failed to load conversation: ${e}`);
55
+ throw e;
56
+ }
57
+ };
253
58
  return /* @__PURE__ */ React.createElement(
254
- ResumeDisplay,
59
+ SessionPicker,
255
60
  {
256
- recentLogs,
257
- projectLogs,
258
- allLogs,
259
- tools,
260
- commands,
261
- verbose,
262
- onClose: onDone,
263
- unmount: context.unmount
61
+ logs: allRawLogs,
62
+ onSelect: handleSelect,
63
+ onClose: onDone
264
64
  }
265
65
  );
266
66
  }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/commands/resume.tsx"],
4
- "sourcesContent": ["/**\n * Resume Command\n *\n * Resume a previous conversation.\n * Uses TabbedListView with 3 tabs: Recent, Project, All.\n *\n * Usage:\n * /resume # Show sessions with tabs\n * /r # Alias\n */\n\nimport React, { useState, useMemo } from 'react'\nimport { render } from 'ink'\nimport path from 'path'\nimport type { Command } from '@commands'\nimport { t } from '@i18n'\nimport { getCwd } from '@utils/state'\nimport { CACHE_PATHS, loadLogList } from '@utils/log'\nimport type { LogOption } from '@minto-types/logs'\nimport { deserializeMessages } from '@utils/conversationRecovery'\nimport { getNextAvailableLogForkNumber, logError } from '@utils/log'\nimport { isDefaultSlowAndCapableModel } from '@utils/model'\nimport { prepareTerminalForREPL } from '@utils/terminal'\nimport { REPL } from '@screens/REPL'\nimport type { Tool } from '@tool'\nimport {\n TabbedListView,\n type ListItem,\n type TabDefinition,\n} from '@components/TabbedListView'\n\n/**\n * Format date for display\n * - Today: \"Today HH:mm\"\n * - Yesterday: \"Yesterday HH:mm\"\n * - Other: \"MM-DD HH:mm\"\n */\nfunction formatDate(date: Date): string {\n const now = new Date()\n\n const hours = date.getHours().toString().padStart(2, '0')\n const minutes = date.getMinutes().toString().padStart(2, '0')\n const timeStr = `${hours}:${minutes}`\n\n // Check if it's today\n const isToday =\n date.getDate() === now.getDate() &&\n date.getMonth() === now.getMonth() &&\n date.getFullYear() === now.getFullYear()\n\n if (isToday) {\n return `${t('commands.sessions.today')} ${timeStr}`\n }\n\n // Check if it's yesterday\n const yesterday = new Date(now)\n yesterday.setDate(yesterday.getDate() - 1)\n const isYesterday =\n date.getDate() === yesterday.getDate() &&\n date.getMonth() === yesterday.getMonth() &&\n date.getFullYear() === yesterday.getFullYear()\n\n if (isYesterday) {\n return `${t('commands.sessions.yesterday')} ${timeStr}`\n }\n\n // Default format: MM-DD HH:mm\n const month = (date.getMonth() + 1).toString().padStart(2, '0')\n const day = date.getDate().toString().padStart(2, '0')\n return `${month}-${day} ${timeStr}`\n}\n\n/**\n * Truncate string with ellipsis\n */\nfunction truncate(str: string, maxLength: number): string {\n if (str.length <= maxLength) return str\n return str.slice(0, maxLength - 3) + '...'\n}\n\n/**\n * Check if the conversation was discarded (last user message is /clear)\n */\nfunction wasCleared(log: LogOption): boolean {\n // Find the last user message by iterating backwards\n for (let i = log.messages.length - 1; i >= 0; i--) {\n const msg = log.messages[i]\n if (msg.type === 'user') {\n const content =\n typeof msg.message?.content === 'string'\n ? msg.message.content\n : Array.isArray(msg.message?.content)\n ? msg.message.content\n .filter((c: any) => c.type === 'text')\n .map((c: any) => c.text)\n .join('')\n : ''\n // Check if the last user message is a /clear command\n return content.includes('<command-name>clear</command-name>')\n }\n }\n return false\n}\n\n/**\n * Deduplicate logs by keeping only the latest fork for each base conversation.\n * Groups logs by their base date (timestamp without fork number) and keeps\n * the one with the highest fork number or most recent modification.\n */\nfunction deduplicateLogForks(logs: LogOption[]): LogOption[] {\n // Group by base date (the original conversation timestamp)\n const groupedByDate = new Map<string, LogOption[]>()\n\n for (const log of logs) {\n const existing = groupedByDate.get(log.date) || []\n existing.push(log)\n groupedByDate.set(log.date, existing)\n }\n\n // For each group, keep the one with highest fork number (most recent state)\n const deduped: LogOption[] = []\n for (const [, group] of groupedByDate) {\n // Sort by forkNumber desc (higher = more recent), then by modified desc\n const sorted = group.sort((a, b) => {\n const forkDiff = (b.forkNumber ?? 0) - (a.forkNumber ?? 0)\n if (forkDiff !== 0) return forkDiff\n return b.modified.getTime() - a.modified.getTime()\n })\n // Keep only the first one (highest fork / most recently modified)\n if (sorted[0]) {\n deduped.push(sorted[0])\n }\n }\n\n // Re-sort by modified time descending\n return deduped.sort((a, b) => b.modified.getTime() - a.modified.getTime())\n}\n\n/**\n * Get project path from log's first message\n */\nfunction getLogProjectPath(log: LogOption): string | null {\n const firstMessage = log.messages[0]\n return firstMessage?.cwd || null\n}\n\n/**\n * Get project name from path\n */\nfunction getProjectName(projectPath: string): string {\n return path.basename(projectPath) || projectPath\n}\n\n/**\n * Extract clean first prompt from log (skip system messages and XML tags)\n */\nfunction extractFirstPrompt(log: LogOption): string {\n for (const msg of log.messages) {\n if (msg.type === 'user') {\n let content = ''\n if (typeof msg.message?.content === 'string') {\n content = msg.message.content\n } else if (Array.isArray(msg.message?.content)) {\n content = msg.message.content\n .filter((c: any) => c.type === 'text')\n .map((c: any) => c.text)\n .join('')\n }\n\n // Skip system messages (XML tags like <system-reminder>, <command-name>, etc.)\n const trimmed = content.trim()\n if (\n trimmed.startsWith('<system-reminder>') ||\n trimmed.startsWith('<command-name>') ||\n (trimmed.startsWith('<') && trimmed.includes('</'))\n ) {\n continue\n }\n\n // Return first line, cleaned up\n const firstLine = content.split('\\n')[0]?.trim() || ''\n if (firstLine) {\n return firstLine\n }\n }\n }\n return log.firstPrompt || 'No prompt'\n}\n\n/**\n * Count tool calls in a log\n */\nfunction countToolCalls(log: LogOption): number {\n let count = 0\n for (const msg of log.messages) {\n if (msg.type === 'assistant' && Array.isArray(msg.message?.content)) {\n for (const block of msg.message.content) {\n if (block.type === 'tool_use') {\n count++\n }\n }\n }\n }\n return count\n}\n\n/**\n * Convert LogOption to ListItem for TabbedListView\n */\nfunction logToListItem(log: LogOption): ListItem {\n const dateStr = formatDate(log.modified)\n const projectPath = getLogProjectPath(log) || ''\n const projectName = projectPath\n ? truncate(getProjectName(projectPath), 15)\n : ''\n const msgCount = log.messageCount\n const toolCount = countToolCalls(log)\n const firstPrompt = extractFirstPrompt(log)\n\n return {\n id: log.fullPath, // Use fullPath as unique id (date can be duplicated for forks)\n label: truncate(firstPrompt, 45),\n description: projectName || undefined,\n metadata: `${dateStr} \u00B7 ${msgCount} msgs \u00B7 ${toolCount} tools`,\n category: projectName || 'Unknown',\n data: log,\n }\n}\n\ninterface ResumeDisplayProps {\n recentLogs: LogOption[]\n projectLogs: LogOption[]\n allLogs: LogOption[]\n tools: Tool[]\n commands: Command[]\n verbose: boolean | undefined\n onClose: () => void\n unmount: () => void\n}\n\n/**\n * Resume display component with TabbedListView\n */\nfunction ResumeDisplay({\n recentLogs,\n projectLogs,\n allLogs,\n tools,\n commands,\n verbose,\n onClose,\n unmount,\n}: ResumeDisplayProps) {\n const [activeTab, setActiveTab] = useState('recent')\n const [searchQuery, setSearchQuery] = useState('')\n\n // Tab definitions\n const tabs: TabDefinition[] = useMemo(\n () => [\n {\n id: 'recent',\n label: t('commands.sessions.title'),\n badge: recentLogs.length,\n },\n {\n id: 'project',\n label: t('commands.sessions.headerProject'),\n badge: projectLogs.length,\n },\n {\n id: 'all',\n label: t('common.all'),\n badge: allLogs.length,\n },\n ],\n [recentLogs.length, projectLogs.length, allLogs.length],\n )\n\n // Get items based on active tab\n const items: ListItem[] = useMemo(() => {\n let logs: LogOption[]\n\n switch (activeTab) {\n case 'project':\n logs = projectLogs\n break\n case 'all':\n logs = allLogs\n break\n case 'recent':\n default:\n logs = recentLogs\n }\n\n return logs.map(logToListItem)\n }, [activeTab, recentLogs, projectLogs, allLogs])\n\n // Handle item selection - load and resume conversation\n const handleSelect = async (item: ListItem) => {\n const log = item.data as LogOption\n\n try {\n // First close the selection UI\n onClose()\n\n // Check if using default model before unmounting\n const isDefaultModel = await isDefaultSlowAndCapableModel()\n\n // Unmount current REPL before creating new one\n // This prevents two Ink instances from conflicting\n unmount()\n\n // Clear screen and prepare terminal for REPL\n await prepareTerminalForREPL()\n\n render(\n <REPL\n messageLogName={log.date}\n initialPrompt=\"\"\n shouldShowPromptInput={true}\n verbose={verbose}\n commands={commands}\n tools={tools}\n initialMessages={deserializeMessages(log.messages, tools)}\n initialForkNumber={getNextAvailableLogForkNumber(\n log.date,\n log.forkNumber ?? 1,\n 0,\n )}\n isDefaultModel={isDefaultModel}\n isResumedConversation={true}\n />,\n {\n exitOnCtrlC: false,\n },\n )\n } catch (e) {\n logError(`Failed to load conversation: ${e}`)\n throw e\n }\n }\n\n return (\n <TabbedListView\n title={t('commands.resume.title')}\n tabs={tabs}\n activeTab={activeTab}\n onTabChange={setActiveTab}\n items={items}\n searchEnabled={true}\n searchPlaceholder={t('ui.tabbedList.search')}\n searchQuery={searchQuery}\n onSearchChange={setSearchQuery}\n onSelect={handleSelect}\n onClose={onClose}\n emptyText={t('commands.resume.noSessions')}\n footerHint={t('commands.resume.navigationHint')}\n groupByCategory={activeTab === 'all'}\n />\n )\n}\n\nexport default {\n type: 'local-jsx',\n name: 'resume',\n description: t('commands.resume.description'),\n isEnabled: true,\n isHidden: false,\n hidePromptInput: true,\n aliases: ['r'],\n userFacingName() {\n return 'resume'\n },\n async call(onDone, context) {\n const { commands = [], tools = [], verbose = false } = context.options || {}\n const cwd = getCwd()\n\n // Load all logs\n const allRawLogs = await loadLogList(CACHE_PATHS.messages())\n\n // Filter out cleared conversations, then deduplicate forks\n // (keep only the latest fork for each base conversation)\n const validLogs = deduplicateLogForks(\n allRawLogs.filter(log => !wasCleared(log)),\n )\n\n // Recent: first 20 logs (already sorted by modified time)\n const recentLogs = validLogs.slice(0, 20)\n\n // Project: logs from current project\n const projectLogs = validLogs.filter(log => {\n const logPath = getLogProjectPath(log)\n return logPath === cwd\n })\n\n // All: all valid logs (up to 100)\n const allLogs = validLogs.slice(0, 100)\n\n return (\n <ResumeDisplay\n recentLogs={recentLogs}\n projectLogs={projectLogs}\n allLogs={allLogs}\n tools={tools}\n commands={commands}\n verbose={verbose}\n onClose={onDone}\n unmount={context.unmount}\n />\n )\n },\n} satisfies Command\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["/**\n * Resume Command (/resume, /r)\n *\n * Resume a previous conversation from within the REPL.\n * Reuses SessionPicker from ResumeConversation screen.\n */\n\nimport React from 'react'\nimport { render } from 'ink'\nimport type { Command } from '@commands'\nimport { t } from '@i18n'\nimport { CACHE_PATHS, loadLogList } from '@utils/log'\nimport type { LogOption } from '@minto-types/logs'\nimport { deserializeMessages } from '@utils/conversationRecovery'\nimport { getNextAvailableLogForkNumber, logError } from '@utils/log'\nimport { isDefaultSlowAndCapableModel } from '@utils/model'\nimport { prepareTerminalForREPL } from '@utils/terminal'\nimport { REPL } from '@screens/REPL'\nimport type { Tool } from '@tool'\nimport { SessionPicker } from '@screens/ResumeConversation'\n\nexport default {\n type: 'local-jsx',\n name: 'resume',\n description: t('commands.resume.description'),\n isEnabled: true,\n isHidden: false,\n hidePromptInput: true,\n aliases: ['r'],\n userFacingName() {\n return 'resume'\n },\n async call(onDone, context) {\n const { commands = [], tools = [], verbose = false } = context.options || {}\n\n const allRawLogs = await loadLogList(CACHE_PATHS.messages())\n\n const handleSelect = async (log: LogOption) => {\n try {\n onDone()\n const isDefaultModel = await isDefaultSlowAndCapableModel()\n context.unmount()\n await prepareTerminalForREPL()\n render(\n <REPL\n messageLogName={log.date}\n initialPrompt=\"\"\n shouldShowPromptInput={true}\n verbose={verbose}\n commands={commands}\n tools={tools as Tool[]}\n initialMessages={deserializeMessages(log.messages, tools as Tool[])}\n initialForkNumber={getNextAvailableLogForkNumber(\n log.date,\n log.forkNumber ?? 1,\n 0,\n )}\n isDefaultModel={isDefaultModel}\n isResumedConversation={true}\n />,\n { exitOnCtrlC: false },\n )\n } catch (e) {\n logError(`Failed to load conversation: ${e}`)\n throw e\n }\n }\n\n return (\n <SessionPicker\n logs={allRawLogs}\n onSelect={handleSelect}\n onClose={onDone}\n />\n )\n },\n} satisfies Command\n"],
5
+ "mappings": "AAOA,OAAO,WAAW;AAClB,SAAS,cAAc;AAEvB,SAAS,SAAS;AAClB,SAAS,aAAa,mBAAmB;AAEzC,SAAS,2BAA2B;AACpC,SAAS,+BAA+B,gBAAgB;AACxD,SAAS,oCAAoC;AAC7C,SAAS,8BAA8B;AACvC,SAAS,YAAY;AAErB,SAAS,qBAAqB;AAE9B,IAAO,iBAAQ;AAAA,EACb,MAAM;AAAA,EACN,MAAM;AAAA,EACN,aAAa,EAAE,6BAA6B;AAAA,EAC5C,WAAW;AAAA,EACX,UAAU;AAAA,EACV,iBAAiB;AAAA,EACjB,SAAS,CAAC,GAAG;AAAA,EACb,iBAAiB;AACf,WAAO;AAAA,EACT;AAAA,EACA,MAAM,KAAK,QAAQ,SAAS;AAC1B,UAAM,EAAE,WAAW,CAAC,GAAG,QAAQ,CAAC,GAAG,UAAU,MAAM,IAAI,QAAQ,WAAW,CAAC;AAE3E,UAAM,aAAa,MAAM,YAAY,YAAY,SAAS,CAAC;AAE3D,UAAM,eAAe,OAAO,QAAmB;AAC7C,UAAI;AACF,eAAO;AACP,cAAM,iBAAiB,MAAM,6BAA6B;AAC1D,gBAAQ,QAAQ;AAChB,cAAM,uBAAuB;AAC7B;AAAA,UACE;AAAA,YAAC;AAAA;AAAA,cACC,gBAAgB,IAAI;AAAA,cACpB,eAAc;AAAA,cACd,uBAAuB;AAAA,cACvB;AAAA,cACA;AAAA,cACA;AAAA,cACA,iBAAiB,oBAAoB,IAAI,UAAU,KAAe;AAAA,cAClE,mBAAmB;AAAA,gBACjB,IAAI;AAAA,gBACJ,IAAI,cAAc;AAAA,gBAClB;AAAA,cACF;AAAA,cACA;AAAA,cACA,uBAAuB;AAAA;AAAA,UACzB;AAAA,UACA,EAAE,aAAa,MAAM;AAAA,QACvB;AAAA,MACF,SAAS,GAAG;AACV,iBAAS,gCAAgC,CAAC,EAAE;AAC5C,cAAM;AAAA,MACR;AAAA,IACF;AAEA,WACE;AAAA,MAAC;AAAA;AAAA,QACC,MAAM;AAAA,QACN,UAAU;AAAA,QACV,SAAS;AAAA;AAAA,IACX;AAAA,EAEJ;AACF;",
6
6
  "names": []
7
7
  }
@@ -84,7 +84,7 @@ function formatTasks(tasks2) {
84
84
  );
85
85
  lines.push("");
86
86
  lines.push("Use TaskOutput tool to get output from a specific task.");
87
- lines.push("Use KillShell tool to terminate a running shell.");
87
+ lines.push("Use TaskStop tool to terminate a running task.");
88
88
  return lines.join("\n");
89
89
  }
90
90
  const tasks = {
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/commands/tasks.ts"],
4
- "sourcesContent": ["import type { Command } from '@commands'\nimport { BackgroundShellManager } from '@utils/BackgroundShellManager'\nimport {\n listAgentTranscripts,\n type AgentTranscriptSummary,\n} from '@utils/agentTranscripts'\nimport { formatDuration } from '@utils/format'\n\n/**\n * List background tasks (shells and agents)\n * Shows running and recently completed tasks\n */\n\ntype TaskType = 'shell' | 'agent'\ntype TaskStatus =\n | 'running'\n | 'done'\n | 'killed'\n | 'completed'\n | 'failed'\n | 'interrupted'\n\ninterface TaskInfo {\n id: string\n type: TaskType\n command: string\n status: TaskStatus\n startTime: number\n endTime?: number\n duration: number\n}\n\nfunction collectTasks(): TaskInfo[] {\n const tasks: TaskInfo[] = []\n\n // Collect background shells\n const shellManager = BackgroundShellManager.getInstance()\n const shells = shellManager.list()\n\n for (const shell of shells) {\n const duration = shell.endTime\n ? shell.endTime - shell.startTime\n : Date.now() - shell.startTime\n\n tasks.push({\n id: shell.id,\n type: 'shell',\n command:\n shell.command.length > 50\n ? shell.command.slice(0, 47) + '...'\n : shell.command,\n status: shell.status,\n startTime: shell.startTime,\n endTime: shell.endTime,\n duration,\n })\n }\n\n // Collect agent transcripts\n const transcripts = listAgentTranscripts({\n limit: 20,\n })\n\n for (const transcript of transcripts) {\n const duration = transcript.endTime\n ? transcript.endTime - transcript.startTime\n : Date.now() - transcript.startTime\n\n tasks.push({\n id: transcript.agentId,\n type: 'agent',\n command: transcript.description,\n status: transcript.status,\n startTime: transcript.startTime,\n endTime: transcript.endTime,\n duration,\n })\n }\n\n // Sort by start time, most recent first\n return tasks.sort((a, b) => b.startTime - a.startTime)\n}\n\nfunction formatStatus(status: TaskStatus): string {\n switch (status) {\n case 'running':\n return '\u25B6 running'\n case 'done':\n case 'completed':\n return '\u2713 done'\n case 'killed':\n return '\u2717 killed'\n case 'failed':\n return '\u2717 failed'\n case 'interrupted':\n return '\u23F8 interrupted'\n default:\n return status\n }\n}\n\nfunction formatTasks(tasks: TaskInfo[]): string {\n if (tasks.length === 0) {\n return 'No background tasks'\n }\n\n const lines: string[] = []\n lines.push('=== Background Tasks ===\\n')\n\n // Group by status\n const running = tasks.filter(t => t.status === 'running')\n const completed = tasks.filter(t => t.status !== 'running')\n\n if (running.length > 0) {\n lines.push('## Running')\n for (const task of running) {\n lines.push(\n ` [${task.type}] ${task.id} ${formatDuration(task.duration)} ${task.command}`,\n )\n }\n lines.push('')\n }\n\n if (completed.length > 0) {\n lines.push('## Recent')\n for (const task of completed.slice(0, 10)) {\n lines.push(\n ` [${task.type}] ${task.id} ${formatStatus(task.status)} ${formatDuration(task.duration)} ${task.command}`,\n )\n }\n lines.push('')\n }\n\n // Summary\n lines.push(\n `Total: ${running.length} running, ${completed.length} completed/stopped`,\n )\n lines.push('')\n lines.push('Use TaskOutput tool to get output from a specific task.')\n lines.push('Use KillShell tool to terminate a running shell.')\n\n return lines.join('\\n')\n}\n\nconst tasks = {\n type: 'local',\n name: 'tasks',\n description: 'List background tasks (shells and agents)',\n isEnabled: true,\n isHidden: false,\n async call() {\n const taskList = collectTasks()\n return formatTasks(taskList)\n },\n userFacingName() {\n return 'tasks'\n },\n} satisfies Command\n\nexport default tasks\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["import type { Command } from '@commands'\nimport { BackgroundShellManager } from '@utils/BackgroundShellManager'\nimport {\n listAgentTranscripts,\n type AgentTranscriptSummary,\n} from '@utils/agentTranscripts'\nimport { formatDuration } from '@utils/format'\n\n/**\n * List background tasks (shells and agents)\n * Shows running and recently completed tasks\n */\n\ntype TaskType = 'shell' | 'agent'\ntype TaskStatus =\n | 'running'\n | 'done'\n | 'killed'\n | 'completed'\n | 'failed'\n | 'interrupted'\n\ninterface TaskInfo {\n id: string\n type: TaskType\n command: string\n status: TaskStatus\n startTime: number\n endTime?: number\n duration: number\n}\n\nfunction collectTasks(): TaskInfo[] {\n const tasks: TaskInfo[] = []\n\n // Collect background shells\n const shellManager = BackgroundShellManager.getInstance()\n const shells = shellManager.list()\n\n for (const shell of shells) {\n const duration = shell.endTime\n ? shell.endTime - shell.startTime\n : Date.now() - shell.startTime\n\n tasks.push({\n id: shell.id,\n type: 'shell',\n command:\n shell.command.length > 50\n ? shell.command.slice(0, 47) + '...'\n : shell.command,\n status: shell.status,\n startTime: shell.startTime,\n endTime: shell.endTime,\n duration,\n })\n }\n\n // Collect agent transcripts\n const transcripts = listAgentTranscripts({\n limit: 20,\n })\n\n for (const transcript of transcripts) {\n const duration = transcript.endTime\n ? transcript.endTime - transcript.startTime\n : Date.now() - transcript.startTime\n\n tasks.push({\n id: transcript.agentId,\n type: 'agent',\n command: transcript.description,\n status: transcript.status,\n startTime: transcript.startTime,\n endTime: transcript.endTime,\n duration,\n })\n }\n\n // Sort by start time, most recent first\n return tasks.sort((a, b) => b.startTime - a.startTime)\n}\n\nfunction formatStatus(status: TaskStatus): string {\n switch (status) {\n case 'running':\n return '\u25B6 running'\n case 'done':\n case 'completed':\n return '\u2713 done'\n case 'killed':\n return '\u2717 killed'\n case 'failed':\n return '\u2717 failed'\n case 'interrupted':\n return '\u23F8 interrupted'\n default:\n return status\n }\n}\n\nfunction formatTasks(tasks: TaskInfo[]): string {\n if (tasks.length === 0) {\n return 'No background tasks'\n }\n\n const lines: string[] = []\n lines.push('=== Background Tasks ===\\n')\n\n // Group by status\n const running = tasks.filter(t => t.status === 'running')\n const completed = tasks.filter(t => t.status !== 'running')\n\n if (running.length > 0) {\n lines.push('## Running')\n for (const task of running) {\n lines.push(\n ` [${task.type}] ${task.id} ${formatDuration(task.duration)} ${task.command}`,\n )\n }\n lines.push('')\n }\n\n if (completed.length > 0) {\n lines.push('## Recent')\n for (const task of completed.slice(0, 10)) {\n lines.push(\n ` [${task.type}] ${task.id} ${formatStatus(task.status)} ${formatDuration(task.duration)} ${task.command}`,\n )\n }\n lines.push('')\n }\n\n // Summary\n lines.push(\n `Total: ${running.length} running, ${completed.length} completed/stopped`,\n )\n lines.push('')\n lines.push('Use TaskOutput tool to get output from a specific task.')\n lines.push('Use TaskStop tool to terminate a running task.')\n\n return lines.join('\\n')\n}\n\nconst tasks = {\n type: 'local',\n name: 'tasks',\n description: 'List background tasks (shells and agents)',\n isEnabled: true,\n isHidden: false,\n async call() {\n const taskList = collectTasks()\n return formatTasks(taskList)\n },\n userFacingName() {\n return 'tasks'\n },\n} satisfies Command\n\nexport default tasks\n"],
5
+ "mappings": "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",
6
6
  "names": ["tasks"]
7
7
  }
@@ -3,7 +3,11 @@ import { execFileNoThrow } from "../utils/execFileNoThrow.js";
3
3
  import chalk from "chalk";
4
4
  import { getTheme } from "../utils/theme.js";
5
5
  import { env } from "../utils/env.js";
6
- import { getGlobalConfig, saveGlobalConfig } from "../utils/config.js";
6
+ import {
7
+ getGlobalConfig,
8
+ getMutableGlobalConfig,
9
+ saveGlobalConfig
10
+ } from "../utils/config.js";
7
11
  import { markProjectOnboardingComplete } from "../components/ProjectOnboarding.js";
8
12
  import { readFileSync, writeFileSync } from "fs";
9
13
  import { join } from "path";
@@ -29,7 +33,7 @@ const terminalSetup = {
29
33
  result = installBindingsForVSCodeTerminal();
30
34
  break;
31
35
  }
32
- const config = getGlobalConfig();
36
+ const config = getMutableGlobalConfig();
33
37
  config.shiftEnterKeyBindingInstalled = true;
34
38
  saveGlobalConfig(config);
35
39
  markProjectOnboardingComplete();
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/commands/terminalSetup.ts"],
4
- "sourcesContent": ["import { Command } from '@commands'\nimport { EOL, platform, homedir } from 'os'\nimport { execFileNoThrow } from '@utils/execFileNoThrow'\nimport chalk from 'chalk'\nimport { getTheme } from '@utils/theme'\nimport { env } from '@utils/env'\nimport { getGlobalConfig, saveGlobalConfig } from '@utils/config'\nimport { markProjectOnboardingComplete } from '@components/ProjectOnboarding'\nimport { readFileSync, writeFileSync } from 'fs'\nimport { join } from 'path'\nimport { safeParseJSON } from '@utils/json'\nimport { logError } from '@utils/log'\nimport { PROJECT_FILE } from '@constants/product'\n\nconst terminalSetup: Command = {\n type: 'local',\n name: 'terminal-setup',\n userFacingName() {\n return 'terminal-setup'\n },\n description:\n '[Developer] Install Shift+Enter key binding for newlines (iTerm2 and VSCode only)',\n isEnabled:\n (platform() === 'darwin' && env.terminal === 'iTerm.app') ||\n env.terminal === 'vscode',\n isHidden: true,\n async call() {\n let result = ''\n\n switch (env.terminal) {\n case 'iTerm.app':\n result = await installBindingsForITerm2()\n break\n case 'vscode':\n result = installBindingsForVSCodeTerminal()\n break\n }\n\n // Update global config to indicate Shift+Enter key binding is installed\n const config = getGlobalConfig()\n config.shiftEnterKeyBindingInstalled = true\n saveGlobalConfig(config)\n\n // Mark onboarding as complete\n markProjectOnboardingComplete()\n\n return result\n },\n}\n\nexport function isShiftEnterKeyBindingInstalled(): boolean {\n return getGlobalConfig().shiftEnterKeyBindingInstalled === true\n}\n\nexport function handleHashCommand(interpreted: string): void {\n // Appends the AI-interpreted content to both MINTO.md and CLAUDE.md (if exists)\n try {\n const cwd = process.cwd()\n const codeContextPath = join(cwd, PROJECT_FILE)\n const claudePath = join(cwd, 'CLAUDE.md')\n\n // Check which files exist and update them\n const filesToUpdate = []\n\n // Always try to update MINTO.md (create if not exists)\n filesToUpdate.push({ path: codeContextPath, name: PROJECT_FILE })\n\n // Update AGENTS.md only if it exists\n const agentsPath = join(cwd, 'AGENTS.md')\n try {\n readFileSync(agentsPath, 'utf-8')\n filesToUpdate.push({ path: agentsPath, name: 'AGENTS.md' })\n } catch {\n // AGENTS.md doesn't exist, skip it\n }\n\n // Update CLAUDE.md only if it exists\n try {\n readFileSync(claudePath, 'utf-8')\n filesToUpdate.push({ path: claudePath, name: 'CLAUDE.md' })\n } catch {\n // CLAUDE.md doesn't exist, skip it\n }\n\n const now = new Date()\n const timezoneMatch = now.toString().match(/\\(([A-Z]+)\\)/)\n const timezone = timezoneMatch\n ? timezoneMatch[1]\n : now\n .toLocaleTimeString('en-us', { timeZoneName: 'short' })\n .split(' ')\n .pop()\n\n const timestamp = interpreted.includes(now.getFullYear().toString())\n ? ''\n : `\\n\\n_Added on ${now.toLocaleString()} ${timezone}_`\n\n const updatedFiles = []\n\n for (const file of filesToUpdate) {\n try {\n // Check if file exists, if not create it\n let existingContent = ''\n try {\n existingContent = readFileSync(file.path, 'utf-8').trim()\n } catch (error) {\n // File doesn't exist yet, that's fine\n }\n\n // Add a separator if the file already has content\n const separator = existingContent ? '\\n\\n' : ''\n\n // Combine everything and write to file\n const newContent = `${existingContent}${separator}${interpreted}${timestamp}`\n writeFileSync(file.path, newContent, 'utf-8')\n updatedFiles.push(file.name)\n } catch (error) {\n logError(error)\n console.error(\n chalk.hex(getTheme().error)(\n `Failed to update ${file.name}: ${error.message}`,\n ),\n )\n }\n }\n\n if (updatedFiles.length > 0) {\n console.log(\n chalk.hex(getTheme().success)(\n `Added note to ${updatedFiles.join(' and ')}`,\n ),\n )\n }\n } catch (e) {\n logError(e)\n console.error(\n chalk.hex(getTheme().error)(`Failed to add note: ${e.message}`),\n )\n }\n}\n\nexport default terminalSetup\n\nasync function installBindingsForITerm2(): Promise<string> {\n const { code } = await execFileNoThrow('defaults', [\n 'write',\n 'com.googlecode.iterm2',\n 'GlobalKeyMap',\n '-dict-add',\n '0xd-0x20000-0x24',\n `<dict>\n <key>Text</key>\n <string>\\\\n</string>\n <key>Action</key>\n <integer>12</integer>\n <key>Version</key>\n <integer>1</integer>\n <key>Keycode</key>\n <integer>13</integer>\n <key>Modifiers</key>\n <integer>131072</integer>\n </dict>`,\n ])\n\n if (code !== 0) {\n throw new Error('Failed to install iTerm2 Shift+Enter key binding')\n }\n\n return `${chalk.hex(getTheme().success)(\n 'Installed iTerm2 Shift+Enter key binding',\n )}${EOL}${chalk.dim('See iTerm2 \u2192 Preferences \u2192 Keys')}${EOL}`\n}\n\ntype VSCodeKeybinding = {\n key: string\n command: string\n args: { text: string }\n when: string\n}\n\nfunction installBindingsForVSCodeTerminal(): string {\n const vscodeKeybindingsPath = join(\n homedir(),\n platform() === 'win32'\n ? join('AppData', 'Roaming', 'Code', 'User')\n : platform() === 'darwin'\n ? join('Library', 'Application Support', 'Code', 'User')\n : join('.config', 'Code', 'User'),\n 'keybindings.json',\n )\n\n try {\n const content = readFileSync(vscodeKeybindingsPath, 'utf-8')\n const keybindings: VSCodeKeybinding[] =\n (safeParseJSON(content) as VSCodeKeybinding[]) ?? []\n\n // Check if keybinding already exists\n const existingBinding = keybindings.find(\n binding =>\n binding.key === 'shift+enter' &&\n binding.command === 'workbench.action.terminal.sendSequence' &&\n binding.when === 'terminalFocus',\n )\n if (existingBinding) {\n return `${chalk.hex(getTheme().warning)(\n 'Found existing VSCode terminal Shift+Enter key binding. Remove it to continue.',\n )}${EOL}${chalk.dim(`See ${vscodeKeybindingsPath}`)}${EOL}`\n }\n\n // Add the keybinding\n keybindings.push({\n key: 'shift+enter',\n command: 'workbench.action.terminal.sendSequence',\n args: { text: '\\\\\\r\\n' },\n when: 'terminalFocus',\n })\n\n writeFileSync(\n vscodeKeybindingsPath,\n JSON.stringify(keybindings, null, 4),\n 'utf-8',\n )\n\n return `${chalk.hex(getTheme().success)(\n 'Installed VSCode terminal Shift+Enter key binding',\n )}${EOL}${chalk.dim(`See ${vscodeKeybindingsPath}`)}${EOL}`\n } catch (e) {\n logError(e)\n throw new Error('Failed to install VSCode terminal Shift+Enter key binding')\n }\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["import { Command } from '@commands'\nimport { EOL, platform, homedir } from 'os'\nimport { execFileNoThrow } from '@utils/execFileNoThrow'\nimport chalk from 'chalk'\nimport { getTheme } from '@utils/theme'\nimport { env } from '@utils/env'\nimport {\n getGlobalConfig,\n getMutableGlobalConfig,\n saveGlobalConfig,\n} from '@utils/config'\nimport { markProjectOnboardingComplete } from '@components/ProjectOnboarding'\nimport { readFileSync, writeFileSync } from 'fs'\nimport { join } from 'path'\nimport { safeParseJSON } from '@utils/json'\nimport { logError } from '@utils/log'\nimport { PROJECT_FILE } from '@constants/product'\n\nconst terminalSetup: Command = {\n type: 'local',\n name: 'terminal-setup',\n userFacingName() {\n return 'terminal-setup'\n },\n description:\n '[Developer] Install Shift+Enter key binding for newlines (iTerm2 and VSCode only)',\n isEnabled:\n (platform() === 'darwin' && env.terminal === 'iTerm.app') ||\n env.terminal === 'vscode',\n isHidden: true,\n async call() {\n let result = ''\n\n switch (env.terminal) {\n case 'iTerm.app':\n result = await installBindingsForITerm2()\n break\n case 'vscode':\n result = installBindingsForVSCodeTerminal()\n break\n }\n\n // Update global config to indicate Shift+Enter key binding is installed\n const config = getMutableGlobalConfig()\n config.shiftEnterKeyBindingInstalled = true\n saveGlobalConfig(config)\n\n // Mark onboarding as complete\n markProjectOnboardingComplete()\n\n return result\n },\n}\n\nexport function isShiftEnterKeyBindingInstalled(): boolean {\n return getGlobalConfig().shiftEnterKeyBindingInstalled === true\n}\n\nexport function handleHashCommand(interpreted: string): void {\n // Appends the AI-interpreted content to both MINTO.md and CLAUDE.md (if exists)\n try {\n const cwd = process.cwd()\n const codeContextPath = join(cwd, PROJECT_FILE)\n const claudePath = join(cwd, 'CLAUDE.md')\n\n // Check which files exist and update them\n const filesToUpdate = []\n\n // Always try to update MINTO.md (create if not exists)\n filesToUpdate.push({ path: codeContextPath, name: PROJECT_FILE })\n\n // Update AGENTS.md only if it exists\n const agentsPath = join(cwd, 'AGENTS.md')\n try {\n readFileSync(agentsPath, 'utf-8')\n filesToUpdate.push({ path: agentsPath, name: 'AGENTS.md' })\n } catch {\n // AGENTS.md doesn't exist, skip it\n }\n\n // Update CLAUDE.md only if it exists\n try {\n readFileSync(claudePath, 'utf-8')\n filesToUpdate.push({ path: claudePath, name: 'CLAUDE.md' })\n } catch {\n // CLAUDE.md doesn't exist, skip it\n }\n\n const now = new Date()\n const timezoneMatch = now.toString().match(/\\(([A-Z]+)\\)/)\n const timezone = timezoneMatch\n ? timezoneMatch[1]\n : now\n .toLocaleTimeString('en-us', { timeZoneName: 'short' })\n .split(' ')\n .pop()\n\n const timestamp = interpreted.includes(now.getFullYear().toString())\n ? ''\n : `\\n\\n_Added on ${now.toLocaleString()} ${timezone}_`\n\n const updatedFiles = []\n\n for (const file of filesToUpdate) {\n try {\n // Check if file exists, if not create it\n let existingContent = ''\n try {\n existingContent = readFileSync(file.path, 'utf-8').trim()\n } catch (error) {\n // File doesn't exist yet, that's fine\n }\n\n // Add a separator if the file already has content\n const separator = existingContent ? '\\n\\n' : ''\n\n // Combine everything and write to file\n const newContent = `${existingContent}${separator}${interpreted}${timestamp}`\n writeFileSync(file.path, newContent, 'utf-8')\n updatedFiles.push(file.name)\n } catch (error) {\n logError(error)\n console.error(\n chalk.hex(getTheme().error)(\n `Failed to update ${file.name}: ${error.message}`,\n ),\n )\n }\n }\n\n if (updatedFiles.length > 0) {\n console.log(\n chalk.hex(getTheme().success)(\n `Added note to ${updatedFiles.join(' and ')}`,\n ),\n )\n }\n } catch (e) {\n logError(e)\n console.error(\n chalk.hex(getTheme().error)(`Failed to add note: ${e.message}`),\n )\n }\n}\n\nexport default terminalSetup\n\nasync function installBindingsForITerm2(): Promise<string> {\n const { code } = await execFileNoThrow('defaults', [\n 'write',\n 'com.googlecode.iterm2',\n 'GlobalKeyMap',\n '-dict-add',\n '0xd-0x20000-0x24',\n `<dict>\n <key>Text</key>\n <string>\\\\n</string>\n <key>Action</key>\n <integer>12</integer>\n <key>Version</key>\n <integer>1</integer>\n <key>Keycode</key>\n <integer>13</integer>\n <key>Modifiers</key>\n <integer>131072</integer>\n </dict>`,\n ])\n\n if (code !== 0) {\n throw new Error('Failed to install iTerm2 Shift+Enter key binding')\n }\n\n return `${chalk.hex(getTheme().success)(\n 'Installed iTerm2 Shift+Enter key binding',\n )}${EOL}${chalk.dim('See iTerm2 \u2192 Preferences \u2192 Keys')}${EOL}`\n}\n\ntype VSCodeKeybinding = {\n key: string\n command: string\n args: { text: string }\n when: string\n}\n\nfunction installBindingsForVSCodeTerminal(): string {\n const vscodeKeybindingsPath = join(\n homedir(),\n platform() === 'win32'\n ? join('AppData', 'Roaming', 'Code', 'User')\n : platform() === 'darwin'\n ? join('Library', 'Application Support', 'Code', 'User')\n : join('.config', 'Code', 'User'),\n 'keybindings.json',\n )\n\n try {\n const content = readFileSync(vscodeKeybindingsPath, 'utf-8')\n const keybindings: VSCodeKeybinding[] =\n (safeParseJSON(content) as VSCodeKeybinding[]) ?? []\n\n // Check if keybinding already exists\n const existingBinding = keybindings.find(\n binding =>\n binding.key === 'shift+enter' &&\n binding.command === 'workbench.action.terminal.sendSequence' &&\n binding.when === 'terminalFocus',\n )\n if (existingBinding) {\n return `${chalk.hex(getTheme().warning)(\n 'Found existing VSCode terminal Shift+Enter key binding. Remove it to continue.',\n )}${EOL}${chalk.dim(`See ${vscodeKeybindingsPath}`)}${EOL}`\n }\n\n // Add the keybinding\n keybindings.push({\n key: 'shift+enter',\n command: 'workbench.action.terminal.sendSequence',\n args: { text: '\\\\\\r\\n' },\n when: 'terminalFocus',\n })\n\n writeFileSync(\n vscodeKeybindingsPath,\n JSON.stringify(keybindings, null, 4),\n 'utf-8',\n )\n\n return `${chalk.hex(getTheme().success)(\n 'Installed VSCode terminal Shift+Enter key binding',\n )}${EOL}${chalk.dim(`See ${vscodeKeybindingsPath}`)}${EOL}`\n } catch (e) {\n logError(e)\n throw new Error('Failed to install VSCode terminal Shift+Enter key binding')\n }\n}\n"],
5
+ "mappings": "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",
6
6
  "names": []
7
7
  }
package/dist/commands.js CHANGED
@@ -21,6 +21,7 @@ import agents from "./commands/agents/index.js";
21
21
  import plugin from "./commands/plugin.js";
22
22
  import undo from "./commands/undo.js";
23
23
  import language from "./commands/language.js";
24
+ import login from "./commands/login.js";
24
25
  import { quit } from "./commands/quit.js";
25
26
  import stats from "./commands/stats.js";
26
27
  import effort from "./commands/effort.js";
@@ -52,6 +53,7 @@ const COMMANDS = memoize(() => [
52
53
  help,
53
54
  init,
54
55
  language,
56
+ login,
55
57
  mcp,
56
58
  memory,
57
59
  model,
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../src/commands.ts"],
4
- "sourcesContent": ["import React from 'react'\nimport clear from './commands/clear'\nimport compact from './commands/compact'\nimport config from './commands/config'\nimport context from './commands/context'\nimport cost from './commands/cost'\nimport ctx_viz from './commands/ctx_viz'\nimport exportCmd from './commands/export'\nimport help from './commands/help'\nimport init from './commands/init'\nimport mcp from './commands/mcp-interactive'\nimport model from './commands/model'\nimport permissions from './commands/permissions'\nimport refreshCommands from './commands/refreshCommands'\nimport sandbox from './commands/sandbox'\nimport setup from './commands/setup'\nimport status from './commands/status'\nimport terminalSetup from './commands/terminalSetup'\nimport { Tool, ToolUseContext } from './Tool'\nimport resume from './commands/resume'\nimport newCmd from './commands/new'\nimport agents from './commands/agents'\nimport plugin from './commands/plugin'\nimport undo from './commands/undo'\nimport language from './commands/language'\nimport { quit } from './commands/quit'\nimport stats from './commands/stats'\n// Phase: CC compatibility commands\nimport effort from './commands/effort'\nimport memory from './commands/memory'\nimport outputStyle from './commands/outputStyle'\nimport review from './commands/review'\n// Phase 4: Diagnostic and task management commands\nimport doctor from './commands/doctor'\nimport bug from './commands/bug'\nimport tasks from './commands/tasks'\nimport todos from './commands/todos'\nimport { getMCPCommands } from './services/mcpClient'\nimport {\n loadCustomCommands,\n loadPluginCommands,\n} from './services/customCommands'\nimport type { MessageParam } from '@anthropic-ai/sdk/resources/index.mjs'\nimport { memoize } from 'lodash-es'\nimport type { Message } from './query'\n\ntype PromptCommand = {\n type: 'prompt'\n progressMessage: string\n argNames?: string[]\n getPromptForCommand(args: string): Promise<MessageParam[]>\n}\n\ntype LocalCommand = {\n type: 'local'\n call(\n args: string,\n context: {\n options: {\n commands: Command[]\n tools: Tool[]\n slowAndCapableModel: string\n }\n abortController: AbortController\n setForkConvoWithMessagesOnTheNextRender: (\n forkConvoWithMessages: Message[],\n ) => void\n },\n ): Promise<string>\n}\n\ntype LocalJSXCommand = {\n type: 'local-jsx'\n call(\n onDone: (result?: string) => void,\n context: ToolUseContext & {\n setForkConvoWithMessagesOnTheNextRender: (\n forkConvoWithMessages: Message[],\n ) => void\n /** Unmount current REPL (for commands that need to replace the entire UI) */\n unmount?: () => void\n },\n args?: string,\n ): Promise<React.ReactNode>\n}\n\nexport type Command = {\n description: string\n isEnabled: boolean\n isHidden: boolean\n name: string\n aliases?: string[]\n /** When true, the command's JSX replaces the PromptInput instead of rendering below it */\n hidePromptInput?: boolean\n userFacingName(): string\n} & (PromptCommand | LocalCommand | LocalJSXCommand)\n\n// Hidden developer commands (not shown in /help but still accessible)\nconst HIDDEN_COMMANDS = [ctx_viz, refreshCommands, terminalSetup]\n\n// Declared as a function so that we don't run this until getCommands is called,\n// since underlying functions read from config, which can't be read at module initialization time\nconst COMMANDS = memoize((): Command[] => [\n agents,\n bug,\n clear,\n compact,\n config,\n context,\n cost,\n doctor,\n effort,\n exportCmd,\n help,\n init,\n language,\n mcp,\n memory,\n model,\n newCmd,\n outputStyle,\n permissions,\n plugin,\n quit,\n resume,\n review,\n sandbox,\n setup,\n stats,\n status,\n tasks,\n todos,\n undo,\n ...HIDDEN_COMMANDS,\n])\n\n/**\n * Get built-in commands only (no MCP/custom/plugin I/O).\n * Synchronous \u2014 safe to call before render for instant startup.\n */\nexport function getBuiltInCommands(): Command[] {\n return [...COMMANDS()]\n .sort((a, b) => a.userFacingName().localeCompare(b.userFacingName()))\n .filter(_ => _.isEnabled)\n}\n\nexport const getCommands = memoize(async (): Promise<Command[]> => {\n const [mcpCommands, customCommands, pluginCommands] = await Promise.all([\n getMCPCommands(),\n loadCustomCommands(),\n loadPluginCommands(),\n ])\n\n // Get built-in commands\n const builtInCommands = COMMANDS()\n\n // Sort built-in commands alphabetically by name\n const sortedBuiltIn = [...builtInCommands].sort((a, b) =>\n a.userFacingName().localeCompare(b.userFacingName()),\n )\n\n // Sort MCP commands alphabetically by name\n const sortedMCP = [...mcpCommands].sort((a, b) =>\n a.userFacingName().localeCompare(b.userFacingName()),\n )\n\n // Sort plugin commands alphabetically by name\n const sortedPlugin = [...pluginCommands].sort((a, b) =>\n a.userFacingName().localeCompare(b.userFacingName()),\n )\n\n // Sort custom commands alphabetically by name\n const sortedCustom = [...customCommands].sort((a, b) =>\n a.userFacingName().localeCompare(b.userFacingName()),\n )\n\n // Command priority (later overrides earlier):\n // 1. MCP commands (lowest priority) - sorted alphabetically\n // 2. Plugin commands - sorted alphabetically\n // 3. Custom commands (user/project) - sorted alphabetically\n // 4. Built-in commands (highest priority) - sorted alphabetically\n // Display order: Built-in first, then custom/plugin/MCP\n return [\n ...sortedBuiltIn,\n ...sortedCustom,\n ...sortedPlugin,\n ...sortedMCP,\n ].filter(_ => _.isEnabled)\n})\n\nexport function hasCommand(commandName: string, commands: Command[]): boolean {\n return commands.some(\n _ => _.userFacingName() === commandName || _.aliases?.includes(commandName),\n )\n}\n\nexport function getCommand(commandName: string, commands: Command[]): Command {\n const command = commands.find(\n _ => _.userFacingName() === commandName || _.aliases?.includes(commandName),\n ) as Command | undefined\n if (!command) {\n throw ReferenceError(\n `Command ${commandName} not found. Available commands: ${commands\n .map(_ => {\n const name = _.userFacingName()\n return _.aliases ? `${name} (aliases: ${_.aliases.join(', ')})` : name\n })\n .join(', ')}`,\n )\n }\n\n return command\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["import React from 'react'\nimport clear from './commands/clear'\nimport compact from './commands/compact'\nimport config from './commands/config'\nimport context from './commands/context'\nimport cost from './commands/cost'\nimport ctx_viz from './commands/ctx_viz'\nimport exportCmd from './commands/export'\nimport help from './commands/help'\nimport init from './commands/init'\nimport mcp from './commands/mcp-interactive'\nimport model from './commands/model'\nimport permissions from './commands/permissions'\nimport refreshCommands from './commands/refreshCommands'\nimport sandbox from './commands/sandbox'\nimport setup from './commands/setup'\nimport status from './commands/status'\nimport terminalSetup from './commands/terminalSetup'\nimport { Tool, ToolUseContext } from './Tool'\nimport resume from './commands/resume'\nimport newCmd from './commands/new'\nimport agents from './commands/agents'\nimport plugin from './commands/plugin'\nimport undo from './commands/undo'\nimport language from './commands/language'\nimport login from './commands/login'\nimport { quit } from './commands/quit'\nimport stats from './commands/stats'\n// Phase: CC compatibility commands\nimport effort from './commands/effort'\nimport memory from './commands/memory'\nimport outputStyle from './commands/outputStyle'\nimport review from './commands/review'\n// Phase 4: Diagnostic and task management commands\nimport doctor from './commands/doctor'\nimport bug from './commands/bug'\nimport tasks from './commands/tasks'\nimport todos from './commands/todos'\nimport { getMCPCommands } from './services/mcpClient'\nimport {\n loadCustomCommands,\n loadPluginCommands,\n} from './services/customCommands'\nimport type { MessageParam } from '@anthropic-ai/sdk/resources/index.mjs'\nimport { memoize } from 'lodash-es'\nimport type { Message } from './query'\n\ntype PromptCommand = {\n type: 'prompt'\n progressMessage: string\n argNames?: string[]\n getPromptForCommand(args: string): Promise<MessageParam[]>\n}\n\ntype LocalCommand = {\n type: 'local'\n call(\n args: string,\n context: {\n options: {\n commands: Command[]\n tools: Tool[]\n slowAndCapableModel: string\n }\n abortController: AbortController\n setForkConvoWithMessagesOnTheNextRender: (\n forkConvoWithMessages: Message[],\n ) => void\n },\n ): Promise<string | null>\n}\n\ntype LocalJSXCommand = {\n type: 'local-jsx'\n call(\n onDone: (result?: string) => void,\n context: ToolUseContext & {\n setForkConvoWithMessagesOnTheNextRender: (\n forkConvoWithMessages: Message[],\n ) => void\n /** Unmount current REPL (for commands that need to replace the entire UI) */\n unmount?: () => void\n },\n args?: string,\n ): Promise<React.ReactNode>\n}\n\nexport type Command = {\n description: string\n isEnabled: boolean\n isHidden: boolean\n name: string\n aliases?: string[]\n /** When true, the command's JSX replaces the PromptInput instead of rendering below it */\n hidePromptInput?: boolean\n userFacingName(): string\n} & (PromptCommand | LocalCommand | LocalJSXCommand)\n\n// Hidden developer commands (not shown in /help but still accessible)\nconst HIDDEN_COMMANDS = [ctx_viz, refreshCommands, terminalSetup]\n\n// Declared as a function so that we don't run this until getCommands is called,\n// since underlying functions read from config, which can't be read at module initialization time\nconst COMMANDS = memoize((): Command[] => [\n agents,\n bug,\n clear,\n compact,\n config,\n context,\n cost,\n doctor,\n effort,\n exportCmd,\n help,\n init,\n language,\n login,\n mcp,\n memory,\n model,\n newCmd,\n outputStyle,\n permissions,\n plugin,\n quit,\n resume,\n review,\n sandbox,\n setup,\n stats,\n status,\n tasks,\n todos,\n undo,\n ...HIDDEN_COMMANDS,\n])\n\n/**\n * Get built-in commands only (no MCP/custom/plugin I/O).\n * Synchronous \u2014 safe to call before render for instant startup.\n */\nexport function getBuiltInCommands(): Command[] {\n return [...COMMANDS()]\n .sort((a, b) => a.userFacingName().localeCompare(b.userFacingName()))\n .filter(_ => _.isEnabled)\n}\n\nexport const getCommands = memoize(async (): Promise<Command[]> => {\n const [mcpCommands, customCommands, pluginCommands] = await Promise.all([\n getMCPCommands(),\n loadCustomCommands(),\n loadPluginCommands(),\n ])\n\n // Get built-in commands\n const builtInCommands = COMMANDS()\n\n // Sort built-in commands alphabetically by name\n const sortedBuiltIn = [...builtInCommands].sort((a, b) =>\n a.userFacingName().localeCompare(b.userFacingName()),\n )\n\n // Sort MCP commands alphabetically by name\n const sortedMCP = [...mcpCommands].sort((a, b) =>\n a.userFacingName().localeCompare(b.userFacingName()),\n )\n\n // Sort plugin commands alphabetically by name\n const sortedPlugin = [...pluginCommands].sort((a, b) =>\n a.userFacingName().localeCompare(b.userFacingName()),\n )\n\n // Sort custom commands alphabetically by name\n const sortedCustom = [...customCommands].sort((a, b) =>\n a.userFacingName().localeCompare(b.userFacingName()),\n )\n\n // Command priority (later overrides earlier):\n // 1. MCP commands (lowest priority) - sorted alphabetically\n // 2. Plugin commands - sorted alphabetically\n // 3. Custom commands (user/project) - sorted alphabetically\n // 4. Built-in commands (highest priority) - sorted alphabetically\n // Display order: Built-in first, then custom/plugin/MCP\n return [\n ...sortedBuiltIn,\n ...sortedCustom,\n ...sortedPlugin,\n ...sortedMCP,\n ].filter(_ => _.isEnabled)\n})\n\nexport function hasCommand(commandName: string, commands: Command[]): boolean {\n return commands.some(\n _ => _.userFacingName() === commandName || _.aliases?.includes(commandName),\n )\n}\n\nexport function getCommand(commandName: string, commands: Command[]): Command {\n const command = commands.find(\n _ => _.userFacingName() === commandName || _.aliases?.includes(commandName),\n ) as Command | undefined\n if (!command) {\n throw ReferenceError(\n `Command ${commandName} not found. Available commands: ${commands\n .map(_ => {\n const name = _.userFacingName()\n return _.aliases ? `${name} (aliases: ${_.aliases.join(', ')})` : name\n })\n .join(', ')}`,\n )\n }\n\n return command\n}\n"],
5
+ "mappings": "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",
6
6
  "names": []
7
7
  }