@copilotkit/aimock 1.43.0 → 1.45.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 (396) hide show
  1. package/.claude-plugin/marketplace.json +1 -1
  2. package/.claude-plugin/plugin.json +1 -1
  3. package/CHANGELOG.md +46 -0
  4. package/README.md +14 -2
  5. package/dist/agui-handler.d.ts.map +1 -1
  6. package/dist/aimock-cli.cjs +31 -5
  7. package/dist/aimock-cli.cjs.map +1 -1
  8. package/dist/aimock-cli.d.cts.map +1 -1
  9. package/dist/aimock-cli.d.ts.map +1 -1
  10. package/dist/aimock-cli.js +31 -5
  11. package/dist/aimock-cli.js.map +1 -1
  12. package/dist/bedrock-converse.cjs +344 -43
  13. package/dist/bedrock-converse.cjs.map +1 -1
  14. package/dist/bedrock-converse.d.cts.map +1 -1
  15. package/dist/bedrock-converse.d.ts.map +1 -1
  16. package/dist/bedrock-converse.js +345 -44
  17. package/dist/bedrock-converse.js.map +1 -1
  18. package/dist/bedrock.cjs +195 -42
  19. package/dist/bedrock.cjs.map +1 -1
  20. package/dist/bedrock.d.cts.map +1 -1
  21. package/dist/bedrock.d.ts.map +1 -1
  22. package/dist/bedrock.js +196 -43
  23. package/dist/bedrock.js.map +1 -1
  24. package/dist/chaos.cjs +9 -5
  25. package/dist/chaos.cjs.map +1 -1
  26. package/dist/chaos.d.cts.map +1 -1
  27. package/dist/chaos.d.ts.map +1 -1
  28. package/dist/chaos.js +10 -7
  29. package/dist/chaos.js.map +1 -1
  30. package/dist/cli.cjs +238 -9
  31. package/dist/cli.cjs.map +1 -1
  32. package/dist/cli.js +242 -13
  33. package/dist/cli.js.map +1 -1
  34. package/dist/cohere.cjs +159 -72
  35. package/dist/cohere.cjs.map +1 -1
  36. package/dist/cohere.d.cts.map +1 -1
  37. package/dist/cohere.d.ts.map +1 -1
  38. package/dist/cohere.js +160 -73
  39. package/dist/cohere.js.map +1 -1
  40. package/dist/config-loader.cjs +63 -5
  41. package/dist/config-loader.cjs.map +1 -1
  42. package/dist/config-loader.d.cts +37 -4
  43. package/dist/config-loader.d.cts.map +1 -1
  44. package/dist/config-loader.d.ts +37 -4
  45. package/dist/config-loader.d.ts.map +1 -1
  46. package/dist/config-loader.js +63 -5
  47. package/dist/config-loader.js.map +1 -1
  48. package/dist/constants.cjs +8 -0
  49. package/dist/constants.cjs.map +1 -1
  50. package/dist/constants.d.cts +6 -2
  51. package/dist/constants.d.ts +6 -2
  52. package/dist/constants.js +8 -1
  53. package/dist/constants.js.map +1 -1
  54. package/dist/echo-text.cjs +65 -0
  55. package/dist/echo-text.cjs.map +1 -0
  56. package/dist/echo-text.d.cts +22 -0
  57. package/dist/echo-text.d.cts.map +1 -0
  58. package/dist/echo-text.d.ts +22 -0
  59. package/dist/echo-text.d.ts.map +1 -0
  60. package/dist/echo-text.js +65 -0
  61. package/dist/echo-text.js.map +1 -0
  62. package/dist/embeddings.cjs +18 -1
  63. package/dist/embeddings.cjs.map +1 -1
  64. package/dist/embeddings.d.cts +1 -1
  65. package/dist/embeddings.d.cts.map +1 -1
  66. package/dist/embeddings.d.ts +1 -1
  67. package/dist/embeddings.d.ts.map +1 -1
  68. package/dist/embeddings.js +18 -1
  69. package/dist/embeddings.js.map +1 -1
  70. package/dist/fakes-plugin.cjs +131 -0
  71. package/dist/fakes-plugin.cjs.map +1 -0
  72. package/dist/fakes-plugin.d.cts +23 -0
  73. package/dist/fakes-plugin.d.cts.map +1 -0
  74. package/dist/fakes-plugin.d.ts +23 -0
  75. package/dist/fakes-plugin.d.ts.map +1 -0
  76. package/dist/fakes-plugin.js +127 -0
  77. package/dist/fakes-plugin.js.map +1 -0
  78. package/dist/files.cjs +9 -11
  79. package/dist/files.cjs.map +1 -1
  80. package/dist/files.d.cts.map +1 -1
  81. package/dist/files.d.ts.map +1 -1
  82. package/dist/files.js +10 -13
  83. package/dist/files.js.map +1 -1
  84. package/dist/fine-tuning.cjs +1 -19
  85. package/dist/fine-tuning.cjs.map +1 -1
  86. package/dist/fine-tuning.d.cts.map +1 -1
  87. package/dist/fine-tuning.d.ts.map +1 -1
  88. package/dist/fine-tuning.js +2 -20
  89. package/dist/fine-tuning.js.map +1 -1
  90. package/dist/fixture-loader-services.cjs +116 -0
  91. package/dist/fixture-loader-services.cjs.map +1 -0
  92. package/dist/fixture-loader-services.d.cts +48 -0
  93. package/dist/fixture-loader-services.d.cts.map +1 -0
  94. package/dist/fixture-loader-services.d.ts +48 -0
  95. package/dist/fixture-loader-services.d.ts.map +1 -0
  96. package/dist/fixture-loader-services.js +114 -0
  97. package/dist/fixture-loader-services.js.map +1 -0
  98. package/dist/fixture-loader.cjs +552 -29
  99. package/dist/fixture-loader.cjs.map +1 -1
  100. package/dist/fixture-loader.d.cts +140 -2
  101. package/dist/fixture-loader.d.cts.map +1 -1
  102. package/dist/fixture-loader.d.ts +140 -2
  103. package/dist/fixture-loader.d.ts.map +1 -1
  104. package/dist/fixture-loader.js +542 -31
  105. package/dist/fixture-loader.js.map +1 -1
  106. package/dist/gemini-embeddings.cjs +42 -2
  107. package/dist/gemini-embeddings.cjs.map +1 -1
  108. package/dist/gemini-embeddings.js +43 -3
  109. package/dist/gemini-embeddings.js.map +1 -1
  110. package/dist/gemini-interactions.cjs +288 -52
  111. package/dist/gemini-interactions.cjs.map +1 -1
  112. package/dist/gemini-interactions.d.cts.map +1 -1
  113. package/dist/gemini-interactions.d.ts.map +1 -1
  114. package/dist/gemini-interactions.js +289 -53
  115. package/dist/gemini-interactions.js.map +1 -1
  116. package/dist/gemini.cjs +234 -38
  117. package/dist/gemini.cjs.map +1 -1
  118. package/dist/gemini.d.cts.map +1 -1
  119. package/dist/gemini.d.ts.map +1 -1
  120. package/dist/gemini.js +235 -39
  121. package/dist/gemini.js.map +1 -1
  122. package/dist/helpers.cjs +1157 -12
  123. package/dist/helpers.cjs.map +1 -1
  124. package/dist/helpers.d.cts +85 -4
  125. package/dist/helpers.d.cts.map +1 -1
  126. package/dist/helpers.d.ts +85 -4
  127. package/dist/helpers.d.ts.map +1 -1
  128. package/dist/helpers.js +1113 -14
  129. package/dist/helpers.js.map +1 -1
  130. package/dist/images.cjs +3 -2
  131. package/dist/images.cjs.map +1 -1
  132. package/dist/images.js +3 -2
  133. package/dist/images.js.map +1 -1
  134. package/dist/index.cjs +39 -1
  135. package/dist/index.d.cts +11 -4
  136. package/dist/index.d.ts +11 -4
  137. package/dist/index.js +11 -4
  138. package/dist/jest.cjs +43 -14
  139. package/dist/jest.cjs.map +1 -1
  140. package/dist/jest.d.cts +47 -5
  141. package/dist/jest.d.cts.map +1 -1
  142. package/dist/jest.d.ts +47 -5
  143. package/dist/jest.d.ts.map +1 -1
  144. package/dist/jest.js +45 -16
  145. package/dist/jest.js.map +1 -1
  146. package/dist/journal.cjs +155 -13
  147. package/dist/journal.cjs.map +1 -1
  148. package/dist/journal.d.cts +54 -4
  149. package/dist/journal.d.cts.map +1 -1
  150. package/dist/journal.d.ts +54 -4
  151. package/dist/journal.d.ts.map +1 -1
  152. package/dist/journal.js +155 -13
  153. package/dist/journal.js.map +1 -1
  154. package/dist/live-sanitize.cjs +4 -32
  155. package/dist/live-sanitize.cjs.map +1 -1
  156. package/dist/live-sanitize.js +4 -32
  157. package/dist/live-sanitize.js.map +1 -1
  158. package/dist/llmock.cjs +204 -39
  159. package/dist/llmock.cjs.map +1 -1
  160. package/dist/llmock.d.cts +51 -1
  161. package/dist/llmock.d.cts.map +1 -1
  162. package/dist/llmock.d.ts +51 -1
  163. package/dist/llmock.d.ts.map +1 -1
  164. package/dist/llmock.js +206 -41
  165. package/dist/llmock.js.map +1 -1
  166. package/dist/mcp-fakes-mount.cjs +217 -0
  167. package/dist/mcp-fakes-mount.cjs.map +1 -0
  168. package/dist/mcp-fakes-mount.js +211 -0
  169. package/dist/mcp-fakes-mount.js.map +1 -0
  170. package/dist/mcp-fakes-report.cjs +111 -0
  171. package/dist/mcp-fakes-report.cjs.map +1 -0
  172. package/dist/mcp-fakes-report.d.cts +40 -0
  173. package/dist/mcp-fakes-report.d.cts.map +1 -0
  174. package/dist/mcp-fakes-report.d.ts +40 -0
  175. package/dist/mcp-fakes-report.d.ts.map +1 -0
  176. package/dist/mcp-fakes-report.js +107 -0
  177. package/dist/mcp-fakes-report.js.map +1 -0
  178. package/dist/mcp-fakes.cjs +1942 -0
  179. package/dist/mcp-fakes.cjs.map +1 -0
  180. package/dist/mcp-fakes.d.cts +504 -0
  181. package/dist/mcp-fakes.d.cts.map +1 -0
  182. package/dist/mcp-fakes.d.ts +504 -0
  183. package/dist/mcp-fakes.d.ts.map +1 -0
  184. package/dist/mcp-fakes.js +1937 -0
  185. package/dist/mcp-fakes.js.map +1 -0
  186. package/dist/mcp-handler.cjs +534 -27
  187. package/dist/mcp-handler.cjs.map +1 -1
  188. package/dist/mcp-handler.d.cts +49 -0
  189. package/dist/mcp-handler.d.cts.map +1 -0
  190. package/dist/mcp-handler.d.ts +49 -0
  191. package/dist/mcp-handler.d.ts.map +1 -0
  192. package/dist/mcp-handler.js +530 -28
  193. package/dist/mcp-handler.js.map +1 -1
  194. package/dist/mcp-mock.cjs +326 -47
  195. package/dist/mcp-mock.cjs.map +1 -1
  196. package/dist/mcp-mock.d.cts +97 -1
  197. package/dist/mcp-mock.d.cts.map +1 -1
  198. package/dist/mcp-mock.d.ts +97 -1
  199. package/dist/mcp-mock.d.ts.map +1 -1
  200. package/dist/mcp-mock.js +327 -48
  201. package/dist/mcp-mock.js.map +1 -1
  202. package/dist/mcp-recorder.cjs +1224 -0
  203. package/dist/mcp-recorder.cjs.map +1 -0
  204. package/dist/mcp-recorder.d.cts +108 -0
  205. package/dist/mcp-recorder.d.cts.map +1 -0
  206. package/dist/mcp-recorder.d.ts +108 -0
  207. package/dist/mcp-recorder.d.ts.map +1 -0
  208. package/dist/mcp-recorder.js +1215 -0
  209. package/dist/mcp-recorder.js.map +1 -0
  210. package/dist/mcp-stub.cjs +5 -1
  211. package/dist/mcp-stub.d.cts +3 -1
  212. package/dist/mcp-stub.d.ts +3 -1
  213. package/dist/mcp-stub.js +3 -1
  214. package/dist/mcp-types.d.cts +6 -0
  215. package/dist/mcp-types.d.ts +6 -0
  216. package/dist/message-text.cjs +192 -0
  217. package/dist/message-text.cjs.map +1 -0
  218. package/dist/message-text.d.cts +31 -0
  219. package/dist/message-text.d.cts.map +1 -0
  220. package/dist/message-text.d.ts +31 -0
  221. package/dist/message-text.d.ts.map +1 -0
  222. package/dist/message-text.js +184 -0
  223. package/dist/message-text.js.map +1 -0
  224. package/dist/messages.cjs +400 -56
  225. package/dist/messages.cjs.map +1 -1
  226. package/dist/messages.d.cts.map +1 -1
  227. package/dist/messages.d.ts.map +1 -1
  228. package/dist/messages.js +401 -58
  229. package/dist/messages.js.map +1 -1
  230. package/dist/metrics.cjs +46 -66
  231. package/dist/metrics.cjs.map +1 -1
  232. package/dist/metrics.d.cts +14 -6
  233. package/dist/metrics.d.cts.map +1 -1
  234. package/dist/metrics.d.ts +14 -6
  235. package/dist/metrics.d.ts.map +1 -1
  236. package/dist/metrics.js +32 -40
  237. package/dist/metrics.js.map +1 -1
  238. package/dist/misbehavior.cjs +1523 -0
  239. package/dist/misbehavior.cjs.map +1 -0
  240. package/dist/misbehavior.d.cts +43 -0
  241. package/dist/misbehavior.d.cts.map +1 -0
  242. package/dist/misbehavior.d.ts +43 -0
  243. package/dist/misbehavior.d.ts.map +1 -0
  244. package/dist/misbehavior.js +1511 -0
  245. package/dist/misbehavior.js.map +1 -0
  246. package/dist/ollama.cjs +315 -113
  247. package/dist/ollama.cjs.map +1 -1
  248. package/dist/ollama.d.cts.map +1 -1
  249. package/dist/ollama.d.ts.map +1 -1
  250. package/dist/ollama.js +316 -114
  251. package/dist/ollama.js.map +1 -1
  252. package/dist/openapi.cjs +3405 -0
  253. package/dist/openapi.cjs.map +1 -0
  254. package/dist/openapi.d.cts +30 -0
  255. package/dist/openapi.d.cts.map +1 -0
  256. package/dist/openapi.d.ts +30 -0
  257. package/dist/openapi.d.ts.map +1 -0
  258. package/dist/openapi.js +3404 -0
  259. package/dist/openapi.js.map +1 -0
  260. package/dist/openrouter-video.cjs +4 -4
  261. package/dist/openrouter-video.cjs.map +1 -1
  262. package/dist/openrouter-video.d.cts.map +1 -1
  263. package/dist/openrouter-video.d.ts.map +1 -1
  264. package/dist/openrouter-video.js +4 -4
  265. package/dist/openrouter-video.js.map +1 -1
  266. package/dist/record-sanitize.cjs +231 -0
  267. package/dist/record-sanitize.cjs.map +1 -0
  268. package/dist/record-sanitize.js +224 -0
  269. package/dist/record-sanitize.js.map +1 -0
  270. package/dist/recorder.cjs +115 -6
  271. package/dist/recorder.cjs.map +1 -1
  272. package/dist/recorder.d.cts +2 -1
  273. package/dist/recorder.d.cts.map +1 -1
  274. package/dist/recorder.d.ts +2 -1
  275. package/dist/recorder.d.ts.map +1 -1
  276. package/dist/recorder.js +116 -8
  277. package/dist/recorder.js.map +1 -1
  278. package/dist/responses.cjs +701 -166
  279. package/dist/responses.cjs.map +1 -1
  280. package/dist/responses.d.cts +5 -13
  281. package/dist/responses.d.cts.map +1 -1
  282. package/dist/responses.d.ts +5 -13
  283. package/dist/responses.d.ts.map +1 -1
  284. package/dist/responses.js +699 -169
  285. package/dist/responses.js.map +1 -1
  286. package/dist/route-registry.cjs +951 -0
  287. package/dist/route-registry.cjs.map +1 -0
  288. package/dist/route-registry.d.cts +33 -0
  289. package/dist/route-registry.d.cts.map +1 -0
  290. package/dist/route-registry.d.ts +33 -0
  291. package/dist/route-registry.d.ts.map +1 -0
  292. package/dist/route-registry.js +866 -0
  293. package/dist/route-registry.js.map +1 -0
  294. package/dist/router.cjs +24 -2
  295. package/dist/router.cjs.map +1 -1
  296. package/dist/router.d.cts.map +1 -1
  297. package/dist/router.d.ts.map +1 -1
  298. package/dist/router.js +25 -4
  299. package/dist/router.js.map +1 -1
  300. package/dist/server.cjs +1159 -264
  301. package/dist/server.cjs.map +1 -1
  302. package/dist/server.d.cts +4 -1
  303. package/dist/server.d.cts.map +1 -1
  304. package/dist/server.d.ts +4 -1
  305. package/dist/server.d.ts.map +1 -1
  306. package/dist/server.js +1067 -172
  307. package/dist/server.js.map +1 -1
  308. package/dist/speech.cjs +4 -2
  309. package/dist/speech.cjs.map +1 -1
  310. package/dist/speech.js +4 -2
  311. package/dist/speech.js.map +1 -1
  312. package/dist/stream-collapse.cjs +236 -34
  313. package/dist/stream-collapse.cjs.map +1 -1
  314. package/dist/stream-collapse.d.cts +39 -4
  315. package/dist/stream-collapse.d.cts.map +1 -1
  316. package/dist/stream-collapse.d.ts +39 -4
  317. package/dist/stream-collapse.d.ts.map +1 -1
  318. package/dist/stream-collapse.js +235 -35
  319. package/dist/stream-collapse.js.map +1 -1
  320. package/dist/suite.cjs +1 -1
  321. package/dist/suite.js +1 -1
  322. package/dist/transcription.cjs +2 -2
  323. package/dist/transcription.cjs.map +1 -1
  324. package/dist/transcription.d.cts.map +1 -1
  325. package/dist/transcription.d.ts.map +1 -1
  326. package/dist/transcription.js +2 -2
  327. package/dist/transcription.js.map +1 -1
  328. package/dist/types.cjs +18 -0
  329. package/dist/types.cjs.map +1 -0
  330. package/dist/types.d.cts +516 -5
  331. package/dist/types.d.cts.map +1 -1
  332. package/dist/types.d.ts +516 -5
  333. package/dist/types.d.ts.map +1 -1
  334. package/dist/types.js +17 -0
  335. package/dist/types.js.map +1 -0
  336. package/dist/validate-cli.cjs +123 -33
  337. package/dist/validate-cli.cjs.map +1 -1
  338. package/dist/validate-cli.js +125 -35
  339. package/dist/validate-cli.js.map +1 -1
  340. package/dist/vector-stores.cjs +1180 -0
  341. package/dist/vector-stores.cjs.map +1 -0
  342. package/dist/vector-stores.d.cts +106 -0
  343. package/dist/vector-stores.d.cts.map +1 -0
  344. package/dist/vector-stores.d.ts +106 -0
  345. package/dist/vector-stores.d.ts.map +1 -0
  346. package/dist/vector-stores.js +1164 -0
  347. package/dist/vector-stores.js.map +1 -0
  348. package/dist/vector-types.d.cts.map +1 -1
  349. package/dist/version.cjs +45 -0
  350. package/dist/version.cjs.map +1 -0
  351. package/dist/version.js +44 -0
  352. package/dist/version.js.map +1 -0
  353. package/dist/video.cjs +19 -0
  354. package/dist/video.cjs.map +1 -1
  355. package/dist/video.d.cts.map +1 -1
  356. package/dist/video.d.ts.map +1 -1
  357. package/dist/video.js +19 -0
  358. package/dist/video.js.map +1 -1
  359. package/dist/vitest.cjs +77 -16
  360. package/dist/vitest.cjs.map +1 -1
  361. package/dist/vitest.d.cts +38 -5
  362. package/dist/vitest.d.cts.map +1 -1
  363. package/dist/vitest.d.ts +38 -5
  364. package/dist/vitest.d.ts.map +1 -1
  365. package/dist/vitest.js +78 -17
  366. package/dist/vitest.js.map +1 -1
  367. package/dist/watcher.cjs +6 -2
  368. package/dist/watcher.cjs.map +1 -1
  369. package/dist/watcher.js +6 -2
  370. package/dist/watcher.js.map +1 -1
  371. package/dist/ws-gemini-live.cjs +210 -101
  372. package/dist/ws-gemini-live.cjs.map +1 -1
  373. package/dist/ws-gemini-live.d.cts +9 -3
  374. package/dist/ws-gemini-live.d.cts.map +1 -1
  375. package/dist/ws-gemini-live.d.ts +9 -3
  376. package/dist/ws-gemini-live.d.ts.map +1 -1
  377. package/dist/ws-gemini-live.js +211 -102
  378. package/dist/ws-gemini-live.js.map +1 -1
  379. package/dist/ws-realtime.cjs +175 -62
  380. package/dist/ws-realtime.cjs.map +1 -1
  381. package/dist/ws-realtime.d.cts +8 -3
  382. package/dist/ws-realtime.d.cts.map +1 -1
  383. package/dist/ws-realtime.d.ts +8 -3
  384. package/dist/ws-realtime.d.ts.map +1 -1
  385. package/dist/ws-realtime.js +176 -63
  386. package/dist/ws-realtime.js.map +1 -1
  387. package/dist/ws-responses.cjs +121 -16
  388. package/dist/ws-responses.cjs.map +1 -1
  389. package/dist/ws-responses.d.cts +8 -12
  390. package/dist/ws-responses.d.cts.map +1 -1
  391. package/dist/ws-responses.d.ts +8 -12
  392. package/dist/ws-responses.d.ts.map +1 -1
  393. package/dist/ws-responses.js +123 -18
  394. package/dist/ws-responses.js.map +1 -1
  395. package/package.json +13 -2
  396. package/skills/write-fixtures/SKILL.md +179 -21
