@ai-sdk/langchain 3.0.113 → 3.0.116

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.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,28 @@
1
1
  # @ai-sdk/langchain
2
2
 
3
+ ## 3.0.116
4
+
5
+ ### Patch Changes
6
+
7
+ - Updated dependencies [af9597b]
8
+ - Updated dependencies [bc49f78]
9
+ - ai@7.0.116
10
+
11
+ ## 3.0.115
12
+
13
+ ### Patch Changes
14
+
15
+ - Updated dependencies [be877ff]
16
+ - ai@7.0.115
17
+
18
+ ## 3.0.114
19
+
20
+ ### Patch Changes
21
+
22
+ - Updated dependencies [b5679a7]
23
+ - Updated dependencies [ca31b89]
24
+ - ai@7.0.114
25
+
3
26
  ## 3.0.113
4
27
 
5
28
  ### Patch Changes
package/dist/index.js CHANGED
@@ -24,7 +24,6 @@ function getLangGraphProviderMetadata(namespace) {
24
24
  };
25
25
  }
26
26
  function addLangGraphNamespace(chunk, namespace) {
27
- var _a;
28
27
  if (namespace === void 0) {
29
28
  return chunk;
30
29
  }
@@ -51,7 +50,7 @@ function addLangGraphNamespace(chunk, namespace) {
51
50
  providerMetadata: {
52
51
  ...chunk.providerMetadata,
53
52
  langchain: {
54
- ...(_a = chunk.providerMetadata) == null ? void 0 : _a.langchain,
53
+ ...chunk.providerMetadata?.langchain,
55
54
  namespace
56
55
  }
57
56
  }
@@ -84,7 +83,7 @@ function createLangGraphNamespaceController(controller, state, eventNamespace) {
84
83
  break;
85
84
  }
86
85
  controller.enqueue(
87
- addLangGraphNamespace(chunk, messageNamespace != null ? messageNamespace : eventNamespace)
86
+ addLangGraphNamespace(chunk, messageNamespace ?? eventNamespace)
88
87
  );
89
88
  }
90
89
  };
@@ -170,7 +169,6 @@ function convertImageToContentBlock(data, mediaType = "image/png") {
170
169
  };
171
170
  }
