@friendliai/ai-provider 1.1.3 → 1.1.5

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,18 @@
1
1
  # @friendliai/ai-provider
2
2
 
3
+ ## 1.1.5
4
+
5
+ ### Patch Changes
6
+
7
+ - f09ec79: Remove EXAONE-4.0.1 from FSE model list
8
+
9
+ ## 1.1.4
10
+
11
+ ### Patch Changes
12
+
13
+ - f97fb70: Remove K-EXAONE from FSE model list
14
+ - 3664158: Improve AI SDK compatibility in @friendliai/ai-provider by updating core SDK dependencies, wrapping Friendli JSON envelope chat errors as APICallError, and aligning chat usage and tool streaming events.
15
+
3
16
  ## 1.1.3
4
17
 
5
18
  ### Patch Changes
package/dist/index.d.mts CHANGED
@@ -12,7 +12,7 @@ declare const friendliaiErrorSchema: z.ZodUnion<readonly [z.ZodObject<{
12
12
  }, z.core.$strip>]>;
13
13
  type FriendliAIErrorData = z.infer<typeof friendliaiErrorSchema>;
14
14
 
15
- declare const FriendliAIServerlessModelIds: readonly ["LGAI-EXAONE/K-EXAONE-236B-A23B", "MiniMaxAI/MiniMax-M2.5", "MiniMaxAI/MiniMax-M2.1", "zai-org/GLM-5", "zai-org/GLM-4.7", "zai-org/GLM-4.6", "LGAI-EXAONE/EXAONE-4.0.1-32B", "deepseek-ai/DeepSeek-V3.1", "meta-llama/Llama-4-Maverick-17B-128E-Instruct", "meta-llama/Llama-4-Scout-17B-16E-Instruct", "meta-llama/Llama-3.3-70B-Instruct", "meta-llama-3.3-70b-instruct", "meta-llama/Llama-3.1-8B-Instruct", "meta-llama-3.1-8b-instruct", "Qwen/Qwen3-235B-A22B-Thinking-2507", "Qwen/Qwen3-235B-A22B-Instruct-2507", "Qwen/Qwen3-30B-A3B", "Qwen/Qwen3-32B"];
15
+ declare const FriendliAIServerlessModelIds: readonly ["MiniMaxAI/MiniMax-M2.5", "MiniMaxAI/MiniMax-M2.1", "zai-org/GLM-5", "zai-org/GLM-4.7", "zai-org/GLM-4.6", "meta-llama/Llama-4-Maverick-17B-128E-Instruct", "meta-llama/Llama-4-Scout-17B-16E-Instruct", "meta-llama/Llama-3.3-70B-Instruct", "meta-llama-3.3-70b-instruct", "meta-llama/Llama-3.1-8B-Instruct", "meta-llama-3.1-8b-instruct", "Qwen/Qwen3-235B-A22B-Thinking-2507", "Qwen/Qwen3-235B-A22B-Instruct-2507", "Qwen/Qwen3-30B-A3B", "Qwen/Qwen3-32B", "deepseek-ai/DeepSeek-V3.1"];
16
16
  type FriendliAIServerlessModelId = (typeof FriendliAIServerlessModelIds)[number];
17
17
  type FriendliAILanguageModelId = FriendliAIServerlessModelId | (string & {});
18
18
 
package/dist/index.d.ts CHANGED
@@ -12,7 +12,7 @@ declare const friendliaiErrorSchema: z.ZodUnion<readonly [z.ZodObject<{
12
12
  }, z.core.$strip>]>;
13
13
  type FriendliAIErrorData = z.infer<typeof friendliaiErrorSchema>;
14
14
 
