@librechat/agents 3.1.75 → 3.1.77-dev.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (272) hide show
  1. package/dist/cjs/graphs/Graph.cjs +22 -3
  2. package/dist/cjs/graphs/Graph.cjs.map +1 -1
  3. package/dist/cjs/hitl/askUserQuestion.cjs +67 -0
  4. package/dist/cjs/hitl/askUserQuestion.cjs.map +1 -0
  5. package/dist/cjs/hooks/HookRegistry.cjs +54 -0
  6. package/dist/cjs/hooks/HookRegistry.cjs.map +1 -1
  7. package/dist/cjs/hooks/createToolPolicyHook.cjs +115 -0
  8. package/dist/cjs/hooks/createToolPolicyHook.cjs.map +1 -0
  9. package/dist/cjs/hooks/executeHooks.cjs +40 -1
  10. package/dist/cjs/hooks/executeHooks.cjs.map +1 -1
  11. package/dist/cjs/hooks/types.cjs +1 -0
  12. package/dist/cjs/hooks/types.cjs.map +1 -1
  13. package/dist/cjs/langchain/google-common.cjs +3 -0
  14. package/dist/cjs/langchain/google-common.cjs.map +1 -0
  15. package/dist/cjs/langchain/index.cjs +86 -0
  16. package/dist/cjs/langchain/index.cjs.map +1 -0
  17. package/dist/cjs/langchain/language_models/chat_models.cjs +3 -0
  18. package/dist/cjs/langchain/language_models/chat_models.cjs.map +1 -0
  19. package/dist/cjs/langchain/messages/tool.cjs +3 -0
  20. package/dist/cjs/langchain/messages/tool.cjs.map +1 -0
  21. package/dist/cjs/langchain/messages.cjs +51 -0
  22. package/dist/cjs/langchain/messages.cjs.map +1 -0
  23. package/dist/cjs/langchain/openai.cjs +3 -0
  24. package/dist/cjs/langchain/openai.cjs.map +1 -0
  25. package/dist/cjs/langchain/prompts.cjs +11 -0
  26. package/dist/cjs/langchain/prompts.cjs.map +1 -0
  27. package/dist/cjs/langchain/runnables.cjs +19 -0
  28. package/dist/cjs/langchain/runnables.cjs.map +1 -0
  29. package/dist/cjs/langchain/tools.cjs +23 -0
  30. package/dist/cjs/langchain/tools.cjs.map +1 -0
  31. package/dist/cjs/langchain/utils/env.cjs +11 -0
  32. package/dist/cjs/langchain/utils/env.cjs.map +1 -0
  33. package/dist/cjs/llm/anthropic/index.cjs +145 -52
  34. package/dist/cjs/llm/anthropic/index.cjs.map +1 -1
  35. package/dist/cjs/llm/anthropic/types.cjs.map +1 -1
  36. package/dist/cjs/llm/anthropic/utils/message_inputs.cjs +21 -14
  37. package/dist/cjs/llm/anthropic/utils/message_inputs.cjs.map +1 -1
  38. package/dist/cjs/llm/anthropic/utils/message_outputs.cjs +84 -70
  39. package/dist/cjs/llm/anthropic/utils/message_outputs.cjs.map +1 -1
  40. package/dist/cjs/llm/bedrock/index.cjs +1 -1
  41. package/dist/cjs/llm/bedrock/index.cjs.map +1 -1
  42. package/dist/cjs/llm/bedrock/utils/message_inputs.cjs +213 -3
  43. package/dist/cjs/llm/bedrock/utils/message_inputs.cjs.map +1 -1
  44. package/dist/cjs/llm/bedrock/utils/message_outputs.cjs +2 -1
  45. package/dist/cjs/llm/bedrock/utils/message_outputs.cjs.map +1 -1
  46. package/dist/cjs/llm/google/utils/common.cjs +5 -4
  47. package/dist/cjs/llm/google/utils/common.cjs.map +1 -1
  48. package/dist/cjs/llm/openai/index.cjs +519 -655
  49. package/dist/cjs/llm/openai/index.cjs.map +1 -1
  50. package/dist/cjs/llm/openai/utils/index.cjs +20 -458
  51. package/dist/cjs/llm/openai/utils/index.cjs.map +1 -1
  52. package/dist/cjs/llm/openrouter/index.cjs +57 -175
  53. package/dist/cjs/llm/openrouter/index.cjs.map +1 -1
  54. package/dist/cjs/llm/vertexai/index.cjs +5 -3
  55. package/dist/cjs/llm/vertexai/index.cjs.map +1 -1
  56. package/dist/cjs/main.cjs +112 -3
  57. package/dist/cjs/main.cjs.map +1 -1
  58. package/dist/cjs/messages/cache.cjs +2 -1
  59. package/dist/cjs/messages/cache.cjs.map +1 -1
  60. package/dist/cjs/messages/core.cjs +7 -6
  61. package/dist/cjs/messages/core.cjs.map +1 -1
  62. package/dist/cjs/messages/format.cjs +73 -15
  63. package/dist/cjs/messages/format.cjs.map +1 -1
  64. package/dist/cjs/messages/langchain.cjs +26 -0
  65. package/dist/cjs/messages/langchain.cjs.map +1 -0
  66. package/dist/cjs/messages/prune.cjs +7 -6
  67. package/dist/cjs/messages/prune.cjs.map +1 -1
  68. package/dist/cjs/run.cjs +400 -42
  69. package/dist/cjs/run.cjs.map +1 -1
  70. package/dist/cjs/tools/ToolNode.cjs +556 -56
  71. package/dist/cjs/tools/ToolNode.cjs.map +1 -1
  72. package/dist/cjs/tools/search/search.cjs +55 -66
  73. package/dist/cjs/tools/search/search.cjs.map +1 -1
  74. package/dist/cjs/tools/search/tavily-scraper.cjs +189 -0
  75. package/dist/cjs/tools/search/tavily-scraper.cjs.map +1 -0
  76. package/dist/cjs/tools/search/tavily-search.cjs +372 -0
  77. package/dist/cjs/tools/search/tavily-search.cjs.map +1 -0
  78. package/dist/cjs/tools/search/tool.cjs +26 -4
  79. package/dist/cjs/tools/search/tool.cjs.map +1 -1
  80. package/dist/cjs/tools/search/utils.cjs +10 -3
  81. package/dist/cjs/tools/search/utils.cjs.map +1 -1
  82. package/dist/esm/graphs/Graph.mjs +22 -3
  83. package/dist/esm/graphs/Graph.mjs.map +1 -1
  84. package/dist/esm/hitl/askUserQuestion.mjs +65 -0
  85. package/dist/esm/hitl/askUserQuestion.mjs.map +1 -0
  86. package/dist/esm/hooks/HookRegistry.mjs +54 -0
  87. package/dist/esm/hooks/HookRegistry.mjs.map +1 -1
  88. package/dist/esm/hooks/createToolPolicyHook.mjs +113 -0
  89. package/dist/esm/hooks/createToolPolicyHook.mjs.map +1 -0
  90. package/dist/esm/hooks/executeHooks.mjs +40 -1
  91. package/dist/esm/hooks/executeHooks.mjs.map +1 -1
  92. package/dist/esm/hooks/types.mjs +1 -0
  93. package/dist/esm/hooks/types.mjs.map +1 -1
  94. package/dist/esm/langchain/google-common.mjs +2 -0
  95. package/dist/esm/langchain/google-common.mjs.map +1 -0
  96. package/dist/esm/langchain/index.mjs +5 -0
  97. package/dist/esm/langchain/index.mjs.map +1 -0
  98. package/dist/esm/langchain/language_models/chat_models.mjs +2 -0
  99. package/dist/esm/langchain/language_models/chat_models.mjs.map +1 -0
  100. package/dist/esm/langchain/messages/tool.mjs +2 -0
  101. package/dist/esm/langchain/messages/tool.mjs.map +1 -0
  102. package/dist/esm/langchain/messages.mjs +2 -0
  103. package/dist/esm/langchain/messages.mjs.map +1 -0
  104. package/dist/esm/langchain/openai.mjs +2 -0
  105. package/dist/esm/langchain/openai.mjs.map +1 -0
  106. package/dist/esm/langchain/prompts.mjs +2 -0
  107. package/dist/esm/langchain/prompts.mjs.map +1 -0
  108. package/dist/esm/langchain/runnables.mjs +2 -0
  109. package/dist/esm/langchain/runnables.mjs.map +1 -0
  110. package/dist/esm/langchain/tools.mjs +2 -0
  111. package/dist/esm/langchain/tools.mjs.map +1 -0
  112. package/dist/esm/langchain/utils/env.mjs +2 -0
  113. package/dist/esm/langchain/utils/env.mjs.map +1 -0
  114. package/dist/esm/llm/anthropic/index.mjs +146 -54
  115. package/dist/esm/llm/anthropic/index.mjs.map +1 -1
  116. package/dist/esm/llm/anthropic/types.mjs.map +1 -1
  117. package/dist/esm/llm/anthropic/utils/message_inputs.mjs +21 -14
  118. package/dist/esm/llm/anthropic/utils/message_inputs.mjs.map +1 -1
  119. package/dist/esm/llm/anthropic/utils/message_outputs.mjs +84 -71
  120. package/dist/esm/llm/anthropic/utils/message_outputs.mjs.map +1 -1
  121. package/dist/esm/llm/bedrock/index.mjs +1 -1
  122. package/dist/esm/llm/bedrock/index.mjs.map +1 -1
  123. package/dist/esm/llm/bedrock/utils/message_inputs.mjs +214 -4
  124. package/dist/esm/llm/bedrock/utils/message_inputs.mjs.map +1 -1
  125. package/dist/esm/llm/bedrock/utils/message_outputs.mjs +2 -1
  126. package/dist/esm/llm/bedrock/utils/message_outputs.mjs.map +1 -1
  127. package/dist/esm/llm/google/utils/common.mjs +5 -4
  128. package/dist/esm/llm/google/utils/common.mjs.map +1 -1
  129. package/dist/esm/llm/openai/index.mjs +520 -656
  130. package/dist/esm/llm/openai/index.mjs.map +1 -1
  131. package/dist/esm/llm/openai/utils/index.mjs +23 -459
  132. package/dist/esm/llm/openai/utils/index.mjs.map +1 -1
  133. package/dist/esm/llm/openrouter/index.mjs +57 -175
  134. package/dist/esm/llm/openrouter/index.mjs.map +1 -1
  135. package/dist/esm/llm/vertexai/index.mjs +5 -3
  136. package/dist/esm/llm/vertexai/index.mjs.map +1 -1
  137. package/dist/esm/main.mjs +7 -0
  138. package/dist/esm/main.mjs.map +1 -1
  139. package/dist/esm/messages/cache.mjs +2 -1
  140. package/dist/esm/messages/cache.mjs.map +1 -1
  141. package/dist/esm/messages/core.mjs +7 -6
  142. package/dist/esm/messages/core.mjs.map +1 -1
  143. package/dist/esm/messages/format.mjs +73 -15
  144. package/dist/esm/messages/format.mjs.map +1 -1
  145. package/dist/esm/messages/langchain.mjs +23 -0
  146. package/dist/esm/messages/langchain.mjs.map +1 -0
  147. package/dist/esm/messages/prune.mjs +7 -6
  148. package/dist/esm/messages/prune.mjs.map +1 -1
  149. package/dist/esm/run.mjs +400 -42
  150. package/dist/esm/run.mjs.map +1 -1
  151. package/dist/esm/tools/ToolNode.mjs +557 -57
  152. package/dist/esm/tools/ToolNode.mjs.map +1 -1
  153. package/dist/esm/tools/search/search.mjs +55 -66
  154. package/dist/esm/tools/search/search.mjs.map +1 -1
  155. package/dist/esm/tools/search/tavily-scraper.mjs +186 -0
  156. package/dist/esm/tools/search/tavily-scraper.mjs.map +1 -0
  157. package/dist/esm/tools/search/tavily-search.mjs +370 -0
  158. package/dist/esm/tools/search/tavily-search.mjs.map +1 -0
  159. package/dist/esm/tools/search/tool.mjs +26 -4
  160. package/dist/esm/tools/search/tool.mjs.map +1 -1
  161. package/dist/esm/tools/search/utils.mjs +10 -3
  162. package/dist/esm/tools/search/utils.mjs.map +1 -1
  163. package/dist/types/graphs/Graph.d.ts +7 -0
  164. package/dist/types/hitl/askUserQuestion.d.ts +55 -0
  165. package/dist/types/hitl/index.d.ts +6 -0
  166. package/dist/types/hooks/HookRegistry.d.ts +58 -0
  167. package/dist/types/hooks/createToolPolicyHook.d.ts +87 -0
  168. package/dist/types/hooks/index.d.ts +4 -1
  169. package/dist/types/hooks/types.d.ts +109 -3
  170. package/dist/types/index.d.ts +10 -0
  171. package/dist/types/langchain/google-common.d.ts +1 -0
  172. package/dist/types/langchain/index.d.ts +8 -0
  173. package/dist/types/langchain/language_models/chat_models.d.ts +1 -0
  174. package/dist/types/langchain/messages/tool.d.ts +1 -0
  175. package/dist/types/langchain/messages.d.ts +2 -0
  176. package/dist/types/langchain/openai.d.ts +1 -0
  177. package/dist/types/langchain/prompts.d.ts +1 -0
  178. package/dist/types/langchain/runnables.d.ts +2 -0
  179. package/dist/types/langchain/tools.d.ts +2 -0
  180. package/dist/types/langchain/utils/env.d.ts +1 -0
  181. package/dist/types/llm/anthropic/index.d.ts +22 -9
  182. package/dist/types/llm/anthropic/types.d.ts +5 -1
  183. package/dist/types/llm/anthropic/utils/message_outputs.d.ts +13 -6
  184. package/dist/types/llm/anthropic/utils/output_parsers.d.ts +1 -1
  185. package/dist/types/llm/openai/index.d.ts +21 -24
  186. package/dist/types/llm/openrouter/index.d.ts +11 -9
  187. package/dist/types/llm/vertexai/index.d.ts +1 -0
  188. package/dist/types/messages/cache.d.ts +4 -1
  189. package/dist/types/messages/format.d.ts +4 -1
  190. package/dist/types/messages/langchain.d.ts +27 -0
  191. package/dist/types/run.d.ts +117 -1
  192. package/dist/types/tools/ToolNode.d.ts +26 -1
  193. package/dist/types/tools/search/tavily-scraper.d.ts +19 -0
  194. package/dist/types/tools/search/tavily-search.d.ts +4 -0
  195. package/dist/types/tools/search/types.d.ts +99 -5
  196. package/dist/types/tools/search/utils.d.ts +2 -2
  197. package/dist/types/types/graph.d.ts +23 -37
  198. package/dist/types/types/hitl.d.ts +272 -0
  199. package/dist/types/types/index.d.ts +1 -0
  200. package/dist/types/types/llm.d.ts +3 -3
  201. package/dist/types/types/run.d.ts +33 -0
  202. package/dist/types/types/stream.d.ts +1 -1
  203. package/dist/types/types/tools.d.ts +19 -0
  204. package/package.json +80 -17
  205. package/src/graphs/Graph.ts +33 -4
  206. package/src/graphs/__tests__/composition.smoke.test.ts +188 -0
  207. package/src/hitl/askUserQuestion.ts +72 -0
  208. package/src/hitl/index.ts +7 -0
  209. package/src/hooks/HookRegistry.ts +71 -0
  210. package/src/hooks/__tests__/createToolPolicyHook.test.ts +259 -0
  211. package/src/hooks/createToolPolicyHook.ts +184 -0
  212. package/src/hooks/executeHooks.ts +50 -1
  213. package/src/hooks/index.ts +6 -0
  214. package/src/hooks/types.ts +112 -0
  215. package/src/index.ts +22 -0
  216. package/src/langchain/google-common.ts +1 -0
  217. package/src/langchain/index.ts +8 -0
  218. package/src/langchain/language_models/chat_models.ts +1 -0
  219. package/src/langchain/messages/tool.ts +5 -0
  220. package/src/langchain/messages.ts +21 -0
  221. package/src/langchain/openai.ts +1 -0
  222. package/src/langchain/prompts.ts +1 -0
  223. package/src/langchain/runnables.ts +7 -0
  224. package/src/langchain/tools.ts +8 -0
  225. package/src/langchain/utils/env.ts +1 -0
  226. package/src/llm/anthropic/index.ts +252 -84
  227. package/src/llm/anthropic/llm.spec.ts +751 -102
  228. package/src/llm/anthropic/types.ts +9 -1
  229. package/src/llm/anthropic/utils/message_inputs.ts +37 -19
  230. package/src/llm/anthropic/utils/message_outputs.ts +119 -101
  231. package/src/llm/bedrock/index.ts +2 -2
  232. package/src/llm/bedrock/llm.spec.ts +341 -0
  233. package/src/llm/bedrock/utils/message_inputs.ts +303 -4
  234. package/src/llm/bedrock/utils/message_outputs.ts +2 -1
  235. package/src/llm/custom-chat-models.smoke.test.ts +836 -0
  236. package/src/llm/google/llm.spec.ts +339 -57
  237. package/src/llm/google/utils/common.ts +53 -48
  238. package/src/llm/openai/contentBlocks.test.ts +346 -0
  239. package/src/llm/openai/index.ts +856 -833
  240. package/src/llm/openai/utils/index.ts +107 -78
  241. package/src/llm/openai/utils/messages.test.ts +159 -0
  242. package/src/llm/openrouter/index.ts +124 -247
  243. package/src/llm/openrouter/reasoning.test.ts +8 -1
  244. package/src/llm/vertexai/index.ts +11 -5
  245. package/src/llm/vertexai/llm.spec.ts +28 -1
  246. package/src/messages/cache.test.ts +4 -3
  247. package/src/messages/cache.ts +3 -2
  248. package/src/messages/core.ts +16 -9
  249. package/src/messages/format.ts +96 -16
  250. package/src/messages/formatAgentMessages.test.ts +166 -1
  251. package/src/messages/langchain.ts +39 -0
  252. package/src/messages/prune.ts +12 -8
  253. package/src/run.ts +456 -47
  254. package/src/scripts/caching.ts +2 -3
  255. package/src/specs/summarization.test.ts +51 -58
  256. package/src/tools/ToolNode.ts +706 -63
  257. package/src/tools/__tests__/hitl.test.ts +3593 -0
  258. package/src/tools/search/search.ts +83 -73
  259. package/src/tools/search/tavily-scraper.ts +235 -0
  260. package/src/tools/search/tavily-search.ts +424 -0
  261. package/src/tools/search/tavily.test.ts +965 -0
  262. package/src/tools/search/tool.ts +36 -26
  263. package/src/tools/search/types.ts +133 -8
  264. package/src/tools/search/utils.ts +13 -5
  265. package/src/types/graph.ts +32 -87
  266. package/src/types/hitl.ts +303 -0
  267. package/src/types/index.ts +1 -0
  268. package/src/types/llm.ts +3 -3
  269. package/src/types/run.ts +33 -0
  270. package/src/types/stream.ts +1 -1
  271. package/src/types/tools.ts +19 -0
  272. package/src/utils/llmConfig.ts +1 -6
