@otto-assistant/bridge 0.4.92

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 (483) hide show
  1. package/bin.js +2 -0
  2. package/dist/agent-model.e2e.test.js +755 -0
  3. package/dist/ai-tool-to-genai.js +233 -0
  4. package/dist/ai-tool-to-genai.test.js +267 -0
  5. package/dist/ai-tool.js +6 -0
  6. package/dist/anthropic-auth-plugin.js +728 -0
  7. package/dist/anthropic-auth-plugin.test.js +125 -0
  8. package/dist/anthropic-auth-state.js +231 -0
  9. package/dist/bin.js +90 -0
  10. package/dist/channel-management.js +227 -0
  11. package/dist/cli-parsing.test.js +137 -0
  12. package/dist/cli-send-thread.e2e.test.js +356 -0
  13. package/dist/cli.js +3276 -0
  14. package/dist/commands/abort.js +65 -0
  15. package/dist/commands/action-buttons.js +245 -0
  16. package/dist/commands/add-project.js +113 -0
  17. package/dist/commands/agent.js +335 -0
  18. package/dist/commands/ask-question.js +274 -0
  19. package/dist/commands/btw.js +116 -0
  20. package/dist/commands/compact.js +120 -0
  21. package/dist/commands/context-usage.js +140 -0
  22. package/dist/commands/create-new-project.js +130 -0
  23. package/dist/commands/diff.js +63 -0
  24. package/dist/commands/file-upload.js +275 -0
  25. package/dist/commands/fork.js +220 -0
  26. package/dist/commands/gemini-apikey.js +70 -0
  27. package/dist/commands/login.js +885 -0
  28. package/dist/commands/mcp.js +239 -0
  29. package/dist/commands/memory-snapshot.js +24 -0
  30. package/dist/commands/mention-mode.js +44 -0
  31. package/dist/commands/merge-worktree.js +159 -0
  32. package/dist/commands/model-variant.js +364 -0
  33. package/dist/commands/model.js +776 -0
  34. package/dist/commands/new-worktree.js +366 -0
  35. package/dist/commands/paginated-select.js +57 -0
  36. package/dist/commands/permissions.js +274 -0
  37. package/dist/commands/queue.js +206 -0
  38. package/dist/commands/remove-project.js +115 -0
  39. package/dist/commands/restart-opencode-server.js +127 -0
  40. package/dist/commands/resume.js +149 -0
  41. package/dist/commands/run-command.js +79 -0
  42. package/dist/commands/screenshare.js +303 -0
  43. package/dist/commands/screenshare.test.js +20 -0
  44. package/dist/commands/session-id.js +78 -0
  45. package/dist/commands/session.js +176 -0
  46. package/dist/commands/share.js +80 -0
  47. package/dist/commands/tasks.js +205 -0
  48. package/dist/commands/types.js +2 -0
  49. package/dist/commands/undo-redo.js +305 -0
  50. package/dist/commands/unset-model.js +138 -0
  51. package/dist/commands/upgrade.js +42 -0
  52. package/dist/commands/user-command.js +155 -0
  53. package/dist/commands/verbosity.js +125 -0
  54. package/dist/commands/worktree-settings.js +43 -0
  55. package/dist/commands/worktrees.js +410 -0
  56. package/dist/condense-memory.js +33 -0
  57. package/dist/config.js +94 -0
  58. package/dist/context-awareness-plugin.js +363 -0
  59. package/dist/context-awareness-plugin.test.js +124 -0
  60. package/dist/critique-utils.js +95 -0
  61. package/dist/database.js +1310 -0
  62. package/dist/db.js +251 -0
  63. package/dist/db.test.js +138 -0
  64. package/dist/debounce-timeout.js +28 -0
  65. package/dist/debounced-process-flush.js +77 -0
  66. package/dist/discord-bot.js +1008 -0
  67. package/dist/discord-command-registration.js +524 -0
  68. package/dist/discord-urls.js +81 -0
  69. package/dist/discord-utils.js +591 -0
  70. package/dist/discord-utils.test.js +134 -0
  71. package/dist/errors.js +157 -0
  72. package/dist/escape-backticks.test.js +429 -0
  73. package/dist/event-stream-real-capture.e2e.test.js +533 -0
  74. package/dist/eventsource-parser.test.js +327 -0
  75. package/dist/exec-async.js +26 -0
  76. package/dist/external-opencode-sync.js +480 -0
  77. package/dist/format-tables.js +302 -0
  78. package/dist/format-tables.test.js +308 -0
  79. package/dist/forum-sync/config.js +79 -0
  80. package/dist/forum-sync/discord-operations.js +154 -0
  81. package/dist/forum-sync/index.js +5 -0
  82. package/dist/forum-sync/markdown.js +113 -0
  83. package/dist/forum-sync/sync-to-discord.js +417 -0
  84. package/dist/forum-sync/sync-to-files.js +190 -0
  85. package/dist/forum-sync/types.js +53 -0
  86. package/dist/forum-sync/watchers.js +307 -0
  87. package/dist/gateway-proxy-reconnect.e2e.test.js +394 -0
  88. package/dist/gateway-proxy.e2e.test.js +483 -0
  89. package/dist/genai-worker-wrapper.js +111 -0
  90. package/dist/genai-worker.js +311 -0
  91. package/dist/genai.js +232 -0
  92. package/dist/generated/browser.js +17 -0
  93. package/dist/generated/client.js +37 -0
  94. package/dist/generated/commonInputTypes.js +10 -0
  95. package/dist/generated/enums.js +52 -0
  96. package/dist/generated/internal/class.js +49 -0
  97. package/dist/generated/internal/prismaNamespace.js +253 -0
  98. package/dist/generated/internal/prismaNamespaceBrowser.js +223 -0
  99. package/dist/generated/models/bot_api_keys.js +1 -0
  100. package/dist/generated/models/bot_tokens.js +1 -0
  101. package/dist/generated/models/channel_agents.js +1 -0
  102. package/dist/generated/models/channel_directories.js +1 -0
  103. package/dist/generated/models/channel_mention_mode.js +1 -0
  104. package/dist/generated/models/channel_models.js +1 -0
  105. package/dist/generated/models/channel_verbosity.js +1 -0
  106. package/dist/generated/models/channel_worktrees.js +1 -0
  107. package/dist/generated/models/forum_sync_configs.js +1 -0
  108. package/dist/generated/models/global_models.js +1 -0
  109. package/dist/generated/models/ipc_requests.js +1 -0
  110. package/dist/generated/models/part_messages.js +1 -0
  111. package/dist/generated/models/scheduled_tasks.js +1 -0
  112. package/dist/generated/models/session_agents.js +1 -0
  113. package/dist/generated/models/session_events.js +1 -0
  114. package/dist/generated/models/session_models.js +1 -0
  115. package/dist/generated/models/session_start_sources.js +1 -0
  116. package/dist/generated/models/thread_sessions.js +1 -0
  117. package/dist/generated/models/thread_worktrees.js +1 -0
  118. package/dist/generated/models.js +1 -0
  119. package/dist/heap-monitor.js +122 -0
  120. package/dist/hrana-server.js +263 -0
  121. package/dist/hrana-server.test.js +370 -0
  122. package/dist/html-actions.js +123 -0
  123. package/dist/html-actions.test.js +70 -0
  124. package/dist/html-components.js +117 -0
  125. package/dist/html-components.test.js +34 -0
  126. package/dist/image-optimizer-plugin.js +153 -0
  127. package/dist/image-utils.js +112 -0
  128. package/dist/interaction-handler.js +397 -0
  129. package/dist/ipc-polling.js +252 -0
  130. package/dist/ipc-tools-plugin.js +193 -0
  131. package/dist/kimaki-digital-twin.e2e.test.js +161 -0
  132. package/dist/kimaki-opencode-plugin-loading.e2e.test.js +87 -0
  133. package/dist/kimaki-opencode-plugin.js +17 -0
  134. package/dist/kimaki-opencode-plugin.test.js +98 -0
  135. package/dist/limit-heading-depth.js +25 -0
  136. package/dist/limit-heading-depth.test.js +105 -0
  137. package/dist/logger.js +165 -0
  138. package/dist/markdown.js +342 -0
  139. package/dist/markdown.test.js +257 -0
  140. package/dist/message-finish-field.e2e.test.js +165 -0
  141. package/dist/message-formatting.js +413 -0
  142. package/dist/message-formatting.test.js +73 -0
  143. package/dist/message-preprocessing.js +330 -0
  144. package/dist/onboarding-tutorial.js +172 -0
  145. package/dist/onboarding-welcome.js +37 -0
  146. package/dist/openai-realtime.js +224 -0
  147. package/dist/opencode-command-detection.js +65 -0
  148. package/dist/opencode-command-detection.test.js +240 -0
  149. package/dist/opencode-command.js +129 -0
  150. package/dist/opencode-command.test.js +48 -0
  151. package/dist/opencode-interrupt-plugin.js +361 -0
  152. package/dist/opencode-interrupt-plugin.test.js +458 -0
  153. package/dist/opencode.js +861 -0
  154. package/dist/otto/branding.js +22 -0
  155. package/dist/otto/index.js +21 -0
  156. package/dist/parse-permission-rules.test.js +117 -0
  157. package/dist/patch-text-parser.js +97 -0
  158. package/dist/plugin-logger.js +59 -0
  159. package/dist/privacy-sanitizer.js +105 -0
  160. package/dist/queue-advanced-abort.e2e.test.js +293 -0
  161. package/dist/queue-advanced-action-buttons.e2e.test.js +206 -0
  162. package/dist/queue-advanced-e2e-setup.js +786 -0
  163. package/dist/queue-advanced-footer.e2e.test.js +472 -0
  164. package/dist/queue-advanced-model-switch.e2e.test.js +299 -0
  165. package/dist/queue-advanced-permissions-typing.e2e.test.js +180 -0
  166. package/dist/queue-advanced-question.e2e.test.js +261 -0
  167. package/dist/queue-advanced-typing-interrupt.e2e.test.js +114 -0
  168. package/dist/queue-advanced-typing.e2e.test.js +153 -0
  169. package/dist/queue-drain-after-interactive-ui.e2e.test.js +119 -0
  170. package/dist/queue-interrupt-drain.e2e.test.js +135 -0
  171. package/dist/queue-question-select-drain.e2e.test.js +120 -0
  172. package/dist/runtime-idle-sweeper.js +52 -0
  173. package/dist/runtime-lifecycle.e2e.test.js +508 -0
  174. package/dist/sentry.js +23 -0
  175. package/dist/session-handler/agent-utils.js +67 -0
  176. package/dist/session-handler/event-stream-state.js +420 -0
  177. package/dist/session-handler/event-stream-state.test.js +563 -0
  178. package/dist/session-handler/model-utils.js +124 -0
  179. package/dist/session-handler/opencode-session-event-log.js +94 -0
  180. package/dist/session-handler/thread-runtime-state.js +104 -0
  181. package/dist/session-handler/thread-session-runtime.js +3258 -0
  182. package/dist/session-handler.js +9 -0
  183. package/dist/session-search.js +100 -0
  184. package/dist/session-search.test.js +40 -0
  185. package/dist/session-title-rename.test.js +80 -0
  186. package/dist/startup-service.js +153 -0
  187. package/dist/startup-time.e2e.test.js +296 -0
  188. package/dist/store.js +17 -0
  189. package/dist/system-message.js +613 -0
  190. package/dist/system-message.test.js +602 -0
  191. package/dist/task-runner.js +295 -0
  192. package/dist/task-schedule.js +209 -0
  193. package/dist/task-schedule.test.js +71 -0
  194. package/dist/test-utils.js +299 -0
  195. package/dist/thinking-utils.js +35 -0
  196. package/dist/thread-message-queue.e2e.test.js +999 -0
  197. package/dist/tools.js +357 -0
  198. package/dist/undo-redo.e2e.test.js +161 -0
  199. package/dist/unnest-code-blocks.js +146 -0
  200. package/dist/unnest-code-blocks.test.js +673 -0
  201. package/dist/upgrade.js +114 -0
  202. package/dist/utils.js +144 -0
  203. package/dist/voice-attachment.js +34 -0
  204. package/dist/voice-handler.js +646 -0
  205. package/dist/voice-message.e2e.test.js +1021 -0
  206. package/dist/voice.js +447 -0
  207. package/dist/voice.test.js +235 -0
  208. package/dist/wait-session.js +94 -0
  209. package/dist/websockify.js +69 -0
  210. package/dist/worker-types.js +4 -0
  211. package/dist/worktree-lifecycle.e2e.test.js +308 -0
  212. package/dist/worktree-utils.js +3 -0
  213. package/dist/worktrees.js +929 -0
  214. package/dist/worktrees.test.js +189 -0
  215. package/dist/xml.js +92 -0
  216. package/dist/xml.test.js +32 -0
  217. package/package.json +98 -0
  218. package/schema.prisma +295 -0
  219. package/skills/batch/SKILL.md +87 -0
  220. package/skills/critique/SKILL.md +112 -0
  221. package/skills/egaki/SKILL.md +100 -0
  222. package/skills/errore/SKILL.md +647 -0
  223. package/skills/event-sourcing-state/SKILL.md +252 -0
  224. package/skills/gitchamber/SKILL.md +93 -0
  225. package/skills/goke/SKILL.md +644 -0
  226. package/skills/jitter/EDITOR.md +219 -0
  227. package/skills/jitter/EXPORT-INTERNALS.md +309 -0
  228. package/skills/jitter/SKILL.md +158 -0
  229. package/skills/jitter/jitter-clipboard.json +1042 -0
  230. package/skills/jitter/package.json +14 -0
  231. package/skills/jitter/tsconfig.json +15 -0
  232. package/skills/jitter/utils/actions.ts +212 -0
  233. package/skills/jitter/utils/export.ts +114 -0
  234. package/skills/jitter/utils/index.ts +141 -0
  235. package/skills/jitter/utils/snapshot.ts +154 -0
  236. package/skills/jitter/utils/traverse.ts +246 -0
  237. package/skills/jitter/utils/types.ts +279 -0
  238. package/skills/jitter/utils/wait.ts +133 -0
  239. package/skills/lintcn/SKILL.md +873 -0
  240. package/skills/new-skill/SKILL.md +211 -0
  241. package/skills/npm-package/SKILL.md +239 -0
  242. package/skills/playwriter/SKILL.md +35 -0
  243. package/skills/proxyman/SKILL.md +215 -0
  244. package/skills/security-review/SKILL.md +208 -0
  245. package/skills/simplify/SKILL.md +58 -0
  246. package/skills/spiceflow/SKILL.md +14 -0
  247. package/skills/termcast/SKILL.md +945 -0
  248. package/skills/tuistory/SKILL.md +250 -0
  249. package/skills/usecomputer/SKILL.md +264 -0
  250. package/skills/x-articles/SKILL.md +554 -0
  251. package/skills/zele/SKILL.md +112 -0
  252. package/skills/zustand-centralized-state/SKILL.md +1004 -0
  253. package/src/agent-model.e2e.test.ts +976 -0
  254. package/src/ai-tool-to-genai.test.ts +296 -0
  255. package/src/ai-tool-to-genai.ts +283 -0
  256. package/src/ai-tool.ts +39 -0
  257. package/src/anthropic-auth-plugin.test.ts +159 -0
  258. package/src/anthropic-auth-plugin.ts +861 -0
  259. package/src/anthropic-auth-state.ts +282 -0
  260. package/src/bin.ts +111 -0
  261. package/src/channel-management.ts +334 -0
  262. package/src/cli-parsing.test.ts +195 -0
  263. package/src/cli-send-thread.e2e.test.ts +464 -0
  264. package/src/cli.ts +4581 -0
  265. package/src/commands/abort.ts +89 -0
  266. package/src/commands/action-buttons.ts +364 -0
  267. package/src/commands/add-project.ts +149 -0
  268. package/src/commands/agent.ts +473 -0
  269. package/src/commands/ask-question.ts +390 -0
  270. package/src/commands/btw.ts +164 -0
  271. package/src/commands/compact.ts +157 -0
  272. package/src/commands/context-usage.ts +199 -0
  273. package/src/commands/create-new-project.ts +190 -0
  274. package/src/commands/diff.ts +91 -0
  275. package/src/commands/file-upload.ts +389 -0
  276. package/src/commands/fork.ts +321 -0
  277. package/src/commands/gemini-apikey.ts +104 -0
  278. package/src/commands/login.ts +1173 -0
  279. package/src/commands/mcp.ts +307 -0
  280. package/src/commands/memory-snapshot.ts +30 -0
  281. package/src/commands/mention-mode.ts +68 -0
  282. package/src/commands/merge-worktree.ts +223 -0
  283. package/src/commands/model-variant.ts +483 -0
  284. package/src/commands/model.ts +1053 -0
  285. package/src/commands/new-worktree.ts +510 -0
  286. package/src/commands/paginated-select.ts +81 -0
  287. package/src/commands/permissions.ts +397 -0
  288. package/src/commands/queue.ts +271 -0
  289. package/src/commands/remove-project.ts +155 -0
  290. package/src/commands/restart-opencode-server.ts +162 -0
  291. package/src/commands/resume.ts +230 -0
  292. package/src/commands/run-command.ts +123 -0
  293. package/src/commands/screenshare.test.ts +30 -0
  294. package/src/commands/screenshare.ts +366 -0
  295. package/src/commands/session-id.ts +109 -0
  296. package/src/commands/session.ts +227 -0
  297. package/src/commands/share.ts +106 -0
  298. package/src/commands/tasks.ts +293 -0
  299. package/src/commands/types.ts +25 -0
  300. package/src/commands/undo-redo.ts +386 -0
  301. package/src/commands/unset-model.ts +173 -0
  302. package/src/commands/upgrade.ts +52 -0
  303. package/src/commands/user-command.ts +198 -0
  304. package/src/commands/verbosity.ts +173 -0
  305. package/src/commands/worktree-settings.ts +70 -0
  306. package/src/commands/worktrees.ts +552 -0
  307. package/src/condense-memory.ts +36 -0
  308. package/src/config.ts +111 -0
  309. package/src/context-awareness-plugin.test.ts +142 -0
  310. package/src/context-awareness-plugin.ts +510 -0
  311. package/src/critique-utils.ts +139 -0
  312. package/src/database.ts +1876 -0
  313. package/src/db.test.ts +162 -0
  314. package/src/db.ts +286 -0
  315. package/src/debounce-timeout.ts +43 -0
  316. package/src/debounced-process-flush.ts +104 -0
  317. package/src/discord-bot.ts +1330 -0
  318. package/src/discord-command-registration.ts +693 -0
  319. package/src/discord-urls.ts +88 -0
  320. package/src/discord-utils.test.ts +153 -0
  321. package/src/discord-utils.ts +800 -0
  322. package/src/errors.ts +201 -0
  323. package/src/escape-backticks.test.ts +469 -0
  324. package/src/event-stream-real-capture.e2e.test.ts +692 -0
  325. package/src/eventsource-parser.test.ts +351 -0
  326. package/src/exec-async.ts +35 -0
  327. package/src/external-opencode-sync.ts +685 -0
  328. package/src/format-tables.test.ts +335 -0
  329. package/src/format-tables.ts +445 -0
  330. package/src/forum-sync/config.ts +92 -0
  331. package/src/forum-sync/discord-operations.ts +241 -0
  332. package/src/forum-sync/index.ts +9 -0
  333. package/src/forum-sync/markdown.ts +172 -0
  334. package/src/forum-sync/sync-to-discord.ts +595 -0
  335. package/src/forum-sync/sync-to-files.ts +294 -0
  336. package/src/forum-sync/types.ts +175 -0
  337. package/src/forum-sync/watchers.ts +454 -0
  338. package/src/gateway-proxy-reconnect.e2e.test.ts +523 -0
  339. package/src/gateway-proxy.e2e.test.ts +640 -0
  340. package/src/genai-worker-wrapper.ts +164 -0
  341. package/src/genai-worker.ts +386 -0
  342. package/src/genai.ts +321 -0
  343. package/src/generated/browser.ts +114 -0
  344. package/src/generated/client.ts +138 -0
  345. package/src/generated/commonInputTypes.ts +736 -0
  346. package/src/generated/enums.ts +88 -0
  347. package/src/generated/internal/class.ts +384 -0
  348. package/src/generated/internal/prismaNamespace.ts +2386 -0
  349. package/src/generated/internal/prismaNamespaceBrowser.ts +326 -0
  350. package/src/generated/models/bot_api_keys.ts +1288 -0
  351. package/src/generated/models/bot_tokens.ts +1656 -0
  352. package/src/generated/models/channel_agents.ts +1256 -0
  353. package/src/generated/models/channel_directories.ts +1859 -0
  354. package/src/generated/models/channel_mention_mode.ts +1300 -0
  355. package/src/generated/models/channel_models.ts +1288 -0
  356. package/src/generated/models/channel_verbosity.ts +1228 -0
  357. package/src/generated/models/channel_worktrees.ts +1300 -0
  358. package/src/generated/models/forum_sync_configs.ts +1452 -0
  359. package/src/generated/models/global_models.ts +1288 -0
  360. package/src/generated/models/ipc_requests.ts +1485 -0
  361. package/src/generated/models/part_messages.ts +1302 -0
  362. package/src/generated/models/scheduled_tasks.ts +2320 -0
  363. package/src/generated/models/session_agents.ts +1086 -0
  364. package/src/generated/models/session_events.ts +1439 -0
  365. package/src/generated/models/session_models.ts +1114 -0
  366. package/src/generated/models/session_start_sources.ts +1408 -0
  367. package/src/generated/models/thread_sessions.ts +1781 -0
  368. package/src/generated/models/thread_worktrees.ts +1356 -0
  369. package/src/generated/models.ts +30 -0
  370. package/src/heap-monitor.ts +152 -0
  371. package/src/hrana-server.test.ts +434 -0
  372. package/src/hrana-server.ts +314 -0
  373. package/src/html-actions.test.ts +87 -0
  374. package/src/html-actions.ts +174 -0
  375. package/src/html-components.test.ts +38 -0
  376. package/src/html-components.ts +181 -0
  377. package/src/image-optimizer-plugin.ts +194 -0
  378. package/src/image-utils.ts +149 -0
  379. package/src/interaction-handler.ts +576 -0
  380. package/src/ipc-polling.ts +326 -0
  381. package/src/ipc-tools-plugin.ts +236 -0
  382. package/src/kimaki-digital-twin.e2e.test.ts +199 -0
  383. package/src/kimaki-opencode-plugin-loading.e2e.test.ts +109 -0
  384. package/src/kimaki-opencode-plugin.test.ts +108 -0
  385. package/src/kimaki-opencode-plugin.ts +18 -0
  386. package/src/limit-heading-depth.test.ts +116 -0
  387. package/src/limit-heading-depth.ts +26 -0
  388. package/src/logger.ts +208 -0
  389. package/src/markdown.test.ts +308 -0
  390. package/src/markdown.ts +410 -0
  391. package/src/message-finish-field.e2e.test.ts +192 -0
  392. package/src/message-formatting.test.ts +81 -0
  393. package/src/message-formatting.ts +533 -0
  394. package/src/message-preprocessing.ts +455 -0
  395. package/src/onboarding-tutorial.ts +176 -0
  396. package/src/onboarding-welcome.ts +49 -0
  397. package/src/openai-realtime.ts +358 -0
  398. package/src/opencode-command-detection.test.ts +307 -0
  399. package/src/opencode-command-detection.ts +76 -0
  400. package/src/opencode-command.test.ts +70 -0
  401. package/src/opencode-command.ts +188 -0
  402. package/src/opencode-interrupt-plugin.test.ts +677 -0
  403. package/src/opencode-interrupt-plugin.ts +477 -0
  404. package/src/opencode.ts +1110 -0
  405. package/src/otto/branding.ts +23 -0
  406. package/src/otto/index.ts +22 -0
  407. package/src/parse-permission-rules.test.ts +127 -0
  408. package/src/patch-text-parser.ts +107 -0
  409. package/src/plugin-logger.ts +68 -0
  410. package/src/privacy-sanitizer.ts +142 -0
  411. package/src/queue-advanced-abort.e2e.test.ts +382 -0
  412. package/src/queue-advanced-action-buttons.e2e.test.ts +268 -0
  413. package/src/queue-advanced-e2e-setup.ts +873 -0
  414. package/src/queue-advanced-footer.e2e.test.ts +576 -0
  415. package/src/queue-advanced-model-switch.e2e.test.ts +383 -0
  416. package/src/queue-advanced-permissions-typing.e2e.test.ts +245 -0
  417. package/src/queue-advanced-question.e2e.test.ts +316 -0
  418. package/src/queue-advanced-typing-interrupt.e2e.test.ts +146 -0
  419. package/src/queue-advanced-typing.e2e.test.ts +199 -0
  420. package/src/queue-drain-after-interactive-ui.e2e.test.ts +151 -0
  421. package/src/queue-interrupt-drain.e2e.test.ts +166 -0
  422. package/src/queue-question-select-drain.e2e.test.ts +152 -0
  423. package/src/runtime-idle-sweeper.ts +76 -0
  424. package/src/runtime-lifecycle.e2e.test.ts +641 -0
  425. package/src/schema.sql +173 -0
  426. package/src/sentry.ts +26 -0
  427. package/src/session-handler/agent-utils.ts +97 -0
  428. package/src/session-handler/event-stream-fixtures/real-session-action-buttons.jsonl +45 -0
  429. package/src/session-handler/event-stream-fixtures/real-session-footer-suppressed-on-pre-idle-interrupt.jsonl +40 -0
  430. package/src/session-handler/event-stream-fixtures/real-session-permission-external-file.jsonl +23 -0
  431. package/src/session-handler/event-stream-fixtures/real-session-task-normal.jsonl +22 -0
  432. package/src/session-handler/event-stream-fixtures/real-session-task-three-parallel-sleeps.jsonl +277 -0
  433. package/src/session-handler/event-stream-fixtures/real-session-task-user-interruption.jsonl +46 -0
  434. package/src/session-handler/event-stream-fixtures/session-abort-after-idle-race.jsonl +21 -0
  435. package/src/session-handler/event-stream-fixtures/session-concurrent-messages-serialized.jsonl +56 -0
  436. package/src/session-handler/event-stream-fixtures/session-explicit-abort.jsonl +44 -0
  437. package/src/session-handler/event-stream-fixtures/session-normal-completion.jsonl +29 -0
  438. package/src/session-handler/event-stream-fixtures/session-tool-call-noisy-stream.jsonl +29 -0
  439. package/src/session-handler/event-stream-fixtures/session-two-completions-same-session.jsonl +50 -0
  440. package/src/session-handler/event-stream-fixtures/session-user-interruption.jsonl +59 -0
  441. package/src/session-handler/event-stream-fixtures/session-voice-queued-followup.jsonl +52 -0
  442. package/src/session-handler/event-stream-state.test.ts +645 -0
  443. package/src/session-handler/event-stream-state.ts +608 -0
  444. package/src/session-handler/model-utils.ts +183 -0
  445. package/src/session-handler/opencode-session-event-log.ts +130 -0
  446. package/src/session-handler/thread-runtime-state.ts +212 -0
  447. package/src/session-handler/thread-session-runtime.ts +4281 -0
  448. package/src/session-handler.ts +15 -0
  449. package/src/session-search.test.ts +50 -0
  450. package/src/session-search.ts +148 -0
  451. package/src/session-title-rename.test.ts +112 -0
  452. package/src/startup-service.ts +200 -0
  453. package/src/startup-time.e2e.test.ts +373 -0
  454. package/src/store.ts +122 -0
  455. package/src/system-message.test.ts +612 -0
  456. package/src/system-message.ts +723 -0
  457. package/src/task-runner.ts +421 -0
  458. package/src/task-schedule.test.ts +84 -0
  459. package/src/task-schedule.ts +311 -0
  460. package/src/test-utils.ts +435 -0
  461. package/src/thinking-utils.ts +61 -0
  462. package/src/thread-message-queue.e2e.test.ts +1219 -0
  463. package/src/tools.ts +430 -0
  464. package/src/undici.d.ts +12 -0
  465. package/src/undo-redo.e2e.test.ts +209 -0
  466. package/src/unnest-code-blocks.test.ts +713 -0
  467. package/src/unnest-code-blocks.ts +185 -0
  468. package/src/upgrade.ts +127 -0
  469. package/src/utils.ts +212 -0
  470. package/src/voice-attachment.ts +51 -0
  471. package/src/voice-handler.ts +908 -0
  472. package/src/voice-message.e2e.test.ts +1255 -0
  473. package/src/voice.test.ts +281 -0
  474. package/src/voice.ts +627 -0
  475. package/src/wait-session.ts +147 -0
  476. package/src/websockify.ts +101 -0
  477. package/src/worker-types.ts +64 -0
  478. package/src/worktree-lifecycle.e2e.test.ts +391 -0
  479. package/src/worktree-utils.ts +4 -0
  480. package/src/worktrees.test.ts +223 -0
  481. package/src/worktrees.ts +1294 -0
  482. package/src/xml.test.ts +38 -0
  483. package/src/xml.ts +121 -0