15
- declare const FriendliAIServerlessModelIds: readonly ["LGAI-EXAONE/K-EXAONE-236B-A23B", "MiniMaxAI/MiniMax-M2.5", "MiniMaxAI/MiniMax-M2.1", "zai-org/GLM-5", "zai-org/GLM-4.7", "zai-org/GLM-4.6", "LGAI-EXAONE/EXAONE-4.0.1-32B", "deepseek-ai/DeepSeek-V3.1", "meta-llama/Llama-4-Maverick-17B-128E-Instruct", "meta-llama/Llama-4-Scout-17B-16E-Instruct", "meta-llama/Llama-3.3-70B-Instruct", "meta-llama-3.3-70b-instruct", "meta-llama/Llama-3.1-8B-Instruct", "meta-llama-3.1-8b-instruct", "Qwen/Qwen3-235B-A22B-Thinking-2507", "Qwen/Qwen3-235B-A22B-Instruct-2507", "Qwen/Qwen3-30B-A3B", "Qwen/Qwen3-32B"];
15
+ declare const FriendliAIServerlessModelIds: readonly ["MiniMaxAI/MiniMax-M2.5", "MiniMaxAI/MiniMax-M2.1", "zai-org/GLM-5", "zai-org/GLM-4.7", "zai-org/GLM-4.6", "meta-llama/Llama-4-Maverick-17B-128E-Instruct", "meta-llama/Llama-4-Scout-17B-16E-Instruct", "meta-llama/Llama-3.3-70B-Instruct", "meta-llama-3.3-70b-instruct", "meta-llama/Llama-3.1-8B-Instruct", "meta-llama-3.1-8b-instruct", "Qwen/Qwen3-235B-A22B-Thinking-2507", "Qwen/Qwen3-235B-A22B-Instruct-2507", "Qwen/Qwen3-30B-A3B", "Qwen/Qwen3-32B", "deepseek-ai/DeepSeek-V3.1"];
16
16
  type FriendliAIServerlessModelId = (typeof FriendliAIServerlessModelIds)[number];
17
17
  type FriendliAILanguageModelId = FriendliAIServerlessModelId | (string & {});
18
18
 
package/dist/index.js CHANGED
@@ -119,6 +119,33 @@ var friendliaiFailedResponseHandler = async ({
119
119
  })
120
120
  };
121
121
  };
122
+ var tryWrapFriendliJsonEnvelopeError = async (error) => {
123
+ if (!import_provider.APICallError.isInstance(error)) {
124
+ return void 0;
125
+ }
126
+ const responseBody = error.responseBody;
127
+ if (typeof responseBody !== "string" || responseBody.trim() === "") {
128
+ return void 0;
129
+ }
130
+ const parsedError = await (0, import_provider_utils.safeParseJSON)({
131
+ text: responseBody,
132
+ schema: friendliaiErrorSchema
133
+ });
134
+ if (!parsedError.success) {
135
+ return void 0;
136
+ }
137
+ return new import_provider.APICallError({
138
+ message: friendliaiErrorStructure.errorToMessage(parsedError.value),
139
+ url: error.url,
140
+ requestBodyValues: error.requestBodyValues,
141
+ statusCode: error.statusCode,
142
+ responseHeaders: error.responseHeaders,
143
+ responseBody: error.responseBody,
144
+ cause: error,
145
+ isRetryable: error.isRetryable,
146
+ data: parsedError.value
147
+ });
148
+ };
122
149
 
123
150
  // src/friendli-prepare-tools.ts
124
151
  var import_provider2 = require("@ai-sdk/provider");
@@ -343,25 +370,32 @@ var FriendliAIChatLanguageModel = class {
343
370
  };
344
371
  }
