@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
@@ -1,12 +1,11 @@
1
- import React, { useState, useEffect } from "react";
2
- import { Box, Text, useInput } from "ink";
3
- import { SEMANTIC_COLORS } from "../constants/colors.js";
1
+ import React, { useState, useEffect, useCallback, useMemo } from "react";
4
2
  import { getCwd } from "../utils/state.js";
5
3
  import {
6
4
  listBackedUpFiles,
7
5
  getBackupVersions,
8
6
  restoreBackup
9
7
  } from "../core/backupManager.js";
8
+ import { TabbedListView } from "../components/TabbedListView/TabbedListView.js";
10
9
  import { t } from "../i18n/index.js";
11
10
  function formatTimestamp(timestamp) {
12
11
  const date = new Date(timestamp);
@@ -42,198 +41,170 @@ function getRelativePath(filePath) {
42
41
  }
43
42
  return filePath;
44
43
  }
45
- const FileListView = ({ files, selectedIndex, onSelect, onClose }) => {
46
- useInput((input, key) => {
47
- if (key.escape || input === "q") {
48
- onClose();
49
- } else if (key.return) {
50
- if (files.length > 0 && files[selectedIndex]) {
51
- onSelect(files[selectedIndex]);
52
- }
53
- }
54
- });
55
- if (files.length === 0) {
56
- return /* @__PURE__ */ React.createElement(Box, { flexDirection: "column", marginY: 1 }, /* @__PURE__ */ React.createElement(Box, { marginBottom: 1 }, /* @__PURE__ */ React.createElement(Text, { bold: true, color: SEMANTIC_COLORS.brand }, t("commands.undo.title"))), /* @__PURE__ */ React.createElement(Box, { flexDirection: "column", paddingLeft: 1 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, t("commands.undo.noBackups")), /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.muted }, " "), /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, t("commands.undo.smartModeHint").replace("--smart", ""), /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.info }, "--smart")), /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.muted }, t("commands.undo.smartModeCommand"))), /* @__PURE__ */ React.createElement(Box, { marginTop: 2 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.muted }, t("commands.undo.pressQOrEsc"))));
57
- }
58
- return /* @__PURE__ */ React.createElement(Box, { flexDirection: "column", marginY: 1 }, /* @__PURE__ */ React.createElement(Box, { marginBottom: 1 }, /* @__PURE__ */ React.createElement(Text, { bold: true, color: SEMANTIC_COLORS.brand }, t("commands.undo.title")), /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, " ", "- ", t("commands.undo.selectFile"))), /* @__PURE__ */ React.createElement(Box, { flexDirection: "column" }, files.map((file, index) => {
59
- const isSelected = index === selectedIndex;
60
- const relativePath = getRelativePath(file.filePath);
61
- return /* @__PURE__ */ React.createElement(Box, { key: file.filePath, paddingLeft: 1 }, /* @__PURE__ */ React.createElement(Text, { color: isSelected ? SEMANTIC_COLORS.info : void 0 }, isSelected ? "\u25B6 " : " ", /* @__PURE__ */ React.createElement(
62
- Text,
63
- {
64
- color: isSelected ? SEMANTIC_COLORS.primary : SEMANTIC_COLORS.secondary
65
- },
66
- relativePath
67
- ), /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, " ", "(", t("commands.undo.versions", { count: file.versionCount }), ")")));
68
- })), /* @__PURE__ */ React.createElement(Box, { marginTop: 2 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.muted }, t("commands.undo.navHintsFile"))));
69
- };
70
- const VersionListView = ({ file, versions, selectedIndex, onSelect, onBack }) => {
71
- useInput((input, key) => {
72
- if (key.escape || input === "q") {
73
- onBack();
74
- } else if (key.return) {
75
- if (versions.length > 0 && versions[selectedIndex]) {
76
- onSelect(versions[selectedIndex]);
77
- }
78
- }
79
- });
80
- const relativePath = getRelativePath(file.filePath);
81
- return /* @__PURE__ */ React.createElement(Box, { flexDirection: "column", marginY: 1 }, /* @__PURE__ */ React.createElement(Box, { marginBottom: 1 }, /* @__PURE__ */ React.createElement(Text, { bold: true, color: SEMANTIC_COLORS.brand }, t("commands.undo.selectVersion"))), /* @__PURE__ */ React.createElement(Box, { marginBottom: 1, paddingLeft: 1 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, t("commands.undo.file"), ": "), /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.secondary }, relativePath)), /* @__PURE__ */ React.createElement(Box, { flexDirection: "column" }, versions.map((version, index) => {
82
- const isSelected = index === selectedIndex;
83
- return /* @__PURE__ */ React.createElement(Box, { key: version.version, paddingLeft: 1 }, /* @__PURE__ */ React.createElement(Text, { color: isSelected ? SEMANTIC_COLORS.info : void 0 }, isSelected ? "\u25B6 " : " ", /* @__PURE__ */ React.createElement(
84
- Text,
85
- {
86
- color: isSelected ? SEMANTIC_COLORS.primary : SEMANTIC_COLORS.secondary
87
- },
88
- "v",
89
- version.version
90
- ), /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, ": ", version.operation, " - ", formatTimestamp(version.timestamp))));
91
- })), /* @__PURE__ */ React.createElement(Box, { marginTop: 2 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.muted }, t("commands.undo.navHintsVersion"))));
92
- };
93
- const SuccessView = ({ file, version, onClose }) => {
94
- useInput((input, key) => {
95
- if (key.escape || input === "q" || key.return) {
96
- onClose();
97
- }
98
- });
99
- const relativePath = getRelativePath(file.filePath);
100
- return /* @__PURE__ */ React.createElement(Box, { flexDirection: "column", marginY: 1 }, /* @__PURE__ */ React.createElement(Box, { marginBottom: 1 }, /* @__PURE__ */ React.createElement(Text, { bold: true, color: SEMANTIC_COLORS.success }, "\u2713 ", t("commands.undo.fileRestored"))), /* @__PURE__ */ React.createElement(Box, { flexDirection: "column", paddingLeft: 1 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, t("commands.undo.file"), ": "), /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.secondary }, relativePath)), /* @__PURE__ */ React.createElement(Box, { paddingLeft: 1, marginTop: 1 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, t("commands.undo.restoredTo"), ": ", version.operation, " (", formatTimestamp(version.timestamp), ")")), /* @__PURE__ */ React.createElement(Box, { marginTop: 2 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.muted }, t("commands.undo.pressAnyKey"))));
101
- };
102
44
  const UndoCommand = ({ onClose }) => {
103
- const [view, setView] = useState("file-list");
45
+ const [phase, setPhase] = useState({ type: "file-list" });
104
46
  const [files, setFiles] = useState([]);
105
- const [selectedFileIndex, setSelectedFileIndex] = useState(0);
106
- const [selectedFile, setSelectedFile] = useState(
107
- null
108
- );
109
47
  const [versions, setVersions] = useState([]);
110
- const [selectedVersionIndex, setSelectedVersionIndex] = useState(0);
111
- const [restoredVersion, setRestoredVersion] = useState(
112
- null
113
- );
114
- const [error, setError] = useState(null);
115
- const [isLoading, setIsLoading] = useState(true);
48
+ const [loading, setLoading] = useState(true);
49
+ const [statusOverlay, setStatusOverlay] = useState(null);
116
50
  useEffect(() => {
117
51
  const loadFiles = async () => {
118
52
  try {
119
53
  const backupFiles = await listBackedUpFiles();
120
54
  setFiles(backupFiles);
121
- } catch (err) {
122
- setError(err instanceof Error ? err.message : String(err));
55
+ } catch {
56
+ setFiles([]);
123
57
  } finally {
124
- setIsLoading(false);
58
+ setLoading(false);
125
59
  }
126
60
  };
127
61
  loadFiles();
128
62
  }, []);
129
- useInput(
130
- (input, key) => {
131
- if (view === "file-list" && files.length > 0) {
132
- if (key.upArrow) {
133
- setSelectedFileIndex((prev) => Math.max(0, prev - 1));
134
- } else if (key.downArrow) {
135
- setSelectedFileIndex((prev) => Math.min(files.length - 1, prev + 1));
63
+ useEffect(() => {
64
+ if (phase.type === "version-list") {
65
+ const loadVersions = async () => {
66
+ setLoading(true);
67
+ try {
68
+ const fileVersions = await getBackupVersions(phase.file.filePath);
69
+ setVersions(fileVersions);
70
+ } catch {
71
+ setVersions([]);
72
+ } finally {
73
+ setLoading(false);
136
74
  }
75
+ };
76
+ loadVersions();
77
+ }
78
+ }, [phase]);
79
+ const { tabs, items, title, footerHint, emptyText } = useMemo(() => {
80
+ switch (phase.type) {
81
+ case "file-list": {
82
+ const fileTabs = [
83
+ { id: "files", label: t("commands.undo.tabFiles") }
84
+ ];
85
+ const fileItems = files.map((file) => ({
86
+ id: file.filePath,
87
+ label: getRelativePath(file.filePath),
88
+ description: t("commands.undo.versions", {
89
+ count: file.versionCount
90
+ }),
91
+ data: { file }
92
+ }));
93
+ return {
94
+ tabs: fileTabs,
95
+ items: fileItems,
96
+ title: t("commands.undo.title"),
97
+ footerHint: "\u2191\u2193 Navigate \xB7 Enter Select \xB7 Esc Close",
98
+ emptyText: t("commands.undo.noBackups")
99
+ };
137
100
  }
138
- },
139
- { isActive: view === "file-list" }
140
- );
141
- useInput(
142
- (input, key) => {
143
- if (view === "version-list" && versions.length > 0) {
144
- if (key.upArrow) {
145
- setSelectedVersionIndex((prev) => Math.max(0, prev - 1));
146
- } else if (key.downArrow) {
147
- setSelectedVersionIndex(
148
- (prev) => Math.min(versions.length - 1, prev + 1)
149
- );
150
- }
101
+ case "version-list": {
102
+ const versionTabs = [
103
+ { id: "versions", label: t("commands.undo.tabVersions") }
104
+ ];
105
+ const versionItems = versions.map((version) => ({
106
+ id: String(version.version),
107
+ label: `v${version.version}: ${version.operation}`,
108
+ description: formatTimestamp(version.timestamp),
109
+ data: { version }
110
+ }));
111
+ return {
112
+ tabs: versionTabs,
113
+ items: versionItems,
114
+ title: getRelativePath(phase.file.filePath),
115
+ footerHint: "\u2191\u2193 Navigate \xB7 Enter Restore \xB7 Esc Back",
116
+ emptyText: "No versions found"
117
+ };
151
118
  }
152
- },
153
- { isActive: view === "version-list" }
154
- );
155
- const handleFileSelect = async (file) => {
156
- setSelectedFile(file);
157
- try {
158
- const fileVersions = await getBackupVersions(file.filePath);
159
- setVersions(fileVersions);
160
- setSelectedVersionIndex(0);
161
- setView("version-list");
162
- } catch (err) {
163
- setError(err instanceof Error ? err.message : String(err));
119
+ default:
120
+ return {
121
+ tabs: [],
122
+ items: [],
123
+ title: "",
124
+ footerHint: "",
125
+ emptyText: ""
126
+ };
164
127
  }
165
- };
166
- const handleVersionSelect = async (version) => {
167
- if (!selectedFile) return;
168
- try {
169
- const success = await restoreBackup(
170
- selectedFile.filePath,
171
- version.version
172
- );
173
- if (success) {
174
- setRestoredVersion(version);
175
- setView("success");
176
- } else {
177
- setError(t("commands.undo.restoreFailed"));
178
- }
179
- } catch (err) {
180
- setError(err instanceof Error ? err.message : String(err));
128
+ }, [phase, files, versions]);
129
+ const handleStatusDismiss = useCallback(() => {
130
+ setStatusOverlay(null);
131
+ onClose();
132
+ }, [onClose]);
133
+ const handleBack = useCallback(() => {
134
+ if (statusOverlay && statusOverlay.type !== "loading") {
135
+ handleStatusDismiss();
136
+ return;
181
137
  }
182
- };
183
- const handleBack = () => {
184
- setView("file-list");
185
- setSelectedFile(null);
186
- setVersions([]);
187
- setSelectedVersionIndex(0);
188
- };
189
- if (isLoading) {
190
- return /* @__PURE__ */ React.createElement(Box, { flexDirection: "column", marginY: 1 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, t("commands.undo.loading")));
191
- }
192
- if (error) {
193
- return /* @__PURE__ */ React.createElement(Box, { flexDirection: "column", marginY: 1 }, /* @__PURE__ */ React.createElement(Box, { marginBottom: 1 }, /* @__PURE__ */ React.createElement(Text, { bold: true, color: SEMANTIC_COLORS.error }, t("commands.undo.error"))), /* @__PURE__ */ React.createElement(Box, { paddingLeft: 1 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.dim }, error)), /* @__PURE__ */ React.createElement(Box, { marginTop: 2 }, /* @__PURE__ */ React.createElement(Text, { color: SEMANTIC_COLORS.muted }, t("commands.undo.pressAnyKey"))));
194
- }
195
- switch (view) {
196
- case "file-list":
197
- return /* @__PURE__ */ React.createElement(
198
- FileListView,
199
- {
200
- files,
201
- selectedIndex: selectedFileIndex,
202
- onSelect: handleFileSelect,
203
- onClose
138
+ if (phase.type === "file-list") {
139
+ onClose();
140
+ } else {
141
+ setPhase({ type: "file-list" });
142
+ }
143
+ }, [phase, statusOverlay, onClose, handleStatusDismiss]);
144
+ const handleClose = handleBack;
145
+ const handleTabChange = useCallback(() => {
146
+ }, []);
147
+ const handleSelect = useCallback(
148
+ async (item) => {
149
+ switch (phase.type) {
150
+ case "file-list": {
151
+ const data = item.data;
152
+ setPhase({ type: "version-list", file: data.file });
153
+ break;
204
154
  }
205
- );
206
- case "version-list":
207
- if (!selectedFile) {
208
- handleBack();
209
- return null;
210
- }
211
- return /* @__PURE__ */ React.createElement(
212
- VersionListView,
213
- {
214
- file: selectedFile,
215
- versions,
216
- selectedIndex: selectedVersionIndex,
217
- onSelect: handleVersionSelect,
218
- onBack: handleBack
155
+ case "version-list": {
156
+ const data = item.data;
157
+ setStatusOverlay({
158
+ type: "loading",
159
+ message: "Restoring file..."
160
+ });
161
+ try {
162
+ const success = await restoreBackup(
163
+ phase.file.filePath,
164
+ data.version.version
165
+ );
166
+ if (success) {
167
+ setStatusOverlay({
168
+ type: "success",
169
+ message: `${t("commands.undo.fileRestored")}: v${data.version.version}`
170
+ });
171
+ } else {
172
+ setStatusOverlay({
173
+ type: "error",
174
+ message: t("commands.undo.restoreFailed")
175
+ });
176
+ }
177
+ } catch (err) {
178
+ const msg = err instanceof Error ? err.message : String(err);
179
+ setStatusOverlay({ type: "error", message: msg });
180
+ }
181
+ break;
219
182
  }
220
- );
221
- case "success":
222
- if (!selectedFile || !restoredVersion) {
223
- onClose();
224
- return null;
225
183
  }
226
- return /* @__PURE__ */ React.createElement(
227
- SuccessView,
228
- {
229
- file: selectedFile,
230
- version: restoredVersion,
231
- onClose
232
- }
233
- );
234
- default:
235
- return null;
236
- }
184
+ },
185
+ [phase]
186
+ );
187
+ const currentTab = phase.type === "file-list" ? "files" : "versions";
188
+ return /* @__PURE__ */ React.createElement(
189
+ TabbedListView,
190
+ {
191
+ title,
192
+ tabs,
193
+ activeTab: currentTab,
194
+ onTabChange: handleTabChange,
195
+ items,
196
+ searchEnabled: false,
197
+ onSelect: handleSelect,
198
+ onClose: handleClose,
199
+ onBack: handleBack,
200
+ statusOverlay,
201
+ footerHint,
202
+ isLoading: loading,
203
+ loadingText: t("commands.undo.loading"),
204
+ emptyText,
205
+ statusDismissHint: "Enter Close"
206
+ }
207
+ );
237
208
  };
238
209
  const command = {
239
210
  name: "undo",
@@ -241,6 +212,7 @@ const command = {
241
212
  type: "local-jsx",
242
213
  isEnabled: true,
243
214
  isHidden: false,
215
+ hidePromptInput: true,
244
216
  userFacingName() {
245
217
  return "undo";
246
218
  },
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/commands/undo.tsx"],
4
- "sourcesContent": ["/**\n * Undo Command\n *\n * Interactive command to restore file versions from backups.\n * Requires --smart mode to have backups available.\n */\n\nimport React, { useState, useEffect } from 'react'\nimport { Box, Text, useInput } from 'ink'\nimport type { Command } from '@commands'\nimport { SEMANTIC_COLORS } from '@constants/colors'\nimport { getCwd } from '@utils/state'\nimport {\n listBackedUpFiles,\n getBackupVersions,\n restoreBackup,\n type BackupFileSummary,\n type BackupMetadata,\n} from '../core/backupManager'\nimport { t } from '@i18n'\n\ntype ViewState = 'file-list' | 'version-list' | 'success'\n\ninterface UndoCommandProps {\n onClose: () => void\n}\n\n/**\n * Format a timestamp as a human-readable string\n */\nfunction formatTimestamp(timestamp: number): string {\n const date = new Date(timestamp)\n const now = new Date()\n const diff = now.getTime() - timestamp\n const timeStr = `${date.getHours().toString().padStart(2, '0')}:${date.getMinutes().toString().padStart(2, '0')}`\n\n // Within last hour - show minutes\n if (diff < 60 * 60 * 1000) {\n const minutes = Math.floor(diff / (60 * 1000))\n return minutes <= 1\n ? t('commands.undo.justNow')\n : t('commands.undo.minutesAgo', { count: minutes })\n }\n\n // Within today - show time\n if (\n date.getDate() === now.getDate() &&\n date.getMonth() === now.getMonth() &&\n date.getFullYear() === now.getFullYear()\n ) {\n return `${t('commands.undo.today')} ${timeStr}`\n }\n\n // Within this week - show day and time\n if (diff < 7 * 24 * 60 * 60 * 1000) {\n const weekdayKeys = [\n 'commands.undo.weekday.sun',\n 'commands.undo.weekday.mon',\n 'commands.undo.weekday.tue',\n 'commands.undo.weekday.wed',\n 'commands.undo.weekday.thu',\n 'commands.undo.weekday.fri',\n 'commands.undo.weekday.sat',\n ] as const\n return `${t(weekdayKeys[date.getDay()])} ${timeStr}`\n }\n\n // Otherwise - show date\n return `${date.getMonth() + 1}/${date.getDate()} ${timeStr}`\n}\n\n/**\n * Get relative path from cwd\n */\nfunction getRelativePath(filePath: string): string {\n const cwd = getCwd()\n if (filePath.startsWith(cwd)) {\n const relative = filePath.slice(cwd.length)\n return relative.startsWith('/') ? relative.slice(1) : relative\n }\n return filePath\n}\n\n/**\n * File List View - shows all files with backups\n */\nconst FileListView: React.FC<{\n files: BackupFileSummary[]\n selectedIndex: number\n onSelect: (file: BackupFileSummary) => void\n onClose: () => void\n}> = ({ files, selectedIndex, onSelect, onClose }) => {\n useInput((input, key) => {\n if (key.escape || input === 'q') {\n onClose()\n } else if (key.return) {\n if (files.length > 0 && files[selectedIndex]) {\n onSelect(files[selectedIndex])\n }\n }\n })\n\n if (files.length === 0) {\n return (\n <Box flexDirection=\"column\" marginY={1}>\n <Box marginBottom={1}>\n <Text bold color={SEMANTIC_COLORS.brand}>\n {t('commands.undo.title')}\n </Text>\n </Box>\n\n <Box flexDirection=\"column\" paddingLeft={1}>\n <Text color={SEMANTIC_COLORS.dim}>\n {t('commands.undo.noBackups')}\n </Text>\n <Text color={SEMANTIC_COLORS.muted}> </Text>\n <Text color={SEMANTIC_COLORS.dim}>\n {t('commands.undo.smartModeHint').replace('--smart', '')}\n <Text color={SEMANTIC_COLORS.info}>--smart</Text>\n </Text>\n <Text color={SEMANTIC_COLORS.muted}>\n {t('commands.undo.smartModeCommand')}\n </Text>\n </Box>\n\n <Box marginTop={2}>\n <Text color={SEMANTIC_COLORS.muted}>\n {t('commands.undo.pressQOrEsc')}\n </Text>\n </Box>\n </Box>\n )\n }\n\n return (\n <Box flexDirection=\"column\" marginY={1}>\n <Box marginBottom={1}>\n <Text bold color={SEMANTIC_COLORS.brand}>\n {t('commands.undo.title')}\n </Text>\n <Text color={SEMANTIC_COLORS.dim}>\n {' '}\n - {t('commands.undo.selectFile')}\n </Text>\n </Box>\n\n <Box flexDirection=\"column\">\n {files.map((file, index) => {\n const isSelected = index === selectedIndex\n const relativePath = getRelativePath(file.filePath)\n\n return (\n <Box key={file.filePath} paddingLeft={1}>\n <Text color={isSelected ? SEMANTIC_COLORS.info : undefined}>\n {isSelected ? '\u25B6 ' : ' '}\n <Text\n color={\n isSelected\n ? SEMANTIC_COLORS.primary\n : SEMANTIC_COLORS.secondary\n }\n >\n {relativePath}\n </Text>\n <Text color={SEMANTIC_COLORS.dim}>\n {' '}\n ({t('commands.undo.versions', { count: file.versionCount })})\n </Text>\n </Text>\n </Box>\n )\n })}\n </Box>\n\n <Box marginTop={2}>\n <Text color={SEMANTIC_COLORS.muted}>\n {t('commands.undo.navHintsFile')}\n </Text>\n </Box>\n </Box>\n )\n}\n\n/**\n * Version List View - shows all versions for a selected file\n */\nconst VersionListView: React.FC<{\n file: BackupFileSummary\n versions: BackupMetadata[]\n selectedIndex: number\n onSelect: (version: BackupMetadata) => void\n onBack: () => void\n}> = ({ file, versions, selectedIndex, onSelect, onBack }) => {\n useInput((input, key) => {\n if (key.escape || input === 'q') {\n onBack()\n } else if (key.return) {\n if (versions.length > 0 && versions[selectedIndex]) {\n onSelect(versions[selectedIndex])\n }\n }\n })\n\n const relativePath = getRelativePath(file.filePath)\n\n return (\n <Box flexDirection=\"column\" marginY={1}>\n <Box marginBottom={1}>\n <Text bold color={SEMANTIC_COLORS.brand}>\n {t('commands.undo.selectVersion')}\n </Text>\n </Box>\n\n <Box marginBottom={1} paddingLeft={1}>\n <Text color={SEMANTIC_COLORS.dim}>{t('commands.undo.file')}: </Text>\n <Text color={SEMANTIC_COLORS.secondary}>{relativePath}</Text>\n </Box>\n\n <Box flexDirection=\"column\">\n {versions.map((version, index) => {\n const isSelected = index === selectedIndex\n\n return (\n <Box key={version.version} paddingLeft={1}>\n <Text color={isSelected ? SEMANTIC_COLORS.info : undefined}>\n {isSelected ? '\u25B6 ' : ' '}\n <Text\n color={\n isSelected\n ? SEMANTIC_COLORS.primary\n : SEMANTIC_COLORS.secondary\n }\n >\n v{version.version}\n </Text>\n <Text color={SEMANTIC_COLORS.dim}>\n : {version.operation} - {formatTimestamp(version.timestamp)}\n </Text>\n </Text>\n </Box>\n )\n })}\n </Box>\n\n <Box marginTop={2}>\n <Text color={SEMANTIC_COLORS.muted}>\n {t('commands.undo.navHintsVersion')}\n </Text>\n </Box>\n </Box>\n )\n}\n\n/**\n * Success View - shows restoration confirmation\n */\nconst SuccessView: React.FC<{\n file: BackupFileSummary\n version: BackupMetadata\n onClose: () => void\n}> = ({ file, version, onClose }) => {\n useInput((input, key) => {\n if (key.escape || input === 'q' || key.return) {\n onClose()\n }\n })\n\n const relativePath = getRelativePath(file.filePath)\n\n return (\n <Box flexDirection=\"column\" marginY={1}>\n <Box marginBottom={1}>\n <Text bold color={SEMANTIC_COLORS.success}>\n \u2713 {t('commands.undo.fileRestored')}\n </Text>\n </Box>\n\n <Box flexDirection=\"column\" paddingLeft={1}>\n <Text color={SEMANTIC_COLORS.dim}>{t('commands.undo.file')}: </Text>\n <Text color={SEMANTIC_COLORS.secondary}>{relativePath}</Text>\n </Box>\n\n <Box paddingLeft={1} marginTop={1}>\n <Text color={SEMANTIC_COLORS.dim}>\n {t('commands.undo.restoredTo')}: {version.operation} (\n {formatTimestamp(version.timestamp)})\n </Text>\n </Box>\n\n <Box marginTop={2}>\n <Text color={SEMANTIC_COLORS.muted}>\n {t('commands.undo.pressAnyKey')}\n </Text>\n </Box>\n </Box>\n )\n}\n\n/**\n * Main Undo Command Component\n */\nconst UndoCommand: React.FC<UndoCommandProps> = ({ onClose }) => {\n const [view, setView] = useState<ViewState>('file-list')\n const [files, setFiles] = useState<BackupFileSummary[]>([])\n const [selectedFileIndex, setSelectedFileIndex] = useState(0)\n const [selectedFile, setSelectedFile] = useState<BackupFileSummary | null>(\n null,\n )\n const [versions, setVersions] = useState<BackupMetadata[]>([])\n const [selectedVersionIndex, setSelectedVersionIndex] = useState(0)\n const [restoredVersion, setRestoredVersion] = useState<BackupMetadata | null>(\n null,\n )\n const [error, setError] = useState<string | null>(null)\n const [isLoading, setIsLoading] = useState(true)\n\n // Load files with backups on mount\n useEffect(() => {\n const loadFiles = async () => {\n try {\n const backupFiles = await listBackedUpFiles()\n // Already sorted by most recent in listBackedUpFiles\n setFiles(backupFiles)\n } catch (err) {\n setError(err instanceof Error ? err.message : String(err))\n } finally {\n setIsLoading(false)\n }\n }\n loadFiles()\n }, [])\n\n // Handle keyboard navigation for file list\n useInput(\n (input, key) => {\n if (view === 'file-list' && files.length > 0) {\n if (key.upArrow) {\n setSelectedFileIndex(prev => Math.max(0, prev - 1))\n } else if (key.downArrow) {\n setSelectedFileIndex(prev => Math.min(files.length - 1, prev + 1))\n }\n }\n },\n { isActive: view === 'file-list' },\n )\n\n // Handle keyboard navigation for version list\n useInput(\n (input, key) => {\n if (view === 'version-list' && versions.length > 0) {\n if (key.upArrow) {\n setSelectedVersionIndex(prev => Math.max(0, prev - 1))\n } else if (key.downArrow) {\n setSelectedVersionIndex(prev =>\n Math.min(versions.length - 1, prev + 1),\n )\n }\n }\n },\n { isActive: view === 'version-list' },\n )\n\n // Handle file selection\n const handleFileSelect = async (file: BackupFileSummary) => {\n setSelectedFile(file)\n try {\n const fileVersions = await getBackupVersions(file.filePath)\n // Already sorted by newest first in getBackupVersions\n setVersions(fileVersions)\n setSelectedVersionIndex(0)\n setView('version-list')\n } catch (err) {\n setError(err instanceof Error ? err.message : String(err))\n }\n }\n\n // Handle version selection and restore\n const handleVersionSelect = async (version: BackupMetadata) => {\n if (!selectedFile) return\n\n try {\n const success = await restoreBackup(\n selectedFile.filePath,\n version.version,\n )\n if (success) {\n setRestoredVersion(version)\n setView('success')\n } else {\n setError(t('commands.undo.restoreFailed'))\n }\n } catch (err) {\n setError(err instanceof Error ? err.message : String(err))\n }\n }\n\n // Handle back navigation\n const handleBack = () => {\n setView('file-list')\n setSelectedFile(null)\n setVersions([])\n setSelectedVersionIndex(0)\n }\n\n // Loading state\n if (isLoading) {\n return (\n <Box flexDirection=\"column\" marginY={1}>\n <Text color={SEMANTIC_COLORS.dim}>{t('commands.undo.loading')}</Text>\n </Box>\n )\n }\n\n // Error display\n if (error) {\n return (\n <Box flexDirection=\"column\" marginY={1}>\n <Box marginBottom={1}>\n <Text bold color={SEMANTIC_COLORS.error}>\n {t('commands.undo.error')}\n </Text>\n </Box>\n <Box paddingLeft={1}>\n <Text color={SEMANTIC_COLORS.dim}>{error}</Text>\n </Box>\n <Box marginTop={2}>\n <Text color={SEMANTIC_COLORS.muted}>\n {t('commands.undo.pressAnyKey')}\n </Text>\n </Box>\n </Box>\n )\n }\n\n // Render current view\n switch (view) {\n case 'file-list':\n return (\n <FileListView\n files={files}\n selectedIndex={selectedFileIndex}\n onSelect={handleFileSelect}\n onClose={onClose}\n />\n )\n\n case 'version-list':\n if (!selectedFile) {\n handleBack()\n return null\n }\n return (\n <VersionListView\n file={selectedFile}\n versions={versions}\n selectedIndex={selectedVersionIndex}\n onSelect={handleVersionSelect}\n onBack={handleBack}\n />\n )\n\n case 'success':\n if (!selectedFile || !restoredVersion) {\n onClose()\n return null\n }\n return (\n <SuccessView\n file={selectedFile}\n version={restoredVersion}\n onClose={onClose}\n />\n )\n\n default:\n return null\n }\n}\n\n/**\n * Undo Command Export\n */\nconst command: Command = {\n name: 'undo',\n description: t('commands.undo.description'),\n type: 'local-jsx' as const,\n isEnabled: true,\n isHidden: false,\n\n userFacingName() {\n return 'undo'\n },\n\n async call(onDone: (result?: string) => void) {\n return <UndoCommand onClose={onDone} />\n },\n}\n\nexport default command\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["/**\n * Undo Command\n *\n * Interactive command to restore file versions from backups.\n * Uses TabbedListView with a phase state machine for consistent UI.\n */\n\nimport React, { useState, useEffect, useCallback, useMemo } from 'react'\nimport type { Command } from '@commands'\nimport { getCwd } from '@utils/state'\nimport {\n listBackedUpFiles,\n getBackupVersions,\n restoreBackup,\n type BackupFileSummary,\n type BackupMetadata,\n} from '../core/backupManager'\nimport { TabbedListView } from '@components/TabbedListView/TabbedListView'\nimport type {\n ListItem,\n TabDefinition,\n StatusOverlay,\n} from '@components/TabbedListView/types'\nimport { t } from '@i18n'\n\n// =============================================================================\n// Helpers\n// =============================================================================\n\nfunction formatTimestamp(timestamp: number): string {\n const date = new Date(timestamp)\n const now = new Date()\n const diff = now.getTime() - timestamp\n const timeStr = `${date.getHours().toString().padStart(2, '0')}:${date.getMinutes().toString().padStart(2, '0')}`\n\n if (diff < 60 * 60 * 1000) {\n const minutes = Math.floor(diff / (60 * 1000))\n return minutes <= 1\n ? t('commands.undo.justNow')\n : t('commands.undo.minutesAgo', { count: minutes })\n }\n\n if (\n date.getDate() === now.getDate() &&\n date.getMonth() === now.getMonth() &&\n date.getFullYear() === now.getFullYear()\n ) {\n return `${t('commands.undo.today')} ${timeStr}`\n }\n\n if (diff < 7 * 24 * 60 * 60 * 1000) {\n const weekdayKeys = [\n 'commands.undo.weekday.sun',\n 'commands.undo.weekday.mon',\n 'commands.undo.weekday.tue',\n 'commands.undo.weekday.wed',\n 'commands.undo.weekday.thu',\n 'commands.undo.weekday.fri',\n 'commands.undo.weekday.sat',\n ] as const\n return `${t(weekdayKeys[date.getDay()])} ${timeStr}`\n }\n\n return `${date.getMonth() + 1}/${date.getDate()} ${timeStr}`\n}\n\nfunction getRelativePath(filePath: string): string {\n const cwd = getCwd()\n if (filePath.startsWith(cwd)) {\n const relative = filePath.slice(cwd.length)\n return relative.startsWith('/') ? relative.slice(1) : relative\n }\n return filePath\n}\n\n// =============================================================================\n// Types\n// =============================================================================\n\ntype UndoPhase =\n | { type: 'file-list' }\n | { type: 'version-list'; file: BackupFileSummary }\n\n// =============================================================================\n// Main Component\n// =============================================================================\n\nconst UndoCommand: React.FC<{ onClose: () => void }> = ({ onClose }) => {\n const [phase, setPhase] = useState<UndoPhase>({ type: 'file-list' })\n const [files, setFiles] = useState<BackupFileSummary[]>([])\n const [versions, setVersions] = useState<BackupMetadata[]>([])\n const [loading, setLoading] = useState(true)\n const [statusOverlay, setStatusOverlay] = useState<StatusOverlay | null>(null)\n\n // Load files on mount\n useEffect(() => {\n const loadFiles = async () => {\n try {\n const backupFiles = await listBackedUpFiles()\n setFiles(backupFiles)\n } catch {\n setFiles([])\n } finally {\n setLoading(false)\n }\n }\n loadFiles()\n }, [])\n\n // Load versions when entering version-list phase\n useEffect(() => {\n if (phase.type === 'version-list') {\n const loadVersions = async () => {\n setLoading(true)\n try {\n const fileVersions = await getBackupVersions(phase.file.filePath)\n setVersions(fileVersions)\n } catch {\n setVersions([])\n } finally {\n setLoading(false)\n }\n }\n loadVersions()\n }\n }, [phase])\n\n // Build tabs, items, title based on phase\n const { tabs, items, title, footerHint, emptyText } = useMemo(() => {\n switch (phase.type) {\n case 'file-list': {\n const fileTabs: TabDefinition[] = [\n { id: 'files', label: t('commands.undo.tabFiles') },\n ]\n\n const fileItems: ListItem[] = files.map(file => ({\n id: file.filePath,\n label: getRelativePath(file.filePath),\n description: t('commands.undo.versions', {\n count: file.versionCount,\n }),\n data: { file },\n }))\n\n return {\n tabs: fileTabs,\n items: fileItems,\n title: t('commands.undo.title'),\n footerHint: '\u2191\u2193 Navigate \u00B7 Enter Select \u00B7 Esc Close',\n emptyText: t('commands.undo.noBackups'),\n }\n }\n\n case 'version-list': {\n const versionTabs: TabDefinition[] = [\n { id: 'versions', label: t('commands.undo.tabVersions') },\n ]\n\n const versionItems: ListItem[] = versions.map(version => ({\n id: String(version.version),\n label: `v${version.version}: ${version.operation}`,\n description: formatTimestamp(version.timestamp),\n data: { version },\n }))\n\n return {\n tabs: versionTabs,\n items: versionItems,\n title: getRelativePath(phase.file.filePath),\n footerHint: '\u2191\u2193 Navigate \u00B7 Enter Restore \u00B7 Esc Back',\n emptyText: 'No versions found',\n }\n }\n default:\n return {\n tabs: [],\n items: [],\n title: '',\n footerHint: '',\n emptyText: '',\n }\n }\n }, [phase, files, versions])\n\n // Handle status overlay dismiss\n const handleStatusDismiss = useCallback(() => {\n setStatusOverlay(null)\n onClose()\n }, [onClose])\n\n // Handle back / close\n const handleBack = useCallback(() => {\n if (statusOverlay && statusOverlay.type !== 'loading') {\n handleStatusDismiss()\n return\n }\n if (phase.type === 'file-list') {\n onClose()\n } else {\n setPhase({ type: 'file-list' })\n }\n }, [phase, statusOverlay, onClose, handleStatusDismiss])\n\n const handleClose = handleBack\n\n // Handle tab change (no-op, single tab per phase)\n const handleTabChange = useCallback(() => {}, [])\n\n // Handle item selection\n const handleSelect = useCallback(\n async (item: ListItem) => {\n switch (phase.type) {\n case 'file-list': {\n const data = item.data as { file: BackupFileSummary }\n setPhase({ type: 'version-list', file: data.file })\n break\n }\n\n case 'version-list': {\n const data = item.data as { version: BackupMetadata }\n setStatusOverlay({\n type: 'loading',\n message: 'Restoring file...',\n })\n\n try {\n const success = await restoreBackup(\n phase.file.filePath,\n data.version.version,\n )\n if (success) {\n setStatusOverlay({\n type: 'success',\n message: `${t('commands.undo.fileRestored')}: v${data.version.version}`,\n })\n } else {\n setStatusOverlay({\n type: 'error',\n message: t('commands.undo.restoreFailed'),\n })\n }\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err)\n setStatusOverlay({ type: 'error', message: msg })\n }\n break\n }\n }\n },\n [phase],\n )\n\n const currentTab = phase.type === 'file-list' ? 'files' : 'versions'\n\n return (\n <TabbedListView\n title={title}\n tabs={tabs}\n activeTab={currentTab}\n onTabChange={handleTabChange}\n items={items}\n searchEnabled={false}\n onSelect={handleSelect}\n onClose={handleClose}\n onBack={handleBack}\n statusOverlay={statusOverlay}\n footerHint={footerHint}\n isLoading={loading}\n loadingText={t('commands.undo.loading')}\n emptyText={emptyText}\n statusDismissHint=\"Enter Close\"\n />\n )\n}\n\n// =============================================================================\n// Command Export\n// =============================================================================\n\nconst command: Command = {\n name: 'undo',\n description: t('commands.undo.description'),\n type: 'local-jsx' as const,\n isEnabled: true,\n isHidden: false,\n hidePromptInput: true,\n\n userFacingName() {\n return 'undo'\n },\n\n async call(onDone: (result?: string) => void) {\n return <UndoCommand onClose={onDone} />\n },\n}\n\nexport default command\n"],
5
+ "mappings": "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",
6
6
  "names": []
7
7
  }
@@ -0,0 +1,22 @@
1
+ import { getGlobalConfig, saveGlobalConfig } from "../utils/config.js";
2
+ const vim = {
3
+ name: "vim",
4
+ description: "Toggle vim keybinding mode",
5
+ isEnabled: true,
6
+ isHidden: false,
7
+ type: "local",
8
+ userFacingName() {
9
+ return "vim";
10
+ },
11
+ async call() {
12
+ const config = getGlobalConfig();
13
+ const newValue = !config.viMode;
14
+ saveGlobalConfig({ ...config, viMode: newValue });
15
+ return newValue ? "Vim mode enabled. Use vim keybindings in the input prompt." : "Vim mode disabled. Standard keybindings restored.";
16
+ }
17
+ };
18
+ var vim_default = vim;
19
+ export {
20
+ vim_default as default
21
+ };
22
+ //# sourceMappingURL=vim.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../src/commands/vim.ts"],
4
+ "sourcesContent": ["/**\n * /vim command\n *\n * Toggle vim keybinding mode on/off.\n */\n\nimport { getGlobalConfig, saveGlobalConfig } from '@utils/config'\nimport type { Command } from '../commands'\n\nconst vim: Command = {\n name: 'vim',\n description: 'Toggle vim keybinding mode',\n isEnabled: true,\n isHidden: false,\n type: 'local',\n userFacingName() {\n return 'vim'\n },\n async call() {\n const config = getGlobalConfig()\n const newValue = !config.viMode\n saveGlobalConfig({ ...config, viMode: newValue })\n\n return newValue\n ? 'Vim mode enabled. Use vim keybindings in the input prompt.'\n : 'Vim mode disabled. Standard keybindings restored.'\n },\n}\n\nexport default vim\n"],
5
+ "mappings": "AAMA,SAAS,iBAAiB,wBAAwB;AAGlD,MAAM,MAAe;AAAA,EACnB,MAAM;AAAA,EACN,aAAa;AAAA,EACb,WAAW;AAAA,EACX,UAAU;AAAA,EACV,MAAM;AAAA,EACN,iBAAiB;AACf,WAAO;AAAA,EACT;AAAA,EACA,MAAM,OAAO;AACX,UAAM,SAAS,gBAAgB;AAC/B,UAAM,WAAW,CAAC,OAAO;AACzB,qBAAiB,EAAE,GAAG,QAAQ,QAAQ,SAAS,CAAC;AAEhD,WAAO,WACH,+DACA;AAAA,EACN;AACF;AAEA,IAAO,cAAQ;",
6
+ "names": []
7
+ }
package/dist/commands.js CHANGED
@@ -23,6 +23,10 @@ import undo from "./commands/undo.js";
23
23
  import language from "./commands/language.js";
24
24
  import { quit } from "./commands/quit.js";
25
25
  import stats from "./commands/stats.js";
26
+ import effort from "./commands/effort.js";
27
+ import memory from "./commands/memory.js";
28
+ import outputStyle from "./commands/outputStyle.js";
29
+ import review from "./commands/review.js";
26
30
  import doctor from "./commands/doctor.js";
27
31
  import bug from "./commands/bug.js";
28
32
  import tasks from "./commands/tasks.js";
@@ -43,17 +47,21 @@ const COMMANDS = memoize(() => [
43
47
  context,
44
48
  cost,
45
49
  doctor,
50
+ effort,
46
51
  exportCmd,
47
52
  help,
48
53
  init,
49
54
  language,
50
55
  mcp,
56
+ memory,
51
57
  model,
52
58
  newCmd,
59
+ outputStyle,
53
60
  permissions,
54
61
  plugin,
55
62
  quit,
56
63
  resume,
64
+ review,
57
65
  sandbox,
58
66
  setup,
59
67
  stats,
@@ -63,6 +71,9 @@ const COMMANDS = memoize(() => [
63
71
  undo,
64
72
  ...HIDDEN_COMMANDS
65
73
  ]);
74
+ function getBuiltInCommands() {
75
+ return [...COMMANDS()].sort((a, b) => a.userFacingName().localeCompare(b.userFacingName())).filter((_) => _.isEnabled);
76
+ }
66
77
  const getCommands = memoize(async () => {
67
78
  const [mcpCommands, customCommands, pluginCommands] = await Promise.all([
68
79
  getMCPCommands(),
@@ -109,6 +120,7 @@ function getCommand(commandName, commands) {
109
120
  return command;
110
121
  }
111
122
  export {
123
+ getBuiltInCommands,
112
124
  getCommand,
113
125
  getCommands,
114
126
  hasCommand
@@ -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 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 /** If true, the command UI will show below PromptInput instead of replacing it */\n showBelowPrompt?: boolean\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 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 exportCmd,\n help,\n init,\n language,\n mcp,\n model,\n newCmd,\n permissions,\n plugin,\n quit,\n resume,\n sandbox,\n setup,\n stats,\n status,\n tasks,\n todos,\n undo,\n ...HIDDEN_COMMANDS,\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": "AACA,OAAO,WAAW;AAClB,OAAO,aAAa;AACpB,OAAO,YAAY;AACnB,OAAO,aAAa;AACpB,OAAO,UAAU;AACjB,OAAO,aAAa;AACpB,OAAO,eAAe;AACtB,OAAO,UAAU;AACjB,OAAO,UAAU;AACjB,OAAO,SAAS;AAChB,OAAO,WAAW;AAClB,OAAO,iBAAiB;AACxB,OAAO,qBAAqB;AAC5B,OAAO,aAAa;AACpB,OAAO,WAAW;AAClB,OAAO,YAAY;AACnB,OAAO,mBAAmB;AAE1B,OAAO,YAAY;AACnB,OAAO,YAAY;AACnB,OAAO,YAAY;AACnB,OAAO,YAAY;AACnB,OAAO,UAAU;AACjB,OAAO,cAAc;AACrB,SAAS,YAAY;AACrB,OAAO,WAAW;AAElB,OAAO,YAAY;AACnB,OAAO,SAAS;AAChB,OAAO,WAAW;AAClB,OAAO,WAAW;AAClB,SAAS,sBAAsB;AAC/B;AAAA,EACE;AAAA,EACA;AAAA,OACK;AAEP,SAAS,eAAe;AAuDxB,MAAM,kBAAkB,CAAC,SAAS,iBAAiB,aAAa;AAIhE,MAAM,WAAW,QAAQ,MAAiB;AAAA,EACxC;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA,GAAG;AACL,CAAC;AAEM,MAAM,cAAc,QAAQ,YAAgC;AACjE,QAAM,CAAC,aAAa,gBAAgB,cAAc,IAAI,MAAM,QAAQ,IAAI;AAAA,IACtE,eAAe;AAAA,IACf,mBAAmB;AAAA,IACnB,mBAAmB;AAAA,EACrB,CAAC;AAGD,QAAM,kBAAkB,SAAS;AAGjC,QAAM,gBAAgB,CAAC,GAAG,eAAe,EAAE;AAAA,IAAK,CAAC,GAAG,MAClD,EAAE,eAAe,EAAE,cAAc,EAAE,eAAe,CAAC;AAAA,EACrD;AAGA,QAAM,YAAY,CAAC,GAAG,WAAW,EAAE;AAAA,IAAK,CAAC,GAAG,MAC1C,EAAE,eAAe,EAAE,cAAc,EAAE,eAAe,CAAC;AAAA,EACrD;AAGA,QAAM,eAAe,CAAC,GAAG,cAAc,EAAE;AAAA,IAAK,CAAC,GAAG,MAChD,EAAE,eAAe,EAAE,cAAc,EAAE,eAAe,CAAC;AAAA,EACrD;AAGA,QAAM,eAAe,CAAC,GAAG,cAAc,EAAE;AAAA,IAAK,CAAC,GAAG,MAChD,EAAE,eAAe,EAAE,cAAc,EAAE,eAAe,CAAC;AAAA,EACrD;AAQA,SAAO;AAAA,IACL,GAAG;AAAA,IACH,GAAG;AAAA,IACH,GAAG;AAAA,IACH,GAAG;AAAA,EACL,EAAE,OAAO,OAAK,EAAE,SAAS;AAC3B,CAAC;AAEM,SAAS,WAAW,aAAqB,UAA8B;AAC5E,SAAO,SAAS;AAAA,IACd,OAAK,EAAE,eAAe,MAAM,eAAe,EAAE,SAAS,SAAS,WAAW;AAAA,EAC5E;AACF;AAEO,SAAS,WAAW,aAAqB,UAA8B;AAC5E,QAAM,UAAU,SAAS;AAAA,IACvB,OAAK,EAAE,eAAe,MAAM,eAAe,EAAE,SAAS,SAAS,WAAW;AAAA,EAC5E;AACA,MAAI,CAAC,SAAS;AACZ,UAAM;AAAA,MACJ,WAAW,WAAW,mCAAmC,SACtD,IAAI,OAAK;AACR,cAAM,OAAO,EAAE,eAAe;AAC9B,eAAO,EAAE,UAAU,GAAG,IAAI,cAAc,EAAE,QAAQ,KAAK,IAAI,CAAC,MAAM;AAAA,MACpE,CAAC,EACA,KAAK,IAAI,CAAC;AAAA,IACf;AAAA,EACF;AAEA,SAAO;AACT;",
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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",
6
6
  "names": []
7
7
  }