172
171
  function convertUserContent(content) {
173
- var _a;
174
172
  if (typeof content === "string") {
175
173
  return new HumanMessage({ content });
176
174
  }
@@ -209,7 +207,7 @@ function convertUserContent(content) {
209
207
  mediaType: rawFilePart.mediaType,
210
208
  filename: rawFilePart.filename
211
209
  };
212
- const isImage = (_a = filePart.mediaType) == null ? void 0 : _a.startsWith("image/");
210
+ const isImage = filePart.mediaType?.startsWith("image/");
213
211
  if (isImage) {
214
212
  contentBlocks.push(
215
213
  convertImageToContentBlock(filePart.data, filePart.mediaType)
@@ -280,7 +278,6 @@ function isToolResultPart(item) {
280
278
  return item != null && typeof item === "object" && "type" in item && item.type === "tool-result";
281
279
  }
282
280
  function processModelChunk(chunk, state, controller) {
283
- var _a, _b, _c;
284
281
  if (!state.emittedImages) {
285
282
  state.emittedImages = /* @__PURE__ */ new Set();
286
283
  }
@@ -316,7 +313,7 @@ function processModelChunk(chunk, state, controller) {
316
313
  controller.enqueue({
317
314
  type: "reasoning-delta",
318
315
  delta: reasoning,
319
- id: (_a = state.reasoningMessageId) != null ? _a : state.messageId
316
+ id: state.reasoningMessageId ?? state.messageId
320
317
  });
321
318
  }
322
319
  const text = typeof chunk.content === "string" ? chunk.content : Array.isArray(chunk.content) ? chunk.content.filter(
@@ -326,7 +323,7 @@ function processModelChunk(chunk, state, controller) {
326
323
  if (state.reasoningStarted && !state.textStarted) {
327
324
  controller.enqueue({
328
325
  type: "reasoning-end",
329
- id: (_b = state.reasoningMessageId) != null ? _b : state.messageId
326
+ id: state.reasoningMessageId ?? state.messageId
330
327
  });
331
328
  state.reasoningStarted = false;
332
329
  }
@@ -339,7 +336,7 @@ function processModelChunk(chunk, state, controller) {
339
336
  controller.enqueue({
340
337
  type: "text-delta",
341
338
  delta: text,
342
- id: (_c = state.textMessageId) != null ? _c : state.messageId
339
+ id: state.textMessageId ?? state.messageId
343
340
  });
344
341
  }
345
342
  const citations = extractCitationsFromContentBlocks(chunk);
@@ -400,9 +397,8 @@ function isToolMessageType(msg) {
400
397
  return false;
401
398
  }
402
399
  function getMessageText(msg) {
403
- var _a;
404
400
  if (AIMessageChunk.isInstance(msg)) {
405
- return (_a = msg.text) != null ? _a : "";
401
+ return msg.text ?? "";
406
402
  }
407
403
  if (msg == null || typeof msg !== "object") return "";
408
404
  const msgObj = msg;
@@ -431,12 +427,11 @@ function isGPT5ReasoningOutput(obj) {
431
427
  return obj != null && typeof obj === "object" && "type" in obj && obj.type === "reasoning" && "summary" in obj && Array.isArray(obj.summary);
432
428
  }
433
429
  function extractReasoningId(msg) {
434
- var _a;
435
430
  if (msg == null || typeof msg !== "object") return void 0;
436
431
  const msgObj = msg;
437
432
  const kwargs = msgObj.kwargs && typeof msgObj.kwargs === "object" ? msgObj.kwargs : msgObj;
438
433
  const additionalKwargs = kwargs.additional_kwargs;
439
- if ((_a = additionalKwargs == null ? void 0 : additionalKwargs.reasoning) == null ? void 0 : _a.id) {
434
+ if (additionalKwargs?.reasoning?.id) {
440
435
  return additionalKwargs.reasoning.id;
441
436
  }
442
437
  const responseMetadata = kwargs.response_metadata;
@@ -467,7 +462,7 @@ function extractReasoningFromContentBlocks(msg) {
467
462
  }
468
463
  }
469
464
  const additionalKwargs = kwargs.additional_kwargs;
470
- if ((additionalKwargs == null ? void 0 : additionalKwargs.reasoning) && Array.isArray(additionalKwargs.reasoning.summary)) {
465
+ if (additionalKwargs?.reasoning && Array.isArray(additionalKwargs.reasoning.summary)) {
471
466
  const reasoningParts = [];
472
467
  for (const summaryItem of additionalKwargs.reasoning.summary) {
473
468
  if (typeof summaryItem === "object" && summaryItem !== null && "text" in summaryItem && typeof summaryItem.text === "string") {
@@ -503,7 +498,7 @@ function extractReasoningFromValuesMessage(msg) {
503
498
  }
504
499
  }
505
500
  const additionalKwargs = kwargs.additional_kwargs;
506
- if ((additionalKwargs == null ? void 0 : additionalKwargs.reasoning) && Array.isArray(additionalKwargs.reasoning.summary)) {
501
+ if (additionalKwargs?.reasoning && Array.isArray(additionalKwargs.reasoning.summary)) {
507
502
  const reasoningParts = [];
508
503
  for (const summaryItem of additionalKwargs.reasoning.summary) {
509
504
  if (typeof summaryItem === "object" && summaryItem !== null && "text" in summaryItem && typeof summaryItem.text === "string") {
@@ -564,7 +559,6 @@ function buildSourceProviderMetadata(citation) {
564
559
  return { langchain };
565
560
  }
566
561
  function emitSourceChunks(citations, messageId, emittedSourceIds, controller) {
567
- var _a, _b, _c, _d;
568
562
  for (const citation of citations) {
569
563
  if (citation.url) {
570
564
  if (emittedSourceIds.has(citation.url)) continue;
@@ -579,9 +573,9 @@ function emitSourceChunks(citations, messageId, emittedSourceIds, controller) {
579
573
  });
580
574
  continue;
581
575
  }
582
- const title = (_a = citation.title) != null ? _a : citation.source;
576
+ const title = citation.title ?? citation.source;
583
577
  if (!title) continue;
584
- const sourceId = `${messageId}:${title}:${(_b = citation.citedText) != null ? _b : ""}:${(_c = citation.startIndex) != null ? _c : ""}:${(_d = citation.endIndex) != null ? _d : ""}`;
578
+ const sourceId = `${messageId}:${title}:${citation.citedText ?? ""}:${citation.startIndex ?? ""}:${citation.endIndex ?? ""}`;
585
579
  if (emittedSourceIds.has(sourceId)) continue;
586
580
  emittedSourceIds.add(sourceId);
587
581
  const providerMetadata = buildSourceProviderMetadata(citation);
@@ -608,8 +602,8 @@ function formatToolError(error) {
608
602
  if (typeof error === "string") return error;
609
603
  try {
610
604
  const serialized = JSON.stringify(error);
611
- return serialized != null ? serialized : String(error);
612
- } catch (e) {
605
+ return serialized ?? String(error);
606
+ } catch {
613
607
  return String(error);
614
608
  }
615
609
  }
@@ -630,7 +624,7 @@ function getOrCreateToolCallInfoByIndex(toolCallInfoByIndex, msgId) {
630
624
  return toolCallInfo;
631
625
  }
632
626
  function getLangGraphNamespaceKey(namespace) {
633
- return JSON.stringify(namespace != null ? namespace : []);
627
+ return JSON.stringify(namespace ?? []);
634
628
  }
635
629
  function getOrCreateNamespaceSet(setsByNamespace, namespace) {
636
630
  let values = setsByNamespace.get(namespace);
@@ -641,8 +635,7 @@ function getOrCreateNamespaceSet(setsByNamespace, namespace) {
641
635
  return values;
642
636
  }
643
637
  function hasEmittedToolCallInCurrentStep(state, toolCallId, namespace) {
644
- var _a;
645
- return !state.currentStepsByNamespace.has(namespace) ? state.emittedToolCalls.has(toolCallId) : ((_a = state.emittedToolCallsInCurrentStepByNamespace.get(namespace)) == null ? void 0 : _a.has(toolCallId)) === true;
638
+ return !state.currentStepsByNamespace.has(namespace) ? state.emittedToolCalls.has(toolCallId) : state.emittedToolCallsInCurrentStepByNamespace.get(namespace)?.has(toolCallId) === true;
646
639
  }
647
640
  function markToolCallEmitted(state, toolCallId, namespace) {
648
641
  state.emittedToolCalls.add(toolCallId);
@@ -654,8 +647,7 @@ function markToolCallEmitted(state, toolCallId, namespace) {
654
647
  }
655
648
  }
656
649
  function hasEmittedToolInputInCurrentStep(state, toolCallId, namespace) {
657
- var _a;
658
- return !state.currentStepsByNamespace.has(namespace) ? state.emittedToolInputs.has(toolCallId) : ((_a = state.emittedToolInputsInCurrentStepByNamespace.get(namespace)) == null ? void 0 : _a.has(toolCallId)) === true;
650
+ return !state.currentStepsByNamespace.has(namespace) ? state.emittedToolInputs.has(toolCallId) : state.emittedToolInputsInCurrentStepByNamespace.get(namespace)?.has(toolCallId) === true;
659
651
  }
660
652
  function markToolInputEmitted(state, toolCallId, namespace) {
661
653
  state.emittedToolInputs.add(toolCallId);
@@ -667,8 +659,7 @@ function markToolInputEmitted(state, toolCallId, namespace) {
667
659
  }
668
660
  }
669
661
  function hasEmittedToolOutputInCurrentStep(state, toolCallId, namespace) {
670
- var _a;
671
- return !state.currentStepsByNamespace.has(namespace) ? state.emittedToolOutputCallIds.has(toolCallId) : ((_a = state.emittedToolOutputsInCurrentStepByNamespace.get(namespace)) == null ? void 0 : _a.has(toolCallId)) === true;
662
+ return !state.currentStepsByNamespace.has(namespace) ? state.emittedToolOutputCallIds.has(toolCallId) : state.emittedToolOutputsInCurrentStepByNamespace.get(namespace)?.has(toolCallId) === true;
672
663
  }
673
664
  function markToolOutputEmitted(state, toolCallId, namespace) {
674
665
  state.emittedToolOutputCallIds.add(toolCallId);
@@ -715,7 +706,6 @@ function closeStepNamespaceMessages(state, stepNamespace, controller) {
715
706
  return hasConcurrentMessageParts;
716
707
  }
717
708
  function processLangGraphEvent(event, state, controller) {
718
- var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o;
719
709
  const {
720
710
  messageSeen,
721
711
  messageConcat,
@@ -759,9 +749,9 @@ function processLangGraphEvent(event, state, controller) {
759
749
  if (namespace !== void 0) {
760
750
  state.messageNamespaces.set(msgId, namespace);
761
751
  }
762
- const langgraphStep = typeof (metadata == null ? void 0 : metadata.langgraph_step) === "number" ? metadata.langgraph_step : null;
752
+ const langgraphStep = typeof metadata?.langgraph_step === "number" ? metadata.langgraph_step : null;
763
753
  if (langgraphStep !== null) {
764
- const currentStep = (_a = state.currentStepsByNamespace.get(eventNamespace)) != null ? _a : null;
754
+ const currentStep = state.currentStepsByNamespace.get(eventNamespace) ?? null;
765
755
  if (currentStep === null) {
766
756
  if (state.currentStepsByNamespace.size === 0) {
767
757
  controller.enqueue({ type: "start-step" });
@@ -847,28 +837,28 @@ function processLangGraphEvent(event, state, controller) {
847
837
  }
848
838
  }
849
839
  const toolCallChunks = dataSource.tool_call_chunks;
850
- if (toolCallChunks == null ? void 0 : toolCallChunks.length) {
840
+ if (toolCallChunks?.length) {
851
841
  for (const toolCallChunk of toolCallChunks) {
852
- const toolCallIndex = (_b = toolCallChunk.index) != null ? _b : 0;
842
+ const toolCallIndex = toolCallChunk.index ?? 0;
853
843
  if (toolCallChunk.id) {
854
844
  getOrCreateToolCallInfoByIndex(toolCallInfoByIndex, msgId).set(
855
845
  toolCallIndex,
856
846
  {
857
847
  id: toolCallChunk.id,
858
- name: toolCallChunk.name || ((_d = (_c = concatChunk == null ? void 0 : concatChunk.tool_call_chunks) == null ? void 0 : _c[toolCallIndex]) == null ? void 0 : _d.name) || "unknown"
848
+ name: toolCallChunk.name || concatChunk?.tool_call_chunks?.[toolCallIndex]?.name || "unknown"
859
849
  }
860
850
  );
861
851
  }
862
- const storedToolCallInfo = (_e = toolCallInfoByIndex.get(msgId)) == null ? void 0 : _e.get(toolCallIndex);
863
- const toolCallId = toolCallChunk.id || (storedToolCallInfo == null ? void 0 : storedToolCallInfo.id) || ((_g = (_f = concatChunk == null ? void 0 : concatChunk.tool_call_chunks) == null ? void 0 : _f[toolCallIndex]) == null ? void 0 : _g.id);
852
+ const storedToolCallInfo = toolCallInfoByIndex.get(msgId)?.get(toolCallIndex);
853
+ const toolCallId = toolCallChunk.id || storedToolCallInfo?.id || concatChunk?.tool_call_chunks?.[toolCallIndex]?.id;
864
854
  if (!toolCallId) {
865
855
  continue;
866
856
  }
867
- const toolName = toolCallChunk.name || (storedToolCallInfo == null ? void 0 : storedToolCallInfo.name) || ((_i = (_h = concatChunk == null ? void 0 : concatChunk.tool_call_chunks) == null ? void 0 : _h[toolCallIndex]) == null ? void 0 : _i.name) || "unknown";
857
+ const toolName = toolCallChunk.name || storedToolCallInfo?.name || concatChunk?.tool_call_chunks?.[toolCallIndex]?.name || "unknown";
868
858
  const seen = messageSeen.get(msgId);
869
- if (!((_j = seen == null ? void 0 : seen.tool) == null ? void 0 : _j.has(toolCallId))) {
859
+ if (!seen?.tool?.has(toolCallId)) {
870
860
  const updatedSeen = getOrCreateMessageSeen(messageSeen, msgId);
871
- (_k = updatedSeen.tool) != null ? _k : updatedSeen.tool = /* @__PURE__ */ new Set();
861
+ updatedSeen.tool ??= /* @__PURE__ */ new Set();
872
862
  updatedSeen.tool.add(toolCallId);
873
863
  if (!hasEmittedToolCallInCurrentStep(
874
864
  state,
@@ -903,9 +893,9 @@ function processLangGraphEvent(event, state, controller) {
903
893
  }
904
894
  const reasoning = extractReasoningFromContentBlocks(msg);
905
895
  if (reasoning) {
906
- const reasoningId = (_m = (_l = messageReasoningIds.get(msgId)) != null ? _l : chunkReasoningId) != null ? _m : msgId;
896
+ const reasoningId = messageReasoningIds.get(msgId) ?? chunkReasoningId ?? msgId;
907
897
  const seen = messageSeen.get(msgId);
908
- if (!(seen == null ? void 0 : seen.reasoning)) {
898
+ if (!seen?.reasoning) {
909
899
  controller.enqueue({ type: "reasoning-start", id: msgId });
910
900
  getOrCreateMessageSeen(messageSeen, msgId).reasoning = true;
911
901
  }
@@ -919,11 +909,11 @@ function processLangGraphEvent(event, state, controller) {
919
909
  const text = getMessageText(msg);
920
910
  if (text) {
921
911
  const seen = messageSeen.get(msgId);
922
- if ((seen == null ? void 0 : seen.reasoning) && !seen.text) {
912
+ if (seen?.reasoning && !seen.text) {
923
913
  controller.enqueue({ type: "reasoning-end", id: msgId });
924
914
  seen.reasoning = false;
925
915
  }
926
- if (!(seen == null ? void 0 : seen.text)) {
916
+ if (!seen?.text) {
927
917
  controller.enqueue({ type: "text-start", id: msgId });
928
918
  getOrCreateMessageSeen(messageSeen, msgId).text = true;
929
919
  }
@@ -1050,7 +1040,7 @@ function processLangGraphEvent(event, state, controller) {
1050
1040
  if (seen.tool) {
1051
1041
  for (const toolCallId of seen.tool) {
1052
1042
  const concatMsg = messageConcat.get(id);
1053
- const toolCall = (_n = concatMsg == null ? void 0 : concatMsg.tool_calls) == null ? void 0 : _n.find(
1043
+ const toolCall = concatMsg?.tool_calls?.find(
1054
1044
  (call) => call.id === toolCallId
1055
1045
  );
1056
1046
  if (toolCall) {
@@ -1102,7 +1092,7 @@ function processLangGraphEvent(event, state, controller) {
1102
1092
  if (index >= trailingToolMessageStart) {
1103
1093
  trailingToolMessages.set(toolCallId, {
1104
1094
  data: dataSource,
1105
- outputId: (_o = getMessageId(msg)) != null ? _o : `${toolCallId}:${index}`
1095
+ outputId: getMessageId(msg) ?? `${toolCallId}:${index}`
1106
1096
  });
1107
1097
  }
1108
1098
  }
@@ -1120,13 +1110,13 @@ function processLangGraphEvent(event, state, controller) {
1120
1110
  const isSerializedFormat = messageRecord.type === "constructor" && Array.isArray(messageRecord.id) && (messageRecord.id.includes("AIMessageChunk") || messageRecord.id.includes("AIMessage"));
1121
1111
  const dataSource = isSerializedFormat ? messageRecord.kwargs : messageRecord;
1122
1112
  if (messageRecord.type === "ai" || messageRecord.type === "AIMessageChunk" || isSerializedFormat) {
1123
- if (Array.isArray(dataSource == null ? void 0 : dataSource.tool_calls)) {
1113
+ if (Array.isArray(dataSource?.tool_calls)) {
1124
1114
  toolCalls = dataSource.tool_calls;
1125
1115
  } else if (
1126
1116
  /**
1127
1117
  * Fall back to additional_kwargs.tool_calls (OpenAI format)
1128
1118
  */
1129
- (dataSource == null ? void 0 : dataSource.additional_kwargs) && typeof dataSource.additional_kwargs === "object"
1119
+ dataSource?.additional_kwargs && typeof dataSource.additional_kwargs === "object"
1130
1120
  ) {
1131
1121
  const additionalKwargs = dataSource.additional_kwargs;
1132
1122
  if (Array.isArray(additionalKwargs.tool_calls)) {
@@ -1134,13 +1124,13 @@ function processLangGraphEvent(event, state, controller) {
1134
1124
  const functionData = tc.function;
1135
1125
  let args;
1136
1126
  try {
1137
- args = (functionData == null ? void 0 : functionData.arguments) ? JSON.parse(functionData.arguments) : {};
1138
- } catch (e) {
1127
+ args = functionData?.arguments ? JSON.parse(functionData.arguments) : {};
1128
+ } catch {
1139
1129
  args = {};
1140
1130
  }
1141
1131
  return {
1142
1132
  id: tc.id || `call_${idx}`,
1143
- name: (functionData == null ? void 0 : functionData.name) || "unknown",
1133
+ name: functionData?.name || "unknown",
1144
1134
  args
1145
1135
  };
1146
1136
  });
@@ -1154,7 +1144,7 @@ function processLangGraphEvent(event, state, controller) {
1154
1144
  state,
1155
1145
  msgId
1156
1146
  );
1157
- const lifecycleNamespace = messageNamespace != null ? messageNamespace : eventNamespace;
1147
+ const lifecycleNamespace = messageNamespace ?? eventNamespace;
1158
1148
  const wasObservedInCurrentStep = messageNamespace !== void 0;
1159
1149
  const wasToolCallEmittedInCurrentStep = toolCall.id ? hasEmittedToolCallInCurrentStep(
1160
1150
  state,
@@ -1246,7 +1236,7 @@ function processLangGraphEvent(event, state, controller) {
1246
1236
  const interrupt = data.__interrupt__;
1247
1237
  if (Array.isArray(interrupt) && interrupt.length > 0) {
1248
1238
  for (const interruptItem of interrupt) {
1249
- const interruptValue = interruptItem == null ? void 0 : interruptItem.value;
1239
+ const interruptValue = interruptItem?.value;
1250
1240
  if (!interruptValue) continue;
1251
1241
  const actionRequests = interruptValue.actionRequests || interruptValue.action_requests;
1252
1242
  if (!Array.isArray(actionRequests)) continue;
@@ -1328,7 +1318,6 @@ function isStreamEventsEvent(value) {
1328
1318
  return obj.data === null || typeof obj.data === "object";
1329
1319
  }
1330
1320
  function processStreamEventsEvent(event, state, controller) {
1331
- var _a, _b, _c;
1332
1321
  if (event.run_id && !state.started) {
1333
1322
  state.messageId = event.run_id;
1334
1323
  }
@@ -1378,7 +1367,7 @@ function processStreamEventsEvent(event, state, controller) {
1378
1367
  controller.enqueue({
1379
1368
  type: "reasoning-delta",
1380
1369
  delta: reasoning,
1381
- id: (_a = state.reasoningMessageId) != null ? _a : state.messageId
1370
+ id: state.reasoningMessageId ?? state.messageId
1382
1371
  });
1383
1372
  }
1384
1373
  const content = chunk.content;
@@ -1389,7 +1378,7 @@ function processStreamEventsEvent(event, state, controller) {
1389
1378
  if (state.reasoningStarted && !state.textStarted) {
1390
1379
  controller.enqueue({
1391
1380
  type: "reasoning-end",
1392
- id: (_b = state.reasoningMessageId) != null ? _b : state.messageId
1381
+ id: state.reasoningMessageId ?? state.messageId
1393
1382
  });
1394
1383
  state.reasoningStarted = false;
1395
1384
  }
@@ -1402,7 +1391,7 @@ function processStreamEventsEvent(event, state, controller) {
1402
1391
  controller.enqueue({
1403
1392
  type: "text-delta",
1404
1393
  delta: text,
1405
- id: (_c = state.textMessageId) != null ? _c : state.messageId
1394
+ id: state.textMessageId ?? state.messageId
1406
1395
  });
1407
1396
  }
1408
1397
  const citations = extractCitationsFromContentBlocks(chunk);
@@ -1451,7 +1440,7 @@ function isAbortError(error) {
1451
1440
  return false;
1452
1441
  }
1453
1442
  function toUIMessageStream(stream, options) {
1454
- const { sendStart = true, sendFinish = true } = options != null ? options : {};
1443
+ const { sendStart = true, sendFinish = true } = options ?? {};
1455
1444
  const textChunks = [];
1456
1445
  let lastValuesData;
1457
1446
  const modelState = {
@@ -1507,13 +1496,12 @@ function toUIMessageStream(stream, options) {
1507
1496
  close: () => originalController.close(),
1508
1497
  error: (e) => originalController.error(e),
1509
1498
  enqueue: (chunk) => {
1510
- var _a, _b;
1511
1499
  if (chunk.type === "text-delta" && chunk.delta) {
1512
- if (options == null ? void 0 : options.onFinal) {
1500
+ if (options?.onFinal) {
1513
1501
  textChunks.push(chunk.delta);
1514
1502
  }
1515
- (_a = options == null ? void 0 : options.onToken) == null ? void 0 : _a.call(options, chunk.delta);
1516
- (_b = options == null ? void 0 : options.onText) == null ? void 0 : _b.call(options, chunk.delta);
1503
+ options?.onToken?.(chunk.delta);
1504
+ options?.onText?.(chunk.delta);
1517
1505
  }
1518
1506
  originalController.enqueue(chunk);
1519
1507
  }
@@ -1521,8 +1509,7 @@ function toUIMessageStream(stream, options) {
1521
1509
  };
1522
1510
  return new ReadableStream({
1523
1511
  async start(controller) {
1524
- var _a, _b, _c, _d, _e, _f, _g, _h;
1525
- await ((_a = options == null ? void 0 : options.onStart) == null ? void 0 : _a.call(options));
1512
+ await options?.onStart?.();
1526
1513
  const wrappedController = createCallbackController(controller);
1527
1514
  if (sendStart) {
1528
1515
  controller.enqueue({ type: "start" });
@@ -1569,13 +1556,13 @@ function toUIMessageStream(stream, options) {
1569
1556
  if (modelState.reasoningStarted) {
1570
1557
  controller.enqueue({
1571
1558
  type: "reasoning-end",
1572
- id: (_b = modelState.reasoningMessageId) != null ? _b : modelState.messageId
1559
+ id: modelState.reasoningMessageId ?? modelState.messageId
1573
1560
  });
1574
1561
  }
1575
1562
  if (modelState.textStarted) {
1576
1563
  controller.enqueue({
1577
1564
  type: "text-end",
1578
- id: (_c = modelState.textMessageId) != null ? _c : modelState.messageId
1565
+ id: modelState.textMessageId ?? modelState.messageId
1579
1566
  });
1580
1567
  }
1581
1568
  if (sendFinish) {
@@ -1608,15 +1595,15 @@ function toUIMessageStream(stream, options) {
1608
1595
  controller.enqueue({ type: "finish" });
1609
1596
  }
1610
1597
  }
1611
- await ((_d = options == null ? void 0 : options.onFinal) == null ? void 0 : _d.call(options, textChunks.join("")));
1612
- await ((_e = options == null ? void 0 : options.onFinish) == null ? void 0 : _e.call(options, lastValuesData));
1598
+ await options?.onFinal?.(textChunks.join(""));
1599
+ await options?.onFinish?.(lastValuesData);
1613
1600
  } catch (error) {
1614
1601
  const errorObj = error instanceof Error ? error : new Error(String(error));
1615
- await ((_f = options == null ? void 0 : options.onFinal) == null ? void 0 : _f.call(options, textChunks.join("")));
1602
+ await options?.onFinal?.(textChunks.join(""));
1616
1603
  if (isAbortError(error)) {
1617
- await ((_g = options == null ? void 0 : options.onAbort) == null ? void 0 : _g.call(options));
1604
+ await options?.onAbort?.();
1618
1605
  } else {
1619
- await ((_h = options == null ? void 0 : options.onError) == null ? void 0 : _h.call(options, errorObj));
1606
+ await options?.onError?.(errorObj);
1620
1607
  }
1621
1608
  controller.enqueue({
1622
1609
  type: "error",
@@ -1635,10 +1622,9 @@ import {
1635
1622
  } from "@langchain/langgraph/remote";
1636
1623
  var LangSmithDeploymentTransport = class {
1637
1624
  constructor(options) {
1638
- var _a;
1639
1625
  this.graph = new RemoteGraph({
1640
1626
  ...options,
1641
- graphId: (_a = options.graphId) != null ? _a : "agent"
1627
+ graphId: options.graphId ?? "agent"
1642
1628
  });
1643
1629
  }
1644
1630
  async sendMessages(options) {
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/adapter.ts","../src/utils.ts","../src/transport.ts"],"sourcesContent":["import {\n SystemMessage,\n type BaseMessage,\n type AIMessageChunk,\n} from '@langchain/core/messages';\nimport {\n convertToModelMessages,\n type UIMessage,\n type UIMessageChunk,\n type ModelMessage,\n} from 'ai';\nimport {\n convertToolResultPart,\n convertAssistantContent,\n convertUserContent,\n processModelChunk,\n processLangGraphEvent,\n parseLangGraphEvent,\n isToolResultPart,\n extractReasoningFromContentBlocks,\n extractCitationsFromContentBlocks,\n emitSourceChunks,\n getLangGraphProviderMetadata,\n} from './utils';\nimport type { LangGraphEventState } from './types';\nimport type { StreamCallbacks } from './stream-callbacks';\n\n/**\n * Options for converting a LangChain stream to an AI SDK UIMessageStream.\n */\nexport interface ToUIMessageStreamOptions<\n TState = unknown,\n> extends StreamCallbacks<TState> {\n /**\n * Whether to emit the outer `start` chunk.\n *\n * @default true\n */\n sendStart?: boolean;\n\n /**\n * Whether to emit the outer `finish` chunk.\n *\n * @default true\n */\n sendFinish?: boolean;\n}\n\n/**\n * Converts AI SDK UIMessages to LangChain BaseMessage objects.\n *\n * This function transforms the AI SDK's message format into LangChain's message\n * format, enabling seamless integration between the two frameworks.\n *\n * @param messages - Array of AI SDK UIMessage objects to convert.\n * @returns Promise resolving to an array of LangChain BaseMessage objects.\n *\n * @example\n * ```ts\n * import { toBaseMessages } from '@ai-sdk/langchain';\n *\n * const langchainMessages = await toBaseMessages(uiMessages);\n *\n * // Use with LangChain\n * const response = await model.invoke(langchainMessages);\n * ```\n */\nexport async function toBaseMessages(\n messages: UIMessage[],\n): Promise<BaseMessage[]> {\n const modelMessages = await convertToModelMessages(messages);\n return convertModelMessages(modelMessages);\n}\n\n/**\n * Converts ModelMessages to LangChain BaseMessage objects.\n *\n * @param modelMessages - Array of ModelMessage objects from convertToModelMessages.\n * @returns Array of LangChain BaseMessage objects.\n */\nexport function convertModelMessages(\n modelMessages: ModelMessage[],\n): BaseMessage[] {\n const result: BaseMessage[] = [];\n\n for (const message of modelMessages) {\n switch (message.role) {\n case 'tool': {\n // Tool messages contain an array of tool results\n for (const item of message.content) {\n if (isToolResultPart(item)) {\n result.push(convertToolResultPart(item));\n }\n }\n break;\n }\n\n case 'assistant': {\n result.push(convertAssistantContent(message.content));\n break;\n }\n\n case 'system': {\n result.push(new SystemMessage({ content: message.content }));\n break;\n }\n\n case 'user': {\n result.push(convertUserContent(message.content));\n break;\n }\n }\n }\n\n return result;\n}\n\n/**\n * Type guard to check if a value is a streamEvents event object.\n * streamEvents produces objects with `event` and `data` properties.\n *\n * @param value - The value to check.\n * @returns True if the value is a streamEvents event object.\n */\nfunction isStreamEventsEvent(\n value: unknown,\n): value is { event: string; data: Record<string, unknown> } {\n if (value == null || typeof value !== 'object') return false;\n const obj = value as Record<string, unknown>;\n // Check for event property being a string\n if (!('event' in obj) || typeof obj.event !== 'string') return false;\n // Check for data property being an object (but allow null/undefined)\n if (!('data' in obj)) return false;\n // data can be null in some events, treat as empty object\n return obj.data === null || typeof obj.data === 'object';\n}\n\n/**\n * Processes a streamEvents event and emits UI message chunks.\n *\n * @param event - The streamEvents event to process.\n * @param state - The state for tracking stream progress.\n * @param controller - The controller to emit UI message chunks.\n */\nfunction processStreamEventsEvent(\n event: {\n event: string;\n data: Record<string, unknown> | null;\n run_id?: string;\n name?: string;\n },\n state: {\n started: boolean;\n messageId: string;\n reasoningStarted: boolean;\n textStarted: boolean;\n textMessageId: string | null;\n reasoningMessageId: string | null;\n emittedSourceIds: Set<string>;\n },\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): void {\n /**\n * Capture run_id from event level if available (streamEvents v2 format)\n */\n if (event.run_id && !state.started) {\n state.messageId = event.run_id;\n }\n\n /**\n * Skip events with null/undefined data\n */\n if (!event.data) return;\n\n switch (event.event) {\n case 'on_chat_model_start': {\n /**\n * End the previous model turn's reasoning stream before a new LLM invocation.\n * Without this, reasoning-delta chunks from the next turn could attach to the\n * wrong reasoning part in the UI message stream.\n */\n if (state.reasoningStarted) {\n controller.enqueue({\n type: 'reasoning-end',\n id:\n state.reasoningMessageId != null\n ? state.reasoningMessageId\n : state.messageId,\n });\n state.reasoningStarted = false;\n state.reasoningMessageId = null;\n }\n\n /**\n * End the previous model turn's text stream before a new LLM invocation.\n * The streamEvents adapter otherwise leaves `textStarted` true, so all later\n * text-delta chunks append to the first text part — tools still grow the parts\n * array, which breaks chronological order in the assistant message.\n */\n if (state.textStarted) {\n controller.enqueue({\n type: 'text-end',\n id:\n state.textMessageId != null ? state.textMessageId : state.messageId,\n });\n state.textStarted = false;\n state.textMessageId = null;\n }\n\n /**\n * Handle model start — capture message metadata if available.\n * `run_id` is on the event in streamEvents v2; fall back to `data` for compatibility.\n */\n const runId = event.run_id || (event.data.run_id as string | undefined);\n if (runId) {\n state.messageId = runId;\n }\n break;\n }\n\n case 'on_chat_model_stream': {\n /**\n * Handle streaming token chunks\n */\n const chunk = event.data.chunk;\n if (chunk && typeof chunk === 'object') {\n /**\n * Get message ID from chunk if available\n */\n const chunkId = (chunk as { id?: string }).id;\n if (chunkId) {\n state.messageId = chunkId;\n }\n\n /**\n * Handle reasoning content from contentBlocks\n */\n const reasoning = extractReasoningFromContentBlocks(chunk);\n if (reasoning) {\n if (!state.reasoningStarted) {\n // Track the ID used for reasoning-start to ensure reasoning-end uses the same ID\n state.reasoningMessageId = state.messageId;\n controller.enqueue({\n type: 'reasoning-start',\n id: state.messageId,\n });\n state.reasoningStarted = true;\n state.started = true;\n }\n controller.enqueue({\n type: 'reasoning-delta',\n delta: reasoning,\n id: state.reasoningMessageId ?? state.messageId,\n });\n }\n\n /**\n * Extract text content from chunk\n */\n const content = (chunk as { content?: unknown }).content;\n const text =\n typeof content === 'string'\n ? content\n : Array.isArray(content)\n ? content\n .filter(\n (c): c is { type: 'text'; text: string } =>\n typeof c === 'object' &&\n c !== null &&\n 'type' in c &&\n c.type === 'text',\n )\n .map(c => c.text)\n .join('')\n : '';\n\n if (text) {\n /**\n * If reasoning was streamed before text, close reasoning first\n */\n if (state.reasoningStarted && !state.textStarted) {\n controller.enqueue({\n type: 'reasoning-end',\n id: state.reasoningMessageId ?? state.messageId,\n });\n state.reasoningStarted = false;\n }\n\n if (!state.textStarted) {\n // Track the ID used for text-start to ensure text-end uses the same ID\n state.textMessageId = state.messageId;\n controller.enqueue({ type: 'text-start', id: state.messageId });\n state.textStarted = true;\n state.started = true;\n }\n controller.enqueue({\n type: 'text-delta',\n delta: text,\n id: state.textMessageId ?? state.messageId,\n });\n }\n\n const citations = extractCitationsFromContentBlocks(chunk);\n if (citations.length > 0) {\n emitSourceChunks(\n citations,\n state.messageId,\n state.emittedSourceIds,\n controller,\n );\n }\n }\n break;\n }\n\n case 'on_tool_start': {\n /**\n * Handle tool call start\n * run_id and name are at event level in v2, check data for backwards compatibility\n */\n const runId = event.run_id || (event.data.run_id as string | undefined);\n const name = event.name || (event.data.name as string | undefined);\n\n if (runId && name) {\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId: runId,\n toolName: name,\n dynamic: true,\n });\n }\n break;\n }\n\n case 'on_tool_end': {\n /**\n * Handle tool call end\n * run_id is at event level in v2, check data for backwards compatibility\n */\n const runId = event.run_id || (event.data.run_id as string | undefined);\n const output = event.data.output;\n\n if (runId) {\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId: runId,\n output,\n });\n }\n break;\n }\n }\n}\n\n/**\n * Checks if an error is an abort error.\n */\nfunction isAbortError(error: unknown): boolean {\n if (error instanceof Error) {\n return (\n error.name === 'AbortError' ||\n (error instanceof DOMException && error.name === 'AbortError')\n );\n }\n return false;\n}\n\n/**\n * Converts a LangChain stream to an AI SDK UIMessageStream.\n *\n * This function automatically detects the stream type and handles:\n * - Direct model streams (AsyncIterable from `model.stream()`)\n * - LangGraph streams (ReadableStream with `streamMode: ['values', 'messages']`)\n * - streamEvents streams (from `agent.streamEvents()` or `model.streamEvents()`)\n *\n * @param stream - A stream from LangChain model.stream(), graph.stream(), or streamEvents().\n * @param options - Optional lifecycle callbacks and outer chunk controls.\n * @returns A ReadableStream of UIMessageChunk objects.\n *\n * @example\n * ```ts\n * // With a direct model stream\n * const model = new ChatOpenAI({ model: 'gpt-4o-mini' });\n * const stream = await model.stream(messages);\n * return createUIMessageStreamResponse({\n * stream: toUIMessageStream(stream),\n * });\n *\n * // With a LangGraph stream\n * const graphStream = await graph.stream(\n * { messages },\n * { streamMode: ['values', 'messages'] }\n * );\n * return createUIMessageStreamResponse({\n * stream: toUIMessageStream(graphStream),\n * });\n *\n * // With streamEvents\n * const streamEvents = agent.streamEvents(\n * { messages },\n * { version: \"v2\" }\n * );\n * return createUIMessageStreamResponse({\n * stream: toUIMessageStream(streamEvents),\n * });\n *\n * // With callbacks for LangGraph state\n * const graphStream = await graph.stream(\n * { messages },\n * { streamMode: ['values', 'messages'] }\n * );\n * return createUIMessageStreamResponse({\n * stream: toUIMessageStream<MyStateType>(graphStream, {\n * onFinish: async (finalState) => {\n * if (finalState) {\n * await saveToDatabase(finalState);\n * }\n * },\n * onError: (error) => console.error('Stream failed:', error),\n * onAbort: () => console.log('Stream aborted'),\n * }),\n * });\n * ```\n */\nexport function toUIMessageStream<TState = unknown>(\n stream: AsyncIterable<AIMessageChunk> | ReadableStream,\n options?: ToUIMessageStreamOptions<TState>,\n): ReadableStream<UIMessageChunk> {\n const { sendStart = true, sendFinish = true } = options ?? {};\n\n /**\n * Track text chunks for onFinal callback\n */\n const textChunks: string[] = [];\n\n /** Last LangGraph values event data for onFinish callback */\n let lastValuesData: TState | undefined;\n\n /**\n * State for model stream handling\n */\n const modelState = {\n started: false,\n messageId: 'langchain-msg-1',\n reasoningStarted: false,\n textStarted: false,\n /** Track the ID used for text-start to ensure text-end uses the same ID */\n textMessageId: null as string | null,\n /** Track the ID used for reasoning-start to ensure reasoning-end uses the same ID */\n reasoningMessageId: null as string | null,\n emittedSourceIds: new Set<string>(),\n };\n\n /**\n * State for LangGraph stream handling\n */\n const langGraphState: LangGraphEventState = {\n messageSeen: new Map(),\n messageNamespaces: new Map(),\n messageConcat: new Map(),\n messageIdsInCurrentStepByNamespace: new Map(),\n emittedToolCalls: new Set<string>(),\n emittedToolCallsInCurrentStepByNamespace: new Map(),\n emittedToolInputs: new Set<string>(),\n emittedToolInputsInCurrentStepByNamespace: new Map(),\n emittedToolOutputMessageIds: new Set<string>(),\n emittedToolOutputCallIds: new Set<string>(),\n emittedToolOutputsInCurrentStepByNamespace: new Map(),\n emittedImages: new Set<string>(),\n emittedReasoningIds: new Set<string>(),\n messageReasoningIds: new Map(),\n toolCallInfoByIndex: new Map(),\n currentStepsByNamespace: new Map(),\n emittedToolCallsByKey: new Map<string, string>(),\n emittedSourceIds: new Set<string>(),\n };\n\n /**\n * Track detected stream type: null = not yet detected\n */\n let streamType: 'model' | 'langgraph' | 'streamEvents' | null = null;\n\n /**\n * Get async iterator from the stream (works for both AsyncIterable and ReadableStream)\n */\n const getAsyncIterator = (): AsyncIterator<unknown> => {\n if (Symbol.asyncIterator in stream) {\n return (stream as AsyncIterable<unknown>)[Symbol.asyncIterator]();\n }\n /**\n * For ReadableStream without Symbol.asyncIterator\n */\n const reader = (stream as ReadableStream).getReader();\n return {\n async next() {\n const { done, value } = await reader.read();\n return { done, value };\n },\n };\n };\n\n const iterator = getAsyncIterator();\n\n /**\n * Create a wrapper around the controller to intercept text chunks for callbacks\n */\n const createCallbackController = (\n originalController: ReadableStreamDefaultController<UIMessageChunk>,\n ): ReadableStreamDefaultController<UIMessageChunk> => {\n return {\n get desiredSize() {\n return originalController.desiredSize;\n },\n close: () => originalController.close(),\n error: (e?: unknown) => originalController.error(e),\n enqueue: (chunk: UIMessageChunk) => {\n /**\n * Intercept text-delta chunks for callbacks\n */\n if (chunk.type === 'text-delta' && chunk.delta) {\n if (options?.onFinal) {\n textChunks.push(chunk.delta);\n }\n options?.onToken?.(chunk.delta);\n options?.onText?.(chunk.delta);\n }\n originalController.enqueue(chunk);\n },\n };\n };\n\n return new ReadableStream<UIMessageChunk>({\n async start(controller) {\n await options?.onStart?.();\n\n const wrappedController = createCallbackController(controller);\n if (sendStart) {\n controller.enqueue({ type: 'start' });\n }\n\n try {\n while (true) {\n const { done, value } = await iterator.next();\n if (done) break;\n\n /**\n * Detect stream type on first value\n */\n if (streamType === null) {\n if (Array.isArray(value)) {\n streamType = 'langgraph';\n } else if (isStreamEventsEvent(value)) {\n streamType = 'streamEvents';\n } else {\n streamType = 'model';\n }\n }\n\n /**\n * Process based on detected type\n */\n if (streamType === 'model') {\n processModelChunk(\n value as AIMessageChunk,\n modelState,\n wrappedController,\n );\n } else if (streamType === 'streamEvents') {\n processStreamEventsEvent(\n value as {\n event: string;\n data: Record<string, unknown> | null;\n run_id?: string;\n name?: string;\n },\n modelState,\n wrappedController,\n );\n } else {\n const eventArray = value as unknown[];\n const [, type, data] = parseLangGraphEvent(eventArray);\n\n if (type === 'values') {\n lastValuesData = data as TState;\n }\n\n processLangGraphEvent(\n eventArray,\n langGraphState,\n wrappedController,\n );\n }\n }\n\n /**\n * Finalize based on stream type\n */\n if (streamType === 'model' || streamType === 'streamEvents') {\n if (modelState.reasoningStarted) {\n controller.enqueue({\n type: 'reasoning-end',\n id: modelState.reasoningMessageId ?? modelState.messageId,\n });\n }\n if (modelState.textStarted) {\n /**\n * Use the same ID that was used for text-start\n */\n controller.enqueue({\n type: 'text-end',\n id: modelState.textMessageId ?? modelState.messageId,\n });\n }\n if (sendFinish) {\n controller.enqueue({ type: 'finish' });\n }\n } else if (streamType === 'langgraph') {\n /**\n * Close any open text/reasoning parts before finishing.\n * This handles streams without values events (e.g. streamMode: 'messages')\n * where the values handler never ran to emit *-end events.\n */\n for (const [id, seen] of langGraphState.messageSeen) {\n const providerMetadata = getLangGraphProviderMetadata(\n langGraphState.messageNamespaces.get(id),\n );\n if (seen.text) {\n controller.enqueue({\n type: 'text-end',\n id,\n ...(providerMetadata !== undefined && { providerMetadata }),\n });\n }\n if (seen.reasoning) {\n controller.enqueue({\n type: 'reasoning-end',\n id,\n ...(providerMetadata !== undefined && { providerMetadata }),\n });\n }\n }\n\n /**\n * Emit finish-step if a step was started\n */\n if (langGraphState.currentStepsByNamespace.size > 0) {\n controller.enqueue({ type: 'finish-step' });\n }\n if (sendFinish) {\n controller.enqueue({ type: 'finish' });\n }\n }\n\n /**\n * Call onFinal callback with aggregated text\n */\n await options?.onFinal?.(textChunks.join(''));\n await options?.onFinish?.(lastValuesData);\n } catch (error) {\n const errorObj =\n error instanceof Error ? error : new Error(String(error));\n\n await options?.onFinal?.(textChunks.join(''));\n\n if (isAbortError(error)) {\n await options?.onAbort?.();\n } else {\n await options?.onError?.(errorObj);\n }\n\n controller.enqueue({\n type: 'error',\n errorText: errorObj.message,\n });\n } finally {\n controller.close();\n }\n },\n });\n}\n","import {\n AIMessage,\n HumanMessage,\n ToolMessage,\n AIMessageChunk,\n type ContentBlock,\n type ToolCall,\n type BaseMessage,\n type BaseMessageChunk,\n type ToolCallChunk,\n} from '@langchain/core/messages';\nimport type {\n UIMessageChunk,\n ToolResultPart,\n AssistantContent,\n UserContent,\n ProviderMetadata,\n JSONValue,\n} from 'ai';\n\nimport type {\n LangGraphEventState,\n LangGraphMessageSeen,\n ReasoningContentBlock,\n ThinkingContentBlock,\n GPT5ReasoningOutput,\n ImageGenerationOutput,\n NormalizedCitation,\n} from './types';\n\n/**\n * Parses a LangGraph event tuple into [namespace, type, data].\n * Handles both 2-element [type, data] and 3-element [namespace, type, data] formats.\n *\n * @param event - The raw LangGraph event array.\n * @returns A tuple of [namespace, type, data].\n */\nexport function parseLangGraphEvent(\n event: unknown[],\n): [namespace: unknown | undefined, type: unknown, data: unknown] {\n return event.length === 3\n ? [event[0], event[1], event[2]]\n : [undefined, event[0], event[1]];\n}\n\nexport function getLangGraphProviderMetadata(\n namespace: string[] | undefined,\n): ProviderMetadata | undefined {\n return namespace === undefined\n ? undefined\n : {\n langchain: {\n namespace,\n },\n };\n}\n\nfunction addLangGraphNamespace(\n chunk: UIMessageChunk,\n namespace: string[] | undefined,\n): UIMessageChunk {\n if (namespace === undefined) {\n return chunk;\n }\n\n switch (chunk.type) {\n case 'text-start':\n case 'text-delta':\n case 'text-end':\n case 'reasoning-start':\n case 'reasoning-delta':\n case 'reasoning-end':\n case 'custom':\n case 'tool-input-start':\n case 'tool-input-available':\n case 'tool-input-error':\n case 'tool-approval-response':\n case 'tool-output-available':\n case 'tool-output-error':\n case 'source-url':\n case 'source-document':\n case 'file':\n case 'reasoning-file': {\n return {\n ...chunk,\n providerMetadata: {\n ...chunk.providerMetadata,\n langchain: {\n ...chunk.providerMetadata?.langchain,\n namespace,\n },\n },\n };\n }\n default:\n return chunk;\n }\n}\n\nfunction createLangGraphNamespaceController(\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n state: LangGraphEventState,\n eventNamespace: string[] | undefined,\n): ReadableStreamDefaultController<UIMessageChunk> {\n return {\n get desiredSize() {\n return controller.desiredSize;\n },\n close: () => controller.close(),\n error: reason => controller.error(reason),\n enqueue: chunk => {\n if (chunk === undefined) {\n return;\n }\n\n let messageNamespace: string[] | undefined;\n switch (chunk.type) {\n case 'text-start':\n case 'text-delta':\n case 'text-end':\n case 'reasoning-start':\n case 'reasoning-delta':\n case 'reasoning-end':\n messageNamespace = state.messageNamespaces.get(chunk.id);\n break;\n }\n\n controller.enqueue(\n addLangGraphNamespace(chunk, messageNamespace ?? eventNamespace),\n );\n },\n };\n}\n\n/**\n * Converts a ToolResultPart to a LangChain ToolMessage\n * @param block - The ToolResultPart to convert.\n * @returns The converted ToolMessage.\n */\nexport function convertToolResultPart(block: ToolResultPart): ToolMessage {\n const content = (() => {\n if (block.output.type === 'text' || block.output.type === 'error-text') {\n return block.output.value;\n }\n\n if (block.output.type === 'json' || block.output.type === 'error-json') {\n return JSON.stringify(block.output.value);\n }\n\n if (block.output.type === 'content') {\n return block.output.value\n .map(outputBlock => {\n if (outputBlock.type === 'text') {\n return outputBlock.text;\n }\n return '';\n })\n .join('');\n }\n\n return '';\n })();\n\n return new ToolMessage({\n tool_call_id: block.toolCallId,\n content,\n });\n}\n\n/**\n * Converts AssistantContent to LangChain AIMessage\n * @param content - The AssistantContent to convert.\n * @returns The converted AIMessage.\n */\nexport function convertAssistantContent(content: AssistantContent): AIMessage {\n if (typeof content === 'string') {\n return new AIMessage({ content });\n }\n\n const textParts: string[] = [];\n const toolCalls: Array<{\n id: string;\n name: string;\n args: Record<string, unknown>;\n }> = [];\n\n for (const part of content) {\n if (part.type === 'text') {\n textParts.push(part.text);\n } else if (part.type === 'tool-call') {\n toolCalls.push({\n id: part.toolCallId,\n name: part.toolName,\n args: part.input as Record<string, unknown>,\n });\n }\n }\n\n return new AIMessage({\n content: textParts.join(''),\n tool_calls: toolCalls.length > 0 ? toolCalls : undefined,\n });\n}\n\n/**\n * Helper to generate a default filename from mediaType\n */\nfunction getDefaultFilename(\n mediaType: string,\n prefix: string = 'file',\n): string {\n const fileExtension = mediaType.split('/')[1] || 'bin';\n return `${prefix}.${fileExtension}`;\n}\n\nfunction convertImageToContentBlock(\n data: string | Uint8Array | URL | ArrayBuffer,\n mediaType: string = 'image/png',\n): ContentBlock.Multimodal.Image {\n if (data instanceof URL) {\n if (data.protocol !== 'data:') {\n return { type: 'image', url: data.toString() };\n }\n\n data = data.toString();\n }\n\n if (typeof data === 'string') {\n if (data.startsWith('http://') || data.startsWith('https://')) {\n return { type: 'image', url: data };\n }\n\n if (data.startsWith('data:')) {\n const matches = data.match(/^data:([^;]+);base64,(.+)$/);\n if (matches) {\n return {\n type: 'image',\n data: matches[2],\n mimeType: matches[1],\n };\n }\n\n return { type: 'image', url: data };\n }\n\n return { type: 'image', data, mimeType: mediaType };\n }\n\n const bytes = data instanceof ArrayBuffer ? new Uint8Array(data) : data;\n return {\n type: 'image',\n data: btoa(String.fromCharCode(...bytes)),\n mimeType: mediaType,\n };\n}\n\n/**\n * Converts UserContent to LangChain HumanMessage\n * @param content - The UserContent to convert.\n * @returns The converted HumanMessage.\n */\nexport function convertUserContent(content: UserContent): HumanMessage {\n if (typeof content === 'string') {\n return new HumanMessage({ content });\n }\n\n const contentBlocks: ContentBlock.Standard[] = [];\n\n for (const part of content) {\n if (part.type === 'text') {\n contentBlocks.push({ type: 'text', text: part.text });\n } else if (part.type === 'image') {\n const imagePart = part as {\n type: 'image';\n image: string | Uint8Array | URL | ArrayBuffer;\n mediaType?: string;\n };\n\n if (\n imagePart.image instanceof URL ||\n typeof imagePart.image === 'string' ||\n imagePart.image instanceof Uint8Array ||\n imagePart.image instanceof ArrayBuffer\n ) {\n contentBlocks.push(\n convertImageToContentBlock(imagePart.image, imagePart.mediaType),\n );\n }\n } else if (part.type === 'file') {\n const rawFilePart = part as {\n type: 'file';\n data:\n | string\n | Uint8Array\n | URL\n | ArrayBuffer\n | { type: 'data'; data: string | Uint8Array | ArrayBuffer }\n | { type: 'url'; url: URL }\n | { type: 'reference'; reference: Record<string, string> }\n | { type: 'text'; text: string };\n mediaType: string;\n filename?: string;\n };\n\n // Normalize tagged data shape into the legacy bare value this code expects.\n const normalizedData: string | Uint8Array | URL | ArrayBuffer = (() => {\n const data = rawFilePart.data;\n if (\n typeof data === 'object' &&\n data !== null &&\n !(data instanceof URL) &&\n !(data instanceof Uint8Array) &&\n !(data instanceof ArrayBuffer) &&\n 'type' in data\n ) {\n switch (data.type) {\n case 'data':\n return data.data;\n case 'url':\n return data.url;\n case 'text':\n return data.text;\n default:\n return '';\n }\n }\n return data as string | Uint8Array | URL | ArrayBuffer;\n })();\n\n const filePart = {\n type: 'file' as const,\n data: normalizedData,\n mediaType: rawFilePart.mediaType,\n filename: rawFilePart.filename,\n };\n\n const isImage = filePart.mediaType?.startsWith('image/');\n\n if (isImage) {\n contentBlocks.push(\n convertImageToContentBlock(filePart.data, filePart.mediaType),\n );\n } else {\n // Handle non-image files using LangChain's ContentBlock format\n const filename =\n filePart.filename || getDefaultFilename(filePart.mediaType, 'file');\n\n if (filePart.data instanceof URL) {\n contentBlocks.push({\n type: 'file',\n url: filePart.data.toString(),\n mimeType: filePart.mediaType,\n filename,\n });\n } else if (typeof filePart.data === 'string') {\n if (\n filePart.data.startsWith('http://') ||\n filePart.data.startsWith('https://')\n ) {\n contentBlocks.push({\n type: 'file',\n url: filePart.data,\n mimeType: filePart.mediaType,\n filename,\n });\n } else if (filePart.data.startsWith('data:')) {\n const matches = filePart.data.match(/^data:([^;]+);base64,(.+)$/);\n if (matches) {\n contentBlocks.push({\n type: 'file',\n data: matches[2],\n mimeType: matches[1],\n filename,\n });\n } else {\n contentBlocks.push({\n type: 'file',\n url: filePart.data,\n mimeType: filePart.mediaType,\n filename,\n });\n }\n } else {\n contentBlocks.push({\n type: 'file',\n data: filePart.data,\n mimeType: filePart.mediaType,\n filename,\n });\n }\n } else if (\n filePart.data instanceof Uint8Array ||\n filePart.data instanceof ArrayBuffer\n ) {\n const bytes =\n filePart.data instanceof ArrayBuffer\n ? new Uint8Array(filePart.data)\n : filePart.data;\n const base64 = btoa(String.fromCharCode(...bytes));\n contentBlocks.push({\n type: 'file',\n data: base64,\n mimeType: filePart.mediaType,\n filename,\n });\n }\n }\n }\n }\n\n /**\n * If we only have text parts, join them as a simple string for efficiency\n */\n if (contentBlocks.every(block => block.type === 'text')) {\n return new HumanMessage({\n content: contentBlocks\n .map(block => (block as unknown as { text: string }).text)\n .join(''),\n });\n }\n\n return new HumanMessage({ contentBlocks });\n}\n\n/**\n * Helper to check if a content item is a ToolResultPart\n * @param item - The item to check.\n * @returns True if the item is a ToolResultPart, false otherwise.\n */\nexport function isToolResultPart(item: unknown): item is ToolResultPart {\n return (\n item != null &&\n typeof item === 'object' &&\n 'type' in item &&\n (item as { type: string }).type === 'tool-result'\n );\n}\n\n/**\n * Processes a model stream chunk and emits UI message chunks.\n * @param chunk - The AIMessageChunk to process.\n * @param state - The state of the model stream.\n * @param controller - The controller to use to emit the UI message chunks.\n */\nexport function processModelChunk(\n chunk: AIMessageChunk,\n state: {\n started: boolean;\n messageId: string;\n reasoningStarted?: boolean;\n textStarted?: boolean;\n /** Track the ID used for reasoning-start to ensure reasoning-end uses the same ID */\n reasoningMessageId?: string | null;\n /** Track the ID used for text-start to ensure text-end uses the same ID */\n textMessageId?: string | null;\n emittedImages?: Set<string>;\n emittedSourceIds?: Set<string>;\n },\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): void {\n /**\n * Initialize emittedImages set if not present\n */\n if (!state.emittedImages) {\n state.emittedImages = new Set<string>();\n }\n\n if (!state.emittedSourceIds) {\n state.emittedSourceIds = new Set<string>();\n }\n\n /**\n * Get the message ID from the chunk if available\n */\n if (chunk.id) {\n state.messageId = chunk.id;\n }\n\n /**\n * Handle image generation outputs from additional_kwargs.tool_outputs\n */\n const chunkObj = chunk as unknown as Record<string, unknown>;\n const additionalKwargs = chunkObj.additional_kwargs as\n | Record<string, unknown>\n | undefined;\n const imageOutputs = extractImageOutputs(additionalKwargs);\n\n for (const imageOutput of imageOutputs) {\n /**\n * Only emit if we have image data and haven't emitted this image yet\n */\n if (imageOutput.result && !state.emittedImages.has(imageOutput.id)) {\n state.emittedImages.add(imageOutput.id);\n\n /**\n * Emit as a file part using proper AI SDK multimodal format\n */\n const mediaType = `image/${imageOutput.output_format || 'png'}`;\n controller.enqueue({\n type: 'file',\n mediaType,\n url: `data:${mediaType};base64,${imageOutput.result}`,\n });\n state.started = true;\n }\n }\n\n /**\n * Handle reasoning content from contentBlocks or response_metadata.output\n * For direct model streams, we check both sources since there's no values event\n * that would cause duplication (unlike LangGraph streams)\n */\n const reasoning =\n extractReasoningFromContentBlocks(chunk) ||\n extractReasoningFromValuesMessage(chunk);\n if (reasoning) {\n if (!state.reasoningStarted) {\n // Track the ID used for reasoning-start to ensure subsequent chunks use the same ID\n state.reasoningMessageId = state.messageId;\n controller.enqueue({ type: 'reasoning-start', id: state.messageId });\n state.reasoningStarted = true;\n state.started = true;\n }\n controller.enqueue({\n type: 'reasoning-delta',\n delta: reasoning,\n id: state.reasoningMessageId ?? state.messageId,\n });\n }\n\n /**\n * Extract text content from AIMessageChunk\n */\n const text =\n typeof chunk.content === 'string'\n ? chunk.content\n : Array.isArray(chunk.content)\n ? chunk.content\n .filter(\n (c): c is { type: 'text'; text: string } =>\n typeof c === 'object' &&\n c !== null &&\n 'type' in c &&\n c.type === 'text',\n )\n .map(c => c.text)\n .join('')\n : '';\n\n if (text) {\n /**\n * If reasoning was streamed before text, close reasoning first\n */\n if (state.reasoningStarted && !state.textStarted) {\n controller.enqueue({\n type: 'reasoning-end',\n id: state.reasoningMessageId ?? state.messageId,\n });\n state.reasoningStarted = false;\n }\n\n if (!state.textStarted) {\n // Track the ID used for text-start to ensure subsequent chunks use the same ID\n state.textMessageId = state.messageId;\n controller.enqueue({ type: 'text-start', id: state.messageId });\n state.textStarted = true;\n state.started = true;\n }\n controller.enqueue({\n type: 'text-delta',\n delta: text,\n id: state.textMessageId ?? state.messageId,\n });\n }\n\n const citations = extractCitationsFromContentBlocks(chunk);\n if (citations.length > 0) {\n emitSourceChunks(\n citations,\n state.messageId,\n state.emittedSourceIds,\n controller,\n );\n }\n}\n\n/**\n * Checks if a message is a plain object (not a LangChain class instance).\n * LangChain class instances have a _getType method.\n *\n * @param msg - The message to check.\n * @returns True if the message is a plain object, false otherwise.\n */\nexport function isPlainMessageObject(msg: unknown): boolean {\n if (msg == null || typeof msg !== 'object') return false;\n /**\n * LangChain class instances have _getType method\n */\n return typeof (msg as { _getType?: unknown })._getType !== 'function';\n}\n\n/**\n * Extracts the actual message ID from a message.\n * Handles both class instances (msg.id) and serialized LangChain messages (msg.kwargs.id).\n *\n * @param msg - The message to extract the ID from.\n * @returns The message ID string, or undefined if not found.\n */\nexport function getMessageId(msg: unknown): string | undefined {\n if (msg == null || typeof msg !== 'object') return undefined;\n\n const msgObj = msg as Record<string, unknown>;\n\n /**\n * For class instances, id is directly on the object\n */\n if (typeof msgObj.id === 'string') {\n return msgObj.id;\n }\n\n /**\n * For serialized LangChain messages, id is in kwargs\n */\n if (\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ) {\n const kwargs = msgObj.kwargs as Record<string, unknown>;\n if (typeof kwargs.id === 'string') {\n return kwargs.id;\n }\n }\n}\n\n/**\n * Checks if a message is an AIMessageChunk class instance, including instances\n * created by a different LangChain module build.\n */\nfunction isAIMessageChunkInstance(msg: unknown): msg is AIMessageChunk {\n if (AIMessageChunk.isInstance(msg)) return true;\n if (msg == null || typeof msg !== 'object') return false;\n\n const message = msg as {\n _getType?: () => unknown;\n concat?: unknown;\n };\n\n return (\n typeof message._getType === 'function' &&\n typeof message.concat === 'function' &&\n message._getType() === 'ai'\n );\n}\n\n/**\n * Checks if a message is an AI message chunk (works for both class instances and plain objects).\n * For class instances, only AIMessageChunk is matched (not AIMessage).\n * For plain objects from RemoteGraph API, matches type === 'ai' (TypeScript langchain-core)\n * or type === 'AIMessageChunk' (Python langchain-core).\n * For serialized LangChain messages, matches type === 'constructor' with AIMessageChunk in id path.\n *\n * @param msg - The message to check.\n * @returns True if the message is an AI message chunk, false otherwise.\n */\nexport function isAIMessageChunk(\n msg: unknown,\n): msg is AIMessageChunk & { type?: string; content?: string } {\n /**\n * Actual AIMessageChunk class instance\n */\n if (isAIMessageChunkInstance(msg)) return true;\n /**\n * Plain object from RemoteGraph API (not a LangChain class instance)\n */\n if (isPlainMessageObject(msg)) {\n const messageRecord = msg as Record<string, unknown>;\n /**\n * Direct type from RemoteGraph format. TypeScript langchain-core emits\n * type === 'ai'; Python langchain-core emits type === 'AIMessageChunk'.\n */\n if (\n 'type' in messageRecord &&\n (messageRecord.type === 'ai' || messageRecord.type === 'AIMessageChunk')\n ) {\n return true;\n }\n /**\n * Serialized LangChain message format: { lc: 1, type: \"constructor\", id: [\"...\", \"AIMessageChunk\"], kwargs: {...} }\n */\n if (\n messageRecord.type === 'constructor' &&\n Array.isArray(messageRecord.id) &&\n (messageRecord.id.includes('AIMessageChunk') ||\n messageRecord.id.includes('AIMessage'))\n ) {\n return true;\n }\n }\n return false;\n}\n\n/**\n * Checks if a message is a Tool message (works for both class instances and plain objects).\n *\n * @param msg - The message to check.\n * @returns True if the message is a Tool message, false otherwise.\n */\nexport function isToolMessageType(\n msg: unknown,\n): msg is ToolMessage & { type?: string; tool_call_id?: string } {\n if (ToolMessage.isInstance(msg)) return true;\n /**\n * Plain object from RemoteGraph API (not a LangChain class instance)\n */\n if (isPlainMessageObject(msg)) {\n const messageRecord = msg as Record<string, unknown>;\n /**\n * Direct type === 'tool' (RemoteGraph format)\n */\n if ('type' in messageRecord && messageRecord.type === 'tool') return true;\n /**\n * Serialized LangChain message format\n */\n if (\n messageRecord.type === 'constructor' &&\n Array.isArray(messageRecord.id) &&\n messageRecord.id.includes('ToolMessage')\n ) {\n return true;\n }\n }\n return false;\n}\n\n/**\n * Gets text content from a message (works for both class instances and plain objects).\n *\n * @param msg - The message to get the text from.\n * @returns The text content of the message.\n */\nexport function getMessageText(msg: unknown): string {\n if (AIMessageChunk.isInstance(msg)) {\n return msg.text ?? '';\n }\n\n if (msg == null || typeof msg !== 'object') return '';\n\n const msgObj = msg as Record<string, unknown>;\n\n // For serialized LangChain messages, content is in kwargs\n const dataSource =\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n if ('content' in dataSource) {\n const content = dataSource.content;\n /**\n * Handle string content\n */\n if (typeof content === 'string') {\n return content;\n }\n /**\n * Handle array of content blocks (e.g., [{ type: 'text', text: 'The', index: 0 }])\n */\n if (Array.isArray(content)) {\n return content\n .filter(\n (block): block is { type: 'text'; text: string } =>\n block != null &&\n typeof block === 'object' &&\n block.type === 'text' &&\n typeof block.text === 'string',\n )\n .map(block => block.text)\n .join('');\n }\n return '';\n }\n return '';\n}\n\n/**\n * Checks if an object is a reasoning content block\n *\n * @param obj - The object to check.\n * @returns True if the object is a reasoning content block, false otherwise.\n */\nexport function isReasoningContentBlock(\n obj: unknown,\n): obj is ReasoningContentBlock {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: string }).type === 'reasoning' &&\n 'reasoning' in obj &&\n typeof (obj as { reasoning: unknown }).reasoning === 'string'\n );\n}\n\n/**\n * Checks if an object is a thinking content block (Anthropic-style)\n *\n * @param obj - The object to check.\n * @returns True if the object is a thinking content block, false otherwise.\n */\nexport function isThinkingContentBlock(\n obj: unknown,\n): obj is ThinkingContentBlock {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: string }).type === 'thinking' &&\n 'thinking' in obj &&\n typeof (obj as { thinking: unknown }).thinking === 'string'\n );\n}\n\n/**\n * Checks if an object is a GPT-5 reasoning output block\n */\nfunction isGPT5ReasoningOutput(obj: unknown): obj is GPT5ReasoningOutput {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: string }).type === 'reasoning' &&\n 'summary' in obj &&\n Array.isArray((obj as { summary: unknown }).summary)\n );\n}\n\n/**\n * Extracts the reasoning block ID from a message (GPT-5 format).\n * This ID is consistent across streaming and values events.\n * Handles both class instances and serialized LangChain message objects.\n *\n * @param msg - The message to extract the reasoning ID from.\n * @returns The reasoning block ID if found, undefined otherwise.\n */\nexport function extractReasoningId(msg: unknown): string | undefined {\n if (msg == null || typeof msg !== 'object') return undefined;\n\n // For serialized LangChain messages, the data is in kwargs\n const msgObj = msg as Record<string, unknown>;\n const kwargs =\n msgObj.kwargs && typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n // Check additional_kwargs.reasoning.id (GPT-5 streaming format)\n const additionalKwargs = (\n kwargs as { additional_kwargs?: { reasoning?: { id?: string } } }\n ).additional_kwargs;\n if (additionalKwargs?.reasoning?.id) {\n return additionalKwargs.reasoning.id;\n }\n\n // Check response_metadata.output for reasoning block ID (GPT-5 final format)\n const responseMetadata = (\n kwargs as { response_metadata?: { output?: unknown[] } }\n ).response_metadata;\n if (responseMetadata && Array.isArray(responseMetadata.output)) {\n for (const item of responseMetadata.output) {\n if (isGPT5ReasoningOutput(item)) {\n return item.id;\n }\n }\n }\n}\n\n/**\n * Extracts reasoning content from contentBlocks or additional_kwargs.reasoning.summary\n *\n * IMPORTANT: This function is designed for STREAMING chunks where content is delta-based.\n * It does NOT extract from response_metadata.output because that contains accumulated\n * content (not deltas) and would cause duplication during streaming.\n *\n * For non-streaming/values events, use extractReasoningFromValuesMessage instead.\n *\n * Handles both class instances and serialized LangChain message objects.\n *\n * @param msg - The message to extract reasoning from.\n * @returns The reasoning text if found, undefined otherwise.\n */\nexport function extractReasoningFromContentBlocks(\n msg: unknown,\n): string | undefined {\n if (msg == null || typeof msg !== 'object') return undefined;\n\n // For serialized LangChain messages, the data is in kwargs\n const msgObj = msg as Record<string, unknown>;\n const kwargs =\n msgObj.kwargs && typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n // Check contentBlocks (Anthropic-style) - highest priority\n const contentBlocks = (kwargs as { contentBlocks?: unknown[] }).contentBlocks;\n if (Array.isArray(contentBlocks)) {\n const reasoningParts: string[] = [];\n for (const block of contentBlocks) {\n if (isReasoningContentBlock(block)) {\n reasoningParts.push(block.reasoning);\n } else if (isThinkingContentBlock(block)) {\n reasoningParts.push(block.thinking);\n }\n }\n if (reasoningParts.length > 0) {\n return reasoningParts.join('');\n }\n }\n\n // Check additional_kwargs.reasoning.summary (GPT-5 streaming format)\n // This contains DELTA content during streaming, not accumulated content\n // Format can be either { type: \"summary_text\", text: \"...\" } or just { text: \"...\" }\n const additionalKwargs = (\n kwargs as { additional_kwargs?: { reasoning?: { summary?: unknown[] } } }\n ).additional_kwargs;\n if (\n additionalKwargs?.reasoning &&\n Array.isArray(additionalKwargs.reasoning.summary)\n ) {\n const reasoningParts: string[] = [];\n for (const summaryItem of additionalKwargs.reasoning.summary) {\n if (\n typeof summaryItem === 'object' &&\n summaryItem !== null &&\n 'text' in summaryItem &&\n typeof (summaryItem as { text: unknown }).text === 'string'\n ) {\n reasoningParts.push((summaryItem as { text: string }).text);\n }\n }\n if (reasoningParts.length > 0) {\n return reasoningParts.join('');\n }\n }\n}\n\n/**\n * Extracts reasoning content from a values event message.\n * This checks response_metadata.output which contains the full accumulated reasoning.\n *\n * @param msg - The message to extract reasoning from.\n * @returns The reasoning text if found, undefined otherwise.\n */\nexport function extractReasoningFromValuesMessage(\n msg: unknown,\n): string | undefined {\n if (msg == null || typeof msg !== 'object') return undefined;\n\n // For serialized LangChain messages, the data is in kwargs\n const msgObj = msg as Record<string, unknown>;\n const kwargs =\n msgObj.kwargs && typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n // Check response_metadata.output (GPT-5 final style) - for values events\n const responseMetadata = (\n kwargs as { response_metadata?: { output?: unknown[] } }\n ).response_metadata;\n if (responseMetadata && Array.isArray(responseMetadata.output)) {\n const reasoningParts: string[] = [];\n for (const item of responseMetadata.output) {\n if (isGPT5ReasoningOutput(item)) {\n // Extract text from summary array - handles both { type: \"summary_text\", text } and { text } formats\n for (const summaryItem of item.summary) {\n if (typeof summaryItem === 'object' && summaryItem !== null) {\n const text = (summaryItem as { text?: string }).text;\n if (typeof text === 'string' && text) {\n reasoningParts.push(text);\n }\n }\n }\n }\n }\n if (reasoningParts.length > 0) {\n return reasoningParts.join('');\n }\n }\n\n // Also check additional_kwargs.reasoning.summary as fallback\n const additionalKwargs = (\n kwargs as { additional_kwargs?: { reasoning?: { summary?: unknown[] } } }\n ).additional_kwargs;\n if (\n additionalKwargs?.reasoning &&\n Array.isArray(additionalKwargs.reasoning.summary)\n ) {\n const reasoningParts: string[] = [];\n for (const summaryItem of additionalKwargs.reasoning.summary) {\n if (\n typeof summaryItem === 'object' &&\n summaryItem !== null &&\n 'text' in summaryItem &&\n typeof (summaryItem as { text: unknown }).text === 'string'\n ) {\n reasoningParts.push((summaryItem as { text: string }).text);\n }\n }\n if (reasoningParts.length > 0) {\n return reasoningParts.join('');\n }\n }\n}\n\nexport function isCitationContentBlock(\n obj: unknown,\n): obj is ContentBlock.Citation {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: unknown }).type === 'citation'\n );\n}\n\n/**\n * LangChain Core standardizes citations as `{ type: 'citation', ... }` entries in\n * the `annotations` array of a text content block. The text extractors elsewhere\n * in this file only read the `text` field, so without this the citations would be\n * dropped instead of surfaced as AI SDK source parts.\n *\n * Handles both class instances and serialized LangChain message objects.\n */\nexport function extractCitationsFromContentBlocks(\n msg: unknown,\n): NormalizedCitation[] {\n if (msg == null || typeof msg !== 'object') return [];\n\n const msgObj = msg as Record<string, unknown>;\n const kwargs =\n msgObj.kwargs && typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n // `contentBlocks` is the normalized view derived from `content`; reading both\n // would double-count annotations, so prefer it and only fall back to `content`.\n const contentBlocks = (kwargs as { contentBlocks?: unknown }).contentBlocks;\n const content = (kwargs as { content?: unknown }).content;\n const blockSources: unknown[] = Array.isArray(contentBlocks)\n ? contentBlocks\n : Array.isArray(content)\n ? content\n : [];\n\n const citations: NormalizedCitation[] = [];\n\n for (const block of blockSources) {\n if (block == null || typeof block !== 'object') continue;\n\n const annotations = (block as { annotations?: unknown }).annotations;\n if (!Array.isArray(annotations)) continue;\n\n for (const annotation of annotations) {\n if (!isCitationContentBlock(annotation)) continue;\n\n citations.push({\n url: annotation.url,\n title: annotation.title,\n source: annotation.source,\n citedText: annotation.citedText,\n startIndex: annotation.startIndex,\n endIndex: annotation.endIndex,\n });\n }\n }\n\n return citations;\n}\n\nfunction buildSourceProviderMetadata(\n citation: NormalizedCitation,\n): ProviderMetadata | undefined {\n const langchain: Record<string, JSONValue> = {};\n\n if (typeof citation.citedText === 'string') {\n langchain.citedText = citation.citedText;\n }\n if (typeof citation.startIndex === 'number') {\n langchain.startIndex = citation.startIndex;\n }\n if (typeof citation.endIndex === 'number') {\n langchain.endIndex = citation.endIndex;\n }\n if (typeof citation.source === 'string') {\n langchain.source = citation.source;\n }\n\n if (Object.keys(langchain).length === 0) {\n return undefined;\n }\n\n return { langchain };\n}\n\n/**\n * Emits AI SDK source chunks (`source-url` / `source-document`) for the given\n * citations.\n *\n * Citations with a `url` become `source-url` parts keyed by that url; the rest\n * become `source-document` parts. Citation metadata that the source parts cannot\n * represent natively (`citedText`, `startIndex`, `endIndex`, `source`) is preserved\n * under `providerMetadata.langchain`.\n *\n * `emittedSourceIds` dedupes across the LangGraph messages and values events, which\n * can each surface the same citation. URL-less citations are keyed by their content\n * rather than position, so a differing citation subset/order between those two events\n * does not cause an id collision.\n */\nexport function emitSourceChunks(\n citations: NormalizedCitation[],\n messageId: string,\n emittedSourceIds: Set<string>,\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): void {\n for (const citation of citations) {\n if (citation.url) {\n if (emittedSourceIds.has(citation.url)) continue;\n emittedSourceIds.add(citation.url);\n\n const providerMetadata = buildSourceProviderMetadata(citation);\n controller.enqueue({\n type: 'source-url',\n sourceId: citation.url,\n url: citation.url,\n ...(citation.title ? { title: citation.title } : {}),\n ...(providerMetadata ? { providerMetadata } : {}),\n });\n continue;\n }\n\n // A citation with no url and no human-readable label carries no information a\n // UI could render, so skip it rather than emit a placeholder source.\n const title = citation.title ?? citation.source;\n if (!title) continue;\n\n const sourceId = `${messageId}:${title}:${citation.citedText ?? ''}:${citation.startIndex ?? ''}:${citation.endIndex ?? ''}`;\n if (emittedSourceIds.has(sourceId)) continue;\n emittedSourceIds.add(sourceId);\n\n const providerMetadata = buildSourceProviderMetadata(citation);\n controller.enqueue({\n type: 'source-document',\n sourceId,\n mediaType: 'text/plain',\n title,\n ...(providerMetadata ? { providerMetadata } : {}),\n });\n }\n}\n\n/**\n * Checks if an object is an image generation output\n *\n * @param obj - The object to check.\n * @returns True if the object is an image generation output, false otherwise.\n */\nexport function isImageGenerationOutput(\n obj: unknown,\n): obj is ImageGenerationOutput {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: string }).type === 'image_generation_call'\n );\n}\n\n/**\n * Extracts image generation outputs from `additional_kwargs`\n *\n * @param additionalKwargs - The additional kwargs to extract the image generation outputs from.\n * @returns The image generation outputs.\n */\nexport function extractImageOutputs(\n additionalKwargs: Record<string, unknown> | undefined,\n): ImageGenerationOutput[] {\n if (!additionalKwargs) return [];\n\n const toolOutputs = additionalKwargs.tool_outputs;\n if (!Array.isArray(toolOutputs)) return [];\n\n return toolOutputs.filter(isImageGenerationOutput);\n}\n\nfunction formatToolError(error: unknown): string {\n if (error instanceof Error) return error.message;\n if (typeof error === 'string') return error;\n\n try {\n const serialized = JSON.stringify(error);\n return serialized ?? String(error);\n } catch {\n return String(error);\n }\n}\n\n/**\n * Returns per-message bookkeeping, creating it on first use.\n * Map keys keep remote-controlled message IDs like \"__proto__\" from touching Object.prototype.\n */\nfunction getOrCreateMessageSeen(\n messageSeen: LangGraphEventState['messageSeen'],\n msgId: string,\n): LangGraphMessageSeen {\n let seen = messageSeen.get(msgId);\n if (!seen) {\n seen = {};\n messageSeen.set(msgId, seen);\n }\n return seen;\n}\n\n/**\n * Returns the per-index tool call metadata for a message, creating it on first use.\n * Later streamed chunks use this to recover tool call IDs/names from earlier chunks.\n */\nfunction getOrCreateToolCallInfoByIndex(\n toolCallInfoByIndex: LangGraphEventState['toolCallInfoByIndex'],\n msgId: string,\n): Map<number, { id: string; name: string }> {\n let toolCallInfo = toolCallInfoByIndex.get(msgId);\n if (!toolCallInfo) {\n toolCallInfo = new Map();\n toolCallInfoByIndex.set(msgId, toolCallInfo);\n }\n return toolCallInfo;\n}\n\n/**\n * Normalizes legacy tuples without a namespace and explicit empty root\n * namespaces to the same key.\n */\nfunction getLangGraphNamespaceKey(namespace: string[] | undefined): string {\n return JSON.stringify(namespace ?? []);\n}\n\nfunction getOrCreateNamespaceSet(\n setsByNamespace: Map<string, Set<string>>,\n namespace: string,\n): Set<string> {\n let values = setsByNamespace.get(namespace);\n if (!values) {\n values = new Set();\n setsByNamespace.set(namespace, values);\n }\n return values;\n}\n\nfunction hasEmittedToolCallInCurrentStep(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): boolean {\n return !state.currentStepsByNamespace.has(namespace)\n ? state.emittedToolCalls.has(toolCallId)\n : state.emittedToolCallsInCurrentStepByNamespace\n .get(namespace)\n ?.has(toolCallId) === true;\n}\n\nfunction markToolCallEmitted(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): void {\n state.emittedToolCalls.add(toolCallId);\n if (state.currentStepsByNamespace.has(namespace)) {\n getOrCreateNamespaceSet(\n state.emittedToolCallsInCurrentStepByNamespace,\n namespace,\n ).add(toolCallId);\n }\n}\n\nfunction hasEmittedToolInputInCurrentStep(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): boolean {\n return !state.currentStepsByNamespace.has(namespace)\n ? state.emittedToolInputs.has(toolCallId)\n : state.emittedToolInputsInCurrentStepByNamespace\n .get(namespace)\n ?.has(toolCallId) === true;\n}\n\nfunction markToolInputEmitted(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): void {\n state.emittedToolInputs.add(toolCallId);\n if (state.currentStepsByNamespace.has(namespace)) {\n getOrCreateNamespaceSet(\n state.emittedToolInputsInCurrentStepByNamespace,\n namespace,\n ).add(toolCallId);\n }\n}\n\nfunction hasEmittedToolOutputInCurrentStep(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): boolean {\n return !state.currentStepsByNamespace.has(namespace)\n ? state.emittedToolOutputCallIds.has(toolCallId)\n : state.emittedToolOutputsInCurrentStepByNamespace\n .get(namespace)\n ?.has(toolCallId) === true;\n}\n\nfunction markToolOutputEmitted(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): void {\n state.emittedToolOutputCallIds.add(toolCallId);\n if (state.currentStepsByNamespace.has(namespace)) {\n getOrCreateNamespaceSet(\n state.emittedToolOutputsInCurrentStepByNamespace,\n namespace,\n ).add(toolCallId);\n }\n}\n\nfunction findMessageCurrentStepNamespace(\n state: LangGraphEventState,\n messageId: string,\n): string | undefined {\n for (const [\n namespace,\n messageIds,\n ] of state.messageIdsInCurrentStepByNamespace) {\n if (messageIds.has(messageId)) {\n return namespace;\n }\n }\n}\n\n/**\n * Ends and clears message state for an advancing namespace. Returns whether\n * another namespace still has active text or reasoning that would be\n * invalidated by a global finish-step chunk.\n */\nfunction closeStepNamespaceMessages(\n state: LangGraphEventState,\n stepNamespace: string,\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): boolean {\n let hasConcurrentMessageParts = false;\n\n for (const [id, seen] of state.messageSeen) {\n const messageNamespace = getLangGraphNamespaceKey(\n state.messageNamespaces.get(id),\n );\n\n if (messageNamespace !== stepNamespace) {\n if (seen.text || seen.reasoning) {\n hasConcurrentMessageParts = true;\n }\n continue;\n }\n\n if (seen.text) {\n controller.enqueue({ type: 'text-end', id });\n }\n if (seen.reasoning) {\n controller.enqueue({ type: 'reasoning-end', id });\n }\n state.messageSeen.delete(id);\n state.messageNamespaces.delete(id);\n state.messageConcat.delete(id);\n state.messageReasoningIds.delete(id);\n }\n\n return hasConcurrentMessageParts;\n}\n\n/**\n * Processes a LangGraph event and emits UI message chunks.\n *\n * @param event - The event to process.\n * @param state - The state of the LangGraph event.\n * @param controller - The controller to use to emit the UI message chunks.\n */\nexport function processLangGraphEvent(\n event: unknown[],\n state: LangGraphEventState,\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): void {\n const {\n messageSeen,\n messageConcat,\n emittedToolCalls,\n emittedImages,\n emittedReasoningIds,\n messageReasoningIds,\n toolCallInfoByIndex,\n emittedToolCallsByKey,\n } = state;\n const [rawNamespace, type, data] = parseLangGraphEvent(event);\n const namespace =\n Array.isArray(rawNamespace) &&\n rawNamespace.every(segment => typeof segment === 'string')\n ? rawNamespace\n : undefined;\n const eventNamespace = getLangGraphNamespaceKey(namespace);\n controller = createLangGraphNamespaceController(controller, state, namespace);\n\n switch (type) {\n case 'custom': {\n /**\n * Extract custom event type from the data's 'type' field if present.\n * This allows users to emit custom events like:\n * writer({ type: 'progress', value: 50 }) -> { type: 'data-progress', data: {...} }\n * writer({ type: 'status', message: '...' }) -> { type: 'data-status', data: {...} }\n * writer({ key: 'value' }) -> { type: 'data-custom', data: {...} } (fallback)\n *\n * The 'id' field can be used to make parts persistent and updateable.\n * Parts with an 'id' are NOT transient (added to message.parts).\n * Parts without an 'id' are transient (only passed to onData callback).\n */\n let customTypeName = 'custom';\n let partId: string | undefined;\n\n if (data != null && typeof data === 'object' && !Array.isArray(data)) {\n const dataObj = data as Record<string, unknown>;\n if (typeof dataObj.type === 'string' && dataObj.type) {\n customTypeName = dataObj.type;\n }\n if (typeof dataObj.id === 'string' && dataObj.id) {\n partId = dataObj.id;\n }\n }\n\n controller.enqueue({\n type: `data-${customTypeName}` as `data-${string}`,\n id: partId,\n transient: partId == null,\n data,\n });\n break;\n }\n\n case 'messages': {\n const [rawMsg, metadata] = data as [\n BaseMessageChunk | BaseMessage | undefined,\n Record<string, unknown> | undefined,\n ];\n\n const msg = rawMsg;\n const msgId = getMessageId(msg);\n\n if (!msgId) return;\n\n if (namespace !== undefined) {\n state.messageNamespaces.set(msgId, namespace);\n }\n\n /**\n * Each namespace has an independent LangGraph step counter. Advancing a\n * namespace starts a new reducer scope so provider-scoped tool call IDs\n * can be reused in that namespace. A finish-step chunk clears every\n * active UI text/reasoning part, so omit it when another namespace is\n * still active.\n */\n const langgraphStep =\n typeof metadata?.langgraph_step === 'number'\n ? metadata.langgraph_step\n : null;\n if (langgraphStep !== null) {\n const currentStep =\n state.currentStepsByNamespace.get(eventNamespace) ?? null;\n if (currentStep === null) {\n if (state.currentStepsByNamespace.size === 0) {\n controller.enqueue({ type: 'start-step' });\n }\n state.currentStepsByNamespace.set(eventNamespace, langgraphStep);\n state.messageIdsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolCallsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolInputsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolOutputsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n } else if (langgraphStep !== currentStep) {\n const hasConcurrentMessageParts = closeStepNamespaceMessages(\n state,\n eventNamespace,\n controller,\n );\n if (!hasConcurrentMessageParts) {\n controller.enqueue({ type: 'finish-step' });\n }\n\n /**\n * A concurrent namespace prevents finish-step because it would close\n * that namespace's active text/reasoning parts. Still emit start-step\n * so tool calls in the advancing namespace have a distinct reducer\n * scope while the concurrent message lifecycle remains active.\n */\n controller.enqueue({ type: 'start-step' });\n state.currentStepsByNamespace.set(eventNamespace, langgraphStep);\n state.messageIdsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolCallsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolInputsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolOutputsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n }\n }\n if (state.currentStepsByNamespace.has(eventNamespace)) {\n getOrCreateNamespaceSet(\n state.messageIdsInCurrentStepByNamespace,\n eventNamespace,\n ).add(msgId);\n }\n\n /**\n * Accumulate message chunks for later reference\n * Note: Only works for actual class instances, not serialized messages\n */\n if (isAIMessageChunkInstance(msg)) {\n const existingMessage = messageConcat.get(msgId);\n if (existingMessage) {\n messageConcat.set(\n msgId,\n existingMessage.concat(msg) as AIMessageChunk,\n );\n } else {\n messageConcat.set(msgId, msg);\n }\n }\n\n if (isAIMessageChunk(msg)) {\n const concatChunk = messageConcat.get(msgId);\n\n /**\n * Handle image generation outputs from additional_kwargs.tool_outputs\n * Handle both direct properties and serialized messages (kwargs)\n */\n const msgObj = msg as unknown as Record<string, unknown>;\n const dataSource =\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n const additionalKwargs = dataSource.additional_kwargs as\n | Record<string, unknown>\n | undefined;\n const imageOutputs = extractImageOutputs(additionalKwargs);\n\n for (const imageOutput of imageOutputs) {\n /**\n * Only emit if we have image data and haven't emitted this image yet\n */\n if (imageOutput.result && !emittedImages.has(imageOutput.id)) {\n emittedImages.add(imageOutput.id);\n\n /**\n * Emit as a file part using proper AI SDK multimodal format\n */\n const mediaType = `image/${imageOutput.output_format || 'png'}`;\n controller.enqueue({\n type: 'file',\n mediaType,\n url: `data:${mediaType};base64,${imageOutput.result}`,\n });\n }\n }\n\n /**\n * Handle tool call chunks for streaming tool calls\n * Access from dataSource to handle both direct and serialized messages\n *\n * Tool call chunks are streamed as follows:\n * 1. First chunk: has name, id, but often empty args\n * 2. Subsequent chunks: have args but NO id or name\n *\n * We store tool call info by index when we first see it, then look it up\n * for subsequent chunks that don't include the id.\n */\n const toolCallChunks = dataSource.tool_call_chunks as\n | ToolCallChunk[]\n | undefined;\n if (toolCallChunks?.length) {\n for (const toolCallChunk of toolCallChunks) {\n const toolCallIndex = toolCallChunk.index ?? 0;\n\n /**\n * If this chunk has an id, store it for future lookups by index\n */\n if (toolCallChunk.id) {\n getOrCreateToolCallInfoByIndex(toolCallInfoByIndex, msgId).set(\n toolCallIndex,\n {\n id: toolCallChunk.id,\n name:\n toolCallChunk.name ||\n concatChunk?.tool_call_chunks?.[toolCallIndex]?.name ||\n 'unknown',\n },\n );\n }\n\n /**\n * Get the tool call ID from the chunk, stored info, or accumulated chunks\n */\n const storedToolCallInfo = toolCallInfoByIndex\n .get(msgId)\n ?.get(toolCallIndex);\n const toolCallId =\n toolCallChunk.id ||\n storedToolCallInfo?.id ||\n concatChunk?.tool_call_chunks?.[toolCallIndex]?.id;\n\n /**\n * Skip if we don't have a proper tool call ID - we'll handle it in values\n */\n if (!toolCallId) {\n continue;\n }\n\n const toolName =\n toolCallChunk.name ||\n storedToolCallInfo?.name ||\n concatChunk?.tool_call_chunks?.[toolCallIndex]?.name ||\n 'unknown';\n\n /**\n * Emit tool-input-start when we first see this tool call\n * (even if args is empty - the first chunk often has empty args)\n * Set dynamic: true to enable HITL approval requests\n */\n const seen = messageSeen.get(msgId);\n if (!seen?.tool?.has(toolCallId)) {\n const updatedSeen = getOrCreateMessageSeen(messageSeen, msgId);\n updatedSeen.tool ??= new Set();\n updatedSeen.tool.add(toolCallId);\n\n if (\n !hasEmittedToolCallInCurrentStep(\n state,\n toolCallId,\n eventNamespace,\n )\n ) {\n markToolCallEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId: toolCallId,\n toolName: toolName,\n dynamic: true,\n });\n }\n }\n\n /**\n * Only emit tool-input-delta when args is non-empty\n */\n if (toolCallChunk.args) {\n controller.enqueue({\n type: 'tool-input-delta',\n toolCallId: toolCallId,\n inputTextDelta: toolCallChunk.args,\n });\n }\n }\n\n return;\n }\n\n /**\n * Handle reasoning content from contentBlocks\n * Streaming chunks contain DELTA text (not accumulated), so emit directly.\n * Use reasoning block ID for deduplication as it's consistent across streaming and values events.\n *\n * Important: Early chunks may have reasoning ID but no content, later chunks may\n * have content but no reasoning ID. We capture the ID when first seen and reuse it.\n * We also immediately add to emittedReasoningIds to prevent values events from\n * emitting the same reasoning (values events can arrive between streaming chunks).\n */\n // Capture reasoning ID when we first see it (even if no content yet)\n const chunkReasoningId = extractReasoningId(msg);\n if (chunkReasoningId) {\n if (!messageReasoningIds.has(msgId)) {\n messageReasoningIds.set(msgId, chunkReasoningId);\n }\n // Immediately mark as emitted to prevent values from duplicating\n // This must happen as soon as we see the ID, before content arrives\n emittedReasoningIds.add(chunkReasoningId);\n }\n\n const reasoning = extractReasoningFromContentBlocks(msg);\n if (reasoning) {\n // Use stored reasoning ID, or current chunk's ID, or fall back to message ID\n const reasoningId =\n messageReasoningIds.get(msgId) ?? chunkReasoningId ?? msgId;\n\n const seen = messageSeen.get(msgId);\n if (!seen?.reasoning) {\n controller.enqueue({ type: 'reasoning-start', id: msgId });\n getOrCreateMessageSeen(messageSeen, msgId).reasoning = true;\n }\n\n // Streaming chunks have delta text, emit directly without slicing\n controller.enqueue({\n type: 'reasoning-delta',\n delta: reasoning,\n id: msgId,\n });\n // Also ensure the reasoning ID is marked (handles case where ID wasn't in first chunk)\n emittedReasoningIds.add(reasoningId);\n }\n\n /**\n * Handle text content\n */\n const text = getMessageText(msg);\n if (text) {\n const seen = messageSeen.get(msgId);\n if (seen?.reasoning && !seen.text) {\n controller.enqueue({ type: 'reasoning-end', id: msgId });\n seen.reasoning = false;\n }\n\n if (!seen?.text) {\n controller.enqueue({ type: 'text-start', id: msgId });\n getOrCreateMessageSeen(messageSeen, msgId).text = true;\n }\n\n controller.enqueue({\n type: 'text-delta',\n delta: text,\n id: msgId,\n });\n }\n\n const citations = extractCitationsFromContentBlocks(msg);\n if (citations.length > 0) {\n emitSourceChunks(\n citations,\n msgId,\n state.emittedSourceIds,\n controller,\n );\n }\n } else if (isToolMessageType(msg)) {\n // Handle both direct properties and serialized messages (kwargs)\n const msgObj = msg as unknown as Record<string, unknown>;\n const dataSource =\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n const toolCallId = dataSource.tool_call_id as string | undefined;\n const status = dataSource.status as string | undefined;\n\n if (toolCallId) {\n state.emittedToolOutputMessageIds.add(msgId);\n markToolOutputEmitted(state, toolCallId, eventNamespace);\n if (status === 'error') {\n // Tool execution failed\n controller.enqueue({\n type: 'tool-output-error',\n toolCallId,\n errorText:\n typeof dataSource.content === 'string'\n ? dataSource.content\n : 'Tool execution failed',\n });\n } else {\n // Tool execution succeeded\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId,\n output: dataSource.content,\n });\n }\n }\n }\n\n return;\n }\n\n case 'tools': {\n if (data == null || typeof data !== 'object' || Array.isArray(data)) {\n return;\n }\n\n const payload = data as {\n event?: unknown;\n name?: unknown;\n input?: unknown;\n data?: unknown;\n output?: unknown;\n error?: unknown;\n toolCallId?: unknown;\n };\n const toolCallId =\n typeof payload.toolCallId === 'string' ? payload.toolCallId : undefined;\n const toolName =\n typeof payload.name === 'string' ? payload.name : 'unknown';\n\n if (!toolCallId) return;\n\n const ensureToolInputLifecycle = ({\n allowPreviousStep,\n }: {\n allowPreviousStep: boolean;\n }) => {\n if (\n !hasEmittedToolCallInCurrentStep(state, toolCallId, eventNamespace)\n ) {\n if (allowPreviousStep && emittedToolCalls.has(toolCallId)) {\n return;\n }\n\n markToolCallEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId,\n toolName,\n dynamic: true,\n });\n }\n\n if (\n !hasEmittedToolInputInCurrentStep(state, toolCallId, eventNamespace)\n ) {\n markToolInputEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-input-available',\n toolCallId,\n toolName,\n input: payload.input,\n dynamic: true,\n });\n }\n };\n\n switch (payload.event) {\n case 'on_tool_start': {\n const toolCallKey = `${toolName}:${JSON.stringify(payload.input)}`;\n emittedToolCallsByKey.set(toolCallKey, toolCallId);\n\n ensureToolInputLifecycle({ allowPreviousStep: false });\n break;\n }\n\n case 'on_tool_event': {\n ensureToolInputLifecycle({ allowPreviousStep: true });\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId,\n output: payload.data,\n preliminary: true,\n });\n break;\n }\n\n case 'on_tool_end': {\n ensureToolInputLifecycle({ allowPreviousStep: true });\n markToolOutputEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId,\n output: payload.output,\n });\n break;\n }\n\n case 'on_tool_error': {\n ensureToolInputLifecycle({ allowPreviousStep: true });\n markToolOutputEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-output-error',\n toolCallId,\n errorText: formatToolError(payload.error),\n });\n break;\n }\n }\n\n return;\n }\n\n case 'values': {\n /**\n * Finalize all pending message chunks\n */\n for (const [id, seen] of messageSeen) {\n const messageNamespace = getLangGraphNamespaceKey(\n state.messageNamespaces.get(id),\n );\n if (seen.text) controller.enqueue({ type: 'text-end', id });\n if (seen.tool) {\n for (const toolCallId of seen.tool) {\n const concatMsg = messageConcat.get(id);\n const toolCall = concatMsg?.tool_calls?.find(\n call => call.id === toolCallId,\n );\n\n if (toolCall) {\n markToolCallEmitted(state, toolCallId, messageNamespace);\n // Store mapping for HITL interrupt lookup\n const toolCallKey = `${toolCall.name}:${JSON.stringify(toolCall.args)}`;\n emittedToolCallsByKey.set(toolCallKey, toolCallId);\n if (\n !hasEmittedToolInputInCurrentStep(\n state,\n toolCallId,\n messageNamespace,\n )\n ) {\n markToolInputEmitted(state, toolCallId, messageNamespace);\n controller.enqueue({\n type: 'tool-input-available',\n toolCallId,\n toolName: toolCall.name,\n input: toolCall.args,\n dynamic: true,\n });\n }\n }\n }\n }\n\n if (seen.reasoning) {\n controller.enqueue({ type: 'reasoning-end', id });\n }\n\n messageSeen.delete(id);\n state.messageNamespaces.delete(id);\n messageConcat.delete(id);\n messageReasoningIds.delete(id);\n }\n\n /**\n * Also check for tool calls in the final state that weren't streamed\n * This handles cases where tool calls appear directly in values without being in messages events\n */\n if (data != null && typeof data === 'object' && 'messages' in data) {\n const messages = (data as { messages?: unknown[] }).messages;\n if (Array.isArray(messages)) {\n /**\n * First pass: Collect all tool call IDs that have been responded to by\n * ToolMessages. Calls followed by another non-tool message are historical,\n * while trailing ToolMessages can be the only evidence of a completed call\n * when the node is tagged with `nostream`.\n */\n const completedToolCallIds = new Set<string>();\n const trailingToolMessages = new Map<\n string,\n {\n data: Record<string, unknown>;\n outputId: string;\n }\n >();\n let trailingToolMessageStart = messages.length;\n while (\n trailingToolMessageStart > 0 &&\n isToolMessageType(messages[trailingToolMessageStart - 1])\n ) {\n trailingToolMessageStart--;\n }\n\n for (const [index, msg] of messages.entries()) {\n if (!msg || typeof msg !== 'object') continue;\n\n if (isToolMessageType(msg)) {\n // Handle both direct properties and serialized messages (kwargs)\n const msgObj = msg as unknown as Record<string, unknown>;\n const dataSource =\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n const toolCallId = dataSource.tool_call_id as string | undefined;\n if (toolCallId) {\n completedToolCallIds.add(toolCallId);\n if (index >= trailingToolMessageStart) {\n trailingToolMessages.set(toolCallId, {\n data: dataSource,\n outputId: getMessageId(msg) ?? `${toolCallId}:${index}`,\n });\n }\n }\n }\n }\n\n /**\n * Second pass: Process messages and emit tool events for new tool calls,\n * including calls completed by trailing ToolMessages that were not streamed.\n */\n for (const msg of messages) {\n if (!msg || typeof msg !== 'object') continue;\n\n // Use getMessageId to handle both class instances and serialized messages\n const msgId = getMessageId(msg);\n if (!msgId) continue;\n\n /**\n * Check if this is an AI message with tool calls\n */\n let toolCalls: ToolCall[] | undefined;\n\n /**\n * For class instances\n */\n if (AIMessageChunk.isInstance(msg) || AIMessage.isInstance(msg)) {\n toolCalls = msg.tool_calls;\n } else if (isPlainMessageObject(msg)) {\n /**\n * For plain objects from RemoteGraph API or serialized LangChain messages\n */\n const messageRecord = msg as Record<string, unknown>;\n\n /**\n * Determine the data source (handle both direct and serialized formats)\n */\n const isSerializedFormat =\n messageRecord.type === 'constructor' &&\n Array.isArray(messageRecord.id) &&\n ((messageRecord.id as string[]).includes('AIMessageChunk') ||\n (messageRecord.id as string[]).includes('AIMessage'));\n const dataSource = isSerializedFormat\n ? (messageRecord.kwargs as Record<string, unknown>)\n : messageRecord;\n\n if (\n messageRecord.type === 'ai' ||\n messageRecord.type === 'AIMessageChunk' ||\n isSerializedFormat\n ) {\n /**\n * Try tool_calls first (normalized format)\n */\n if (Array.isArray(dataSource?.tool_calls)) {\n toolCalls = dataSource.tool_calls as ToolCall[];\n } else if (\n /**\n * Fall back to additional_kwargs.tool_calls (OpenAI format)\n */\n dataSource?.additional_kwargs &&\n typeof dataSource.additional_kwargs === 'object'\n ) {\n const additionalKwargs =\n dataSource.additional_kwargs as Record<string, unknown>;\n if (Array.isArray(additionalKwargs.tool_calls)) {\n /**\n * Convert OpenAI format to normalized format\n */\n toolCalls = (\n additionalKwargs.tool_calls as Array<{\n id?: string;\n function?: { name?: string; arguments?: string };\n }>\n ).map((tc, idx) => {\n const functionData = tc.function;\n let args: unknown;\n try {\n args = functionData?.arguments\n ? JSON.parse(functionData.arguments)\n : {};\n } catch {\n args = {};\n }\n return {\n id: tc.id || `call_${idx}`,\n name: functionData?.name || 'unknown',\n args,\n } as ToolCall;\n });\n }\n }\n }\n }\n\n if (toolCalls && toolCalls.length > 0) {\n for (const toolCall of toolCalls) {\n const messageNamespace = findMessageCurrentStepNamespace(\n state,\n msgId,\n );\n const lifecycleNamespace = messageNamespace ?? eventNamespace;\n const wasObservedInCurrentStep = messageNamespace !== undefined;\n const wasToolCallEmittedInCurrentStep = toolCall.id\n ? hasEmittedToolCallInCurrentStep(\n state,\n toolCall.id,\n lifecycleNamespace,\n )\n : false;\n const trailingToolMessageInfo = toolCall.id\n ? trailingToolMessages.get(toolCall.id)\n : undefined;\n const canRecoverCompletedToolCall =\n wasObservedInCurrentStep || wasToolCallEmittedInCurrentStep;\n /**\n * Emit tool calls recovered from a message in the current step,\n * even when a prior step used the same provider-scoped ID.\n * Otherwise, preserve stream-wide suppression for historical calls\n * while recovering completed calls observed in the current step or\n * an earlier values snapshot before their trailing ToolMessage arrived.\n */\n if (\n toolCall.id &&\n !wasToolCallEmittedInCurrentStep &&\n (wasObservedInCurrentStep ||\n (!emittedToolCalls.has(toolCall.id) &&\n !completedToolCallIds.has(toolCall.id)))\n ) {\n markToolCallEmitted(state, toolCall.id, lifecycleNamespace);\n // Store mapping for HITL interrupt lookup\n const toolCallKey = `${toolCall.name}:${JSON.stringify(toolCall.args)}`;\n emittedToolCallsByKey.set(toolCallKey, toolCall.id);\n /**\n * Emit tool-input-start first to ensure proper lifecycle.\n * Tool calls that weren't streamed (no tool_call_chunks) need\n * the start event before tool-input-available.\n */\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId: toolCall.id,\n toolName: toolCall.name,\n dynamic: true,\n });\n markToolInputEmitted(state, toolCall.id, lifecycleNamespace);\n controller.enqueue({\n type: 'tool-input-available',\n toolCallId: toolCall.id,\n toolName: toolCall.name,\n input: toolCall.args,\n dynamic: true,\n });\n } else if (toolCall.id && emittedToolCalls.has(toolCall.id)) {\n // Register key mapping for tool calls already emitted via messages mode\n // so that __interrupt__ handling can match them by key\n const toolCallKey = `${toolCall.name}:${JSON.stringify(toolCall.args)}`;\n emittedToolCallsByKey.set(toolCallKey, toolCall.id);\n }\n\n if (\n toolCall.id &&\n trailingToolMessageInfo != null &&\n !state.emittedToolOutputMessageIds.has(\n trailingToolMessageInfo.outputId,\n ) &&\n !hasEmittedToolOutputInCurrentStep(\n state,\n toolCall.id,\n lifecycleNamespace,\n ) &&\n canRecoverCompletedToolCall\n ) {\n state.emittedToolOutputMessageIds.add(\n trailingToolMessageInfo.outputId,\n );\n markToolOutputEmitted(state, toolCall.id, lifecycleNamespace);\n const trailingToolMessage = trailingToolMessageInfo.data;\n if (trailingToolMessage.status === 'error') {\n controller.enqueue({\n type: 'tool-output-error',\n toolCallId: toolCall.id,\n errorText:\n typeof trailingToolMessage.content === 'string'\n ? trailingToolMessage.content\n : 'Tool execution failed',\n });\n } else {\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId: toolCall.id,\n output: trailingToolMessage.content,\n });\n }\n }\n }\n }\n\n /**\n * Check for reasoning content that wasn't streamed\n * Use reasoning block ID for deduplication as it's consistent across streaming and values.\n *\n * IMPORTANT: Handle two cases differently:\n * 1. Message has reasoning WITHOUT tool_calls → emit reasoning (pure reasoning case)\n * 2. Message has reasoning WITH tool_calls → only emit if streamed this request\n * (When resuming from HITL interrupt, historical messages have both reasoning\n * AND tool_calls. We skip those to avoid duplicate reasoning entries.)\n */\n const reasoningId = extractReasoningId(msg);\n const wasStreamedThisRequest = messageSeen.has(msgId);\n const hasToolCalls = toolCalls && toolCalls.length > 0;\n\n /**\n * Determine if we should emit reasoning:\n * - If we already emitted this reasoning ID, skip\n * - If the message was streamed this request, emit (normal flow)\n * - If NOT streamed but has NO tool_calls, emit (pure reasoning in values case)\n * - If NOT streamed but HAS tool_calls, skip (historical HITL message)\n */\n const shouldEmitReasoning =\n reasoningId &&\n !emittedReasoningIds.has(reasoningId) &&\n (wasStreamedThisRequest || !hasToolCalls);\n\n if (shouldEmitReasoning) {\n /**\n * Use extractReasoningFromValuesMessage which extracts from response_metadata.output\n * This is the full accumulated reasoning, not deltas\n */\n const reasoning = extractReasoningFromValuesMessage(msg);\n\n if (reasoning) {\n controller.enqueue({ type: 'reasoning-start', id: msgId });\n controller.enqueue({\n type: 'reasoning-delta',\n delta: reasoning,\n id: msgId,\n });\n controller.enqueue({ type: 'reasoning-end', id: msgId });\n emittedReasoningIds.add(reasoningId);\n }\n }\n\n const valuesCitations = extractCitationsFromContentBlocks(msg);\n if (valuesCitations.length > 0) {\n emitSourceChunks(\n valuesCitations,\n msgId,\n state.emittedSourceIds,\n controller,\n );\n }\n }\n }\n }\n\n /**\n * Handle Human-in-the-Loop interrupts\n * When HITL middleware pauses execution, the interrupt data is in __interrupt__\n * Note: This is outside the 'messages' check because interrupt can come as a separate event\n */\n if (data != null && typeof data === 'object') {\n const interrupt = (data as Record<string, unknown>).__interrupt__;\n if (Array.isArray(interrupt) && interrupt.length > 0) {\n for (const interruptItem of interrupt) {\n const interruptValue = (interruptItem as { value?: unknown })\n ?.value as Record<string, unknown> | undefined;\n\n if (!interruptValue) continue;\n\n /**\n * Support both camelCase (JS SDK) and snake_case (Python SDK)\n */\n const actionRequests = (interruptValue.actionRequests ||\n interruptValue.action_requests) as\n | Array<{\n name: string;\n args?: Record<string, unknown>; // JS SDK uses 'args'\n arguments?: Record<string, unknown>; // Python SDK uses 'arguments'\n id?: string;\n }>\n | undefined;\n\n if (!Array.isArray(actionRequests)) continue;\n\n for (const actionRequest of actionRequests) {\n const toolName = actionRequest.name;\n /**\n * Support both 'args' (JS SDK) and 'arguments' (Python SDK)\n */\n const input = actionRequest.args || actionRequest.arguments;\n\n /**\n * Look up the original tool call ID using the name+args key\n * Fall back to action request ID or generate one if not found\n */\n const toolCallKey = `${toolName}:${JSON.stringify(input)}`;\n const toolCallId =\n emittedToolCallsByKey.get(toolCallKey) ||\n actionRequest.id ||\n `hitl-${toolName}-${Date.now()}`;\n\n /**\n * First emit tool-input-start then tool-input-available\n * so the UI knows what tool is being called with proper lifecycle\n */\n if (!emittedToolCalls.has(toolCallId)) {\n markToolCallEmitted(state, toolCallId, eventNamespace);\n emittedToolCallsByKey.set(toolCallKey, toolCallId);\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId,\n toolName,\n dynamic: true,\n });\n markToolInputEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-input-available',\n toolCallId,\n toolName,\n input,\n dynamic: true,\n });\n }\n\n /**\n * Then emit tool-approval-request to mark it as awaiting approval\n */\n controller.enqueue({\n type: 'tool-approval-request',\n approvalId: toolCallId,\n toolCallId,\n });\n }\n }\n }\n }\n\n break;\n }\n }\n}\n","import type { AIMessageChunk } from '@langchain/core/messages';\nimport type {\n UIMessage,\n UIMessageChunk,\n ChatTransport,\n ChatRequestOptions,\n} from 'ai';\nimport {\n RemoteGraph,\n type RemoteGraphParams,\n} from '@langchain/langgraph/remote';\nimport { toBaseMessages, toUIMessageStream } from './adapter';\n\n/**\n * Options for configuring a LangSmith deployment transport.\n * Extends RemoteGraphParams but makes graphId optional (defaults to 'agent').\n */\nexport type LangSmithDeploymentTransportOptions = Omit<\n RemoteGraphParams,\n 'graphId'\n> & {\n /**\n * The ID of the graph to connect to.\n * @default 'agent'\n */\n graphId?: string;\n};\n\n/**\n * A ChatTransport implementation for LangSmith/LangGraph deployments.\n *\n * This transport enables seamless integration between the AI SDK's useChat hook\n * and LangSmith deployed LangGraph agents.\n *\n * @example\n * ```ts\n * import { LangSmithDeploymentTransport } from '@ai-sdk/langchain';\n *\n * // Use with useChat\n * const { messages, input, handleSubmit } = useChat({\n * transport: new LangSmithDeploymentTransport({\n * url: 'https://your-deployment.us.langgraph.app',\n * apiKey: 'my-api-key',\n * }),\n * });\n * ```\n */\nexport class LangSmithDeploymentTransport<\n UI_MESSAGE extends UIMessage,\n> implements ChatTransport<UI_MESSAGE> {\n protected graph: RemoteGraph;\n\n constructor(options: LangSmithDeploymentTransportOptions) {\n this.graph = new RemoteGraph({\n ...options,\n graphId: options.graphId ?? 'agent',\n });\n }\n\n async sendMessages(\n options: {\n trigger: 'submit-message' | 'regenerate-message';\n chatId: string;\n messageId: string | undefined;\n messages: UI_MESSAGE[];\n abortSignal: AbortSignal | undefined;\n } & ChatRequestOptions,\n ): Promise<ReadableStream<UIMessageChunk>> {\n const baseMessages = await toBaseMessages(options.messages);\n\n const stream = await this.graph.stream(\n { messages: baseMessages },\n { streamMode: ['values', 'messages'] },\n );\n\n return toUIMessageStream(\n stream as AsyncIterable<AIMessageChunk> | ReadableStream,\n );\n }\n\n async reconnectToStream(\n _options: {\n chatId: string;\n } & ChatRequestOptions,\n ): Promise<ReadableStream<UIMessageChunk> | null> {\n throw new Error('Method not implemented.');\n }\n}\n"],"mappings":"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","names":["providerMetadata"]}
1
+ {"version":3,"sources":["../src/adapter.ts","../src/utils.ts","../src/transport.ts"],"sourcesContent":["import {\n SystemMessage,\n type BaseMessage,\n type AIMessageChunk,\n} from '@langchain/core/messages';\nimport {\n convertToModelMessages,\n type UIMessage,\n type UIMessageChunk,\n type ModelMessage,\n} from 'ai';\nimport {\n convertToolResultPart,\n convertAssistantContent,\n convertUserContent,\n processModelChunk,\n processLangGraphEvent,\n parseLangGraphEvent,\n isToolResultPart,\n extractReasoningFromContentBlocks,\n extractCitationsFromContentBlocks,\n emitSourceChunks,\n getLangGraphProviderMetadata,\n} from './utils';\nimport type { LangGraphEventState } from './types';\nimport type { StreamCallbacks } from './stream-callbacks';\n\n/**\n * Options for converting a LangChain stream to an AI SDK UIMessageStream.\n */\nexport interface ToUIMessageStreamOptions<\n TState = unknown,\n> extends StreamCallbacks<TState> {\n /**\n * Whether to emit the outer `start` chunk.\n *\n * @default true\n */\n sendStart?: boolean;\n\n /**\n * Whether to emit the outer `finish` chunk.\n *\n * @default true\n */\n sendFinish?: boolean;\n}\n\n/**\n * Converts AI SDK UIMessages to LangChain BaseMessage objects.\n *\n * This function transforms the AI SDK's message format into LangChain's message\n * format, enabling seamless integration between the two frameworks.\n *\n * @param messages - Array of AI SDK UIMessage objects to convert.\n * @returns Promise resolving to an array of LangChain BaseMessage objects.\n *\n * @example\n * ```ts\n * import { toBaseMessages } from '@ai-sdk/langchain';\n *\n * const langchainMessages = await toBaseMessages(uiMessages);\n *\n * // Use with LangChain\n * const response = await model.invoke(langchainMessages);\n * ```\n */\nexport async function toBaseMessages(\n messages: UIMessage[],\n): Promise<BaseMessage[]> {\n const modelMessages = await convertToModelMessages(messages);\n return convertModelMessages(modelMessages);\n}\n\n/**\n * Converts ModelMessages to LangChain BaseMessage objects.\n *\n * @param modelMessages - Array of ModelMessage objects from convertToModelMessages.\n * @returns Array of LangChain BaseMessage objects.\n */\nexport function convertModelMessages(\n modelMessages: ModelMessage[],\n): BaseMessage[] {\n const result: BaseMessage[] = [];\n\n for (const message of modelMessages) {\n switch (message.role) {\n case 'tool': {\n // Tool messages contain an array of tool results\n for (const item of message.content) {\n if (isToolResultPart(item)) {\n result.push(convertToolResultPart(item));\n }\n }\n break;\n }\n\n case 'assistant': {\n result.push(convertAssistantContent(message.content));\n break;\n }\n\n case 'system': {\n result.push(new SystemMessage({ content: message.content }));\n break;\n }\n\n case 'user': {\n result.push(convertUserContent(message.content));\n break;\n }\n }\n }\n\n return result;\n}\n\n/**\n * Type guard to check if a value is a streamEvents event object.\n * streamEvents produces objects with `event` and `data` properties.\n *\n * @param value - The value to check.\n * @returns True if the value is a streamEvents event object.\n */\nfunction isStreamEventsEvent(\n value: unknown,\n): value is { event: string; data: Record<string, unknown> } {\n if (value == null || typeof value !== 'object') return false;\n const obj = value as Record<string, unknown>;\n // Check for event property being a string\n if (!('event' in obj) || typeof obj.event !== 'string') return false;\n // Check for data property being an object (but allow null/undefined)\n if (!('data' in obj)) return false;\n // data can be null in some events, treat as empty object\n return obj.data === null || typeof obj.data === 'object';\n}\n\n/**\n * Processes a streamEvents event and emits UI message chunks.\n *\n * @param event - The streamEvents event to process.\n * @param state - The state for tracking stream progress.\n * @param controller - The controller to emit UI message chunks.\n */\nfunction processStreamEventsEvent(\n event: {\n event: string;\n data: Record<string, unknown> | null;\n run_id?: string;\n name?: string;\n },\n state: {\n started: boolean;\n messageId: string;\n reasoningStarted: boolean;\n textStarted: boolean;\n textMessageId: string | null;\n reasoningMessageId: string | null;\n emittedSourceIds: Set<string>;\n },\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): void {\n /**\n * Capture run_id from event level if available (streamEvents v2 format)\n */\n if (event.run_id && !state.started) {\n state.messageId = event.run_id;\n }\n\n /**\n * Skip events with null/undefined data\n */\n if (!event.data) return;\n\n switch (event.event) {\n case 'on_chat_model_start': {\n /**\n * End the previous model turn's reasoning stream before a new LLM invocation.\n * Without this, reasoning-delta chunks from the next turn could attach to the\n * wrong reasoning part in the UI message stream.\n */\n if (state.reasoningStarted) {\n controller.enqueue({\n type: 'reasoning-end',\n id:\n state.reasoningMessageId != null\n ? state.reasoningMessageId\n : state.messageId,\n });\n state.reasoningStarted = false;\n state.reasoningMessageId = null;\n }\n\n /**\n * End the previous model turn's text stream before a new LLM invocation.\n * The streamEvents adapter otherwise leaves `textStarted` true, so all later\n * text-delta chunks append to the first text part — tools still grow the parts\n * array, which breaks chronological order in the assistant message.\n */\n if (state.textStarted) {\n controller.enqueue({\n type: 'text-end',\n id:\n state.textMessageId != null ? state.textMessageId : state.messageId,\n });\n state.textStarted = false;\n state.textMessageId = null;\n }\n\n /**\n * Handle model start — capture message metadata if available.\n * `run_id` is on the event in streamEvents v2; fall back to `data` for compatibility.\n */\n const runId = event.run_id || (event.data.run_id as string | undefined);\n if (runId) {\n state.messageId = runId;\n }\n break;\n }\n\n case 'on_chat_model_stream': {\n /**\n * Handle streaming token chunks\n */\n const chunk = event.data.chunk;\n if (chunk && typeof chunk === 'object') {\n /**\n * Get message ID from chunk if available\n */\n const chunkId = (chunk as { id?: string }).id;\n if (chunkId) {\n state.messageId = chunkId;\n }\n\n /**\n * Handle reasoning content from contentBlocks\n */\n const reasoning = extractReasoningFromContentBlocks(chunk);\n if (reasoning) {\n if (!state.reasoningStarted) {\n // Track the ID used for reasoning-start to ensure reasoning-end uses the same ID\n state.reasoningMessageId = state.messageId;\n controller.enqueue({\n type: 'reasoning-start',\n id: state.messageId,\n });\n state.reasoningStarted = true;\n state.started = true;\n }\n controller.enqueue({\n type: 'reasoning-delta',\n delta: reasoning,\n id: state.reasoningMessageId ?? state.messageId,\n });\n }\n\n /**\n * Extract text content from chunk\n */\n const content = (chunk as { content?: unknown }).content;\n const text =\n typeof content === 'string'\n ? content\n : Array.isArray(content)\n ? content\n .filter(\n (c): c is { type: 'text'; text: string } =>\n typeof c === 'object' &&\n c !== null &&\n 'type' in c &&\n c.type === 'text',\n )\n .map(c => c.text)\n .join('')\n : '';\n\n if (text) {\n /**\n * If reasoning was streamed before text, close reasoning first\n */\n if (state.reasoningStarted && !state.textStarted) {\n controller.enqueue({\n type: 'reasoning-end',\n id: state.reasoningMessageId ?? state.messageId,\n });\n state.reasoningStarted = false;\n }\n\n if (!state.textStarted) {\n // Track the ID used for text-start to ensure text-end uses the same ID\n state.textMessageId = state.messageId;\n controller.enqueue({ type: 'text-start', id: state.messageId });\n state.textStarted = true;\n state.started = true;\n }\n controller.enqueue({\n type: 'text-delta',\n delta: text,\n id: state.textMessageId ?? state.messageId,\n });\n }\n\n const citations = extractCitationsFromContentBlocks(chunk);\n if (citations.length > 0) {\n emitSourceChunks(\n citations,\n state.messageId,\n state.emittedSourceIds,\n controller,\n );\n }\n }\n break;\n }\n\n case 'on_tool_start': {\n /**\n * Handle tool call start\n * run_id and name are at event level in v2, check data for backwards compatibility\n */\n const runId = event.run_id || (event.data.run_id as string | undefined);\n const name = event.name || (event.data.name as string | undefined);\n\n if (runId && name) {\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId: runId,\n toolName: name,\n dynamic: true,\n });\n }\n break;\n }\n\n case 'on_tool_end': {\n /**\n * Handle tool call end\n * run_id is at event level in v2, check data for backwards compatibility\n */\n const runId = event.run_id || (event.data.run_id as string | undefined);\n const output = event.data.output;\n\n if (runId) {\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId: runId,\n output,\n });\n }\n break;\n }\n }\n}\n\n/**\n * Checks if an error is an abort error.\n */\nfunction isAbortError(error: unknown): boolean {\n if (error instanceof Error) {\n return (\n error.name === 'AbortError' ||\n (error instanceof DOMException && error.name === 'AbortError')\n );\n }\n return false;\n}\n\n/**\n * Converts a LangChain stream to an AI SDK UIMessageStream.\n *\n * This function automatically detects the stream type and handles:\n * - Direct model streams (AsyncIterable from `model.stream()`)\n * - LangGraph streams (ReadableStream with `streamMode: ['values', 'messages']`)\n * - streamEvents streams (from `agent.streamEvents()` or `model.streamEvents()`)\n *\n * @param stream - A stream from LangChain model.stream(), graph.stream(), or streamEvents().\n * @param options - Optional lifecycle callbacks and outer chunk controls.\n * @returns A ReadableStream of UIMessageChunk objects.\n *\n * @example\n * ```ts\n * // With a direct model stream\n * const model = new ChatOpenAI({ model: 'gpt-4o-mini' });\n * const stream = await model.stream(messages);\n * return createUIMessageStreamResponse({\n * stream: toUIMessageStream(stream),\n * });\n *\n * // With a LangGraph stream\n * const graphStream = await graph.stream(\n * { messages },\n * { streamMode: ['values', 'messages'] }\n * );\n * return createUIMessageStreamResponse({\n * stream: toUIMessageStream(graphStream),\n * });\n *\n * // With streamEvents\n * const streamEvents = agent.streamEvents(\n * { messages },\n * { version: \"v2\" }\n * );\n * return createUIMessageStreamResponse({\n * stream: toUIMessageStream(streamEvents),\n * });\n *\n * // With callbacks for LangGraph state\n * const graphStream = await graph.stream(\n * { messages },\n * { streamMode: ['values', 'messages'] }\n * );\n * return createUIMessageStreamResponse({\n * stream: toUIMessageStream<MyStateType>(graphStream, {\n * onFinish: async (finalState) => {\n * if (finalState) {\n * await saveToDatabase(finalState);\n * }\n * },\n * onError: (error) => console.error('Stream failed:', error),\n * onAbort: () => console.log('Stream aborted'),\n * }),\n * });\n * ```\n */\nexport function toUIMessageStream<TState = unknown>(\n stream: AsyncIterable<AIMessageChunk> | ReadableStream,\n options?: ToUIMessageStreamOptions<TState>,\n): ReadableStream<UIMessageChunk> {\n const { sendStart = true, sendFinish = true } = options ?? {};\n\n /**\n * Track text chunks for onFinal callback\n */\n const textChunks: string[] = [];\n\n /** Last LangGraph values event data for onFinish callback */\n let lastValuesData: TState | undefined;\n\n /**\n * State for model stream handling\n */\n const modelState = {\n started: false,\n messageId: 'langchain-msg-1',\n reasoningStarted: false,\n textStarted: false,\n /** Track the ID used for text-start to ensure text-end uses the same ID */\n textMessageId: null as string | null,\n /** Track the ID used for reasoning-start to ensure reasoning-end uses the same ID */\n reasoningMessageId: null as string | null,\n emittedSourceIds: new Set<string>(),\n };\n\n /**\n * State for LangGraph stream handling\n */\n const langGraphState: LangGraphEventState = {\n messageSeen: new Map(),\n messageNamespaces: new Map(),\n messageConcat: new Map(),\n messageIdsInCurrentStepByNamespace: new Map(),\n emittedToolCalls: new Set<string>(),\n emittedToolCallsInCurrentStepByNamespace: new Map(),\n emittedToolInputs: new Set<string>(),\n emittedToolInputsInCurrentStepByNamespace: new Map(),\n emittedToolOutputMessageIds: new Set<string>(),\n emittedToolOutputCallIds: new Set<string>(),\n emittedToolOutputsInCurrentStepByNamespace: new Map(),\n emittedImages: new Set<string>(),\n emittedReasoningIds: new Set<string>(),\n messageReasoningIds: new Map(),\n toolCallInfoByIndex: new Map(),\n currentStepsByNamespace: new Map(),\n emittedToolCallsByKey: new Map<string, string>(),\n emittedSourceIds: new Set<string>(),\n };\n\n /**\n * Track detected stream type: null = not yet detected\n */\n let streamType: 'model' | 'langgraph' | 'streamEvents' | null = null;\n\n /**\n * Get async iterator from the stream (works for both AsyncIterable and ReadableStream)\n */\n const getAsyncIterator = (): AsyncIterator<unknown> => {\n if (Symbol.asyncIterator in stream) {\n return (stream as AsyncIterable<unknown>)[Symbol.asyncIterator]();\n }\n /**\n * For ReadableStream without Symbol.asyncIterator\n */\n const reader = (stream as ReadableStream).getReader();\n return {\n async next() {\n const { done, value } = await reader.read();\n return { done, value };\n },\n };\n };\n\n const iterator = getAsyncIterator();\n\n /**\n * Create a wrapper around the controller to intercept text chunks for callbacks\n */\n const createCallbackController = (\n originalController: ReadableStreamDefaultController<UIMessageChunk>,\n ): ReadableStreamDefaultController<UIMessageChunk> => {\n return {\n get desiredSize() {\n return originalController.desiredSize;\n },\n close: () => originalController.close(),\n error: (e?: unknown) => originalController.error(e),\n enqueue: (chunk: UIMessageChunk) => {\n /**\n * Intercept text-delta chunks for callbacks\n */\n if (chunk.type === 'text-delta' && chunk.delta) {\n if (options?.onFinal) {\n textChunks.push(chunk.delta);\n }\n options?.onToken?.(chunk.delta);\n options?.onText?.(chunk.delta);\n }\n originalController.enqueue(chunk);\n },\n };\n };\n\n return new ReadableStream<UIMessageChunk>({\n async start(controller) {\n await options?.onStart?.();\n\n const wrappedController = createCallbackController(controller);\n if (sendStart) {\n controller.enqueue({ type: 'start' });\n }\n\n try {\n while (true) {\n const { done, value } = await iterator.next();\n if (done) break;\n\n /**\n * Detect stream type on first value\n */\n if (streamType === null) {\n if (Array.isArray(value)) {\n streamType = 'langgraph';\n } else if (isStreamEventsEvent(value)) {\n streamType = 'streamEvents';\n } else {\n streamType = 'model';\n }\n }\n\n /**\n * Process based on detected type\n */\n if (streamType === 'model') {\n processModelChunk(\n value as AIMessageChunk,\n modelState,\n wrappedController,\n );\n } else if (streamType === 'streamEvents') {\n processStreamEventsEvent(\n value as {\n event: string;\n data: Record<string, unknown> | null;\n run_id?: string;\n name?: string;\n },\n modelState,\n wrappedController,\n );\n } else {\n const eventArray = value as unknown[];\n const [, type, data] = parseLangGraphEvent(eventArray);\n\n if (type === 'values') {\n lastValuesData = data as TState;\n }\n\n processLangGraphEvent(\n eventArray,\n langGraphState,\n wrappedController,\n );\n }\n }\n\n /**\n * Finalize based on stream type\n */\n if (streamType === 'model' || streamType === 'streamEvents') {\n if (modelState.reasoningStarted) {\n controller.enqueue({\n type: 'reasoning-end',\n id: modelState.reasoningMessageId ?? modelState.messageId,\n });\n }\n if (modelState.textStarted) {\n /**\n * Use the same ID that was used for text-start\n */\n controller.enqueue({\n type: 'text-end',\n id: modelState.textMessageId ?? modelState.messageId,\n });\n }\n if (sendFinish) {\n controller.enqueue({ type: 'finish' });\n }\n } else if (streamType === 'langgraph') {\n /**\n * Close any open text/reasoning parts before finishing.\n * This handles streams without values events (e.g. streamMode: 'messages')\n * where the values handler never ran to emit *-end events.\n */\n for (const [id, seen] of langGraphState.messageSeen) {\n const providerMetadata = getLangGraphProviderMetadata(\n langGraphState.messageNamespaces.get(id),\n );\n if (seen.text) {\n controller.enqueue({\n type: 'text-end',\n id,\n ...(providerMetadata !== undefined && { providerMetadata }),\n });\n }\n if (seen.reasoning) {\n controller.enqueue({\n type: 'reasoning-end',\n id,\n ...(providerMetadata !== undefined && { providerMetadata }),\n });\n }\n }\n\n /**\n * Emit finish-step if a step was started\n */\n if (langGraphState.currentStepsByNamespace.size > 0) {\n controller.enqueue({ type: 'finish-step' });\n }\n if (sendFinish) {\n controller.enqueue({ type: 'finish' });\n }\n }\n\n /**\n * Call onFinal callback with aggregated text\n */\n await options?.onFinal?.(textChunks.join(''));\n await options?.onFinish?.(lastValuesData);\n } catch (error) {\n const errorObj =\n error instanceof Error ? error : new Error(String(error));\n\n await options?.onFinal?.(textChunks.join(''));\n\n if (isAbortError(error)) {\n await options?.onAbort?.();\n } else {\n await options?.onError?.(errorObj);\n }\n\n controller.enqueue({\n type: 'error',\n errorText: errorObj.message,\n });\n } finally {\n controller.close();\n }\n },\n });\n}\n","import {\n AIMessage,\n HumanMessage,\n ToolMessage,\n AIMessageChunk,\n type ContentBlock,\n type ToolCall,\n type BaseMessage,\n type BaseMessageChunk,\n type ToolCallChunk,\n} from '@langchain/core/messages';\nimport type {\n UIMessageChunk,\n ToolResultPart,\n AssistantContent,\n UserContent,\n ProviderMetadata,\n JSONValue,\n} from 'ai';\n\nimport type {\n LangGraphEventState,\n LangGraphMessageSeen,\n ReasoningContentBlock,\n ThinkingContentBlock,\n GPT5ReasoningOutput,\n ImageGenerationOutput,\n NormalizedCitation,\n} from './types';\n\n/**\n * Parses a LangGraph event tuple into [namespace, type, data].\n * Handles both 2-element [type, data] and 3-element [namespace, type, data] formats.\n *\n * @param event - The raw LangGraph event array.\n * @returns A tuple of [namespace, type, data].\n */\nexport function parseLangGraphEvent(\n event: unknown[],\n): [namespace: unknown | undefined, type: unknown, data: unknown] {\n return event.length === 3\n ? [event[0], event[1], event[2]]\n : [undefined, event[0], event[1]];\n}\n\nexport function getLangGraphProviderMetadata(\n namespace: string[] | undefined,\n): ProviderMetadata | undefined {\n return namespace === undefined\n ? undefined\n : {\n langchain: {\n namespace,\n },\n };\n}\n\nfunction addLangGraphNamespace(\n chunk: UIMessageChunk,\n namespace: string[] | undefined,\n): UIMessageChunk {\n if (namespace === undefined) {\n return chunk;\n }\n\n switch (chunk.type) {\n case 'text-start':\n case 'text-delta':\n case 'text-end':\n case 'reasoning-start':\n case 'reasoning-delta':\n case 'reasoning-end':\n case 'custom':\n case 'tool-input-start':\n case 'tool-input-available':\n case 'tool-input-error':\n case 'tool-approval-response':\n case 'tool-output-available':\n case 'tool-output-error':\n case 'source-url':\n case 'source-document':\n case 'file':\n case 'reasoning-file': {\n return {\n ...chunk,\n providerMetadata: {\n ...chunk.providerMetadata,\n langchain: {\n ...chunk.providerMetadata?.langchain,\n namespace,\n },\n },\n };\n }\n default:\n return chunk;\n }\n}\n\nfunction createLangGraphNamespaceController(\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n state: LangGraphEventState,\n eventNamespace: string[] | undefined,\n): ReadableStreamDefaultController<UIMessageChunk> {\n return {\n get desiredSize() {\n return controller.desiredSize;\n },\n close: () => controller.close(),\n error: reason => controller.error(reason),\n enqueue: chunk => {\n if (chunk === undefined) {\n return;\n }\n\n let messageNamespace: string[] | undefined;\n switch (chunk.type) {\n case 'text-start':\n case 'text-delta':\n case 'text-end':\n case 'reasoning-start':\n case 'reasoning-delta':\n case 'reasoning-end':\n messageNamespace = state.messageNamespaces.get(chunk.id);\n break;\n }\n\n controller.enqueue(\n addLangGraphNamespace(chunk, messageNamespace ?? eventNamespace),\n );\n },\n };\n}\n\n/**\n * Converts a ToolResultPart to a LangChain ToolMessage\n * @param block - The ToolResultPart to convert.\n * @returns The converted ToolMessage.\n */\nexport function convertToolResultPart(block: ToolResultPart): ToolMessage {\n const content = (() => {\n if (block.output.type === 'text' || block.output.type === 'error-text') {\n return block.output.value;\n }\n\n if (block.output.type === 'json' || block.output.type === 'error-json') {\n return JSON.stringify(block.output.value);\n }\n\n if (block.output.type === 'content') {\n return block.output.value\n .map(outputBlock => {\n if (outputBlock.type === 'text') {\n return outputBlock.text;\n }\n return '';\n })\n .join('');\n }\n\n return '';\n })();\n\n return new ToolMessage({\n tool_call_id: block.toolCallId,\n content,\n });\n}\n\n/**\n * Converts AssistantContent to LangChain AIMessage\n * @param content - The AssistantContent to convert.\n * @returns The converted AIMessage.\n */\nexport function convertAssistantContent(content: AssistantContent): AIMessage {\n if (typeof content === 'string') {\n return new AIMessage({ content });\n }\n\n const textParts: string[] = [];\n const toolCalls: Array<{\n id: string;\n name: string;\n args: Record<string, unknown>;\n }> = [];\n\n for (const part of content) {\n if (part.type === 'text') {\n textParts.push(part.text);\n } else if (part.type === 'tool-call') {\n toolCalls.push({\n id: part.toolCallId,\n name: part.toolName,\n args: part.input as Record<string, unknown>,\n });\n }\n }\n\n return new AIMessage({\n content: textParts.join(''),\n tool_calls: toolCalls.length > 0 ? toolCalls : undefined,\n });\n}\n\n/**\n * Helper to generate a default filename from mediaType\n */\nfunction getDefaultFilename(\n mediaType: string,\n prefix: string = 'file',\n): string {\n const fileExtension = mediaType.split('/')[1] || 'bin';\n return `${prefix}.${fileExtension}`;\n}\n\nfunction convertImageToContentBlock(\n data: string | Uint8Array | URL | ArrayBuffer,\n mediaType: string = 'image/png',\n): ContentBlock.Multimodal.Image {\n if (data instanceof URL) {\n if (data.protocol !== 'data:') {\n return { type: 'image', url: data.toString() };\n }\n\n data = data.toString();\n }\n\n if (typeof data === 'string') {\n if (data.startsWith('http://') || data.startsWith('https://')) {\n return { type: 'image', url: data };\n }\n\n if (data.startsWith('data:')) {\n const matches = data.match(/^data:([^;]+);base64,(.+)$/);\n if (matches) {\n return {\n type: 'image',\n data: matches[2],\n mimeType: matches[1],\n };\n }\n\n return { type: 'image', url: data };\n }\n\n return { type: 'image', data, mimeType: mediaType };\n }\n\n const bytes = data instanceof ArrayBuffer ? new Uint8Array(data) : data;\n return {\n type: 'image',\n data: btoa(String.fromCharCode(...bytes)),\n mimeType: mediaType,\n };\n}\n\n/**\n * Converts UserContent to LangChain HumanMessage\n * @param content - The UserContent to convert.\n * @returns The converted HumanMessage.\n */\nexport function convertUserContent(content: UserContent): HumanMessage {\n if (typeof content === 'string') {\n return new HumanMessage({ content });\n }\n\n const contentBlocks: ContentBlock.Standard[] = [];\n\n for (const part of content) {\n if (part.type === 'text') {\n contentBlocks.push({ type: 'text', text: part.text });\n } else if (part.type === 'image') {\n const imagePart = part as {\n type: 'image';\n image: string | Uint8Array | URL | ArrayBuffer;\n mediaType?: string;\n };\n\n if (\n imagePart.image instanceof URL ||\n typeof imagePart.image === 'string' ||\n imagePart.image instanceof Uint8Array ||\n imagePart.image instanceof ArrayBuffer\n ) {\n contentBlocks.push(\n convertImageToContentBlock(imagePart.image, imagePart.mediaType),\n );\n }\n } else if (part.type === 'file') {\n const rawFilePart = part as {\n type: 'file';\n data:\n | string\n | Uint8Array\n | URL\n | ArrayBuffer\n | { type: 'data'; data: string | Uint8Array | ArrayBuffer }\n | { type: 'url'; url: URL }\n | { type: 'reference'; reference: Record<string, string> }\n | { type: 'text'; text: string };\n mediaType: string;\n filename?: string;\n };\n\n // Normalize tagged data shape into the legacy bare value this code expects.\n const normalizedData: string | Uint8Array | URL | ArrayBuffer = (() => {\n const data = rawFilePart.data;\n if (\n typeof data === 'object' &&\n data !== null &&\n !(data instanceof URL) &&\n !(data instanceof Uint8Array) &&\n !(data instanceof ArrayBuffer) &&\n 'type' in data\n ) {\n switch (data.type) {\n case 'data':\n return data.data;\n case 'url':\n return data.url;\n case 'text':\n return data.text;\n default:\n return '';\n }\n }\n return data as string | Uint8Array | URL | ArrayBuffer;\n })();\n\n const filePart = {\n type: 'file' as const,\n data: normalizedData,\n mediaType: rawFilePart.mediaType,\n filename: rawFilePart.filename,\n };\n\n const isImage = filePart.mediaType?.startsWith('image/');\n\n if (isImage) {\n contentBlocks.push(\n convertImageToContentBlock(filePart.data, filePart.mediaType),\n );\n } else {\n // Handle non-image files using LangChain's ContentBlock format\n const filename =\n filePart.filename || getDefaultFilename(filePart.mediaType, 'file');\n\n if (filePart.data instanceof URL) {\n contentBlocks.push({\n type: 'file',\n url: filePart.data.toString(),\n mimeType: filePart.mediaType,\n filename,\n });\n } else if (typeof filePart.data === 'string') {\n if (\n filePart.data.startsWith('http://') ||\n filePart.data.startsWith('https://')\n ) {\n contentBlocks.push({\n type: 'file',\n url: filePart.data,\n mimeType: filePart.mediaType,\n filename,\n });\n } else if (filePart.data.startsWith('data:')) {\n const matches = filePart.data.match(/^data:([^;]+);base64,(.+)$/);\n if (matches) {\n contentBlocks.push({\n type: 'file',\n data: matches[2],\n mimeType: matches[1],\n filename,\n });\n } else {\n contentBlocks.push({\n type: 'file',\n url: filePart.data,\n mimeType: filePart.mediaType,\n filename,\n });\n }\n } else {\n contentBlocks.push({\n type: 'file',\n data: filePart.data,\n mimeType: filePart.mediaType,\n filename,\n });\n }\n } else if (\n filePart.data instanceof Uint8Array ||\n filePart.data instanceof ArrayBuffer\n ) {\n const bytes =\n filePart.data instanceof ArrayBuffer\n ? new Uint8Array(filePart.data)\n : filePart.data;\n const base64 = btoa(String.fromCharCode(...bytes));\n contentBlocks.push({\n type: 'file',\n data: base64,\n mimeType: filePart.mediaType,\n filename,\n });\n }\n }\n }\n }\n\n /**\n * If we only have text parts, join them as a simple string for efficiency\n */\n if (contentBlocks.every(block => block.type === 'text')) {\n return new HumanMessage({\n content: contentBlocks\n .map(block => (block as unknown as { text: string }).text)\n .join(''),\n });\n }\n\n return new HumanMessage({ contentBlocks });\n}\n\n/**\n * Helper to check if a content item is a ToolResultPart\n * @param item - The item to check.\n * @returns True if the item is a ToolResultPart, false otherwise.\n */\nexport function isToolResultPart(item: unknown): item is ToolResultPart {\n return (\n item != null &&\n typeof item === 'object' &&\n 'type' in item &&\n (item as { type: string }).type === 'tool-result'\n );\n}\n\n/**\n * Processes a model stream chunk and emits UI message chunks.\n * @param chunk - The AIMessageChunk to process.\n * @param state - The state of the model stream.\n * @param controller - The controller to use to emit the UI message chunks.\n */\nexport function processModelChunk(\n chunk: AIMessageChunk,\n state: {\n started: boolean;\n messageId: string;\n reasoningStarted?: boolean;\n textStarted?: boolean;\n /** Track the ID used for reasoning-start to ensure reasoning-end uses the same ID */\n reasoningMessageId?: string | null;\n /** Track the ID used for text-start to ensure text-end uses the same ID */\n textMessageId?: string | null;\n emittedImages?: Set<string>;\n emittedSourceIds?: Set<string>;\n },\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): void {\n /**\n * Initialize emittedImages set if not present\n */\n if (!state.emittedImages) {\n state.emittedImages = new Set<string>();\n }\n\n if (!state.emittedSourceIds) {\n state.emittedSourceIds = new Set<string>();\n }\n\n /**\n * Get the message ID from the chunk if available\n */\n if (chunk.id) {\n state.messageId = chunk.id;\n }\n\n /**\n * Handle image generation outputs from additional_kwargs.tool_outputs\n */\n const chunkObj = chunk as unknown as Record<string, unknown>;\n const additionalKwargs = chunkObj.additional_kwargs as\n | Record<string, unknown>\n | undefined;\n const imageOutputs = extractImageOutputs(additionalKwargs);\n\n for (const imageOutput of imageOutputs) {\n /**\n * Only emit if we have image data and haven't emitted this image yet\n */\n if (imageOutput.result && !state.emittedImages.has(imageOutput.id)) {\n state.emittedImages.add(imageOutput.id);\n\n /**\n * Emit as a file part using proper AI SDK multimodal format\n */\n const mediaType = `image/${imageOutput.output_format || 'png'}`;\n controller.enqueue({\n type: 'file',\n mediaType,\n url: `data:${mediaType};base64,${imageOutput.result}`,\n });\n state.started = true;\n }\n }\n\n /**\n * Handle reasoning content from contentBlocks or response_metadata.output\n * For direct model streams, we check both sources since there's no values event\n * that would cause duplication (unlike LangGraph streams)\n */\n const reasoning =\n extractReasoningFromContentBlocks(chunk) ||\n extractReasoningFromValuesMessage(chunk);\n if (reasoning) {\n if (!state.reasoningStarted) {\n // Track the ID used for reasoning-start to ensure subsequent chunks use the same ID\n state.reasoningMessageId = state.messageId;\n controller.enqueue({ type: 'reasoning-start', id: state.messageId });\n state.reasoningStarted = true;\n state.started = true;\n }\n controller.enqueue({\n type: 'reasoning-delta',\n delta: reasoning,\n id: state.reasoningMessageId ?? state.messageId,\n });\n }\n\n /**\n * Extract text content from AIMessageChunk\n */\n const text =\n typeof chunk.content === 'string'\n ? chunk.content\n : Array.isArray(chunk.content)\n ? chunk.content\n .filter(\n (c): c is { type: 'text'; text: string } =>\n typeof c === 'object' &&\n c !== null &&\n 'type' in c &&\n c.type === 'text',\n )\n .map(c => c.text)\n .join('')\n : '';\n\n if (text) {\n /**\n * If reasoning was streamed before text, close reasoning first\n */\n if (state.reasoningStarted && !state.textStarted) {\n controller.enqueue({\n type: 'reasoning-end',\n id: state.reasoningMessageId ?? state.messageId,\n });\n state.reasoningStarted = false;\n }\n\n if (!state.textStarted) {\n // Track the ID used for text-start to ensure subsequent chunks use the same ID\n state.textMessageId = state.messageId;\n controller.enqueue({ type: 'text-start', id: state.messageId });\n state.textStarted = true;\n state.started = true;\n }\n controller.enqueue({\n type: 'text-delta',\n delta: text,\n id: state.textMessageId ?? state.messageId,\n });\n }\n\n const citations = extractCitationsFromContentBlocks(chunk);\n if (citations.length > 0) {\n emitSourceChunks(\n citations,\n state.messageId,\n state.emittedSourceIds,\n controller,\n );\n }\n}\n\n/**\n * Checks if a message is a plain object (not a LangChain class instance).\n * LangChain class instances have a _getType method.\n *\n * @param msg - The message to check.\n * @returns True if the message is a plain object, false otherwise.\n */\nexport function isPlainMessageObject(msg: unknown): boolean {\n if (msg == null || typeof msg !== 'object') return false;\n /**\n * LangChain class instances have _getType method\n */\n return typeof (msg as { _getType?: unknown })._getType !== 'function';\n}\n\n/**\n * Extracts the actual message ID from a message.\n * Handles both class instances (msg.id) and serialized LangChain messages (msg.kwargs.id).\n *\n * @param msg - The message to extract the ID from.\n * @returns The message ID string, or undefined if not found.\n */\nexport function getMessageId(msg: unknown): string | undefined {\n if (msg == null || typeof msg !== 'object') return undefined;\n\n const msgObj = msg as Record<string, unknown>;\n\n /**\n * For class instances, id is directly on the object\n */\n if (typeof msgObj.id === 'string') {\n return msgObj.id;\n }\n\n /**\n * For serialized LangChain messages, id is in kwargs\n */\n if (\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ) {\n const kwargs = msgObj.kwargs as Record<string, unknown>;\n if (typeof kwargs.id === 'string') {\n return kwargs.id;\n }\n }\n}\n\n/**\n * Checks if a message is an AIMessageChunk class instance, including instances\n * created by a different LangChain module build.\n */\nfunction isAIMessageChunkInstance(msg: unknown): msg is AIMessageChunk {\n if (AIMessageChunk.isInstance(msg)) return true;\n if (msg == null || typeof msg !== 'object') return false;\n\n const message = msg as {\n _getType?: () => unknown;\n concat?: unknown;\n };\n\n return (\n typeof message._getType === 'function' &&\n typeof message.concat === 'function' &&\n message._getType() === 'ai'\n );\n}\n\n/**\n * Checks if a message is an AI message chunk (works for both class instances and plain objects).\n * For class instances, only AIMessageChunk is matched (not AIMessage).\n * For plain objects from RemoteGraph API, matches type === 'ai' (TypeScript langchain-core)\n * or type === 'AIMessageChunk' (Python langchain-core).\n * For serialized LangChain messages, matches type === 'constructor' with AIMessageChunk in id path.\n *\n * @param msg - The message to check.\n * @returns True if the message is an AI message chunk, false otherwise.\n */\nexport function isAIMessageChunk(\n msg: unknown,\n): msg is AIMessageChunk & { type?: string; content?: string } {\n /**\n * Actual AIMessageChunk class instance\n */\n if (isAIMessageChunkInstance(msg)) return true;\n /**\n * Plain object from RemoteGraph API (not a LangChain class instance)\n */\n if (isPlainMessageObject(msg)) {\n const messageRecord = msg as Record<string, unknown>;\n /**\n * Direct type from RemoteGraph format. TypeScript langchain-core emits\n * type === 'ai'; Python langchain-core emits type === 'AIMessageChunk'.\n */\n if (\n 'type' in messageRecord &&\n (messageRecord.type === 'ai' || messageRecord.type === 'AIMessageChunk')\n ) {\n return true;\n }\n /**\n * Serialized LangChain message format: { lc: 1, type: \"constructor\", id: [\"...\", \"AIMessageChunk\"], kwargs: {...} }\n */\n if (\n messageRecord.type === 'constructor' &&\n Array.isArray(messageRecord.id) &&\n (messageRecord.id.includes('AIMessageChunk') ||\n messageRecord.id.includes('AIMessage'))\n ) {\n return true;\n }\n }\n return false;\n}\n\n/**\n * Checks if a message is a Tool message (works for both class instances and plain objects).\n *\n * @param msg - The message to check.\n * @returns True if the message is a Tool message, false otherwise.\n */\nexport function isToolMessageType(\n msg: unknown,\n): msg is ToolMessage & { type?: string; tool_call_id?: string } {\n if (ToolMessage.isInstance(msg)) return true;\n /**\n * Plain object from RemoteGraph API (not a LangChain class instance)\n */\n if (isPlainMessageObject(msg)) {\n const messageRecord = msg as Record<string, unknown>;\n /**\n * Direct type === 'tool' (RemoteGraph format)\n */\n if ('type' in messageRecord && messageRecord.type === 'tool') return true;\n /**\n * Serialized LangChain message format\n */\n if (\n messageRecord.type === 'constructor' &&\n Array.isArray(messageRecord.id) &&\n messageRecord.id.includes('ToolMessage')\n ) {\n return true;\n }\n }\n return false;\n}\n\n/**\n * Gets text content from a message (works for both class instances and plain objects).\n *\n * @param msg - The message to get the text from.\n * @returns The text content of the message.\n */\nexport function getMessageText(msg: unknown): string {\n if (AIMessageChunk.isInstance(msg)) {\n return msg.text ?? '';\n }\n\n if (msg == null || typeof msg !== 'object') return '';\n\n const msgObj = msg as Record<string, unknown>;\n\n // For serialized LangChain messages, content is in kwargs\n const dataSource =\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n if ('content' in dataSource) {\n const content = dataSource.content;\n /**\n * Handle string content\n */\n if (typeof content === 'string') {\n return content;\n }\n /**\n * Handle array of content blocks (e.g., [{ type: 'text', text: 'The', index: 0 }])\n */\n if (Array.isArray(content)) {\n return content\n .filter(\n (block): block is { type: 'text'; text: string } =>\n block != null &&\n typeof block === 'object' &&\n block.type === 'text' &&\n typeof block.text === 'string',\n )\n .map(block => block.text)\n .join('');\n }\n return '';\n }\n return '';\n}\n\n/**\n * Checks if an object is a reasoning content block\n *\n * @param obj - The object to check.\n * @returns True if the object is a reasoning content block, false otherwise.\n */\nexport function isReasoningContentBlock(\n obj: unknown,\n): obj is ReasoningContentBlock {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: string }).type === 'reasoning' &&\n 'reasoning' in obj &&\n typeof (obj as { reasoning: unknown }).reasoning === 'string'\n );\n}\n\n/**\n * Checks if an object is a thinking content block (Anthropic-style)\n *\n * @param obj - The object to check.\n * @returns True if the object is a thinking content block, false otherwise.\n */\nexport function isThinkingContentBlock(\n obj: unknown,\n): obj is ThinkingContentBlock {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: string }).type === 'thinking' &&\n 'thinking' in obj &&\n typeof (obj as { thinking: unknown }).thinking === 'string'\n );\n}\n\n/**\n * Checks if an object is a GPT-5 reasoning output block\n */\nfunction isGPT5ReasoningOutput(obj: unknown): obj is GPT5ReasoningOutput {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: string }).type === 'reasoning' &&\n 'summary' in obj &&\n Array.isArray((obj as { summary: unknown }).summary)\n );\n}\n\n/**\n * Extracts the reasoning block ID from a message (GPT-5 format).\n * This ID is consistent across streaming and values events.\n * Handles both class instances and serialized LangChain message objects.\n *\n * @param msg - The message to extract the reasoning ID from.\n * @returns The reasoning block ID if found, undefined otherwise.\n */\nexport function extractReasoningId(msg: unknown): string | undefined {\n if (msg == null || typeof msg !== 'object') return undefined;\n\n // For serialized LangChain messages, the data is in kwargs\n const msgObj = msg as Record<string, unknown>;\n const kwargs =\n msgObj.kwargs && typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n // Check additional_kwargs.reasoning.id (GPT-5 streaming format)\n const additionalKwargs = (\n kwargs as { additional_kwargs?: { reasoning?: { id?: string } } }\n ).additional_kwargs;\n if (additionalKwargs?.reasoning?.id) {\n return additionalKwargs.reasoning.id;\n }\n\n // Check response_metadata.output for reasoning block ID (GPT-5 final format)\n const responseMetadata = (\n kwargs as { response_metadata?: { output?: unknown[] } }\n ).response_metadata;\n if (responseMetadata && Array.isArray(responseMetadata.output)) {\n for (const item of responseMetadata.output) {\n if (isGPT5ReasoningOutput(item)) {\n return item.id;\n }\n }\n }\n}\n\n/**\n * Extracts reasoning content from contentBlocks or additional_kwargs.reasoning.summary\n *\n * IMPORTANT: This function is designed for STREAMING chunks where content is delta-based.\n * It does NOT extract from response_metadata.output because that contains accumulated\n * content (not deltas) and would cause duplication during streaming.\n *\n * For non-streaming/values events, use extractReasoningFromValuesMessage instead.\n *\n * Handles both class instances and serialized LangChain message objects.\n *\n * @param msg - The message to extract reasoning from.\n * @returns The reasoning text if found, undefined otherwise.\n */\nexport function extractReasoningFromContentBlocks(\n msg: unknown,\n): string | undefined {\n if (msg == null || typeof msg !== 'object') return undefined;\n\n // For serialized LangChain messages, the data is in kwargs\n const msgObj = msg as Record<string, unknown>;\n const kwargs =\n msgObj.kwargs && typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n // Check contentBlocks (Anthropic-style) - highest priority\n const contentBlocks = (kwargs as { contentBlocks?: unknown[] }).contentBlocks;\n if (Array.isArray(contentBlocks)) {\n const reasoningParts: string[] = [];\n for (const block of contentBlocks) {\n if (isReasoningContentBlock(block)) {\n reasoningParts.push(block.reasoning);\n } else if (isThinkingContentBlock(block)) {\n reasoningParts.push(block.thinking);\n }\n }\n if (reasoningParts.length > 0) {\n return reasoningParts.join('');\n }\n }\n\n // Check additional_kwargs.reasoning.summary (GPT-5 streaming format)\n // This contains DELTA content during streaming, not accumulated content\n // Format can be either { type: \"summary_text\", text: \"...\" } or just { text: \"...\" }\n const additionalKwargs = (\n kwargs as { additional_kwargs?: { reasoning?: { summary?: unknown[] } } }\n ).additional_kwargs;\n if (\n additionalKwargs?.reasoning &&\n Array.isArray(additionalKwargs.reasoning.summary)\n ) {\n const reasoningParts: string[] = [];\n for (const summaryItem of additionalKwargs.reasoning.summary) {\n if (\n typeof summaryItem === 'object' &&\n summaryItem !== null &&\n 'text' in summaryItem &&\n typeof (summaryItem as { text: unknown }).text === 'string'\n ) {\n reasoningParts.push((summaryItem as { text: string }).text);\n }\n }\n if (reasoningParts.length > 0) {\n return reasoningParts.join('');\n }\n }\n}\n\n/**\n * Extracts reasoning content from a values event message.\n * This checks response_metadata.output which contains the full accumulated reasoning.\n *\n * @param msg - The message to extract reasoning from.\n * @returns The reasoning text if found, undefined otherwise.\n */\nexport function extractReasoningFromValuesMessage(\n msg: unknown,\n): string | undefined {\n if (msg == null || typeof msg !== 'object') return undefined;\n\n // For serialized LangChain messages, the data is in kwargs\n const msgObj = msg as Record<string, unknown>;\n const kwargs =\n msgObj.kwargs && typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n // Check response_metadata.output (GPT-5 final style) - for values events\n const responseMetadata = (\n kwargs as { response_metadata?: { output?: unknown[] } }\n ).response_metadata;\n if (responseMetadata && Array.isArray(responseMetadata.output)) {\n const reasoningParts: string[] = [];\n for (const item of responseMetadata.output) {\n if (isGPT5ReasoningOutput(item)) {\n // Extract text from summary array - handles both { type: \"summary_text\", text } and { text } formats\n for (const summaryItem of item.summary) {\n if (typeof summaryItem === 'object' && summaryItem !== null) {\n const text = (summaryItem as { text?: string }).text;\n if (typeof text === 'string' && text) {\n reasoningParts.push(text);\n }\n }\n }\n }\n }\n if (reasoningParts.length > 0) {\n return reasoningParts.join('');\n }\n }\n\n // Also check additional_kwargs.reasoning.summary as fallback\n const additionalKwargs = (\n kwargs as { additional_kwargs?: { reasoning?: { summary?: unknown[] } } }\n ).additional_kwargs;\n if (\n additionalKwargs?.reasoning &&\n Array.isArray(additionalKwargs.reasoning.summary)\n ) {\n const reasoningParts: string[] = [];\n for (const summaryItem of additionalKwargs.reasoning.summary) {\n if (\n typeof summaryItem === 'object' &&\n summaryItem !== null &&\n 'text' in summaryItem &&\n typeof (summaryItem as { text: unknown }).text === 'string'\n ) {\n reasoningParts.push((summaryItem as { text: string }).text);\n }\n }\n if (reasoningParts.length > 0) {\n return reasoningParts.join('');\n }\n }\n}\n\nexport function isCitationContentBlock(\n obj: unknown,\n): obj is ContentBlock.Citation {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: unknown }).type === 'citation'\n );\n}\n\n/**\n * LangChain Core standardizes citations as `{ type: 'citation', ... }` entries in\n * the `annotations` array of a text content block. The text extractors elsewhere\n * in this file only read the `text` field, so without this the citations would be\n * dropped instead of surfaced as AI SDK source parts.\n *\n * Handles both class instances and serialized LangChain message objects.\n */\nexport function extractCitationsFromContentBlocks(\n msg: unknown,\n): NormalizedCitation[] {\n if (msg == null || typeof msg !== 'object') return [];\n\n const msgObj = msg as Record<string, unknown>;\n const kwargs =\n msgObj.kwargs && typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n // `contentBlocks` is the normalized view derived from `content`; reading both\n // would double-count annotations, so prefer it and only fall back to `content`.\n const contentBlocks = (kwargs as { contentBlocks?: unknown }).contentBlocks;\n const content = (kwargs as { content?: unknown }).content;\n const blockSources: unknown[] = Array.isArray(contentBlocks)\n ? contentBlocks\n : Array.isArray(content)\n ? content\n : [];\n\n const citations: NormalizedCitation[] = [];\n\n for (const block of blockSources) {\n if (block == null || typeof block !== 'object') continue;\n\n const annotations = (block as { annotations?: unknown }).annotations;\n if (!Array.isArray(annotations)) continue;\n\n for (const annotation of annotations) {\n if (!isCitationContentBlock(annotation)) continue;\n\n citations.push({\n url: annotation.url,\n title: annotation.title,\n source: annotation.source,\n citedText: annotation.citedText,\n startIndex: annotation.startIndex,\n endIndex: annotation.endIndex,\n });\n }\n }\n\n return citations;\n}\n\nfunction buildSourceProviderMetadata(\n citation: NormalizedCitation,\n): ProviderMetadata | undefined {\n const langchain: Record<string, JSONValue> = {};\n\n if (typeof citation.citedText === 'string') {\n langchain.citedText = citation.citedText;\n }\n if (typeof citation.startIndex === 'number') {\n langchain.startIndex = citation.startIndex;\n }\n if (typeof citation.endIndex === 'number') {\n langchain.endIndex = citation.endIndex;\n }\n if (typeof citation.source === 'string') {\n langchain.source = citation.source;\n }\n\n if (Object.keys(langchain).length === 0) {\n return undefined;\n }\n\n return { langchain };\n}\n\n/**\n * Emits AI SDK source chunks (`source-url` / `source-document`) for the given\n * citations.\n *\n * Citations with a `url` become `source-url` parts keyed by that url; the rest\n * become `source-document` parts. Citation metadata that the source parts cannot\n * represent natively (`citedText`, `startIndex`, `endIndex`, `source`) is preserved\n * under `providerMetadata.langchain`.\n *\n * `emittedSourceIds` dedupes across the LangGraph messages and values events, which\n * can each surface the same citation. URL-less citations are keyed by their content\n * rather than position, so a differing citation subset/order between those two events\n * does not cause an id collision.\n */\nexport function emitSourceChunks(\n citations: NormalizedCitation[],\n messageId: string,\n emittedSourceIds: Set<string>,\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): void {\n for (const citation of citations) {\n if (citation.url) {\n if (emittedSourceIds.has(citation.url)) continue;\n emittedSourceIds.add(citation.url);\n\n const providerMetadata = buildSourceProviderMetadata(citation);\n controller.enqueue({\n type: 'source-url',\n sourceId: citation.url,\n url: citation.url,\n ...(citation.title ? { title: citation.title } : {}),\n ...(providerMetadata ? { providerMetadata } : {}),\n });\n continue;\n }\n\n // A citation with no url and no human-readable label carries no information a\n // UI could render, so skip it rather than emit a placeholder source.\n const title = citation.title ?? citation.source;\n if (!title) continue;\n\n const sourceId = `${messageId}:${title}:${citation.citedText ?? ''}:${citation.startIndex ?? ''}:${citation.endIndex ?? ''}`;\n if (emittedSourceIds.has(sourceId)) continue;\n emittedSourceIds.add(sourceId);\n\n const providerMetadata = buildSourceProviderMetadata(citation);\n controller.enqueue({\n type: 'source-document',\n sourceId,\n mediaType: 'text/plain',\n title,\n ...(providerMetadata ? { providerMetadata } : {}),\n });\n }\n}\n\n/**\n * Checks if an object is an image generation output\n *\n * @param obj - The object to check.\n * @returns True if the object is an image generation output, false otherwise.\n */\nexport function isImageGenerationOutput(\n obj: unknown,\n): obj is ImageGenerationOutput {\n return (\n obj != null &&\n typeof obj === 'object' &&\n 'type' in obj &&\n (obj as { type: string }).type === 'image_generation_call'\n );\n}\n\n/**\n * Extracts image generation outputs from `additional_kwargs`\n *\n * @param additionalKwargs - The additional kwargs to extract the image generation outputs from.\n * @returns The image generation outputs.\n */\nexport function extractImageOutputs(\n additionalKwargs: Record<string, unknown> | undefined,\n): ImageGenerationOutput[] {\n if (!additionalKwargs) return [];\n\n const toolOutputs = additionalKwargs.tool_outputs;\n if (!Array.isArray(toolOutputs)) return [];\n\n return toolOutputs.filter(isImageGenerationOutput);\n}\n\nfunction formatToolError(error: unknown): string {\n if (error instanceof Error) return error.message;\n if (typeof error === 'string') return error;\n\n try {\n const serialized = JSON.stringify(error);\n return serialized ?? String(error);\n } catch {\n return String(error);\n }\n}\n\n/**\n * Returns per-message bookkeeping, creating it on first use.\n * Map keys keep remote-controlled message IDs like \"__proto__\" from touching Object.prototype.\n */\nfunction getOrCreateMessageSeen(\n messageSeen: LangGraphEventState['messageSeen'],\n msgId: string,\n): LangGraphMessageSeen {\n let seen = messageSeen.get(msgId);\n if (!seen) {\n seen = {};\n messageSeen.set(msgId, seen);\n }\n return seen;\n}\n\n/**\n * Returns the per-index tool call metadata for a message, creating it on first use.\n * Later streamed chunks use this to recover tool call IDs/names from earlier chunks.\n */\nfunction getOrCreateToolCallInfoByIndex(\n toolCallInfoByIndex: LangGraphEventState['toolCallInfoByIndex'],\n msgId: string,\n): Map<number, { id: string; name: string }> {\n let toolCallInfo = toolCallInfoByIndex.get(msgId);\n if (!toolCallInfo) {\n toolCallInfo = new Map();\n toolCallInfoByIndex.set(msgId, toolCallInfo);\n }\n return toolCallInfo;\n}\n\n/**\n * Normalizes legacy tuples without a namespace and explicit empty root\n * namespaces to the same key.\n */\nfunction getLangGraphNamespaceKey(namespace: string[] | undefined): string {\n return JSON.stringify(namespace ?? []);\n}\n\nfunction getOrCreateNamespaceSet(\n setsByNamespace: Map<string, Set<string>>,\n namespace: string,\n): Set<string> {\n let values = setsByNamespace.get(namespace);\n if (!values) {\n values = new Set();\n setsByNamespace.set(namespace, values);\n }\n return values;\n}\n\nfunction hasEmittedToolCallInCurrentStep(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): boolean {\n return !state.currentStepsByNamespace.has(namespace)\n ? state.emittedToolCalls.has(toolCallId)\n : state.emittedToolCallsInCurrentStepByNamespace\n .get(namespace)\n ?.has(toolCallId) === true;\n}\n\nfunction markToolCallEmitted(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): void {\n state.emittedToolCalls.add(toolCallId);\n if (state.currentStepsByNamespace.has(namespace)) {\n getOrCreateNamespaceSet(\n state.emittedToolCallsInCurrentStepByNamespace,\n namespace,\n ).add(toolCallId);\n }\n}\n\nfunction hasEmittedToolInputInCurrentStep(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): boolean {\n return !state.currentStepsByNamespace.has(namespace)\n ? state.emittedToolInputs.has(toolCallId)\n : state.emittedToolInputsInCurrentStepByNamespace\n .get(namespace)\n ?.has(toolCallId) === true;\n}\n\nfunction markToolInputEmitted(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): void {\n state.emittedToolInputs.add(toolCallId);\n if (state.currentStepsByNamespace.has(namespace)) {\n getOrCreateNamespaceSet(\n state.emittedToolInputsInCurrentStepByNamespace,\n namespace,\n ).add(toolCallId);\n }\n}\n\nfunction hasEmittedToolOutputInCurrentStep(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): boolean {\n return !state.currentStepsByNamespace.has(namespace)\n ? state.emittedToolOutputCallIds.has(toolCallId)\n : state.emittedToolOutputsInCurrentStepByNamespace\n .get(namespace)\n ?.has(toolCallId) === true;\n}\n\nfunction markToolOutputEmitted(\n state: LangGraphEventState,\n toolCallId: string,\n namespace: string,\n): void {\n state.emittedToolOutputCallIds.add(toolCallId);\n if (state.currentStepsByNamespace.has(namespace)) {\n getOrCreateNamespaceSet(\n state.emittedToolOutputsInCurrentStepByNamespace,\n namespace,\n ).add(toolCallId);\n }\n}\n\nfunction findMessageCurrentStepNamespace(\n state: LangGraphEventState,\n messageId: string,\n): string | undefined {\n for (const [\n namespace,\n messageIds,\n ] of state.messageIdsInCurrentStepByNamespace) {\n if (messageIds.has(messageId)) {\n return namespace;\n }\n }\n}\n\n/**\n * Ends and clears message state for an advancing namespace. Returns whether\n * another namespace still has active text or reasoning that would be\n * invalidated by a global finish-step chunk.\n */\nfunction closeStepNamespaceMessages(\n state: LangGraphEventState,\n stepNamespace: string,\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): boolean {\n let hasConcurrentMessageParts = false;\n\n for (const [id, seen] of state.messageSeen) {\n const messageNamespace = getLangGraphNamespaceKey(\n state.messageNamespaces.get(id),\n );\n\n if (messageNamespace !== stepNamespace) {\n if (seen.text || seen.reasoning) {\n hasConcurrentMessageParts = true;\n }\n continue;\n }\n\n if (seen.text) {\n controller.enqueue({ type: 'text-end', id });\n }\n if (seen.reasoning) {\n controller.enqueue({ type: 'reasoning-end', id });\n }\n state.messageSeen.delete(id);\n state.messageNamespaces.delete(id);\n state.messageConcat.delete(id);\n state.messageReasoningIds.delete(id);\n }\n\n return hasConcurrentMessageParts;\n}\n\n/**\n * Processes a LangGraph event and emits UI message chunks.\n *\n * @param event - The event to process.\n * @param state - The state of the LangGraph event.\n * @param controller - The controller to use to emit the UI message chunks.\n */\nexport function processLangGraphEvent(\n event: unknown[],\n state: LangGraphEventState,\n controller: ReadableStreamDefaultController<UIMessageChunk>,\n): void {\n const {\n messageSeen,\n messageConcat,\n emittedToolCalls,\n emittedImages,\n emittedReasoningIds,\n messageReasoningIds,\n toolCallInfoByIndex,\n emittedToolCallsByKey,\n } = state;\n const [rawNamespace, type, data] = parseLangGraphEvent(event);\n const namespace =\n Array.isArray(rawNamespace) &&\n rawNamespace.every(segment => typeof segment === 'string')\n ? rawNamespace\n : undefined;\n const eventNamespace = getLangGraphNamespaceKey(namespace);\n controller = createLangGraphNamespaceController(controller, state, namespace);\n\n switch (type) {\n case 'custom': {\n /**\n * Extract custom event type from the data's 'type' field if present.\n * This allows users to emit custom events like:\n * writer({ type: 'progress', value: 50 }) -> { type: 'data-progress', data: {...} }\n * writer({ type: 'status', message: '...' }) -> { type: 'data-status', data: {...} }\n * writer({ key: 'value' }) -> { type: 'data-custom', data: {...} } (fallback)\n *\n * The 'id' field can be used to make parts persistent and updateable.\n * Parts with an 'id' are NOT transient (added to message.parts).\n * Parts without an 'id' are transient (only passed to onData callback).\n */\n let customTypeName = 'custom';\n let partId: string | undefined;\n\n if (data != null && typeof data === 'object' && !Array.isArray(data)) {\n const dataObj = data as Record<string, unknown>;\n if (typeof dataObj.type === 'string' && dataObj.type) {\n customTypeName = dataObj.type;\n }\n if (typeof dataObj.id === 'string' && dataObj.id) {\n partId = dataObj.id;\n }\n }\n\n controller.enqueue({\n type: `data-${customTypeName}` as `data-${string}`,\n id: partId,\n transient: partId == null,\n data,\n });\n break;\n }\n\n case 'messages': {\n const [rawMsg, metadata] = data as [\n BaseMessageChunk | BaseMessage | undefined,\n Record<string, unknown> | undefined,\n ];\n\n const msg = rawMsg;\n const msgId = getMessageId(msg);\n\n if (!msgId) return;\n\n if (namespace !== undefined) {\n state.messageNamespaces.set(msgId, namespace);\n }\n\n /**\n * Each namespace has an independent LangGraph step counter. Advancing a\n * namespace starts a new reducer scope so provider-scoped tool call IDs\n * can be reused in that namespace. A finish-step chunk clears every\n * active UI text/reasoning part, so omit it when another namespace is\n * still active.\n */\n const langgraphStep =\n typeof metadata?.langgraph_step === 'number'\n ? metadata.langgraph_step\n : null;\n if (langgraphStep !== null) {\n const currentStep =\n state.currentStepsByNamespace.get(eventNamespace) ?? null;\n if (currentStep === null) {\n if (state.currentStepsByNamespace.size === 0) {\n controller.enqueue({ type: 'start-step' });\n }\n state.currentStepsByNamespace.set(eventNamespace, langgraphStep);\n state.messageIdsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolCallsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolInputsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolOutputsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n } else if (langgraphStep !== currentStep) {\n const hasConcurrentMessageParts = closeStepNamespaceMessages(\n state,\n eventNamespace,\n controller,\n );\n if (!hasConcurrentMessageParts) {\n controller.enqueue({ type: 'finish-step' });\n }\n\n /**\n * A concurrent namespace prevents finish-step because it would close\n * that namespace's active text/reasoning parts. Still emit start-step\n * so tool calls in the advancing namespace have a distinct reducer\n * scope while the concurrent message lifecycle remains active.\n */\n controller.enqueue({ type: 'start-step' });\n state.currentStepsByNamespace.set(eventNamespace, langgraphStep);\n state.messageIdsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolCallsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolInputsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n state.emittedToolOutputsInCurrentStepByNamespace.set(\n eventNamespace,\n new Set(),\n );\n }\n }\n if (state.currentStepsByNamespace.has(eventNamespace)) {\n getOrCreateNamespaceSet(\n state.messageIdsInCurrentStepByNamespace,\n eventNamespace,\n ).add(msgId);\n }\n\n /**\n * Accumulate message chunks for later reference\n * Note: Only works for actual class instances, not serialized messages\n */\n if (isAIMessageChunkInstance(msg)) {\n const existingMessage = messageConcat.get(msgId);\n if (existingMessage) {\n messageConcat.set(\n msgId,\n existingMessage.concat(msg) as AIMessageChunk,\n );\n } else {\n messageConcat.set(msgId, msg);\n }\n }\n\n if (isAIMessageChunk(msg)) {\n const concatChunk = messageConcat.get(msgId);\n\n /**\n * Handle image generation outputs from additional_kwargs.tool_outputs\n * Handle both direct properties and serialized messages (kwargs)\n */\n const msgObj = msg as unknown as Record<string, unknown>;\n const dataSource =\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n const additionalKwargs = dataSource.additional_kwargs as\n | Record<string, unknown>\n | undefined;\n const imageOutputs = extractImageOutputs(additionalKwargs);\n\n for (const imageOutput of imageOutputs) {\n /**\n * Only emit if we have image data and haven't emitted this image yet\n */\n if (imageOutput.result && !emittedImages.has(imageOutput.id)) {\n emittedImages.add(imageOutput.id);\n\n /**\n * Emit as a file part using proper AI SDK multimodal format\n */\n const mediaType = `image/${imageOutput.output_format || 'png'}`;\n controller.enqueue({\n type: 'file',\n mediaType,\n url: `data:${mediaType};base64,${imageOutput.result}`,\n });\n }\n }\n\n /**\n * Handle tool call chunks for streaming tool calls\n * Access from dataSource to handle both direct and serialized messages\n *\n * Tool call chunks are streamed as follows:\n * 1. First chunk: has name, id, but often empty args\n * 2. Subsequent chunks: have args but NO id or name\n *\n * We store tool call info by index when we first see it, then look it up\n * for subsequent chunks that don't include the id.\n */\n const toolCallChunks = dataSource.tool_call_chunks as\n | ToolCallChunk[]\n | undefined;\n if (toolCallChunks?.length) {\n for (const toolCallChunk of toolCallChunks) {\n const toolCallIndex = toolCallChunk.index ?? 0;\n\n /**\n * If this chunk has an id, store it for future lookups by index\n */\n if (toolCallChunk.id) {\n getOrCreateToolCallInfoByIndex(toolCallInfoByIndex, msgId).set(\n toolCallIndex,\n {\n id: toolCallChunk.id,\n name:\n toolCallChunk.name ||\n concatChunk?.tool_call_chunks?.[toolCallIndex]?.name ||\n 'unknown',\n },\n );\n }\n\n /**\n * Get the tool call ID from the chunk, stored info, or accumulated chunks\n */\n const storedToolCallInfo = toolCallInfoByIndex\n .get(msgId)\n ?.get(toolCallIndex);\n const toolCallId =\n toolCallChunk.id ||\n storedToolCallInfo?.id ||\n concatChunk?.tool_call_chunks?.[toolCallIndex]?.id;\n\n /**\n * Skip if we don't have a proper tool call ID - we'll handle it in values\n */\n if (!toolCallId) {\n continue;\n }\n\n const toolName =\n toolCallChunk.name ||\n storedToolCallInfo?.name ||\n concatChunk?.tool_call_chunks?.[toolCallIndex]?.name ||\n 'unknown';\n\n /**\n * Emit tool-input-start when we first see this tool call\n * (even if args is empty - the first chunk often has empty args)\n * Set dynamic: true to enable HITL approval requests\n */\n const seen = messageSeen.get(msgId);\n if (!seen?.tool?.has(toolCallId)) {\n const updatedSeen = getOrCreateMessageSeen(messageSeen, msgId);\n updatedSeen.tool ??= new Set();\n updatedSeen.tool.add(toolCallId);\n\n if (\n !hasEmittedToolCallInCurrentStep(\n state,\n toolCallId,\n eventNamespace,\n )\n ) {\n markToolCallEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId: toolCallId,\n toolName: toolName,\n dynamic: true,\n });\n }\n }\n\n /**\n * Only emit tool-input-delta when args is non-empty\n */\n if (toolCallChunk.args) {\n controller.enqueue({\n type: 'tool-input-delta',\n toolCallId: toolCallId,\n inputTextDelta: toolCallChunk.args,\n });\n }\n }\n\n return;\n }\n\n /**\n * Handle reasoning content from contentBlocks\n * Streaming chunks contain DELTA text (not accumulated), so emit directly.\n * Use reasoning block ID for deduplication as it's consistent across streaming and values events.\n *\n * Important: Early chunks may have reasoning ID but no content, later chunks may\n * have content but no reasoning ID. We capture the ID when first seen and reuse it.\n * We also immediately add to emittedReasoningIds to prevent values events from\n * emitting the same reasoning (values events can arrive between streaming chunks).\n */\n // Capture reasoning ID when we first see it (even if no content yet)\n const chunkReasoningId = extractReasoningId(msg);\n if (chunkReasoningId) {\n if (!messageReasoningIds.has(msgId)) {\n messageReasoningIds.set(msgId, chunkReasoningId);\n }\n // Immediately mark as emitted to prevent values from duplicating\n // This must happen as soon as we see the ID, before content arrives\n emittedReasoningIds.add(chunkReasoningId);\n }\n\n const reasoning = extractReasoningFromContentBlocks(msg);\n if (reasoning) {\n // Use stored reasoning ID, or current chunk's ID, or fall back to message ID\n const reasoningId =\n messageReasoningIds.get(msgId) ?? chunkReasoningId ?? msgId;\n\n const seen = messageSeen.get(msgId);\n if (!seen?.reasoning) {\n controller.enqueue({ type: 'reasoning-start', id: msgId });\n getOrCreateMessageSeen(messageSeen, msgId).reasoning = true;\n }\n\n // Streaming chunks have delta text, emit directly without slicing\n controller.enqueue({\n type: 'reasoning-delta',\n delta: reasoning,\n id: msgId,\n });\n // Also ensure the reasoning ID is marked (handles case where ID wasn't in first chunk)\n emittedReasoningIds.add(reasoningId);\n }\n\n /**\n * Handle text content\n */\n const text = getMessageText(msg);\n if (text) {\n const seen = messageSeen.get(msgId);\n if (seen?.reasoning && !seen.text) {\n controller.enqueue({ type: 'reasoning-end', id: msgId });\n seen.reasoning = false;\n }\n\n if (!seen?.text) {\n controller.enqueue({ type: 'text-start', id: msgId });\n getOrCreateMessageSeen(messageSeen, msgId).text = true;\n }\n\n controller.enqueue({\n type: 'text-delta',\n delta: text,\n id: msgId,\n });\n }\n\n const citations = extractCitationsFromContentBlocks(msg);\n if (citations.length > 0) {\n emitSourceChunks(\n citations,\n msgId,\n state.emittedSourceIds,\n controller,\n );\n }\n } else if (isToolMessageType(msg)) {\n // Handle both direct properties and serialized messages (kwargs)\n const msgObj = msg as unknown as Record<string, unknown>;\n const dataSource =\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n const toolCallId = dataSource.tool_call_id as string | undefined;\n const status = dataSource.status as string | undefined;\n\n if (toolCallId) {\n state.emittedToolOutputMessageIds.add(msgId);\n markToolOutputEmitted(state, toolCallId, eventNamespace);\n if (status === 'error') {\n // Tool execution failed\n controller.enqueue({\n type: 'tool-output-error',\n toolCallId,\n errorText:\n typeof dataSource.content === 'string'\n ? dataSource.content\n : 'Tool execution failed',\n });\n } else {\n // Tool execution succeeded\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId,\n output: dataSource.content,\n });\n }\n }\n }\n\n return;\n }\n\n case 'tools': {\n if (data == null || typeof data !== 'object' || Array.isArray(data)) {\n return;\n }\n\n const payload = data as {\n event?: unknown;\n name?: unknown;\n input?: unknown;\n data?: unknown;\n output?: unknown;\n error?: unknown;\n toolCallId?: unknown;\n };\n const toolCallId =\n typeof payload.toolCallId === 'string' ? payload.toolCallId : undefined;\n const toolName =\n typeof payload.name === 'string' ? payload.name : 'unknown';\n\n if (!toolCallId) return;\n\n const ensureToolInputLifecycle = ({\n allowPreviousStep,\n }: {\n allowPreviousStep: boolean;\n }) => {\n if (\n !hasEmittedToolCallInCurrentStep(state, toolCallId, eventNamespace)\n ) {\n if (allowPreviousStep && emittedToolCalls.has(toolCallId)) {\n return;\n }\n\n markToolCallEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId,\n toolName,\n dynamic: true,\n });\n }\n\n if (\n !hasEmittedToolInputInCurrentStep(state, toolCallId, eventNamespace)\n ) {\n markToolInputEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-input-available',\n toolCallId,\n toolName,\n input: payload.input,\n dynamic: true,\n });\n }\n };\n\n switch (payload.event) {\n case 'on_tool_start': {\n const toolCallKey = `${toolName}:${JSON.stringify(payload.input)}`;\n emittedToolCallsByKey.set(toolCallKey, toolCallId);\n\n ensureToolInputLifecycle({ allowPreviousStep: false });\n break;\n }\n\n case 'on_tool_event': {\n ensureToolInputLifecycle({ allowPreviousStep: true });\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId,\n output: payload.data,\n preliminary: true,\n });\n break;\n }\n\n case 'on_tool_end': {\n ensureToolInputLifecycle({ allowPreviousStep: true });\n markToolOutputEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId,\n output: payload.output,\n });\n break;\n }\n\n case 'on_tool_error': {\n ensureToolInputLifecycle({ allowPreviousStep: true });\n markToolOutputEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-output-error',\n toolCallId,\n errorText: formatToolError(payload.error),\n });\n break;\n }\n }\n\n return;\n }\n\n case 'values': {\n /**\n * Finalize all pending message chunks\n */\n for (const [id, seen] of messageSeen) {\n const messageNamespace = getLangGraphNamespaceKey(\n state.messageNamespaces.get(id),\n );\n if (seen.text) controller.enqueue({ type: 'text-end', id });\n if (seen.tool) {\n for (const toolCallId of seen.tool) {\n const concatMsg = messageConcat.get(id);\n const toolCall = concatMsg?.tool_calls?.find(\n call => call.id === toolCallId,\n );\n\n if (toolCall) {\n markToolCallEmitted(state, toolCallId, messageNamespace);\n // Store mapping for HITL interrupt lookup\n const toolCallKey = `${toolCall.name}:${JSON.stringify(toolCall.args)}`;\n emittedToolCallsByKey.set(toolCallKey, toolCallId);\n if (\n !hasEmittedToolInputInCurrentStep(\n state,\n toolCallId,\n messageNamespace,\n )\n ) {\n markToolInputEmitted(state, toolCallId, messageNamespace);\n controller.enqueue({\n type: 'tool-input-available',\n toolCallId,\n toolName: toolCall.name,\n input: toolCall.args,\n dynamic: true,\n });\n }\n }\n }\n }\n\n if (seen.reasoning) {\n controller.enqueue({ type: 'reasoning-end', id });\n }\n\n messageSeen.delete(id);\n state.messageNamespaces.delete(id);\n messageConcat.delete(id);\n messageReasoningIds.delete(id);\n }\n\n /**\n * Also check for tool calls in the final state that weren't streamed\n * This handles cases where tool calls appear directly in values without being in messages events\n */\n if (data != null && typeof data === 'object' && 'messages' in data) {\n const messages = (data as { messages?: unknown[] }).messages;\n if (Array.isArray(messages)) {\n /**\n * First pass: Collect all tool call IDs that have been responded to by\n * ToolMessages. Calls followed by another non-tool message are historical,\n * while trailing ToolMessages can be the only evidence of a completed call\n * when the node is tagged with `nostream`.\n */\n const completedToolCallIds = new Set<string>();\n const trailingToolMessages = new Map<\n string,\n {\n data: Record<string, unknown>;\n outputId: string;\n }\n >();\n let trailingToolMessageStart = messages.length;\n while (\n trailingToolMessageStart > 0 &&\n isToolMessageType(messages[trailingToolMessageStart - 1])\n ) {\n trailingToolMessageStart--;\n }\n\n for (const [index, msg] of messages.entries()) {\n if (!msg || typeof msg !== 'object') continue;\n\n if (isToolMessageType(msg)) {\n // Handle both direct properties and serialized messages (kwargs)\n const msgObj = msg as unknown as Record<string, unknown>;\n const dataSource =\n msgObj.type === 'constructor' &&\n msgObj.kwargs &&\n typeof msgObj.kwargs === 'object'\n ? (msgObj.kwargs as Record<string, unknown>)\n : msgObj;\n\n const toolCallId = dataSource.tool_call_id as string | undefined;\n if (toolCallId) {\n completedToolCallIds.add(toolCallId);\n if (index >= trailingToolMessageStart) {\n trailingToolMessages.set(toolCallId, {\n data: dataSource,\n outputId: getMessageId(msg) ?? `${toolCallId}:${index}`,\n });\n }\n }\n }\n }\n\n /**\n * Second pass: Process messages and emit tool events for new tool calls,\n * including calls completed by trailing ToolMessages that were not streamed.\n */\n for (const msg of messages) {\n if (!msg || typeof msg !== 'object') continue;\n\n // Use getMessageId to handle both class instances and serialized messages\n const msgId = getMessageId(msg);\n if (!msgId) continue;\n\n /**\n * Check if this is an AI message with tool calls\n */\n let toolCalls: ToolCall[] | undefined;\n\n /**\n * For class instances\n */\n if (AIMessageChunk.isInstance(msg) || AIMessage.isInstance(msg)) {\n toolCalls = msg.tool_calls;\n } else if (isPlainMessageObject(msg)) {\n /**\n * For plain objects from RemoteGraph API or serialized LangChain messages\n */\n const messageRecord = msg as Record<string, unknown>;\n\n /**\n * Determine the data source (handle both direct and serialized formats)\n */\n const isSerializedFormat =\n messageRecord.type === 'constructor' &&\n Array.isArray(messageRecord.id) &&\n ((messageRecord.id as string[]).includes('AIMessageChunk') ||\n (messageRecord.id as string[]).includes('AIMessage'));\n const dataSource = isSerializedFormat\n ? (messageRecord.kwargs as Record<string, unknown>)\n : messageRecord;\n\n if (\n messageRecord.type === 'ai' ||\n messageRecord.type === 'AIMessageChunk' ||\n isSerializedFormat\n ) {\n /**\n * Try tool_calls first (normalized format)\n */\n if (Array.isArray(dataSource?.tool_calls)) {\n toolCalls = dataSource.tool_calls as ToolCall[];\n } else if (\n /**\n * Fall back to additional_kwargs.tool_calls (OpenAI format)\n */\n dataSource?.additional_kwargs &&\n typeof dataSource.additional_kwargs === 'object'\n ) {\n const additionalKwargs =\n dataSource.additional_kwargs as Record<string, unknown>;\n if (Array.isArray(additionalKwargs.tool_calls)) {\n /**\n * Convert OpenAI format to normalized format\n */\n toolCalls = (\n additionalKwargs.tool_calls as Array<{\n id?: string;\n function?: { name?: string; arguments?: string };\n }>\n ).map((tc, idx) => {\n const functionData = tc.function;\n let args: unknown;\n try {\n args = functionData?.arguments\n ? JSON.parse(functionData.arguments)\n : {};\n } catch {\n args = {};\n }\n return {\n id: tc.id || `call_${idx}`,\n name: functionData?.name || 'unknown',\n args,\n } as ToolCall;\n });\n }\n }\n }\n }\n\n if (toolCalls && toolCalls.length > 0) {\n for (const toolCall of toolCalls) {\n const messageNamespace = findMessageCurrentStepNamespace(\n state,\n msgId,\n );\n const lifecycleNamespace = messageNamespace ?? eventNamespace;\n const wasObservedInCurrentStep = messageNamespace !== undefined;\n const wasToolCallEmittedInCurrentStep = toolCall.id\n ? hasEmittedToolCallInCurrentStep(\n state,\n toolCall.id,\n lifecycleNamespace,\n )\n : false;\n const trailingToolMessageInfo = toolCall.id\n ? trailingToolMessages.get(toolCall.id)\n : undefined;\n const canRecoverCompletedToolCall =\n wasObservedInCurrentStep || wasToolCallEmittedInCurrentStep;\n /**\n * Emit tool calls recovered from a message in the current step,\n * even when a prior step used the same provider-scoped ID.\n * Otherwise, preserve stream-wide suppression for historical calls\n * while recovering completed calls observed in the current step or\n * an earlier values snapshot before their trailing ToolMessage arrived.\n */\n if (\n toolCall.id &&\n !wasToolCallEmittedInCurrentStep &&\n (wasObservedInCurrentStep ||\n (!emittedToolCalls.has(toolCall.id) &&\n !completedToolCallIds.has(toolCall.id)))\n ) {\n markToolCallEmitted(state, toolCall.id, lifecycleNamespace);\n // Store mapping for HITL interrupt lookup\n const toolCallKey = `${toolCall.name}:${JSON.stringify(toolCall.args)}`;\n emittedToolCallsByKey.set(toolCallKey, toolCall.id);\n /**\n * Emit tool-input-start first to ensure proper lifecycle.\n * Tool calls that weren't streamed (no tool_call_chunks) need\n * the start event before tool-input-available.\n */\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId: toolCall.id,\n toolName: toolCall.name,\n dynamic: true,\n });\n markToolInputEmitted(state, toolCall.id, lifecycleNamespace);\n controller.enqueue({\n type: 'tool-input-available',\n toolCallId: toolCall.id,\n toolName: toolCall.name,\n input: toolCall.args,\n dynamic: true,\n });\n } else if (toolCall.id && emittedToolCalls.has(toolCall.id)) {\n // Register key mapping for tool calls already emitted via messages mode\n // so that __interrupt__ handling can match them by key\n const toolCallKey = `${toolCall.name}:${JSON.stringify(toolCall.args)}`;\n emittedToolCallsByKey.set(toolCallKey, toolCall.id);\n }\n\n if (\n toolCall.id &&\n trailingToolMessageInfo != null &&\n !state.emittedToolOutputMessageIds.has(\n trailingToolMessageInfo.outputId,\n ) &&\n !hasEmittedToolOutputInCurrentStep(\n state,\n toolCall.id,\n lifecycleNamespace,\n ) &&\n canRecoverCompletedToolCall\n ) {\n state.emittedToolOutputMessageIds.add(\n trailingToolMessageInfo.outputId,\n );\n markToolOutputEmitted(state, toolCall.id, lifecycleNamespace);\n const trailingToolMessage = trailingToolMessageInfo.data;\n if (trailingToolMessage.status === 'error') {\n controller.enqueue({\n type: 'tool-output-error',\n toolCallId: toolCall.id,\n errorText:\n typeof trailingToolMessage.content === 'string'\n ? trailingToolMessage.content\n : 'Tool execution failed',\n });\n } else {\n controller.enqueue({\n type: 'tool-output-available',\n toolCallId: toolCall.id,\n output: trailingToolMessage.content,\n });\n }\n }\n }\n }\n\n /**\n * Check for reasoning content that wasn't streamed\n * Use reasoning block ID for deduplication as it's consistent across streaming and values.\n *\n * IMPORTANT: Handle two cases differently:\n * 1. Message has reasoning WITHOUT tool_calls → emit reasoning (pure reasoning case)\n * 2. Message has reasoning WITH tool_calls → only emit if streamed this request\n * (When resuming from HITL interrupt, historical messages have both reasoning\n * AND tool_calls. We skip those to avoid duplicate reasoning entries.)\n */\n const reasoningId = extractReasoningId(msg);\n const wasStreamedThisRequest = messageSeen.has(msgId);\n const hasToolCalls = toolCalls && toolCalls.length > 0;\n\n /**\n * Determine if we should emit reasoning:\n * - If we already emitted this reasoning ID, skip\n * - If the message was streamed this request, emit (normal flow)\n * - If NOT streamed but has NO tool_calls, emit (pure reasoning in values case)\n * - If NOT streamed but HAS tool_calls, skip (historical HITL message)\n */\n const shouldEmitReasoning =\n reasoningId &&\n !emittedReasoningIds.has(reasoningId) &&\n (wasStreamedThisRequest || !hasToolCalls);\n\n if (shouldEmitReasoning) {\n /**\n * Use extractReasoningFromValuesMessage which extracts from response_metadata.output\n * This is the full accumulated reasoning, not deltas\n */\n const reasoning = extractReasoningFromValuesMessage(msg);\n\n if (reasoning) {\n controller.enqueue({ type: 'reasoning-start', id: msgId });\n controller.enqueue({\n type: 'reasoning-delta',\n delta: reasoning,\n id: msgId,\n });\n controller.enqueue({ type: 'reasoning-end', id: msgId });\n emittedReasoningIds.add(reasoningId);\n }\n }\n\n const valuesCitations = extractCitationsFromContentBlocks(msg);\n if (valuesCitations.length > 0) {\n emitSourceChunks(\n valuesCitations,\n msgId,\n state.emittedSourceIds,\n controller,\n );\n }\n }\n }\n }\n\n /**\n * Handle Human-in-the-Loop interrupts\n * When HITL middleware pauses execution, the interrupt data is in __interrupt__\n * Note: This is outside the 'messages' check because interrupt can come as a separate event\n */\n if (data != null && typeof data === 'object') {\n const interrupt = (data as Record<string, unknown>).__interrupt__;\n if (Array.isArray(interrupt) && interrupt.length > 0) {\n for (const interruptItem of interrupt) {\n const interruptValue = (interruptItem as { value?: unknown })\n ?.value as Record<string, unknown> | undefined;\n\n if (!interruptValue) continue;\n\n /**\n * Support both camelCase (JS SDK) and snake_case (Python SDK)\n */\n const actionRequests = (interruptValue.actionRequests ||\n interruptValue.action_requests) as\n | Array<{\n name: string;\n args?: Record<string, unknown>; // JS SDK uses 'args'\n arguments?: Record<string, unknown>; // Python SDK uses 'arguments'\n id?: string;\n }>\n | undefined;\n\n if (!Array.isArray(actionRequests)) continue;\n\n for (const actionRequest of actionRequests) {\n const toolName = actionRequest.name;\n /**\n * Support both 'args' (JS SDK) and 'arguments' (Python SDK)\n */\n const input = actionRequest.args || actionRequest.arguments;\n\n /**\n * Look up the original tool call ID using the name+args key\n * Fall back to action request ID or generate one if not found\n */\n const toolCallKey = `${toolName}:${JSON.stringify(input)}`;\n const toolCallId =\n emittedToolCallsByKey.get(toolCallKey) ||\n actionRequest.id ||\n `hitl-${toolName}-${Date.now()}`;\n\n /**\n * First emit tool-input-start then tool-input-available\n * so the UI knows what tool is being called with proper lifecycle\n */\n if (!emittedToolCalls.has(toolCallId)) {\n markToolCallEmitted(state, toolCallId, eventNamespace);\n emittedToolCallsByKey.set(toolCallKey, toolCallId);\n controller.enqueue({\n type: 'tool-input-start',\n toolCallId,\n toolName,\n dynamic: true,\n });\n markToolInputEmitted(state, toolCallId, eventNamespace);\n controller.enqueue({\n type: 'tool-input-available',\n toolCallId,\n toolName,\n input,\n dynamic: true,\n });\n }\n\n /**\n * Then emit tool-approval-request to mark it as awaiting approval\n */\n controller.enqueue({\n type: 'tool-approval-request',\n approvalId: toolCallId,\n toolCallId,\n });\n }\n }\n }\n }\n\n break;\n }\n }\n}\n","import type { AIMessageChunk } from '@langchain/core/messages';\nimport type {\n UIMessage,\n UIMessageChunk,\n ChatTransport,\n ChatRequestOptions,\n} from 'ai';\nimport {\n RemoteGraph,\n type RemoteGraphParams,\n} from '@langchain/langgraph/remote';\nimport { toBaseMessages, toUIMessageStream } from './adapter';\n\n/**\n * Options for configuring a LangSmith deployment transport.\n * Extends RemoteGraphParams but makes graphId optional (defaults to 'agent').\n */\nexport type LangSmithDeploymentTransportOptions = Omit<\n RemoteGraphParams,\n 'graphId'\n> & {\n /**\n * The ID of the graph to connect to.\n * @default 'agent'\n */\n graphId?: string;\n};\n\n/**\n * A ChatTransport implementation for LangSmith/LangGraph deployments.\n *\n * This transport enables seamless integration between the AI SDK's useChat hook\n * and LangSmith deployed LangGraph agents.\n *\n * @example\n * ```ts\n * import { LangSmithDeploymentTransport } from '@ai-sdk/langchain';\n *\n * // Use with useChat\n * const { messages, input, handleSubmit } = useChat({\n * transport: new LangSmithDeploymentTransport({\n * url: 'https://your-deployment.us.langgraph.app',\n * apiKey: 'my-api-key',\n * }),\n * });\n * ```\n */\nexport class LangSmithDeploymentTransport<\n UI_MESSAGE extends UIMessage,\n> implements ChatTransport<UI_MESSAGE> {\n protected graph: RemoteGraph;\n\n constructor(options: LangSmithDeploymentTransportOptions) {\n this.graph = new RemoteGraph({\n ...options,\n graphId: options.graphId ?? 'agent',\n });\n }\n\n async sendMessages(\n options: {\n trigger: 'submit-message' | 'regenerate-message';\n chatId: string;\n messageId: string | undefined;\n messages: UI_MESSAGE[];\n abortSignal: AbortSignal | undefined;\n } & ChatRequestOptions,\n ): Promise<ReadableStream<UIMessageChunk>> {\n const baseMessages = await toBaseMessages(options.messages);\n\n const stream = await this.graph.stream(\n { messages: baseMessages },\n { streamMode: ['values', 'messages'] },\n );\n\n return toUIMessageStream(\n stream as AsyncIterable<AIMessageChunk> | ReadableStream,\n );\n }\n\n async reconnectToStream(\n _options: {\n chatId: string;\n } & ChatRequestOptions,\n ): Promise<ReadableStream<UIMessageChunk> | null> {\n throw new Error('Method not implemented.');\n }\n}\n"],"mappings":"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","names":["providerMetadata"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ai-sdk/langchain",
3
- "version": "3.0.113",
3
+ "version": "3.0.116",
4
4
  "type": "module",
5
5
  "license": "Apache-2.0",
6
6
  "sideEffects": false,
@@ -25,10 +25,10 @@
25
25
  }
26
26
  },
27
27
  "dependencies": {
28
- "ai": "7.0.113"
28
+ "ai": "7.0.116"
29
29
  },
30
30
  "devDependencies": {
31
- "@ai-sdk/provider-utils": "5.0.47",
31
+ "@ai-sdk/provider-utils": "5.0.49",
32
32
  "@langchain/core": "^1.1.46",
33
33
  "@langchain/langgraph": "^1.3.0",
34
34
  "@types/node": "22.19.19",