@gguf/coder 0.2.9 → 0.3.1

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 (439) hide show
  1. package/.editorconfig +16 -0
  2. package/.env.example +63 -0
  3. package/.gitattributes +1 -0
  4. package/.semgrepignore +19 -0
  5. package/coder-dummy-file.ts +52 -0
  6. package/coder.config.example.json +59 -0
  7. package/coder.config.json +13 -0
  8. package/color_picker.html +36 -0
  9. package/dist/tools/execute-bash.js +3 -3
  10. package/dist/tools/execute-bash.js.map +1 -1
  11. package/dist/tools/fetch-url.js +3 -3
  12. package/dist/tools/fetch-url.js.map +1 -1
  13. package/dist/tools/find-files.d.ts.map +1 -1
  14. package/dist/tools/find-files.js +1 -1
  15. package/dist/tools/find-files.js.map +1 -1
  16. package/dist/tools/lsp-get-diagnostics.js +1 -1
  17. package/dist/tools/lsp-get-diagnostics.js.map +1 -1
  18. package/dist/tools/read-file.d.ts.map +1 -1
  19. package/dist/tools/read-file.js +6 -6
  20. package/dist/tools/read-file.js.map +1 -1
  21. package/dist/tools/search-file-contents.d.ts.map +1 -1
  22. package/dist/tools/search-file-contents.js +1 -1
  23. package/dist/tools/search-file-contents.js.map +1 -1
  24. package/dist/tools/string-replace.js +11 -11
  25. package/dist/tools/string-replace.js.map +1 -1
  26. package/dist/tools/web-search.d.ts.map +1 -1
  27. package/dist/tools/web-search.js +3 -3
  28. package/dist/tools/web-search.js.map +1 -1
  29. package/dist/tools/write-file.js +4 -4
  30. package/dist/tools/write-file.js.map +1 -1
  31. package/dist/utils/tool-result-display.d.ts.map +1 -1
  32. package/dist/utils/tool-result-display.js +3 -3
  33. package/dist/utils/tool-result-display.js.map +1 -1
  34. package/package.json +2 -14
  35. package/scripts/extract-changelog.js +73 -0
  36. package/scripts/fetch-models.js +143 -0
  37. package/scripts/test.sh +40 -0
  38. package/scripts/update-homebrew-formula.sh +125 -0
  39. package/scripts/update-nix-version.sh +157 -0
  40. package/source/ai-sdk-client/AISDKClient.spec.ts +117 -0
  41. package/source/ai-sdk-client/AISDKClient.ts +155 -0
  42. package/source/ai-sdk-client/chat/chat-handler.spec.ts +121 -0
  43. package/source/ai-sdk-client/chat/chat-handler.ts +276 -0
  44. package/source/ai-sdk-client/chat/streaming-handler.spec.ts +173 -0
  45. package/source/ai-sdk-client/chat/streaming-handler.ts +110 -0
  46. package/source/ai-sdk-client/chat/tool-processor.spec.ts +92 -0
  47. package/source/ai-sdk-client/chat/tool-processor.ts +70 -0
  48. package/source/ai-sdk-client/converters/message-converter.spec.ts +220 -0
  49. package/source/ai-sdk-client/converters/message-converter.ts +113 -0
  50. package/source/ai-sdk-client/converters/tool-converter.spec.ts +90 -0
  51. package/source/ai-sdk-client/converters/tool-converter.ts +46 -0
  52. package/source/ai-sdk-client/error-handling/error-extractor.spec.ts +55 -0
  53. package/source/ai-sdk-client/error-handling/error-extractor.ts +15 -0
  54. package/source/ai-sdk-client/error-handling/error-parser.spec.ts +169 -0
  55. package/source/ai-sdk-client/error-handling/error-parser.ts +161 -0
  56. package/source/ai-sdk-client/index.ts +7 -0
  57. package/source/ai-sdk-client/providers/provider-factory.spec.ts +71 -0
  58. package/source/ai-sdk-client/providers/provider-factory.ts +41 -0
  59. package/source/ai-sdk-client/types.ts +9 -0
  60. package/source/ai-sdk-client-empty-message.spec.ts +141 -0
  61. package/source/ai-sdk-client-error-handling.spec.ts +186 -0
  62. package/source/ai-sdk-client-maxretries.spec.ts +114 -0
  63. package/source/ai-sdk-client-preparestep.spec.ts +279 -0
  64. package/source/app/App.spec.tsx +32 -0
  65. package/source/app/App.tsx +480 -0
  66. package/source/app/components/AppContainer.spec.tsx +96 -0
  67. package/source/app/components/AppContainer.tsx +56 -0
  68. package/source/app/components/ChatInterface.spec.tsx +163 -0
  69. package/source/app/components/ChatInterface.tsx +144 -0
  70. package/source/app/components/ModalSelectors.spec.tsx +141 -0
  71. package/source/app/components/ModalSelectors.tsx +135 -0
  72. package/source/app/helpers.spec.ts +97 -0
  73. package/source/app/helpers.ts +63 -0
  74. package/source/app/index.ts +4 -0
  75. package/source/app/types.ts +39 -0
  76. package/source/app/utils/appUtils.ts +294 -0
  77. package/source/app/utils/conversationState.ts +310 -0
  78. package/source/app.spec.tsx +244 -0
  79. package/source/cli.spec.ts +73 -0
  80. package/source/cli.tsx +51 -0
  81. package/source/client-factory.spec.ts +48 -0
  82. package/source/client-factory.ts +178 -0
  83. package/source/command-parser.spec.ts +127 -0
  84. package/source/command-parser.ts +36 -0
  85. package/source/commands/checkpoint.spec.tsx +277 -0
  86. package/source/commands/checkpoint.tsx +366 -0
  87. package/source/commands/clear.tsx +22 -0
  88. package/source/commands/custom-commands.tsx +121 -0
  89. package/source/commands/exit.ts +21 -0
  90. package/source/commands/export.spec.tsx +131 -0
  91. package/source/commands/export.tsx +79 -0
  92. package/source/commands/help.tsx +120 -0
  93. package/source/commands/index.ts +17 -0
  94. package/source/commands/init.tsx +339 -0
  95. package/source/commands/lsp-command.spec.tsx +281 -0
  96. package/source/commands/lsp.tsx +120 -0
  97. package/source/commands/mcp-command.spec.tsx +313 -0
  98. package/source/commands/mcp.tsx +162 -0
  99. package/source/commands/model-database.spec.tsx +758 -0
  100. package/source/commands/model-database.tsx +418 -0
  101. package/source/commands/model.ts +12 -0
  102. package/source/commands/provider.ts +12 -0
  103. package/source/commands/setup-config.tsx +16 -0
  104. package/source/commands/simple-commands.spec.tsx +175 -0
  105. package/source/commands/status.ts +12 -0
  106. package/source/commands/theme.ts +12 -0
  107. package/source/commands/update.spec.tsx +261 -0
  108. package/source/commands/update.tsx +201 -0
  109. package/source/commands/usage.spec.tsx +495 -0
  110. package/source/commands/usage.tsx +100 -0
  111. package/source/commands.spec.ts +436 -0
  112. package/source/commands.ts +83 -0
  113. package/source/components/assistant-message.spec.tsx +796 -0
  114. package/source/components/assistant-message.tsx +34 -0
  115. package/source/components/bash-execution-indicator.tsx +21 -0
  116. package/source/components/cancelling-indicator.tsx +16 -0
  117. package/source/components/chat-queue.spec.tsx +83 -0
  118. package/source/components/chat-queue.tsx +36 -0
  119. package/source/components/checkpoint-display.spec.tsx +219 -0
  120. package/source/components/checkpoint-display.tsx +126 -0
  121. package/source/components/checkpoint-selector.spec.tsx +173 -0
  122. package/source/components/checkpoint-selector.tsx +173 -0
  123. package/source/components/development-mode-indicator.spec.tsx +268 -0
  124. package/source/components/development-mode-indicator.tsx +38 -0
  125. package/source/components/message-box.spec.tsx +427 -0
  126. package/source/components/message-box.tsx +87 -0
  127. package/source/components/model-selector.tsx +132 -0
  128. package/source/components/provider-selector.tsx +75 -0
  129. package/source/components/random-spinner.tsx +19 -0
  130. package/source/components/security-disclaimer.tsx +73 -0
  131. package/source/components/status-connection-display.spec.tsx +133 -0
  132. package/source/components/status.tsx +267 -0
  133. package/source/components/theme-selector.tsx +126 -0
  134. package/source/components/tool-confirmation.tsx +190 -0
  135. package/source/components/tool-execution-indicator.tsx +33 -0
  136. package/source/components/tool-message.tsx +85 -0
  137. package/source/components/ui/titled-box.spec.tsx +207 -0
  138. package/source/components/ui/titled-box.tsx +57 -0
  139. package/source/components/usage/progress-bar.spec.tsx +398 -0
  140. package/source/components/usage/progress-bar.tsx +30 -0
  141. package/source/components/usage/usage-display.spec.tsx +780 -0
  142. package/source/components/usage/usage-display.tsx +291 -0
  143. package/source/components/user-input.spec.tsx +327 -0
  144. package/source/components/user-input.tsx +533 -0
  145. package/source/components/user-message.spec.tsx +230 -0
  146. package/source/components/user-message.tsx +84 -0
  147. package/source/components/welcome-message.tsx +76 -0
  148. package/source/config/env-substitution.ts +65 -0
  149. package/source/config/index.spec.ts +171 -0
  150. package/source/config/index.ts +154 -0
  151. package/source/config/paths.spec.ts +241 -0
  152. package/source/config/paths.ts +55 -0
  153. package/source/config/preferences.ts +51 -0
  154. package/source/config/themes.ts +315 -0
  155. package/source/constants.ts +130 -0
  156. package/source/context/mode-context.spec.ts +79 -0
  157. package/source/context/mode-context.ts +24 -0
  158. package/source/custom-commands/executor.spec.ts +142 -0
  159. package/source/custom-commands/executor.ts +64 -0
  160. package/source/custom-commands/loader.spec.ts +314 -0
  161. package/source/custom-commands/loader.ts +153 -0
  162. package/source/custom-commands/parser.ts +196 -0
  163. package/source/hooks/chat-handler/conversation/conversation-loop.spec.ts +39 -0
  164. package/source/hooks/chat-handler/conversation/conversation-loop.tsx +511 -0
  165. package/source/hooks/chat-handler/conversation/tool-executor.spec.ts +50 -0
  166. package/source/hooks/chat-handler/conversation/tool-executor.tsx +109 -0
  167. package/source/hooks/chat-handler/index.ts +12 -0
  168. package/source/hooks/chat-handler/state/streaming-state.spec.ts +26 -0
  169. package/source/hooks/chat-handler/state/streaming-state.ts +19 -0
  170. package/source/hooks/chat-handler/types.ts +38 -0
  171. package/source/hooks/chat-handler/useChatHandler.spec.tsx +321 -0
  172. package/source/hooks/chat-handler/useChatHandler.tsx +194 -0
  173. package/source/hooks/chat-handler/utils/context-checker.spec.ts +60 -0
  174. package/source/hooks/chat-handler/utils/context-checker.tsx +73 -0
  175. package/source/hooks/chat-handler/utils/message-helpers.spec.ts +42 -0
  176. package/source/hooks/chat-handler/utils/message-helpers.tsx +36 -0
  177. package/source/hooks/chat-handler/utils/tool-filters.spec.ts +109 -0
  178. package/source/hooks/chat-handler/utils/tool-filters.ts +64 -0
  179. package/source/hooks/useAppHandlers.tsx +291 -0
  180. package/source/hooks/useAppInitialization.tsx +422 -0
  181. package/source/hooks/useAppState.tsx +311 -0
  182. package/source/hooks/useDirectoryTrust.tsx +98 -0
  183. package/source/hooks/useInputState.ts +414 -0
  184. package/source/hooks/useModeHandlers.tsx +302 -0
  185. package/source/hooks/useNonInteractiveMode.ts +140 -0
  186. package/source/hooks/useTerminalWidth.tsx +81 -0
  187. package/source/hooks/useTheme.ts +18 -0
  188. package/source/hooks/useToolHandler.tsx +349 -0
  189. package/source/hooks/useUIState.ts +61 -0
  190. package/source/init/agents-template-generator.ts +421 -0
  191. package/source/init/existing-rules-extractor.ts +319 -0
  192. package/source/init/file-scanner.spec.ts +227 -0
  193. package/source/init/file-scanner.ts +238 -0
  194. package/source/init/framework-detector.ts +382 -0
  195. package/source/init/language-detector.ts +269 -0
  196. package/source/init/project-analyzer.spec.ts +231 -0
  197. package/source/init/project-analyzer.ts +458 -0
  198. package/source/lsp/index.ts +31 -0
  199. package/source/lsp/lsp-client.spec.ts +508 -0
  200. package/source/lsp/lsp-client.ts +487 -0
  201. package/source/lsp/lsp-manager.spec.ts +477 -0
  202. package/source/lsp/lsp-manager.ts +419 -0
  203. package/source/lsp/protocol.spec.ts +502 -0
  204. package/source/lsp/protocol.ts +360 -0
  205. package/source/lsp/server-discovery.spec.ts +654 -0
  206. package/source/lsp/server-discovery.ts +515 -0
  207. package/source/markdown-parser/html-entities.spec.ts +88 -0
  208. package/source/markdown-parser/html-entities.ts +45 -0
  209. package/source/markdown-parser/index.spec.ts +281 -0
  210. package/source/markdown-parser/index.ts +126 -0
  211. package/source/markdown-parser/table-parser.spec.ts +133 -0
  212. package/source/markdown-parser/table-parser.ts +114 -0
  213. package/source/markdown-parser/utils.spec.ts +70 -0
  214. package/source/markdown-parser/utils.ts +13 -0
  215. package/source/mcp/mcp-client.spec.ts +81 -0
  216. package/source/mcp/mcp-client.ts +625 -0
  217. package/source/mcp/transport-factory.spec.ts +406 -0
  218. package/source/mcp/transport-factory.ts +312 -0
  219. package/source/message-handler.ts +67 -0
  220. package/source/model-database/database-engine.spec.ts +494 -0
  221. package/source/model-database/database-engine.ts +50 -0
  222. package/source/model-database/model-database.spec.ts +363 -0
  223. package/source/model-database/model-database.ts +91 -0
  224. package/source/model-database/model-engine.spec.ts +447 -0
  225. package/source/model-database/model-engine.ts +65 -0
  226. package/source/model-database/model-fetcher.spec.ts +583 -0
  227. package/source/model-database/model-fetcher.ts +330 -0
  228. package/source/models/index.ts +1 -0
  229. package/source/models/models-cache.spec.ts +214 -0
  230. package/source/models/models-cache.ts +78 -0
  231. package/source/models/models-dev-client.spec.ts +379 -0
  232. package/source/models/models-dev-client.ts +329 -0
  233. package/source/models/models-types.ts +68 -0
  234. package/source/prompt-history.ts +155 -0
  235. package/source/security/command-injection.spec.ts +240 -0
  236. package/source/services/checkpoint-manager.spec.ts +523 -0
  237. package/source/services/checkpoint-manager.ts +466 -0
  238. package/source/services/file-snapshot.spec.ts +569 -0
  239. package/source/services/file-snapshot.ts +220 -0
  240. package/source/test-utils/render-with-theme.tsx +48 -0
  241. package/source/tokenization/index.ts +1 -0
  242. package/source/tokenization/tokenizer-factory.spec.ts +170 -0
  243. package/source/tokenization/tokenizer-factory.ts +125 -0
  244. package/source/tokenization/tokenizers/anthropic-tokenizer.spec.ts +200 -0
  245. package/source/tokenization/tokenizers/anthropic-tokenizer.ts +43 -0
  246. package/source/tokenization/tokenizers/fallback-tokenizer.spec.ts +236 -0
  247. package/source/tokenization/tokenizers/fallback-tokenizer.ts +26 -0
  248. package/source/tokenization/tokenizers/llama-tokenizer.spec.ts +224 -0
  249. package/source/tokenization/tokenizers/llama-tokenizer.ts +41 -0
  250. package/source/tokenization/tokenizers/openai-tokenizer.spec.ts +184 -0
  251. package/source/tokenization/tokenizers/openai-tokenizer.ts +57 -0
  252. package/source/tool-calling/index.ts +5 -0
  253. package/source/tool-calling/json-parser.spec.ts +639 -0
  254. package/source/tool-calling/json-parser.ts +247 -0
  255. package/source/tool-calling/tool-parser.spec.ts +395 -0
  256. package/source/tool-calling/tool-parser.ts +120 -0
  257. package/source/tool-calling/xml-parser.spec.ts +662 -0
  258. package/source/tool-calling/xml-parser.ts +289 -0
  259. package/source/tools/execute-bash.spec.tsx +353 -0
  260. package/source/tools/execute-bash.tsx +219 -0
  261. package/source/tools/execute-function.spec.ts +130 -0
  262. package/source/tools/fetch-url.spec.tsx +342 -0
  263. package/source/tools/fetch-url.tsx +172 -0
  264. package/source/tools/find-files.spec.tsx +924 -0
  265. package/source/tools/find-files.tsx +293 -0
  266. package/source/tools/index.ts +102 -0
  267. package/source/tools/lsp-get-diagnostics.tsx +192 -0
  268. package/source/tools/needs-approval.spec.ts +282 -0
  269. package/source/tools/read-file.spec.tsx +801 -0
  270. package/source/tools/read-file.tsx +387 -0
  271. package/source/tools/search-file-contents.spec.tsx +1273 -0
  272. package/source/tools/search-file-contents.tsx +293 -0
  273. package/source/tools/string-replace.spec.tsx +730 -0
  274. package/source/tools/string-replace.tsx +548 -0
  275. package/source/tools/tool-manager.ts +210 -0
  276. package/source/tools/tool-registry.spec.ts +415 -0
  277. package/source/tools/tool-registry.ts +228 -0
  278. package/source/tools/web-search.tsx +223 -0
  279. package/source/tools/write-file.spec.tsx +559 -0
  280. package/source/tools/write-file.tsx +228 -0
  281. package/source/types/app.ts +37 -0
  282. package/source/types/checkpoint.ts +48 -0
  283. package/source/types/commands.ts +46 -0
  284. package/source/types/components.ts +27 -0
  285. package/source/types/config.ts +103 -0
  286. package/source/types/core-connection-status.spec.ts +67 -0
  287. package/source/types/core.ts +181 -0
  288. package/source/types/hooks.ts +50 -0
  289. package/source/types/index.ts +12 -0
  290. package/source/types/markdown-parser.ts +11 -0
  291. package/source/types/mcp.ts +52 -0
  292. package/source/types/system.ts +16 -0
  293. package/source/types/tokenization.ts +41 -0
  294. package/source/types/ui.ts +40 -0
  295. package/source/types/usage.ts +58 -0
  296. package/source/types/utils.ts +16 -0
  297. package/source/usage/calculator.spec.ts +385 -0
  298. package/source/usage/calculator.ts +104 -0
  299. package/source/usage/storage.spec.ts +703 -0
  300. package/source/usage/storage.ts +238 -0
  301. package/source/usage/tracker.spec.ts +456 -0
  302. package/source/usage/tracker.ts +102 -0
  303. package/source/utils/atomic-deletion.spec.ts +194 -0
  304. package/source/utils/atomic-deletion.ts +127 -0
  305. package/source/utils/bounded-map.spec.ts +300 -0
  306. package/source/utils/bounded-map.ts +193 -0
  307. package/source/utils/checkpoint-utils.spec.ts +222 -0
  308. package/source/utils/checkpoint-utils.ts +92 -0
  309. package/source/utils/error-formatter.spec.ts +169 -0
  310. package/source/utils/error-formatter.ts +194 -0
  311. package/source/utils/file-autocomplete.spec.ts +173 -0
  312. package/source/utils/file-autocomplete.ts +196 -0
  313. package/source/utils/file-cache.spec.ts +309 -0
  314. package/source/utils/file-cache.ts +195 -0
  315. package/source/utils/file-content-loader.spec.ts +180 -0
  316. package/source/utils/file-content-loader.ts +179 -0
  317. package/source/utils/file-mention-handler.spec.ts +261 -0
  318. package/source/utils/file-mention-handler.ts +84 -0
  319. package/source/utils/file-mention-parser.spec.ts +182 -0
  320. package/source/utils/file-mention-parser.ts +170 -0
  321. package/source/utils/fuzzy-matching.spec.ts +149 -0
  322. package/source/utils/fuzzy-matching.ts +146 -0
  323. package/source/utils/indentation-normalizer.spec.ts +216 -0
  324. package/source/utils/indentation-normalizer.ts +76 -0
  325. package/source/utils/installation-detector.spec.ts +178 -0
  326. package/source/utils/installation-detector.ts +153 -0
  327. package/source/utils/logging/config.spec.ts +311 -0
  328. package/source/utils/logging/config.ts +210 -0
  329. package/source/utils/logging/console-facade.spec.ts +184 -0
  330. package/source/utils/logging/console-facade.ts +384 -0
  331. package/source/utils/logging/correlation.spec.ts +679 -0
  332. package/source/utils/logging/correlation.ts +474 -0
  333. package/source/utils/logging/formatters.spec.ts +464 -0
  334. package/source/utils/logging/formatters.ts +207 -0
  335. package/source/utils/logging/health-monitor/alerts/alert-manager.spec.ts +93 -0
  336. package/source/utils/logging/health-monitor/alerts/alert-manager.ts +79 -0
  337. package/source/utils/logging/health-monitor/checks/configuration-check.spec.ts +56 -0
  338. package/source/utils/logging/health-monitor/checks/configuration-check.ts +43 -0
  339. package/source/utils/logging/health-monitor/checks/logging-check.spec.ts +56 -0
  340. package/source/utils/logging/health-monitor/checks/logging-check.ts +58 -0
  341. package/source/utils/logging/health-monitor/checks/memory-check.spec.ts +100 -0
  342. package/source/utils/logging/health-monitor/checks/memory-check.ts +78 -0
  343. package/source/utils/logging/health-monitor/checks/performance-check.spec.ts +56 -0
  344. package/source/utils/logging/health-monitor/checks/performance-check.ts +56 -0
  345. package/source/utils/logging/health-monitor/checks/request-check.spec.ts +56 -0
  346. package/source/utils/logging/health-monitor/checks/request-check.ts +76 -0
  347. package/source/utils/logging/health-monitor/core/health-check-runner.spec.ts +70 -0
  348. package/source/utils/logging/health-monitor/core/health-check-runner.ts +138 -0
  349. package/source/utils/logging/health-monitor/core/health-monitor.spec.ts +58 -0
  350. package/source/utils/logging/health-monitor/core/health-monitor.ts +344 -0
  351. package/source/utils/logging/health-monitor/core/scoring.spec.ts +65 -0
  352. package/source/utils/logging/health-monitor/core/scoring.ts +91 -0
  353. package/source/utils/logging/health-monitor/index.ts +15 -0
  354. package/source/utils/logging/health-monitor/instances.ts +48 -0
  355. package/source/utils/logging/health-monitor/middleware/http-middleware.spec.ts +141 -0
  356. package/source/utils/logging/health-monitor/middleware/http-middleware.ts +75 -0
  357. package/source/utils/logging/health-monitor/types.ts +126 -0
  358. package/source/utils/logging/index.spec.ts +284 -0
  359. package/source/utils/logging/index.ts +236 -0
  360. package/source/utils/logging/integration.spec.ts +441 -0
  361. package/source/utils/logging/log-method-factory.spec.ts +573 -0
  362. package/source/utils/logging/log-method-factory.ts +233 -0
  363. package/source/utils/logging/log-query/aggregation/aggregator.spec.ts +277 -0
  364. package/source/utils/logging/log-query/aggregation/aggregator.ts +159 -0
  365. package/source/utils/logging/log-query/aggregation/facet-generator.spec.ts +159 -0
  366. package/source/utils/logging/log-query/aggregation/facet-generator.ts +47 -0
  367. package/source/utils/logging/log-query/index.ts +23 -0
  368. package/source/utils/logging/log-query/query/filter-predicates.spec.ts +247 -0
  369. package/source/utils/logging/log-query/query/filter-predicates.ts +154 -0
  370. package/source/utils/logging/log-query/query/query-builder.spec.ts +182 -0
  371. package/source/utils/logging/log-query/query/query-builder.ts +151 -0
  372. package/source/utils/logging/log-query/query/query-engine.spec.ts +214 -0
  373. package/source/utils/logging/log-query/query/query-engine.ts +45 -0
  374. package/source/utils/logging/log-query/storage/circular-buffer.spec.ts +143 -0
  375. package/source/utils/logging/log-query/storage/circular-buffer.ts +75 -0
  376. package/source/utils/logging/log-query/storage/index-manager.spec.ts +150 -0
  377. package/source/utils/logging/log-query/storage/index-manager.ts +71 -0
  378. package/source/utils/logging/log-query/storage/log-storage.spec.ts +257 -0
  379. package/source/utils/logging/log-query/storage/log-storage.ts +80 -0
  380. package/source/utils/logging/log-query/types.ts +163 -0
  381. package/source/utils/logging/log-query/utils/helpers.spec.ts +263 -0
  382. package/source/utils/logging/log-query/utils/helpers.ts +72 -0
  383. package/source/utils/logging/log-query/utils/sorting.spec.ts +182 -0
  384. package/source/utils/logging/log-query/utils/sorting.ts +61 -0
  385. package/source/utils/logging/logger-provider.spec.ts +262 -0
  386. package/source/utils/logging/logger-provider.ts +362 -0
  387. package/source/utils/logging/performance.spec.ts +209 -0
  388. package/source/utils/logging/performance.ts +757 -0
  389. package/source/utils/logging/pino-logger.spec.ts +425 -0
  390. package/source/utils/logging/pino-logger.ts +514 -0
  391. package/source/utils/logging/redaction.spec.ts +490 -0
  392. package/source/utils/logging/redaction.ts +267 -0
  393. package/source/utils/logging/request-tracker.spec.ts +1198 -0
  394. package/source/utils/logging/request-tracker.ts +803 -0
  395. package/source/utils/logging/transports.spec.ts +505 -0
  396. package/source/utils/logging/transports.ts +305 -0
  397. package/source/utils/logging/types.ts +216 -0
  398. package/source/utils/message-builder.spec.ts +179 -0
  399. package/source/utils/message-builder.ts +101 -0
  400. package/source/utils/message-queue.tsx +486 -0
  401. package/source/utils/paste-detection.spec.ts +69 -0
  402. package/source/utils/paste-detection.ts +124 -0
  403. package/source/utils/paste-roundtrip.spec.ts +442 -0
  404. package/source/utils/paste-utils.spec.ts +128 -0
  405. package/source/utils/paste-utils.ts +52 -0
  406. package/source/utils/programming-language-helper.spec.ts +74 -0
  407. package/source/utils/programming-language-helper.ts +32 -0
  408. package/source/utils/prompt-assembly.spec.ts +221 -0
  409. package/source/utils/prompt-processor.ts +173 -0
  410. package/source/utils/tool-args-parser.spec.ts +136 -0
  411. package/source/utils/tool-args-parser.ts +54 -0
  412. package/source/utils/tool-cancellation.spec.ts +230 -0
  413. package/source/utils/tool-cancellation.ts +28 -0
  414. package/source/utils/tool-result-display.spec.tsx +469 -0
  415. package/source/utils/tool-result-display.tsx +90 -0
  416. package/source/utils/update-checker.spec.ts +383 -0
  417. package/source/utils/update-checker.ts +183 -0
  418. package/source/wizard/config-wizard.spec.tsx +103 -0
  419. package/source/wizard/config-wizard.tsx +382 -0
  420. package/source/wizard/steps/location-step.spec.tsx +186 -0
  421. package/source/wizard/steps/location-step.tsx +147 -0
  422. package/source/wizard/steps/mcp-step.spec.tsx +607 -0
  423. package/source/wizard/steps/mcp-step.tsx +632 -0
  424. package/source/wizard/steps/provider-step.spec.tsx +342 -0
  425. package/source/wizard/steps/provider-step.tsx +957 -0
  426. package/source/wizard/steps/summary-step.spec.tsx +749 -0
  427. package/source/wizard/steps/summary-step.tsx +228 -0
  428. package/source/wizard/templates/mcp-templates.spec.ts +613 -0
  429. package/source/wizard/templates/mcp-templates.ts +570 -0
  430. package/source/wizard/templates/provider-templates.spec.ts +152 -0
  431. package/source/wizard/templates/provider-templates.ts +485 -0
  432. package/source/wizard/utils/fetch-cloud-models.spec.ts +428 -0
  433. package/source/wizard/utils/fetch-cloud-models.ts +223 -0
  434. package/source/wizard/utils/fetch-local-models.spec.ts +297 -0
  435. package/source/wizard/utils/fetch-local-models.ts +192 -0
  436. package/source/wizard/validation-array.spec.ts +264 -0
  437. package/source/wizard/validation.spec.ts +373 -0
  438. package/source/wizard/validation.ts +232 -0
  439. package/source/app/prompts/main-prompt.md +0 -122