@@ -1,7 +1,7 @@
1
1
  'use strict';
2
2
 
3
3
  var messages = require('@langchain/core/messages');
4
- var outputs = require('@langchain/core/outputs');
4
+ require('@langchain/core/outputs');
5
5
  var openai_tools = require('@langchain/core/output_parsers/openai_tools');
6
6
 
7
7
  function extractGenericMessageCustomRole(message) {
@@ -165,6 +165,7 @@ const completionsApiContentBlockConverter = {
165
165
  };
166
166
  // Used in LangSmith, export is important here
167
167
  function _convertMessagesToOpenAIParams(messages$1, model, options) {
168
+ let hasReasoningToolCallContext = false;
168
169
  // TODO: Function messages do not support array content, fix cast
169
170
  return messages$1.flatMap((message) => {
170
171
  let role = messageToOpenAIRole(message);
@@ -189,6 +190,8 @@ function _convertMessagesToOpenAIParams(messages$1, model, options) {
189
190
  role,
190
191
  content,
191
192
  };
193
+ let messageHasToolCalls = false;
194
+ let messageIsToolResult = false;
192
195
  if (message.name != null) {
193
196
  completionParam.name = message.name;
194
197
  }
@@ -197,13 +200,9 @@ function _convertMessagesToOpenAIParams(messages$1, model, options) {
197
200
  completionParam.content = '';
198
201
  }
199
202
  if (messages.isAIMessage(message) && !!message.tool_calls?.length) {
203
+ messageHasToolCalls = true;
200
204
  completionParam.tool_calls = message.tool_calls.map(openai_tools.convertLangChainToolCallToOpenAI);
201
205
  completionParam.content = hasAnthropicThinkingBlock ? content : '';
202
- if (options?.includeReasoningContent === true &&
203
- message.additional_kwargs.reasoning_content != null) {
204
- completionParam.reasoning_content =
205
- message.additional_kwargs.reasoning_content;
206
- }
207
206
  if (options?.includeReasoningDetails === true &&
208
207
  message.additional_kwargs.reasoning_details != null) {
209
208
  // For Claude via OpenRouter, convert reasoning_details to content blocks
@@ -245,12 +244,10 @@ function _convertMessagesToOpenAIParams(messages$1, model, options) {
245
244
  }
246
245
  else {
247
246
  if (message.additional_kwargs.tool_calls != null) {
247
+ messageHasToolCalls =
248
+ !Array.isArray(message.additional_kwargs.tool_calls) ||
249
+ message.additional_kwargs.tool_calls.length > 0;
248
250
  completionParam.tool_calls = message.additional_kwargs.tool_calls;
249
- if (options?.includeReasoningContent === true &&
250
- message.additional_kwargs.reasoning_content != null) {
251
- completionParam.reasoning_content =
252
- message.additional_kwargs.reasoning_content;
253
- }
254
251
  if (options?.includeReasoningDetails === true &&
255
252
  message.additional_kwargs.reasoning_details != null) {
256
253
  // For Claude via OpenRouter, convert reasoning_details to content blocks
@@ -291,9 +288,21 @@ function _convertMessagesToOpenAIParams(messages$1, model, options) {
291
288
  }
292
289
  }
293
290
  if (message.tool_call_id != null) {
291
+ messageIsToolResult = true;
294
292
  completionParam.tool_call_id = message.tool_call_id;
295
293
  }
296
294
  }
295
+ if (options?.includeReasoningContent === true &&
296
+ messages.isAIMessage(message) &&
297
+ (hasReasoningToolCallContext || messageHasToolCalls) &&
298
+ typeof message.additional_kwargs.reasoning_content === 'string' &&
299
+ message.additional_kwargs.reasoning_content !== '') {
300
+ completionParam.reasoning_content =
301
+ message.additional_kwargs.reasoning_content;
302
+ }
303
+ if (messageHasToolCalls || messageIsToolResult) {
304
+ hasReasoningToolCallContext = true;
305
+ }
297
306
  if (message.additional_kwargs.audio &&
298
307
  typeof message.additional_kwargs.audio === 'object' &&
299
308
  'id' in message.additional_kwargs.audio) {
@@ -308,458 +317,11 @@ function _convertMessagesToOpenAIParams(messages$1, model, options) {
308
317
  return completionParam;
309
318
  });
310
319
  }
311
- const _FUNCTION_CALL_IDS_MAP_KEY = '__openai_function_call_ids__';
312
- function _convertReasoningSummaryToOpenAIResponsesParams(reasoning) {
313
- // combine summary parts that have the the same index and then remove the indexes
314
- const summary = (reasoning.summary.length > 1
315
- ? reasoning.summary.reduce((acc, curr) => {
316
- const last = acc.at(-1);
317
- if (last.index === curr.index) {
318
- last.text += curr.text;
319
- }
320
- else {
321
- acc.push(curr);
322
- }
323
- return acc;
324
- }, [{ ...reasoning.summary[0] }])
325
- : reasoning.summary).map((s) => Object.fromEntries(Object.entries(s).filter(([k]) => k !== 'index')));
326
- return {
327
- ...reasoning,
328
- summary,
329
- };
330
- }
331
- function _convertMessagesToOpenAIResponsesParams(messages$1, model, zdrEnabled) {
332
- return messages$1.flatMap((lcMsg) => {
333
- const additional_kwargs = lcMsg.additional_kwargs;
334
- let role = messageToOpenAIRole(lcMsg);
335
- if (role === 'system' && isReasoningModel(model))
336
- role = 'developer';
337
- if (role === 'function') {
338
- throw new Error('Function messages are not supported in Responses API');
339
- }
340
- if (role === 'tool') {
341
- const toolMessage = lcMsg;
342
- // Handle computer call output
343
- if (additional_kwargs.type === 'computer_call_output') {
344
- const output = (() => {
345
- if (typeof toolMessage.content === 'string') {
346
- return {
347
- type: 'computer_screenshot',
348
- image_url: toolMessage.content,
349
- };
350
- }
351
- if (Array.isArray(toolMessage.content)) {
352
- const oaiScreenshot = toolMessage.content.find((i) => i.type === 'computer_screenshot');
353
- if (oaiScreenshot)
354
- return oaiScreenshot;
355
- const lcImage = toolMessage.content.find((i) => i.type === 'image_url');
356
- if (lcImage) {
357
- return {
358
- type: 'computer_screenshot',
359
- image_url: typeof lcImage.image_url === 'string'
360
- ? lcImage.image_url
361
- : lcImage.image_url.url,
362
- };
363
- }
364
- }
365
- throw new Error('Invalid computer call output');
366
- })();
367
- return {
368
- type: 'computer_call_output',
369
- output,
370
- call_id: toolMessage.tool_call_id,
371
- };
372
- }
373
- return {
374
- type: 'function_call_output',
375
- call_id: toolMessage.tool_call_id,
376
- id: toolMessage.id?.startsWith('fc_') ? toolMessage.id : undefined,
377
- output: typeof toolMessage.content !== 'string'
378
- ? JSON.stringify(toolMessage.content)
379
- : toolMessage.content,
380
- };
381
- }
382
- if (role === 'assistant') {
383
- // if we have the original response items, just reuse them
384
- if (!zdrEnabled &&
385
- lcMsg.response_metadata.output != null &&
386
- Array.isArray(lcMsg.response_metadata.output) &&
387
- lcMsg.response_metadata.output.length > 0 &&
388
- lcMsg.response_metadata.output.every((item) => 'type' in item)) {
389
- return lcMsg.response_metadata.output;
390
- }
391
- // otherwise, try to reconstruct the response from what we have
392
- const input = [];
393
- // reasoning items
394
- if (additional_kwargs.reasoning && !zdrEnabled) {
395
- const reasoningItem = _convertReasoningSummaryToOpenAIResponsesParams(additional_kwargs.reasoning);
396
- input.push(reasoningItem);
397
- }
398
- // ai content
399
- let { content } = lcMsg;
400
- if (additional_kwargs.refusal) {
401
- if (typeof content === 'string') {
402
- content = [{ type: 'output_text', text: content, annotations: [] }];
403
- }
404
- content = [
405
- ...content,
406
- { type: 'refusal', refusal: additional_kwargs.refusal },
407
- ];
408
- }
409
- input.push({
410
- type: 'message',
411
- role: 'assistant',
412
- ...(lcMsg.id && !zdrEnabled && lcMsg.id.startsWith('msg_')
413
- ? { id: lcMsg.id }
414
- : {}),
415
- content: typeof content === 'string'
416
- ? content
417
- : content.flatMap((item) => {
418
- if (item.type === 'text') {
419
- return {
420
- type: 'output_text',
421
- text: item.text,
422
- // @ts-expect-error TODO: add types for `annotations`
423
- annotations: item.annotations ?? [],
424
- };
425
- }
426
- if (item.type === 'output_text' || item.type === 'refusal') {
427
- return item;
428
- }
429
- return [];
430
- }),
431
- });
432
- const functionCallIds = additional_kwargs[_FUNCTION_CALL_IDS_MAP_KEY];
433
- if (messages.isAIMessage(lcMsg) && !!lcMsg.tool_calls?.length) {
434
- input.push(...lcMsg.tool_calls.map((toolCall) => ({
435
- type: 'function_call',
436
- name: toolCall.name,
437
- arguments: JSON.stringify(toolCall.args),
438
- call_id: toolCall.id,
439
- ...(zdrEnabled ? { id: functionCallIds?.[toolCall.id] } : {}),
440
- })));
441
- }
442
- else if (additional_kwargs.tool_calls) {
443
- input.push(...additional_kwargs.tool_calls.map((toolCall) => ({
444
- type: 'function_call',
445
- name: toolCall.function.name,
446
- call_id: toolCall.id,
447
- arguments: toolCall.function.arguments,
448
- ...(zdrEnabled ? { id: functionCallIds?.[toolCall.id] } : {}),
449
- })));
450
- }
451
- const toolOutputs = (lcMsg.response_metadata.output?.length ?? 0) > 0
452
- ? lcMsg.response_metadata.output
453
- : additional_kwargs.tool_outputs;
454
- const fallthroughCallTypes = [
455
- 'computer_call',
456
- /** @ts-ignore */
457
- 'mcp_call',
458
- /** @ts-ignore */
459
- 'code_interpreter_call',
460
- /** @ts-ignore */
461
- 'image_generation_call',
462
- ];
463
- if (toolOutputs != null) {
464
- const castToolOutputs = toolOutputs;
465
- const fallthroughCalls = castToolOutputs.filter((item) => fallthroughCallTypes.includes(item.type));
466
- if (fallthroughCalls.length > 0)
467
- input.push(...fallthroughCalls);
468
- }
469
- return input;
470
- }
471
- if (role === 'user' || role === 'system' || role === 'developer') {
472
- if (typeof lcMsg.content === 'string') {
473
- return { type: 'message', role, content: lcMsg.content };
474
- }
475
- const messages$1 = [];
476
- const content = lcMsg.content.flatMap((item) => {
477
- if (item.type === 'mcp_approval_response') {
478
- messages$1.push({
479
- // @ts-ignore
480
- type: 'mcp_approval_response',
481
- approval_request_id: item.approval_request_id,
482
- approve: item.approve,
483
- });
484
- }
485
- if (messages.isDataContentBlock(item)) {
486
- return messages.convertToProviderContentBlock(item, completionsApiContentBlockConverter);
487
- }
488
- if (item.type === 'text') {
489
- return {
490
- type: 'input_text',
491
- text: item.text,
492
- };
493
- }
494
- if (item.type === 'image_url') {
495
- return {
496
- type: 'input_image',
497
- image_url: typeof item.image_url === 'string'
498
- ? item.image_url
499
- : item.image_url.url,
500
- detail: typeof item.image_url === 'string'
501
- ? 'auto'
502
- : item.image_url.detail,
503
- };
504
- }
505
- if (item.type === 'input_text' ||
506
- item.type === 'input_image' ||
507
- item.type === 'input_file') {
508
- return item;
509
- }
510
- return [];
511
- });
512
- if (content.length > 0) {
513
- messages$1.push({ type: 'message', role, content });
514
- }
515
- return messages$1;
516
- }
517
- console.warn(`Unsupported role found when converting to OpenAI Responses API: ${role}`);
518
- return [];
519
- });
520
- }
521
320
  function isReasoningModel(model) {
522
321
  return model != null && model !== '' && /\b(o\d|gpt-[5-9])\b/i.test(model);
523
322
  }
524
- function _convertOpenAIResponsesMessageToBaseMessage(response) {
525
- if (response.error) {
526
- // TODO: add support for `addLangChainErrorFields`
527
- const error = new Error(response.error.message);
528
- error.name = response.error.code;
529
- throw error;
530
- }
531
- let messageId;
532
- const content = [];
533
- const tool_calls = [];
534
- const invalid_tool_calls = [];
535
- const response_metadata = {
536
- model: response.model,
537
- created_at: response.created_at,
538
- id: response.id,
539
- incomplete_details: response.incomplete_details,
540
- metadata: response.metadata,
541
- object: response.object,
542
- status: response.status,
543
- user: response.user,
544
- service_tier: response.service_tier,
545
- // for compatibility with chat completion calls.
546
- model_name: response.model,
547
- };
548
- const additional_kwargs = {};
549
- for (const item of response.output) {
550
- if (item.type === 'message') {
551
- messageId = item.id;
552
- content.push(...item.content.flatMap((part) => {
553
- if (part.type === 'output_text') {
554
- if ('parsed' in part && part.parsed != null) {
555
- additional_kwargs.parsed = part.parsed;
556
- }
557
- return {
558
- type: 'text',
559
- text: part.text,
560
- annotations: part.annotations,
561
- };
562
- }
563
- if (part.type === 'refusal') {
564
- additional_kwargs.refusal = part.refusal;
565
- return [];
566
- }
567
- return part;
568
- }));
569
- }
570
- else if (item.type === 'function_call') {
571
- const fnAdapter = {
572
- function: { name: item.name, arguments: item.arguments },
573
- id: item.call_id,
574
- };
575
- try {
576
- tool_calls.push(openai_tools.parseToolCall(fnAdapter, { returnId: true }));
577
- }
578
- catch (e) {
579
- let errMessage;
580
- if (typeof e === 'object' &&
581
- e != null &&
582
- 'message' in e &&
583
- typeof e.message === 'string') {
584
- errMessage = e.message;
585
- }
586
- invalid_tool_calls.push(openai_tools.makeInvalidToolCall(fnAdapter, errMessage));
587
- }
588
- additional_kwargs[_FUNCTION_CALL_IDS_MAP_KEY] ??= {};
589
- if (item.id) {
590
- additional_kwargs[_FUNCTION_CALL_IDS_MAP_KEY][item.call_id] = item.id;
591
- }
592
- }
593
- else if (item.type === 'reasoning') {
594
- additional_kwargs.reasoning = item;
595
- }
596
- else {
597
- additional_kwargs.tool_outputs ??= [];
598
- additional_kwargs.tool_outputs.push(item);
599
- }
600
- }
601
- return new messages.AIMessage({
602
- id: messageId,
603
- content,
604
- tool_calls,
605
- invalid_tool_calls,
606
- usage_metadata: response.usage,
607
- additional_kwargs,
608
- response_metadata,
609
- });
610
- }
611
- function _convertOpenAIResponsesDeltaToBaseMessageChunk(chunk) {
612
- const content = [];
613
- let generationInfo = {};
614
- let usage_metadata;
615
- const tool_call_chunks = [];
616
- const response_metadata = {};
617
- const additional_kwargs = {};
618
- let id;
619
- if (chunk.type === 'response.output_text.delta') {
620
- content.push({
621
- type: 'text',
622
- text: chunk.delta,
623
- index: chunk.content_index,
624
- });
625
- /** @ts-ignore */
626
- }
627
- else if (chunk.type === 'response.output_text_annotation.added') {
628
- content.push({
629
- type: 'text',
630
- text: '',
631
- /** @ts-ignore */
632
- annotations: [chunk.annotation],
633
- /** @ts-ignore */
634
- index: chunk.content_index,
635
- });
636
- }
637
- else if (chunk.type === 'response.output_item.added' &&
638
- chunk.item.type === 'message') {
639
- id = chunk.item.id;
640
- }
641
- else if (chunk.type === 'response.output_item.added' &&
642
- chunk.item.type === 'function_call') {
643
- tool_call_chunks.push({
644
- type: 'tool_call_chunk',
645
- name: chunk.item.name,
646
- args: chunk.item.arguments,
647
- id: chunk.item.call_id,
648
- index: chunk.output_index,
649
- });
650
- additional_kwargs[_FUNCTION_CALL_IDS_MAP_KEY] = {
651
- [chunk.item.call_id]: chunk.item.id,
652
- };
653
- }
654
- else if (chunk.type === 'response.output_item.done' &&
655
- [
656
- 'web_search_call',
657
- 'file_search_call',
658
- 'computer_call',
659
- 'code_interpreter_call',
660
- 'mcp_call',
661
- 'mcp_list_tools',
662
- 'mcp_approval_request',
663
- 'image_generation_call',
664
- ].includes(chunk.item.type)) {
665
- additional_kwargs.tool_outputs = [chunk.item];
666
- }
667
- else if (chunk.type === 'response.created') {
668
- response_metadata.id = chunk.response.id;
669
- response_metadata.model_name = chunk.response.model;
670
- response_metadata.model = chunk.response.model;
671
- }
672
- else if (chunk.type === 'response.completed') {
673
- const msg = _convertOpenAIResponsesMessageToBaseMessage(chunk.response);
674
- usage_metadata = chunk.response.usage;
675
- if (chunk.response.text?.format?.type === 'json_schema') {
676
- additional_kwargs.parsed ??= JSON.parse(msg.text);
677
- }
678
- for (const [key, value] of Object.entries(chunk.response)) {
679
- if (key !== 'id')
680
- response_metadata[key] = value;
681
- }
682
- }
683
- else if (chunk.type === 'response.function_call_arguments.delta') {
684
- tool_call_chunks.push({
685
- type: 'tool_call_chunk',
686
- args: chunk.delta,
687
- index: chunk.output_index,
688
- });
689
- }
690
- else if (chunk.type === 'response.web_search_call.completed' ||
691
- chunk.type === 'response.file_search_call.completed') {
692
- generationInfo = {
693
- tool_outputs: {
694
- id: chunk.item_id,
695
- type: chunk.type.replace('response.', '').replace('.completed', ''),
696
- status: 'completed',
697
- },
698
- };
699
- }
700
- else if (chunk.type === 'response.refusal.done') {
701
- additional_kwargs.refusal = chunk.refusal;
702
- }
703
- else if (chunk.type === 'response.output_item.added' &&
704
- 'item' in chunk &&
705
- chunk.item.type === 'reasoning') {
706
- const summary = chunk
707
- .item.summary
708
- ? chunk.item.summary.map((s, index) => ({
709
- ...s,
710
- index,
711
- }))
712
- : undefined;
713
- additional_kwargs.reasoning = {
714
- // We only capture ID in the first chunk or else the concatenated result of all chunks will
715
- // have an ID field that is repeated once per chunk. There is special handling for the `type`
716
- // field that prevents this, however.
717
- id: chunk.item.id,
718
- type: chunk.item.type,
719
- ...(summary ? { summary } : {}),
720
- };
721
- }
722
- else if (chunk.type === 'response.reasoning_summary_part.added') {
723
- additional_kwargs.reasoning = {
724
- type: 'reasoning',
725
- summary: [{ ...chunk.part, index: chunk.summary_index }],
726
- };
727
- }
728
- else if (chunk.type === 'response.reasoning_summary_text.delta') {
729
- additional_kwargs.reasoning = {
730
- type: 'reasoning',
731
- summary: [
732
- { text: chunk.delta, type: 'summary_text', index: chunk.summary_index },
733
- ],
734
- };
735
- /** @ts-ignore */
736
- }
737
- else if (chunk.type === 'response.image_generation_call.partial_image') {
738
- // noop/fixme: retaining partial images in a message chunk means that _all_
739
- // partial images get kept in history, so we don't do anything here.
740
- return null;
741
- }
742
- else {
743
- return null;
744
- }
745
- return new outputs.ChatGenerationChunk({
746
- // Legacy reasons, `onLLMNewToken` should pulls this out
747
- text: content.map((part) => part.text).join(''),
748
- message: new messages.AIMessageChunk({
749
- id,
750
- content,
751
- tool_call_chunks,
752
- usage_metadata,
753
- additional_kwargs,
754
- response_metadata,
755
- }),
756
- generationInfo,
757
- });
758
- }
759
323
 
760
324
  exports._convertMessagesToOpenAIParams = _convertMessagesToOpenAIParams;
761
- exports._convertMessagesToOpenAIResponsesParams = _convertMessagesToOpenAIResponsesParams;
762
- exports._convertOpenAIResponsesDeltaToBaseMessageChunk = _convertOpenAIResponsesDeltaToBaseMessageChunk;
763
325
  exports.isReasoningModel = isReasoningModel;
764
326
  exports.messageToOpenAIRole = messageToOpenAIRole;
765
327
  //# sourceMappingURL=index.cjs.map