345
372
  async doGenerate(options) {
346
- var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l;
373
+ var _a, _b;
347
374
  const { args, warnings } = await this.getArgs({ ...options, stream: false });
348
375
  const body = JSON.stringify(args);
349
- const {
350
- responseHeaders,
351
- value: responseBody,
352
- rawValue: rawResponse
353
- } = await (0, import_provider_utils2.postJsonToApi)({
354
- url: this.config.url({
355
- path: "/chat/completions",
356
- modelId: this.modelId
357
- }),
358
- headers: (0, import_provider_utils2.combineHeaders)(this.config.headers(), options.headers),
359
- body: args,
360
- failedResponseHandler: this.failedResponseHandler,
361
- successfulResponseHandler: (0, import_provider_utils2.createJsonResponseHandler)(OpenAICompatibleChatResponseSchema),
362
- abortSignal: options.abortSignal,
363
- fetch: this.config.fetch
364
- });
376
+ const response = await (async () => {
377
+ try {
378
+ return await (0, import_provider_utils2.postJsonToApi)({
379
+ url: this.config.url({
380
+ path: "/chat/completions",
381
+ modelId: this.modelId
382
+ }),
383
+ headers: (0, import_provider_utils2.combineHeaders)(this.config.headers(), options.headers),
384
+ body: args,
385
+ failedResponseHandler: this.failedResponseHandler,
386
+ successfulResponseHandler: (0, import_provider_utils2.createJsonResponseHandler)(OpenAICompatibleChatResponseSchema),
387
+ abortSignal: options.abortSignal,
388
+ fetch: this.config.fetch
389
+ });
390
+ } catch (error) {
391
+ const wrappedError = await tryWrapFriendliJsonEnvelopeError(error);
392
+ if (wrappedError != null) {
393
+ throw wrappedError;
394
+ }
395
+ throw error;
396
+ }
397
+ })();
398
+ const { responseHeaders, value: responseBody, rawValue: rawResponse } = response;
365
399
  const choice = responseBody.choices[0];
366
400
  const content = [];
367
401
  const text = choice.message.content;
@@ -391,19 +425,7 @@ var FriendliAIChatLanguageModel = class {
391
425
  unified: (0, import_internal.mapOpenAICompatibleFinishReason)(choice.finish_reason),
392
426
  raw: (_b = choice.finish_reason) != null ? _b : void 0
393
427
  },
394
- usage: {
395
- inputTokens: {
396
- total: (_d = (_c = responseBody.usage) == null ? void 0 : _c.prompt_tokens) != null ? _d : void 0,
397
- noCache: void 0,
398
- cacheRead: (_g = (_f = (_e = responseBody.usage) == null ? void 0 : _e.prompt_tokens_details) == null ? void 0 : _f.cached_tokens) != null ? _g : void 0,
399
- cacheWrite: void 0
400
- },
401
- outputTokens: {
402
- total: (_i = (_h = responseBody.usage) == null ? void 0 : _h.completion_tokens) != null ? _i : void 0,
403
- text: void 0,
404
- reasoning: (_l = (_k = (_j = responseBody.usage) == null ? void 0 : _j.completion_tokens_details) == null ? void 0 : _k.reasoning_tokens) != null ? _l : void 0
405
- }
406
- },
428
+ usage: (0, import_internal.convertOpenAICompatibleChatUsage)(responseBody.usage),
407
429
  // providerMetadata,
408
430
  request: { body },
409
431
  response: {
@@ -441,19 +463,7 @@ var FriendliAIChatLanguageModel = class {
441
463
  unified: "other",
442
464
  raw: void 0
443
465
  };
444
- const usage = {
445
- completionTokens: void 0,
446
- completionTokensDetails: {
447
- reasoningTokens: void 0,
448
- acceptedPredictionTokens: void 0,
449
- rejectedPredictionTokens: void 0
450
- },
451
- promptTokens: void 0,
452
- promptTokensDetails: {
453
- cachedTokens: void 0
454
- },
455
- totalTokens: void 0
456
- };
466
+ let usage = void 0;
457
467
  let isFirstChunk = true;
458
468
  const providerOptionsName = "friendliai";
459
469
  let currentTextId = null;
@@ -468,6 +478,9 @@ var FriendliAIChatLanguageModel = class {
468
478
  // We narrow with type guards for safe handling.
469
479
  transform(chunk, controller) {
470
480
  var _a2, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n, _o, _p, _q;
481
+ if (options.includeRawChunks) {
482
+ controller.enqueue({ type: "raw", rawValue: chunk.rawValue });
483
+ }
471
484
  if (!chunk.success) {
472
485
  finishReason = { unified: "error", raw: void 0 };
473
486
  controller.enqueue({ type: "error", error: chunk.error });
@@ -541,28 +554,7 @@ var FriendliAIChatLanguageModel = class {
541
554
  });
542
555
  }
543
556
  if (chunkValue.usage != null) {
544
- const {
545
- prompt_tokens,
546
- completion_tokens,
547
- total_tokens,
548
- prompt_tokens_details,
549
- completion_tokens_details
550
- } = chunkValue.usage;
551
- usage.promptTokens = prompt_tokens != null ? prompt_tokens : void 0;
552
- usage.completionTokens = completion_tokens != null ? completion_tokens : void 0;
553
- usage.totalTokens = total_tokens != null ? total_tokens : void 0;
554
- if ((completion_tokens_details == null ? void 0 : completion_tokens_details.reasoning_tokens) != null) {
555
- usage.completionTokensDetails.reasoningTokens = completion_tokens_details == null ? void 0 : completion_tokens_details.reasoning_tokens;
556
- }
557
- if ((completion_tokens_details == null ? void 0 : completion_tokens_details.accepted_prediction_tokens) != null) {
558
- usage.completionTokensDetails.acceptedPredictionTokens = completion_tokens_details == null ? void 0 : completion_tokens_details.accepted_prediction_tokens;
559
- }
560
- if ((completion_tokens_details == null ? void 0 : completion_tokens_details.rejected_prediction_tokens) != null) {
561
- usage.completionTokensDetails.rejectedPredictionTokens = completion_tokens_details == null ? void 0 : completion_tokens_details.rejected_prediction_tokens;
562
- }
563
- if ((prompt_tokens_details == null ? void 0 : prompt_tokens_details.cached_tokens) != null) {
564
- usage.promptTokensDetails.cachedTokens = prompt_tokens_details == null ? void 0 : prompt_tokens_details.cached_tokens;
565
- }
557
+ usage = chunkValue.usage;
566
558
  }
567
559
  const choice = chunkValue.choices[0];
568
560
  if ((choice == null ? void 0 : choice.finish_reason) != null) {
@@ -634,6 +626,11 @@ var FriendliAIChatLanguageModel = class {
634
626
  },
635
627
  hasFinished: false
636
628
  };
629
+ controller.enqueue({
630
+ type: "tool-input-start",
631
+ id: toolCallDelta.id,
632
+ toolName: toolCallDelta.function.name
633
+ });
637
634
  const toolCall2 = toolCalls[index];
638
635
  if (((_g = toolCall2.function) == null ? void 0 : _g.name) != null && ((_h = toolCall2.function) == null ? void 0 : _h.arguments) != null) {
639
636
  if (toolCall2.function.arguments.length > 0) {
@@ -644,6 +641,10 @@ var FriendliAIChatLanguageModel = class {
644
641
  });
645
642
  }
646
643
  if ((0, import_provider_utils2.isParsableJson)(toolCall2.function.arguments)) {
644
+ controller.enqueue({
645
+ type: "tool-input-end",
646
+ id: toolCall2.id
647
+ });
647
648
  controller.enqueue({
648
649
  type: "tool-call",
649
650
  toolCallId: (_i = toolCall2.id) != null ? _i : (0, import_provider_utils2.generateId)(),
@@ -668,6 +669,10 @@ var FriendliAIChatLanguageModel = class {
668
669
  delta: (_n = (_m = toolCallDelta.function) == null ? void 0 : _m.arguments) != null ? _n : ""
669
670
  });
670
671
  if (((_o = toolCall.function) == null ? void 0 : _o.name) != null && ((_p = toolCall.function) == null ? void 0 : _p.arguments) != null && (0, import_provider_utils2.isParsableJson)(toolCall.function.arguments)) {
672
+ controller.enqueue({
673
+ type: "tool-input-end",
674
+ id: toolCall.id
675
+ });
671
676
  controller.enqueue({
672
677
  type: "tool-call",
673
678
  toolCallId: (_q = toolCall.id) != null ? _q : (0, import_provider_utils2.generateId)(),
@@ -680,7 +685,7 @@ var FriendliAIChatLanguageModel = class {
680
685
  }
681
686
  },
682
687
  flush(controller) {
683
- var _a2, _b, _c, _d;
688
+ var _a2, _b, _c;
684
689
  if (currentReasoningId != null) {
685
690
  controller.enqueue({
686
691
  type: "reasoning-end",
@@ -693,32 +698,34 @@ var FriendliAIChatLanguageModel = class {
693
698
  id: currentTextId
694
699
  });
695
700
  }
701
+ for (const toolCall of toolCalls.filter(
702
+ (pendingToolCall) => !pendingToolCall.hasFinished
703
+ )) {
704
+ controller.enqueue({
705
+ type: "tool-input-end",
706
+ id: toolCall.id
707
+ });
708
+ controller.enqueue({
709
+ type: "tool-call",
710
+ toolCallId: (_a2 = toolCall.id) != null ? _a2 : (0, import_provider_utils2.generateId)(),
711
+ toolName: toolCall.function.name,
712
+ input: toolCall.function.arguments
713
+ });
714
+ }
696
715
  const providerMetadata = {
697
716
  [providerOptionsName]: {},
698
717
  ...metadataExtractor == null ? void 0 : metadataExtractor.buildMetadata()
699
718
  };
700
- if (usage.completionTokensDetails.acceptedPredictionTokens != null) {
701
- providerMetadata[providerOptionsName].acceptedPredictionTokens = usage.completionTokensDetails.acceptedPredictionTokens;
719
+ if (((_b = usage == null ? void 0 : usage.completion_tokens_details) == null ? void 0 : _b.accepted_prediction_tokens) != null) {
720
+ providerMetadata[providerOptionsName].acceptedPredictionTokens = usage.completion_tokens_details.accepted_prediction_tokens;
702
721
  }
703
- if (usage.completionTokensDetails.rejectedPredictionTokens != null) {
704
- providerMetadata[providerOptionsName].rejectedPredictionTokens = usage.completionTokensDetails.rejectedPredictionTokens;
722
+ if (((_c = usage == null ? void 0 : usage.completion_tokens_details) == null ? void 0 : _c.rejected_prediction_tokens) != null) {
723
+ providerMetadata[providerOptionsName].rejectedPredictionTokens = usage.completion_tokens_details.rejected_prediction_tokens;
705
724
  }
706
725
  controller.enqueue({
707
726
  type: "finish",
708
727
  finishReason,
709
- usage: {
710
- inputTokens: {
711
- total: (_a2 = usage.promptTokens) != null ? _a2 : void 0,
712
- noCache: void 0,
713
- cacheRead: (_b = usage.promptTokensDetails.cachedTokens) != null ? _b : void 0,
714
- cacheWrite: void 0
715
- },
716
- outputTokens: {
717
- total: (_c = usage.completionTokens) != null ? _c : void 0,
718
- text: void 0,
719
- reasoning: (_d = usage.completionTokensDetails.reasoningTokens) != null ? _d : void 0
720
- }
721
- },
728
+ usage: (0, import_internal.convertOpenAICompatibleChatUsage)(usage),
722
729
  providerMetadata
723
730
  });
724
731
  }
@@ -848,14 +855,11 @@ var friendliProviderOptionsSchema = import_v4.z.object({
848
855
 
849
856
  // src/friendli-settings.ts
850
857
  var FriendliAIServerlessModelIds = [
851
- "LGAI-EXAONE/K-EXAONE-236B-A23B",
852
858
  "MiniMaxAI/MiniMax-M2.5",
853
859
  "MiniMaxAI/MiniMax-M2.1",
854
860
  "zai-org/GLM-5",
855
861
  "zai-org/GLM-4.7",
856
862
  "zai-org/GLM-4.6",
857
- "LGAI-EXAONE/EXAONE-4.0.1-32B",
858
- "deepseek-ai/DeepSeek-V3.1",
859
863
  "meta-llama/Llama-4-Maverick-17B-128E-Instruct",
860
864
  "meta-llama/Llama-4-Scout-17B-16E-Instruct",
861
865
  "meta-llama/Llama-3.3-70B-Instruct",
@@ -865,7 +869,8 @@ var FriendliAIServerlessModelIds = [
865
869
  "Qwen/Qwen3-235B-A22B-Thinking-2507",
866
870
  "Qwen/Qwen3-235B-A22B-Instruct-2507",
867
871
  "Qwen/Qwen3-30B-A3B",
868
- "Qwen/Qwen3-32B"
872
+ "Qwen/Qwen3-32B",
873
+ "deepseek-ai/DeepSeek-V3.1"
869
874
  ];
870
875
 
871
876
  // src/friendli-tools.ts