@@ -0,0 +1,576 @@
1
+ // Discord slash command and interaction handler.
2
+ // Processes all slash commands (/session, /resume, /fork, /model, /abort, etc.)
3
+ // and manages autocomplete, select menu interactions for the bot.
4
+
5
+ import {
6
+ Events,
7
+ MessageFlags,
8
+ type Client,
9
+ type Interaction,
10
+ } from 'discord.js'
11
+ import {
12
+ handleSessionCommand,
13
+ handleSessionAutocomplete,
14
+ } from './commands/session.js'
15
+ import {
16
+ handleNewWorktreeCommand,
17
+ handleNewWorktreeAutocomplete,
18
+ } from './commands/new-worktree.js'
19
+ import {
20
+ handleMergeWorktreeCommand,
21
+ handleMergeWorktreeAutocomplete,
22
+ } from './commands/merge-worktree.js'
23
+ import { handleToggleWorktreesCommand } from './commands/worktree-settings.js'
24
+ import { handleWorktreesCommand } from './commands/worktrees.js'
25
+ import { handleTasksCommand } from './commands/tasks.js'
26
+
27
+ import {
28
+ handleResumeCommand,
29
+ handleResumeAutocomplete,
30
+ } from './commands/resume.js'
31
+ import {
32
+ handleAddProjectCommand,
33
+ handleAddProjectAutocomplete,
34
+ } from './commands/add-project.js'
35
+ import {
36
+ handleRemoveProjectCommand,
37
+ handleRemoveProjectAutocomplete,
38
+ } from './commands/remove-project.js'
39
+ import { handleCreateNewProjectCommand } from './commands/create-new-project.js'
40
+ import { handlePermissionButton } from './commands/permissions.js'
41
+ import { handleAbortCommand } from './commands/abort.js'
42
+ import { handleCompactCommand } from './commands/compact.js'
43
+ import { handleShareCommand } from './commands/share.js'
44
+ import { handleDiffCommand } from './commands/diff.js'
45
+ import { handleForkCommand, handleForkSelectMenu } from './commands/fork.js'
46
+ import { handleBtwCommand } from './commands/btw.js'
47
+ import {
48
+ handleModelCommand,
49
+ handleProviderSelectMenu,
50
+ handleModelSelectMenu,
51
+ handleModelScopeSelectMenu,
52
+ } from './commands/model.js'
53
+ import { handleUnsetModelCommand } from './commands/unset-model.js'
54
+ import {
55
+ handleLoginCommand,
56
+ handleLoginSelect,
57
+ handleLoginTextButton,
58
+ handleLoginTextModalSubmit,
59
+ handleLoginApiKeyButton,
60
+ handleOAuthCodeButton,
61
+ handleOAuthCodeModalSubmit,
62
+ handleApiKeyModalSubmit,
63
+ } from './commands/login.js'
64
+ import {
65
+ handleTranscriptionApiKeyButton,
66
+ handleTranscriptionApiKeyCommand,
67
+ handleTranscriptionApiKeyModalSubmit,
68
+ } from './commands/gemini-apikey.js'
69
+ import {
70
+ handleAgentCommand,
71
+ handleAgentSelectMenu,
72
+ handleQuickAgentCommand,
73
+ } from './commands/agent.js'
74
+ import { handleAskQuestionSelectMenu } from './commands/ask-question.js'
75
+ import {
76
+ handleFileUploadButton,
77
+ handleFileUploadModalSubmit,
78
+ } from './commands/file-upload.js'
79
+ import { handleActionButton } from './commands/action-buttons.js'
80
+ import { handleHtmlActionButton } from './html-actions.js'
81
+ import {
82
+ handleQueueCommand,
83
+ handleClearQueueCommand,
84
+ handleQueueCommandCommand,
85
+ handleQueueCommandAutocomplete,
86
+ } from './commands/queue.js'
87
+ import { handleUndoCommand, handleRedoCommand } from './commands/undo-redo.js'
88
+ import { handleUserCommand } from './commands/user-command.js'
89
+ import {
90
+ handleVerbosityCommand,
91
+ handleVerbositySelectMenu,
92
+ } from './commands/verbosity.js'
93
+ import { handleRestartOpencodeServerCommand } from './commands/restart-opencode-server.js'
94
+ import { handleRunCommand } from './commands/run-command.js'
95
+ import { handleContextUsageCommand } from './commands/context-usage.js'
96
+ import { handleSessionIdCommand } from './commands/session-id.js'
97
+
98
+ import { handleUpgradeAndRestartCommand } from './commands/upgrade.js'
99
+ import { handleMcpCommand, handleMcpSelectMenu } from './commands/mcp.js'
100
+ import {
101
+ handleScreenshareCommand,
102
+ handleScreenshareStopCommand,
103
+ } from './commands/screenshare.js'
104
+ import { handleModelVariantSelectMenu } from './commands/model.js'
105
+ import {
106
+ handleModelVariantCommand,
107
+ handleVariantQuickSelectMenu,
108
+ handleVariantScopeSelectMenu,
109
+ } from './commands/model-variant.js'
110
+ import { hasKimakiBotPermission } from './discord-utils.js'
111
+ import { createLogger, LogPrefix } from './logger.js'
112
+ import { notifyError } from './sentry.js'
113
+
114
+ const interactionLogger = createLogger(LogPrefix.INTERACTION)
115
+
116
+ export function registerInteractionHandler({
117
+ discordClient,
118
+ appId,
119
+ }: {
120
+ discordClient: Client
121
+ appId: string
122
+ }) {
123
+ interactionLogger.log('[REGISTER] Interaction handler registered')
124
+
125
+ discordClient.on(
126
+ Events.InteractionCreate,
127
+ async (interaction: Interaction) => {
128
+ try {
129
+ interactionLogger.log(
130
+ `[INTERACTION] Received: ${interaction.type} - ${
131
+ interaction.isChatInputCommand()
132
+ ? interaction.commandName
133
+ : interaction.isAutocomplete()
134
+ ? `autocomplete:${interaction.commandName}`
135
+ : 'other'
136
+ }`,
137
+ )
138
+
139
+ if (interaction.isAutocomplete()) {
140
+ switch (interaction.commandName) {
141
+ case 'new-session':
142
+ await handleSessionAutocomplete({ interaction, appId })
143
+ return
144
+
145
+ case 'resume':
146
+ await handleResumeAutocomplete({ interaction, appId })
147
+ return
148
+
149
+ case 'add-project':
150
+ await handleAddProjectAutocomplete({ interaction, appId })
151
+ return
152
+
153
+ case 'remove-project':
154
+ await handleRemoveProjectAutocomplete({ interaction, appId })
155
+ return
156
+
157
+ case 'queue-command':
158
+ await handleQueueCommandAutocomplete({ interaction, appId })
159
+ return
160
+
161
+ case 'new-worktree':
162
+ await handleNewWorktreeAutocomplete({ interaction, appId })
163
+ return
164
+
165
+ case 'merge-worktree':
166
+ await handleMergeWorktreeAutocomplete({ interaction, appId })
167
+ return
168
+
169
+ default:
170
+ await interaction.respond([])
171
+ return
172
+ }
173
+ }
174
+
175
+ if (interaction.isChatInputCommand()) {
176
+ interactionLogger.log(
177
+ `[COMMAND] Processing: ${interaction.commandName}`,
178
+ )
179
+
180
+ if (!hasKimakiBotPermission(interaction.member, interaction.guild)) {
181
+ await interaction.reply({
182
+ content: `You don't have permission to use this command.\nTo use Kimaki, ask a server admin to give you the **Kimaki** role.`,
183
+ flags: MessageFlags.Ephemeral,
184
+ })
185
+ return
186
+ }
187
+
188
+ switch (interaction.commandName) {
189
+ case 'new-session':
190
+ await handleSessionCommand({ command: interaction, appId })
191
+ return
192
+
193
+ case 'new-worktree':
194
+ await handleNewWorktreeCommand({ command: interaction, appId })
195
+ return
196
+
197
+ case 'merge-worktree':
198
+ await handleMergeWorktreeCommand({ command: interaction, appId })
199
+ return
200
+
201
+ case 'toggle-worktrees':
202
+ await handleToggleWorktreesCommand({
203
+ command: interaction,
204
+ appId,
205
+ })
206
+ return
207
+
208
+ case 'worktrees':
209
+ await handleWorktreesCommand({
210
+ command: interaction,
211
+ appId,
212
+ })
213
+ return
214
+
215
+ case 'tasks':
216
+ await handleTasksCommand({
217
+ command: interaction,
218
+ appId,
219
+ })
220
+ return
221
+
222
+
223
+ case 'resume':
224
+ await handleResumeCommand({ command: interaction, appId })
225
+ return
226
+
227
+ case 'add-project':
228
+ await handleAddProjectCommand({ command: interaction, appId })
229
+ return
230
+
231
+ case 'remove-project':
232
+ await handleRemoveProjectCommand({ command: interaction, appId })
233
+ return
234
+
235
+ case 'create-new-project':
236
+ await handleCreateNewProjectCommand({
237
+ command: interaction,
238
+ appId,
239
+ })
240
+ return
241
+
242
+ case 'abort':
243
+ await handleAbortCommand({ command: interaction, appId })
244
+ return
245
+
246
+ case 'compact':
247
+ await handleCompactCommand({ command: interaction, appId })
248
+ return
249
+
250
+ case 'share':
251
+ await handleShareCommand({ command: interaction, appId })
252
+ return
253
+
254
+ case 'diff':
255
+ await handleDiffCommand({ command: interaction, appId })
256
+ return
257
+
258
+ case 'fork':
259
+ await handleForkCommand(interaction)
260
+ return
261
+
262
+ case 'btw':
263
+ await handleBtwCommand({ command: interaction, appId })
264
+ return
265
+
266
+ case 'model':
267
+ await handleModelCommand({ interaction, appId })
268
+ return
269
+
270
+ case 'model-variant':
271
+ await handleModelVariantCommand({ interaction, appId })
272
+ return
273
+
274
+ case 'unset-model-override':
275
+ await handleUnsetModelCommand({ interaction, appId })
276
+ return
277
+
278
+ case 'login':
279
+ await handleLoginCommand({ interaction, appId })
280
+ return
281
+
282
+ case 'agent':
283
+ await handleAgentCommand({ interaction, appId })
284
+ return
285
+
286
+ case 'queue':
287
+ await handleQueueCommand({ command: interaction, appId })
288
+ return
289
+
290
+ case 'clear-queue':
291
+ await handleClearQueueCommand({ command: interaction, appId })
292
+ return
293
+
294
+ case 'queue-command':
295
+ await handleQueueCommandCommand({ command: interaction, appId })
296
+ return
297
+
298
+ case 'undo':
299
+ await handleUndoCommand({ command: interaction, appId })
300
+ return
301
+
302
+ case 'redo':
303
+ await handleRedoCommand({ command: interaction, appId })
304
+ return
305
+
306
+ case 'verbosity':
307
+ await handleVerbosityCommand({ command: interaction, appId })
308
+ return
309
+
310
+ case 'restart-opencode-server':
311
+ await handleRestartOpencodeServerCommand({
312
+ command: interaction,
313
+ appId,
314
+ })
315
+ return
316
+
317
+ case 'run-shell-command':
318
+ await handleRunCommand({ command: interaction, appId })
319
+ return
320
+
321
+ case 'context-usage':
322
+ await handleContextUsageCommand({ command: interaction, appId })
323
+ return
324
+
325
+ case 'session-id':
326
+ await handleSessionIdCommand({ command: interaction, appId })
327
+ return
328
+
329
+
330
+
331
+ case 'upgrade-and-restart':
332
+ await handleUpgradeAndRestartCommand({
333
+ command: interaction,
334
+ appId,
335
+ })
336
+ return
337
+
338
+ case 'transcription-key':
339
+ await handleTranscriptionApiKeyCommand({
340
+ interaction,
341
+ appId,
342
+ })
343
+ return
344
+
345
+ case 'mcp':
346
+ await handleMcpCommand({ command: interaction, appId })
347
+ return
348
+
349
+ case 'screenshare':
350
+ await handleScreenshareCommand({ command: interaction, appId })
351
+ return
352
+
353
+ case 'screenshare-stop':
354
+ await handleScreenshareStopCommand({
355
+ command: interaction,
356
+ appId,
357
+ })
358
+ return
359
+ }
360
+
361
+ // Handle quick agent commands (ending with -agent suffix, but not the base /agent command)
362
+ if (
363
+ interaction.commandName.endsWith('-agent') &&
364
+ interaction.commandName !== 'agent'
365
+ ) {
366
+ await handleQuickAgentCommand({ command: interaction, appId })
367
+ return
368
+ }
369
+
370
+ // Handle user-defined commands (ending with -cmd, -skill, or -mcp-prompt suffix)
371
+ if (
372
+ interaction.commandName.endsWith('-cmd') ||
373
+ interaction.commandName.endsWith('-skill') ||
374
+ interaction.commandName.endsWith('-mcp-prompt')
375
+ ) {
376
+ await handleUserCommand({ command: interaction, appId })
377
+ return
378
+ }
379
+ return
380
+ }
381
+
382
+ if (interaction.isButton()) {
383
+ if (!hasKimakiBotPermission(interaction.member, interaction.guild)) {
384
+ await interaction.reply({
385
+ content: `You don't have permission to use this.\nTo use Kimaki, ask a server admin to give you the **Kimaki** role.`,
386
+ flags: MessageFlags.Ephemeral,
387
+ })
388
+ return
389
+ }
390
+
391
+ const customId = interaction.customId
392
+
393
+ if (customId.startsWith('transcription_apikey:')) {
394
+ await handleTranscriptionApiKeyButton(interaction)
395
+ return
396
+ }
397
+
398
+ if (
399
+ customId.startsWith('permission_once:') ||
400
+ customId.startsWith('permission_always:') ||
401
+ customId.startsWith('permission_reject:')
402
+ ) {
403
+ await handlePermissionButton(interaction)
404
+ return
405
+ }
406
+
407
+ if (customId.startsWith('file_upload_btn:')) {
408
+ await handleFileUploadButton(interaction)
409
+ return
410
+ }
411
+
412
+ if (customId.startsWith('login_text_btn:')) {
413
+ await handleLoginTextButton(interaction)
414
+ return
415
+ }
416
+
417
+ if (customId.startsWith('login_apikey_btn:')) {
418
+ await handleLoginApiKeyButton(interaction)
419
+ return
420
+ }
421
+
422
+ if (customId.startsWith('login_oauth_code_btn:')) {
423
+ await handleOAuthCodeButton(interaction)
424
+ return
425
+ }
426
+
427
+ if (customId.startsWith('action_button:')) {
428
+ await handleActionButton(interaction)
429
+ return
430
+ }
431
+
432
+ if (customId.startsWith('html_action:')) {
433
+ await handleHtmlActionButton(interaction)
434
+ return
435
+ }
436
+
437
+ return
438
+ }
439
+
440
+ if (interaction.isStringSelectMenu()) {
441
+ if (!hasKimakiBotPermission(interaction.member, interaction.guild)) {
442
+ await interaction.reply({
443
+ content: `You don't have permission to use this.\nTo use Kimaki, ask a server admin to give you the **Kimaki** role.`,
444
+ flags: MessageFlags.Ephemeral,
445
+ })
446
+ return
447
+ }
448
+
449
+ const customId = interaction.customId
450
+
451
+ if (customId.startsWith('fork_select:')) {
452
+ await handleForkSelectMenu(interaction)
453
+ return
454
+ }
455
+
456
+ if (customId.startsWith('model_provider:')) {
457
+ await handleProviderSelectMenu(interaction)
458
+ return
459
+ }
460
+
461
+ if (customId.startsWith('model_select:')) {
462
+ await handleModelSelectMenu(interaction)
463
+ return
464
+ }
465
+
466
+ if (customId.startsWith('model_scope:')) {
467
+ await handleModelScopeSelectMenu(interaction)
468
+ return
469
+ }
470
+
471
+ if (customId.startsWith('model_variant:')) {
472
+ await handleModelVariantSelectMenu(interaction)
473
+ return
474
+ }
475
+
476
+ if (customId.startsWith('variant_quick:')) {
477
+ await handleVariantQuickSelectMenu(interaction)
478
+ return
479
+ }
480
+
481
+ if (customId.startsWith('variant_scope:')) {
482
+ await handleVariantScopeSelectMenu(interaction)
483
+ return
484
+ }
485
+
486
+ if (customId.startsWith('agent_select:')) {
487
+ await handleAgentSelectMenu(interaction)
488
+ return
489
+ }
490
+
491
+ if (customId.startsWith('verbosity_select:')) {
492
+ await handleVerbositySelectMenu(interaction)
493
+ return
494
+ }
495
+
496
+ if (customId.startsWith('ask_question:')) {
497
+ await handleAskQuestionSelectMenu(interaction)
498
+ return
499
+ }
500
+
501
+ if (customId.startsWith('mcp_toggle:')) {
502
+ await handleMcpSelectMenu(interaction)
503
+ return
504
+ }
505
+
506
+ if (customId.startsWith('login_select:')) {
507
+ await handleLoginSelect(interaction)
508
+ return
509
+ }
510
+ return
511
+ }
512
+
513
+ if (interaction.isModalSubmit()) {
514
+ if (!hasKimakiBotPermission(interaction.member, interaction.guild)) {
515
+ await interaction.reply({
516
+ content: `You don't have permission to use this.\nTo use Kimaki, ask a server admin to give you the **Kimaki** role.`,
517
+ flags: MessageFlags.Ephemeral,
518
+ })
519
+ return
520
+ }
521
+
522
+ const customId = interaction.customId
523
+
524
+ if (customId.startsWith('login_apikey:')) {
525
+ await handleApiKeyModalSubmit(interaction)
526
+ return
527
+ }
528
+
529
+ if (customId.startsWith('login_text:')) {
530
+ await handleLoginTextModalSubmit(interaction)
531
+ return
532
+ }
533
+
534
+ if (customId.startsWith('login_oauth_code:')) {
535
+ await handleOAuthCodeModalSubmit(interaction)
536
+ return
537
+ }
538
+
539
+ if (customId.startsWith('transcription_apikey_modal:')) {
540
+ await handleTranscriptionApiKeyModalSubmit(interaction)
541
+ return
542
+ }
543
+
544
+ if (customId.startsWith('file_upload_modal:')) {
545
+ await handleFileUploadModalSubmit(interaction)
546
+ return
547
+ }
548
+ return
549
+ }
550
+ } catch (error) {
551
+ interactionLogger.error(
552
+ '[INTERACTION] Error handling interaction:',
553
+ error,
554
+ )
555
+ void notifyError(error, 'Interaction handler error')
556
+ try {
557
+ if (
558
+ interaction.isRepliable() &&
559
+ !interaction.replied &&
560
+ !interaction.deferred
561
+ ) {
562
+ await interaction.reply({
563
+ content: 'An error occurred processing this command.',
564
+ flags: MessageFlags.Ephemeral,
565
+ })
566
+ }
567
+ } catch (replyError) {
568
+ interactionLogger.error(
569
+ '[INTERACTION] Failed to send error reply:',
570
+ replyError,
571
+ )
572
+ }
573
+ }
574
+ },
575
+ )
576
+ }