@@ -1,5 +1,5 @@
1
1
  import { Logger } from "./logger.cjs";
2
- import { FixtureBlock, RecordProviderKey, ToolCall } from "./types.cjs";
2
+ import { CustomToolCall, FixtureBlock, RecordProviderKey, ResponsesFixtureBlock, ToolCall } from "./types.cjs";
3
3
 
4
4
  //#region src/stream-collapse.d.ts
5
5
 
@@ -71,7 +71,17 @@ interface CollapseResult {
71
71
  * `response.usage` override shape before persisting.
72
72
  */
73
73
  usage?: Record<string, unknown>;
74
+ /**
75
+ * Function calls. An OpenAI Responses `function_call` item's `namespace` is
76
+ * kept on its entry (internal {@link collapseOpenAISSEWithResponsesTools} only).
77
+ */
74
78
  toolCalls?: ToolCall[];
79
+ /**
80
+ * OpenAI Responses custom tool calls (`custom_tool_call` items), in output
81
+ * order (internal {@link collapseOpenAISSEWithResponsesTools} only). They are never part of `toolCalls`
82
+ * or `blocks`.
83
+ */
84
+ customToolCalls?: CustomToolCall[];
75
85
  droppedChunks?: number;
76
86
  firstDroppedSample?: string;
77
87
  truncated?: boolean;
@@ -100,10 +110,21 @@ interface CollapseResult {
100
110
  * keeps the legacy `{ content, toolCalls }` shape byte-identical.
101
111
  *
102
112
  * Each text block coalesces all contiguous content deltas between tool
103
- * atoms; each toolCall block carries the fully-assembled name/arguments/id
104
- * for one tool call in the position its FIRST delta arrived.
113
+ * atoms. Each tool block sits in the position where its FIRST delta arrived:
114
+ * a function call becomes a `toolCall` block with the fully-assembled
115
+ * name/arguments/id, and an OpenAI Responses custom call becomes a
116
+ * `customToolCall` block with name/input/id, where `input` is kept verbatim.
117
+ * Custom calls are left out of `blocks` (which, like `toolCalls`, describes
118
+ * function calls and text only); see {@link CollapseResult.responsesBlocks}.
105
119
  */
106
120
  blocks?: FixtureBlock[];
121
+ /**
122
+ * OpenAI Responses only: the full ordered output (text, function calls and
123
+ * custom calls) when the stream carried a custom call whose position the
124
+ * `content` + `toolCalls` + `customToolCalls` shape cannot express (it is
125
+ * interleaved with text, or comes before a function call).
126
+ */
127
+ responsesBlocks?: ResponsesFixtureBlock[];
107
128
  }
108
129
  /**
109
130
  * The opaque `data` of a non-empty Anthropic `redacted_thinking` block, or
@@ -121,8 +142,16 @@ interface CollapseResult {
121
142
  * Format:
122
143
  * data: {"id":"chatcmpl-123","choices":[{"delta":{"content":"Hello"}}]}\n\n
123
144
  * data: [DONE]\n\n
145
+ *
146
+ * Public, with the 1.44.0 result: an OpenAI Responses `namespace` and custom
147
+ * tool calls are dropped. The recorder uses {@link collapseOpenAISSEWithResponsesTools}.
124
148
  */
125
149
  declare function collapseOpenAISSE(rawBody: string): CollapseResult;
150
+ /**
151
+ * A collapse result as 1.44.0 returned and recorded it: no `namespace` on a
152
+ * function call or `toolCall` block, and no custom tool calls.
153
+ */
154
+
126
155
  /**
127
156
  * Collapse Anthropic Claude Messages SSE stream into a single response.
128
157
  *
@@ -186,9 +215,15 @@ declare function collapseGeminiInteractionsSSE(rawBody: string): CollapseResult;
186
215
  * Collapse a streaming response body into a non-streaming fixture response.
187
216
  * Returns null if the content type is not a known streaming format.
188
217
  * Falls back to OpenAI SSE parsing for unrecognized provider keys with text/event-stream.
218
+ *
219
+ * Public, with the 1.44.0 result (see {@link collapseOpenAISSE}). The recorder
220
+ * uses {@link collapseStreamingResponseWithResponsesTools}.
189
221
  */
190
222
  declare function collapseStreamingResponse(contentType: string, providerKey: RecordProviderKey, body: string | Buffer, logger?: Logger): CollapseResult | null;
191
- //# sourceMappingURL=stream-collapse.d.ts.map
223
+ /**
224
+ * @internal {@link collapseStreamingResponse} keeping an OpenAI Responses
225
+ * `namespace` and custom tool calls.
226
+ */
192
227
  //#endregion
193
228
  export { CollapseResult, MAX_COLLAPSE_STRING_LENGTH, collapseAnthropicSSE, collapseBedrockEventStream, collapseCohereSSE, collapseGeminiInteractionsSSE, collapseGeminiSSE, collapseOllamaNDJSON, collapseOpenAISSE, collapseStreamingResponse, setCollapseStringLimitForTests };
194
229
  //# sourceMappingURL=stream-collapse.d.cts.map
@@ -1 +1 @@
1
- {"version":3,"file":"stream-collapse.d.cts","names":[],"sources":["../src/stream-collapse.ts"],"sourcesContent":[],"mappings":";;;;;;;;;AA2XA;AAiaA;AAkMA;AAyJA;AAmIA;AA6RA;;;;;AA0RA;AAwLA;;;;;AAKG,cAx8DU,0BAw8DV,EAAA,MAAA;;iBA77Da,8BAAA;UAgDC,cAAA;;;;gBAID;;;YACJ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;UAqCF;cACI;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;WAgCH;;;;;;;;;;;;;;;;;;;iBA+MK,iBAAA,mBAAoC;;;;;;;;iBAiapC,oBAAA,mBAAuC;;;;;;;iBAkMvC,iBAAA,mBAAoC;;;;;;;;;;;;;;;iBAyJpC,oBAAA,mBAAuC;;;;;;;iBAmIvC,iBAAA,mBAAoC;;;;;;;iBA6RpC,0BAAA,UAAoC,SAAS;;;;;;;;;;;;;;;iBA0R7C,6BAAA,mBAAgD;;;;;;iBAwLhD,yBAAA,mCAED,kCACE,iBACN,SACR"}
1
+ {"version":3,"file":"stream-collapse.d.cts","names":[],"sources":["../src/stream-collapse.ts"],"sourcesContent":[],"mappings":";;;;;;;;;;;AA+eA;AAsjBA;AAkMA;AAyJA;AAmIA;AA6RA;;;;;AAyTA;AA2LA;;;AAGiB,cA3uEJ,0BA2uEI,EAAA,MAAA;;AAEd,iBAluEa,8BAAA,CAkuEb,KAAA,EAAA,MAAA,GAAA,SAAA,CAAA,EAAA,IAAA;AAAc,UAlrEA,cAAA,CAkrEA;;;;gBA9qED;;;YACJ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;UAqCF;;;;;cAKI;;;;;;oBAMM;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;WAoCT;;;;;;;oBAOS;;;;;;;;;;;;;;;;;;;;;;iBAwSJ,iBAAA,mBAAoC;;;;;;;;;;;;;iBAsjBpC,oBAAA,mBAAuC;;;;;;;iBAkMvC,iBAAA,mBAAoC;;;;;;;;;;;;;;;iBAyJpC,oBAAA,mBAAuC;;;;;;;iBAmIvC,iBAAA,mBAAoC;;;;;;;iBA6RpC,0BAAA,UAAoC,SAAS;;;;;;;;;;;;;;;iBAyT7C,6BAAA,mBAAgD;;;;;;;;;iBA2LhD,yBAAA,mCAED,kCACE,iBACN,SACR"}
@@ -1,5 +1,5 @@
1
1
  import { Logger } from "./logger.js";
2
- import { FixtureBlock, RecordProviderKey, ToolCall } from "./types.js";
2
+ import { CustomToolCall, FixtureBlock, RecordProviderKey, ResponsesFixtureBlock, ToolCall } from "./types.js";
3
3
 
4
4
  //#region src/stream-collapse.d.ts
5
5
 
@@ -71,7 +71,17 @@ interface CollapseResult {
71
71
  * `response.usage` override shape before persisting.
72
72
  */
73
73
  usage?: Record<string, unknown>;
74
+ /**
75
+ * Function calls. An OpenAI Responses `function_call` item's `namespace` is
76
+ * kept on its entry (internal {@link collapseOpenAISSEWithResponsesTools} only).
77
+ */
74
78
  toolCalls?: ToolCall[];
79
+ /**
80
+ * OpenAI Responses custom tool calls (`custom_tool_call` items), in output
81
+ * order (internal {@link collapseOpenAISSEWithResponsesTools} only). They are never part of `toolCalls`
82
+ * or `blocks`.
83
+ */
84
+ customToolCalls?: CustomToolCall[];
75
85
  droppedChunks?: number;
76
86
  firstDroppedSample?: string;
77
87
  truncated?: boolean;
@@ -100,10 +110,21 @@ interface CollapseResult {
100
110
  * keeps the legacy `{ content, toolCalls }` shape byte-identical.
101
111
  *
102
112
  * Each text block coalesces all contiguous content deltas between tool
103
- * atoms; each toolCall block carries the fully-assembled name/arguments/id
104
- * for one tool call in the position its FIRST delta arrived.
113
+ * atoms. Each tool block sits in the position where its FIRST delta arrived:
114
+ * a function call becomes a `toolCall` block with the fully-assembled
115
+ * name/arguments/id, and an OpenAI Responses custom call becomes a
116
+ * `customToolCall` block with name/input/id, where `input` is kept verbatim.
117
+ * Custom calls are left out of `blocks` (which, like `toolCalls`, describes
118
+ * function calls and text only); see {@link CollapseResult.responsesBlocks}.
105
119
  */
106
120
  blocks?: FixtureBlock[];
121
+ /**
122
+ * OpenAI Responses only: the full ordered output (text, function calls and
123
+ * custom calls) when the stream carried a custom call whose position the
124
+ * `content` + `toolCalls` + `customToolCalls` shape cannot express (it is
125
+ * interleaved with text, or comes before a function call).
126
+ */
127
+ responsesBlocks?: ResponsesFixtureBlock[];
107
128
  }
108
129
  /**
109
130
  * The opaque `data` of a non-empty Anthropic `redacted_thinking` block, or
@@ -121,8 +142,16 @@ interface CollapseResult {
121
142
  * Format:
122
143
  * data: {"id":"chatcmpl-123","choices":[{"delta":{"content":"Hello"}}]}\n\n
123
144
  * data: [DONE]\n\n
145
+ *
146
+ * Public, with the 1.44.0 result: an OpenAI Responses `namespace` and custom
147
+ * tool calls are dropped. The recorder uses {@link collapseOpenAISSEWithResponsesTools}.
124
148
  */
125
149
  declare function collapseOpenAISSE(rawBody: string): CollapseResult;
150
+ /**
151
+ * A collapse result as 1.44.0 returned and recorded it: no `namespace` on a
152
+ * function call or `toolCall` block, and no custom tool calls.
153
+ */
154
+
126
155
  /**
127
156
  * Collapse Anthropic Claude Messages SSE stream into a single response.
128
157
  *
@@ -186,9 +215,15 @@ declare function collapseGeminiInteractionsSSE(rawBody: string): CollapseResult;
186
215
  * Collapse a streaming response body into a non-streaming fixture response.
187
216
  * Returns null if the content type is not a known streaming format.
188
217
  * Falls back to OpenAI SSE parsing for unrecognized provider keys with text/event-stream.
218
+ *
219
+ * Public, with the 1.44.0 result (see {@link collapseOpenAISSE}). The recorder
220
+ * uses {@link collapseStreamingResponseWithResponsesTools}.
189
221
  */
190
222
  declare function collapseStreamingResponse(contentType: string, providerKey: RecordProviderKey, body: string | Buffer, logger?: Logger): CollapseResult | null;
191
- //# sourceMappingURL=stream-collapse.d.ts.map
223
+ /**
224
+ * @internal {@link collapseStreamingResponse} keeping an OpenAI Responses
225
+ * `namespace` and custom tool calls.
226
+ */
192
227
  //#endregion
193
228
  export { CollapseResult, MAX_COLLAPSE_STRING_LENGTH, collapseAnthropicSSE, collapseBedrockEventStream, collapseCohereSSE, collapseGeminiInteractionsSSE, collapseGeminiSSE, collapseOllamaNDJSON, collapseOpenAISSE, collapseStreamingResponse, setCollapseStringLimitForTests };
194
229
  //# sourceMappingURL=stream-collapse.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"stream-collapse.d.ts","names":[],"sources":["../src/stream-collapse.ts"],"sourcesContent":[],"mappings":";;;;;;;;;AA2XA;AAiaA;AAkMA;AAyJA;AAmIA;AA6RA;;;;;AA0RA;AAwLA;;;;;AAKG,cAx8DU,0BAw8DV,EAAA,MAAA;;iBA77Da,8BAAA;UAgDC,cAAA;;;;gBAID;;;YACJ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;UAqCF;cACI;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;WAgCH;;;;;;;;;;;;;;;;;;;iBA+MK,iBAAA,mBAAoC;;;;;;;;iBAiapC,oBAAA,mBAAuC;;;;;;;iBAkMvC,iBAAA,mBAAoC;;;;;;;;;;;;;;;iBAyJpC,oBAAA,mBAAuC;;;;;;;iBAmIvC,iBAAA,mBAAoC;;;;;;;iBA6RpC,0BAAA,UAAoC,SAAS;;;;;;;;;;;;;;;iBA0R7C,6BAAA,mBAAgD;;;;;;iBAwLhD,yBAAA,mCAED,kCACE,iBACN,SACR"}
1
+ {"version":3,"file":"stream-collapse.d.ts","names":[],"sources":["../src/stream-collapse.ts"],"sourcesContent":[],"mappings":";;;;;;;;;;;AA+eA;AAsjBA;AAkMA;AAyJA;AAmIA;AA6RA;;;;;AAyTA;AA2LA;;;AAGiB,cA3uEJ,0BA2uEI,EAAA,MAAA;;AAEd,iBAluEa,8BAAA,CAkuEb,KAAA,EAAA,MAAA,GAAA,SAAA,CAAA,EAAA,IAAA;AAAc,UAlrEA,cAAA,CAkrEA;;;;gBA9qED;;;YACJ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;UAqCF;;;;;cAKI;;;;;;oBAMM;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;WAoCT;;;;;;;oBAOS;;;;;;;;;;;;;;;;;;;;;;iBAwSJ,iBAAA,mBAAoC;;;;;;;;;;;;;iBAsjBpC,oBAAA,mBAAuC;;;;;;;iBAkMvC,iBAAA,mBAAoC;;;;;;;;;;;;;;;iBAyJpC,oBAAA,mBAAuC;;;;;;;iBAmIvC,iBAAA,mBAAoC;;;;;;;iBA6RpC,0BAAA,UAAoC,SAAS;;;;;;;;;;;;;;;iBAyT7C,6BAAA,mBAAgD;;;;;;;;;iBA2LhD,yBAAA,mCAED,kCACE,iBACN,SACR"}
@@ -79,6 +79,10 @@ function guardCollapseBody(body) {
79
79
  function isCollapseInputTruncated(body) {
80
80
  return body.length > effectiveCollapseStringLimit();
81
81
  }
82
+ /** A Responses `namespace` field when it is a non-empty string, else undefined. */
83
+ function responsesNamespace(item) {
84
+ return typeof item.namespace === "string" && item.namespace !== "" ? item.namespace : void 0;
85
+ }
82
86
  /**
83
87
  * Normalize a tool call's accumulated `arguments` into valid JSON exactly like
84
88
  * the flat-`toolCalls` recorder path: an empty / whitespace-only / missing
@@ -100,7 +104,40 @@ function toToolCallBlock(ref) {
100
104
  type: "toolCall",
101
105
  name: ref.name,
102
106
  arguments: normalizeToolArguments(ref.arguments),
103
- ...ref.id ? { id: ref.id } : {}
107
+ ...ref.id ? { id: ref.id } : {},
108
+ ...ref.namespace ? { namespace: ref.namespace } : {}
109
+ };
110
+ }
111
+ /**
112
+ * Build a `customToolCall` block from a custom-call accumulator. The `input` is
113
+ * free text: it is kept as is, never normalized to `"{}"`.
114
+ */
115
+ function toCustomToolCallBlock(ref) {
116
+ return {
117
+ type: "customToolCall",
118
+ name: ref.name,
119
+ input: ref.input,
120
+ ...ref.id ? { id: ref.id } : {},
121
+ ...ref.namespace ? { namespace: ref.namespace } : {}
122
+ };
123
+ }
124
+ /** Project a function-call accumulator to a flat fixture tool call. */
125
+ function toFunctionToolCall(ref) {
126
+ return {
127
+ name: ref.name,
128
+ arguments: normalizeToolArguments(ref.arguments),
129
+ ...ref.id ? { id: ref.id } : {},
130
+ ...ref.namespace ? { namespace: ref.namespace } : {}
131
+ };
132
+ }
133
+ /** Project a custom-call accumulator to a flat fixture custom tool call. */
134
+ function toCustomToolCall(ref) {
135
+ return {
136
+ type: "custom",
137
+ name: ref.name,
138
+ input: ref.input,
139
+ ...ref.id ? { id: ref.id } : {},
140
+ ...ref.namespace ? { namespace: ref.namespace } : {}
104
141
  };
105
142
  }
106
143
  /**
@@ -110,19 +147,31 @@ function toToolCallBlock(ref) {
110
147
  * `CollapseResult.blocks` unset and the recorder keeps the legacy shape.
111
148
  *
112
149
  * Interleaved ⇔ (a tool atom appears strictly before the first text atom) OR
113
- * (a text atom appears after any tool atom). A stream with no tool atoms, or
150
+ * (a text atom appears after any tool atom). Tool atoms are `toolCall` and
151
+ * `customToolCall` atoms. A stream with no tool atoms, or
114
152
  * with no text atoms, is never interleaved. Text-first-then-tools is the common
115
153
  * legacy case and is explicitly NOT interleaved.
116
154
  *
117
- * CONSISTENCY (#274): each toolCall block is derived from the SAME accumulator
118
- * object referenced by its atom and normalized identically to the flat
119
- * `toolCalls` path ({@link toToolCallBlock} / {@link normalizeToolArguments}).
120
- * Because the atom `ref` is the very object the flat list is built from, the
121
- * block and its flat counterpart describe the same call by identity — even when
122
- * upstream tool-call indices do not match stream-arrival order. Empty/missing
123
- * arguments normalize to `"{}"` in BOTH representations, never `""`.
155
+ * CONSISTENCY (#274): each tool block is derived from the SAME accumulator
156
+ * object referenced by its atom. Because the atom `ref` is the very object the
157
+ * flat list is built from, the block and its flat counterpart describe the same
158
+ * call by identity — even when upstream tool-call indices do not match
159
+ * stream-arrival order. A `toolCall` block is normalized identically to the
160
+ * flat `toolCalls` path ({@link toToolCallBlock} / {@link normalizeToolArguments}):
161
+ * empty/missing arguments become `"{}"` in BOTH representations, never `""`. A
162
+ * `customToolCall` block ({@link toCustomToolCallBlock}) keeps `input` verbatim,
163
+ * the same as the flat custom tool call ({@link toCustomToolCall}); it is never
164
+ * normalized to `"{}"`.
124
165
  */
125
166
  function buildOrderedBlocks(atoms) {
167
+ return orderedBlocksFrom(atoms.filter((a) => a.kind !== "customToolCall"))?.filter((block) => block.type !== "customToolCall");
168
+ }
169
+ /**
170
+ * {@link buildOrderedBlocks} over every atom, custom calls included, for
171
+ * `CollapseResult.responsesBlocks`. With `force`, the blocks are built even
172
+ * when text and tools are not interleaved.
173
+ */
174
+ function orderedBlocksFrom(atoms, force = false) {
126
175
  let firstTextIndex = -1;
127
176
  let firstToolIndex = -1;
128
177
  let textAfterTool = false;
@@ -136,8 +185,10 @@ function buildOrderedBlocks(atoms) {
136
185
  sawTool = true;
137
186
  if (firstToolIndex === -1) firstToolIndex = i;
138
187
  }
139
- if (!sawTool || !sawText) return void 0;
140
- if (!(firstToolIndex < firstTextIndex) && !textAfterTool) return void 0;
188
+ if (!force) {
189
+ if (!sawTool || !sawText) return void 0;
190
+ if (!(firstToolIndex < firstTextIndex) && !textAfterTool) return void 0;
191
+ }
141
192
  const blocks = [];
142
193
  let pendingText = "";
143
194
  let hasPendingText = false;
@@ -156,7 +207,7 @@ function buildOrderedBlocks(atoms) {
156
207
  hasPendingText = true;
157
208
  } else {
158
209
  flushText();
159
- blocks.push(toToolCallBlock(a.ref));
210
+ blocks.push(a.kind === "customToolCall" ? toCustomToolCallBlock(a.ref) : toToolCallBlock(a.ref));
160
211
  }
161
212
  flushText();
162
213
  return blocks;
@@ -233,8 +284,41 @@ function extractSSEData(lines) {
233
284
  * Format:
234
285
  * data: {"id":"chatcmpl-123","choices":[{"delta":{"content":"Hello"}}]}\n\n
235
286
  * data: [DONE]\n\n
287
+ *
288
+ * Public, with the 1.44.0 result: an OpenAI Responses `namespace` and custom
289
+ * tool calls are dropped. The recorder uses {@link collapseOpenAISSEWithResponsesTools}.
236
290
  */
237
291
  function collapseOpenAISSE(rawBody) {
292
+ return withoutResponsesToolFields(collapseOpenAISSEWithResponsesTools(rawBody));
293
+ }
294
+ /**
295
+ * A collapse result as 1.44.0 returned and recorded it: no `namespace` on a
296
+ * function call or `toolCall` block, and no custom tool calls.
297
+ */
298
+ function withoutResponsesToolFields(collapsed) {
299
+ if (collapsed.customToolCalls === void 0 && collapsed.responsesBlocks === void 0 && !collapsed.toolCalls?.some((tc) => tc.namespace !== void 0) && !collapsed.blocks?.some((block) => block.type !== "text" && block.namespace !== void 0)) return collapsed;
300
+ const result = { ...collapsed };
301
+ delete result.customToolCalls;
302
+ delete result.responsesBlocks;
303
+ if (result.toolCalls) result.toolCalls = result.toolCalls.map((tc) => {
304
+ if (tc.namespace === void 0) return tc;
305
+ const copy = { ...tc };
306
+ delete copy.namespace;
307
+ return copy;
308
+ });
309
+ if (result.blocks) result.blocks = result.blocks.map((block) => {
310
+ if (block.type === "text" || block.namespace === void 0) return block;
311
+ const copy = { ...block };
312
+ delete copy.namespace;
313
+ return copy;
314
+ });
315
+ return result;
316
+ }
317
+ /**
318
+ * @internal {@link collapseOpenAISSE} keeping an OpenAI Responses `namespace`
319
+ * and custom tool calls, for the recorder with `responsesTools: "extended"`.
320
+ */
321
+ function collapseOpenAISSEWithResponsesTools(rawBody) {
238
322
  const inputTruncated = isCollapseInputTruncated(rawBody);
239
323
  const lines = splitSSEEvents(guardCollapseBody(rawBody));
240
324
  let content = "";
@@ -295,14 +379,19 @@ function collapseOpenAISSE(rawBody) {
295
379
  if (item?.type === "function_call" && typeof parsed.output_index === "number") {
296
380
  const entry = toolCallMap.get(parsed.output_index);
297
381
  if (entry) {
298
- if (!entry.id && typeof item.call_id === "string") entry.id = item.call_id;
299
- if (!entry.name && typeof item.name === "string") entry.name = item.name;
300
- if (entry.arguments === "" && typeof item.arguments === "string") entry.arguments = item.arguments;
382
+ if (entry.kind === "function") {
383
+ if (!entry.id && typeof item.call_id === "string") entry.id = item.call_id;
384
+ if (!entry.name && typeof item.name === "string") entry.name = item.name;
385
+ if (!entry.namespace) entry.namespace = responsesNamespace(item);
386
+ if (entry.arguments === "" && typeof item.arguments === "string") entry.arguments = item.arguments;
387
+ }
301
388
  } else {
302
389
  const created = {
390
+ kind: "function",
303
391
  id: typeof item.call_id === "string" ? item.call_id : "",
304
392
  name: typeof item.name === "string" ? item.name : "",
305
- arguments: typeof item.arguments === "string" ? item.arguments : ""
393
+ arguments: typeof item.arguments === "string" ? item.arguments : "",
394
+ namespace: responsesNamespace(item)
306
395
  };
307
396
  toolCallMap.set(parsed.output_index, created);
308
397
  orderAtoms.push({
@@ -312,15 +401,42 @@ function collapseOpenAISSE(rawBody) {
312
401
  }
313
402
  continue;
314
403
  }
404
+ if (item?.type === "custom_tool_call" && typeof parsed.output_index === "number") {
405
+ const entry = toolCallMap.get(parsed.output_index);
406
+ if (entry) {
407
+ if (entry.kind === "custom") {
408
+ if (!entry.id && typeof item.call_id === "string") entry.id = item.call_id;
409
+ if (!entry.name && typeof item.name === "string") entry.name = item.name;
410
+ if (!entry.namespace) entry.namespace = responsesNamespace(item);
411
+ if (entry.input === "" && typeof item.input === "string") entry.input = item.input;
412
+ }
413
+ } else {
414
+ const created = {
415
+ kind: "custom",
416
+ id: typeof item.call_id === "string" ? item.call_id : "",
417
+ name: typeof item.name === "string" ? item.name : "",
418
+ input: typeof item.input === "string" ? item.input : "",
419
+ namespace: responsesNamespace(item)
420
+ };
421
+ toolCallMap.set(parsed.output_index, created);
422
+ orderAtoms.push({
423
+ kind: "customToolCall",
424
+ ref: created
425
+ });
426
+ }
427
+ continue;
428
+ }
315
429
  }
316
430
  if (parsed.type === "response.output_item.added") {
317
431
  const item = parsed.item;
318
432
  if (item?.type === "function_call" && typeof parsed.output_index === "number") {
319
433
  if (!toolCallMap.has(parsed.output_index)) {
320
434
  const created = {
435
+ kind: "function",
321
436
  id: typeof item.call_id === "string" ? item.call_id : "",
322
437
  name: typeof item.name === "string" ? item.name : "",
323
- arguments: ""
438
+ arguments: "",
439
+ namespace: responsesNamespace(item)
324
440
  };
325
441
  toolCallMap.set(parsed.output_index, created);
326
442
  orderAtoms.push({
@@ -330,11 +446,66 @@ function collapseOpenAISSE(rawBody) {
330
446
  }
331
447
  continue;
332
448
  }
449
+ if (item?.type === "custom_tool_call" && typeof parsed.output_index === "number") {
450
+ if (!toolCallMap.has(parsed.output_index)) {
451
+ const created = {
452
+ kind: "custom",
453
+ id: typeof item.call_id === "string" ? item.call_id : "",
454
+ name: typeof item.name === "string" ? item.name : "",
455
+ input: "",
456
+ namespace: responsesNamespace(item)
457
+ };
458
+ toolCallMap.set(parsed.output_index, created);
459
+ orderAtoms.push({
460
+ kind: "customToolCall",
461
+ ref: created
462
+ });
463
+ }
464
+ continue;
465
+ }
466
+ }
467
+ if (parsed.type === "response.custom_tool_call_input.delta" && typeof parsed.delta === "string" && typeof parsed.output_index === "number") {
468
+ let entry = toolCallMap.get(parsed.output_index);
469
+ if (!entry) {
470
+ entry = {
471
+ kind: "custom",
472
+ id: "",
473
+ name: "",
474
+ input: ""
475
+ };
476
+ toolCallMap.set(parsed.output_index, entry);
477
+ orderAtoms.push({
478
+ kind: "customToolCall",
479
+ ref: entry
480
+ });
481
+ }
482
+ if (entry.kind === "custom") entry.input += parsed.delta;
483
+ continue;
484
+ }
485
+ if (parsed.type === "response.custom_tool_call_input.done" && typeof parsed.output_index === "number") {
486
+ const entry = toolCallMap.get(parsed.output_index);
487
+ if (entry) {
488
+ if (entry.kind === "custom" && entry.input === "" && typeof parsed.input === "string") entry.input = parsed.input;
489
+ } else if (typeof parsed.input === "string") {
490
+ const created = {
491
+ kind: "custom",
492
+ id: "",
493
+ name: "",
494
+ input: parsed.input
495
+ };
496
+ toolCallMap.set(parsed.output_index, created);
497
+ orderAtoms.push({
498
+ kind: "customToolCall",
499
+ ref: created
500
+ });
501
+ }
502
+ continue;
333
503
  }
334
504
  if (parsed.type === "response.function_call_arguments.delta" && typeof parsed.delta === "string" && typeof parsed.output_index === "number") {
335
505
  let entry = toolCallMap.get(parsed.output_index);
336
506
  if (!entry) {
337
507
  entry = {
508
+ kind: "function",
338
509
  id: "",
339
510
  name: "",
340
511
  arguments: ""
@@ -345,15 +516,16 @@ function collapseOpenAISSE(rawBody) {
345
516
  ref: entry
346
517
  });
347
518
  }
348
- entry.arguments += parsed.delta;
519
+ if (entry.kind === "function") entry.arguments += parsed.delta;
349
520
  continue;
350
521
  }
351
522
  if (parsed.type === "response.function_call_arguments.done" && typeof parsed.output_index === "number") {
352
523
  const entry = toolCallMap.get(parsed.output_index);
353
524
  if (entry) {
354
- if (entry.arguments === "" && typeof parsed.arguments === "string") entry.arguments = parsed.arguments;
525
+ if (entry.kind === "function" && entry.arguments === "" && typeof parsed.arguments === "string") entry.arguments = parsed.arguments;
355
526
  } else if (typeof parsed.arguments === "string") {
356
527
  const created = {
528
+ kind: "function",
357
529
  id: "",
358
530
  name: "",
359
531
  arguments: parsed.arguments
@@ -406,6 +578,7 @@ function collapseOpenAISSE(rawBody) {
406
578
  lastToolCallKey = index;
407
579
  if (!toolCallMap.has(index)) {
408
580
  const created = {
581
+ kind: "function",
409
582
  id: rawId ?? "",
410
583
  name: fn?.name ?? "",
411
584
  arguments: ""
@@ -419,11 +592,11 @@ function collapseOpenAISSE(rawBody) {
419
592
  const entry = toolCallMap.get(index);
420
593
  if (fn?.name && typeof fn.name === "string" && !entry.name) entry.name = fn.name;
421
594
  if (tc.id && typeof tc.id === "string" && !entry.id) entry.id = tc.id;
422
- if (fn?.arguments && typeof fn.arguments === "string") entry.arguments += fn.arguments;
595
+ if (entry.kind === "function" && fn?.arguments && typeof fn.arguments === "string") entry.arguments += fn.arguments;
423
596
  }
424
597
  }
425
598
  const harmonyToolCalls = [];
426
- if (toolCallMap.size === 0 && isHarmonyContent(content)) {
599
+ if (!Array.from(toolCallMap.values()).some((tc) => tc.kind === "function") && isHarmonyContent(content)) {
427
600
  const parsed = parseHarmonyContent(content);
428
601
  if (parsed.failed) {
429
602
  harmonyUnparsed = true;
@@ -434,18 +607,22 @@ function collapseOpenAISSE(rawBody) {
434
607
  harmonyToolCalls.push(...parsed.toolCalls);
435
608
  }
436
609
  }
437
- if (toolCallMap.size > 0 || harmonyToolCalls.length > 0) {
610
+ const sortedEntries = Array.from(toolCallMap.entries()).sort(([a], [b]) => a - b);
611
+ const customEntries = sortedEntries.flatMap(([, tc]) => tc.kind === "custom" ? [tc] : []);
612
+ const functionEntries = sortedEntries.flatMap(([, tc]) => tc.kind === "function" ? [tc] : []);
613
+ let customFields = {};
614
+ if (customEntries.length > 0) {
615
+ const firstCustomAtom = orderAtoms.findIndex((a) => a.kind === "customToolCall");
616
+ const responsesBlocks = orderedBlocksFrom(orderAtoms, orderAtoms.some((a, i) => a.kind === "toolCall" && i > firstCustomAtom));
617
+ customFields = {
618
+ customToolCalls: responsesBlocks ? orderAtoms.flatMap((a) => a.kind === "customToolCall" ? [toCustomToolCall(a.ref)] : []) : customEntries.map(toCustomToolCall),
619
+ ...responsesBlocks ? { responsesBlocks } : {}
620
+ };
621
+ }
622
+ if (functionEntries.length > 0 || harmonyToolCalls.length > 0) {
438
623
  const blocks = buildOrderedBlocks(orderAtoms);
439
- const orderedToolCalls = orderAtoms.filter((a) => a.kind === "toolCall").map((a) => ({
440
- name: a.ref.name,
441
- arguments: normalizeToolArguments(a.ref.arguments),
442
- ...a.ref.id ? { id: a.ref.id } : {}
443
- }));
444
- const indexSortedToolCalls = Array.from(toolCallMap.entries()).sort(([a], [b]) => a - b).map(([, tc]) => ({
445
- name: tc.name,
446
- arguments: normalizeToolArguments(tc.arguments),
447
- ...tc.id ? { id: tc.id } : {}
448
- }));
624
+ const orderedToolCalls = orderAtoms.flatMap((a) => a.kind === "toolCall" ? [toFunctionToolCall(a.ref)] : []);
625
+ const indexSortedToolCalls = functionEntries.map(toFunctionToolCall);
449
626
  return {
450
627
  ...transcriptSeen ? { transcription: {
451
628
  text: transcript,
@@ -455,6 +632,7 @@ function collapseOpenAISSE(rawBody) {
455
632
  ...blocks ? { blocks } : {},
456
633
  ...content ? { content } : {},
457
634
  toolCalls: [...blocks ? orderedToolCalls : indexSortedToolCalls, ...harmonyToolCalls],
635
+ ...customFields,
458
636
  ...reasoning ? { reasoning } : {},
459
637
  ...webSearchQueries.length > 0 ? { webSearches: webSearchQueries } : {},
460
638
  ...usage ? { usage } : {},
@@ -472,6 +650,7 @@ function collapseOpenAISSE(rawBody) {
472
650
  ...transcriptUsage ? { usage: transcriptUsage } : {}
473
651
  } } : {},
474
652
  content,
653
+ ...customFields,
475
654
  ...reasoning ? { reasoning } : {},
476
655
  ...webSearchQueries.length > 0 ? { webSearches: webSearchQueries } : {},
477
656
  ...usage ? { usage } : {},
@@ -1010,6 +1189,16 @@ function collapseBedrockEventStream(rawBody) {
1010
1189
  let parsed;
1011
1190
  try {
1012
1191
  parsed = JSON.parse(frameStr);
1192
+ if (frame.headers[":event-type"] === "chunk" && parsed !== null && typeof parsed === "object" && Object.hasOwn(parsed, "bytes")) try {
1193
+ const bytes = parsed.bytes;
1194
+ if (typeof bytes !== "string" || bytes.length === 0 || !/^(?:[A-Za-z0-9+/]{4})*(?:[A-Za-z0-9+/]{2}==|[A-Za-z0-9+/]{3}=)?$/.test(bytes)) throw new TypeError("bytes must be a nonempty base64 string");
1195
+ const event = JSON.parse(Buffer.from(bytes, "base64").toString("utf8"));
1196
+ if (event === null || typeof event !== "object" || Array.isArray(event) || !("type" in event) || typeof event.type !== "string") throw new TypeError("decoded bytes must contain a Claude event object");
1197
+ parsed = event;
1198
+ } catch (err) {
1199
+ const message = err instanceof Error ? err.message : "unknown";
1200
+ throw new TypeError(`Invalid Invoke PayloadPart: ${message}`);
1201
+ }
1013
1202
  } catch (err) {
1014
1203
  droppedChunks++;
1015
1204
  if (droppedChunks === 1) firstDroppedSample = `parse failed (${err instanceof Error ? err.message : "unknown"}): ${surrogateSafeSlice(frameStr, 200)}`;
@@ -1255,8 +1444,19 @@ function collapseGeminiInteractionsSSE(rawBody) {
1255
1444
  * Collapse a streaming response body into a non-streaming fixture response.
1256
1445
  * Returns null if the content type is not a known streaming format.
1257
1446
  * Falls back to OpenAI SSE parsing for unrecognized provider keys with text/event-stream.
1447
+ *
1448
+ * Public, with the 1.44.0 result (see {@link collapseOpenAISSE}). The recorder
1449
+ * uses {@link collapseStreamingResponseWithResponsesTools}.
1258
1450
  */
1259
1451
  function collapseStreamingResponse(contentType, providerKey, body, logger) {
1452
+ const collapsed = collapseStreamingResponseWithResponsesTools(contentType, providerKey, body, logger);
1453
+ return collapsed && withoutResponsesToolFields(collapsed);
1454
+ }
1455
+ /**
1456
+ * @internal {@link collapseStreamingResponse} keeping an OpenAI Responses
1457
+ * `namespace` and custom tool calls.
1458
+ */
1459
+ function collapseStreamingResponseWithResponsesTools(contentType, providerKey, body, logger) {
1260
1460
  const ct = contentType.toLowerCase();
1261
1461
  if (ct.includes("application/vnd.amazon.eventstream")) return collapseBedrockEventStream(typeof body === "string" ? Buffer.from(body, "binary") : body);
1262
1462
  if (ct.includes("application/x-ndjson")) return collapseOllamaNDJSON(typeof body === "string" ? body : body.toString("utf8"));
@@ -1266,7 +1466,7 @@ function collapseStreamingResponse(contentType, providerKey, body, logger) {
1266
1466
  case "openai":
1267
1467
  case "azure":
1268
1468
  case "openrouter":
1269
- case "byteplus": return collapseOpenAISSE(str);
1469
+ case "byteplus": return collapseOpenAISSEWithResponsesTools(str);
1270
1470
  case "anthropic": return collapseAnthropicSSE(str);
1271
1471
  case "gemini":
1272
1472
  case "vertexai": return collapseGeminiSSE(str);
@@ -1275,12 +1475,12 @@ function collapseStreamingResponse(contentType, providerKey, body, logger) {
1275
1475
  case "bedrock": return collapseAnthropicSSE(str);
1276
1476
  default:
1277
1477
  logger?.warn(`[stream-collapse] unknown SSE provider "${providerKey}", falling back to OpenAI SSE format`);
1278
- return collapseOpenAISSE(str);
1478
+ return collapseOpenAISSEWithResponsesTools(str);
1279
1479
  }
1280
1480
  }
1281
1481
  return null;
1282
1482
  }
1283
1483
 
1284
1484
  //#endregion
1285
- export { MAX_COLLAPSE_STRING_LENGTH, capturedRedactedData, collapseAnthropicSSE, collapseBedrockEventStream, collapseCohereSSE, collapseGeminiInteractionsSSE, collapseGeminiSSE, collapseOllamaNDJSON, collapseOpenAISSE, collapseStreamingResponse, setCollapseStringLimitForTests };
1485
+ export { MAX_COLLAPSE_STRING_LENGTH, capturedRedactedData, collapseAnthropicSSE, collapseBedrockEventStream, collapseCohereSSE, collapseGeminiInteractionsSSE, collapseGeminiSSE, collapseOllamaNDJSON, collapseOpenAISSE, collapseStreamingResponse, collapseStreamingResponseWithResponsesTools, setCollapseStringLimitForTests, withoutResponsesToolFields };
1286
1486
  //# sourceMappingURL=stream-collapse.js.map