gaunt-sloth 2.0.0-alpha.9 → 2.0.0-beta.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (376) hide show
  1. package/README.md +66 -56
  2. package/cli.js +22 -26
  3. package/dist/cli.js +65 -8
  4. package/dist/cli.js.map +1 -1
  5. package/dist/commands/adkEvalRunner.d.ts +66 -0
  6. package/dist/commands/adkEvalRunner.js +69 -0
  7. package/dist/commands/adkEvalRunner.js.map +1 -0
  8. package/dist/commands/agUiEvalRunner.d.ts +90 -0
  9. package/dist/commands/agUiEvalRunner.js +320 -0
  10. package/dist/commands/agUiEvalRunner.js.map +1 -0
  11. package/dist/commands/apiCommand.js +1 -0
  12. package/dist/commands/apiCommand.js.map +1 -1
  13. package/dist/commands/askCommand.d.ts +3 -2
  14. package/dist/commands/askCommand.js +25 -9
  15. package/dist/commands/askCommand.js.map +1 -1
  16. package/dist/commands/batchCommand.d.ts +83 -0
  17. package/dist/commands/batchCommand.js +260 -0
  18. package/dist/commands/batchCommand.js.map +1 -0
  19. package/dist/commands/chatCommand.js +11 -1
  20. package/dist/commands/chatCommand.js.map +1 -1
  21. package/dist/commands/cliOptionParsers.d.ts +12 -0
  22. package/dist/commands/cliOptionParsers.js +18 -0
  23. package/dist/commands/cliOptionParsers.js.map +1 -0
  24. package/dist/commands/codeCommand.js +8 -1
  25. package/dist/commands/codeCommand.js.map +1 -1
  26. package/dist/commands/commandIntrospection.d.ts +32 -0
  27. package/dist/commands/commandIntrospection.js +43 -0
  28. package/dist/commands/commandIntrospection.js.map +1 -1
  29. package/dist/commands/commandUtils.d.ts +9 -8
  30. package/dist/commands/commandUtils.js +2 -1
  31. package/dist/commands/commandUtils.js.map +1 -1
  32. package/dist/commands/configCommand.d.ts +6 -2
  33. package/dist/commands/configCommand.js +78 -9
  34. package/dist/commands/configCommand.js.map +1 -1
  35. package/dist/commands/configSetup.d.ts +0 -1
  36. package/dist/commands/configSetup.js +6 -36
  37. package/dist/commands/configSetup.js.map +1 -1
  38. package/dist/commands/evalCommand.d.ts +63 -0
  39. package/dist/commands/evalCommand.js +789 -0
  40. package/dist/commands/evalCommand.js.map +1 -0
  41. package/dist/commands/execCommand.d.ts +9 -3
  42. package/dist/commands/execCommand.js +25 -9
  43. package/dist/commands/execCommand.js.map +1 -1
  44. package/dist/commands/firstRunDialog.d.ts +27 -7
  45. package/dist/commands/firstRunDialog.js +59 -15
  46. package/dist/commands/firstRunDialog.js.map +1 -1
  47. package/dist/commands/getCommand.js +1 -0
  48. package/dist/commands/getCommand.js.map +1 -1
  49. package/dist/commands/historyCommand.d.ts +10 -6
  50. package/dist/commands/historyCommand.js +47 -12
  51. package/dist/commands/historyCommand.js.map +1 -1
  52. package/dist/commands/initCommand.js +4 -0
  53. package/dist/commands/initCommand.js.map +1 -1
  54. package/dist/commands/insightsCommand.js +1 -0
  55. package/dist/commands/insightsCommand.js.map +1 -1
  56. package/dist/commands/modelsCommand.d.ts +25 -0
  57. package/dist/commands/modelsCommand.js +101 -0
  58. package/dist/commands/modelsCommand.js.map +1 -0
  59. package/dist/commands/prCommand.js +24 -5
  60. package/dist/commands/prCommand.js.map +1 -1
  61. package/dist/commands/prDiscovery.d.ts +2 -2
  62. package/dist/commands/prDiscovery.js +6 -1
  63. package/dist/commands/prDiscovery.js.map +1 -1
  64. package/dist/commands/reviewCommand.js +41 -11
  65. package/dist/commands/reviewCommand.js.map +1 -1
  66. package/dist/commands/workflowCommand.d.ts +19 -0
  67. package/dist/commands/workflowCommand.js +81 -0
  68. package/dist/commands/workflowCommand.js.map +1 -0
  69. package/dist/helpers/jira/jiraLogWork.js.map +1 -1
  70. package/dist/modules/startSession.d.ts +3 -1
  71. package/dist/modules/startSession.js +73 -9
  72. package/dist/modules/startSession.js.map +1 -1
  73. package/dist/tui/colour.d.ts +49 -0
  74. package/dist/tui/colour.js +58 -0
  75. package/dist/tui/colour.js.map +1 -0
  76. package/dist/tui/components/App.d.ts +19 -0
  77. package/dist/tui/components/App.js +795 -108
  78. package/dist/tui/components/App.js.map +1 -1
  79. package/dist/tui/components/ApprovalPrompt.d.ts +39 -8
  80. package/dist/tui/components/ApprovalPrompt.js +152 -13
  81. package/dist/tui/components/ApprovalPrompt.js.map +1 -1
  82. package/dist/tui/components/ApprovalStopMessage.d.ts +28 -0
  83. package/dist/tui/components/ApprovalStopMessage.js +42 -0
  84. package/dist/tui/components/ApprovalStopMessage.js.map +1 -0
  85. package/dist/tui/components/ApprovalsPicker.d.ts +44 -0
  86. package/dist/tui/components/ApprovalsPicker.js +52 -0
  87. package/dist/tui/components/ApprovalsPicker.js.map +1 -0
  88. package/dist/tui/components/AttackBanner.d.ts +55 -0
  89. package/dist/tui/components/AttackBanner.js +66 -0
  90. package/dist/tui/components/AttackBanner.js.map +1 -0
  91. package/dist/tui/components/ClearBanner.d.ts +8 -6
  92. package/dist/tui/components/ClearBanner.js +9 -7
  93. package/dist/tui/components/ClearBanner.js.map +1 -1
  94. package/dist/tui/components/DebugPanel.d.ts +31 -11
  95. package/dist/tui/components/DebugPanel.js +54 -25
  96. package/dist/tui/components/DebugPanel.js.map +1 -1
  97. package/dist/tui/components/FetchProgress.d.ts +36 -0
  98. package/dist/tui/components/FetchProgress.js +39 -0
  99. package/dist/tui/components/FetchProgress.js.map +1 -0
  100. package/dist/tui/components/FramedLines.d.ts +25 -0
  101. package/dist/tui/components/FramedLines.js +24 -0
  102. package/dist/tui/components/FramedLines.js.map +1 -0
  103. package/dist/tui/components/LaunchBanner.d.ts +33 -0
  104. package/dist/tui/components/LaunchBanner.js +56 -0
  105. package/dist/tui/components/LaunchBanner.js.map +1 -0
  106. package/dist/tui/components/LiveTurn.d.ts +91 -9
  107. package/dist/tui/components/LiveTurn.js +148 -23
  108. package/dist/tui/components/LiveTurn.js.map +1 -1
  109. package/dist/tui/components/NoticeBar.d.ts +32 -0
  110. package/dist/tui/components/NoticeBar.js +39 -0
  111. package/dist/tui/components/NoticeBar.js.map +1 -0
  112. package/dist/tui/components/PromptEditor.d.ts +28 -0
  113. package/dist/tui/components/PromptEditor.js +216 -0
  114. package/dist/tui/components/PromptEditor.js.map +1 -0
  115. package/dist/tui/components/PromptInput.d.ts +49 -6
  116. package/dist/tui/components/PromptInput.js +215 -42
  117. package/dist/tui/components/PromptInput.js.map +1 -1
  118. package/dist/tui/components/Rule.d.ts +8 -14
  119. package/dist/tui/components/Rule.js +12 -38
  120. package/dist/tui/components/Rule.js.map +1 -1
  121. package/dist/tui/components/SelectList.d.ts +87 -9
  122. package/dist/tui/components/SelectList.js +169 -49
  123. package/dist/tui/components/SelectList.js.map +1 -1
  124. package/dist/tui/components/SlashCommandMenu.d.ts +1 -1
  125. package/dist/tui/components/SlashCommandMenu.js +1 -1
  126. package/dist/tui/components/StatusBar.d.ts +19 -1
  127. package/dist/tui/components/StatusBar.js +15 -3
  128. package/dist/tui/components/StatusBar.js.map +1 -1
  129. package/dist/tui/components/TranscriptViewport.d.ts +75 -0
  130. package/dist/tui/components/TranscriptViewport.js +130 -0
  131. package/dist/tui/components/TranscriptViewport.js.map +1 -0
  132. package/dist/tui/debugRender.d.ts +41 -6
  133. package/dist/tui/debugRender.js +126 -12
  134. package/dist/tui/debugRender.js.map +1 -1
  135. package/dist/tui/debugSearch.d.ts +40 -0
  136. package/dist/tui/debugSearch.js +73 -0
  137. package/dist/tui/debugSearch.js.map +1 -0
  138. package/dist/tui/hitRegions.d.ts +85 -0
  139. package/dist/tui/hitRegions.js +114 -0
  140. package/dist/tui/hitRegions.js.map +1 -0
  141. package/dist/tui/keyBindings.d.ts +40 -0
  142. package/dist/tui/keyBindings.js +187 -0
  143. package/dist/tui/keyBindings.js.map +1 -0
  144. package/dist/tui/lineEditor.d.ts +139 -0
  145. package/dist/tui/lineEditor.js +318 -0
  146. package/dist/tui/lineEditor.js.map +1 -0
  147. package/dist/tui/markdown.d.ts +5 -22
  148. package/dist/tui/markdown.js +33 -8
  149. package/dist/tui/markdown.js.map +1 -1
  150. package/dist/tui/mouseParser.d.ts +75 -0
  151. package/dist/tui/mouseParser.js +108 -0
  152. package/dist/tui/mouseParser.js.map +1 -0
  153. package/dist/tui/mouseReporting.d.ts +70 -0
  154. package/dist/tui/mouseReporting.js +110 -0
  155. package/dist/tui/mouseReporting.js.map +1 -0
  156. package/dist/tui/mouseStdin.d.ts +100 -0
  157. package/dist/tui/mouseStdin.js +252 -0
  158. package/dist/tui/mouseStdin.js.map +1 -0
  159. package/dist/tui/pasteParser.d.ts +21 -0
  160. package/dist/tui/pasteParser.js +24 -0
  161. package/dist/tui/pasteParser.js.map +1 -0
  162. package/dist/tui/ruleWidth.d.ts +16 -0
  163. package/dist/tui/ruleWidth.js +24 -0
  164. package/dist/tui/ruleWidth.js.map +1 -0
  165. package/dist/tui/selectCancelled.d.ts +13 -0
  166. package/dist/tui/selectCancelled.js +17 -0
  167. package/dist/tui/selectCancelled.js.map +1 -0
  168. package/dist/tui/shouldUseTui.d.ts +23 -2
  169. package/dist/tui/shouldUseTui.js +31 -6
  170. package/dist/tui/shouldUseTui.js.map +1 -1
  171. package/dist/tui/transcriptScroll.d.ts +129 -0
  172. package/dist/tui/transcriptScroll.js +169 -0
  173. package/dist/tui/transcriptScroll.js.map +1 -0
  174. package/dist/tui/transcriptWindow.d.ts +75 -0
  175. package/dist/tui/transcriptWindow.js +226 -0
  176. package/dist/tui/transcriptWindow.js.map +1 -0
  177. package/dist/tui/tuiSessionModule.d.ts +13 -1
  178. package/dist/tui/tuiSessionModule.js +375 -56
  179. package/dist/tui/tuiSessionModule.js.map +1 -1
  180. package/dist/tui/types.d.ts +161 -18
  181. package/dist/tui/useMouse.d.ts +52 -0
  182. package/dist/tui/useMouse.js +114 -0
  183. package/dist/tui/useMouse.js.map +1 -0
  184. package/dist/tui/useSlothAnimation.d.ts +29 -0
  185. package/dist/tui/useSlothAnimation.js +65 -0
  186. package/dist/tui/useSlothAnimation.js.map +1 -0
  187. package/dist/tui/useTerminalSize.d.ts +50 -0
  188. package/dist/tui/useTerminalSize.js +95 -0
  189. package/dist/tui/useTerminalSize.js.map +1 -0
  190. package/dist/tui/useTranscriptScroll.d.ts +82 -0
  191. package/dist/tui/useTranscriptScroll.js +168 -0
  192. package/dist/tui/useTranscriptScroll.js.map +1 -0
  193. package/dist/tui/viewModel.d.ts +120 -7
  194. package/dist/tui/viewModel.js +251 -19
  195. package/dist/tui/viewModel.js.map +1 -1
  196. package/dist/utils/configErrorGuard.d.ts +44 -0
  197. package/dist/utils/configErrorGuard.js +75 -0
  198. package/dist/utils/configErrorGuard.js.map +1 -0
  199. package/dist/utils/stdinPolicy.d.ts +31 -0
  200. package/dist/utils/stdinPolicy.js +37 -0
  201. package/dist/utils/stdinPolicy.js.map +1 -0
  202. package/package.json +24 -22
  203. package/dist/builtInToolsConfig.d.ts +0 -1
  204. package/dist/builtInToolsConfig.js +0 -2
  205. package/dist/builtInToolsConfig.js.map +0 -1
  206. package/dist/config.d.ts +0 -1
  207. package/dist/config.js +0 -2
  208. package/dist/config.js.map +0 -1
  209. package/dist/constants.d.ts +0 -1
  210. package/dist/constants.js +0 -2
  211. package/dist/constants.js.map +0 -1
  212. package/dist/core/GthAgentRunner.d.ts +0 -1
  213. package/dist/core/GthAgentRunner.js +0 -2
  214. package/dist/core/GthAgentRunner.js.map +0 -1
  215. package/dist/core/GthLangChainAgent.d.ts +0 -1
  216. package/dist/core/GthLangChainAgent.js +0 -2
  217. package/dist/core/GthLangChainAgent.js.map +0 -1
  218. package/dist/core/types.d.ts +0 -1
  219. package/dist/core/types.js +0 -2
  220. package/dist/core/types.js.map +0 -1
  221. package/dist/helpers/jira/jiraClient.d.ts +0 -1
  222. package/dist/helpers/jira/jiraClient.js +0 -2
  223. package/dist/helpers/jira/jiraClient.js.map +0 -1
  224. package/dist/mcp/OAuthClientProviderImpl.d.ts +0 -1
  225. package/dist/mcp/OAuthClientProviderImpl.js +0 -2
  226. package/dist/mcp/OAuthClientProviderImpl.js.map +0 -1
  227. package/dist/middleware/binaryContentInjectionMiddleware.d.ts +0 -1
  228. package/dist/middleware/binaryContentInjectionMiddleware.js +0 -2
  229. package/dist/middleware/binaryContentInjectionMiddleware.js.map +0 -1
  230. package/dist/middleware/registry.d.ts +0 -1
  231. package/dist/middleware/registry.js +0 -2
  232. package/dist/middleware/registry.js.map +0 -1
  233. package/dist/middleware/reviewRateMiddleware.d.ts +0 -1
  234. package/dist/middleware/reviewRateMiddleware.js +0 -2
  235. package/dist/middleware/reviewRateMiddleware.js.map +0 -1
  236. package/dist/middleware/types.d.ts +0 -1
  237. package/dist/middleware/types.js +0 -2
  238. package/dist/middleware/types.js.map +0 -1
  239. package/dist/modules/a2a/A2AClientWrapper.d.ts +0 -1
  240. package/dist/modules/a2a/A2AClientWrapper.js +0 -2
  241. package/dist/modules/a2a/A2AClientWrapper.js.map +0 -1
  242. package/dist/modules/apiAgUiModule.d.ts +0 -1
  243. package/dist/modules/apiAgUiModule.js +0 -2
  244. package/dist/modules/apiAgUiModule.js.map +0 -1
  245. package/dist/modules/interactiveSessionModule.d.ts +0 -1
  246. package/dist/modules/interactiveSessionModule.js +0 -2
  247. package/dist/modules/interactiveSessionModule.js.map +0 -1
  248. package/dist/modules/reviewModule.d.ts +0 -1
  249. package/dist/modules/reviewModule.js +0 -2
  250. package/dist/modules/reviewModule.js.map +0 -1
  251. package/dist/modules/types.d.ts +0 -1
  252. package/dist/modules/types.js +0 -2
  253. package/dist/modules/types.js.map +0 -1
  254. package/dist/presets/anthropic.d.ts +0 -1
  255. package/dist/presets/anthropic.js +0 -2
  256. package/dist/presets/anthropic.js.map +0 -1
  257. package/dist/presets/deepseek.d.ts +0 -1
  258. package/dist/presets/deepseek.js +0 -2
  259. package/dist/presets/deepseek.js.map +0 -1
  260. package/dist/presets/fake.d.ts +0 -1
  261. package/dist/presets/fake.js +0 -2
  262. package/dist/presets/fake.js.map +0 -1
  263. package/dist/presets/google-genai.d.ts +0 -1
  264. package/dist/presets/google-genai.js +0 -2
  265. package/dist/presets/google-genai.js.map +0 -1
  266. package/dist/presets/groq.d.ts +0 -1
  267. package/dist/presets/groq.js +0 -2
  268. package/dist/presets/groq.js.map +0 -1
  269. package/dist/presets/openai.d.ts +0 -1
  270. package/dist/presets/openai.js +0 -2
  271. package/dist/presets/openai.js.map +0 -1
  272. package/dist/presets/openrouter.d.ts +0 -1
  273. package/dist/presets/openrouter.js +0 -2
  274. package/dist/presets/openrouter.js.map +0 -1
  275. package/dist/presets/vertexai.d.ts +0 -1
  276. package/dist/presets/vertexai.js +0 -2
  277. package/dist/presets/vertexai.js.map +0 -1
  278. package/dist/presets/xai.d.ts +0 -1
  279. package/dist/presets/xai.js +0 -2
  280. package/dist/presets/xai.js.map +0 -1
  281. package/dist/providers/file.d.ts +0 -1
  282. package/dist/providers/file.js +0 -2
  283. package/dist/providers/file.js.map +0 -1
  284. package/dist/providers/ghIssueProvider.d.ts +0 -1
  285. package/dist/providers/ghIssueProvider.js +0 -2
  286. package/dist/providers/ghIssueProvider.js.map +0 -1
  287. package/dist/providers/ghPrDiffProvider.d.ts +0 -1
  288. package/dist/providers/ghPrDiffProvider.js +0 -2
  289. package/dist/providers/ghPrDiffProvider.js.map +0 -1
  290. package/dist/providers/jiraIssueLegacyProvider.d.ts +0 -1
  291. package/dist/providers/jiraIssueLegacyProvider.js +0 -2
  292. package/dist/providers/jiraIssueLegacyProvider.js.map +0 -1
  293. package/dist/providers/jiraIssueProvider.d.ts +0 -1
  294. package/dist/providers/jiraIssueProvider.js +0 -2
  295. package/dist/providers/jiraIssueProvider.js.map +0 -1
  296. package/dist/providers/text.d.ts +0 -1
  297. package/dist/providers/text.js +0 -2
  298. package/dist/providers/text.js.map +0 -1
  299. package/dist/providers/types.d.ts +0 -1
  300. package/dist/providers/types.js +0 -2
  301. package/dist/providers/types.js.map +0 -1
  302. package/dist/state/artifactStore.d.ts +0 -1
  303. package/dist/state/artifactStore.js +0 -2
  304. package/dist/state/artifactStore.js.map +0 -1
  305. package/dist/tools/A2AAgentTool.d.ts +0 -1
  306. package/dist/tools/A2AAgentTool.js +0 -2
  307. package/dist/tools/A2AAgentTool.js.map +0 -1
  308. package/dist/tools/GthCustomToolkit.d.ts +0 -1
  309. package/dist/tools/GthCustomToolkit.js +0 -2
  310. package/dist/tools/GthCustomToolkit.js.map +0 -1
  311. package/dist/tools/GthDevToolkit.d.ts +0 -1
  312. package/dist/tools/GthDevToolkit.js +0 -2
  313. package/dist/tools/GthDevToolkit.js.map +0 -1
  314. package/dist/tools/GthFileSystemToolkit.d.ts +0 -1
  315. package/dist/tools/GthFileSystemToolkit.js +0 -2
  316. package/dist/tools/GthFileSystemToolkit.js.map +0 -1
  317. package/dist/tools/binaryUtils.d.ts +0 -1
  318. package/dist/tools/binaryUtils.js +0 -2
  319. package/dist/tools/binaryUtils.js.map +0 -1
  320. package/dist/tools/gthJiraLogWorkTool.d.ts +0 -3
  321. package/dist/tools/gthJiraLogWorkTool.js +0 -37
  322. package/dist/tools/gthJiraLogWorkTool.js.map +0 -1
  323. package/dist/tools/gthStatusUpdateTool.d.ts +0 -1
  324. package/dist/tools/gthStatusUpdateTool.js +0 -2
  325. package/dist/tools/gthStatusUpdateTool.js.map +0 -1
  326. package/dist/tools/gthWebFetchTool.d.ts +0 -1
  327. package/dist/tools/gthWebFetchTool.js +0 -2
  328. package/dist/tools/gthWebFetchTool.js.map +0 -1
  329. package/dist/tools/showA2UISurfaceTool.d.ts +0 -1
  330. package/dist/tools/showA2UISurfaceTool.js +0 -2
  331. package/dist/tools/showA2UISurfaceTool.js.map +0 -1
  332. package/dist/tui/components/Transcript.d.ts +0 -15
  333. package/dist/tui/components/Transcript.js +0 -37
  334. package/dist/tui/components/Transcript.js.map +0 -1
  335. package/dist/tui/slashCommands.d.ts +0 -192
  336. package/dist/tui/slashCommands.js +0 -319
  337. package/dist/tui/slashCommands.js.map +0 -1
  338. package/dist/tui/terminal.d.ts +0 -14
  339. package/dist/tui/terminal.js +0 -20
  340. package/dist/tui/terminal.js.map +0 -1
  341. package/dist/utils/ProgressIndicator.d.ts +0 -1
  342. package/dist/utils/ProgressIndicator.js +0 -2
  343. package/dist/utils/ProgressIndicator.js.map +0 -1
  344. package/dist/utils/aiignoreUtils.d.ts +0 -1
  345. package/dist/utils/aiignoreUtils.js +0 -2
  346. package/dist/utils/aiignoreUtils.js.map +0 -1
  347. package/dist/utils/binaryOutputUtils.d.ts +0 -1
  348. package/dist/utils/binaryOutputUtils.js +0 -2
  349. package/dist/utils/binaryOutputUtils.js.map +0 -1
  350. package/dist/utils/consoleUtils.d.ts +0 -1
  351. package/dist/utils/consoleUtils.js +0 -2
  352. package/dist/utils/consoleUtils.js.map +0 -1
  353. package/dist/utils/debugUtils.d.ts +0 -1
  354. package/dist/utils/debugUtils.js +0 -2
  355. package/dist/utils/debugUtils.js.map +0 -1
  356. package/dist/utils/fileUtils.d.ts +0 -1
  357. package/dist/utils/fileUtils.js +0 -2
  358. package/dist/utils/fileUtils.js.map +0 -1
  359. package/dist/utils/globalConfigUtils.d.ts +0 -1
  360. package/dist/utils/globalConfigUtils.js +0 -2
  361. package/dist/utils/globalConfigUtils.js.map +0 -1
  362. package/dist/utils/llmUtils.d.ts +0 -1
  363. package/dist/utils/llmUtils.js +0 -2
  364. package/dist/utils/llmUtils.js.map +0 -1
  365. package/dist/utils/mcpUtils.d.ts +0 -1
  366. package/dist/utils/mcpUtils.js +0 -2
  367. package/dist/utils/mcpUtils.js.map +0 -1
  368. package/dist/utils/stringUtils.d.ts +0 -1
  369. package/dist/utils/stringUtils.js +0 -2
  370. package/dist/utils/stringUtils.js.map +0 -1
  371. package/dist/utils/systemUtils.d.ts +0 -1
  372. package/dist/utils/systemUtils.js +0 -2
  373. package/dist/utils/systemUtils.js.map +0 -1
  374. package/dist/utils/vertexaiUtils.d.ts +0 -1
  375. package/dist/utils/vertexaiUtils.js +0 -2
  376. package/dist/utils/vertexaiUtils.js.map +0 -1