@@ -0,0 +1,163 @@
1
+ import test from 'ava';
2
+ import React from 'react';
3
+ import {renderWithTheme} from '../../test-utils/render-with-theme';
4
+ import {ChatInterface} from './ChatInterface';
5
+ import type {ChatInterfaceProps} from './ChatInterface';
6
+
7
+ // Helper to create default props
8
+ function createDefaultProps(
9
+ overrides: Partial<ChatInterfaceProps> = {},
10
+ ): ChatInterfaceProps {
11
+ return {
12
+ startChat: true,
13
+ staticComponents: [],
14
+ queuedComponents: [],
15
+ isCancelling: false,
16
+ isToolExecuting: false,
17
+ isToolConfirmationMode: false,
18
+ isBashExecuting: false,
19
+ currentBashCommand: '',
20
+ pendingToolCalls: [],
21
+ currentToolIndex: 0,
22
+ mcpInitialized: true,
23
+ client: {},
24
+ nonInteractivePrompt: undefined,
25
+ nonInteractiveLoadingMessage: null,
26
+ customCommands: [],
27
+ inputDisabled: false,
28
+ developmentMode: 'normal',
29
+ onToolConfirm: async () => {},
30
+ onToolCancel: () => {},
31
+ onSubmit: async () => {},
32
+ onCancel: () => {},
33
+ onToggleMode: () => {},
34
+ ...overrides,
35
+ };
36
+ }
37
+
38
+ test('ChatInterface renders without error', t => {
39
+ const props = createDefaultProps();
40
+ const {lastFrame, unmount} = renderWithTheme(<ChatInterface {...props} />);
41
+ const output = lastFrame();
42
+ t.truthy(output);
43
+ unmount();
44
+ });
45
+
46
+ test('ChatInterface renders chat structure', t => {
47
+ const props = createDefaultProps();
48
+ const {lastFrame, unmount} = renderWithTheme(<ChatInterface {...props} />);
49
+ const output = lastFrame();
50
+ t.truthy(output);
51
+ unmount();
52
+ });
53
+
54
+ test('ChatInterface shows UserInput when ready for input', t => {
55
+ const props = createDefaultProps({
56
+ startChat: true,
57
+ mcpInitialized: true,
58
+ client: {},
59
+ nonInteractivePrompt: undefined,
60
+ isToolExecuting: false,
61
+ isToolConfirmationMode: false,
62
+ isBashExecuting: false,
63
+ });
64
+
65
+ const {lastFrame, unmount} = renderWithTheme(<ChatInterface {...props} />);
66
+ const output = lastFrame();
67
+ t.truthy(output);
68
+ unmount();
69
+ });
70
+
71
+ test('ChatInterface shows loading spinner when not initialized', t => {
72
+ const props = createDefaultProps({
73
+ startChat: true,
74
+ mcpInitialized: false,
75
+ client: null,
76
+ });
77
+
78
+ const {lastFrame, unmount} = renderWithTheme(<ChatInterface {...props} />);
79
+ const output = lastFrame();
80
+ t.truthy(output);
81
+ t.regex(output!, /Loading/);
82
+ unmount();
83
+ });
84
+
85
+ test('ChatInterface shows completion message in non-interactive mode when done', t => {
86
+ const props = createDefaultProps({
87
+ startChat: true,
88
+ nonInteractivePrompt: 'test prompt',
89
+ nonInteractiveLoadingMessage: null, // Signals completion
90
+ mcpInitialized: true,
91
+ client: {},
92
+ });
93
+
94
+ const {lastFrame, unmount} = renderWithTheme(<ChatInterface {...props} />);
95
+ const output = lastFrame();
96
+ t.truthy(output);
97
+ // Note: marginLeft={-1} in the component cuts off the first character in tests
98
+ t.regex(output!, /ompleted.*Exiting/);
99
+ unmount();
100
+ });
101
+
102
+ test('ChatInterface shows tool confirmation when in tool confirmation mode', t => {
103
+ const mockToolCall = {
104
+ id: 'test-1',
105
+ function: {name: 'test_tool', arguments: {}},
106
+ };
107
+
108
+ const props = createDefaultProps({
109
+ startChat: true,
110
+ isToolConfirmationMode: true,
111
+ pendingToolCalls: [mockToolCall],
112
+ currentToolIndex: 0,
113
+ });
114
+
115
+ const {lastFrame, unmount} = renderWithTheme(<ChatInterface {...props} />);
116
+ const output = lastFrame();
117
+ t.truthy(output);
118
+ unmount();
119
+ });
120
+
121
+ test('ChatInterface shows tool execution indicator when executing', t => {
122
+ const mockToolCall = {
123
+ id: 'test-1',
124
+ function: {name: 'test_tool', arguments: {}},
125
+ };
126
+
127
+ const props = createDefaultProps({
128
+ startChat: true,
129
+ isToolExecuting: true,
130
+ pendingToolCalls: [mockToolCall],
131
+ currentToolIndex: 0,
132
+ });
133
+
134
+ const {lastFrame, unmount} = renderWithTheme(<ChatInterface {...props} />);
135
+ const output = lastFrame();
136
+ t.truthy(output);
137
+ unmount();
138
+ });
139
+
140
+ test('ChatInterface shows bash execution indicator when executing bash', t => {
141
+ const props = createDefaultProps({
142
+ startChat: true,
143
+ isBashExecuting: true,
144
+ currentBashCommand: 'ls -la',
145
+ });
146
+
147
+ const {lastFrame, unmount} = renderWithTheme(<ChatInterface {...props} />);
148
+ const output = lastFrame();
149
+ t.truthy(output);
150
+ unmount();
151
+ });
152
+
153
+ test('ChatInterface shows cancelling indicator when cancelling', t => {
154
+ const props = createDefaultProps({
155
+ startChat: true,
156
+ isCancelling: true,
157
+ });
158
+
159
+ const {lastFrame, unmount} = renderWithTheme(<ChatInterface {...props} />);
160
+ const output = lastFrame();
161
+ t.truthy(output);
162
+ unmount();
163
+ });
@@ -0,0 +1,144 @@
1
+ import BashExecutionIndicator from '@/components/bash-execution-indicator';
2
+ import CancellingIndicator from '@/components/cancelling-indicator';
3
+ import ChatQueue from '@/components/chat-queue';
4
+ import ToolConfirmation from '@/components/tool-confirmation';
5
+ import ToolExecutionIndicator from '@/components/tool-execution-indicator';
6
+ import UserInput from '@/components/user-input';
7
+ import { useTheme } from '@/hooks/useTheme';
8
+ import type { DevelopmentMode, ToolCall } from '@/types';
9
+ import { Box, Text } from 'ink';
10
+ import RandomSpinner from '@/components/random-spinner';
11
+ import React from 'react';
12
+
13
+ export interface ChatInterfaceProps {
14
+ // Chat state
15
+ startChat: boolean;
16
+ staticComponents: React.ReactNode[];
17
+ queuedComponents: React.ReactNode[];
18
+
19
+ // Execution state
20
+ isCancelling: boolean;
21
+ isToolExecuting: boolean;
22
+ isToolConfirmationMode: boolean;
23
+ isBashExecuting: boolean;
24
+ currentBashCommand: string;
25
+
26
+ // Tool state
27
+ pendingToolCalls: ToolCall[];
28
+ currentToolIndex: number;
29
+
30
+ // Client state
31
+ mcpInitialized: boolean;
32
+ client: unknown | null; // LLMClient type, but kept as unknown to avoid import
33
+
34
+ // Non-interactive mode
35
+ nonInteractivePrompt?: string;
36
+ nonInteractiveLoadingMessage: string | null;
37
+
38
+ // Input state
39
+ customCommands: string[];
40
+ inputDisabled: boolean;
41
+ developmentMode: DevelopmentMode;
42
+
43
+ // Handlers
44
+ onToolConfirm: (confirmed: boolean) => void;
45
+ onToolCancel: () => void;
46
+ onSubmit: (message: string) => Promise<void>;
47
+ onCancel: () => void;
48
+ onToggleMode: () => void;
49
+ }
50
+
51
+ /**
52
+ * Main chat interface component that renders the chat queue and input area
53
+ */
54
+ export function ChatInterface({
55
+ startChat,
56
+ staticComponents,
57
+ queuedComponents,
58
+ isCancelling,
59
+ isToolExecuting,
60
+ isToolConfirmationMode,
61
+ isBashExecuting,
62
+ currentBashCommand,
63
+ pendingToolCalls,
64
+ currentToolIndex,
65
+ mcpInitialized,
66
+ client,
67
+ nonInteractivePrompt,
68
+ nonInteractiveLoadingMessage,
69
+ customCommands,
70
+ inputDisabled,
71
+ developmentMode,
72
+ onToolConfirm,
73
+ onToolCancel,
74
+ onSubmit,
75
+ onCancel,
76
+ onToggleMode,
77
+ }: ChatInterfaceProps): React.ReactElement {
78
+ const { colors } = useTheme();
79
+
80
+ const loadingLabel = nonInteractivePrompt
81
+ ? (nonInteractiveLoadingMessage ?? 'Loading...')
82
+ : 'Loading...';
83
+
84
+ return (
85
+ <>
86
+ {/* Chat Queue */}
87
+ <Box flexGrow={1} flexDirection="column" minHeight={0}>
88
+ {startChat && (
89
+ <ChatQueue
90
+ staticComponents={staticComponents}
91
+ queuedComponents={queuedComponents}
92
+ />
93
+ )}
94
+ </Box>
95
+
96
+ {/* Input Area */}
97
+ {startChat && (
98
+ <Box flexDirection="column" marginLeft={-1}>
99
+ {isCancelling && <CancellingIndicator />}
100
+
101
+ {/* Tool Confirmation */}
102
+ {isToolConfirmationMode && pendingToolCalls[currentToolIndex] ? (
103
+ <ToolConfirmation
104
+ toolCall={pendingToolCalls[currentToolIndex]}
105
+ onConfirm={onToolConfirm}
106
+ onCancel={onToolCancel}
107
+ />
108
+ ) : /* Tool Execution */
109
+ isToolExecuting && pendingToolCalls[currentToolIndex] ? (
110
+ <ToolExecutionIndicator
111
+ toolName={pendingToolCalls[currentToolIndex].function.name}
112
+ currentIndex={currentToolIndex}
113
+ totalTools={pendingToolCalls.length}
114
+ />
115
+ ) : /* Bash Execution */
116
+ isBashExecuting ? (
117
+ <BashExecutionIndicator command={currentBashCommand} />
118
+ ) : /* User Input */
119
+ mcpInitialized && client && !nonInteractivePrompt ? (
120
+ <UserInput
121
+ customCommands={customCommands}
122
+ onSubmit={msg => void onSubmit(msg)}
123
+ disabled={inputDisabled}
124
+ onCancel={onCancel}
125
+ onToggleMode={onToggleMode}
126
+ developmentMode={developmentMode}
127
+ />
128
+ ) : /* Client Missing */
129
+ mcpInitialized && !client ? (
130
+ <></>
131
+ ) : /* Non-Interactive Complete */
132
+ nonInteractivePrompt && !nonInteractiveLoadingMessage ? (
133
+ <Text color={colors.secondary}>Completed. Exiting.</Text>
134
+ ) : (
135
+ /* Loading */
136
+ <Text color={colors.secondary}>
137
+ <RandomSpinner /> {loadingLabel}
138
+ </Text>
139
+ )}
140
+ </Box>
141
+ )}
142
+ </>
143
+ );
144
+ }
@@ -0,0 +1,141 @@
1
+ import test from 'ava';
2
+ import React from 'react';
3
+ import {renderWithTheme} from '../../test-utils/render-with-theme';
4
+ import {ModalSelectors} from './ModalSelectors';
5
+ import type {ModalSelectorsProps} from './ModalSelectors';
6
+
7
+ // Helper to create default props
8
+ function createDefaultProps(
9
+ overrides: Partial<ModalSelectorsProps> = {},
10
+ ): ModalSelectorsProps {
11
+ return {
12
+ isModelSelectionMode: false,
13
+ isProviderSelectionMode: false,
14
+ isThemeSelectionMode: false,
15
+ isModelDatabaseMode: false,
16
+ isConfigWizardMode: false,
17
+ isCheckpointLoadMode: false,
18
+ client: null,
19
+ currentModel: 'test-model',
20
+ currentProvider: 'test-provider',
21
+ checkpointLoadData: null,
22
+ onModelSelect: async () => {},
23
+ onModelSelectionCancel: () => {},
24
+ onProviderSelect: async () => {},
25
+ onProviderSelectionCancel: () => {},
26
+ onThemeSelect: () => {},
27
+ onThemeSelectionCancel: () => {},
28
+ onModelDatabaseCancel: () => {},
29
+ onConfigWizardComplete: async () => {},
30
+ onConfigWizardCancel: () => {},
31
+ onCheckpointSelect: async () => {},
32
+ onCheckpointCancel: () => {},
33
+ ...overrides,
34
+ };
35
+ }
36
+
37
+ test('ModalSelectors returns null when no mode is active', t => {
38
+ const props = createDefaultProps();
39
+ const result = ModalSelectors(props);
40
+ t.is(result, null);
41
+ });
42
+
43
+ test('ModalSelectors renders ModelSelector when isModelSelectionMode is true', t => {
44
+ const props = createDefaultProps({
45
+ isModelSelectionMode: true,
46
+ client: {}, // Mock client
47
+ });
48
+ const component = ModalSelectors(props);
49
+ t.truthy(component);
50
+
51
+ const {lastFrame, unmount} = renderWithTheme(<>{component}</>);
52
+ const output = lastFrame();
53
+ t.truthy(output);
54
+ unmount();
55
+ });
56
+
57
+ test('ModalSelectors renders ProviderSelector when isProviderSelectionMode is true', t => {
58
+ const props = createDefaultProps({isProviderSelectionMode: true});
59
+ const component = ModalSelectors(props);
60
+ t.truthy(component);
61
+
62
+ const {lastFrame, unmount} = renderWithTheme(<>{component}</>);
63
+ const output = lastFrame();
64
+ t.truthy(output);
65
+ unmount();
66
+ });
67
+
68
+ test('ModalSelectors renders ThemeSelector when isThemeSelectionMode is true', t => {
69
+ const props = createDefaultProps({isThemeSelectionMode: true});
70
+ const component = ModalSelectors(props);
71
+ t.truthy(component);
72
+
73
+ const {lastFrame, unmount} = renderWithTheme(<>{component}</>);
74
+ const output = lastFrame();
75
+ t.truthy(output);
76
+ unmount();
77
+ });
78
+
79
+ test('ModalSelectors renders ModelDatabaseDisplay when isModelDatabaseMode is true', t => {
80
+ const props = createDefaultProps({isModelDatabaseMode: true});
81
+ const component = ModalSelectors(props);
82
+ t.truthy(component);
83
+
84
+ const {lastFrame, unmount} = renderWithTheme(<>{component}</>);
85
+ const output = lastFrame();
86
+ t.truthy(output);
87
+ unmount();
88
+ });
89
+
90
+ test('ModalSelectors renders ConfigWizard when isConfigWizardMode is true', t => {
91
+ const props = createDefaultProps({isConfigWizardMode: true});
92
+ const component = ModalSelectors(props);
93
+ t.truthy(component);
94
+
95
+ const {lastFrame, unmount} = renderWithTheme(<>{component}</>);
96
+ const output = lastFrame();
97
+ t.truthy(output);
98
+ unmount();
99
+ });
100
+
101
+ test('ModalSelectors renders CheckpointSelector when isCheckpointLoadMode is true and data exists', t => {
102
+ const props = createDefaultProps({
103
+ isCheckpointLoadMode: true,
104
+ checkpointLoadData: {
105
+ checkpoints: [],
106
+ currentMessageCount: 0,
107
+ },
108
+ });
109
+ const component = ModalSelectors(props);
110
+ t.truthy(component);
111
+
112
+ const {lastFrame, unmount} = renderWithTheme(<>{component}</>);
113
+ const output = lastFrame();
114
+ t.truthy(output);
115
+ unmount();
116
+ });
117
+
118
+ test('ModalSelectors returns null when isCheckpointLoadMode is true but data is null', t => {
119
+ const props = createDefaultProps({
120
+ isCheckpointLoadMode: true,
121
+ checkpointLoadData: null,
122
+ });
123
+ const result = ModalSelectors(props);
124
+ t.is(result, null);
125
+ });
126
+
127
+ test('ModalSelectors prioritizes first active mode when multiple are true', t => {
128
+ const props = createDefaultProps({
129
+ isModelSelectionMode: true,
130
+ isProviderSelectionMode: true,
131
+ isThemeSelectionMode: true,
132
+ client: {}, // Mock client for ModelSelector
133
+ });
134
+ const component = ModalSelectors(props);
135
+ t.truthy(component);
136
+
137
+ const {lastFrame, unmount} = renderWithTheme(<>{component}</>);
138
+ const output = lastFrame();
139
+ t.truthy(output);
140
+ unmount();
141
+ });
@@ -0,0 +1,135 @@
1
+ import {ModelDatabaseDisplay} from '@/commands/model-database';
2
+ import CheckpointSelector from '@/components/checkpoint-selector';
3
+ import ModelSelector from '@/components/model-selector';
4
+ import ProviderSelector from '@/components/provider-selector';
5
+ import ThemeSelector from '@/components/theme-selector';
6
+ import type {CheckpointListItem, LLMClient} from '@/types';
7
+ import {ConfigWizard} from '@/wizard/config-wizard';
8
+ import React from 'react';
9
+
10
+ export interface ModalSelectorsProps {
11
+ // State flags
12
+ isModelSelectionMode: boolean;
13
+ isProviderSelectionMode: boolean;
14
+ isThemeSelectionMode: boolean;
15
+ isModelDatabaseMode: boolean;
16
+ isConfigWizardMode: boolean;
17
+ isCheckpointLoadMode: boolean;
18
+
19
+ // Current values
20
+ client: LLMClient | null;
21
+ currentModel: string;
22
+ currentProvider: string;
23
+ checkpointLoadData: {
24
+ checkpoints: CheckpointListItem[];
25
+ currentMessageCount: number;
26
+ } | null;
27
+
28
+ // Handlers - Model Selection
29
+ onModelSelect: (model: string) => Promise<void>;
30
+ onModelSelectionCancel: () => void;
31
+
32
+ // Handlers - Provider Selection
33
+ onProviderSelect: (provider: string) => Promise<void>;
34
+ onProviderSelectionCancel: () => void;
35
+
36
+ // Handlers - Theme Selection
37
+ onThemeSelect: (theme: import('@/types/ui').ThemePreset) => void;
38
+ onThemeSelectionCancel: () => void;
39
+
40
+ // Handlers - Model Database
41
+ onModelDatabaseCancel: () => void;
42
+
43
+ // Handlers - Config Wizard
44
+ onConfigWizardComplete: (configPath: string) => Promise<void>;
45
+ onConfigWizardCancel: () => void;
46
+
47
+ // Handlers - Checkpoint
48
+ onCheckpointSelect: (name: string, backup: boolean) => Promise<void>;
49
+ onCheckpointCancel: () => void;
50
+ }
51
+
52
+ /**
53
+ * Renders the appropriate modal selector based on current application mode
54
+ * Returns null if no modal is active
55
+ */
56
+ export function ModalSelectors({
57
+ isModelSelectionMode,
58
+ isProviderSelectionMode,
59
+ isThemeSelectionMode,
60
+ isModelDatabaseMode,
61
+ isConfigWizardMode,
62
+ isCheckpointLoadMode,
63
+ client,
64
+ currentModel,
65
+ currentProvider,
66
+ checkpointLoadData,
67
+ onModelSelect,
68
+ onModelSelectionCancel,
69
+ onProviderSelect,
70
+ onProviderSelectionCancel,
71
+ onThemeSelect,
72
+ onThemeSelectionCancel,
73
+ onModelDatabaseCancel,
74
+ onConfigWizardComplete,
75
+ onConfigWizardCancel,
76
+ onCheckpointSelect,
77
+ onCheckpointCancel,
78
+ }: ModalSelectorsProps): React.ReactElement | null {
79
+ if (isModelSelectionMode) {
80
+ return (
81
+ <ModelSelector
82
+ client={client}
83
+ currentModel={currentModel}
84
+ onModelSelect={model => void onModelSelect(model)}
85
+ onCancel={onModelSelectionCancel}
86
+ />
87
+ );
88
+ }
89
+
90
+ if (isProviderSelectionMode) {
91
+ return (
92
+ <ProviderSelector
93
+ currentProvider={currentProvider}
94
+ onProviderSelect={provider => void onProviderSelect(provider)}
95
+ onCancel={onProviderSelectionCancel}
96
+ />
97
+ );
98
+ }
99
+
100
+ if (isThemeSelectionMode) {
101
+ return (
102
+ <ThemeSelector
103
+ onThemeSelect={onThemeSelect}
104
+ onCancel={onThemeSelectionCancel}
105
+ />
106
+ );
107
+ }
108
+
109
+ if (isModelDatabaseMode) {
110
+ return <ModelDatabaseDisplay onCancel={onModelDatabaseCancel} />;
111
+ }
112
+
113
+ if (isConfigWizardMode) {
114
+ return (
115
+ <ConfigWizard
116
+ projectDir={process.cwd()}
117
+ onComplete={configPath => void onConfigWizardComplete(configPath)}
118
+ onCancel={onConfigWizardCancel}
119
+ />
120
+ );
121
+ }
122
+
123
+ if (isCheckpointLoadMode && checkpointLoadData) {
124
+ return (
125
+ <CheckpointSelector
126
+ checkpoints={checkpointLoadData.checkpoints}
127
+ currentMessageCount={checkpointLoadData.currentMessageCount}
128
+ onSelect={(name, backup) => void onCheckpointSelect(name, backup)}
129
+ onCancel={onCheckpointCancel}
130
+ />
131
+ );
132
+ }
133
+
134
+ return null;
135
+ }
@@ -0,0 +1,97 @@
1
+ import test from 'ava';
2
+ import {isNonInteractiveModeComplete, shouldRenderWelcome} from './helpers';
3
+ import type {NonInteractiveModeState} from './types';
4
+
5
+ test('shouldRenderWelcome returns true when not in non-interactive mode', t => {
6
+ t.true(shouldRenderWelcome(false));
7
+ t.true(shouldRenderWelcome(undefined));
8
+ });
9
+
10
+ test('shouldRenderWelcome returns false when in non-interactive mode', t => {
11
+ t.false(shouldRenderWelcome(true));
12
+ });
13
+
14
+ test('isNonInteractiveModeComplete returns timeout when time exceeded', t => {
15
+ const state: NonInteractiveModeState = {
16
+ isToolExecuting: false,
17
+ isBashExecuting: false,
18
+ isToolConfirmationMode: false,
19
+ isConversationComplete: false,
20
+ messages: [],
21
+ };
22
+
23
+ const startTime = Date.now() - 11000; // 11 seconds ago
24
+ const maxTime = 10000; // 10 second timeout
25
+
26
+ const result = isNonInteractiveModeComplete(state, startTime, maxTime);
27
+ t.true(result.shouldExit);
28
+ t.is(result.reason, 'timeout');
29
+ });
30
+
31
+ test('isNonInteractiveModeComplete returns tool-approval when tool approval required', t => {
32
+ const state: NonInteractiveModeState = {
33
+ isToolExecuting: false,
34
+ isBashExecuting: false,
35
+ isToolConfirmationMode: false,
36
+ isConversationComplete: false,
37
+ messages: [{role: 'assistant', content: 'Tool approval required'}],
38
+ };
39
+
40
+ const startTime = Date.now();
41
+ const maxTime = 10000;
42
+
43
+ const result = isNonInteractiveModeComplete(state, startTime, maxTime);
44
+ t.true(result.shouldExit);
45
+ t.is(result.reason, 'tool-approval');
46
+ });
47
+
48
+ test('isNonInteractiveModeComplete returns error when error messages present', t => {
49
+ const state: NonInteractiveModeState = {
50
+ isToolExecuting: false,
51
+ isBashExecuting: false,
52
+ isToolConfirmationMode: false,
53
+ isConversationComplete: false,
54
+ messages: [{role: 'error', content: 'Something went wrong'}],
55
+ };
56
+
57
+ const startTime = Date.now();
58
+ const maxTime = 10000;
59
+
60
+ const result = isNonInteractiveModeComplete(state, startTime, maxTime);
61
+ t.true(result.shouldExit);
62
+ t.is(result.reason, 'error');
63
+ });
64
+
65
+ test('isNonInteractiveModeComplete returns complete when conversation finished', t => {
66
+ const state: NonInteractiveModeState = {
67
+ isToolExecuting: false,
68
+ isBashExecuting: false,
69
+ isToolConfirmationMode: false,
70
+ isConversationComplete: true,
71
+ messages: [{role: 'assistant', content: 'Done'}],
72
+ };
73
+
74
+ const startTime = Date.now();
75
+ const maxTime = 10000;
76
+
77
+ const result = isNonInteractiveModeComplete(state, startTime, maxTime);
78
+ t.true(result.shouldExit);
79
+ t.is(result.reason, 'complete');
80
+ });
81
+
82
+ test('isNonInteractiveModeComplete returns false when still processing', t => {
83
+ const state: NonInteractiveModeState = {
84
+ isToolExecuting: true,
85
+ isBashExecuting: false,
86
+ isToolConfirmationMode: false,
87
+ isConversationComplete: false,
88
+ messages: [],
89
+ };
90
+
91
+ const startTime = Date.now();
92
+ const maxTime = 10000;
93
+
94
+ const result = isNonInteractiveModeComplete(state, startTime, maxTime);
95
+ t.false(result.shouldExit);
96
+ t.is(result.reason, null);
97
+ });