@langchain/openai 0.3.9 → 0.3.10

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.
@@ -78,9 +78,8 @@ function openAIResponseToChatMessage(message, rawResponse, includeRawResponse) {
78
78
  system_fingerprint: rawResponse.system_fingerprint,
79
79
  };
80
80
  }
81
- const content = message.audio ? [message.audio] : message.content;
82
81
  return new messages_1.AIMessage({
83
- content: content || "",
82
+ content: message.content || "",
84
83
  tool_calls: toolCalls,
85
84
  invalid_tool_calls: invalidToolCalls,
86
85
  additional_kwargs,
@@ -96,18 +95,7 @@ function _convertDeltaToMessageChunk(
96
95
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
97
96
  delta, rawResponse, defaultRole, includeRawResponse) {
98
97
  const role = delta.role ?? defaultRole;
99
- let content;
100
- if (delta.audio) {
101
- content = [
102
- {
103
- ...delta.audio,
104
- index: rawResponse.choices[0].index,
105
- },
106
- ];
107
- }
108
- else {
109
- content = delta.content ?? "";
110
- }
98
+ const content = delta.content ?? "";
111
99
  let additional_kwargs;
112
100
  if (delta.function_call) {
113
101
  additional_kwargs = {
@@ -681,43 +669,6 @@ function _convertChatOpenAIToolTypeToOpenAITool(tool, fields) {
681
669
  * </details>
682
670
  *
683
671
  * <br />
684
- *
685
- * <details>
686
- * <summary><strong>Audio Outputs</strong></summary>
687
- *
688
- * ```typescript
689
- * import { ChatOpenAI } from "@langchain/openai";
690
- *
691
- * const modelWithAudioOutput = new ChatOpenAI({
692
- * model: "gpt-4o-audio-preview",
693
- * // You may also pass these fields to `.bind` as a call argument.
694
- * modalities: ["text", "audio"], // Specifies that the model should output audio.
695
- * audio: {
696
- * voice: "alloy",
697
- * format: "wav",
698
- * },
699
- * });
700
- *
701
- * const audioOutputResult = await modelWithAudioOutput.invoke("Tell me a joke about cats.");
702
- * const castMessageContent = audioOutputResult.content[0] as Record<string, any>;
703
- *
704
- * console.log({
705
- * ...castMessageContent,
706
- * data: castMessageContent.data.slice(0, 100) // Sliced for brevity
707
- * })
708
- * ```
709
- *
710
- * ```txt
711
- * {
712
- * id: 'audio_67117718c6008190a3afad3e3054b9b6',
713
- * data: 'UklGRqYwBgBXQVZFZm10IBAAAAABAAEAwF0AAIC7AAACABAATElTVBoAAABJTkZPSVNGVA4AAABMYXZmNTguMjkuMTAwAGRhdGFg',
714
- * expires_at: 1729201448,
715
- * transcript: 'Sure! Why did the cat sit on the computer? Because it wanted to keep an eye on the mouse!'
716
- * }
717
- * ```
718
- * </details>
719
- *
720
- * <br />
721
672
  */
722
673
  class ChatOpenAI extends chat_models_1.BaseChatModel {
723
674
  static lc_name() {
@@ -961,18 +912,6 @@ class ChatOpenAI extends chat_models_1.BaseChatModel {
961
912
  writable: true,
962
913
  value: void 0
963
914
  });
964
- Object.defineProperty(this, "audio", {
965
- enumerable: true,
966
- configurable: true,
967
- writable: true,
968
- value: void 0
969
- });
970
- Object.defineProperty(this, "modalities", {
971
- enumerable: true,
972
- configurable: true,
973
- writable: true,
974
- value: void 0
975
- });
976
915
  this.openAIApiKey =
977
916
  fields?.apiKey ??
978
917
  fields?.openAIApiKey ??
@@ -1021,8 +960,6 @@ class ChatOpenAI extends chat_models_1.BaseChatModel {
1021
960
  this.stopSequences = this?.stop;
1022
961
  this.user = fields?.user;
1023
962
  this.__includeRawResponse = fields?.__includeRawResponse;
1024
- this.audio = fields?.audio;
1025
- this.modalities = fields?.modalities;
1026
963
  if (this.azureOpenAIApiKey || this.azureADTokenProvider) {
1027
964
  if (!this.azureOpenAIApiInstanceName &&
1028
965
  !this.azureOpenAIBasePath &&
@@ -1144,12 +1081,6 @@ class ChatOpenAI extends chat_models_1.BaseChatModel {
1144
1081
  seed: options?.seed,
1145
1082
  ...streamOptionsConfig,
1146
1083
  parallel_tool_calls: options?.parallel_tool_calls,
1147
- ...(this.audio || options?.audio
1148
- ? { audio: this.audio || options?.audio }
1149
- : {}),
1150
- ...(this.modalities || options?.modalities
1151
- ? { modalities: this.modalities || options?.modalities }
1152
- : {}),
1153
1084
  ...this.modelKwargs,
1154
1085
  };
1155
1086
  return params;
@@ -1185,7 +1116,7 @@ class ChatOpenAI extends chat_models_1.BaseChatModel {
1185
1116
  const streamIterable = await this.completionWithRetry(params, options);
1186
1117
  let usage;
1187
1118
  for await (const data of streamIterable) {
1188
- const choice = data?.choices?.[0];
1119
+ const choice = data?.choices[0];
1189
1120
  if (data.usage) {
1190
1121
  usage = data.usage;
1191
1122
  }
@@ -1202,6 +1133,10 @@ class ChatOpenAI extends chat_models_1.BaseChatModel {
1202
1133
  prompt: options.promptIndex ?? 0,
1203
1134
  completion: choice.index ?? 0,
1204
1135
  };
1136
+ if (typeof chunk.content !== "string") {
1137
+ console.log("[WARNING]: Received non-string content from OpenAI. This is currently not supported.");
1138
+ continue;
1139
+ }
1205
1140
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
1206
1141
  const generationInfo = { ...newTokenIndices };
1207
1142
  if (choice.finish_reason != null) {
@@ -1215,7 +1150,7 @@ class ChatOpenAI extends chat_models_1.BaseChatModel {
1215
1150
  }
1216
1151
  const generationChunk = new outputs_1.ChatGenerationChunk({
1217
1152
  message: chunk,
1218
- text: typeof chunk.content === "string" ? chunk.content : "",
1153
+ text: chunk.content,
1219
1154
  generationInfo,
1220
1155
  });
1221
1156
  yield generationChunk;
@@ -1374,8 +1309,9 @@ class ChatOpenAI extends chat_models_1.BaseChatModel {
1374
1309
  }
1375
1310
  const generations = [];
1376
1311
  for (const part of data?.choices ?? []) {
1312
+ const text = part.message?.content ?? "";
1377
1313
  const generation = {
1378
- text: part.message?.content ?? "",
1314
+ text,
1379
1315
  message: openAIResponseToChatMessage(part.message ?? { role: "assistant" }, data, this.__includeRawResponse),
1380
1316
  };
1381
1317
  generation.generationInfo = {
@@ -75,25 +75,6 @@ export interface ChatOpenAICallOptions extends OpenAICallOptions, BaseFunctionCa
75
75
  * @version 0.2.6
76
76
  */
77
77
  strict?: boolean;
78
- /**
79
- * Output types that you would like the model to generate for this request. Most
80
- * models are capable of generating text, which is the default:
81
- *
82
- * `["text"]`
83
- *
84
- * The `gpt-4o-audio-preview` model can also be used to
85
- * [generate audio](https://platform.openai.com/docs/guides/audio). To request that
86
- * this model generate both text and audio responses, you can use:
87
- *
88
- * `["text", "audio"]`
89
- */
90
- modalities?: Array<OpenAIClient.Chat.ChatCompletionModality>;
91
- /**
92
- * Parameters for audio output. Required when audio output is requested with
93
- * `modalities: ["audio"]`.
94
- * [Learn more](https://platform.openai.com/docs/guides/audio).
95
- */
96
- audio?: OpenAIClient.Chat.ChatCompletionAudioParam;
97
78
  }
98
79
  export interface ChatOpenAIFields extends Partial<OpenAIChatInput>, Partial<AzureOpenAIInput>, BaseChatModelParams {
99
80
  configuration?: ClientOptions & LegacyOpenAIInput;
@@ -559,43 +540,6 @@ export interface ChatOpenAIFields extends Partial<OpenAIChatInput>, Partial<Azur
559
540
  * </details>
560
541
  *
561
542
  * <br />
562
- *
563
- * <details>
564
- * <summary><strong>Audio Outputs</strong></summary>
565
- *
566
- * ```typescript
567
- * import { ChatOpenAI } from "@langchain/openai";
568
- *
569
- * const modelWithAudioOutput = new ChatOpenAI({
570
- * model: "gpt-4o-audio-preview",
571
- * // You may also pass these fields to `.bind` as a call argument.
572
- * modalities: ["text", "audio"], // Specifies that the model should output audio.
573
- * audio: {
574
- * voice: "alloy",
575
- * format: "wav",
576
- * },
577
- * });
578
- *
579
- * const audioOutputResult = await modelWithAudioOutput.invoke("Tell me a joke about cats.");
580
- * const castMessageContent = audioOutputResult.content[0] as Record<string, any>;
581
- *
582
- * console.log({
583
- * ...castMessageContent,
584
- * data: castMessageContent.data.slice(0, 100) // Sliced for brevity
585
- * })
586
- * ```
587
- *
588
- * ```txt
589
- * {
590
- * id: 'audio_67117718c6008190a3afad3e3054b9b6',
591
- * data: 'UklGRqYwBgBXQVZFZm10IBAAAAABAAEAwF0AAIC7AAACABAATElTVBoAAABJTkZPSVNGVA4AAABMYXZmNTguMjkuMTAwAGRhdGFg',
592
- * expires_at: 1729201448,
593
- * transcript: 'Sure! Why did the cat sit on the computer? Because it wanted to keep an eye on the mouse!'
594
- * }
595
- * ```
596
- * </details>
597
- *
598
- * <br />
599
543
  */
600
544
  export declare class ChatOpenAI<CallOptions extends ChatOpenAICallOptions = ChatOpenAICallOptions> extends BaseChatModel<CallOptions, AIMessageChunk> implements OpenAIChatInput, AzureOpenAIInput {
601
545
  static lc_name(): string;
@@ -641,8 +585,6 @@ export declare class ChatOpenAI<CallOptions extends ChatOpenAICallOptions = Chat
641
585
  * If `undefined` the `strict` argument will not be passed to OpenAI.
642
586
  */
643
587
  supportsStrictToolCalling?: boolean;
644
- audio?: OpenAIClient.Chat.ChatCompletionAudioParam;
645
- modalities?: Array<OpenAIClient.Chat.ChatCompletionModality>;
646
588
  constructor(fields?: ChatOpenAIFields,
647
589
  /** @deprecated */
648
590
  configuration?: ClientOptions & LegacyOpenAIInput);
@@ -74,9 +74,8 @@ function openAIResponseToChatMessage(message, rawResponse, includeRawResponse) {
74
74
  system_fingerprint: rawResponse.system_fingerprint,
75
75
  };
76
76
  }
77
- const content = message.audio ? [message.audio] : message.content;
78
77
  return new AIMessage({
79
- content: content || "",
78
+ content: message.content || "",
80
79
  tool_calls: toolCalls,
81
80
  invalid_tool_calls: invalidToolCalls,
82
81
  additional_kwargs,
@@ -92,18 +91,7 @@ function _convertDeltaToMessageChunk(
92
91
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
93
92
  delta, rawResponse, defaultRole, includeRawResponse) {
94
93
  const role = delta.role ?? defaultRole;
95
- let content;
96
- if (delta.audio) {
97
- content = [
98
- {
99
- ...delta.audio,
100
- index: rawResponse.choices[0].index,
101
- },
102
- ];
103
- }
104
- else {
105
- content = delta.content ?? "";
106
- }
94
+ const content = delta.content ?? "";
107
95
  let additional_kwargs;
108
96
  if (delta.function_call) {
109
97
  additional_kwargs = {
@@ -676,43 +664,6 @@ function _convertChatOpenAIToolTypeToOpenAITool(tool, fields) {
676
664
  * </details>
677
665
  *
678
666
  * <br />
679
- *
680
- * <details>
681
- * <summary><strong>Audio Outputs</strong></summary>
682
- *
683
- * ```typescript
684
- * import { ChatOpenAI } from "@langchain/openai";
685
- *
686
- * const modelWithAudioOutput = new ChatOpenAI({
687
- * model: "gpt-4o-audio-preview",
688
- * // You may also pass these fields to `.bind` as a call argument.
689
- * modalities: ["text", "audio"], // Specifies that the model should output audio.
690
- * audio: {
691
- * voice: "alloy",
692
- * format: "wav",
693
- * },
694
- * });
695
- *
696
- * const audioOutputResult = await modelWithAudioOutput.invoke("Tell me a joke about cats.");
697
- * const castMessageContent = audioOutputResult.content[0] as Record<string, any>;
698
- *
699
- * console.log({
700
- * ...castMessageContent,
701
- * data: castMessageContent.data.slice(0, 100) // Sliced for brevity
702
- * })
703
- * ```
704
- *
705
- * ```txt
706
- * {
707
- * id: 'audio_67117718c6008190a3afad3e3054b9b6',
708
- * data: 'UklGRqYwBgBXQVZFZm10IBAAAAABAAEAwF0AAIC7AAACABAATElTVBoAAABJTkZPSVNGVA4AAABMYXZmNTguMjkuMTAwAGRhdGFg',
709
- * expires_at: 1729201448,
710
- * transcript: 'Sure! Why did the cat sit on the computer? Because it wanted to keep an eye on the mouse!'
711
- * }
712
- * ```
713
- * </details>
714
- *
715
- * <br />
716
667
  */
717
668
  export class ChatOpenAI extends BaseChatModel {
718
669
  static lc_name() {
@@ -956,18 +907,6 @@ export class ChatOpenAI extends BaseChatModel {
956
907
  writable: true,
957
908
  value: void 0
958
909
  });
959
- Object.defineProperty(this, "audio", {
960
- enumerable: true,
961
- configurable: true,
962
- writable: true,
963
- value: void 0
964
- });
965
- Object.defineProperty(this, "modalities", {
966
- enumerable: true,
967
- configurable: true,
968
- writable: true,
969
- value: void 0
970
- });
971
910
  this.openAIApiKey =
972
911
  fields?.apiKey ??
973
912
  fields?.openAIApiKey ??
@@ -1016,8 +955,6 @@ export class ChatOpenAI extends BaseChatModel {
1016
955
  this.stopSequences = this?.stop;
1017
956
  this.user = fields?.user;
1018
957
  this.__includeRawResponse = fields?.__includeRawResponse;
1019
- this.audio = fields?.audio;
1020
- this.modalities = fields?.modalities;
1021
958
  if (this.azureOpenAIApiKey || this.azureADTokenProvider) {
1022
959
  if (!this.azureOpenAIApiInstanceName &&
1023
960
  !this.azureOpenAIBasePath &&
@@ -1139,12 +1076,6 @@ export class ChatOpenAI extends BaseChatModel {
1139
1076
  seed: options?.seed,
1140
1077
  ...streamOptionsConfig,
1141
1078
  parallel_tool_calls: options?.parallel_tool_calls,
1142
- ...(this.audio || options?.audio
1143
- ? { audio: this.audio || options?.audio }
1144
- : {}),
1145
- ...(this.modalities || options?.modalities
1146
- ? { modalities: this.modalities || options?.modalities }
1147
- : {}),
1148
1079
  ...this.modelKwargs,
1149
1080
  };
1150
1081
  return params;
@@ -1180,7 +1111,7 @@ export class ChatOpenAI extends BaseChatModel {
1180
1111
  const streamIterable = await this.completionWithRetry(params, options);
1181
1112
  let usage;
1182
1113
  for await (const data of streamIterable) {
1183
- const choice = data?.choices?.[0];
1114
+ const choice = data?.choices[0];
1184
1115
  if (data.usage) {
1185
1116
  usage = data.usage;
1186
1117
  }
@@ -1197,6 +1128,10 @@ export class ChatOpenAI extends BaseChatModel {
1197
1128
  prompt: options.promptIndex ?? 0,
1198
1129
  completion: choice.index ?? 0,
1199
1130
  };
1131
+ if (typeof chunk.content !== "string") {
1132
+ console.log("[WARNING]: Received non-string content from OpenAI. This is currently not supported.");
1133
+ continue;
1134
+ }
1200
1135
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
1201
1136
  const generationInfo = { ...newTokenIndices };
1202
1137
  if (choice.finish_reason != null) {
@@ -1210,7 +1145,7 @@ export class ChatOpenAI extends BaseChatModel {
1210
1145
  }
1211
1146
  const generationChunk = new ChatGenerationChunk({
1212
1147
  message: chunk,
1213
- text: typeof chunk.content === "string" ? chunk.content : "",
1148
+ text: chunk.content,
1214
1149
  generationInfo,
1215
1150
  });
1216
1151
  yield generationChunk;
@@ -1369,8 +1304,9 @@ export class ChatOpenAI extends BaseChatModel {
1369
1304
  }
1370
1305
  const generations = [];
1371
1306
  for (const part of data?.choices ?? []) {
1307
+ const text = part.message?.content ?? "";
1372
1308
  const generation = {
1373
- text: part.message?.content ?? "",
1309
+ text,
1374
1310
  message: openAIResponseToChatMessage(part.message ?? { role: "assistant" }, data, this.__includeRawResponse),
1375
1311
  };
1376
1312
  generation.generationInfo = {
package/dist/types.d.ts CHANGED
@@ -128,25 +128,6 @@ export interface OpenAIChatInput extends OpenAIBaseInput {
128
128
  * If `undefined` the `strict` argument will not be passed to OpenAI.
129
129
  */
130
130
  supportsStrictToolCalling?: boolean;
131
- /**
132
- * Output types that you would like the model to generate for this request. Most
133
- * models are capable of generating text, which is the default:
134
- *
135
- * `["text"]`
136
- *
137
- * The `gpt-4o-audio-preview` model can also be used to
138
- * [generate audio](https://platform.openai.com/docs/guides/audio). To request that
139
- * this model generate both text and audio responses, you can use:
140
- *
141
- * `["text", "audio"]`
142
- */
143
- modalities?: Array<OpenAIClient.Chat.ChatCompletionModality>;
144
- /**
145
- * Parameters for audio output. Required when audio output is requested with
146
- * `modalities: ["audio"]`.
147
- * [Learn more](https://platform.openai.com/docs/guides/audio).
148
- */
149
- audio?: OpenAIClient.Chat.ChatCompletionAudioParam;
150
131
  }
151
132
  export declare interface AzureOpenAIInput {
152
133
  /**
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@langchain/openai",
3
- "version": "0.3.9",
3
+ "version": "0.3.10",
4
4
  "description": "OpenAI integrations for LangChain.js",
5
5
  "type": "module",
6
6
  "engines": {
@@ -36,7 +36,7 @@
36
36
  "license": "MIT",
37
37
  "dependencies": {
38
38
  "js-tiktoken": "^1.0.12",
39
- "openai": "^4.68.0",
39
+ "openai": "^4.67.2",
40
40
  "zod": "^3.22.4",
41
41
  "zod-to-json-schema": "^3.22.3"
42
42
  },