nastech-tui 0.0.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 (424) hide show
  1. package/.prettierrc +11 -0
  2. package/README.md +346 -0
  3. package/eslint.config.mjs +111 -0
  4. package/package.json +51 -0
  5. package/packages/nastech-ink/ambient.d.ts +83 -0
  6. package/packages/nastech-ink/index.d.ts +40 -0
  7. package/packages/nastech-ink/index.js +1 -0
  8. package/packages/nastech-ink/nastech-ink/ambient.d.ts +83 -0
  9. package/packages/nastech-ink/nastech-ink/index.d.ts +40 -0
  10. package/packages/nastech-ink/nastech-ink/index.js +1 -0
  11. package/packages/nastech-ink/nastech-ink/package.json +54 -0
  12. package/packages/nastech-ink/nastech-ink/src/bootstrap/state.ts +9 -0
  13. package/packages/nastech-ink/nastech-ink/src/entry-exports.ts +32 -0
  14. package/packages/nastech-ink/nastech-ink/src/hooks/use-stderr.ts +15 -0
  15. package/packages/nastech-ink/nastech-ink/src/hooks/use-stdout.ts +15 -0
  16. package/packages/nastech-ink/nastech-ink/src/ink/Ansi.tsx +435 -0
  17. package/packages/nastech-ink/nastech-ink/src/ink/app-mouse.test.ts +123 -0
  18. package/packages/nastech-ink/nastech-ink/src/ink/bidi.ts +145 -0
  19. package/packages/nastech-ink/nastech-ink/src/ink/cache-eviction.ts +45 -0
  20. package/packages/nastech-ink/nastech-ink/src/ink/clearTerminal.ts +68 -0
  21. package/packages/nastech-ink/nastech-ink/src/ink/colorize.test.ts +60 -0
  22. package/packages/nastech-ink/nastech-ink/src/ink/colorize.ts +277 -0
  23. package/packages/nastech-ink/nastech-ink/src/ink/components/AlternateScreen.tsx +133 -0
  24. package/packages/nastech-ink/nastech-ink/src/ink/components/App.tsx +830 -0
  25. package/packages/nastech-ink/nastech-ink/src/ink/components/AppContext.ts +20 -0
  26. package/packages/nastech-ink/nastech-ink/src/ink/components/Box.tsx +294 -0
  27. package/packages/nastech-ink/nastech-ink/src/ink/components/Button.tsx +236 -0
  28. package/packages/nastech-ink/nastech-ink/src/ink/components/ClockContext.tsx +133 -0
  29. package/packages/nastech-ink/nastech-ink/src/ink/components/CursorAdvanceContext.ts +35 -0
  30. package/packages/nastech-ink/nastech-ink/src/ink/components/CursorDeclarationContext.ts +28 -0
  31. package/packages/nastech-ink/nastech-ink/src/ink/components/ErrorOverview.tsx +130 -0
  32. package/packages/nastech-ink/nastech-ink/src/ink/components/Link.tsx +38 -0
  33. package/packages/nastech-ink/nastech-ink/src/ink/components/Newline.tsx +43 -0
  34. package/packages/nastech-ink/nastech-ink/src/ink/components/NoSelect.tsx +73 -0
  35. package/packages/nastech-ink/nastech-ink/src/ink/components/RawAnsi.tsx +61 -0
  36. package/packages/nastech-ink/nastech-ink/src/ink/components/ScrollBox.tsx +290 -0
  37. package/packages/nastech-ink/nastech-ink/src/ink/components/Spacer.tsx +23 -0
  38. package/packages/nastech-ink/nastech-ink/src/ink/components/StdinContext.ts +25 -0
  39. package/packages/nastech-ink/nastech-ink/src/ink/components/TerminalFocusContext.tsx +63 -0
  40. package/packages/nastech-ink/nastech-ink/src/ink/components/TerminalSizeContext.tsx +7 -0
  41. package/packages/nastech-ink/nastech-ink/src/ink/components/Text.test.ts +38 -0
  42. package/packages/nastech-ink/nastech-ink/src/ink/components/Text.tsx +336 -0
  43. package/packages/nastech-ink/nastech-ink/src/ink/constants.ts +6 -0
  44. package/packages/nastech-ink/nastech-ink/src/ink/cursor.ts +5 -0
  45. package/packages/nastech-ink/nastech-ink/src/ink/devtools.ts +2 -0
  46. package/packages/nastech-ink/nastech-ink/src/ink/dom.ts +495 -0
  47. package/packages/nastech-ink/nastech-ink/src/ink/events/click-event.ts +38 -0
  48. package/packages/nastech-ink/nastech-ink/src/ink/events/cmd-shortcuts.test.ts +65 -0
  49. package/packages/nastech-ink/nastech-ink/src/ink/events/dispatcher.ts +242 -0
  50. package/packages/nastech-ink/nastech-ink/src/ink/events/emitter.ts +40 -0
  51. package/packages/nastech-ink/nastech-ink/src/ink/events/event-handlers.ts +84 -0
  52. package/packages/nastech-ink/nastech-ink/src/ink/events/event.ts +11 -0
  53. package/packages/nastech-ink/nastech-ink/src/ink/events/focus-event.ts +18 -0
  54. package/packages/nastech-ink/nastech-ink/src/ink/events/input-event.ts +176 -0
  55. package/packages/nastech-ink/nastech-ink/src/ink/events/keyboard-event.ts +57 -0
  56. package/packages/nastech-ink/nastech-ink/src/ink/events/mouse-event.ts +18 -0
  57. package/packages/nastech-ink/nastech-ink/src/ink/events/paste-event.ts +10 -0
  58. package/packages/nastech-ink/nastech-ink/src/ink/events/resize-event.ts +12 -0
  59. package/packages/nastech-ink/nastech-ink/src/ink/events/terminal-event.ts +107 -0
  60. package/packages/nastech-ink/nastech-ink/src/ink/events/terminal-focus-event.ts +19 -0
  61. package/packages/nastech-ink/nastech-ink/src/ink/focus.ts +219 -0
  62. package/packages/nastech-ink/nastech-ink/src/ink/frame.ts +124 -0
  63. package/packages/nastech-ink/nastech-ink/src/ink/get-max-width.ts +27 -0
  64. package/packages/nastech-ink/nastech-ink/src/ink/global.d.ts +1 -0
  65. package/packages/nastech-ink/nastech-ink/src/ink/hit-test.test.ts +38 -0
  66. package/packages/nastech-ink/nastech-ink/src/ink/hit-test.ts +224 -0
  67. package/packages/nastech-ink/nastech-ink/src/ink/hooks/use-animation-frame.ts +62 -0
  68. package/packages/nastech-ink/nastech-ink/src/ink/hooks/use-app.ts +9 -0
  69. package/packages/nastech-ink/nastech-ink/src/ink/hooks/use-cursor-advance.ts +33 -0
  70. package/packages/nastech-ink/nastech-ink/src/ink/hooks/use-declared-cursor.ts +75 -0
  71. package/packages/nastech-ink/nastech-ink/src/ink/hooks/use-external-process.ts +27 -0
  72. package/packages/nastech-ink/nastech-ink/src/ink/hooks/use-input.ts +95 -0
  73. package/packages/nastech-ink/nastech-ink/src/ink/hooks/use-interval.ts +71 -0
  74. package/packages/nastech-ink/package.json +57 -0
  75. package/packages/nastech-ink/src/bootstrap/state.ts +9 -0
  76. package/packages/nastech-ink/src/entry-exports.ts +32 -0
  77. package/packages/nastech-ink/src/hooks/use-stderr.ts +15 -0
  78. package/packages/nastech-ink/src/hooks/use-stdout.ts +15 -0
  79. package/packages/nastech-ink/src/ink/Ansi.tsx +435 -0
  80. package/packages/nastech-ink/src/ink/app-mouse.test.ts +123 -0
  81. package/packages/nastech-ink/src/ink/app-rawmode-mouse.test.ts +91 -0
  82. package/packages/nastech-ink/src/ink/bidi.ts +145 -0
  83. package/packages/nastech-ink/src/ink/cache-eviction.ts +45 -0
  84. package/packages/nastech-ink/src/ink/clearTerminal.ts +68 -0
  85. package/packages/nastech-ink/src/ink/colorize.test.ts +60 -0
  86. package/packages/nastech-ink/src/ink/colorize.ts +277 -0
  87. package/packages/nastech-ink/src/ink/components/AlternateScreen.tsx +133 -0
  88. package/packages/nastech-ink/src/ink/components/App.tsx +855 -0
  89. package/packages/nastech-ink/src/ink/components/AppContext.ts +20 -0
  90. package/packages/nastech-ink/src/ink/components/Box.tsx +294 -0
  91. package/packages/nastech-ink/src/ink/components/Button.tsx +236 -0
  92. package/packages/nastech-ink/src/ink/components/ClockContext.tsx +133 -0
  93. package/packages/nastech-ink/src/ink/components/CursorAdvanceContext.ts +35 -0
  94. package/packages/nastech-ink/src/ink/components/CursorDeclarationContext.ts +28 -0
  95. package/packages/nastech-ink/src/ink/components/ErrorOverview.tsx +130 -0
  96. package/packages/nastech-ink/src/ink/components/Link.tsx +38 -0
  97. package/packages/nastech-ink/src/ink/components/Newline.tsx +43 -0
  98. package/packages/nastech-ink/src/ink/components/NoSelect.tsx +73 -0
  99. package/packages/nastech-ink/src/ink/components/RawAnsi.tsx +61 -0
  100. package/packages/nastech-ink/src/ink/components/ScrollBox.tsx +290 -0
  101. package/packages/nastech-ink/src/ink/components/Spacer.tsx +23 -0
  102. package/packages/nastech-ink/src/ink/components/StdinContext.ts +25 -0
  103. package/packages/nastech-ink/src/ink/components/TerminalFocusContext.tsx +63 -0
  104. package/packages/nastech-ink/src/ink/components/TerminalSizeContext.tsx +7 -0
  105. package/packages/nastech-ink/src/ink/components/Text.test.ts +38 -0
  106. package/packages/nastech-ink/src/ink/components/Text.tsx +336 -0
  107. package/packages/nastech-ink/src/ink/constants.ts +6 -0
  108. package/packages/nastech-ink/src/ink/cursor.ts +5 -0
  109. package/packages/nastech-ink/src/ink/devtools.ts +2 -0
  110. package/packages/nastech-ink/src/ink/dom.ts +495 -0
  111. package/packages/nastech-ink/src/ink/events/click-event.ts +38 -0
  112. package/packages/nastech-ink/src/ink/events/cmd-shortcuts.test.ts +65 -0
  113. package/packages/nastech-ink/src/ink/events/dispatcher.ts +242 -0
  114. package/packages/nastech-ink/src/ink/events/emitter.ts +40 -0
  115. package/packages/nastech-ink/src/ink/events/event-handlers.ts +84 -0
  116. package/packages/nastech-ink/src/ink/events/event.ts +11 -0
  117. package/packages/nastech-ink/src/ink/events/focus-event.ts +18 -0
  118. package/packages/nastech-ink/src/ink/events/input-event.ts +176 -0
  119. package/packages/nastech-ink/src/ink/events/keyboard-event.ts +57 -0
  120. package/packages/nastech-ink/src/ink/events/mouse-event.ts +18 -0
  121. package/packages/nastech-ink/src/ink/events/paste-event.ts +10 -0
  122. package/packages/nastech-ink/src/ink/events/resize-event.ts +12 -0
  123. package/packages/nastech-ink/src/ink/events/terminal-event.ts +107 -0
  124. package/packages/nastech-ink/src/ink/events/terminal-focus-event.ts +19 -0
  125. package/packages/nastech-ink/src/ink/focus.ts +219 -0
  126. package/packages/nastech-ink/src/ink/frame.ts +124 -0
  127. package/packages/nastech-ink/src/ink/get-max-width.ts +27 -0
  128. package/packages/nastech-ink/src/ink/global.d.ts +1 -0
  129. package/packages/nastech-ink/src/ink/hit-test.test.ts +38 -0
  130. package/packages/nastech-ink/src/ink/hit-test.ts +224 -0
  131. package/packages/nastech-ink/src/ink/hooks/use-animation-frame.ts +62 -0
  132. package/packages/nastech-ink/src/ink/hooks/use-app.ts +9 -0
  133. package/packages/nastech-ink/src/ink/hooks/use-cursor-advance.ts +33 -0
  134. package/packages/nastech-ink/src/ink/hooks/use-declared-cursor.ts +75 -0
  135. package/packages/nastech-ink/src/ink/hooks/use-external-process.ts +27 -0
  136. package/packages/nastech-ink/src/ink/hooks/use-input.ts +95 -0
  137. package/packages/nastech-ink/src/ink/hooks/use-interval.ts +71 -0
  138. package/packages/nastech-ink/src/ink/hooks/use-search-highlight.ts +56 -0
  139. package/packages/nastech-ink/src/ink/hooks/use-selection.ts +101 -0
  140. package/packages/nastech-ink/src/ink/hooks/use-stdin.ts +9 -0
  141. package/packages/nastech-ink/src/ink/hooks/use-tab-status.ts +71 -0
  142. package/packages/nastech-ink/src/ink/hooks/use-terminal-focus.ts +18 -0
  143. package/packages/nastech-ink/src/ink/hooks/use-terminal-title.ts +34 -0
  144. package/packages/nastech-ink/src/ink/hooks/use-terminal-viewport.ts +100 -0
  145. package/packages/nastech-ink/src/ink/hyperlinkHover.ts +52 -0
  146. package/packages/nastech-ink/src/ink/ink-cursor-advance.test.ts +234 -0
  147. package/packages/nastech-ink/src/ink/ink-resize.test.ts +50 -0
  148. package/packages/nastech-ink/src/ink/ink.tsx +2705 -0
  149. package/packages/nastech-ink/src/ink/instances.ts +10 -0
  150. package/packages/nastech-ink/src/ink/layout/engine.ts +6 -0
  151. package/packages/nastech-ink/src/ink/layout/geometry.ts +98 -0
  152. package/packages/nastech-ink/src/ink/layout/node.ts +145 -0
  153. package/packages/nastech-ink/src/ink/layout/yoga.ts +313 -0
  154. package/packages/nastech-ink/src/ink/line-width-cache.ts +38 -0
  155. package/packages/nastech-ink/src/ink/log-update.test.ts +223 -0
  156. package/packages/nastech-ink/src/ink/log-update.ts +752 -0
  157. package/packages/nastech-ink/src/ink/lru.ts +14 -0
  158. package/packages/nastech-ink/src/ink/measure-element.ts +23 -0
  159. package/packages/nastech-ink/src/ink/measure-text.ts +50 -0
  160. package/packages/nastech-ink/src/ink/node-cache.ts +53 -0
  161. package/packages/nastech-ink/src/ink/optimizer.ts +99 -0
  162. package/packages/nastech-ink/src/ink/output.ts +845 -0
  163. package/packages/nastech-ink/src/ink/parse-keypress.test.ts +133 -0
  164. package/packages/nastech-ink/src/ink/parse-keypress.ts +848 -0
  165. package/packages/nastech-ink/src/ink/reconciler.ts +382 -0
  166. package/packages/nastech-ink/src/ink/render-border.ts +206 -0
  167. package/packages/nastech-ink/src/ink/render-node-to-output.ts +1582 -0
  168. package/packages/nastech-ink/src/ink/render-to-screen.ts +236 -0
  169. package/packages/nastech-ink/src/ink/renderer.ts +169 -0
  170. package/packages/nastech-ink/src/ink/root.ts +204 -0
  171. package/packages/nastech-ink/src/ink/screen.ts +1590 -0
  172. package/packages/nastech-ink/src/ink/searchHighlight.ts +91 -0
  173. package/packages/nastech-ink/src/ink/selection.test.ts +82 -0
  174. package/packages/nastech-ink/src/ink/selection.ts +1143 -0
  175. package/packages/nastech-ink/src/ink/squash-text-nodes.ts +74 -0
  176. package/packages/nastech-ink/src/ink/stringWidth.ts +341 -0
  177. package/packages/nastech-ink/src/ink/styles.ts +750 -0
  178. package/packages/nastech-ink/src/ink/supports-hyperlinks.ts +51 -0
  179. package/packages/nastech-ink/src/ink/tabstops.ts +44 -0
  180. package/packages/nastech-ink/src/ink/terminal-focus-state.ts +52 -0
  181. package/packages/nastech-ink/src/ink/terminal-querier.ts +222 -0
  182. package/packages/nastech-ink/src/ink/terminal.test.ts +15 -0
  183. package/packages/nastech-ink/src/ink/terminal.ts +299 -0
  184. package/packages/nastech-ink/src/ink/termio/ansi.ts +75 -0
  185. package/packages/nastech-ink/src/ink/termio/csi.ts +334 -0
  186. package/packages/nastech-ink/src/ink/termio/dec.ts +99 -0
  187. package/packages/nastech-ink/src/ink/termio/esc.ts +69 -0
  188. package/packages/nastech-ink/src/ink/termio/osc.test.ts +191 -0
  189. package/packages/nastech-ink/src/ink/termio/osc.ts +724 -0
  190. package/packages/nastech-ink/src/ink/termio/parser.ts +467 -0
  191. package/packages/nastech-ink/src/ink/termio/sgr.ts +362 -0
  192. package/packages/nastech-ink/src/ink/termio/tokenize.test.ts +185 -0
  193. package/packages/nastech-ink/src/ink/termio/tokenize.ts +350 -0
  194. package/packages/nastech-ink/src/ink/termio/types.ts +230 -0
  195. package/packages/nastech-ink/src/ink/termio.ts +42 -0
  196. package/packages/nastech-ink/src/ink/useTerminalNotification.ts +110 -0
  197. package/packages/nastech-ink/src/ink/warn.ts +15 -0
  198. package/packages/nastech-ink/src/ink/widest-line.ts +22 -0
  199. package/packages/nastech-ink/src/ink/wrap-text.test.ts +17 -0
  200. package/packages/nastech-ink/src/ink/wrap-text.ts +144 -0
  201. package/packages/nastech-ink/src/ink/wrapAnsi.ts +13 -0
  202. package/packages/nastech-ink/src/native-ts/yoga-layout/enums.ts +112 -0
  203. package/packages/nastech-ink/src/native-ts/yoga-layout/index.ts +2326 -0
  204. package/packages/nastech-ink/src/utils/debug.ts +6 -0
  205. package/packages/nastech-ink/src/utils/earlyInput.ts +131 -0
  206. package/packages/nastech-ink/src/utils/env.ts +66 -0
  207. package/packages/nastech-ink/src/utils/envUtils.ts +13 -0
  208. package/packages/nastech-ink/src/utils/execFileNoThrow.test.ts +146 -0
  209. package/packages/nastech-ink/src/utils/execFileNoThrow.ts +115 -0
  210. package/packages/nastech-ink/src/utils/fullscreen.ts +3 -0
  211. package/packages/nastech-ink/src/utils/intl.ts +87 -0
  212. package/packages/nastech-ink/src/utils/log.ts +7 -0
  213. package/packages/nastech-ink/src/utils/semver.ts +57 -0
  214. package/packages/nastech-ink/src/utils/sliceAnsi.ts +106 -0
  215. package/packages/nastech-ink/text-input.d.ts +2 -0
  216. package/packages/nastech-ink/text-input.js +1 -0
  217. package/scripts/build.mjs +61 -0
  218. package/scripts/profile-tui.mjs +121 -0
  219. package/src/__tests__/activeSessionSwitcher.test.ts +157 -0
  220. package/src/__tests__/appChromeStatusRule.test.tsx +84 -0
  221. package/src/__tests__/appChromeStatusRuleDevCredits.test.tsx +73 -0
  222. package/src/__tests__/approvalAction.test.ts +50 -0
  223. package/src/__tests__/asCommandDispatch.test.ts +27 -0
  224. package/src/__tests__/blockLayout.test.ts +122 -0
  225. package/src/__tests__/clipboard.test.ts +369 -0
  226. package/src/__tests__/constants.test.ts +53 -0
  227. package/src/__tests__/createGatewayEventHandler.test.ts +1091 -0
  228. package/src/__tests__/createSlashHandler.test.ts +822 -0
  229. package/src/__tests__/creditsCommand.test.ts +144 -0
  230. package/src/__tests__/cursorDriftRegression.test.ts +114 -0
  231. package/src/__tests__/details.test.ts +115 -0
  232. package/src/__tests__/emoji.test.ts +64 -0
  233. package/src/__tests__/externalLink.test.ts +144 -0
  234. package/src/__tests__/forceTruecolor.test.ts +191 -0
  235. package/src/__tests__/gatewayClient.test.ts +394 -0
  236. package/src/__tests__/gatewayRecovery.test.ts +47 -0
  237. package/src/__tests__/markdown.test.ts +331 -0
  238. package/src/__tests__/mathUnicode.test.ts +293 -0
  239. package/src/__tests__/memoryMonitor.test.ts +102 -0
  240. package/src/__tests__/messageLine.test.ts +19 -0
  241. package/src/__tests__/messages.test.ts +92 -0
  242. package/src/__tests__/orchestratorPromptSession.test.ts +64 -0
  243. package/src/__tests__/osc52.test.ts +67 -0
  244. package/src/__tests__/parentLog.test.ts +75 -0
  245. package/src/__tests__/paths.test.ts +70 -0
  246. package/src/__tests__/platform.test.ts +556 -0
  247. package/src/__tests__/precisionWheel.test.ts +44 -0
  248. package/src/__tests__/prompt.test.ts +31 -0
  249. package/src/__tests__/providers.test.ts +65 -0
  250. package/src/__tests__/reasoning.test.ts +76 -0
  251. package/src/__tests__/rpc.test.ts +27 -0
  252. package/src/__tests__/scroll.test.ts +99 -0
  253. package/src/__tests__/slashParity.test.ts +123 -0
  254. package/src/__tests__/spawnHistoryStore.test.ts +46 -0
  255. package/src/__tests__/stateIsolation.test.ts +46 -0
  256. package/src/__tests__/statusBarTicker.test.ts +18 -0
  257. package/src/__tests__/statusRule.test.ts +32 -0
  258. package/src/__tests__/streamingMarkdown.test.ts +121 -0
  259. package/src/__tests__/subagentTree.test.ts +407 -0
  260. package/src/__tests__/syntax.test.ts +45 -0
  261. package/src/__tests__/terminalModes.test.ts +39 -0
  262. package/src/__tests__/terminalParity.test.ts +77 -0
  263. package/src/__tests__/terminalSetup.test.ts +386 -0
  264. package/src/__tests__/termux.test.ts +35 -0
  265. package/src/__tests__/termuxComposerLayout.test.ts +40 -0
  266. package/src/__tests__/text.test.ts +233 -0
  267. package/src/__tests__/textInputBurstInput.test.ts +40 -0
  268. package/src/__tests__/textInputCursorSourceOfTruth.test.ts +50 -0
  269. package/src/__tests__/textInputFastEcho.test.ts +200 -0
  270. package/src/__tests__/textInputLineNav.test.ts +55 -0
  271. package/src/__tests__/textInputPassThrough.test.ts +59 -0
  272. package/src/__tests__/textInputRightClick.test.ts +48 -0
  273. package/src/__tests__/textInputWrap.test.ts +151 -0
  274. package/src/__tests__/theme.test.ts +311 -0
  275. package/src/__tests__/turnControllerNotice.test.ts +43 -0
  276. package/src/__tests__/turnStore.test.ts +66 -0
  277. package/src/__tests__/useCompletion.test.ts +35 -0
  278. package/src/__tests__/useComposerState.test.ts +59 -0
  279. package/src/__tests__/useConfigSync.test.ts +460 -0
  280. package/src/__tests__/useInputHandlers.test.ts +77 -0
  281. package/src/__tests__/useQueue.test.ts +28 -0
  282. package/src/__tests__/useSessionLifecycle.test.ts +60 -0
  283. package/src/__tests__/useVirtualHistoryHeights.test.ts +39 -0
  284. package/src/__tests__/viewport.test.ts +58 -0
  285. package/src/__tests__/viewportStore.test.ts +85 -0
  286. package/src/__tests__/virtualHeights.test.ts +96 -0
  287. package/src/__tests__/virtualHistoryClamp.test.ts +19 -0
  288. package/src/__tests__/virtualHistoryOffsetCache.test.ts +282 -0
  289. package/src/__tests__/wheelAccel.test.ts +138 -0
  290. package/src/app/createGatewayEventHandler.ts +833 -0
  291. package/src/app/createSlashHandler.ts +130 -0
  292. package/src/app/delegationStore.ts +77 -0
  293. package/src/app/gatewayContext.tsx +19 -0
  294. package/src/app/gatewayRecovery.ts +35 -0
  295. package/src/app/inputSelectionStore.ts +15 -0
  296. package/src/app/interfaces.ts +394 -0
  297. package/src/app/overlayStore.ts +53 -0
  298. package/src/app/scroll.ts +71 -0
  299. package/src/app/setupHandoff.ts +54 -0
  300. package/src/app/slash/commands/core.ts +648 -0
  301. package/src/app/slash/commands/credits.ts +57 -0
  302. package/src/app/slash/commands/debug.ts +48 -0
  303. package/src/app/slash/commands/ops.ts +717 -0
  304. package/src/app/slash/commands/session.ts +554 -0
  305. package/src/app/slash/commands/setup.ts +20 -0
  306. package/src/app/slash/registry.ts +20 -0
  307. package/src/app/slash/types.ts +21 -0
  308. package/src/app/spawnHistoryStore.ts +159 -0
  309. package/src/app/turnController.ts +866 -0
  310. package/src/app/turnStore.ts +85 -0
  311. package/src/app/uiStore.ts +44 -0
  312. package/src/app/useComposerState.ts +367 -0
  313. package/src/app/useConfigSync.ts +288 -0
  314. package/src/app/useInputHandlers.ts +576 -0
  315. package/src/app/useLongRunToolCharms.ts +69 -0
  316. package/src/app/useMainApp.ts +1039 -0
  317. package/src/app/useSessionLifecycle.ts +366 -0
  318. package/src/app/useSubmission.ts +429 -0
  319. package/src/app.tsx +25 -0
  320. package/src/banner.ts +93 -0
  321. package/src/components/activeSessionSwitcher.tsx +635 -0
  322. package/src/components/agentsOverlay.tsx +1073 -0
  323. package/src/components/appChrome.tsx +554 -0
  324. package/src/components/appLayout.tsx +444 -0
  325. package/src/components/appOverlays.tsx +254 -0
  326. package/src/components/branding.tsx +466 -0
  327. package/src/components/fpsOverlay.tsx +30 -0
  328. package/src/components/helpHint.tsx +73 -0
  329. package/src/components/markdown.tsx +1119 -0
  330. package/src/components/maskedPrompt.tsx +34 -0
  331. package/src/components/messageLine.tsx +237 -0
  332. package/src/components/modelPicker.tsx +527 -0
  333. package/src/components/overlayControls.tsx +50 -0
  334. package/src/components/pluginsHub.tsx +238 -0
  335. package/src/components/prompts.tsx +276 -0
  336. package/src/components/queuedMessages.tsx +64 -0
  337. package/src/components/sessionPicker.tsx +227 -0
  338. package/src/components/skillsHub.tsx +308 -0
  339. package/src/components/streamingAssistant.tsx +110 -0
  340. package/src/components/streamingMarkdown.tsx +174 -0
  341. package/src/components/textInput.tsx +1340 -0
  342. package/src/components/themed.tsx +30 -0
  343. package/src/components/thinking.tsx +1224 -0
  344. package/src/components/todoPanel.tsx +93 -0
  345. package/src/config/env.ts +64 -0
  346. package/src/config/limits.ts +13 -0
  347. package/src/config/timing.ts +6 -0
  348. package/src/content/charms.ts +1 -0
  349. package/src/content/faces.ts +17 -0
  350. package/src/content/fortunes.ts +30 -0
  351. package/src/content/hotkeys.ts +37 -0
  352. package/src/content/placeholders.ts +13 -0
  353. package/src/content/setup.ts +17 -0
  354. package/src/content/verbs.ts +38 -0
  355. package/src/domain/blockLayout.ts +146 -0
  356. package/src/domain/details.ts +76 -0
  357. package/src/domain/messages.ts +91 -0
  358. package/src/domain/paths.ts +16 -0
  359. package/src/domain/providers.ts +11 -0
  360. package/src/domain/roles.ts +9 -0
  361. package/src/domain/slash.ts +10 -0
  362. package/src/domain/usage.ts +3 -0
  363. package/src/domain/viewport.ts +51 -0
  364. package/src/entry.tsx +104 -0
  365. package/src/gatewayClient.ts +730 -0
  366. package/src/gatewayTypes.ts +568 -0
  367. package/src/hooks/useCompletion.ts +112 -0
  368. package/src/hooks/useGitBranch.ts +72 -0
  369. package/src/hooks/useInputHistory.ts +11 -0
  370. package/src/hooks/useQueue.ts +76 -0
  371. package/src/hooks/useVirtualHistory.ts +554 -0
  372. package/src/lib/circularBuffer.ts +48 -0
  373. package/src/lib/clipboard.ts +182 -0
  374. package/src/lib/editor.test.ts +74 -0
  375. package/src/lib/editor.ts +47 -0
  376. package/src/lib/emoji.ts +55 -0
  377. package/src/lib/externalCli.ts +16 -0
  378. package/src/lib/externalLink.ts +435 -0
  379. package/src/lib/forceTruecolor.ts +60 -0
  380. package/src/lib/fpsStore.ts +51 -0
  381. package/src/lib/fuzzy.test.ts +109 -0
  382. package/src/lib/fuzzy.ts +177 -0
  383. package/src/lib/gracefulExit.ts +47 -0
  384. package/src/lib/history.ts +82 -0
  385. package/src/lib/inputMetrics.ts +203 -0
  386. package/src/lib/liveProgress.test.ts +116 -0
  387. package/src/lib/liveProgress.ts +79 -0
  388. package/src/lib/mathUnicode.ts +770 -0
  389. package/src/lib/memory.test.ts +155 -0
  390. package/src/lib/memory.ts +188 -0
  391. package/src/lib/memoryMonitor.ts +109 -0
  392. package/src/lib/messages.test.ts +29 -0
  393. package/src/lib/messages.ts +8 -0
  394. package/src/lib/openExternalUrl.test.ts +217 -0
  395. package/src/lib/openExternalUrl.ts +158 -0
  396. package/src/lib/osc52.ts +73 -0
  397. package/src/lib/parentLog.ts +57 -0
  398. package/src/lib/perfPane.tsx +107 -0
  399. package/src/lib/platform.ts +409 -0
  400. package/src/lib/precisionWheel.ts +48 -0
  401. package/src/lib/prompt.ts +35 -0
  402. package/src/lib/reasoning.ts +55 -0
  403. package/src/lib/rpc.ts +41 -0
  404. package/src/lib/subagentTree.ts +355 -0
  405. package/src/lib/syntax.ts +117 -0
  406. package/src/lib/terminalModes.ts +51 -0
  407. package/src/lib/terminalParity.ts +78 -0
  408. package/src/lib/terminalSetup.ts +444 -0
  409. package/src/lib/termux.ts +29 -0
  410. package/src/lib/text.test.ts +18 -0
  411. package/src/lib/text.ts +339 -0
  412. package/src/lib/todo.test.ts +21 -0
  413. package/src/lib/todo.ts +9 -0
  414. package/src/lib/viewportStore.ts +124 -0
  415. package/src/lib/virtualHeights.ts +145 -0
  416. package/src/lib/wheelAccel.ts +190 -0
  417. package/src/protocol/interpolation.ts +3 -0
  418. package/src/protocol/paste.ts +1 -0
  419. package/src/theme.ts +589 -0
  420. package/src/types/nastech-ink.d.ts +176 -0
  421. package/src/types.ts +212 -0
  422. package/tsconfig.build.json +9 -0
  423. package/tsconfig.json +19 -0
  424. package/vitest.config.ts +7 -0
