@ai-sdk/anthropic 2.0.0-alpha.6 → 2.0.0-alpha.8

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/dist/index.mjs CHANGED
@@ -459,13 +459,16 @@ function groupIntoBlocks(prompt) {
459
459
  }
460
460
 
461
461
  // src/map-anthropic-stop-reason.ts
462
- function mapAnthropicStopReason(finishReason) {
462
+ function mapAnthropicStopReason({
463
+ finishReason,
464
+ isJsonResponseFromTool
465
+ }) {
463
466
  switch (finishReason) {
464
467
  case "end_turn":
465
468
  case "stop_sequence":
466
469
  return "stop";
467
470
  case "tool_use":
468
- return "tool-calls";
471
+ return isJsonResponseFromTool ? "stop" : "tool-calls";
469
472
  case "max_tokens":
470
473
  return "length";
471
474
  default:
@@ -526,13 +529,27 @@ var AnthropicMessagesLanguageModel = class {
526
529
  setting: "seed"
527
530
  });
528
531
  }
529
- if (responseFormat != null && responseFormat.type !== "text") {
530
- warnings.push({
531
- type: "unsupported-setting",
532
- setting: "responseFormat",
533
- details: "JSON response format is not supported."
534
- });
532
+ if ((responseFormat == null ? void 0 : responseFormat.type) === "json") {
533
+ if (responseFormat.schema == null) {
534
+ warnings.push({
535
+ type: "unsupported-setting",
536
+ setting: "responseFormat",
537
+ details: "JSON response format requires a schema. The response format is ignored."
538
+ });
539
+ } else if (tools != null) {
540
+ warnings.push({
541
+ type: "unsupported-setting",
542
+ setting: "tools",
543
+ details: "JSON response format does not support tools. The provided tools are ignored."
544
+ });
545
+ }
535
546
  }
547
+ const jsonResponseTool = (responseFormat == null ? void 0 : responseFormat.type) === "json" && responseFormat.schema != null ? {
548
+ type: "function",
549
+ name: "json",
550
+ description: "Respond with a JSON object.",
551
+ parameters: responseFormat.schema
552
+ } : void 0;
536
553
  const anthropicOptions = await parseProviderOptions2({
537
554
  provider: "anthropic",
538
555
  providerOptions,
@@ -599,7 +616,12 @@ var AnthropicMessagesLanguageModel = class {
599
616
  toolChoice: anthropicToolChoice,
600
617
  toolWarnings,
601
618
  betas: toolsBetas
602
- } = prepareTools({ tools, toolChoice });
619
+ } = prepareTools(
620
+ jsonResponseTool != null ? {
621
+ tools: [jsonResponseTool],
622
+ toolChoice: { type: "tool", toolName: jsonResponseTool.name }
623
+ } : { tools, toolChoice }
624
+ );
603
625
  return {
604
626
  args: {
605
627
  ...baseArgs,
@@ -607,7 +629,8 @@ var AnthropicMessagesLanguageModel = class {
607
629
  tool_choice: anthropicToolChoice
608
630
  },
609
631
  warnings: [...warnings, ...toolWarnings],
610
- betas: /* @__PURE__ */ new Set([...messagesBetas, ...toolsBetas])
632
+ betas: /* @__PURE__ */ new Set([...messagesBetas, ...toolsBetas]),
633
+ jsonResponseTool
611
634
  };
612
635
  }
613
636
  async getHeaders({
@@ -630,7 +653,7 @@ var AnthropicMessagesLanguageModel = class {
630
653
  }
631
654
  async doGenerate(options) {
632
655
  var _a, _b, _c, _d;
633
- const { args, warnings, betas } = await this.getArgs(options);
656
+ const { args, warnings, betas, jsonResponseTool } = await this.getArgs(options);
634
657
  const {
635
658
  responseHeaders,
636
659
  value: response,
@@ -650,7 +673,9 @@ var AnthropicMessagesLanguageModel = class {
650
673
  for (const part of response.content) {
651
674
  switch (part.type) {
652
675
  case "text": {
653
- content.push({ type: "text", text: part.text });
676
+ if (jsonResponseTool == null) {
677
+ content.push({ type: "text", text: part.text });
678
+ }
654
679
  break;
655
680
  }
656
681
  case "thinking": {
@@ -678,20 +703,29 @@ var AnthropicMessagesLanguageModel = class {
678
703
  break;
679
704
  }
680
705
  case "tool_use": {
681
- content.push({
682
- type: "tool-call",
683
- toolCallType: "function",
684
- toolCallId: part.id,
685
- toolName: part.name,
686
- args: JSON.stringify(part.input)
687
- });
706
+ content.push(
707
+ // when a json response tool is used, the tool call becomes the text:
708
+ jsonResponseTool != null ? {
709
+ type: "text",
710
+ text: JSON.stringify(part.input)
711
+ } : {
712
+ type: "tool-call",
713
+ toolCallType: "function",
714
+ toolCallId: part.id,
715
+ toolName: part.name,
716
+ args: JSON.stringify(part.input)
717
+ }
718
+ );
688
719
  break;
689
720
  }
690
721
  }
691
722
  }
692
723
  return {
693
724
  content,
694
- finishReason: mapAnthropicStopReason(response.stop_reason),
725
+ finishReason: mapAnthropicStopReason({
726
+ finishReason: response.stop_reason,
727
+ isJsonResponseFromTool: jsonResponseTool != null
728
+ }),
695
729
  usage: {
696
730
  inputTokens: response.usage.input_tokens,
697
731
  outputTokens: response.usage.output_tokens,
@@ -714,7 +748,7 @@ var AnthropicMessagesLanguageModel = class {
714
748
  };
715
749
  }
716
750
  async doStream(options) {
717
- const { args, warnings, betas } = await this.getArgs(options);
751
+ const { args, warnings, betas, jsonResponseTool } = await this.getArgs(options);
718
752
  const body = { ...args, stream: true };
719
753
  const { responseHeaders, value: response } = await postJsonToApi({
720
754
  url: this.buildRequestUrl(true),
@@ -793,13 +827,15 @@ var AnthropicMessagesLanguageModel = class {
793
827
  case "content_block_stop": {
794
828
  if (toolCallContentBlocks[value.index] != null) {
795
829
  const contentBlock = toolCallContentBlocks[value.index];
796
- controller.enqueue({
797
- type: "tool-call",
798
- toolCallType: "function",
799
- toolCallId: contentBlock.toolCallId,
800
- toolName: contentBlock.toolName,
801
- args: contentBlock.jsonText
802
- });
830
+ if (jsonResponseTool == null) {
831
+ controller.enqueue({
832
+ type: "tool-call",
833
+ toolCallType: "function",
834
+ toolCallId: contentBlock.toolCallId,
835
+ toolName: contentBlock.toolName,
836
+ args: contentBlock.jsonText
837
+ });
838
+ }
803
839
  delete toolCallContentBlocks[value.index];
804
840
  }
805
841
  blockType = void 0;
@@ -809,6 +845,9 @@ var AnthropicMessagesLanguageModel = class {
809
845
  const deltaType = value.delta.type;
810
846
  switch (deltaType) {
811
847
  case "text_delta": {
848
+ if (jsonResponseTool != null) {
849
+ return;
850
+ }
812
851
  controller.enqueue({
813
852
  type: "text",
814
853
  text: value.delta.text
@@ -839,13 +878,18 @@ var AnthropicMessagesLanguageModel = class {
839
878
  }
840
879
  case "input_json_delta": {
841
880
  const contentBlock = toolCallContentBlocks[value.index];
842
- controller.enqueue({
843
- type: "tool-call-delta",
844
- toolCallType: "function",
845
- toolCallId: contentBlock.toolCallId,
846
- toolName: contentBlock.toolName,
847
- argsTextDelta: value.delta.partial_json
848
- });
881
+ controller.enqueue(
882
+ jsonResponseTool != null ? {
883
+ type: "text",
884
+ text: value.delta.partial_json
885
+ } : {
886
+ type: "tool-call-delta",
887
+ toolCallType: "function",
888
+ toolCallId: contentBlock.toolCallId,
889
+ toolName: contentBlock.toolName,
890
+ argsTextDelta: value.delta.partial_json
891
+ }
892
+ );
849
893
  contentBlock.jsonText += value.delta.partial_json;
850
894
  return;
851
895
  }
@@ -875,7 +919,10 @@ var AnthropicMessagesLanguageModel = class {
875
919
  case "message_delta": {
876
920
  usage.outputTokens = value.usage.output_tokens;
877
921
  usage.totalTokens = ((_e = usage.inputTokens) != null ? _e : 0) + ((_f = value.usage.output_tokens) != null ? _f : 0);
878
- finishReason = mapAnthropicStopReason(value.delta.stop_reason);
922
+ finishReason = mapAnthropicStopReason({
923
+ finishReason: value.delta.stop_reason,
924
+ isJsonResponseFromTool: jsonResponseTool != null
925
+ });
879
926
  return;
880
927
  }
881
928
  case "message_stop": {