package/README.md CHANGED
@@ -1,37 +1,52 @@
1
1
  # gaunt-sloth
2
2
 
3
- The main CLI application for Gaunt Sloth.
3
+ The main CLI application for Gaunt Sloth — the fat package that turns the `@gaunt-sloth/*`
4
+ libraries into the `gth` command.
4
5
 
5
6
  ## Contents
6
7
 
7
- - CLI entry point and commander-based command registration
8
- - Commands: `ask`, `review`, `pr`, `chat`, `code`, `init`, `get`, `api`
9
- - Command utilities and config setup
8
+ - CLI entry point, commander-based command registration, and the Ink TUI
9
+ - Commands: `ask`, `review`, `pr`, `chat`, `code`, `exec`, `init`, `config`, `get`, `api`,
10
+ `batch`, `eval`, `workflow`, `history`, `insights`, `models` — see
11
+ [docs/COMMANDS.md](https://github.com/pukeko-robotics/gaunt-sloth/blob/main/docs/COMMANDS.md)
10
12
  - Vendor package wiring (all LangChain provider packages)
11
- - Integration tests
12
13
 
13
14
  ## CLI Binaries
14
15
 
15
- The package registers four equivalent binary aliases:
16
+ The package registers three equivalent binary aliases:
16
17
 
17
- - `gaunt-sloth` (primary)
18
- - `gth`
19
- - `gsloth`
20
- - `gaunt-sloth-assistant` (back-compat alias for the former package name)
18
+ - `gth` (primary)
19
+ - `gsloth` (long-form alias)
20
+ - `gaunt-sloth` (package-name alias)
21
21
 
22
22
  ## Dependencies
23
23
 
24
24
  - `@gaunt-sloth/core`
25
25
  - `@gaunt-sloth/agent`
26
26
  - `@gaunt-sloth/review`
27
+ - `@gaunt-sloth/batch`
28
+ - `@gaunt-sloth/eval-reporter-junit`
27
29
  - `commander`
28
- - All LangChain vendor packages (anthropic, google-genai, groq, openai, vertexai, xai, etc.)
30
+ - All LangChain vendor packages (anthropic, google, groq, openai, xai, etc.)
29
31
 
30
32
  This is the only package in the workspace that pulls in AI vendor dependencies directly. All other packages treat vendors as optional peers.
31
33
 
32
- ## Re-exports
34
+ ## Not a library
33
35
 
34
- `gaunt-sloth` re-exports public APIs from the sub-packages for convenience, so common imports are available from a single entry point.
36
+ This package deliberately exports **no importable modules** — its `exports` map exposes only
37
+ `./package.json`. It is the CLI product: install it globally and run `gth`. To embed Gaunt Sloth
38
+ functionality in your own code, depend on the scoped packages instead — they are the supported
39
+ embeddable surface:
40
+
41
+ - [`@gaunt-sloth/core`](https://www.npmjs.com/package/@gaunt-sloth/core) — config resolution and
42
+ the provider factory
43
+ - [`@gaunt-sloth/agent`](https://www.npmjs.com/package/@gaunt-sloth/agent) — the agent runtime,
44
+ tools, and the AG-UI server
45
+ - [`@gaunt-sloth/review`](https://www.npmjs.com/package/@gaunt-sloth/review) — programmatic code
46
+ review (see its README for a worked embed example)
47
+
48
+ (Until 2.0 the app exposed a `./*` deep-path wildcard over a tree of re-export shims; the shims
49
+ are gone and the wildcard with them.)
35
50
 
36
51
  ## Installation
37
52
 
@@ -39,60 +54,55 @@ This is the only package in the workspace that pulls in AI vendor dependencies d
39
54
  npm install -g gaunt-sloth
40
55
  ```
41
56
 
42
- For full usage documentation see the [root README](../../README.md) and [docs/COMMANDS.md](../../docs/COMMANDS.md).
57
+ For full usage documentation see the [root README](https://github.com/pukeko-robotics/gaunt-sloth/blob/main/README.md) and [docs/COMMANDS.md](https://github.com/pukeko-robotics/gaunt-sloth/blob/main/docs/COMMANDS.md).
43
58
 
44
59
  ## ACP server (editor integration)
45
60
 
46
- Gaunt Sloth can run as an [Agent Client Protocol](https://agentclientprotocol.com/) (ACP)
47
- server, so an ACP host — Zed, JetBrains, a future Pukeko client — can spawn it as a coding
48
- agent. It speaks ACP JSON-RPC over **stdio** (no port, no flags beyond the switch below); the
49
- host launches it as a subprocess.
61
+ `gaunt-sloth --acp-agent` — and the standalone `gaunt-sloth-acp` binary — serve the
62
+ [Agent Client Protocol](https://agentclientprotocol.com/) over stdio, so an editor that speaks ACP
63
+ can drive Gaunt Sloth as its coding agent. Point the editor's agent configuration at either
64
+ command; it needs no arguments.
50
65
 
51
- Run it through this package:
66
+ **Both ACP v1 and ACP v2 are served**, and the version is taken from the host's own `initialize` —
67
+ there is nothing to configure. v1 is the stable protocol every shipping ACP editor uses today, Zed
68
+ included; v2 is a draft.
52
69
 
53
- ```bash
54
- npm install -g gaunt-sloth@alpha
55
- gaunt-sloth --acp-agent
56
- ```
70
+ **An ACP session runs as a coding session.** It resolves under the `code` command, so it takes its
71
+ filesystem access, approvals posture and tools from your `commands.code` config: it can run shell
72
+ commands, and it can edit and delete files in the directory the session was opened on.
57
73
 
58
- **Install the app (`gaunt-sloth`), not `@gaunt-sloth/agent`.** The agent package also ships a
59
- standalone `gaunt-sloth-acp` binary, but the LLM providers (`@langchain/anthropic`, `openai`,
60
- `google`, …) are `peerDependencies` of `@gaunt-sloth/core` that **only this app package
61
- declares as real dependencies**. A bare `@gaunt-sloth/agent` install leaves those peers unmet,
62
- so its ACP server has no provider to build a model from. `gaunt-sloth --acp-agent` runs the
63
- exact same ACP server but resolves providers out of the app's dependency tree, so every
64
- configured provider works. (`stdout` is the protocol channel and is kept clean — gsloth's
65
- status/config output is redirected to `stderr`.)
74
+ At the default approvals rung, `assisted`, the gate holds only the **shell** — a command it does not
75
+ clear reaches the editor as a permission request. **File changes are not prompted:** the agent
76
+ rewrites and deletes files in that directory without asking. `manual` is the rung that sends the
77
+ file tools to the editor as well — set `"approvals": "manual"` under `commands.code` to scope that
78
+ to editor sessions, or at the root to apply it everywhere. For a read-only editor agent instead, set
79
+ the mode:
66
80
 
67
- Provider credentials and model selection come from your usual gsloth config
68
- (`.gsloth.config.*` / env vars such as `ANTHROPIC_API_KEY`); the ACP server reads them via the
69
- same `initConfig` path as the CLI. Run the host from your project directory (or set its `cwd`)
70
- so config and the per-session workspace resolve correctly.
81
+ ```json
82
+ { "acp": { "mode": "chat" } }
83
+ ```
71
84
 
72
- ### Zed
85
+ which resolves the session under `commands.chat` instead — read-only filesystem, no shell.
73
86
 
74
- Add to Zed `settings.json` (or Settings -> External Agents -> Add Agent -> Custom Agent):
87
+ Files you attach to a message — an @-mention in Zed — reach the agent as a link it can open with its
88
+ file tools. Images and audio are not accepted; if a host sends them anyway the agent says so in its
89
+ reply rather than ignoring them silently.
75
90
 
76
- ```json
77
- {
78
- "agent_servers": {
79
- "Gaunt Sloth": {
80
- "type": "custom",
81
- "command": "gaunt-sloth",
82
- "args": ["--acp-agent"],
83
- "env": {}
84
- }
85
- }
86
- }
87
- ```
91
+ The editor is asked before a gated tool runs: a shell command the approvals gate stops arrives as
92
+ an ACP permission request, with the command, its working directory, and — when the AI rater
93
+ escalated it — the rater's reason.
94
+
95
+ One agent process serves one project. The working directory the editor opens the session with roots
96
+ config discovery, the file tools and the shell; a session for a different directory is refused, so
97
+ start a separate agent process per project.
88
98
 
89
- Point `command` at the global `gaunt-sloth` binary (after `npm install -g gaunt-sloth@alpha`),
90
- or at an absolute path to `cli.js` for a local build. Other ACP hosts (JetBrains, etc.) take
91
- the same `command` + `args` pair.
99
+ `gth api` runs the AG-UI server if you want a programmatic front door instead, and `gth chat` /
100
+ `gth code` run an interactive session in a terminal.
92
101
 
93
102
  ## Related packages
94
103
 
95
- - [`@gaunt-sloth/core`](../core) — Core utilities, config, and agent infrastructure
96
- - [`@gaunt-sloth/agent`](../agent) — Agent runtime, built-in tools, API/AG-UI/ACP server
97
- - [`@gaunt-sloth/review`](../review) — Review and Q&A modules with standalone CLI
98
- - [`gaunt-sloth`](../app) — Main CLI application (this package)
104
+ - [`@gaunt-sloth/core`](https://www.npmjs.com/package/@gaunt-sloth/core) — Core utilities, config, and agent infrastructure ([source](https://github.com/pukeko-robotics/gaunt-sloth/tree/main/packages/core))
105
+ - [`@gaunt-sloth/agent`](https://www.npmjs.com/package/@gaunt-sloth/agent) — Agent runtime, built-in tools, API/AG-UI server ([source](https://github.com/pukeko-robotics/gaunt-sloth/tree/main/packages/agent))
106
+ - [`@gaunt-sloth/review`](https://www.npmjs.com/package/@gaunt-sloth/review) — Review engine with content/requirement sources (GitHub, Jira, file, text) and standalone CLI ([source](https://github.com/pukeko-robotics/gaunt-sloth/tree/main/packages/review))
107
+ - [`@gaunt-sloth/batch`](https://www.npmjs.com/package/@gaunt-sloth/batch) — Batch / eval / workflow runtime ([source](https://github.com/pukeko-robotics/gaunt-sloth/tree/main/packages/batch))
108
+ - [`gaunt-sloth`](https://www.npmjs.com/package/gaunt-sloth) — Main CLI application (this package) ([source](https://github.com/pukeko-robotics/gaunt-sloth/tree/main/packages/app))
package/cli.js CHANGED
@@ -9,41 +9,37 @@ process.on('warning', (warning) => {
9
9
  console.warn(warning);
10
10
  });
11
11
 
12
- // --- ACP server bypass -----------------------------------------------------
13
- // `gaunt-sloth --acp-agent` runs the Agent Client Protocol (ACP) server instead
14
- // of the normal CLI, so an ACP host (Zed, JetBrains, a future Pukeko client) can
15
- // spawn the fat `gaunt-sloth` package as a coding-agent subprocess.
12
+ // --- ACP server ------------------------------------------------------------
13
+ // `gaunt-sloth --acp-agent` is the ACP (Agent Client Protocol) door into the fat
14
+ // `gaunt-sloth` package. It serves ACP over stdio — v1 or v2, whichever the host
15
+ // asks for — through the SAME startup as the standalone `gaunt-sloth-acp` bin, so
16
+ // the two doors cannot behave differently, including the redirect that keeps
17
+ // stdout free for JSON-RPC.
16
18
  //
17
- // Why route ACP through the app rather than the standalone `gaunt-sloth-acp`
18
- // binary in @gaunt-sloth/agent: the LLM providers (@langchain/anthropic, openai,
19
- // google, …) are peerDependencies of @gaunt-sloth/core, and only this app package
20
- // declares them as real dependencies. A bare `@gaunt-sloth/agent` install leaves
21
- // those peers unmet, so its ACP server has no providers to construct a model from.
22
- // Starting the same ACP server from here resolves providers out of the app's tree.
19
+ // The switch is handled here rather than left to fall through to the normal CLI,
20
+ // which would answer an ACP host with a chat session on stdout and hang it.
23
21
  //
24
- // ACP speaks JSON-RPC over stdio, so stdout MUST stay a clean protocol channel:
25
- // redirect console.log/info (used by initConfig/status output) to stderr BEFORE
26
- // touching config, exactly as the standalone `gaunt-sloth-acp` entry does.
22
+ // A startup failure goes to stderr: to an ACP host stdout is the JSON-RPC framing
23
+ // channel, so prose written there is a protocol error, not a message.
27
24
  if (process.argv.includes('--acp-agent')) {
28
- for (const method of ['log', 'info']) {
29
- console[method] = (...args) => process.stderr.write(args.join(' ') + '\n');
30
- }
31
- const [{ initConfig }, { displayError }, { startAcpServer }] = await Promise.all([
32
- import('@gaunt-sloth/core/config.js'),
33
- import('@gaunt-sloth/core/utils/consoleUtils.js'),
34
- import('@gaunt-sloth/agent'),
35
- ]);
25
+ const { setEntryPoint } = await import('@gaunt-sloth/core/utils/systemUtils.js');
26
+ setEntryPoint(import.meta.url);
27
+ const { startAcpServer } = await import('@gaunt-sloth/agent/modules/acp/acpStdio.js');
36
28
  try {
37
- const config = await initConfig({});
38
- await startAcpServer(config);
29
+ await startAcpServer();
39
30
  } catch (err) {
40
- displayError(`ACP server failed: ${err instanceof Error ? err.message : String(err)}`);
31
+ process.stderr.write(
32
+ `Gaunt Sloth ACP agent failed to start: ${err instanceof Error ? (err.stack ?? err.message) : String(err)}\n`
33
+ );
41
34
  process.exit(1);
42
35
  }
43
36
  } else {
44
37
  // This is a minimalistic entry point that sets the installDir in systemUtils
45
- // and delegates to the compiled TypeScript code in dist/cli.js
46
- const { setEntryPoint } = await import('./dist/utils/systemUtils.js');
38
+ // and delegates to the compiled TypeScript code in dist/cli.js.
39
+ // systemUtils lives in @gaunt-sloth/core (the app-side re-export shim died in
40
+ // GS2-2 B4); importing it from core directly binds the same module instance
41
+ // the rest of the app reads, so setEntryPoint state is shared as before.
42
+ const { setEntryPoint } = await import('@gaunt-sloth/core/utils/systemUtils.js');
47
43
 
48
44
  // Set the installation directory in systemUtils
49
45
  setEntryPoint(import.meta.url);
package/dist/cli.js CHANGED
@@ -1,6 +1,9 @@
1
1
  import { Command, Option } from 'commander';
2
2
  import { askCommand } from '#src/commands/askCommand.js';
3
3
  import { execCommand } from '#src/commands/execCommand.js';
4
+ import { batchCommand } from '#src/commands/batchCommand.js';
5
+ import { evalCommand } from '#src/commands/evalCommand.js';
6
+ import { workflowCommand } from '#src/commands/workflowCommand.js';
4
7
  import { initCommand } from '#src/commands/initCommand.js';
5
8
  import { reviewCommand } from '#src/commands/reviewCommand.js';
6
9
  import { prCommand } from '#src/commands/prCommand.js';
@@ -11,22 +14,35 @@ import { getCommand } from '#src/commands/getCommand.js';
11
14
  import { configCommand } from '#src/commands/configCommand.js';
12
15
  import { historyCommand } from '#src/commands/historyCommand.js';
13
16
  import { insightsCommand } from '#src/commands/insightsCommand.js';
14
- import { argv, getSlothVersion, readStdin } from '@gaunt-sloth/core/utils/systemUtils.js';
15
- import { coerceBooleanOrString } from '@gaunt-sloth/core/utils/consoleUtils.js';
17
+ import { modelsCommand } from '#src/commands/modelsCommand.js';
18
+ import { argv, exit, getSlothVersion, readStdin } from '@gaunt-sloth/core/utils/systemUtils.js';
19
+ import { commandSkipsStdin, resolveInvokedCommandName } from '#src/utils/stdinPolicy.js';
20
+ import { guardProgramConfigErrors } from '#src/utils/configErrorGuard.js';
21
+ import { coerceBooleanOrString, displayError } from '@gaunt-sloth/core/utils/consoleUtils.js';
22
+ import { installCrashHandler } from '@gaunt-sloth/core/utils/crashHandler.js';
23
+ // GS2-48 — install the process-level crash handler as early as possible, so an uncaughtException /
24
+ // unhandledRejection anywhere in the run writes a redacted debug snapshot to ~/.gsloth/debug-dumps/
25
+ // before the process dies. Idempotent and inert on a normal exit.
26
+ installCrashHandler();
16
27
  const program = new Command();
17
28
  program
18
- .name('gsloth')
29
+ .name('gth')
19
30
  .description('Gaunt Sloth reviewing your PRs')
20
31
  .version(getSlothVersion())
21
32
  .option('--verbose', 'Set LangChain/LangGraph to verbose mode, ' +
22
33
  'causing LangChain/LangGraph to log many details to the console. ' +
23
34
  'Consider using debugLog from config.ts for less intrusive debug logging.')
24
35
  .option('-c, --config <path>', 'Path to custom configuration file')
36
+ .option('-g, --global', 'Run with global configuration, bypassing project-level config')
25
37
  .option('-i, --identity-profile <identity>', 'Identity profile (separate config and prompts)')
38
+ .option('--profile <name>', 'Named config profile to run under (alias of --identity-profile; ' +
39
+ 'create one with `gth config profile create <name>`)')
26
40
  .option('-w, --write-output-to-file <value>', 'Write output to file. Accepts true/false or a filename. Shortcuts: -wn or -w0 for false.')
27
- .option('--tui', 'Force the interactive Ink TUI for chat/code sessions (overrides CI auto-off)')
41
+ .option('--tui', 'Force the interactive Ink TUI for chat/code sessions ' +
42
+ '(overrides GTH_NO_TUI, the tui config key and CI auto-off)')
28
43
  .option('--no-tui', 'Force the plain readline session for chat/code (disable the TUI)')
29
- .addOption(new Option('--nopipe').hideHelp(true));
44
+ .addOption(new Option('--nopipe').hideHelp(true))
45
+ .addOption(new Option('--no-pipe').hideHelp(true));
30
46
  const cliConfigOverrides = {};
31
47
  // Parse global options before binding any commands
32
48
  program.parseOptions(argv);
@@ -42,8 +58,29 @@ if (program.getOptionValue('config')) {
42
58
  // Set a custom config path
43
59
  cliConfigOverrides.customConfigPath = program.getOptionValue('config');
44
60
  }
45
- if (program.getOptionValue('identityProfile')) {
46
- cliConfigOverrides.identityProfile = program.getOptionValue('identityProfile');
61
+ // CFG-56 — `-g/--global` and `-c/--config` both choose WHERE configuration comes from, and
62
+ // honouring either one makes the other a silent no-op. Refuse the pair here, before anything is
63
+ // read, rather than quietly loading one source while the user watches for the other.
64
+ if (program.getOptionValue('global')) {
65
+ if (cliConfigOverrides.customConfigPath) {
66
+ displayError('--global and --config select conflicting configuration sources ' +
67
+ '(the global config in ~/.gsloth versus the named file). Pass only one.');
68
+ exit(1);
69
+ }
70
+ cliConfigOverrides.global = true;
71
+ }
72
+ // `--profile` (GS2-33) is the friendly alias of `-i/--identity-profile`: both select a named profile
73
+ // block (`.gsloth/.gsloth-settings/<name>/`). If BOTH are given and disagree, that is a mistake worth
74
+ // surfacing rather than silently picking one; identical values are harmless.
75
+ const identityProfileOpt = program.getOptionValue('identityProfile');
76
+ const profileOpt = program.getOptionValue('profile');
77
+ if (identityProfileOpt && profileOpt && identityProfileOpt !== profileOpt) {
78
+ displayError(`Conflicting profiles: --identity-profile "${identityProfileOpt}" and --profile "${profileOpt}". ` +
79
+ 'Pass only one (they are aliases).');
80
+ exit(1);
81
+ }
82
+ if (profileOpt ?? identityProfileOpt) {
83
+ cliConfigOverrides.identityProfile = profileOpt ?? identityProfileOpt;
47
84
  }
48
85
  // Tri-state TUI flag: leave `tui` undefined (auto-detect) unless the user explicitly passed
49
86
  // `--tui` or `--no-tui`. Commander's `--no-tui` defaults the value to `true`, so we key off
@@ -65,6 +102,9 @@ reviewCommand(program, cliConfigOverrides);
65
102
  prCommand(program, cliConfigOverrides);
66
103
  askCommand(program, cliConfigOverrides);
67
104
  execCommand(program, cliConfigOverrides);
105
+ batchCommand(program, cliConfigOverrides);
106
+ evalCommand(program, cliConfigOverrides);
107
+ workflowCommand(program, cliConfigOverrides);
68
108
  chatCommand(program, cliConfigOverrides);
69
109
  codeCommand(program, cliConfigOverrides);
70
110
  apiCommand(program, cliConfigOverrides);
@@ -74,5 +114,22 @@ configCommand(program, cliConfigOverrides);
74
114
  // default or --db) and do not build the LLM, so they stay decoupled from config/provider setup.
75
115
  historyCommand(program);
76
116
  insightsCommand(program);
77
- await readStdin(program);
117
+ // GS2-6 (B16) — model catalog: lists providers/models enriched with models.dev cost/limit metadata.
118
+ // Read-only; enrichment never gates what `/v1/models` reports as callable.
119
+ modelsCommand(program);
120
+ // BATCH-11 (#405 gotcha #5): `eval`/`batch` never consume piped stdin, so they must not block
121
+ // waiting for stdin EOF before dispatch — a scripted/CI `gth eval suite.yaml` inherits a non-TTY,
122
+ // non-closing stdin and would otherwise hang until EOF (or need `</dev/null`). Resolve the invoked
123
+ // subcommand from argv via commander's own operand parsing (so a `-c <path>` value or a file
124
+ // argument is never mistaken for the command name) and, for those commands, imply the existing
125
+ // `--no-pipe` fast path in readStdin. ask/review/pr etc. are untouched and still block-and-read a
126
+ // piped diff.
127
+ const invokedCommand = resolveInvokedCommandName(program.commands.map((command) => command.name()), program.parseOptions(argv).operands);
128
+ if (commandSkipsStdin(invokedCommand)) {
129
+ program.setOptionValue('nopipe', true);
130
+ }
131
+ // CFG-35 — the config loader raises a catchable error when a provider has no resolvable API key,
132
+ // so programmatic callers can classify it. For a person at a terminal there is nothing to classify,
133
+ // so the `gth` CLI makes the terminating choice here, once, instead of in every command action.
134
+ await readStdin(guardProgramConfigErrors(program));
78
135
  //# sourceMappingURL=cli.js.map
package/dist/cli.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,WAAW,CAAC;AAC5C,OAAO,EAAE,UAAU,EAAE,MAAM,6BAA6B,CAAC;AACzD,OAAO,EAAE,WAAW,EAAE,MAAM,8BAA8B,CAAC;AAC3D,OAAO,EAAE,YAAY,EAAE,MAAM,+BAA+B,CAAC;AAC7D,OAAO,EAAE,WAAW,EAAE,MAAM,8BAA8B,CAAC;AAC3D,OAAO,EAAE,eAAe,EAAE,MAAM,kCAAkC,CAAC;AACnE,OAAO,EAAE,WAAW,EAAE,MAAM,8BAA8B,CAAC;AAC3D,OAAO,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AAC/D,OAAO,EAAE,SAAS,EAAE,MAAM,4BAA4B,CAAC;AACvD,OAAO,EAAE,WAAW,EAAE,MAAM,8BAA8B,CAAC;AAC3D,OAAO,EAAE,WAAW,EAAE,MAAM,8BAA8B,CAAC;AAC3D,OAAO,EAAE,UAAU,EAAE,MAAM,6BAA6B,CAAC;AACzD,OAAO,EAAE,UAAU,EAAE,MAAM,6BAA6B,CAAC;AACzD,OAAO,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AAC/D,OAAO,EAAE,cAAc,EAAE,MAAM,iCAAiC,CAAC;AACjE,OAAO,EAAE,eAAe,EAAE,MAAM,kCAAkC,CAAC;AACnE,OAAO,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AAC/D,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,eAAe,EAAE,SAAS,EAAE,MAAM,wCAAwC,CAAC;AAChG,OAAO,EAAE,iBAAiB,EAAE,yBAAyB,EAAE,MAAM,2BAA2B,CAAC;AACzF,OAAO,EAAE,wBAAwB,EAAE,MAAM,gCAAgC,CAAC;AAG1E,OAAO,EAAE,qBAAqB,EAAE,YAAY,EAAE,MAAM,yCAAyC,CAAC;AAC9F,OAAO,EAAE,mBAAmB,EAAE,MAAM,yCAAyC,CAAC;AAE9E,mGAAmG;AACnG,oGAAoG;AACpG,kEAAkE;AAClE,mBAAmB,EAAE,CAAC;AAEtB,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAC;AAE9B,OAAO;KACJ,IAAI,CAAC,KAAK,CAAC;KACX,WAAW,CAAC,gCAAgC,CAAC;KAC7C,OAAO,CAAC,eAAe,EAAE,CAAC;KAC1B,MAAM,CACL,WAAW,EACX,2CAA2C;IACzC,kEAAkE;IAClE,0EAA0E,CAC7E;KACA,MAAM,CAAC,qBAAqB,EAAE,mCAAmC,CAAC;KAClE,MAAM,CAAC,cAAc,EAAE,+DAA+D,CAAC;KACvF,MAAM,CAAC,mCAAmC,EAAE,gDAAgD,CAAC;KAC7F,MAAM,CACL,kBAAkB,EAClB,kEAAkE;IAChE,qDAAqD,CACxD;KACA,MAAM,CACL,oCAAoC,EACpC,0FAA0F,CAC3F;KACA,MAAM,CACL,OAAO,EACP,uDAAuD;IACrD,4DAA4D,CAC/D;KACA,MAAM,CAAC,UAAU,EAAE,kEAAkE,CAAC;KACtF,SAAS,CAAC,IAAI,MAAM,CAAC,UAAU,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;KAChD,SAAS,CAAC,IAAI,MAAM,CAAC,WAAW,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC;AAErD,MAAM,kBAAkB,GAA+B,EAAE,CAAC;AAE1D,mDAAmD;AACnD,OAAO,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC;AAC3B,IAAI,OAAO,CAAC,cAAc,CAAC,SAAS,CAAC,EAAE,CAAC;IACtC;;;;OAIG;IACH,kBAAkB,CAAC,OAAO,GAAG,IAAI,CAAC;AACpC,CAAC;AACD,IAAI,OAAO,CAAC,cAAc,CAAC,QAAQ,CAAC,EAAE,CAAC;IACrC,2BAA2B;IAC3B,kBAAkB,CAAC,gBAAgB,GAAG,OAAO,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC;AACzE,CAAC;AACD,2FAA2F;AAC3F,gGAAgG;AAChG,qFAAqF;AACrF,IAAI,OAAO,CAAC,cAAc,CAAC,QAAQ,CAAC,EAAE,CAAC;IACrC,IAAI,kBAAkB,CAAC,gBAAgB,EAAE,CAAC;QACxC,YAAY,CACV,iEAAiE;YAC/D,wEAAwE,CAC3E,CAAC;QACF,IAAI,CAAC,CAAC,CAAC,CAAC;IACV,CAAC;IACD,kBAAkB,CAAC,MAAM,GAAG,IAAI,CAAC;AACnC,CAAC;AACD,qGAAqG;AACrG,sGAAsG;AACtG,6EAA6E;AAC7E,MAAM,kBAAkB,GAAG,OAAO,CAAC,cAAc,CAAC,iBAAiB,CAAC,CAAC;AACrE,MAAM,UAAU,GAAG,OAAO,CAAC,cAAc,CAAC,SAAS,CAAC,CAAC;AACrD,IAAI,kBAAkB,IAAI,UAAU,IAAI,kBAAkB,KAAK,UAAU,EAAE,CAAC;IAC1E,YAAY,CACV,6CAA6C,kBAAkB,oBAAoB,UAAU,KAAK;QAChG,mCAAmC,CACtC,CAAC;IACF,IAAI,CAAC,CAAC,CAAC,CAAC;AACV,CAAC;AACD,IAAI,UAAU,IAAI,kBAAkB,EAAE,CAAC;IACrC,kBAAkB,CAAC,eAAe,GAAG,UAAU,IAAI,kBAAkB,CAAC;AACxE,CAAC;AAED,4FAA4F;AAC5F,4FAA4F;AAC5F,mFAAmF;AACnF,IAAI,OAAO,CAAC,oBAAoB,CAAC,KAAK,CAAC,KAAK,KAAK,EAAE,CAAC;IAClD,kBAAkB,CAAC,GAAG,GAAG,OAAO,CAAC,cAAc,CAAC,KAAK,CAAC,CAAC;AACzD,CAAC;AAED,MAAM,WAAW,GAAG,OAAO,CAAC,cAAc,CAAC,mBAAmB,CAAC,CAAC;AAEhE,qEAAqE;AACrE,oEAAoE;AACpE,6EAA6E;AAC7E,MAAM,OAAO,GAAG,qBAAqB,CAAC,WAAW,CAAC,CAAC;AACnD,IAAI,OAAO,KAAK,SAAS,EAAE,CAAC;IAC1B,kBAAkB,CAAC,iBAAiB,GAAG,OAAO,CAAC;AACjD,CAAC;AAED,sEAAsE;AACtE,WAAW,CAAC,OAAO,CAAC,CAAC;AACrB,aAAa,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AAC3C,SAAS,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AACvC,UAAU,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AACxC,WAAW,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AACzC,YAAY,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AAC1C,WAAW,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AACzC,eAAe,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AAC7C,WAAW,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AACzC,WAAW,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AACzC,UAAU,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AACxC,UAAU,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AACxC,aAAa,CAAC,OAAO,EAAE,kBAAkB,CAAC,CAAC;AAC3C,mGAAmG;AACnG,gGAAgG;AAChG,cAAc,CAAC,OAAO,CAAC,CAAC;AACxB,eAAe,CAAC,OAAO,CAAC,CAAC;AACzB,oGAAoG;AACpG,2EAA2E;AAC3E,aAAa,CAAC,OAAO,CAAC,CAAC;AAEvB,8FAA8F;AAC9F,kGAAkG;AAClG,mGAAmG;AACnG,6FAA6F;AAC7F,+FAA+F;AAC/F,kGAAkG;AAClG,cAAc;AACd,MAAM,cAAc,GAAG,yBAAyB,CAC9C,OAAO,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC,EACjD,OAAO,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC,QAAQ,CACpC,CAAC;AACF,IAAI,iBAAiB,CAAC,cAAc,CAAC,EAAE,CAAC;IACtC,OAAO,CAAC,cAAc,CAAC,QAAQ,EAAE,IAAI,CAAC,CAAC;AACzC,CAAC;AAED,iGAAiG;AACjG,oGAAoG;AACpG,gGAAgG;AAChG,MAAM,SAAS,CAAC,wBAAwB,CAAC,OAAO,CAAC,CAAC,CAAC"}
@@ -0,0 +1,66 @@
1
+ /**
2
+ * @module adkEvalRunner
3
+ * BATCH-14 — the ADK (A2A) target's production runner builders for `gth eval`. The eval runner
4
+ * ({@link @gaunt-sloth/batch#runEvalSuite}) is target-agnostic: it consumes an injected
5
+ * {@link RunCellFn} (single-shot) and {@link RunConversationFn} (multi-turn) and grades whatever
6
+ * `answer` they produce with the SAME assertion surface used for the `gth-agent` target. This module
7
+ * builds those two functions for an EXTERNAL Google ADK agent, driving it over the A2A protocol via
8
+ * {@link A2AClientWrapper} (the existing `@a2a-js/sdk` wrapper) — the analogue of `batchCommand.ts`'s
9
+ * `buildProductionRunCell`/`buildProductionRunConversation` for the in-process gth agent.
10
+ *
11
+ * The A2A client is INJECTABLE (like `RunCellFn`/`RunConversationFn` themselves) so unit tests drive
12
+ * these builders against a FAKE client with no network and no live ADK agent — the live end-to-end
13
+ * validation is a separate node (BATCH-16).
14
+ *
15
+ * Honest boundaries (BATCH-14 design point 4): A2A exposes text (and file/data) parts plus task
16
+ * status/artifact events, but NOT the agent's intermediate tool/function calls — so the ADK outcomes
17
+ * never populate `tools`, and `must_call`/`must_not_call` are rejected at suite-parse time rather
18
+ * than silently passed. A2A likewise carries no token accounting, so `tokensInput`/`tokensOutput`
19
+ * are left unset (undefined), unlike the gth-agent path.
20
+ */
21
+ import type { AdkAgentTarget, RunCellFn, RunConversationFn } from '@gaunt-sloth/batch';
22
+ /** One A2A turn's result as the ADK runner needs it: the answer text plus the continuity handles to
23
+ * thread into follow-up turns. */
24
+ export interface AdkA2AResponse {
25
+ text: string;
26
+ contextId?: string;
27
+ taskId?: string;
28
+ }
29
+ /**
30
+ * The minimal A2A client the ADK runner depends on — a single `sendMessage(text, context?)` that
31
+ * returns text + continuity handles. Production wraps {@link A2AClientWrapper.sendMessageWithContext};
32
+ * tests inject a fake implementing exactly this. Kept deliberately narrow so a fake is trivial and
33
+ * the runner never reaches into the full SDK surface.
34
+ */
35
+ export interface AdkA2AClient {
36
+ sendMessage(text: string, context?: {
37
+ contextId?: string;
38
+ taskId?: string;
39
+ }): Promise<AdkA2AResponse>;
40
+ }
41
+ /** Builds an {@link AdkA2AClient} for a target — the injection seam for tests. */
42
+ export type AdkClientFactory = (target: AdkAgentTarget) => AdkA2AClient;
43
+ /** Production factory: a real {@link A2AClientWrapper} over the target's A2A endpoint, adapted to the
44
+ * narrow {@link AdkA2AClient} shape via its context-threading {@link A2AClientWrapper.sendMessageWithContext}. */
45
+ export declare const defaultAdkClientFactory: AdkClientFactory;
46
+ /**
47
+ * Build the injectable single-shot {@link RunCellFn} that drives ONE ADK agent turn over A2A: send
48
+ * the cell's prompt as the A2A message text and return the agent's text as the cell `answer`. A
49
+ * transport/agent error is contained as a failed cell (`ok:false`) so one bad case can never take the
50
+ * whole suite down — matching `buildProductionRunCell`'s discipline for the gth-agent path.
51
+ *
52
+ * `tools`/tokens are intentionally unset (A2A exposes neither); content assertions grade the answer.
53
+ */
54
+ export declare function buildAdkRunCell(target: AdkAgentTarget, createClient?: AdkClientFactory): RunCellFn;
55
+ /**
56
+ * Build the injectable multi-turn {@link RunConversationFn} that drives a whole scripted conversation
57
+ * against the ADK agent over A2A, threading the A2A `contextId` across turns so turn N sees turn
58
+ * N-1's context (an ADK agent keeps conversational memory by `contextId`). ONE client is built for
59
+ * the conversation; the first turn sends no context, and each subsequent turn carries the `contextId`
60
+ * the previous response returned.
61
+ *
62
+ * Returns one {@link TurnRunOutcome} per turn attempted. A turn that throws is recorded as a failed
63
+ * turn and ABORTS the conversation (the returned array is short) — the runner fails the un-run turns
64
+ * with a clear reason, exactly as it does for a gth-agent conversation that ended early.
65
+ */
66
+ export declare function buildAdkRunConversation(target: AdkAgentTarget, createClient?: AdkClientFactory): RunConversationFn;
@@ -0,0 +1,69 @@
1
+ import { A2AClientWrapper } from '@gaunt-sloth/agent/modules/a2a/A2AClientWrapper.js';
2
+ /** Production factory: a real {@link A2AClientWrapper} over the target's A2A endpoint, adapted to the
3
+ * narrow {@link AdkA2AClient} shape via its context-threading {@link A2AClientWrapper.sendMessageWithContext}. */
4
+ export const defaultAdkClientFactory = (target) => {
5
+ const wrapper = new A2AClientWrapper({
6
+ agentId: target.agentId ?? 'adk-agent',
7
+ agentUrl: target.url,
8
+ });
9
+ return {
10
+ sendMessage: (text, context) => wrapper.sendMessageWithContext(text, context),
11
+ };
12
+ };
13
+ /**
14
+ * Build the injectable single-shot {@link RunCellFn} that drives ONE ADK agent turn over A2A: send
15
+ * the cell's prompt as the A2A message text and return the agent's text as the cell `answer`. A
16
+ * transport/agent error is contained as a failed cell (`ok:false`) so one bad case can never take the
17
+ * whole suite down — matching `buildProductionRunCell`'s discipline for the gth-agent path.
18
+ *
19
+ * `tools`/tokens are intentionally unset (A2A exposes neither); content assertions grade the answer.
20
+ */
21
+ export function buildAdkRunCell(target, createClient = defaultAdkClientFactory) {
22
+ return async (cell) => {
23
+ try {
24
+ const client = createClient(target);
25
+ const { text } = await client.sendMessage(cell.content);
26
+ return { ok: true, answer: text };
27
+ }
28
+ catch (error) {
29
+ return { ok: false, error: error instanceof Error ? error.message : String(error) };
30
+ }
31
+ };
32
+ }
33
+ /**
34
+ * Build the injectable multi-turn {@link RunConversationFn} that drives a whole scripted conversation
35
+ * against the ADK agent over A2A, threading the A2A `contextId` across turns so turn N sees turn
36
+ * N-1's context (an ADK agent keeps conversational memory by `contextId`). ONE client is built for
37
+ * the conversation; the first turn sends no context, and each subsequent turn carries the `contextId`
38
+ * the previous response returned.
39
+ *
40
+ * Returns one {@link TurnRunOutcome} per turn attempted. A turn that throws is recorded as a failed
41
+ * turn and ABORTS the conversation (the returned array is short) — the runner fails the un-run turns
42
+ * with a clear reason, exactly as it does for a gth-agent conversation that ended early.
43
+ */
44
+ export function buildAdkRunConversation(target, createClient = defaultAdkClientFactory) {
45
+ return async (userMessages) => {
46
+ const client = createClient(target);
47
+ const outcomes = [];
48
+ let contextId;
49
+ for (const message of userMessages) {
50
+ try {
51
+ const response = await client.sendMessage(message, contextId ? { contextId } : undefined);
52
+ // Carry the server's contextId forward so the next turn continues the same conversation.
53
+ if (response.contextId)
54
+ contextId = response.contextId;
55
+ outcomes.push({ ok: true, answer: response.text });
56
+ }
57
+ catch (error) {
58
+ outcomes.push({
59
+ ok: false,
60
+ error: error instanceof Error ? error.message : String(error),
61
+ });
62
+ // A failed turn aborts the conversation — the runner marks the remaining turns FAILed.
63
+ break;
64
+ }
65
+ }
66
+ return outcomes;
67
+ };
68
+ }
69
+ //# sourceMappingURL=adkEvalRunner.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"adkEvalRunner.js","sourceRoot":"","sources":["../../src/commands/adkEvalRunner.ts"],"names":[],"mappings":"AA0BA,OAAO,EAAE,gBAAgB,EAAE,MAAM,oDAAoD,CAAC;AA0BtF;kHACkH;AAClH,MAAM,CAAC,MAAM,uBAAuB,GAAqB,CAAC,MAAM,EAAE,EAAE;IAClE,MAAM,OAAO,GAAG,IAAI,gBAAgB,CAAC;QACnC,OAAO,EAAE,MAAM,CAAC,OAAO,IAAI,WAAW;QACtC,QAAQ,EAAE,MAAM,CAAC,GAAG;KACrB,CAAC,CAAC;IACH,OAAO;QACL,WAAW,EAAE,CAAC,IAAI,EAAE,OAAO,EAAE,EAAE,CAAC,OAAO,CAAC,sBAAsB,CAAC,IAAI,EAAE,OAAO,CAAC;KAC9E,CAAC;AACJ,CAAC,CAAC;AAEF;;;;;;;GAOG;AACH,MAAM,UAAU,eAAe,CAC7B,MAAsB,EACtB,YAAY,GAAqB,uBAAuB;IAExD,OAAO,KAAK,EAAE,IAAI,EAAE,EAAE;QACpB,IAAI,CAAC;YACH,MAAM,MAAM,GAAG,YAAY,CAAC,MAAM,CAAC,CAAC;YACpC,MAAM,EAAE,IAAI,EAAE,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;YACxD,OAAO,EAAE,EAAE,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC;QACpC,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC;QACtF,CAAC;IACH,CAAC,CAAC;AACJ,CAAC;AAED;;;;;;;;;;GAUG;AACH,MAAM,UAAU,uBAAuB,CACrC,MAAsB,EACtB,YAAY,GAAqB,uBAAuB;IAExD,OAAO,KAAK,EAAE,YAAY,EAAE,EAAE;QAC5B,MAAM,MAAM,GAAG,YAAY,CAAC,MAAM,CAAC,CAAC;QACpC,MAAM,QAAQ,GAAqB,EAAE,CAAC;QACtC,IAAI,SAA6B,CAAC;QAElC,KAAK,MAAM,OAAO,IAAI,YAAY,EAAE,CAAC;YACnC,IAAI,CAAC;gBACH,MAAM,QAAQ,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,OAAO,EAAE,SAAS,CAAC,CAAC,CAAC,EAAE,SAAS,EAAE,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC;gBAC1F,yFAAyF;gBACzF,IAAI,QAAQ,CAAC,SAAS;oBAAE,SAAS,GAAG,QAAQ,CAAC,SAAS,CAAC;gBACvD,QAAQ,CAAC,IAAI,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,MAAM,EAAE,QAAQ,CAAC,IAAI,EAAE,CAAC,CAAC;YACrD,CAAC;YAAC,OAAO,KAAK,EAAE,CAAC;gBACf,QAAQ,CAAC,IAAI,CAAC;oBACZ,EAAE,EAAE,KAAK;oBACT,KAAK,EAAE,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC;iBAC9D,CAAC,CAAC;gBACH,uFAAuF;gBACvF,MAAM;YACR,CAAC;QACH,CAAC;QAED,OAAO,QAAQ,CAAC;IAClB,CAAC,CAAC;AACJ,CAAC"}
@@ -0,0 +1,90 @@
1
+ import type { AgUiAgentTarget, RunCellFn, RunConversationFn } from '@gaunt-sloth/batch';
2
+ /** One AG-UI message as sent in the `RunAgentInput.messages` array. The eval only ever sends `user`
3
+ * turns and, for conversation continuity, the `assistant` answers it assembled — the minimal shape
4
+ * the reference server's `convertMessage` consumes (`{ id, role, content }`). */
5
+ export interface AgUiMessage {
6
+ id: string;
7
+ role: 'user' | 'assistant';
8
+ content: string;
9
+ }
10
+ /** The `RunAgentInput` fields the runner drives per request. `threadId` provides conversation
11
+ * continuity (stable across the turns of ONE conversation); `runId` is fresh per request. */
12
+ export interface AgUiRunInput {
13
+ threadId: string;
14
+ runId: string;
15
+ messages: AgUiMessage[];
16
+ }
17
+ /** One AG-UI run's decoded result: the answer assembled from `TEXT_MESSAGE_CONTENT` deltas and the
18
+ * tool names captured from `TOOL_CALL_START` events (empty array when the agent called no tools —
19
+ * NOT undefined, so `must_not_call` grades against a real, present trace). */
20
+ export interface AgUiRunResult {
21
+ answer: string;
22
+ tools: string[];
23
+ }
24
+ /**
25
+ * The minimal AG-UI client the runner depends on — a single `run(input)` that POSTs one
26
+ * `RunAgentInput` and returns the decoded answer + tools. Production wraps {@link createAgUiClient};
27
+ * tests inject a fake implementing exactly this. Kept deliberately narrow so a fake is trivial and
28
+ * the runner never reaches into transport details.
29
+ */
30
+ export interface AgUiClient {
31
+ run(input: AgUiRunInput): Promise<AgUiRunResult>;
32
+ }
33
+ /** Builds an {@link AgUiClient} for a target — the injection seam for tests. */
34
+ export type AgUiClientFactory = (target: AgUiAgentTarget) => AgUiClient;
35
+ /** The `fetch` seam — global `fetch` in production, a fake in tests (so the real POST-body
36
+ * construction + SSE decode are exercised with no network). */
37
+ export type FetchLike = typeof fetch;
38
+ /**
39
+ * Default deadline for one AG-UI run (fetch + full SSE decode). The runner has no configured
40
+ * timeout, so this bounds a server that hangs at EITHER phase — one that accepts the POST but never
41
+ * sends response headers (the `fetch` await never returns) OR one that opens the stream but never
42
+ * emits `RUN_FINISHED`: past it the case FAILS with a clear error instead of wedging the process.
43
+ * Injectable per-client for tests.
44
+ */
45
+ export declare const AG_UI_RUN_TIMEOUT_MS = 120000;
46
+ /**
47
+ * Create a real {@link AgUiClient} that drives the target's AG-UI run endpoint over HTTP/SSE. Each
48
+ * `run` POSTs a `RunAgentInput` to `{url}/agents/{agentId}/run` and decodes the SSE response via
49
+ * {@link decodeAgUiStream}. A non-2xx response, an absent body, a `RUN_ERROR` event, a truncated
50
+ * stream, or a run that exceeds `timeoutMs` all throw — the runner builders contain that into a
51
+ * failed cell (`ok:false`).
52
+ *
53
+ * The WHOLE run is bounded by `timeoutMs` (default {@link AG_UI_RUN_TIMEOUT_MS}) via a single
54
+ * deadline armed BEFORE the fetch. BOTH phases are raced against it: the `fetch` await (so a server
55
+ * that accepts the POST but never sends response headers is bounded too) AND the SSE decode (so a
56
+ * body that opens but never ends still fails the case rather than hanging). Racing — not the abort
57
+ * signal — is the load-bearing mechanism, since a transport may ignore the abort; on timeout the
58
+ * `AbortController` is fired anyway to free a real socket. On a non-200 the unread body is cancelled
59
+ * first so its socket is released.
60
+ *
61
+ * `fetchImpl` defaults to global `fetch`; tests pass a fake returning a synthetic SSE `Response` so
62
+ * the body construction + decode are exercised without a network or a live server.
63
+ */
64
+ export declare function createAgUiClient(target: AgUiAgentTarget, fetchImpl?: FetchLike, timeoutMs?: number): AgUiClient;
65
+ /** Production factory: a real HTTP/SSE {@link AgUiClient} over the target's AG-UI endpoint. */
66
+ export declare const defaultAgUiClientFactory: AgUiClientFactory;
67
+ /**
68
+ * Build the injectable single-shot {@link RunCellFn} that drives ONE AG-UI run: send the cell's
69
+ * prompt as the sole `user` message (fresh `threadId`/`runId`) and return the agent's assembled text
70
+ * as the cell `answer` plus the tool names captured from the stream as `tools`. A transport/stream
71
+ * error is contained as a failed cell (`ok:false`) so one bad case can never take the whole suite
72
+ * down — matching `buildProductionRunCell`'s discipline for the gth-agent path.
73
+ *
74
+ * `tools` is ALWAYS populated (possibly `[]`) — the AG-UI wire exposes the trace — so
75
+ * `must_call`/`must_not_call` grade normally, the key difference from the ADK target.
76
+ */
77
+ export declare function buildAgUiRunCell(target: AgUiAgentTarget, createClient?: AgUiClientFactory): RunCellFn;
78
+ /**
79
+ * Build the injectable multi-turn {@link RunConversationFn} that drives a whole scripted conversation
80
+ * against the AG-UI agent, threading continuity via the `messages` array + a STABLE `threadId` across
81
+ * the turns of ONE conversation: each turn appends its `user` message, POSTs the accumulated history
82
+ * under the same `threadId`, then appends the assistant's answer so the next turn's request carries
83
+ * it. ONE `threadId` for the whole conversation; a fresh `runId` per turn.
84
+ *
85
+ * Returns one {@link TurnRunOutcome} per turn attempted (answer + per-turn tool trace). A turn that
86
+ * throws is recorded as a failed turn and ABORTS the conversation (the returned array is short) — the
87
+ * runner fails the un-run turns with a clear reason, exactly as it does for a gth-agent conversation
88
+ * that ended early.
89
+ */
90
+ export declare function buildAgUiRunConversation(target: AgUiAgentTarget, createClient?: AgUiClientFactory): RunConversationFn;