@@ -0,0 +1,568 @@
1
+ import type { SessionInfo, SlashCategory, SubagentStatus, Usage } from './types.js'
2
+
3
+ export interface GatewaySkin {
4
+ banner_hero?: string
5
+ banner_logo?: string
6
+ branding?: Record<string, string>
7
+ colors?: Record<string, string>
8
+ help_header?: string
9
+ tool_prefix?: string
10
+ }
11
+
12
+ export interface GatewayCompletionItem {
13
+ display: string
14
+ meta?: string
15
+ text: string
16
+ }
17
+
18
+ export interface GatewayTranscriptMessage {
19
+ context?: string
20
+ name?: string
21
+ role: 'assistant' | 'system' | 'tool' | 'user'
22
+ text?: string
23
+ }
24
+
25
+ // ── Commands / completion ────────────────────────────────────────────
26
+
27
+ export interface CommandsCatalogResponse {
28
+ canon?: Record<string, string>
29
+ categories?: SlashCategory[]
30
+ pairs?: [string, string][]
31
+ skill_count?: number
32
+ sub?: Record<string, string[]>
33
+ warning?: string
34
+ }
35
+
36
+ export interface CompletionResponse {
37
+ items?: GatewayCompletionItem[]
38
+ replace_from?: number
39
+ }
40
+
41
+ export interface SlashExecResponse {
42
+ output?: string
43
+ warning?: string
44
+ }
45
+
46
+ export type CommandDispatchResponse =
47
+ | { output?: string; type: 'exec' | 'plugin' }
48
+ | { target: string; type: 'alias' }
49
+ | { message?: string; name: string; type: 'skill' }
50
+ | { message: string; notice?: string; type: 'send' }
51
+
52
+ // ── Config ───────────────────────────────────────────────────────────
53
+
54
+ export interface ConfigDisplayConfig {
55
+ bell_on_complete?: boolean
56
+ busy_input_mode?: string
57
+ details_mode?: string
58
+ inline_diffs?: boolean
59
+ mouse_tracking?: boolean | null | number | string
60
+ sections?: Record<string, string>
61
+ show_cost?: boolean
62
+ show_reasoning?: boolean
63
+ streaming?: boolean
64
+ thinking_mode?: string
65
+ /**
66
+ * Nudge the user toward the /agents spawn-tree dashboard the first time a
67
+ * turn starts delegating, via a one-time transient activity hint. Opens
68
+ * nothing — just advertises the command. Default true.
69
+ */
70
+ tui_agents_nudge?: boolean
71
+ tui_auto_resume_recent?: boolean
72
+ tui_compact?: boolean
73
+ /** Legacy alias for display.mouse_tracking. */
74
+ tui_mouse?: boolean | null | number | string
75
+ // Forward-compat: backend may send styles this client doesn't know yet —
76
+ // `normalizeIndicatorStyle` falls back to 'kaomoji' for those — but the
77
+ // wire type is documented as `string` so consumers don't get a false
78
+ // narrowing-and-autocomplete contract on a value that requires runtime
79
+ // validation anyway.
80
+ tui_status_indicator?: string
81
+ tui_statusbar?: 'bottom' | 'off' | 'on' | 'top' | boolean
82
+ }
83
+
84
+ export interface ConfigVoiceConfig {
85
+ // Raw `yaml.safe_load()` value from config; may be non-string if hand-edited.
86
+ // Callers must normalize/validate at runtime (parseVoiceRecordKey()).
87
+ record_key?: unknown
88
+ }
89
+
90
+ export interface ConfigFullResponse {
91
+ config?: { display?: ConfigDisplayConfig; voice?: ConfigVoiceConfig; paste_collapse_threshold?: number; paste_collapse_char_threshold?: number }
92
+ }
93
+
94
+ export interface ConfigMtimeResponse {
95
+ mtime?: number
96
+ }
97
+
98
+ export interface ConfigGetValueResponse {
99
+ display?: string
100
+ home?: string
101
+ value?: string
102
+ }
103
+
104
+ export interface ConfigSetResponse {
105
+ credential_warning?: string
106
+ history_reset?: boolean
107
+ info?: SessionInfo
108
+ value?: string
109
+ warning?: string
110
+ }
111
+
112
+ export interface SetupStatusResponse {
113
+ provider_configured?: boolean
114
+ }
115
+
116
+ // ── Session lifecycle ────────────────────────────────────────────────
117
+
118
+ export interface SessionCreateResponse {
119
+ info?: SessionInfo & { config_warning?: string; credential_warning?: string }
120
+ session_id: string
121
+ }
122
+
123
+ export interface SessionResumeResponse {
124
+ info?: SessionInfo
125
+ message_count?: number
126
+ messages: GatewayTranscriptMessage[]
127
+ resumed?: string
128
+ session_id: string
129
+ }
130
+
131
+ export type LiveSessionStatus = 'idle' | 'starting' | 'waiting' | 'working'
132
+
133
+ export interface SessionActiveItem {
134
+ current?: boolean
135
+ id: string
136
+ last_active?: number
137
+ message_count?: number
138
+ model?: string
139
+ preview?: string
140
+ session_key?: string
141
+ started_at?: number
142
+ status: LiveSessionStatus
143
+ title?: string
144
+ }
145
+
146
+ export interface SessionActiveListResponse {
147
+ sessions?: SessionActiveItem[]
148
+ }
149
+
150
+ export interface SessionInflightTurn {
151
+ assistant?: string
152
+ streaming?: boolean
153
+ user?: string
154
+ }
155
+
156
+ export interface SessionActivateResponse {
157
+ inflight?: null | SessionInflightTurn
158
+ info?: SessionInfo
159
+ message_count?: number
160
+ messages: GatewayTranscriptMessage[]
161
+ running?: boolean
162
+ session_id: string
163
+ session_key?: string
164
+ started_at?: number
165
+ status?: LiveSessionStatus
166
+ }
167
+
168
+ export interface SessionListItem {
169
+ id: string
170
+ message_count: number
171
+ preview: string
172
+ source?: string
173
+ started_at: number
174
+ title: string
175
+ }
176
+
177
+ export interface SessionListResponse {
178
+ sessions?: SessionListItem[]
179
+ }
180
+
181
+ export interface SessionDeleteResponse {
182
+ deleted: string
183
+ }
184
+
185
+ export interface SessionMostRecentResponse {
186
+ session_id?: null | string
187
+ source?: string
188
+ started_at?: number
189
+ title?: string
190
+ }
191
+
192
+ export interface SessionTitleResponse {
193
+ pending?: boolean
194
+ session_key?: string
195
+ title?: string
196
+ }
197
+
198
+ export interface SessionSaveResponse {
199
+ file?: string
200
+ }
201
+
202
+ export interface SessionUndoResponse {
203
+ removed?: number
204
+ }
205
+
206
+ export interface SessionUsageResponse {
207
+ cache_read?: number
208
+ cache_write?: number
209
+ calls?: number
210
+ compressions?: number
211
+ context_max?: number
212
+ context_percent?: number
213
+ context_used?: number
214
+ cost_status?: 'estimated' | 'exact'
215
+ cost_usd?: number
216
+ input?: number
217
+ model?: string
218
+ output?: number
219
+ total?: number
220
+ }
221
+
222
+ export interface SessionStatusResponse {
223
+ output?: string
224
+ }
225
+
226
+ export interface SessionCompressResponse {
227
+ after_messages?: number
228
+ after_tokens?: number
229
+ before_messages?: number
230
+ before_tokens?: number
231
+ info?: SessionInfo
232
+ messages?: GatewayTranscriptMessage[]
233
+ removed?: number
234
+ summary?: {
235
+ headline?: string
236
+ noop?: boolean
237
+ note?: null | string
238
+ token_line?: string
239
+ }
240
+ usage?: Usage
241
+ }
242
+
243
+ export interface SessionBranchResponse {
244
+ session_id?: string
245
+ title?: string
246
+ }
247
+
248
+ export interface SessionCloseResponse {
249
+ closed?: boolean
250
+ ok?: boolean
251
+ }
252
+
253
+ export interface SessionInterruptResponse {
254
+ ok?: boolean
255
+ }
256
+
257
+ export interface SessionSteerResponse {
258
+ status?: 'queued' | 'rejected'
259
+ text?: string
260
+ }
261
+
262
+ // ── Prompt / submission ──────────────────────────────────────────────
263
+
264
+ export interface PromptSubmitResponse {
265
+ ok?: boolean
266
+ }
267
+
268
+ export interface BackgroundStartResponse {
269
+ task_id?: string
270
+ }
271
+
272
+ export interface ClarifyRespondResponse {
273
+ ok?: boolean
274
+ }
275
+
276
+ export interface ApprovalRespondResponse {
277
+ ok?: boolean
278
+ }
279
+
280
+ export interface SudoRespondResponse {
281
+ ok?: boolean
282
+ }
283
+
284
+ export interface SecretRespondResponse {
285
+ ok?: boolean
286
+ }
287
+
288
+ // ── Shell / clipboard / input ────────────────────────────────────────
289
+
290
+ export interface ShellExecResponse {
291
+ code: number
292
+ stderr?: string
293
+ stdout?: string
294
+ }
295
+
296
+ export interface ClipboardPasteResponse {
297
+ attached?: boolean
298
+ count?: number
299
+ height?: number
300
+ message?: string
301
+ token_estimate?: number
302
+ width?: number
303
+ }
304
+
305
+ export interface InputDetectDropResponse {
306
+ height?: number
307
+ is_image?: boolean
308
+ matched?: boolean
309
+ name?: string
310
+ text?: string
311
+ token_estimate?: number
312
+ width?: number
313
+ }
314
+
315
+ export interface TerminalResizeResponse {
316
+ ok?: boolean
317
+ }
318
+
319
+ // ── Image attach ─────────────────────────────────────────────────────
320
+
321
+ export interface ImageAttachResponse {
322
+ height?: number
323
+ name?: string
324
+ remainder?: string
325
+ token_estimate?: number
326
+ width?: number
327
+ }
328
+
329
+ // ── Voice ────────────────────────────────────────────────────────────
330
+
331
+ export interface VoiceToggleResponse {
332
+ audio_available?: boolean
333
+ available?: boolean
334
+ details?: string
335
+ enabled?: boolean
336
+ record_key?: string
337
+ stt_available?: boolean
338
+ tts?: boolean
339
+ }
340
+
341
+ export interface VoiceRecordResponse {
342
+ status?: 'busy' | 'recording' | 'stopped'
343
+ text?: string
344
+ }
345
+
346
+ // ── Tools (TS keeps configure since it resets local history) ─────────
347
+
348
+ export interface ToolsConfigureResponse {
349
+ changed?: string[]
350
+ enabled_toolsets?: string[]
351
+ info?: SessionInfo
352
+ missing_servers?: string[]
353
+ reset?: boolean
354
+ unknown?: string[]
355
+ }
356
+
357
+ // ── Model picker ─────────────────────────────────────────────────────
358
+
359
+ export interface ModelOptionProvider {
360
+ auth_type?: string
361
+ authenticated?: boolean
362
+ is_current?: boolean
363
+ key_env?: string
364
+ models?: string[]
365
+ name: string
366
+ slug: string
367
+ total_models?: number
368
+ warning?: string
369
+ }
370
+
371
+ export interface ModelOptionsResponse {
372
+ model?: string
373
+ provider?: string
374
+ providers?: ModelOptionProvider[]
375
+ }
376
+
377
+ // ── MCP ──────────────────────────────────────────────────────────────
378
+
379
+ export interface ReloadMcpResponse {
380
+ status?: string
381
+ message?: string
382
+ }
383
+
384
+ export interface ReloadEnvResponse {
385
+ updated?: number
386
+ }
387
+
388
+ export interface ProcessStopResponse {
389
+ killed?: number
390
+ }
391
+
392
+ export interface BrowserManageResponse {
393
+ connected?: boolean
394
+ messages?: string[]
395
+ url?: string
396
+ }
397
+
398
+ export interface RollbackCheckpoint {
399
+ hash: string
400
+ message?: string
401
+ timestamp?: string
402
+ }
403
+
404
+ export interface RollbackListResponse {
405
+ checkpoints?: RollbackCheckpoint[]
406
+ enabled?: boolean
407
+ }
408
+
409
+ export interface RollbackDiffResponse {
410
+ diff?: string
411
+ rendered?: string
412
+ stat?: string
413
+ }
414
+
415
+ export interface RollbackRestoreResponse {
416
+ error?: string
417
+ history_removed?: number
418
+ message?: string
419
+ reason?: string
420
+ restored_to?: string
421
+ success?: boolean
422
+ }
423
+
424
+ // ── Subagent events ──────────────────────────────────────────────────
425
+
426
+ export interface SubagentEventPayload {
427
+ api_calls?: number
428
+ cost_usd?: number
429
+ depth?: number
430
+ duration_seconds?: number
431
+ files_read?: string[]
432
+ files_written?: string[]
433
+ goal: string
434
+ input_tokens?: number
435
+ iteration?: number
436
+ model?: string
437
+ output_tail?: { is_error?: boolean; preview?: string; tool?: string }[]
438
+ output_tokens?: number
439
+ parent_id?: null | string
440
+ reasoning_tokens?: number
441
+ status?: SubagentStatus
442
+ subagent_id?: string
443
+ summary?: string
444
+ task_count?: number
445
+ task_index: number
446
+ text?: string
447
+ tool_count?: number
448
+ tool_name?: string
449
+ tool_preview?: string
450
+ toolsets?: string[]
451
+ }
452
+
453
+ // ── Delegation control RPCs ──────────────────────────────────────────
454
+
455
+ export interface DelegationStatusResponse {
456
+ active?: {
457
+ depth?: number
458
+ goal?: string
459
+ model?: null | string
460
+ parent_id?: null | string
461
+ started_at?: number
462
+ status?: string
463
+ subagent_id?: string
464
+ tool_count?: number
465
+ }[]
466
+ max_concurrent_children?: number
467
+ max_spawn_depth?: number
468
+ paused?: boolean
469
+ }
470
+
471
+ export interface DelegationPauseResponse {
472
+ paused?: boolean
473
+ }
474
+
475
+ export interface SubagentInterruptResponse {
476
+ found?: boolean
477
+ subagent_id?: string
478
+ }
479
+
480
+ // ── Spawn-tree snapshots ─────────────────────────────────────────────
481
+
482
+ export interface SpawnTreeListEntry {
483
+ count: number
484
+ finished_at?: number
485
+ label?: string
486
+ path: string
487
+ session_id?: string
488
+ started_at?: number | null
489
+ }
490
+
491
+ export interface SpawnTreeListResponse {
492
+ entries?: SpawnTreeListEntry[]
493
+ }
494
+
495
+ export interface SpawnTreeLoadResponse {
496
+ finished_at?: number
497
+ label?: string
498
+ session_id?: string
499
+ started_at?: null | number
500
+ subagents?: unknown[]
501
+ }
502
+
503
+ export type GatewayEvent =
504
+ | { payload?: { skin?: GatewaySkin }; session_id?: string; type: 'gateway.ready' }
505
+ | { payload?: GatewaySkin; session_id?: string; type: 'skin.changed' }
506
+ | { payload: SessionInfo; session_id?: string; type: 'session.info' }
507
+ | { payload?: { text?: string }; session_id?: string; type: 'thinking.delta' }
508
+ | { payload?: undefined; session_id?: string; type: 'message.start' }
509
+ | { payload?: { kind?: string; text?: string }; session_id?: string; type: 'status.update' }
510
+ | { payload?: { state?: 'idle' | 'listening' | 'transcribing' }; session_id?: string; type: 'voice.status' }
511
+ | { payload?: { no_speech_limit?: boolean; text?: string }; session_id?: string; type: 'voice.transcript' }
512
+ | { payload: { line: string }; session_id?: string; type: 'gateway.stderr' }
513
+ | {
514
+ payload?: { level?: 'info' | 'warn' | 'error'; message?: string }
515
+ session_id?: string
516
+ type: 'browser.progress'
517
+ }
518
+ | {
519
+ payload?: { cwd?: string; python?: string; stderr_tail?: string }
520
+ session_id?: string
521
+ type: 'gateway.start_timeout'
522
+ }
523
+ | { payload?: { preview?: string }; session_id?: string; type: 'gateway.protocol_error' }
524
+ | { payload?: { text?: string; verbose?: boolean }; session_id?: string; type: 'reasoning.delta' | 'reasoning.available' }
525
+ | { payload: { name?: string; preview?: string }; session_id?: string; type: 'tool.progress' }
526
+ | { payload: { name?: string }; session_id?: string; type: 'tool.generating' }
527
+ | {
528
+ payload: { args_text?: string; context?: string; name?: string; tool_id: string; todos?: unknown[] }
529
+ session_id?: string
530
+ type: 'tool.start'
531
+ }
532
+ | {
533
+ payload: {
534
+ duration_s?: number
535
+ error?: string
536
+ inline_diff?: string
537
+ name?: string
538
+ result_text?: string
539
+ summary?: string
540
+ tool_id: string
541
+ todos?: unknown[]
542
+ }
543
+ session_id?: string
544
+ type: 'tool.complete'
545
+ }
546
+ | {
547
+ payload: { choices: string[] | null; question: string; request_id: string }
548
+ session_id?: string
549
+ type: 'clarify.request'
550
+ }
551
+ | { payload: { command: string; description: string }; session_id?: string; type: 'approval.request' }
552
+ | { payload: { request_id: string }; session_id?: string; type: 'sudo.request' }
553
+ | { payload: { env_var: string; prompt: string; request_id: string }; session_id?: string; type: 'secret.request' }
554
+ | { payload: { task_id: string; text: string }; session_id?: string; type: 'background.complete' }
555
+ | { payload?: { text?: string }; session_id?: string; type: 'review.summary' }
556
+ | { payload: SubagentEventPayload; session_id?: string; type: 'subagent.spawn_requested' }
557
+ | { payload: SubagentEventPayload; session_id?: string; type: 'subagent.start' }
558
+ | { payload: SubagentEventPayload; session_id?: string; type: 'subagent.thinking' }
559
+ | { payload: SubagentEventPayload; session_id?: string; type: 'subagent.tool' }
560
+ | { payload: SubagentEventPayload; session_id?: string; type: 'subagent.progress' }
561
+ | { payload: SubagentEventPayload; session_id?: string; type: 'subagent.complete' }
562
+ | { payload: { rendered?: string; text?: string }; session_id?: string; type: 'message.delta' }
563
+ | {
564
+ payload?: { reasoning?: string; rendered?: string; text?: string; usage?: Usage }
565
+ session_id?: string
566
+ type: 'message.complete'
567
+ }
568
+ | { payload?: { message?: string }; session_id?: string; type: 'error' }
@@ -0,0 +1,112 @@
1
+ import { useEffect, useRef, useState } from 'react'
2
+
3
+ import type { CompletionItem } from '../app/interfaces.js'
4
+ import { looksLikeSlashCommand } from '../domain/slash.js'
5
+ import type { GatewayClient } from '../gatewayClient.js'
6
+ import type { CompletionResponse } from '../gatewayTypes.js'
7
+ import { asRpcResult } from '../lib/rpc.js'
8
+
9
+ const TAB_PATH_RE = /((?:["']?(?:[A-Za-z]:[\\/]|\.{1,2}\/|~\/|\/|@|[^"'`\s]+\/))[^\s]*)$/
10
+
11
+ export function completionRequestForInput(
12
+ input: string
13
+ ):
14
+ | { method: 'complete.path'; params: { word: string }; replaceFrom: number }
15
+ | { method: 'complete.slash'; params: { text: string }; replaceFrom: number }
16
+ | null {
17
+ const isSlashCommand = looksLikeSlashCommand(input)
18
+ const pathWord = isSlashCommand ? null : (input.match(TAB_PATH_RE)?.[1] ?? null)
19
+
20
+ if (!isSlashCommand && !pathWord) {
21
+ return null
22
+ }
23
+
24
+ // `/model` uses the two-step ModelPicker (real curated IDs).
25
+ // Slash completion here only showed short aliases + vendor/family meta.
26
+ if (isSlashCommand && /^\/model(?:\s|$)/.test(input)) {
27
+ return null
28
+ }
29
+
30
+ if (isSlashCommand) {
31
+ return { method: 'complete.slash', params: { text: input }, replaceFrom: 1 }
32
+ }
33
+
34
+ return {
35
+ method: 'complete.path',
36
+ params: { word: pathWord! },
37
+ replaceFrom: input.length - pathWord!.length
38
+ }
39
+ }
40
+
41
+ export function useCompletion(input: string, blocked: boolean, gw: GatewayClient) {
42
+ const [completions, setCompletions] = useState<CompletionItem[]>([])
43
+ const [compIdx, setCompIdx] = useState(0)
44
+ const [compReplace, setCompReplace] = useState(0)
45
+ const ref = useRef('')
46
+
47
+ useEffect(() => {
48
+ const clear = () => {
49
+ setCompletions(prev => (prev.length ? [] : prev))
50
+ setCompIdx(prev => (prev ? 0 : prev))
51
+ setCompReplace(prev => (prev ? 0 : prev))
52
+ }
53
+
54
+ if (blocked) {
55
+ ref.current = ''
56
+ clear()
57
+
58
+ return
59
+ }
60
+
61
+ if (input === ref.current) {
62
+ return
63
+ }
64
+
65
+ ref.current = input
66
+
67
+ const request = completionRequestForInput(input)
68
+ if (!request) {
69
+ clear()
70
+
71
+ return
72
+ }
73
+
74
+ const t = setTimeout(() => {
75
+ if (ref.current !== input) {
76
+ return
77
+ }
78
+
79
+ gw.request<CompletionResponse>(request.method, request.params)
80
+ .then(raw => {
81
+ if (ref.current !== input) {
82
+ return
83
+ }
84
+
85
+ const r = asRpcResult<CompletionResponse>(raw)
86
+
87
+ setCompletions(r?.items ?? [])
88
+ setCompIdx(0)
89
+ setCompReplace(request.method === 'complete.slash' ? (r?.replace_from ?? 1) : request.replaceFrom)
90
+ })
91
+ .catch((e: unknown) => {
92
+ if (ref.current !== input) {
93
+ return
94
+ }
95
+
96
+ setCompletions([
97
+ {
98
+ text: '',
99
+ display: 'completion unavailable',
100
+ meta: e instanceof Error && e.message ? e.message : 'unavailable'
101
+ }
102
+ ])
103
+ setCompIdx(0)
104
+ setCompReplace(request.replaceFrom)
105
+ })
106
+ }, 60)
107
+
108
+ return () => clearTimeout(t)
109
+ }, [blocked, gw, input])
110
+
111
+ return { completions, compIdx, setCompIdx, compReplace }
112
+ }