diff --git a/.changeset/thin-geckos-breathe.md b/.changeset/thin-geckos-breathe.md new file mode 100644 index 0000000..bf2ba1c --- /dev/null +++ b/.changeset/thin-geckos-breathe.md @@ -0,0 +1,5 @@ +--- +"@hyperbolic/ai-sdk-provider": major +--- + +Remove support for chat and completion models (our APIs are now entirely compatible with openrouter). Upgrade to AI SDK v6 diff --git a/package.json b/package.json index a507b92..005fe6b 100644 --- a/package.json +++ b/package.json @@ -43,7 +43,7 @@ "turbo": "^2.3.4", "typescript": "catalog:", "vite-tsconfig-paths": "^5.1.4", - "vitest": "^2.0.5" + "vitest": "3.2.4" }, "packageManager": "pnpm@9.15.4", "engines": { diff --git a/packages/ai-sdk-provider/LICENSE b/packages/ai-sdk-provider/LICENSE index 1bceb99..5bca256 100644 --- a/packages/ai-sdk-provider/LICENSE +++ b/packages/ai-sdk-provider/LICENSE @@ -186,7 +186,6 @@ APPENDIX: How to apply the Apache License to your work. same "printed page" as the copyright notice for easier identification within third-party archives. - Copyright 2025 OpenRouter Inc, Copyright 2025 Hyperbolic Labs Inc, Licensed under the Apache License, Version 2.0 (the "License"); diff --git a/packages/ai-sdk-provider/README.md b/packages/ai-sdk-provider/README.md index 3e99fbc..5c26533 100644 --- a/packages/ai-sdk-provider/README.md +++ b/packages/ai-sdk-provider/README.md @@ -1,8 +1,6 @@ # Hyperbolic Provider for Vercel AI SDK -The [Hyperbolic](https://hyperbolic.xyz/) provider for the [Vercel AI SDK](https://sdk.vercel.ai/docs) gives access to any model found at . - -This is based on the [OpenRouter](https://openrouter.ai/) provider for the Vercel AI SDK, with a number of changes to support the Hyperbolic API and add image generation support. +The [Hyperbolic](https://hyperbolic.xyz/) provider for the [Vercel AI SDK](https://sdk.vercel.ai/docs) gives access to image models found at . For chat and completion models, use the [@openrouter/ai-sdk-provider](https://www.npmjs.com/package/@openrouter/ai-sdk-provider) package instead. ## Setup @@ -33,53 +31,23 @@ import { generateText } from "ai"; import { createHyperbolic } from "@hyperbolic/ai-sdk-provider"; const hyperbolic = createHyperbolic({ - apiKey: process.env.HYPERBOLIC_API_KEY, // Found in settings after logging in at https://app.hyperbolic.xyz -}); - -const { text } = await generateText({ - model: hyperbolic.chat("deepseek-ai/DeepSeek-R1"), - prompt: "Write a vegetarian lasagna recipe for 4 people.", + apiKey: process.env.HYPERBOLIC_API_KEY, // Found in settings after logging in at https://app.hyperbolic.ai }); -``` - -## Supported models -This list is not a definitive list of models supported by Hyperbolic, as it constantly changes as we add new models (and deprecate old ones) to our system. -You can find the latest list of models supported by Hyperbolic [here](https://openrouter.ai/models). - -## Using Models - -### Language Models - -```ts -const { text } = await generateText({ - model: hyperbolic.chat("deepseek-ai/DeepSeek-R1"), - prompt: "Write a vegetarian lasagna recipe for 4 people.", -}); - -const { text } = await generateText({ - model: hyperbolic.completion("deepseek-ai/DeepSeek-R1"), - prompt: "The capital of France is", -}); -``` - -### Image Generation Models - -```ts -import { experimental_generateImage as generateImage } from "ai"; - -// Text to Image -const { images } = await generateImage({ - model: hyperbolic.image("SDXL1.0-base"), - prompt: "A beautiful sunset over a calm ocean", - size: "1024x1024", +const result = await generateImage({ + model: hyperbolic.image("FLUX.1-dev"), + prompt: "An image of a man riding a horse in SF.", + size: `1020x1020`, providerOptions: { hyperbolic: { cfgScale: 5, steps: 30, - negativePrompt: "low quality, blurry, distorted", - enableRefiner: false, } satisfies HyperbolicImageProviderOptions, }, }); ``` + +## Supported models + +This list is not a definitive list of models supported by Hyperbolic, as it constantly changes as we add new models (and deprecate old ones) to our system. +You can find the latest list of models supported by Hyperbolic [here](https://app.hyperbolic.ai/models). diff --git a/packages/ai-sdk-provider/package.json b/packages/ai-sdk-provider/package.json index b98781a..f9a31a9 100644 --- a/packages/ai-sdk-provider/package.json +++ b/packages/ai-sdk-provider/package.json @@ -54,17 +54,25 @@ "@hyperbolic/eslint-config": "workspace:*", "@hyperbolic/prettier-config": "workspace:*", "@hyperbolic/tsconfig": "workspace:*", + "@types/json-schema": "7.0.15", + "ai": "^6.0.48", "eslint": "catalog:", "handlebars": "^4.7.8", + "msw": "2.12.4", "prettier": "catalog:", - "tsup": "8.4.0", + "tsup": "8.5.0", "type-fest": "^4.37.0", - "typescript": "catalog:" + "typescript": "catalog:", + "vite-tsconfig-paths": "^5.1.4", + "vitest": "3.2.4", + "zod": "^4.0.0" }, "dependencies": { - "@ai-sdk/provider": "^1.1.3", - "@ai-sdk/provider-utils": "^2.2.8", - "ai": "^4.3.16", - "zod": "^3.24.2" + "@ai-sdk/provider": "^3.0.5", + "@ai-sdk/provider-utils": "^4.0.9" + }, + "peerDependencies": { + "ai": "^6.0.48", + "zod": "^3.25.0 || ^4.0.0" } } diff --git a/packages/ai-sdk-provider/src/__generated__/models.gen.ts b/packages/ai-sdk-provider/src/__generated__/models.gen.ts index 08a1ae7..2ad0d9a 100644 --- a/packages/ai-sdk-provider/src/__generated__/models.gen.ts +++ b/packages/ai-sdk-provider/src/__generated__/models.gen.ts @@ -3,38 +3,73 @@ // This file is auto-generated by the pnpm codegen:update-models script. Do not edit manually. const _models = [ - "Qwen/Qwen2.5-72B-Instruct", +] as const; + +const _imageModels = [ + "StableDiffusion", + "FLUX.1-dev", "Qwen/Qwen2.5-VL-72B-Instruct", - "meta-llama/Meta-Llama-3-70B-Instruct", - "meta-llama/Meta-Llama-3.1-70B-Instruct", - "meta-llama/Meta-Llama-3.1-405B-FP8", "Qwen/Qwen2.5-VL-7B-Instruct", + "mistralai/Pixtral-12B-2409", +] as const; + +const _chatModels = [ + "Qwen/Qwen2.5-72B-Instruct", + "deepseek-ai/DeepSeek-V3", + "deepseek-ai/DeepSeek-V3-0324", + "meta-llama/Llama-3.3-70B-Instruct", + "Qwen/Qwen2.5-Coder-32B-Instruct", + "meta-llama/Llama-3.2-3B-Instruct", "meta-llama/Meta-Llama-3.1-405B-Instruct", + "meta-llama/Meta-Llama-3.1-70B-Instruct", + "meta-llama/Meta-Llama-3.1-8B-Instruct", + "meta-llama/Meta-Llama-3.1-405B", + "deepseek-ai/DeepSeek-R1", + "deepseek-ai/DeepSeek-R1-0528", "Qwen/QwQ-32B", + "Qwen/Qwen3-235B-A22B", + "Qwen/Qwen3-235B-A22B-Instruct-2507", + "Qwen/Qwen3-Coder-480B-A35B-Instruct", + "openai/gpt-oss-120b-turbo", + "openai/gpt-oss-120b", + "openai/gpt-oss-20b", + "Qwen/Qwen3-Next-80B-A3B-Instruct", + "Qwen/Qwen3-Next-80B-A3B-Thinking", + "Qwen/Qwen2.5-VL-72B-Instruct", + "Qwen/Qwen2.5-VL-7B-Instruct", + "mistralai/Pixtral-12B-2409", +] as const; + +const _completionModels = [ + "Qwen/Qwen2.5-72B-Instruct", "deepseek-ai/DeepSeek-V3", - "Qwen/QwQ-32B-Preview", + "deepseek-ai/DeepSeek-V3-0324", "meta-llama/Llama-3.3-70B-Instruct", - "NousResearch/Hermes-3-Llama-3.1-70B", - "meta-llama/Meta-Llama-3.1-405B", + "Qwen/Qwen2.5-Coder-32B-Instruct", "meta-llama/Llama-3.2-3B-Instruct", - "FLUX.1-dev", - "mistralai/Pixtral-12B-2409", - "StableDiffusion", + "meta-llama/Meta-Llama-3.1-405B-Instruct", + "meta-llama/Meta-Llama-3.1-70B-Instruct", "meta-llama/Meta-Llama-3.1-8B-Instruct", - "Qwen/Qwen2.5-Coder-32B-Instruct", - "TTS", + "meta-llama/Meta-Llama-3.1-405B", "deepseek-ai/DeepSeek-R1", + "deepseek-ai/DeepSeek-R1-0528", + "Qwen/QwQ-32B", + "Qwen/Qwen3-235B-A22B", + "Qwen/Qwen3-235B-A22B-Instruct-2507", + "Qwen/Qwen3-Coder-480B-A35B-Instruct", + "openai/gpt-oss-120b-turbo", + "openai/gpt-oss-120b", + "openai/gpt-oss-20b", + "Qwen/Qwen3-Next-80B-A3B-Instruct", + "Qwen/Qwen3-Next-80B-A3B-Thinking", + "Qwen/Qwen2.5-VL-72B-Instruct", + "Qwen/Qwen2.5-VL-7B-Instruct", + "mistralai/Pixtral-12B-2409", ] as const; -const _imageModels = [] as const; - -const _chatModels = [] as const; - -const _completionModels = [] as const; - -export type HyperbolicImageModelId = (typeof _imageModels)[number] | string; -export type HyperbolicChatModelId = (typeof _chatModels)[number] | string; -export type HyperbolicCompletionModelId = (typeof _completionModels)[number] | string; +export type HyperbolicImageModelId = (typeof _imageModels)[number] | (string & {}); +export type HyperbolicChatModelId = (typeof _chatModels)[number] | (string & {}); +export type HyperbolicCompletionModelId = (typeof _completionModels)[number] | (string & {}); export type HyperbolicModelId = | HyperbolicImageModelId | HyperbolicChatModelId diff --git a/packages/ai-sdk-provider/src/convert-to-hyperbolic-chat-messages.test.ts b/packages/ai-sdk-provider/src/convert-to-hyperbolic-chat-messages.test.ts deleted file mode 100644 index af2e058..0000000 --- a/packages/ai-sdk-provider/src/convert-to-hyperbolic-chat-messages.test.ts +++ /dev/null @@ -1,437 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import { describe, expect, it } from "vitest"; - -import { convertToHyperbolicChatMessages } from "./convert-to-hyperbolic-chat-messages"; - -describe("user messages", () => { - it("should convert messages with image parts to multiple parts", async () => { - const result = convertToHyperbolicChatMessages([ - { - role: "user", - content: [ - { type: "text", text: "Hello" }, - { - type: "image", - image: new Uint8Array([0, 1, 2, 3]), - mimeType: "image/png", - }, - ], - }, - ]); - - expect(result).toEqual([ - { - role: "user", - content: [ - { type: "text", text: "Hello" }, - { - type: "image_url", - image_url: { url: "data:image/png;base64,AAECAw==" }, - }, - ], - }, - ]); - }); - - it("should convert messages with only a text part to a string content", async () => { - const result = convertToHyperbolicChatMessages([ - { - role: "user", - content: [{ type: "text", text: "Hello" }], - }, - ]); - - expect(result).toEqual([{ role: "user", content: "Hello" }]); - }); -}); - -describe("cache control", () => { - it("should pass cache control from system message provider metadata", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "system", - content: "System prompt", - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - ]); - - expect(result).toEqual([ - { - role: "system", - content: "System prompt", - cache_control: { type: "ephemeral" }, - }, - ]); - }); - - it("should pass cache control from user message provider metadata (single text part)", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "user", - content: [{ type: "text", text: "Hello" }], - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - ]); - - expect(result).toEqual([ - { - role: "user", - content: "Hello", - cache_control: { type: "ephemeral" }, - }, - ]); - }); - - it("should pass cache control from user message provider metadata (multiple parts)", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "user", - content: [ - { type: "text", text: "Hello" }, - { - type: "image", - image: new Uint8Array([0, 1, 2, 3]), - mimeType: "image/png", - }, - ], - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - ]); - - expect(result).toEqual([ - { - role: "user", - content: [ - { - type: "text", - text: "Hello", - cache_control: undefined, - }, - { - type: "image_url", - image_url: { url: "data:image/png;base64,AAECAw==" }, - cache_control: { type: "ephemeral" }, - }, - ], - }, - ]); - }); - - it("should pass cache control to multiple image parts from user message provider metadata", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "user", - content: [ - { type: "text", text: "Hello" }, - { - type: "image", - image: new Uint8Array([0, 1, 2, 3]), - mimeType: "image/png", - }, - { - type: "image", - image: new Uint8Array([4, 5, 6, 7]), - mimeType: "image/jpeg", - }, - ], - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - ]); - - expect(result).toEqual([ - { - role: "user", - content: [ - { - type: "text", - text: "Hello", - cache_control: undefined, - }, - { - type: "image_url", - image_url: { url: "data:image/png;base64,AAECAw==" }, - cache_control: { type: "ephemeral" }, - }, - { - type: "image_url", - image_url: { url: "data:image/jpeg;base64,BAUGBw==" }, - cache_control: { type: "ephemeral" }, - }, - ], - }, - ]); - }); - - it("should pass cache control to file parts from user message provider metadata", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "user", - content: [ - { type: "text", text: "Hello" }, - { - type: "file", - data: "file content", - mimeType: "text/plain", - }, - ], - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - ]); - - expect(result).toEqual([ - { - role: "user", - content: [ - { - type: "text", - text: "Hello", - cache_control: undefined, - }, - { - type: "text", - text: "file content", - cache_control: { type: "ephemeral" }, - }, - ], - }, - ]); - }); - - it("should handle mixed part-specific and message-level cache control for multiple parts", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "user", - content: [ - { - type: "text", - text: "Hello", - // No part-specific provider metadata - }, - { - type: "image", - image: new Uint8Array([0, 1, 2, 3]), - mimeType: "image/png", - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - { - type: "file", - data: "file content", - mimeType: "text/plain", - // No part-specific provider metadata - }, - ], - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - ]); - - expect(result).toEqual([ - { - role: "user", - content: [ - { - type: "text", - text: "Hello", - cache_control: undefined, - }, - { - type: "image_url", - image_url: { url: "data:image/png;base64,AAECAw==" }, - cache_control: { type: "ephemeral" }, - }, - { - type: "text", - text: "file content", - cache_control: { type: "ephemeral" }, - }, - ], - }, - ]); - }); - - it("should pass cache control from individual content part provider metadata", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "user", - content: [ - { - type: "text", - text: "Hello", - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - { - type: "image", - image: new Uint8Array([0, 1, 2, 3]), - mimeType: "image/png", - }, - ], - }, - ]); - - expect(result).toEqual([ - { - role: "user", - content: [ - { - type: "text", - text: "Hello", - cache_control: { type: "ephemeral" }, - }, - { - type: "image_url", - image_url: { url: "data:image/png;base64,AAECAw==" }, - }, - ], - }, - ]); - }); - - it("should pass cache control from assistant message provider metadata", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "assistant", - content: [{ type: "text", text: "Assistant response" }], - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - ]); - - expect(result).toEqual([ - { - role: "assistant", - content: "Assistant response", - cache_control: { type: "ephemeral" }, - }, - ]); - }); - - it("should pass cache control from tool message provider metadata", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "tool", - content: [ - { - type: "tool-result", - toolCallId: "call-123", - toolName: "calculator", - result: { answer: 42 }, - isError: false, - }, - ], - providerMetadata: { - anthropic: { - cacheControl: { type: "ephemeral" }, - }, - }, - }, - ]); - - expect(result).toEqual([ - { - role: "tool", - tool_call_id: "call-123", - content: JSON.stringify({ answer: 42 }), - cache_control: { type: "ephemeral" }, - }, - ]); - }); - - it("should support the alias cache_control field", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "system", - content: "System prompt", - providerMetadata: { - anthropic: { - cache_control: { type: "ephemeral" }, - }, - }, - }, - ]); - - expect(result).toEqual([ - { - role: "system", - content: "System prompt", - cache_control: { type: "ephemeral" }, - }, - ]); - }); - - it("should support cache control on last message in content array", () => { - const result = convertToHyperbolicChatMessages([ - { - role: "system", - content: "System prompt", - }, - { - role: "user", - content: [ - { type: "text", text: "User prompt" }, - { - type: "text", - text: "User prompt 2", - providerMetadata: { - anthropic: { cacheControl: { type: "ephemeral" } }, - }, - }, - ], - }, - ]); - - expect(result).toEqual([ - { - role: "system", - content: "System prompt", - }, - { - role: "user", - content: [ - { type: "text", text: "User prompt" }, - { - type: "text", - text: "User prompt 2", - cache_control: { type: "ephemeral" }, - }, - ], - }, - ]); - }); -}); diff --git a/packages/ai-sdk-provider/src/convert-to-hyperbolic-chat-messages.ts b/packages/ai-sdk-provider/src/convert-to-hyperbolic-chat-messages.ts deleted file mode 100644 index 30bae0b..0000000 --- a/packages/ai-sdk-provider/src/convert-to-hyperbolic-chat-messages.ts +++ /dev/null @@ -1,165 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { LanguageModelV1Prompt, LanguageModelV1ProviderMetadata } from "@ai-sdk/provider"; -import { convertUint8ArrayToBase64 } from "@ai-sdk/provider-utils"; - -import type { ChatCompletionContentPart, HyperbolicChatPrompt } from "./hyperbolic-chat-prompt"; - -// Type for Hyperbolic Cache Control following Anthropic's pattern -export type HyperbolicCacheControl = { type: "ephemeral" }; - -export function convertToHyperbolicChatMessages( - prompt: LanguageModelV1Prompt, -): HyperbolicChatPrompt { - const messages: HyperbolicChatPrompt = []; - - function getCacheControl( - providerMetadata: LanguageModelV1ProviderMetadata | undefined, - ): HyperbolicCacheControl | undefined { - const anthropic = providerMetadata?.anthropic; - - // Allow both cacheControl and cache_control: - const cacheControlValue = anthropic?.cacheControl ?? anthropic?.cache_control; - - // Return the cache control object if it exists - return cacheControlValue as HyperbolicCacheControl | undefined; - } - - for (const { role, content, providerMetadata } of prompt) { - switch (role) { - case "system": { - messages.push({ - role: "system", - content, - cache_control: getCacheControl(providerMetadata), - }); - break; - } - - case "user": { - if (content.length === 1 && content[0]?.type === "text") { - messages.push({ - role: "user", - content: content[0].text, - cache_control: - getCacheControl(providerMetadata) ?? getCacheControl(content[0].providerMetadata), - }); - break; - } - - // Get message level cache control - const messageCacheControl = getCacheControl(providerMetadata); - - const contentParts: ChatCompletionContentPart[] = content.map((part) => { - switch (part.type) { - case "text": - return { - type: "text" as const, - text: part.text, - // For text parts, only use part-specific cache control - cache_control: getCacheControl(part.providerMetadata), - }; - case "image": - return { - type: "image_url" as const, - image_url: { - url: - part.image instanceof URL - ? part.image.toString() - : `data:${part.mimeType ?? "image/jpeg"};base64,${convertUint8ArrayToBase64( - part.image, - )}`, - }, - // For image parts, use part-specific or message-level cache control - cache_control: getCacheControl(part.providerMetadata) ?? messageCacheControl, - }; - case "file": - return { - type: "text" as const, - text: part.data instanceof URL ? part.data.toString() : part.data, - cache_control: getCacheControl(part.providerMetadata) ?? messageCacheControl, - }; - default: { - const _exhaustiveCheck: never = part; - throw new Error(`Unsupported content part type: ${_exhaustiveCheck}`); - } - } - }); - - // For multi-part messages, don't add cache_control at the root level - messages.push({ - role: "user", - content: contentParts, - }); - - break; - } - - case "assistant": { - let text = ""; - const toolCalls: Array<{ - id: string; - type: "function"; - function: { name: string; arguments: string }; - }> = []; - - for (const part of content) { - switch (part.type) { - case "text": { - text += part.text; - break; - } - case "tool-call": { - toolCalls.push({ - id: part.toolCallId, - type: "function", - function: { - name: part.toolName, - arguments: JSON.stringify(part.args), - }, - }); - break; - } - // TODO: Handle reasoning and redacted-reasoning - case "reasoning": - case "redacted-reasoning": - break; - default: { - throw new Error(`Unsupported part: ${part}`); - } - } - } - - messages.push({ - role: "assistant", - content: text, - tool_calls: toolCalls.length > 0 ? toolCalls : undefined, - cache_control: getCacheControl(providerMetadata), - }); - - break; - } - - case "tool": { - for (const toolResponse of content) { - messages.push({ - role: "tool", - tool_call_id: toolResponse.toolCallId, - content: JSON.stringify(toolResponse.result), - cache_control: - getCacheControl(providerMetadata) ?? getCacheControl(toolResponse.providerMetadata), - }); - } - break; - } - - default: { - throw new Error(`Unsupported role: ${role}`); - } - } - } - - return messages; -} diff --git a/packages/ai-sdk-provider/src/convert-to-hyperbolic-completion-prompt.ts b/packages/ai-sdk-provider/src/convert-to-hyperbolic-completion-prompt.ts deleted file mode 100644 index c241b77..0000000 --- a/packages/ai-sdk-provider/src/convert-to-hyperbolic-completion-prompt.ts +++ /dev/null @@ -1,134 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { LanguageModelV1Prompt } from "@ai-sdk/provider"; -import { InvalidPromptError, UnsupportedFunctionalityError } from "@ai-sdk/provider"; - -export function convertToHyperbolicCompletionPrompt({ - prompt, - inputFormat, - user = "user", - assistant = "assistant", -}: { - prompt: LanguageModelV1Prompt; - inputFormat: "prompt" | "messages"; - user?: string; - assistant?: string; -}): { - prompt: string; -} { - // When the user supplied a prompt input, we don't transform it: - if ( - inputFormat === "prompt" && - prompt.length === 1 && - prompt[0] && - prompt[0].role === "user" && - prompt[0].content.length === 1 && - prompt[0].content[0] && - prompt[0].content[0].type === "text" - ) { - return { prompt: prompt[0].content[0].text }; - } - - // otherwise transform to a chat message format: - let text = ""; - - // if first message is a system message, add it to the text: - if (prompt[0] && prompt[0].role === "system") { - text += `${prompt[0].content}\n\n`; - prompt = prompt.slice(1); - } - - for (const { role, content } of prompt) { - switch (role) { - case "system": { - throw new InvalidPromptError({ - message: "Unexpected system message in prompt: ${content}", - prompt, - }); - } - - case "user": { - const userMessage = content - .map((part) => { - switch (part.type) { - case "text": { - return part.text; - } - case "image": { - throw new UnsupportedFunctionalityError({ - functionality: "images", - }); - } - case "file": { - throw new UnsupportedFunctionalityError({ - functionality: "file attachments", - }); - } - default: { - const _exhaustiveCheck: never = part; - throw new Error(`Unsupported content type: ${_exhaustiveCheck}`); - } - } - }) - .join(""); - - text += `${user}:\n${userMessage}\n\n`; - break; - } - - case "assistant": { - const assistantMessage = content - .map((part) => { - switch (part.type) { - case "text": { - return part.text; - } - case "tool-call": { - throw new UnsupportedFunctionalityError({ - functionality: "tool-call messages", - }); - } - case "reasoning": { - throw new UnsupportedFunctionalityError({ - functionality: "reasoning messages", - }); - } - - case "redacted-reasoning": { - throw new UnsupportedFunctionalityError({ - functionality: "redacted reasoning messages", - }); - } - - default: { - throw new Error(`Unsupported content type: ${part}`); - } - } - }) - .join(""); - - text += `${assistant}:\n${assistantMessage}\n\n`; - break; - } - - case "tool": { - throw new UnsupportedFunctionalityError({ - functionality: "tool messages", - }); - } - - default: { - throw new Error(`Unsupported role: ${role}`); - } - } - } - - // Assistant message prefix: - text += `${assistant}:\n`; - - return { - prompt: text, - }; -} diff --git a/packages/ai-sdk-provider/src/hyperbolic-chat-language-model.test.ts b/packages/ai-sdk-provider/src/hyperbolic-chat-language-model.test.ts deleted file mode 100644 index 944ccce..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-chat-language-model.test.ts +++ /dev/null @@ -1,990 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { LanguageModelV1Prompt } from "@ai-sdk/provider"; -import { - convertReadableStreamToArray, - JsonTestServer, - StreamingTestServer, -} from "@ai-sdk/provider-utils/test"; -import { describe, expect, it } from "vitest"; - -import { createHyperbolic } from "./hyperbolic-provider"; -import { mapHyperbolicChatLogProbsOutput } from "./map-hyperbolic-chat-logprobs"; - -const TEST_PROMPT: LanguageModelV1Prompt = [ - { role: "user", content: [{ type: "text", text: "Hello" }] }, -]; - -const TEST_LOGPROBS = { - content: [ - { - token: "Hello", - logprob: -0.0009994634, - top_logprobs: [ - { - token: "Hello", - logprob: -0.0009994634, - }, - ], - }, - { - token: "!", - logprob: -0.13410144, - top_logprobs: [ - { - token: "!", - logprob: -0.13410144, - }, - ], - }, - { - token: " How", - logprob: -0.0009250381, - top_logprobs: [ - { - token: " How", - logprob: -0.0009250381, - }, - ], - }, - { - token: " can", - logprob: -0.047709424, - top_logprobs: [ - { - token: " can", - logprob: -0.047709424, - }, - ], - }, - { - token: " I", - logprob: -0.000009014684, - top_logprobs: [ - { - token: " I", - logprob: -0.000009014684, - }, - ], - }, - { - token: " assist", - logprob: -0.009125131, - top_logprobs: [ - { - token: " assist", - logprob: -0.009125131, - }, - ], - }, - { - token: " you", - logprob: -0.0000066306106, - top_logprobs: [ - { - token: " you", - logprob: -0.0000066306106, - }, - ], - }, - { - token: " today", - logprob: -0.00011093382, - top_logprobs: [ - { - token: " today", - logprob: -0.00011093382, - }, - ], - }, - { - token: "?", - logprob: -0.00004596782, - top_logprobs: [ - { - token: "?", - logprob: -0.00004596782, - }, - ], - }, - ], -}; - -const provider = createHyperbolic({ - apiKey: "test-api-key", - compatibility: "strict", -}); - -const model = provider.chat("anthropic/claude-3.5-sonnet"); - -describe("doGenerate", () => { - const server = new JsonTestServer("https://api.hyperbolic.xyz/v1/chat/completions"); - - server.setupTestEnvironment(); - - function prepareJsonResponse({ - content = "", - usage = { - prompt_tokens: 4, - total_tokens: 34, - completion_tokens: 30, - }, - logprobs = null, - finish_reason = "stop", - }: { - content?: string; - usage?: { - prompt_tokens: number; - total_tokens: number; - completion_tokens: number; - }; - logprobs?: { - content: - | { - token: string; - logprob: number; - top_logprobs: { token: string; logprob: number }[]; - }[] - | null; - } | null; - finish_reason?: string; - } = {}) { - server.responseBodyJson = { - id: "chatcmpl-95ZTZkhr0mHNKqerQfiwkuox3PHAd", - object: "chat.completion", - created: 1711115037, - model: "gpt-3.5-turbo-0125", - choices: [ - { - index: 0, - message: { - role: "assistant", - content, - }, - logprobs, - finish_reason, - }, - ], - usage, - system_fingerprint: "fp_3bc1b5746c", - }; - } - - it("should extract text response", async () => { - prepareJsonResponse({ content: "Hello, World!" }); - - const { text } = await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(text).toStrictEqual("Hello, World!"); - }); - - it("should extract usage", async () => { - prepareJsonResponse({ - content: "", - usage: { prompt_tokens: 20, total_tokens: 25, completion_tokens: 5 }, - }); - - const { usage } = await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(usage).toStrictEqual({ - promptTokens: 20, - completionTokens: 5, - }); - }); - - it("should extract logprobs", async () => { - prepareJsonResponse({ - logprobs: TEST_LOGPROBS, - }); - - const response = await provider.chat("openai/gpt-3.5-turbo", { logprobs: 1 }).doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - expect(response.logprobs).toStrictEqual(mapHyperbolicChatLogProbsOutput(TEST_LOGPROBS)); - }); - - it("should extract finish reason", async () => { - prepareJsonResponse({ - content: "", - finish_reason: "stop", - }); - - const response = await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(response.finishReason).toStrictEqual("stop"); - }); - - it("should support unknown finish reason", async () => { - prepareJsonResponse({ - content: "", - finish_reason: "eos", - }); - - const response = await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(response.finishReason).toStrictEqual("unknown"); - }); - - it("should expose the raw response headers", async () => { - prepareJsonResponse({ content: "" }); - - server.responseHeaders = { - "test-header": "test-value", - }; - - const { rawResponse } = await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(rawResponse?.headers).toStrictEqual({ - // default headers: - "content-length": "337", - "content-type": "application/json", - - // custom header - "test-header": "test-value", - }); - }); - - it("should pass the model and the messages", async () => { - prepareJsonResponse({ content: "" }); - - await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(await server.getRequestBodyJson()).toStrictEqual({ - model: "anthropic/claude-3.5-sonnet", - messages: [{ role: "user", content: "Hello" }], - }); - }); - - it("should pass the models array when provided", async () => { - prepareJsonResponse({ content: "" }); - - const customModel = provider.chat("anthropic/claude-3.5-sonnet", { - models: ["anthropic/claude-2", "gryphe/mythomax-l2-13b"], - }); - - await customModel.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(await server.getRequestBodyJson()).toStrictEqual({ - model: "anthropic/claude-3.5-sonnet", - models: ["anthropic/claude-2", "gryphe/mythomax-l2-13b"], - messages: [{ role: "user", content: "Hello" }], - }); - }); - - it("should pass settings", async () => { - prepareJsonResponse(); - - await provider - .chat("openai/gpt-3.5-turbo", { - logitBias: { 50256: -100 }, - logprobs: 2, - parallelToolCalls: false, - user: "test-user-id", - }) - .doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(await server.getRequestBodyJson()).toStrictEqual({ - model: "openai/gpt-3.5-turbo", - messages: [{ role: "user", content: "Hello" }], - logprobs: true, - top_logprobs: 2, - logit_bias: { 50256: -100 }, - parallel_tool_calls: false, - user: "test-user-id", - }); - }); - - it("should pass tools and toolChoice", async () => { - prepareJsonResponse({ content: "" }); - - await model.doGenerate({ - inputFormat: "prompt", - mode: { - type: "regular", - tools: [ - { - type: "function", - name: "test-tool", - parameters: { - type: "object", - properties: { value: { type: "string" } }, - required: ["value"], - additionalProperties: false, - $schema: "http://json-schema.org/draft-07/schema#", - }, - }, - ], - toolChoice: { - type: "tool", - toolName: "test-tool", - }, - }, - prompt: TEST_PROMPT, - }); - - expect(await server.getRequestBodyJson()).toStrictEqual({ - model: "anthropic/claude-3.5-sonnet", - messages: [{ role: "user", content: "Hello" }], - tools: [ - { - type: "function", - function: { - name: "test-tool", - parameters: { - type: "object", - properties: { value: { type: "string" } }, - required: ["value"], - additionalProperties: false, - $schema: "http://json-schema.org/draft-07/schema#", - }, - }, - }, - ], - tool_choice: { - type: "function", - function: { name: "test-tool" }, - }, - }); - }); - - it("should pass headers", async () => { - prepareJsonResponse({ content: "" }); - - const provider = createHyperbolic({ - apiKey: "test-api-key", - headers: { - "Custom-Provider-Header": "provider-header-value", - }, - }); - - await provider.chat("openai/gpt-3.5-turbo").doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - headers: { - "Custom-Request-Header": "request-header-value", - }, - }); - - const requestHeaders = await server.getRequestHeaders(); - - expect(requestHeaders).toStrictEqual({ - authorization: "Bearer test-api-key", - "content-type": "application/json", - "custom-provider-header": "provider-header-value", - "custom-request-header": "request-header-value", - }); - }); -}); - -describe("doStream", () => { - const server = new StreamingTestServer("https://api.hyperbolic.xyz/v1/chat/completions"); - - server.setupTestEnvironment(); - - function prepareStreamResponse({ - content, - usage = { - prompt_tokens: 17, - total_tokens: 244, - completion_tokens: 227, - }, - logprobs = null, - finish_reason = "stop", - }: { - content: string[]; - usage?: { - prompt_tokens: number; - total_tokens: number; - completion_tokens: number; - }; - logprobs?: { - content: - | { - token: string; - logprob: number; - top_logprobs: { token: string; logprob: number }[]; - }[] - | null; - } | null; - finish_reason?: string; - }) { - server.responseChunks = [ - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1702657020,"model":"gpt-3.5-turbo-0613",` + - `"system_fingerprint":null,"choices":[{"index":0,"delta":{"role":"assistant","content":""},"finish_reason":null}]}\n\n`, - ...content.flatMap((text) => { - return ( - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1702657020,"model":"gpt-3.5-turbo-0613",` + - `"system_fingerprint":null,"choices":[{"index":1,"delta":{"content":"${text}"},"finish_reason":null}]}\n\n` - ); - }), - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1702657020,"model":"gpt-3.5-turbo-0613",` + - `"system_fingerprint":null,"choices":[{"index":0,"delta":{},"finish_reason":"${finish_reason}","logprobs":${JSON.stringify( - logprobs, - )}}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1702657020,"model":"gpt-3.5-turbo-0613",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[],"usage":${JSON.stringify(usage)}}\n\n`, - "data: [DONE]\n\n", - ]; - } - - it("should stream text deltas", async () => { - prepareStreamResponse({ - content: ["Hello", ", ", "World!"], - finish_reason: "stop", - usage: { - prompt_tokens: 17, - total_tokens: 244, - completion_tokens: 227, - }, - logprobs: TEST_LOGPROBS, - }); - - const { stream } = await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - // note: space moved to last chunk bc of trimming - expect(await convertReadableStreamToArray(stream)).toStrictEqual([ - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0613", - }, - { type: "text-delta", textDelta: "" }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0613", - }, - { type: "text-delta", textDelta: "Hello" }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0613", - }, - { type: "text-delta", textDelta: ", " }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0613", - }, - { type: "text-delta", textDelta: "World!" }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0613", - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0613", - }, - { - type: "finish", - finishReason: "stop", - logprobs: mapHyperbolicChatLogProbsOutput(TEST_LOGPROBS), - usage: { promptTokens: 17, completionTokens: 227 }, - }, - ]); - }); - - it("should stream tool deltas", async () => { - server.responseChunks = [ - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{"role":"assistant","content":null,` + - `"tool_calls":[{"index":0,"id":"call_O17Uplv4lJvD6DVdIvFFeRMw","type":"function","function":{"name":"test-tool","arguments":""}}]},` + - `"logprobs":null,"finish_reason":null}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{"tool_calls":[{"index":0,"function":{"arguments":"{\\""}}]},` + - `"logprobs":null,"finish_reason":null}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{"tool_calls":[{"index":0,"function":{"arguments":"value"}}]},` + - `"logprobs":null,"finish_reason":null}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{"tool_calls":[{"index":0,"function":{"arguments":"\\":\\""}}]},` + - `"logprobs":null,"finish_reason":null}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{"tool_calls":[{"index":0,"function":{"arguments":"Spark"}}]},` + - `"logprobs":null,"finish_reason":null}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{"tool_calls":[{"index":0,"function":{"arguments":"le"}}]},` + - `"logprobs":null,"finish_reason":null}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{"tool_calls":[{"index":0,"function":{"arguments":" Day"}}]},` + - `"logprobs":null,"finish_reason":null}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{"tool_calls":[{"index":0,"function":{"arguments":"\\"}"}}]},` + - `"logprobs":null,"finish_reason":null}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{},"logprobs":null,"finish_reason":"tool_calls"}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[],"usage":{"prompt_tokens":53,"completion_tokens":17,"total_tokens":70}}\n\n`, - "data: [DONE]\n\n", - ]; - - const { stream } = await model.doStream({ - inputFormat: "prompt", - mode: { - type: "regular", - tools: [ - { - type: "function", - name: "test-tool", - parameters: { - type: "object", - properties: { value: { type: "string" } }, - required: ["value"], - additionalProperties: false, - $schema: "http://json-schema.org/draft-07/schema#", - }, - }, - ], - }, - prompt: TEST_PROMPT, - }); - - expect(await convertReadableStreamToArray(stream)).toStrictEqual([ - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "tool-call-delta", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - argsTextDelta: '{"', - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "tool-call-delta", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - argsTextDelta: "value", - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "tool-call-delta", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - argsTextDelta: '":"', - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "tool-call-delta", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - argsTextDelta: "Spark", - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "tool-call-delta", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - argsTextDelta: "le", - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "tool-call-delta", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - argsTextDelta: " Day", - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "tool-call-delta", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - argsTextDelta: '"}', - }, - { - type: "tool-call", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - args: '{"value":"Sparkle Day"}', - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "finish", - finishReason: "tool-calls", - logprobs: undefined, - usage: { promptTokens: 53, completionTokens: 17 }, - }, - ]); - }); - - it("should stream tool call that is sent in one chunk", async () => { - server.responseChunks = [ - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{"role":"assistant","content":null,` + - `"tool_calls":[{"index":0,"id":"call_O17Uplv4lJvD6DVdIvFFeRMw","type":"function","function":{"name":"test-tool","arguments":"{\\"value\\":\\"Sparkle Day\\"}"}}]},` + - `"logprobs":null,"finish_reason":null}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[{"index":0,"delta":{},"logprobs":null,"finish_reason":"tool_calls"}]}\n\n`, - `data: {"id":"chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP","object":"chat.completion.chunk","created":1711357598,"model":"gpt-3.5-turbo-0125",` + - `"system_fingerprint":"fp_3bc1b5746c","choices":[],"usage":{"prompt_tokens":53,"completion_tokens":17,"total_tokens":70}}\n\n`, - "data: [DONE]\n\n", - ]; - - const { stream } = await model.doStream({ - inputFormat: "prompt", - mode: { - type: "regular", - tools: [ - { - type: "function", - name: "test-tool", - parameters: { - type: "object", - properties: { value: { type: "string" } }, - required: ["value"], - additionalProperties: false, - $schema: "http://json-schema.org/draft-07/schema#", - }, - }, - ], - }, - prompt: TEST_PROMPT, - }); - - expect(await convertReadableStreamToArray(stream)).toStrictEqual([ - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "tool-call-delta", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - argsTextDelta: '{"value":"Sparkle Day"}', - }, - { - type: "tool-call", - toolCallId: "call_O17Uplv4lJvD6DVdIvFFeRMw", - toolCallType: "function", - toolName: "test-tool", - args: '{"value":"Sparkle Day"}', - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "response-metadata", - id: "chatcmpl-96aZqmeDpA9IPD6tACY8djkMsJCMP", - }, - { - type: "response-metadata", - modelId: "gpt-3.5-turbo-0125", - }, - { - type: "finish", - finishReason: "tool-calls", - logprobs: undefined, - usage: { promptTokens: 53, completionTokens: 17 }, - }, - ]); - }); - - it("should handle error stream parts", async () => { - server.responseChunks = [ - `data: {"object": "error", "message": "The server had an error processing your request. Sorry about that! You can retry your request, or contact us through our ` + - `help center at app.hyperbolic.xyz/support if you keep seeing this error.","type":"server_error","param":null,"code":null}\n\n`, - "data: [DONE]\n\n", - ]; - - const { stream } = await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(await convertReadableStreamToArray(stream)).toStrictEqual([ - { - type: "error", - error: { - object: "error", - message: - "The server had an error processing your request. Sorry about that! " + - "You can retry your request, or contact us through our help center at " + - "app.hyperbolic.xyz/support if you keep seeing this error.", - type: "server_error", - code: null, - param: null, - }, - }, - { - finishReason: "error", - logprobs: undefined, - type: "finish", - usage: { - completionTokens: NaN, - promptTokens: NaN, - }, - }, - ]); - }); - - it("should handle unparsable stream parts", async () => { - server.responseChunks = [`data: {unparsable}\n\n`, "data: [DONE]\n\n"]; - - const { stream } = await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - const elements = await convertReadableStreamToArray(stream); - - expect(elements.length).toBe(2); - expect(elements[0]?.type).toBe("error"); - expect(elements[1]).toStrictEqual({ - finishReason: "error", - logprobs: undefined, - type: "finish", - usage: { - completionTokens: NaN, - promptTokens: NaN, - }, - }); - }); - - it("should expose the raw response headers", async () => { - prepareStreamResponse({ content: [] }); - - server.responseHeaders = { - "test-header": "test-value", - }; - - const { rawResponse } = await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(rawResponse?.headers).toStrictEqual({ - // default headers: - "content-type": "text/event-stream", - "cache-control": "no-cache", - connection: "keep-alive", - - // custom header - "test-header": "test-value", - }); - }); - - it("should pass the messages and the model", async () => { - prepareStreamResponse({ content: [] }); - - await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(await server.getRequestBodyJson()).toStrictEqual({ - stream: true, - stream_options: { include_usage: true }, - model: "anthropic/claude-3.5-sonnet", - messages: [{ role: "user", content: "Hello" }], - }); - }); - - it("should pass headers", async () => { - prepareStreamResponse({ content: [] }); - - const provider = createHyperbolic({ - apiKey: "test-api-key", - headers: { - "Custom-Provider-Header": "provider-header-value", - }, - }); - - await provider.chat("openai/gpt-3.5-turbo").doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - headers: { - "Custom-Request-Header": "request-header-value", - }, - }); - - const requestHeaders = await server.getRequestHeaders(); - - expect(requestHeaders).toStrictEqual({ - authorization: "Bearer test-api-key", - "content-type": "application/json", - "custom-provider-header": "provider-header-value", - "custom-request-header": "request-header-value", - }); - }); - - it("should pass extra body", async () => { - prepareStreamResponse({ content: [] }); - - const provider = createHyperbolic({ - apiKey: "test-api-key", - extraBody: { - custom_field: "custom_value", - providers: { - anthropic: { - custom_field: "custom_value", - }, - }, - }, - }); - - await provider.chat("anthropic/claude-3.5-sonnet").doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - const requestBody = await server.getRequestBodyJson(); - - expect(requestBody).toHaveProperty("custom_field", "custom_value"); - expect(requestBody).toHaveProperty("providers.anthropic.custom_field", "custom_value"); - }); -}); diff --git a/packages/ai-sdk-provider/src/hyperbolic-chat-language-model.ts b/packages/ai-sdk-provider/src/hyperbolic-chat-language-model.ts deleted file mode 100644 index 29d16b2..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-chat-language-model.ts +++ /dev/null @@ -1,659 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { - LanguageModelV1, - LanguageModelV1FinishReason, - LanguageModelV1FunctionTool, - LanguageModelV1LogProbs, - LanguageModelV1ProviderDefinedTool, - LanguageModelV1StreamPart, -} from "@ai-sdk/provider"; -import type { ParseResult } from "@ai-sdk/provider-utils"; -import { InvalidResponseDataError, UnsupportedFunctionalityError } from "@ai-sdk/provider"; -import { - combineHeaders, - createEventSourceResponseHandler, - createJsonResponseHandler, - generateId, - isParsableJson, - postJsonToApi, -} from "@ai-sdk/provider-utils"; -import { z } from "zod"; - -import type { HyperbolicChatModelId, HyperbolicChatSettings } from "./hyperbolic-chat-settings"; -import { convertToHyperbolicChatMessages } from "./convert-to-hyperbolic-chat-messages"; -import { - HyperbolicErrorResponseSchema, - hyperbolicFailedResponseHandler, - isHyperbolicError, - tryParsingHyperbolicError, -} from "./hyperbolic-error"; -import { mapHyperbolicChatLogProbsOutput } from "./map-hyperbolic-chat-logprobs"; -import { mapHyperbolicFinishReason } from "./map-hyperbolic-finish-reason"; - -function isFunctionTool( - tool: LanguageModelV1FunctionTool | LanguageModelV1ProviderDefinedTool, -): tool is LanguageModelV1FunctionTool { - return "parameters" in tool; -} - -type HyperbolicChatConfig = { - provider: string; - compatibility: "strict" | "compatible"; - headers: () => Record; - url: (options: { modelId: string; path: string }) => string; - fetch?: typeof fetch; - extraBody?: Record; -}; - -export class HyperbolicChatLanguageModel implements LanguageModelV1 { - readonly specificationVersion = "v1"; - readonly defaultObjectGenerationMode = "tool"; - - readonly modelId: HyperbolicChatModelId; - readonly settings: HyperbolicChatSettings; - - private readonly config: HyperbolicChatConfig; - - constructor( - modelId: HyperbolicChatModelId, - settings: HyperbolicChatSettings, - config: HyperbolicChatConfig, - ) { - this.modelId = modelId; - this.settings = settings; - this.config = config; - } - - get provider(): string { - return this.config.provider; - } - - private getArgs({ - mode, - prompt, - maxTokens, - temperature, - topP, - frequencyPenalty, - presencePenalty, - seed, - stopSequences, - responseFormat, - topK, - providerMetadata, - }: Parameters[0]) { - const type = mode.type; - const extraCallingBody = providerMetadata?.["hyperbolic"] ?? {}; - - const baseArgs = { - // model id: - model: this.modelId, - models: this.settings.models, - - // model specific settings: - logit_bias: this.settings.logitBias, - logprobs: - this.settings.logprobs === true || typeof this.settings.logprobs === "number" - ? true - : undefined, - top_logprobs: - typeof this.settings.logprobs === "number" - ? this.settings.logprobs - : typeof this.settings.logprobs === "boolean" - ? this.settings.logprobs - ? 0 - : undefined - : undefined, - user: this.settings.user, - parallel_tool_calls: this.settings.parallelToolCalls, - - // standardized settings: - max_tokens: maxTokens, - temperature, - top_p: topP, - frequency_penalty: frequencyPenalty, - presence_penalty: presencePenalty, - seed, - - stop: stopSequences, - response_format: responseFormat, - top_k: topK, - - // messages: - messages: convertToHyperbolicChatMessages(prompt), - - // Hyperbolic specific settings: - include_reasoning: this.settings.includeReasoning, - reasoning: this.settings.reasoning, - - // extra body: - ...this.config.extraBody, - ...this.settings.extraBody, - ...extraCallingBody, - }; - - switch (type) { - case "regular": { - return { ...baseArgs, ...prepareToolsAndToolChoice(mode) }; - } - - case "object-json": { - return { - ...baseArgs, - response_format: { type: "json_object" }, - }; - } - - case "object-tool": { - return { - ...baseArgs, - tool_choice: { type: "function", function: { name: mode.tool.name } }, - tools: [ - { - type: "function", - function: { - name: mode.tool.name, - description: mode.tool.description, - parameters: mode.tool.parameters, - }, - }, - ], - }; - } - - // Handle all non-text types with a single default case - default: { - const _exhaustiveCheck: never = type; - throw new UnsupportedFunctionalityError({ - functionality: `${_exhaustiveCheck} mode`, - }); - } - } - } - async doGenerate( - options: Parameters[0], - ): Promise>> { - const args = this.getArgs(options); - - const { responseHeaders, value: response } = await postJsonToApi({ - url: this.config.url({ - path: "/chat/completions", - modelId: this.modelId, - }), - headers: combineHeaders(this.config.headers(), options.headers), - body: args, - failedResponseHandler: hyperbolicFailedResponseHandler, - successfulResponseHandler: createJsonResponseHandler( - HyperbolicNonStreamChatCompletionResponseSchema, - ), - abortSignal: options.abortSignal, - fetch: this.config.fetch, - }); - - const { messages: rawPrompt, ...rawSettings } = args; - const choice = response.choices[0]; - - if (!choice) { - throw new Error("No choice in response"); - } - - return { - response: { - id: response.id, - modelId: response.model, - }, - text: choice.message.content ?? undefined, - reasoning: choice.message.reasoning ?? undefined, - toolCalls: choice.message.tool_calls?.map((toolCall) => ({ - toolCallType: "function", - toolCallId: toolCall.id ?? generateId(), - toolName: toolCall.function.name, - // eslint-disable-next-line @typescript-eslint/no-non-null-assertion - args: toolCall.function.arguments!, - })), - finishReason: mapHyperbolicFinishReason(choice.finish_reason), - usage: { - promptTokens: response.usage?.prompt_tokens ?? 0, - completionTokens: response.usage?.completion_tokens ?? 0, - }, - rawCall: { rawPrompt, rawSettings }, - rawResponse: { headers: responseHeaders }, - warnings: [], - logprobs: mapHyperbolicChatLogProbsOutput(choice.logprobs), - }; - } - - async doStream( - options: Parameters[0], - ): Promise>> { - const args = this.getArgs(options); - - const { responseHeaders, value: response } = await postJsonToApi({ - url: this.config.url({ - path: "/chat/completions", - modelId: this.modelId, - }), - headers: combineHeaders(this.config.headers(), options.headers), - body: { - ...args, - stream: true, - - // only include stream_options when in strict compatibility mode: - stream_options: - this.config.compatibility === "strict" ? { include_usage: true } : undefined, - }, - failedResponseHandler: hyperbolicFailedResponseHandler, - successfulResponseHandler: createEventSourceResponseHandler( - HyperbolicStreamChatCompletionChunkSchema, - ), - abortSignal: options.abortSignal, - fetch: this.config.fetch, - }); - - const { messages: rawPrompt, ...rawSettings } = args; - - const toolCalls: Array<{ - id: string; - type: "function"; - function: { - name: string; - arguments: string; - }; - }> = []; - - let finishReason: LanguageModelV1FinishReason = "other"; - let usage: { promptTokens: number; completionTokens: number } = { - promptTokens: Number.NaN, - completionTokens: Number.NaN, - }; - let logprobs: LanguageModelV1LogProbs; - - return { - stream: response.pipeThrough( - new TransformStream< - ParseResult>, - LanguageModelV1StreamPart - >({ - transform(chunk, controller) { - // handle failed chunk parsing / validation: - if (!chunk.success) { - finishReason = "error"; - - // Error messages from the API are sometimes an ugly combo of text and JSON in a single chunk, so attempt to parse it as a hyperbolic error. - const maybeHyperbolicError = tryParsingHyperbolicError(chunk.error); - if (maybeHyperbolicError) { - controller.enqueue({ type: "error", error: maybeHyperbolicError }); - return; - } - - controller.enqueue({ - type: "error", - error: chunk.error, - }); - return; - } - - const value = chunk.value; - - // handle error chunks: - if (isHyperbolicError(value)) { - finishReason = "error"; - controller.enqueue({ type: "error", error: value }); - return; - } - - if (value.id) { - controller.enqueue({ - type: "response-metadata", - id: value.id, - }); - } - - if (value.model) { - controller.enqueue({ - type: "response-metadata", - modelId: value.model, - }); - } - - if (value.usage != null) { - usage = { - promptTokens: value.usage.prompt_tokens, - completionTokens: value.usage.completion_tokens, - }; - } - - const choice = value.choices[0]; - - if (choice?.finish_reason != null) { - finishReason = mapHyperbolicFinishReason(choice.finish_reason); - } - - if (choice?.delta == null) { - return; - } - - const delta = choice.delta; - - if (delta.content != null) { - controller.enqueue({ - type: "text-delta", - textDelta: delta.content, - }); - } - - if (delta.reasoning != null) { - controller.enqueue({ - type: "reasoning", - textDelta: delta.reasoning, - }); - } - - const mappedLogprobs = mapHyperbolicChatLogProbsOutput(choice?.logprobs); - if (mappedLogprobs?.length) { - if (logprobs === undefined) logprobs = []; - logprobs.push(...mappedLogprobs); - } - - if (delta.tool_calls != null) { - for (const toolCallDelta of delta.tool_calls) { - const index = toolCallDelta.index; - - // Tool call start. Hyperbolic returns all information except the arguments in the first chunk. - if (toolCalls[index] == null) { - if (toolCallDelta.type !== "function") { - throw new InvalidResponseDataError({ - data: toolCallDelta, - message: `Expected 'function' type.`, - }); - } - - if (toolCallDelta.id == null) { - throw new InvalidResponseDataError({ - data: toolCallDelta, - message: `Expected 'id' to be a string.`, - }); - } - - if (toolCallDelta.function?.name == null) { - throw new InvalidResponseDataError({ - data: toolCallDelta, - message: `Expected 'function.name' to be a string.`, - }); - } - - toolCalls[index] = { - id: toolCallDelta.id, - type: "function", - function: { - name: toolCallDelta.function.name, - arguments: toolCallDelta.function.arguments ?? "", - }, - }; - - const toolCall = toolCalls[index]; - - if (toolCall == null) { - throw new Error("Tool call is missing"); - } - - // check if tool call is complete (some providers send the full tool call in one chunk) - if ( - toolCall.function?.name != null && - toolCall.function?.arguments != null && - isParsableJson(toolCall.function.arguments) - ) { - // send delta - controller.enqueue({ - type: "tool-call-delta", - toolCallType: "function", - toolCallId: toolCall.id, - toolName: toolCall.function.name, - argsTextDelta: toolCall.function.arguments, - }); - - // send tool call - controller.enqueue({ - type: "tool-call", - toolCallType: "function", - toolCallId: toolCall.id ?? generateId(), - toolName: toolCall.function.name, - args: toolCall.function.arguments, - }); - } - - continue; - } - - // existing tool call, merge - const toolCall = toolCalls[index]; - - if (toolCall == null) { - throw new Error("Tool call is missing"); - } - - if (toolCallDelta.function?.arguments != null) { - // eslint-disable-next-line @typescript-eslint/no-non-null-assertion - toolCall.function!.arguments += toolCallDelta.function?.arguments ?? ""; - } - - // send delta - controller.enqueue({ - type: "tool-call-delta", - toolCallType: "function", - toolCallId: toolCall.id, - toolName: toolCall.function.name, - argsTextDelta: toolCallDelta.function.arguments ?? "", - }); - - // check if tool call is complete - if ( - toolCall.function?.name != null && - toolCall.function?.arguments != null && - isParsableJson(toolCall.function.arguments) - ) { - controller.enqueue({ - type: "tool-call", - toolCallType: "function", - toolCallId: toolCall.id ?? generateId(), - toolName: toolCall.function.name, - args: toolCall.function.arguments, - }); - } - } - } - }, - - flush(controller) { - controller.enqueue({ - type: "finish", - finishReason, - logprobs, - usage, - }); - }, - }), - ), - rawCall: { rawPrompt, rawSettings }, - rawResponse: { headers: responseHeaders }, - warnings: [], - }; - } -} - -const HyperbolicChatCompletionBaseResponseSchema = z.object({ - id: z.string().optional(), - model: z.string().optional(), - usage: z - .object({ - prompt_tokens: z.number(), - completion_tokens: z.number(), - total_tokens: z.number(), - }) - .nullish(), -}); - -// limited version of the schema, focussed on what is needed for the implementation -// this approach limits breakages when the API changes and increases efficiency -const HyperbolicNonStreamChatCompletionResponseSchema = - HyperbolicChatCompletionBaseResponseSchema.extend({ - choices: z.array( - z.object({ - message: z.object({ - role: z.literal("assistant"), - content: z.string().nullable().optional(), - reasoning: z.string().nullable().optional(), - tool_calls: z - .array( - z.object({ - id: z.string().optional().nullable(), - type: z.literal("function"), - function: z.object({ - name: z.string(), - arguments: z.string(), - }), - }), - ) - .optional(), - }), - index: z.number(), - logprobs: z - .object({ - content: z - .array( - z.object({ - token: z.string(), - logprob: z.number(), - top_logprobs: z.array( - z.object({ - token: z.string(), - logprob: z.number(), - }), - ), - }), - ) - .nullable(), - }) - .nullable() - .optional(), - finish_reason: z.string().optional().nullable(), - }), - ), - }); - -// limited version of the schema, focussed on what is needed for the implementation -// this approach limits breakages when the API changes and increases efficiency -const HyperbolicStreamChatCompletionChunkSchema = z.union([ - HyperbolicChatCompletionBaseResponseSchema.extend({ - choices: z.array( - z.object({ - delta: z - .object({ - role: z.enum(["assistant"]).optional(), - content: z.string().nullish(), - reasoning: z.string().nullish().optional(), - tool_calls: z - .array( - z.object({ - index: z.number(), - id: z.string().nullish(), - type: z.literal("function").optional(), - function: z.object({ - name: z.string().nullish(), - arguments: z.string().nullish(), - }), - }), - ) - .nullish(), - }) - .nullish(), - logprobs: z - .object({ - content: z - .array( - z.object({ - token: z.string(), - logprob: z.number(), - top_logprobs: z.array( - z.object({ - token: z.string(), - logprob: z.number(), - }), - ), - }), - ) - .nullable(), - }) - .nullish(), - finish_reason: z.string().nullable().optional(), - index: z.number(), - }), - ), - }), - HyperbolicErrorResponseSchema, -]); - -function prepareToolsAndToolChoice( - mode: Parameters[0]["mode"] & { - type: "regular"; - }, -) { - // when the tools array is empty, change it to undefined to prevent errors: - const tools = mode.tools?.length ? mode.tools : undefined; - - if (tools == null) { - return { tools: undefined, tool_choice: undefined }; - } - - const mappedTools = tools.map((tool) => { - if (isFunctionTool(tool)) { - return { - type: "function" as const, - function: { - name: tool.name, - description: tool.description, - parameters: tool.parameters, - }, - }; - } else { - return { - type: "function" as const, - function: { - name: tool.name, - }, - }; - } - }); - - const toolChoice = mode.toolChoice; - - if (toolChoice == null) { - return { tools: mappedTools, tool_choice: undefined }; - } - - const type = toolChoice.type; - - switch (type) { - case "auto": - case "none": - case "required": - return { tools: mappedTools, tool_choice: type }; - case "tool": - return { - tools: mappedTools, - tool_choice: { - type: "function", - function: { - name: toolChoice.toolName, - }, - }, - }; - default: { - const _exhaustiveCheck: never = type; - throw new Error(`Unsupported tool choice type: ${_exhaustiveCheck}`); - } - } -} diff --git a/packages/ai-sdk-provider/src/hyperbolic-chat-prompt.ts b/packages/ai-sdk-provider/src/hyperbolic-chat-prompt.ts deleted file mode 100644 index f1c2a1e..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-chat-prompt.ts +++ /dev/null @@ -1,67 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -// Type for Hyperbolic Cache Control following Anthropic's pattern -export type HyperbolicCacheControl = { type: "ephemeral" }; - -export type HyperbolicChatPrompt = Array; - -export type ChatCompletionMessageParam = - | ChatCompletionSystemMessageParam - | ChatCompletionUserMessageParam - | ChatCompletionAssistantMessageParam - | ChatCompletionToolMessageParam; - -export interface ChatCompletionSystemMessageParam { - role: "system"; - content: string; - cache_control?: HyperbolicCacheControl; -} - -export interface ChatCompletionUserMessageParam { - role: "user"; - content: string | Array; - cache_control?: HyperbolicCacheControl; -} - -export type ChatCompletionContentPart = - | ChatCompletionContentPartText - | ChatCompletionContentPartImage; - -export interface ChatCompletionContentPartImage { - type: "image_url"; - image_url: { - url: string; - }; - cache_control?: HyperbolicCacheControl; -} - -export interface ChatCompletionContentPartText { - type: "text"; - text: string; - cache_control?: HyperbolicCacheControl; -} - -export interface ChatCompletionAssistantMessageParam { - role: "assistant"; - content?: string | null; - tool_calls?: Array; - cache_control?: HyperbolicCacheControl; -} - -export interface ChatCompletionMessageToolCall { - type: "function"; - id: string; - function: { - arguments: string; - name: string; - }; -} - -export interface ChatCompletionToolMessageParam { - role: "tool"; - content: string; - tool_call_id: string; - cache_control?: HyperbolicCacheControl; -} diff --git a/packages/ai-sdk-provider/src/hyperbolic-chat-settings.ts b/packages/ai-sdk-provider/src/hyperbolic-chat-settings.ts deleted file mode 100644 index 76c8fc9..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-chat-settings.ts +++ /dev/null @@ -1,50 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { HyperbolicSharedSettings } from "./types"; - -// https://app.hyperbolic.xyz/models -export type HyperbolicChatModelId = string; - -export type HyperbolicChatSettings = { - /** - * Modify the likelihood of specified tokens appearing in the completion. - * - * Accepts a JSON object that maps tokens (specified by their token ID in - * the GPT tokenizer) to an associated bias value from -100 to 100. You - * can use this tokenizer tool to convert text to token IDs. Mathematically, - * the bias is added to the logits generated by the model prior to sampling. - * The exact effect will vary per model, but values between -1 and 1 should - * decrease or increase likelihood of selection; values like -100 or 100 - * should result in a ban or exclusive selection of the relevant token. - * - * As an example, you can pass {"50256": -100} to prevent the <|endoftext|> - * token from being generated. - */ - logitBias?: Record; - - /** - * Return the log probabilities of the tokens. Including logprobs will increase - * the response size and can slow down response times. However, it can - * be useful to better understand how the model is behaving. - * - * Setting to true will return the log probabilities of the tokens that - * were generated. - * - * Setting to a number will return the log probabilities of the top n - * tokens that were generated. - */ - logprobs?: boolean | number; - - /** - * Whether to enable parallel function calling during tool use. Default to true. - */ - parallelToolCalls?: boolean; - - /** - * A unique identifier representing your end-user, which can help Hyperbolic - * to monitor and detect abuse. Learn more. - */ - user?: string; -} & HyperbolicSharedSettings; diff --git a/packages/ai-sdk-provider/src/hyperbolic-completion-language-model.test.ts b/packages/ai-sdk-provider/src/hyperbolic-completion-language-model.test.ts deleted file mode 100644 index 9fdaec6..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-completion-language-model.test.ts +++ /dev/null @@ -1,496 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { LanguageModelV1Prompt } from "@ai-sdk/provider"; -import { - convertReadableStreamToArray, - JsonTestServer, - StreamingTestServer, -} from "@ai-sdk/provider-utils/test"; -import { describe, expect, it } from "vitest"; - -import { createHyperbolic } from "./hyperbolic-provider"; -import { mapHyperbolicCompletionLogProbs } from "./map-hyperbolic-completion-logprobs"; - -const TEST_PROMPT: LanguageModelV1Prompt = [ - { role: "user", content: [{ type: "text", text: "Hello" }] }, -]; - -const TEST_LOGPROBS = { - tokens: [" ever", " after", ".\n\n", "The", " end", "."], - token_logprobs: [-0.0664508, -0.014520033, -1.3820221, -0.7890417, -0.5323165, -0.10247037], - top_logprobs: [ - { - " ever": -0.0664508, - }, - { - " after": -0.014520033, - }, - { - ".\n\n": -1.3820221, - }, - { - The: -0.7890417, - }, - { - " end": -0.5323165, - }, - { - ".": -0.10247037, - }, - ] as Record[], -}; - -const provider = createHyperbolic({ - apiKey: "test-api-key", - compatibility: "strict", -}); - -const model = provider.completion("meta-llama/Llama-3.1-405B-FP8"); - -describe("doGenerate", () => { - const server = new JsonTestServer("https://api.hyperbolic.xyz/v1/completions"); - server.setupTestEnvironment(); - - function prepareJsonResponse({ - content = "", - usage = { - prompt_tokens: 4, - total_tokens: 34, - completion_tokens: 30, - }, - logprobs = null, - finish_reason = "stop", - }: { - content?: string; - usage?: { - prompt_tokens: number; - total_tokens: number; - completion_tokens: number; - }; - logprobs?: { - tokens: string[]; - token_logprobs: number[]; - top_logprobs: Record[]; - } | null; - finish_reason?: string; - }) { - server.responseBodyJson = { - id: "cmpl-96cAM1v77r4jXa4qb2NSmRREV5oWB", - object: "text_completion", - created: 1711363706, - model: "meta-llama/Llama-3.1-405B-FP8", - choices: [ - { - text: content, - index: 0, - logprobs, - finish_reason, - }, - ], - usage, - }; - } - - it("should extract text response", async () => { - prepareJsonResponse({ content: "Hello, World!" }); - - const { text } = await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(text).toStrictEqual("Hello, World!"); - }); - - it("should extract usage", async () => { - prepareJsonResponse({ - content: "", - usage: { prompt_tokens: 20, total_tokens: 25, completion_tokens: 5 }, - }); - - const { usage } = await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(usage).toStrictEqual({ - promptTokens: 20, - completionTokens: 5, - }); - }); - - it("should extract logprobs", async () => { - prepareJsonResponse({ logprobs: TEST_LOGPROBS }); - - const provider = createHyperbolic({ apiKey: "test-api-key" }); - - const response = await provider.completion("openai/gpt-3.5-turbo", { logprobs: 1 }).doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - expect(response.logprobs).toStrictEqual(mapHyperbolicCompletionLogProbs(TEST_LOGPROBS)); - }); - - it("should extract finish reason", async () => { - prepareJsonResponse({ - content: "", - finish_reason: "stop", - }); - - const { finishReason } = await provider.completion("meta-llama/Llama-3.1-405B-FP8").doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(finishReason).toStrictEqual("stop"); - }); - - it("should support unknown finish reason", async () => { - prepareJsonResponse({ - content: "", - finish_reason: "eos", - }); - - const { finishReason } = await provider.completion("meta-llama/Llama-3.1-405B-FP8").doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(finishReason).toStrictEqual("unknown"); - }); - - it("should expose the raw response headers", async () => { - prepareJsonResponse({ content: "" }); - - server.responseHeaders = { - "test-header": "test-value", - }; - - const { rawResponse } = await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(rawResponse?.headers).toStrictEqual({ - // default headers: - "content-length": "273", - "content-type": "application/json", - - // custom header - "test-header": "test-value", - }); - }); - - it("should pass the model and the prompt", async () => { - prepareJsonResponse({ content: "" }); - - await model.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(await server.getRequestBodyJson()).toStrictEqual({ - model: "meta-llama/Llama-3.1-405B-FP8", - prompt: "Hello", - }); - }); - - it("should pass the models array when provided", async () => { - prepareJsonResponse({ content: "" }); - - const customModel = provider.completion("meta-llama/Llama-3.1-405B-FP8", { - models: ["openai/gpt-4", "anthropic/claude-2"], - }); - - await customModel.doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(await server.getRequestBodyJson()).toStrictEqual({ - model: "meta-llama/Llama-3.1-405B-FP8", - models: ["openai/gpt-4", "anthropic/claude-2"], - prompt: "Hello", - }); - }); - - it("should pass headers", async () => { - prepareJsonResponse({ content: "" }); - - const provider = createHyperbolic({ - apiKey: "test-api-key", - headers: { - "Custom-Provider-Header": "provider-header-value", - }, - }); - - await provider.completion("meta-llama/Llama-3.1-405B-FP8").doGenerate({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - headers: { - "Custom-Request-Header": "request-header-value", - }, - }); - - const requestHeaders = await server.getRequestHeaders(); - - expect(requestHeaders).toStrictEqual({ - authorization: "Bearer test-api-key", - "content-type": "application/json", - "custom-provider-header": "provider-header-value", - "custom-request-header": "request-header-value", - }); - }); -}); - -describe("doStream", () => { - const server = new StreamingTestServer("https://api.hyperbolic.xyz/v1/completions"); - - server.setupTestEnvironment(); - - function prepareStreamResponse({ - content, - finish_reason = "stop", - usage = { - prompt_tokens: 10, - total_tokens: 372, - completion_tokens: 362, - }, - logprobs = null, - }: { - content: string[]; - usage?: { - prompt_tokens: number; - total_tokens: number; - completion_tokens: number; - }; - logprobs?: { - tokens: string[]; - token_logprobs: number[]; - top_logprobs: Record[]; - } | null; - finish_reason?: string; - }) { - server.responseChunks = [ - ...content.map((text) => { - return ( - `data: {"id":"cmpl-96c64EdfhOw8pjFFgVpLuT8k2MtdT","object":"text_completion","created":1711363440,` + - `"choices":[{"text":"${text}","index":0,"logprobs":null,"finish_reason":null}],"model":"meta-llama/Llama-3.1-405B-FP8"}\n\n` - ); - }), - `data: {"id":"cmpl-96c3yLQE1TtZCd6n6OILVmzev8M8H","object":"text_completion","created":1711363310,` + - `"choices":[{"text":"","index":0,"logprobs":${JSON.stringify( - logprobs, - )},"finish_reason":"${finish_reason}"}],"model":"meta-llama/Llama-3.1-405B-FP8"}\n\n`, - `data: {"id":"cmpl-96c3yLQE1TtZCd6n6OILVmzev8M8H","object":"text_completion","created":1711363310,` + - `"model":"meta-llama/Llama-3.1-405B-FP8","usage":${JSON.stringify( - usage, - )},"choices":[]}\n\n`, - "data: [DONE]\n\n", - ]; - } - - it("should stream text deltas", async () => { - prepareStreamResponse({ - content: ["Hello", ", ", "World!"], - finish_reason: "stop", - usage: { - prompt_tokens: 10, - total_tokens: 372, - completion_tokens: 362, - }, - logprobs: TEST_LOGPROBS, - }); - - const { stream } = await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - // note: space moved to last chunk bc of trimming - expect(await convertReadableStreamToArray(stream)).toStrictEqual([ - { type: "text-delta", textDelta: "Hello" }, - { type: "text-delta", textDelta: ", " }, - { type: "text-delta", textDelta: "World!" }, - { type: "text-delta", textDelta: "" }, - { - type: "finish", - finishReason: "stop", - logprobs: mapHyperbolicCompletionLogProbs(TEST_LOGPROBS), - usage: { promptTokens: 10, completionTokens: 362 }, - }, - ]); - }); - - it("should handle error stream parts", async () => { - server.responseChunks = [ - `data: {"object": "error", "message": "The server had an error processing your request. Sorry about that! You can retry your request, or contact us through our ` + - `help center at app.hyperbolic.xyz/support if you keep seeing this error.","type":"server_error","param":null,"code":null}\n\n`, - "data: [DONE]\n\n", - ]; - - const { stream } = await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(await convertReadableStreamToArray(stream)).toStrictEqual([ - { - type: "error", - error: { - object: "error", - message: - "The server had an error processing your request. Sorry about that! " + - "You can retry your request, or contact us through our help center at " + - "app.hyperbolic.xyz/support if you keep seeing this error.", - type: "server_error", - code: null, - param: null, - }, - }, - { - finishReason: "error", - logprobs: undefined, - type: "finish", - usage: { - completionTokens: NaN, - promptTokens: NaN, - }, - }, - ]); - }); - - it("should handle unparsable stream parts", async () => { - server.responseChunks = [`data: {unparsable}\n\n`, "data: [DONE]\n\n"]; - - const { stream } = await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - const elements = await convertReadableStreamToArray(stream); - - expect(elements.length).toBe(2); - expect(elements[0]?.type).toBe("error"); - expect(elements[1]).toStrictEqual({ - finishReason: "error", - logprobs: undefined, - type: "finish", - usage: { - completionTokens: NaN, - promptTokens: NaN, - }, - }); - }); - - it("should expose the raw response headers", async () => { - prepareStreamResponse({ content: [] }); - - server.responseHeaders = { - "test-header": "test-value", - }; - - const { rawResponse } = await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(rawResponse?.headers).toStrictEqual({ - // default headers: - "content-type": "text/event-stream", - "cache-control": "no-cache", - connection: "keep-alive", - - // custom header - "test-header": "test-value", - }); - }); - - it("should pass the model and the prompt", async () => { - prepareStreamResponse({ content: [] }); - - await model.doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - expect(await server.getRequestBodyJson()).toStrictEqual({ - stream: true, - stream_options: { include_usage: true }, - model: "meta-llama/Llama-3.1-405B-FP8", - prompt: "Hello", - }); - }); - - it("should pass headers", async () => { - prepareStreamResponse({ content: [] }); - - const provider = createHyperbolic({ - apiKey: "test-api-key", - headers: { - "Custom-Provider-Header": "provider-header-value", - }, - }); - - await provider.completion("meta-llama/Llama-3.1-405B-FP8").doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - headers: { - "Custom-Request-Header": "request-header-value", - }, - }); - - const requestHeaders = await server.getRequestHeaders(); - - expect(requestHeaders).toStrictEqual({ - authorization: "Bearer test-api-key", - "content-type": "application/json", - "custom-provider-header": "provider-header-value", - "custom-request-header": "request-header-value", - }); - }); - - it("should pass extra body", async () => { - prepareStreamResponse({ content: [] }); - - const provider = createHyperbolic({ - apiKey: "test-api-key", - extraBody: { - custom_field: "custom_value", - providers: { - anthropic: { - custom_field: "custom_value", - }, - }, - }, - }); - - await provider.completion("openai/gpt-4o").doStream({ - inputFormat: "prompt", - mode: { type: "regular" }, - prompt: TEST_PROMPT, - }); - - const requestBody = await server.getRequestBodyJson(); - - expect(requestBody).toHaveProperty("custom_field", "custom_value"); - expect(requestBody).toHaveProperty("providers.anthropic.custom_field", "custom_value"); - }); -}); diff --git a/packages/ai-sdk-provider/src/hyperbolic-completion-language-model.ts b/packages/ai-sdk-provider/src/hyperbolic-completion-language-model.ts deleted file mode 100644 index a37c22c..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-completion-language-model.ts +++ /dev/null @@ -1,352 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { - LanguageModelV1, - LanguageModelV1FinishReason, - LanguageModelV1LogProbs, - LanguageModelV1StreamPart, -} from "@ai-sdk/provider"; -import type { ParseResult } from "@ai-sdk/provider-utils"; -import { UnsupportedFunctionalityError } from "@ai-sdk/provider"; -import { - combineHeaders, - createEventSourceResponseHandler, - createJsonResponseHandler, - postJsonToApi, -} from "@ai-sdk/provider-utils"; -import { z } from "zod"; - -import type { - HyperbolicCompletionModelId, - HyperbolicCompletionSettings, -} from "./hyperbolic-completion-settings"; -import { convertToHyperbolicCompletionPrompt } from "./convert-to-hyperbolic-completion-prompt"; -import { - HyperbolicErrorResponseSchema, - hyperbolicFailedResponseHandler, - isHyperbolicError, -} from "./hyperbolic-error"; -import { mapHyperbolicCompletionLogProbs } from "./map-hyperbolic-completion-logprobs"; -import { mapHyperbolicFinishReason } from "./map-hyperbolic-finish-reason"; - -type HyperbolicCompletionConfig = { - provider: string; - compatibility: "strict" | "compatible"; - headers: () => Record; - url: (options: { modelId: string; path: string }) => string; - fetch?: typeof fetch; - extraBody?: Record; -}; - -export class HyperbolicCompletionLanguageModel implements LanguageModelV1 { - readonly specificationVersion = "v1"; - readonly defaultObjectGenerationMode = undefined; - - readonly modelId: HyperbolicCompletionModelId; - readonly settings: HyperbolicCompletionSettings; - - private readonly config: HyperbolicCompletionConfig; - - constructor( - modelId: HyperbolicCompletionModelId, - settings: HyperbolicCompletionSettings, - config: HyperbolicCompletionConfig, - ) { - this.modelId = modelId; - this.settings = settings; - this.config = config; - } - - get provider(): string { - return this.config.provider; - } - - private getArgs({ - mode, - inputFormat, - prompt, - maxTokens, - temperature, - topP, - frequencyPenalty, - presencePenalty, - seed, - responseFormat, - topK, - stopSequences, - providerMetadata, - }: Parameters[0]) { - const type = mode.type; - - const extraCallingBody = providerMetadata?.["hyperbolic"] ?? {}; - - const { prompt: completionPrompt } = convertToHyperbolicCompletionPrompt({ - prompt, - inputFormat, - }); - - const baseArgs = { - // model id: - model: this.modelId, - models: this.settings.models, - - // model specific settings: - logit_bias: this.settings.logitBias, - logprobs: - typeof this.settings.logprobs === "number" - ? this.settings.logprobs - : typeof this.settings.logprobs === "boolean" - ? this.settings.logprobs - ? 0 - : undefined - : undefined, - suffix: this.settings.suffix, - user: this.settings.user, - - // standardized settings: - max_tokens: maxTokens, - temperature, - top_p: topP, - frequency_penalty: frequencyPenalty, - presence_penalty: presencePenalty, - seed, - - stop: stopSequences, - response_format: responseFormat, - top_k: topK, - - // prompt: - prompt: completionPrompt, - - // Hyperbolic specific settings: - include_reasoning: this.settings.includeReasoning, - reasoning: this.settings.reasoning, - - // extra body: - ...this.config.extraBody, - ...this.settings.extraBody, - ...extraCallingBody, - }; - - switch (type) { - case "regular": { - if (mode.tools?.length) { - throw new UnsupportedFunctionalityError({ - functionality: "tools", - }); - } - - if (mode.toolChoice) { - throw new UnsupportedFunctionalityError({ - functionality: "toolChoice", - }); - } - - return baseArgs; - } - - case "object-json": { - throw new UnsupportedFunctionalityError({ - functionality: "object-json mode", - }); - } - - case "object-tool": { - throw new UnsupportedFunctionalityError({ - functionality: "object-tool mode", - }); - } - - // Handle all non-text types with a single default case - default: { - const _exhaustiveCheck: never = type; - throw new UnsupportedFunctionalityError({ - functionality: `${_exhaustiveCheck} mode`, - }); - } - } - } - - async doGenerate( - options: Parameters[0], - ): Promise>> { - const args = this.getArgs(options); - - const { responseHeaders, value: response } = await postJsonToApi({ - url: this.config.url({ - path: "/completions", - modelId: this.modelId, - }), - headers: combineHeaders(this.config.headers(), options.headers), - body: args, - failedResponseHandler: hyperbolicFailedResponseHandler, - successfulResponseHandler: createJsonResponseHandler(HyperbolicCompletionChunkSchema), - abortSignal: options.abortSignal, - fetch: this.config.fetch, - }); - - const { prompt: rawPrompt, ...rawSettings } = args; - if (isHyperbolicError(response)) { - throw new Error(`${response.message}`); - } - - const choice = response.choices[0]; - - if (!choice) { - throw new Error("No choice in Hyperbolic completion response"); - } - - return { - response: { - id: response.id, - modelId: response.model, - }, - text: choice.text ?? "", - reasoning: choice.reasoning || undefined, - usage: { - promptTokens: response.usage?.prompt_tokens ?? 0, - completionTokens: response.usage?.completion_tokens ?? 0, - }, - finishReason: mapHyperbolicFinishReason(choice.finish_reason), - logprobs: mapHyperbolicCompletionLogProbs(choice.logprobs), - rawCall: { rawPrompt, rawSettings }, - rawResponse: { headers: responseHeaders }, - warnings: [], - }; - } - - async doStream( - options: Parameters[0], - ): Promise>> { - const args = this.getArgs(options); - - const { responseHeaders, value: response } = await postJsonToApi({ - url: this.config.url({ - path: "/completions", - modelId: this.modelId, - }), - headers: combineHeaders(this.config.headers(), options.headers), - body: { - ...this.getArgs(options), - stream: true, - - // only include stream_options when in strict compatibility mode: - stream_options: - this.config.compatibility === "strict" ? { include_usage: true } : undefined, - }, - failedResponseHandler: hyperbolicFailedResponseHandler, - successfulResponseHandler: createEventSourceResponseHandler(HyperbolicCompletionChunkSchema), - abortSignal: options.abortSignal, - fetch: this.config.fetch, - }); - - const { prompt: rawPrompt, ...rawSettings } = args; - - let finishReason: LanguageModelV1FinishReason = "other"; - let usage: { promptTokens: number; completionTokens: number } = { - promptTokens: Number.NaN, - completionTokens: Number.NaN, - }; - let logprobs: LanguageModelV1LogProbs; - - return { - stream: response.pipeThrough( - new TransformStream< - ParseResult>, - LanguageModelV1StreamPart - >({ - transform(chunk, controller) { - // handle failed chunk parsing / validation: - if (!chunk.success) { - finishReason = "error"; - controller.enqueue({ type: "error", error: chunk.error }); - return; - } - - const value = chunk.value; - - // handle error chunks: - if (isHyperbolicError(value)) { - finishReason = "error"; - controller.enqueue({ type: "error", error: value }); - return; - } - - if (value.usage != null) { - usage = { - promptTokens: value.usage.prompt_tokens, - completionTokens: value.usage.completion_tokens, - }; - } - - const choice = value.choices[0]; - - if (choice?.finish_reason != null) { - finishReason = mapHyperbolicFinishReason(choice.finish_reason); - } - - if (choice?.text != null) { - controller.enqueue({ - type: "text-delta", - textDelta: choice.text, - }); - } - - const mappedLogprobs = mapHyperbolicCompletionLogProbs(choice?.logprobs); - if (mappedLogprobs?.length) { - if (logprobs === undefined) logprobs = []; - logprobs.push(...mappedLogprobs); - } - }, - - flush(controller) { - controller.enqueue({ - type: "finish", - finishReason, - logprobs, - usage, - }); - }, - }), - ), - rawCall: { rawPrompt, rawSettings }, - rawResponse: { headers: responseHeaders }, - warnings: [], - }; - } -} - -// limited version of the schema, focussed on what is needed for the implementation -// this approach limits breakages when the API changes and increases efficiency -const HyperbolicCompletionChunkSchema = z.union([ - z.object({ - id: z.string().optional(), - model: z.string().optional(), - choices: z.array( - z.object({ - text: z.string(), - reasoning: z.string().nullish().optional(), - finish_reason: z.string().nullish(), - index: z.number(), - logprobs: z - .object({ - tokens: z.array(z.string()), - token_logprobs: z.array(z.number()), - top_logprobs: z.array(z.record(z.string(), z.number())).nullable(), - }) - .nullable() - .optional(), - }), - ), - usage: z - .object({ - prompt_tokens: z.number(), - completion_tokens: z.number(), - }) - .optional() - .nullable(), - }), - HyperbolicErrorResponseSchema, -]); diff --git a/packages/ai-sdk-provider/src/hyperbolic-completion-settings.ts b/packages/ai-sdk-provider/src/hyperbolic-completion-settings.ts deleted file mode 100644 index efc31a0..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-completion-settings.ts +++ /dev/null @@ -1,42 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { HyperbolicSharedSettings } from "./types"; - -export type HyperbolicCompletionModelId = string; - -export type HyperbolicCompletionSettings = { - /** - * Modify the likelihood of specified tokens appearing in the completion. - * - * Accepts a JSON object that maps tokens (specified by their token ID in - * the GPT tokenizer) to an associated bias value from -100 to 100. You - * can use this tokenizer tool to convert text to token IDs. Mathematically, - * the bias is added to the logits generated by the model prior to sampling. - * The exact effect will vary per model, but values between -1 and 1 should - * decrease or increase likelihood of selection; values like -100 or 100 - * should result in a ban or exclusive selection of the relevant token. - * As an example, you can pass {"50256": -100} to prevent the <|endoftext|> - * token from being generated. - */ - logitBias?: Record; - - /** - * Return the log probabilities of the tokens. Including logprobs will increase - * the response size and can slow down response times. However, it can - * be useful to better understand how the model is behaving. - * - * Setting to true will return the log probabilities of the tokens that - * were generated. - * - * Setting to a number will return the log probabilities of the top n - * tokens that were generated. - */ - logprobs?: boolean | number; - - /** - * The suffix that comes after a completion of inserted text. - */ - suffix?: string; -} & HyperbolicSharedSettings; diff --git a/packages/ai-sdk-provider/src/hyperbolic-error.ts b/packages/ai-sdk-provider/src/hyperbolic-error.ts deleted file mode 100644 index 60eed7e..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-error.ts +++ /dev/null @@ -1,49 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { TypeValidationError } from "ai"; -import { createJsonErrorResponseHandler } from "@ai-sdk/provider-utils"; -import { JSONParseError } from "ai"; -import { z } from "zod"; - -export const HyperbolicErrorResponseSchema = z.object({ - object: z.literal("error"), - message: z.string(), - type: z.string(), - param: z.any().nullable(), - code: z.coerce.number().nullable(), -}); - -// eslint-disable-next-line @typescript-eslint/no-explicit-any -export const isHyperbolicError = (data: any): data is HyperbolicErrorData => { - return "object" in data && data.object === "error"; -}; - -export type HyperbolicErrorData = z.infer; - -export const hyperbolicFailedResponseHandler = createJsonErrorResponseHandler({ - errorSchema: HyperbolicErrorResponseSchema, - errorToMessage: (data) => data.message, -}); - -/** - * Error messages from the API are sometimes an ugly combo of text and JSON in a single chunk. Extract data from error message if it contains JSON - */ -export const tryParsingHyperbolicError = (error: JSONParseError | TypeValidationError) => { - if (!JSONParseError.isInstance(error)) { - return undefined; - } - - const jsonMatch = error.text.match(/\{.*\}/); // Match between brackets - if (jsonMatch) { - try { - const parsedErrorJson = JSON.parse(jsonMatch[0]); - if (parsedErrorJson.message) { - return HyperbolicErrorResponseSchema.parse(parsedErrorJson); - } - } catch { - return undefined; - } - } -}; diff --git a/packages/ai-sdk-provider/src/hyperbolic-provider-options.test.ts b/packages/ai-sdk-provider/src/hyperbolic-provider-options.test.ts deleted file mode 100644 index b1db769..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-provider-options.test.ts +++ /dev/null @@ -1,64 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { LanguageModelV1Prompt } from "@ai-sdk/provider"; -import { createTestServer } from "@ai-sdk/provider-utils/test"; -import { streamText } from "ai"; -import { describe, expect, it, vi } from "vitest"; - -import { createHyperbolic } from "./hyperbolic-provider"; - -// Add type assertions for the mocked classes -const TEST_MESSAGES: LanguageModelV1Prompt = [ - { role: "user", content: [{ type: "text", text: "Hello" }] }, -]; - -describe("providerOptions", () => { - const server = createTestServer({ - "https://api.hyperbolic.xyz/v1/chat/completions": { - response: { - type: "stream-chunks", - chunks: [], - }, - }, - }); - - beforeEach(() => { - vi.clearAllMocks(); - }); - - it("should set providerOptions hyperbolic to extra body", async () => { - const hyperbolic = createHyperbolic({ - apiKey: "test", - }); - const model = hyperbolic("Qwen/Qwen2.5-72B-Instruct"); - - await streamText({ - model, - messages: TEST_MESSAGES, - providerOptions: { - hyperbolic: { - reasoning: { - max_tokens: 1000, - }, - }, - }, - }).consumeStream(); - - expect(await server.calls[0]?.requestBody).toStrictEqual({ - messages: [ - { - content: "Hello", - role: "user", - }, - ], - reasoning: { - max_tokens: 1000, - }, - temperature: 0, - model: "Qwen/Qwen2.5-72B-Instruct", - stream: true, - }); - }); -}); diff --git a/packages/ai-sdk-provider/src/hyperbolic-provider.ts b/packages/ai-sdk-provider/src/hyperbolic-provider.ts deleted file mode 100644 index e878dcf..0000000 --- a/packages/ai-sdk-provider/src/hyperbolic-provider.ts +++ /dev/null @@ -1,180 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import { loadApiKey, withoutTrailingSlash } from "@ai-sdk/provider-utils"; - -import type { HyperbolicChatModelId, HyperbolicChatSettings } from "./hyperbolic-chat-settings"; -import type { - HyperbolicCompletionModelId, - HyperbolicCompletionSettings, -} from "./hyperbolic-completion-settings"; -import type { HyperbolicImageModelId, HyperbolicImageSettings } from "./hyperbolic-image-settings"; -import { HyperbolicChatLanguageModel } from "./hyperbolic-chat-language-model"; -import { HyperbolicCompletionLanguageModel } from "./hyperbolic-completion-language-model"; -import { HyperbolicImageModel } from "./hyperbolic-image-language-model"; - -export type { HyperbolicCompletionSettings }; - -export interface HyperbolicProvider { - ( - modelId: HyperbolicChatModelId, - settings?: HyperbolicCompletionSettings, - ): HyperbolicCompletionLanguageModel; - (modelId: HyperbolicChatModelId, settings?: HyperbolicChatSettings): HyperbolicChatLanguageModel; - - languageModel( - modelId: HyperbolicChatModelId, - settings?: HyperbolicCompletionSettings, - ): HyperbolicCompletionLanguageModel; - languageModel( - modelId: HyperbolicChatModelId, - settings?: HyperbolicChatSettings, - ): HyperbolicChatLanguageModel; - - /** - * Creates a Hyperbolic chat model for text generation. - */ - chat( - modelId: HyperbolicChatModelId, - settings?: HyperbolicChatSettings, - ): HyperbolicChatLanguageModel; - - /** - * Creates a Hyperbolic completion model for text generation. - */ - completion( - modelId: HyperbolicCompletionModelId, - settings?: HyperbolicCompletionSettings, - ): HyperbolicCompletionLanguageModel; - - /** - * Creates a Hyperbolic image model for image generation. - */ - image(modelId: HyperbolicImageModelId, settings?: HyperbolicImageSettings): HyperbolicImageModel; -} - -export interface HyperbolicProviderSettings { - /** - * Base URL for the Hyperbolic API calls. - */ - baseURL?: string; - - /** - * @deprecated Use `baseURL` instead. - */ - baseUrl?: string; - - /** - * API key for authenticating requests. - */ - apiKey?: string; - - /** - * Custom headers to include in the requests. - */ - headers?: Record; - - /** - * Hyperbolic compatibility mode. Should be set to `strict` when using the Hyperbolic API, - * and `compatible` when using 3rd party providers. In `compatible` mode, newer - * information such as streamOptions are not being sent. Defaults to 'compatible'. - */ - compatibility?: "strict" | "compatible"; - - /** - * Custom fetch implementation. You can use it as a middleware to intercept requests, - * or to provide a custom fetch implementation for e.g. testing. - */ - fetch?: typeof fetch; - - /** - * A JSON object to send as the request body to access Hyperbolic features & upstream provider features. - */ - extraBody?: Record; -} - -/** - * Create an Hyperbolic provider instance. - */ -export function createHyperbolic(options: HyperbolicProviderSettings = {}): HyperbolicProvider { - const baseURL = - withoutTrailingSlash(options.baseURL ?? options.baseUrl) ?? "https://api.hyperbolic.xyz/v1"; - - // we default to compatible, because strict breaks providers like Groq: - const compatibility = options.compatibility ?? "compatible"; - - const getHeaders = () => ({ - Authorization: `Bearer ${loadApiKey({ - apiKey: options.apiKey, - environmentVariableName: "HYPERBOLIC_API_KEY", - description: "Hyperbolic", - })}`, - ...options.headers, - }); - - const createChatModel = (modelId: HyperbolicChatModelId, settings: HyperbolicChatSettings = {}) => - new HyperbolicChatLanguageModel(modelId, settings, { - provider: "hyperbolic.chat", - url: ({ path }) => `${baseURL}${path}`, - headers: getHeaders, - compatibility, - fetch: options.fetch, - extraBody: options.extraBody, - }); - - const createCompletionModel = ( - modelId: HyperbolicCompletionModelId, - settings: HyperbolicCompletionSettings = {}, - ) => - new HyperbolicCompletionLanguageModel(modelId, settings, { - provider: "hyperbolic.completion", - url: ({ path }) => `${baseURL}${path}`, - headers: getHeaders, - compatibility, - fetch: options.fetch, - extraBody: options.extraBody, - }); - - const createImageModel = ( - modelId: HyperbolicImageModelId, - settings: HyperbolicImageSettings = {}, - ) => - new HyperbolicImageModel(modelId, settings, { - provider: "hyperbolic.image", - url: ({ path }) => `${baseURL}${path}`, - headers: getHeaders, - compatibility, - fetch: options.fetch, - extraBody: options.extraBody, - }); - - const createLanguageModel = ( - modelId: HyperbolicChatModelId | HyperbolicCompletionModelId, - settings?: HyperbolicChatSettings | HyperbolicCompletionSettings, - ) => { - if (new.target) { - throw new Error("The Hyperbolic model function cannot be called with the new keyword."); - } - - if (modelId === "openai/gpt-3.5-turbo-instruct") { - return createCompletionModel(modelId, settings as HyperbolicCompletionSettings); - } - - return createChatModel(modelId, settings as HyperbolicChatSettings); - }; - - const provider = function ( - modelId: HyperbolicChatModelId | HyperbolicCompletionModelId, - settings?: HyperbolicChatSettings | HyperbolicCompletionSettings, - ) { - return createLanguageModel(modelId, settings); - }; - - provider.languageModel = createLanguageModel; - provider.chat = createChatModel; - provider.completion = createCompletionModel; - provider.image = createImageModel; - - return provider as HyperbolicProvider; -} diff --git a/packages/ai-sdk-provider/src/hyperbolic-image-settings.ts b/packages/ai-sdk-provider/src/image/hyperbolic-image-settings.ts similarity index 54% rename from packages/ai-sdk-provider/src/hyperbolic-image-settings.ts rename to packages/ai-sdk-provider/src/image/hyperbolic-image-settings.ts index 9399faf..1692e45 100644 --- a/packages/ai-sdk-provider/src/hyperbolic-image-settings.ts +++ b/packages/ai-sdk-provider/src/image/hyperbolic-image-settings.ts @@ -1,12 +1,8 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 +import type { GenerateImageResult } from "ai"; -import type { Experimental_GenerateImageResult } from "ai"; +import type { HyperbolicSharedSettings } from "../types"; -import type { HyperbolicSharedSettings } from "./types"; - -export type HyperbolicImageModelId = string; +export type { HyperbolicImageModelId } from "../__generated__/models.gen"; export type HyperbolicImageSettings = { /** @@ -30,11 +26,8 @@ export type HyperbolicImageProviderResponseMetadata = { randomSeeds: number[]; }; -export type Experimental_HyperbolicGenerateImageResult = Omit< - Experimental_GenerateImageResult, - "responses" -> & { - responses: (Experimental_GenerateImageResult["responses"][number] & { +export type HyperbolicGenerateImageResult = Omit & { + responses: (GenerateImageResult["responses"][number] & { hyperbolic: HyperbolicImageProviderResponseMetadata; })[]; }; diff --git a/packages/ai-sdk-provider/src/hyperbolic-image-language-model.ts b/packages/ai-sdk-provider/src/image/index.ts similarity index 79% rename from packages/ai-sdk-provider/src/hyperbolic-image-language-model.ts rename to packages/ai-sdk-provider/src/image/index.ts index da5501d..1a4fb43 100644 --- a/packages/ai-sdk-provider/src/hyperbolic-image-language-model.ts +++ b/packages/ai-sdk-provider/src/image/index.ts @@ -1,8 +1,4 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { ImageModelV1, ImageModelV1CallWarning } from "@ai-sdk/provider"; +import type { ImageModelV3, SharedV3Warning } from "@ai-sdk/provider"; import { combineHeaders, createJsonResponseHandler, postJsonToApi } from "@ai-sdk/provider-utils"; import { z } from "zod"; @@ -12,19 +8,18 @@ import type { HyperbolicImageProviderResponseMetadata, HyperbolicImageSettings, } from "./hyperbolic-image-settings"; -import { hyperbolicFailedResponseHandler } from "./hyperbolic-error"; +import { hyperbolicFailedResponseHandler } from "../schemas/error-response"; type HyperbolicImageModelConfig = { provider: string; - compatibility: "strict" | "compatible"; headers: () => Record; url: (options: { modelId: string; path: string }) => string; fetch?: typeof fetch; extraBody?: Record; }; -export class HyperbolicImageModel implements ImageModelV1 { - readonly specificationVersion = "v1"; +export class HyperbolicImageModel implements ImageModelV3 { + readonly specificationVersion = "v3"; readonly provider = "hyperbolic.image"; get maxImagesPerCall(): number { @@ -38,19 +33,19 @@ export class HyperbolicImageModel implements ImageModelV1 { ) {} async doGenerate( - options: Omit[0], "providerOptions"> & { + options: Omit[0], "providerOptions"> & { providerOptions: { hyperbolic?: HyperbolicImageProviderOptions; }; }, ): Promise< - Omit>, "response"> & { - response: Awaited>["response"] & { + Omit>, "response"> & { + response: Awaited>["response"] & { hyperbolic: HyperbolicImageProviderResponseMetadata; }; } > { - const warnings: Array = []; + const warnings: Array = []; const [width, height] = options.size ? options.size.split("x").map(Number) : []; const args = { @@ -68,22 +63,22 @@ export class HyperbolicImageModel implements ImageModelV1 { if (options.aspectRatio != undefined) { warnings.push({ - type: "unsupported-setting", - setting: "aspectRatio", + type: "unsupported", + feature: "aspectRatio", details: "This model does not support `aspectRatio`. Use `size` instead.", }); } if (options.seed != undefined) { warnings.push({ - type: "unsupported-setting", - setting: "seed", + type: "unsupported", + feature: "seed", details: "This model does not support `seed`.", }); } if (options.n != undefined) { warnings.push({ - type: "unsupported-setting", - setting: "n", + type: "unsupported", + feature: "n", details: "This model does not support `n`.", }); } @@ -128,3 +123,5 @@ const hyperbolicImageResponseSchema = z.object({ ), inference_time: z.number(), }); + +export * from "./hyperbolic-image-settings"; diff --git a/packages/ai-sdk-provider/src/index.ts b/packages/ai-sdk-provider/src/index.ts index 0180b06..8047213 100644 --- a/packages/ai-sdk-provider/src/index.ts +++ b/packages/ai-sdk-provider/src/index.ts @@ -1,3 +1,2 @@ -export * from "./hyperbolic-provider"; -export * from "./types"; -export * from "./hyperbolic-error"; +export * from "./provider"; +export * from "./schemas/error-response"; diff --git a/packages/ai-sdk-provider/src/internal/index.ts b/packages/ai-sdk-provider/src/internal/index.ts index c9936d2..533c4b2 100644 --- a/packages/ai-sdk-provider/src/internal/index.ts +++ b/packages/ai-sdk-provider/src/internal/index.ts @@ -1,7 +1 @@ -export * from "../hyperbolic-chat-language-model"; -export * from "../hyperbolic-chat-settings"; -export * from "../hyperbolic-completion-language-model"; -export * from "../hyperbolic-completion-settings"; -export * from "../hyperbolic-image-language-model"; -export * from "../hyperbolic-image-settings"; -export * from "../types"; +export * from "../image"; diff --git a/packages/ai-sdk-provider/src/map-hyperbolic-chat-logprobs.ts b/packages/ai-sdk-provider/src/map-hyperbolic-chat-logprobs.ts deleted file mode 100644 index f325b88..0000000 --- a/packages/ai-sdk-provider/src/map-hyperbolic-chat-logprobs.ts +++ /dev/null @@ -1,37 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { LanguageModelV1LogProbs } from "@ai-sdk/provider"; - -type HyperbolicChatLogProbs = { - content: - | { - token: string; - logprob: number; - top_logprobs: - | { - token: string; - logprob: number; - }[] - | null; - }[] - | null; -}; - -export function mapHyperbolicChatLogProbsOutput( - logprobs: HyperbolicChatLogProbs | null | undefined, -): LanguageModelV1LogProbs | undefined { - return ( - logprobs?.content?.map(({ token, logprob, top_logprobs }) => ({ - token, - logprob, - topLogprobs: top_logprobs - ? top_logprobs.map(({ token, logprob }) => ({ - token, - logprob, - })) - : [], - })) ?? undefined - ); -} diff --git a/packages/ai-sdk-provider/src/map-hyperbolic-completion-logprobs.ts b/packages/ai-sdk-provider/src/map-hyperbolic-completion-logprobs.ts deleted file mode 100644 index 121d731..0000000 --- a/packages/ai-sdk-provider/src/map-hyperbolic-completion-logprobs.ts +++ /dev/null @@ -1,24 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -type HyperbolicCompletionLogProps = { - tokens: string[]; - token_logprobs: number[]; - top_logprobs: Record[] | null; -}; - -export function mapHyperbolicCompletionLogProbs( - logprobs: HyperbolicCompletionLogProps | null | undefined, -) { - return logprobs?.tokens.map((token, index) => ({ - token, - logprob: logprobs.token_logprobs[index] ?? 0, - topLogprobs: logprobs.top_logprobs - ? Object.entries(logprobs.top_logprobs[index] ?? {}).map(([token, logprob]) => ({ - token, - logprob, - })) - : [], - })); -} diff --git a/packages/ai-sdk-provider/src/map-hyperbolic-finish-reason.ts b/packages/ai-sdk-provider/src/map-hyperbolic-finish-reason.ts deleted file mode 100644 index 5763ff8..0000000 --- a/packages/ai-sdk-provider/src/map-hyperbolic-finish-reason.ts +++ /dev/null @@ -1,23 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { LanguageModelV1FinishReason } from "@ai-sdk/provider"; - -export function mapHyperbolicFinishReason( - finishReason: string | null | undefined, -): LanguageModelV1FinishReason { - switch (finishReason) { - case "stop": - return "stop"; - case "length": - return "length"; - case "content_filter": - return "content-filter"; - case "function_call": - case "tool_calls": - return "tool-calls"; - default: - return "unknown"; - } -} diff --git a/packages/ai-sdk-provider/src/provider.ts b/packages/ai-sdk-provider/src/provider.ts new file mode 100644 index 0000000..7251939 --- /dev/null +++ b/packages/ai-sdk-provider/src/provider.ts @@ -0,0 +1,106 @@ +import type { ProviderV3 } from "@ai-sdk/provider"; +import { loadApiKey, withoutTrailingSlash } from "@ai-sdk/provider-utils"; + +import type { + HyperbolicImageModelId, + HyperbolicImageSettings, +} from "./image/hyperbolic-image-settings"; +import { HyperbolicImageModel } from "./image"; +import { withUserAgentSuffix } from "./utils/with-user-agent-suffix"; +import { VERSION } from "./version"; + +export interface HyperbolicProvider extends ProviderV3 { + (modelId: HyperbolicImageModelId, settings?: HyperbolicImageSettings): HyperbolicImageModel; + + image(modelId: HyperbolicImageModelId, settings?: HyperbolicImageSettings): HyperbolicImageModel; +} + +export interface HyperbolicProviderSettings { + /** +Base URL for the Hyperbolic API calls. + */ + baseURL?: string; + + /** +@deprecated Use `baseURL` instead. + */ + baseUrl?: string; + + /** +API key for authenticating requests. + */ + apiKey?: string; + + /** +Custom headers to include in the requests. + */ + headers?: Record; + + /** +Custom fetch implementation. You can use it as a middleware to intercept requests, +or to provide a custom fetch implementation for e.g. testing. + */ + fetch?: typeof fetch; + + /** +A JSON object to send as the request body to access Hyperbolic features & upstream provider features. + */ + extraBody?: Record; + + /** + * Record of provider slugs to API keys for injecting into provider routing. + * Maps provider slugs (e.g. "anthropic", "openai") to their respective API keys. + */ + api_keys?: Record; +} + +/** + * Create an Hyperbolic provider instance. + * + * For chat and completion models, use the @openrouter/ai-sdk-provider instead. + */ +export function createHyperbolic(options: HyperbolicProviderSettings = {}): HyperbolicProvider { + const baseURL = + withoutTrailingSlash(options.baseURL ?? options.baseUrl) ?? "https://api.hyperbolic.xyz/v1"; + + const getHeaders = () => + withUserAgentSuffix( + { + Authorization: `Bearer ${loadApiKey({ + apiKey: options.apiKey, + environmentVariableName: "HYPERBOLIC_API_KEY", + description: "Hyperbolic", + })}`, + ...options.headers, + ...(options.api_keys && + Object.keys(options.api_keys).length > 0 && { + "X-Provider-API-Keys": JSON.stringify(options.api_keys), + }), + }, + `ai-sdk/hyperbolic/${VERSION}`, + ); + + const createImageModel = ( + modelId: HyperbolicImageModelId, + settings: HyperbolicImageSettings = {}, + ) => + new HyperbolicImageModel(modelId, settings, { + provider: "hyperbolic.image", + url: ({ path }) => `${baseURL}${path}`, + headers: getHeaders, + fetch: options.fetch, + extraBody: options.extraBody, + }); + + const provider = (modelId: HyperbolicImageModelId, settings?: HyperbolicImageSettings) => + createImageModel(modelId, settings); + + provider.image = createImageModel; + + return provider as HyperbolicProvider; +} + +/** + * Default Hyperbolic provider instance. Requires a valid API key set to the `HYPERBOLIC_API_KEY` environment variable. + */ +export const hyperbolic = createHyperbolic(); diff --git a/packages/ai-sdk-provider/src/schemas/error-response.test.ts b/packages/ai-sdk-provider/src/schemas/error-response.test.ts new file mode 100644 index 0000000..3b2d1e7 --- /dev/null +++ b/packages/ai-sdk-provider/src/schemas/error-response.test.ts @@ -0,0 +1,50 @@ +import { HyperbolicErrorResponseSchema } from "./error-response"; + +describe("HyperbolicErrorResponseSchema", () => { + it("should be valid without a type, code, and param", () => { + const errorWithoutTypeCodeAndParam = { + error: { + message: "Example error message", + metadata: { provider_name: "Example Provider" }, + }, + user_id: "example_1", + }; + + const result = HyperbolicErrorResponseSchema.parse(errorWithoutTypeCodeAndParam); + + expect(result).toEqual({ + error: { + message: "Example error message", + code: null, + type: null, + param: null, + metadata: { provider_name: "Example Provider" }, + }, + user_id: "example_1", + }); + }); + + it("should be invalid with a type", () => { + const errorWithType = { + error: { + message: "Example error message with type", + type: "invalid_request_error", + code: 400, + param: "canBeAnything", + metadata: { provider_name: "Example Provider" }, + }, + }; + + const result = HyperbolicErrorResponseSchema.parse(errorWithType); + + expect(result).toEqual({ + error: { + code: 400, + message: "Example error message with type", + type: "invalid_request_error", + param: "canBeAnything", + metadata: { provider_name: "Example Provider" }, + }, + }); + }); +}); diff --git a/packages/ai-sdk-provider/src/schemas/error-response.ts b/packages/ai-sdk-provider/src/schemas/error-response.ts new file mode 100644 index 0000000..3b17c6a --- /dev/null +++ b/packages/ai-sdk-provider/src/schemas/error-response.ts @@ -0,0 +1,24 @@ +import { createJsonErrorResponseHandler } from "@ai-sdk/provider-utils"; +import { z } from "zod/v4"; + +// Use SDK's ChatErrorError type but wrap in response schema +// SDK type: { code: string | number | null; message: string; param?: string | null; type?: string | null } +export const HyperbolicErrorResponseSchema = z + .object({ + error: z + .object({ + code: z.union([z.string(), z.number()]).nullable().optional().default(null), + message: z.string(), + type: z.string().nullable().optional().default(null), + param: z.any().nullable().optional().default(null), + }) + .loose(), + }) + .loose(); + +export type HyperbolicErrorData = z.infer; + +export const hyperbolicFailedResponseHandler = createJsonErrorResponseHandler({ + errorSchema: HyperbolicErrorResponseSchema, + errorToMessage: (data: HyperbolicErrorData) => data.error.message, +}); diff --git a/packages/ai-sdk-provider/src/schemas/image.ts b/packages/ai-sdk-provider/src/schemas/image.ts new file mode 100644 index 0000000..49049ae --- /dev/null +++ b/packages/ai-sdk-provider/src/schemas/image.ts @@ -0,0 +1,23 @@ +import { z } from "zod/v4"; + +const ImageResponseSchema = z + .object({ + type: z.literal("image_url"), + image_url: z + .object({ + url: z.string(), + }) + .loose(), + }) + .loose(); + +export type ImageResponse = z.infer; + +const ImageResponseWithUnknownSchema = z.union([ + ImageResponseSchema, + z.unknown().transform(() => null), +]); + +export const ImageResponseArraySchema = z + .array(ImageResponseWithUnknownSchema) + .transform((d) => d.filter((d): d is ImageResponse => !!d)); diff --git a/packages/ai-sdk-provider/src/scripts/templates/models.ts.hbs b/packages/ai-sdk-provider/src/scripts/templates/models.ts.hbs index 4eefd94..26ff915 100644 --- a/packages/ai-sdk-provider/src/scripts/templates/models.ts.hbs +++ b/packages/ai-sdk-provider/src/scripts/templates/models.ts.hbs @@ -9,19 +9,19 @@ const _models = [ ] as const; const _imageModels = [ -{{#each imageModelId}} +{{#each imageModelIds}} "{{this}}", {{/each}} ] as const; const _chatModels = [ -{{#each chatModelId}} +{{#each chatModelIds}} "{{this}}", {{/each}} ] as const; const _completionModels = [ -{{#each completionModelId}} +{{#each completionModelIds}} "{{this}}", {{/each}} ] as const; diff --git a/packages/ai-sdk-provider/src/scripts/update-models-list.ts b/packages/ai-sdk-provider/src/scripts/update-models-list.ts index 52aea76..5efab77 100644 --- a/packages/ai-sdk-provider/src/scripts/update-models-list.ts +++ b/packages/ai-sdk-provider/src/scripts/update-models-list.ts @@ -15,15 +15,24 @@ const main = async () => { data: { data }, } = await showModelsV1ModelsGet({ client: hyperbolicClient, throwOnError: true }); - const models = data as { id: string; [key: string]: unknown }[]; - const modelIds = models.map((model) => model.id); + const models = data as { + id: string; + supports_chat: boolean; + supports_image_input: boolean; + [key: string]: unknown; + }[]; + const imageModelIds = models + .filter((model) => model.supports_image_input) + .map((model) => model.id); + const chatModelIds = models.filter((model) => model.supports_chat).map((model) => model.id); + const completionModelIds = chatModelIds; const __dirname = path.dirname(fileURLToPath(import.meta.url)); const templatePath = path.join(__dirname, "templates", "models.ts.hbs"); const templateContent = readFileSync(templatePath, "utf-8"); const template = Handlebars.compile(templateContent); - const output = template({ modelId: modelIds }); + const output = template({ imageModelIds, chatModelIds, completionModelIds }); writeFileSync(new URL("../__generated__/models.gen.ts", import.meta.url), output); }; diff --git a/packages/ai-sdk-provider/src/types.ts b/packages/ai-sdk-provider/src/types.ts deleted file mode 100644 index d0d0c8a..0000000 --- a/packages/ai-sdk-provider/src/types.ts +++ /dev/null @@ -1,47 +0,0 @@ -// Modified by Hyperbolic Labs, Inc. on 2025-03-25 -// Original work Copyright 2025 OpenRouter Inc. -// Licensed under the Apache License, Version 2.0 - -import type { LanguageModelV1 } from "@ai-sdk/provider"; - -// Re-export the LanguageModelV1 type to ensure proper type compatibility -export type { LanguageModelV1 }; - -// Export our model types with explicit type constraints -export type HyperbolicLanguageModel = LanguageModelV1; - -export type HyperbolicProviderOptions = { - models?: string[]; - - /** - * https://openrouter.ai/docs/use-cases/reasoning-tokens - * One of `max_tokens` or `effort` is required. - * If `exclude` is true, reasoning will be removed from the response. Default is false. - */ - reasoning?: { - exclude?: boolean; - } & ( - | { - max_tokens: number; - } - | { - effort: "high" | "medium" | "low"; - } - ); - - /** - * A unique identifier representing your end-user, which can - * help Hyperbolic to monitor and detect abuse. - */ - user?: string; -}; - -export type HyperbolicSharedSettings = HyperbolicProviderOptions & { - /** - * @deprecated use `reasoning` instead - */ - includeReasoning?: boolean; - - // eslint-disable-next-line @typescript-eslint/no-explicit-any - extraBody?: Record; -}; diff --git a/packages/ai-sdk-provider/src/types/index.ts b/packages/ai-sdk-provider/src/types/index.ts new file mode 100644 index 0000000..8edd163 --- /dev/null +++ b/packages/ai-sdk-provider/src/types/index.ts @@ -0,0 +1,31 @@ +// Modified by Hyperbolic Labs, Inc. on 2026-01-23 +// Original work Copyright 2025 OpenRouter Inc. +// Licensed under the Apache License, Version 2.0 + +import type { LanguageModelV3, LanguageModelV3Prompt } from "@ai-sdk/provider"; + +export type { LanguageModelV3, LanguageModelV3Prompt }; + +export type HyperbolicProviderOptions = { + models?: string[]; + + /** + * A unique identifier representing your end-user, which can + * help Hyperbolic to monitor and detect abuse. + */ + user?: string; +}; + +export type HyperbolicSharedSettings = HyperbolicProviderOptions & { + extraBody?: Record; + + /** + * Enable usage accounting to get detailed token usage information. + */ + usage?: { + /** + * When true, includes token usage information in the response. + */ + include: boolean; + }; +}; diff --git a/packages/ai-sdk-provider/src/utils/remove-undefined.ts b/packages/ai-sdk-provider/src/utils/remove-undefined.ts new file mode 100644 index 0000000..4c0b391 --- /dev/null +++ b/packages/ai-sdk-provider/src/utils/remove-undefined.ts @@ -0,0 +1,13 @@ +/** + * Removes entries from a record where the value is null or undefined. + * @param record - The input object whose entries may be null or undefined. + * @returns A new object containing only entries with non-null and non-undefined values. + */ +export function removeUndefinedEntries( + record: Record, +): Record { + return Object.fromEntries(Object.entries(record).filter(([, value]) => value !== null)) as Record< + string, + T + >; +} diff --git a/packages/ai-sdk-provider/src/utils/with-user-agent-suffix.ts b/packages/ai-sdk-provider/src/utils/with-user-agent-suffix.ts new file mode 100644 index 0000000..0a7df9d --- /dev/null +++ b/packages/ai-sdk-provider/src/utils/with-user-agent-suffix.ts @@ -0,0 +1,28 @@ +import { removeUndefinedEntries } from "../utils/remove-undefined"; + +/** + * Appends suffix parts to the `user-agent` header. + * If a `user-agent` header already exists, the suffix parts are appended to it. + * If no `user-agent` header exists, a new one is created with the suffix parts. + * Automatically removes undefined entries from the headers. + * + * @param headers - The original headers. + * @param userAgentSuffixParts - The parts to append to the `user-agent` header. + * @returns The new headers with the `user-agent` header set or updated. + */ +export function withUserAgentSuffix( + headers: HeadersInit | Record | undefined, + ...userAgentSuffixParts: string[] +): Record { + const cleanedHeaders = removeUndefinedEntries( + (headers as Record) ?? {}, + ); + + const currentUserAgentHeader = cleanedHeaders["user-agent"] || ""; + const newUserAgent = [currentUserAgentHeader, ...userAgentSuffixParts].filter(Boolean).join(" "); + + return { + ...cleanedHeaders, + "user-agent": newUserAgent, + }; +} diff --git a/packages/ai-sdk-provider/src/version.ts b/packages/ai-sdk-provider/src/version.ts new file mode 100644 index 0000000..8fff599 --- /dev/null +++ b/packages/ai-sdk-provider/src/version.ts @@ -0,0 +1,4 @@ +// Version string of this package injected at build time. +declare const __PACKAGE_VERSION__: string | undefined; +export const VERSION: string = + __PACKAGE_VERSION__ === undefined ? "0.0.0-test" : __PACKAGE_VERSION__; diff --git a/packages/ai-sdk-provider/tsup.config.ts b/packages/ai-sdk-provider/tsup.config.ts index cded0e2..2d8b30b 100644 --- a/packages/ai-sdk-provider/tsup.config.ts +++ b/packages/ai-sdk-provider/tsup.config.ts @@ -1,11 +1,17 @@ +import { readFileSync } from "node:fs"; import { defineConfig } from "tsup"; +const package_ = JSON.parse(readFileSync(new URL("./package.json", import.meta.url), "utf8")); + export default defineConfig([ { entry: ["src/index.ts"], format: ["cjs", "esm"], dts: true, sourcemap: true, + define: { + __PACKAGE_VERSION__: JSON.stringify(package_.version), + }, }, { entry: ["src/internal/index.ts"], @@ -13,5 +19,8 @@ export default defineConfig([ format: ["cjs", "esm"], dts: true, sourcemap: true, + define: { + __PACKAGE_VERSION__: JSON.stringify(package_.version), + }, }, ]); diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index b8568e3..5c59a5c 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -16,8 +16,8 @@ catalogs: specifier: ^3.4.2 version: 3.4.2 typescript: - specifier: ^5.7.3 - version: 5.7.3 + specifier: ^5.9.2 + version: 5.9.3 importers: @@ -55,28 +55,22 @@ importers: version: 2.4.4 typescript: specifier: 'catalog:' - version: 5.7.3 + version: 5.9.3 vite-tsconfig-paths: specifier: ^5.1.4 - version: 5.1.4(typescript@5.7.3)(vite@5.4.14(@types/node@22.13.10)(lightningcss@1.29.1)) + version: 5.1.4(typescript@5.9.3)(vite@5.4.14(@types/node@22.13.10)(lightningcss@1.29.1)) vitest: - specifier: ^2.0.5 - version: 2.1.8(@edge-runtime/vm@5.0.0)(@types/node@22.13.10)(lightningcss@1.29.1)(msw@2.7.1(@types/node@22.13.10)(typescript@5.7.3)) + specifier: 3.2.4 + version: 3.2.4(@edge-runtime/vm@5.0.0)(@types/node@22.13.10)(lightningcss@1.29.1)(msw@2.12.4(@types/node@22.13.10)(typescript@5.9.3)) packages/ai-sdk-provider: dependencies: '@ai-sdk/provider': - specifier: ^1.1.3 - version: 1.1.3 + specifier: ^3.0.5 + version: 3.0.5 '@ai-sdk/provider-utils': - specifier: ^2.2.8 - version: 2.2.8(zod@3.24.2) - ai: - specifier: ^4.3.16 - version: 4.3.16(react@18.3.1)(zod@3.24.2) - zod: - specifier: ^3.24.2 - version: 3.24.2 + specifier: ^4.0.9 + version: 4.0.9(zod@4.3.6) devDependencies: '@edge-runtime/vm': specifier: ^5.0.0 @@ -93,24 +87,42 @@ importers: '@hyperbolic/tsconfig': specifier: workspace:* version: link:../../tooling/typescript + '@types/json-schema': + specifier: 7.0.15 + version: 7.0.15 + ai: + specifier: ^6.0.48 + version: 6.0.48(zod@4.3.6) eslint: specifier: 'catalog:' version: 9.19.0(jiti@2.4.2) handlebars: specifier: ^4.7.8 version: 4.7.8 + msw: + specifier: 2.12.4 + version: 2.12.4(@types/node@22.13.10)(typescript@5.9.3) prettier: specifier: 'catalog:' version: 3.4.2 tsup: - specifier: 8.4.0 - version: 8.4.0(jiti@2.4.2)(postcss@8.5.1)(tsx@4.19.3)(typescript@5.7.3)(yaml@2.7.0) + specifier: 8.5.0 + version: 8.5.0(jiti@2.4.2)(postcss@8.5.1)(tsx@4.19.3)(typescript@5.9.3)(yaml@2.7.0) type-fest: specifier: ^4.37.0 version: 4.37.0 typescript: specifier: 'catalog:' - version: 5.7.3 + version: 5.9.3 + vite-tsconfig-paths: + specifier: ^5.1.4 + version: 5.1.4(typescript@5.9.3)(vite@5.4.14(@types/node@22.13.10)(lightningcss@1.29.1)) + vitest: + specifier: 3.2.4 + version: 3.2.4(@edge-runtime/vm@5.0.0)(@types/node@22.13.10)(lightningcss@1.29.1)(msw@2.12.4(@types/node@22.13.10)(typescript@5.9.3)) + zod: + specifier: ^4.0.0 + version: 4.3.6 packages/api: devDependencies: @@ -119,7 +131,7 @@ importers: version: 0.8.3 '@hey-api/openapi-ts': specifier: 0.64.11 - version: 0.64.11(typescript@5.7.3) + version: 0.64.11(typescript@5.9.3) '@hyperbolic/eslint-config': specifier: workspace:* version: link:../../tooling/eslint @@ -137,7 +149,7 @@ importers: version: 3.4.2 typescript: specifier: 'catalog:' - version: 5.7.3 + version: 5.9.3 tooling/eslint: dependencies: @@ -146,7 +158,7 @@ importers: version: 1.2.7(eslint@9.19.0(jiti@2.4.2)) eslint-plugin-import: specifier: ^2.31.0 - version: 2.31.0(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3))(eslint@9.19.0(jiti@2.4.2)) + version: 2.31.0(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3))(eslint@9.19.0(jiti@2.4.2)) eslint-plugin-jsx-a11y: specifier: ^6.10.2 version: 6.10.2(eslint@9.19.0(jiti@2.4.2)) @@ -155,7 +167,7 @@ importers: version: 2.4.4(eslint@9.19.0(jiti@2.4.2))(turbo@2.4.4) typescript-eslint: specifier: ^8.21.0 - version: 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) + version: 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) devDependencies: '@hyperbolic/prettier-config': specifier: workspace:* @@ -174,7 +186,7 @@ importers: version: 3.4.2 typescript: specifier: 'catalog:' - version: 5.7.3 + version: 5.9.3 tooling/github: devDependencies: @@ -205,7 +217,7 @@ importers: version: link:../typescript typescript: specifier: 'catalog:' - version: 5.7.3 + version: 5.9.3 tooling/typescript: {} @@ -220,31 +232,21 @@ packages: '@actions/http-client@2.2.3': resolution: {integrity: sha512-mx8hyJi/hjFvbPokCg4uRd4ZX78t+YyRPtnKWwIl+RzNaVuFpQHfmlGVfsKEJN8LwTCvL+DfVgAM04XaHkm6bA==} - '@ai-sdk/provider-utils@2.2.8': - resolution: {integrity: sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==} + '@ai-sdk/gateway@3.0.22': + resolution: {integrity: sha512-NgnlY73JNuooACHqUIz5uMOEWvqR1MMVbb2soGLMozLY1fgwEIF5iJFDAGa5/YArlzw2ATVU7zQu7HkR/FUjgA==} engines: {node: '>=18'} peerDependencies: - zod: ^3.23.8 - - '@ai-sdk/provider@1.1.3': - resolution: {integrity: sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==} - engines: {node: '>=18'} + zod: ^3.25.76 || ^4.1.8 - '@ai-sdk/react@1.2.12': - resolution: {integrity: sha512-jK1IZZ22evPZoQW3vlkZ7wvjYGYF+tRBKXtrcolduIkQ/m/sOAVcVeVDUDvh1T91xCnWCdUGCPZg2avZ90mv3g==} + '@ai-sdk/provider-utils@4.0.9': + resolution: {integrity: sha512-bB4r6nfhBOpmoS9mePxjRoCy+LnzP3AfhyMGCkGL4Mn9clVNlqEeKj26zEKEtB6yoSVcT1IQ0Zh9fytwMCDnow==} engines: {node: '>=18'} peerDependencies: - react: ^18 || ^19 || ^19.0.0-rc - zod: ^3.23.8 - peerDependenciesMeta: - zod: - optional: true + zod: ^3.25.76 || ^4.1.8 - '@ai-sdk/ui-utils@1.2.11': - resolution: {integrity: sha512-3zcwCc8ezzFlwp3ZD15wAPjf2Au4s3vAbKsXQVyhxODHcmu0iyPO2Eua6D/vicq/AUm/BAo60r97O6HU+EI0+w==} + '@ai-sdk/provider@3.0.5': + resolution: {integrity: sha512-2Xmoq6DBJqmSl80U6V9z5jJSJP7ehaJJQMy2iFUqTay06wdCqTnPVBBQbtEL8RCChenL+q5DC5H5WzU3vV3v8w==} engines: {node: '>=18'} - peerDependencies: - zod: ^3.23.8 '@babel/code-frame@7.26.2': resolution: {integrity: sha512-RJlIHRueQgwWitWgF8OdFYGZX328Ax5BCemNGlqHfplnRT9ESi8JkFlvaVYbS+UubVY6dpv87Fs2u5M29iNFVQ==} @@ -287,15 +289,6 @@ packages: resolution: {integrity: sha512-t8kDRGrKXyp6+tjUh7hw2RLyclsW4TRoRvRHtSyAX9Bb5ldlFh+90YAYY6awRXrlB4G5G2izNeGySpATlFzmOg==} engines: {node: '>=6.9.0'} - '@bundled-es-modules/cookie@2.0.1': - resolution: {integrity: sha512-8o+5fRPLNbjbdGRRmJj3h6Hh1AQJf2dk3qQ/5ZFb+PXkRNiSoMGGUKlsgLfrxneb72axVJyIYji64E2+nNfYyw==} - - '@bundled-es-modules/statuses@1.0.1': - resolution: {integrity: sha512-yn7BklA5acgcBr+7w064fGV+SGIFySjCKpqjcWgBAIfrAkY+4GQTJJHQMeT3V/sgz23VTEVV8TtOmkvJAhFVfg==} - - '@bundled-es-modules/tough-cookie@0.1.6': - resolution: {integrity: sha512-dvMHbL464C0zI+Yqxbz6kZ5TOEp7GLW+pry/RWndAR8MJQAXZ2rPmIs8tziTZjeIyhSNZgZbCePtfSbdWqStJw==} - '@changesets/apply-release-plan@7.0.8': resolution: {integrity: sha512-qjMUj4DYQ1Z6qHawsn7S71SujrExJ+nceyKKyI9iB+M5p9lCL55afuEd6uLBPRpLGWQwkwvWegDHtwHJb1UjpA==} @@ -887,8 +880,8 @@ packages: '@manypkg/get-packages@1.1.3': resolution: {integrity: sha512-fo+QhuU3qE/2TQMQmbVMqaQ6EWbMhi4ABWP+O4AM1NqPBuy0OrApV5LO6BrrgnhtAHS2NH6RrVk9OL181tTi8A==} - '@mswjs/interceptors@0.37.6': - resolution: {integrity: sha512-wK+5pLK5XFmgtH3aQ2YVvA3HohS3xqV/OxuVOdNx9Wpnz7VE/fnC+e1A7ln6LFYeck7gOJ/dsZV6OLplOtAJ2w==} + '@mswjs/interceptors@0.40.0': + resolution: {integrity: sha512-EFd6cVbHsgLa6wa4RljGj6Wk75qoHxUSyc5asLyyPSyuhIcdS2Q3Phw6ImS1q+CkALthJRShiYfKANcQMuMqsQ==} engines: {node: '>=18'} '@nodelib/fs.scandir@2.1.5': @@ -954,191 +947,96 @@ packages: resolution: {integrity: sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==} engines: {node: '>=14'} - '@rollup/rollup-android-arm-eabi@4.33.0': - resolution: {integrity: sha512-eBVEV1xXlpRFlaW8IhM/kXHY7vnfWIfQG8ZQV1k5q+3gDQI5D39H9fZk5XysGv/b9kj/pSGAUKJ6+rWoWSNdEQ==} - cpu: [arm] - os: [android] - '@rollup/rollup-android-arm-eabi@4.35.0': resolution: {integrity: sha512-uYQ2WfPaqz5QtVgMxfN6NpLD+no0MYHDBywl7itPYd3K5TjjSghNKmX8ic9S8NU8w81NVhJv/XojcHptRly7qQ==} cpu: [arm] os: [android] - '@rollup/rollup-android-arm64@4.33.0': - resolution: {integrity: sha512-CALerXF20lsoIVAEb/FNjnMIvF7v79PUq9NDL2y2sv2cPFC8AFJzE23BbaOvS0CPqsawaAcc+vwlju5v+mw2Pg==} - cpu: [arm64] - os: [android] - '@rollup/rollup-android-arm64@4.35.0': resolution: {integrity: sha512-FtKddj9XZudurLhdJnBl9fl6BwCJ3ky8riCXjEw3/UIbjmIY58ppWwPEvU3fNu+W7FUsAsB1CdH+7EQE6CXAPA==} cpu: [arm64] os: [android] - '@rollup/rollup-darwin-arm64@4.33.0': - resolution: {integrity: sha512-0gR69dCAYCUk5e6jgbekfNBB7ZPLAR3R2VSXL3vyL/c8YlyEg2iq3ol+O3XHS5enKCN/sUsBcBAjSE6sLIXtug==} - cpu: [arm64] - os: [darwin] - '@rollup/rollup-darwin-arm64@4.35.0': resolution: {integrity: sha512-Uk+GjOJR6CY844/q6r5DR/6lkPFOw0hjfOIzVx22THJXMxktXG6CbejseJFznU8vHcEBLpiXKY3/6xc+cBm65Q==} cpu: [arm64] os: [darwin] - '@rollup/rollup-darwin-x64@4.33.0': - resolution: {integrity: sha512-4rOvNnIRt2Kc4a6G6OXlmA8H88PUcrSn9Ac3L6rksCNK83rvHm1xTQz/XAcoy3EWuaKqkRUch0HC5DjF1rNRKA==} - cpu: [x64] - os: [darwin] - '@rollup/rollup-darwin-x64@4.35.0': resolution: {integrity: sha512-3IrHjfAS6Vkp+5bISNQnPogRAW5GAV1n+bNCrDwXmfMHbPl5EhTmWtfmwlJxFRUCBZ+tZ/OxDyU08aF6NI/N5Q==} cpu: [x64] os: [darwin] - '@rollup/rollup-freebsd-arm64@4.33.0': - resolution: {integrity: sha512-VZhX9ymo7t0PSHN3tJXaZ5tne8lmNxFnUBgpjWRT+x6HYWMvfMC0GBrhTEJhLanI6l6ctF0UHrqEWQ8AzgXvOw==} - cpu: [arm64] - os: [freebsd] - '@rollup/rollup-freebsd-arm64@4.35.0': resolution: {integrity: sha512-sxjoD/6F9cDLSELuLNnY0fOrM9WA0KrM0vWm57XhrIMf5FGiN8D0l7fn+bpUeBSU7dCgPV2oX4zHAsAXyHFGcQ==} cpu: [arm64] os: [freebsd] - '@rollup/rollup-freebsd-x64@4.33.0': - resolution: {integrity: sha512-v8zFftaPMqOMiobWgEa/2gZ9O1RrL/qnycxU19OiNIq6ayIziAnZ/WeKaqKiXrg7Riy1sFdXkYo3qVwd1DDVEA==} - cpu: [x64] - os: [freebsd] - '@rollup/rollup-freebsd-x64@4.35.0': resolution: {integrity: sha512-2mpHCeRuD1u/2kruUiHSsnjWtHjqVbzhBkNVQ1aVD63CcexKVcQGwJ2g5VphOd84GvxfSvnnlEyBtQCE5hxVVw==} cpu: [x64] os: [freebsd] - '@rollup/rollup-linux-arm-gnueabihf@4.33.0': - resolution: {integrity: sha512-KZLksFX9g6dZuuiRqC/qVLDn58U3fgDij8rAKqcznbIJi/J1laoE3A2xYZZCo0zITr14K5/4Gecr/HrrhCQ7/w==} - cpu: [arm] - os: [linux] - '@rollup/rollup-linux-arm-gnueabihf@4.35.0': resolution: {integrity: sha512-mrA0v3QMy6ZSvEuLs0dMxcO2LnaCONs1Z73GUDBHWbY8tFFocM6yl7YyMu7rz4zS81NDSqhrUuolyZXGi8TEqg==} cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm-musleabihf@4.33.0': - resolution: {integrity: sha512-p+1NjIzdjNDSXFJxE5lWa/sKdtfpWrqzd8ROnVcOv38weHX+kOA9wTZbogpXEPaCK35wag6vbkm0xas/8FblLQ==} - cpu: [arm] - os: [linux] - '@rollup/rollup-linux-arm-musleabihf@4.35.0': resolution: {integrity: sha512-DnYhhzcvTAKNexIql8pFajr0PiDGrIsBYPRvCKlA5ixSS3uwo/CWNZxB09jhIapEIg945KOzcYEAGGSmTSpk7A==} cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm64-gnu@4.33.0': - resolution: {integrity: sha512-WSyz2HpBxS/EQpZ21/fruXcQSVRYU7kcfOVbZsLuIbberf1Lw8f1y0IoWu4GVv8PK+V6CdjSIsZiLP4/tDKAJA==} - cpu: [arm64] - os: [linux] - '@rollup/rollup-linux-arm64-gnu@4.35.0': resolution: {integrity: sha512-uagpnH2M2g2b5iLsCTZ35CL1FgyuzzJQ8L9VtlJ+FckBXroTwNOaD0z0/UF+k5K3aNQjbm8LIVpxykUOQt1m/A==} cpu: [arm64] os: [linux] - '@rollup/rollup-linux-arm64-musl@4.33.0': - resolution: {integrity: sha512-BgJABG3iaIeiJKDcPhj4x7XRSke4SkcrFxYKnciy/V/auEPbKu4uBhD0SUhIx+0EI/uXtelPqA6VW0GxfDHRYA==} - cpu: [arm64] - os: [linux] - '@rollup/rollup-linux-arm64-musl@4.35.0': resolution: {integrity: sha512-XQxVOCd6VJeHQA/7YcqyV0/88N6ysSVzRjJ9I9UA/xXpEsjvAgDTgH3wQYz5bmr7SPtVK2TsP2fQ2N9L4ukoUg==} cpu: [arm64] os: [linux] - '@rollup/rollup-linux-loongarch64-gnu@4.33.0': - resolution: {integrity: sha512-j991T8HolnEaoJZ4sgzCNhAv6F62+SPzMwUUgZp5R1i8+FknghmMmdMny42erAh4jYbCUpYqFS6PFxjD7B947A==} - cpu: [loong64] - os: [linux] - '@rollup/rollup-linux-loongarch64-gnu@4.35.0': resolution: {integrity: sha512-5pMT5PzfgwcXEwOaSrqVsz/LvjDZt+vQ8RT/70yhPU06PTuq8WaHhfT1LW+cdD7mW6i/J5/XIkX/1tCAkh1W6g==} cpu: [loong64] os: [linux] - '@rollup/rollup-linux-powerpc64le-gnu@4.33.0': - resolution: {integrity: sha512-dtqsVHoQ1xyQpCMTuWJOYbE6j3byEUCjUAD5J9XEHl2zRO/1+F/N8jfu97GZxOx+ugrZHEFn6hTFvI+PR1Fxbg==} - cpu: [ppc64] - os: [linux] - '@rollup/rollup-linux-powerpc64le-gnu@4.35.0': resolution: {integrity: sha512-c+zkcvbhbXF98f4CtEIP1EBA/lCic5xB0lToneZYvMeKu5Kamq3O8gqrxiYYLzlZH6E3Aq+TSW86E4ay8iD8EA==} cpu: [ppc64] os: [linux] - '@rollup/rollup-linux-riscv64-gnu@4.33.0': - resolution: {integrity: sha512-WQltfx27zYsp2miNbI65bgKFuOvBzHzJvUxWeO8+dGmudmvdGq5mPfGhVBjJBdX6BWOZrPtkLftOSlIllKNARQ==} - cpu: [riscv64] - os: [linux] - '@rollup/rollup-linux-riscv64-gnu@4.35.0': resolution: {integrity: sha512-s91fuAHdOwH/Tad2tzTtPX7UZyytHIRR6V4+2IGlV0Cej5rkG0R61SX4l4y9sh0JBibMiploZx3oHKPnQBKe4g==} cpu: [riscv64] os: [linux] - '@rollup/rollup-linux-s390x-gnu@4.33.0': - resolution: {integrity: sha512-j/8mBAf5RQCJgm0lPkFOHu2qJsXxKJKBadwEwjHxB3K9ZIul+BxMfWYXUX/RUKGji3r7AaxOgsbD0XkGV7YaQg==} - cpu: [s390x] - os: [linux] - '@rollup/rollup-linux-s390x-gnu@4.35.0': resolution: {integrity: sha512-hQRkPQPLYJZYGP+Hj4fR9dDBMIM7zrzJDWFEMPdTnTy95Ljnv0/4w/ixFw3pTBMEuuEuoqtBINYND4M7ujcuQw==} cpu: [s390x] os: [linux] - '@rollup/rollup-linux-x64-gnu@4.33.0': - resolution: {integrity: sha512-11lI0xOnzSZUG2RuH8Eqlj3obnu7BGcTnm/sb3LwCGCHD09PLjaMVCaYx4Pf+E0K4AYMPpHKDP5TTKG24W+JXQ==} - cpu: [x64] - os: [linux] - '@rollup/rollup-linux-x64-gnu@4.35.0': resolution: {integrity: sha512-Pim1T8rXOri+0HmV4CdKSGrqcBWX0d1HoPnQ0uw0bdp1aP5SdQVNBy8LjYncvnLgu3fnnCt17xjWGd4cqh8/hA==} cpu: [x64] os: [linux] - '@rollup/rollup-linux-x64-musl@4.33.0': - resolution: {integrity: sha512-1W1Rl8zUm2qIwGDUaH51aH64CfL9sag5BB3U92Dq7HrpRQb5pvv+tUeN1dMYr9KHX1t52fy5HuPEDVBrlywSvQ==} - cpu: [x64] - os: [linux] - '@rollup/rollup-linux-x64-musl@4.35.0': resolution: {integrity: sha512-QysqXzYiDvQWfUiTm8XmJNO2zm9yC9P/2Gkrwg2dH9cxotQzunBHYr6jk4SujCTqnfGxduOmQcI7c2ryuW8XVg==} cpu: [x64] os: [linux] - '@rollup/rollup-win32-arm64-msvc@4.33.0': - resolution: {integrity: sha512-Wmr+r26PU9fu2BMGA2Rb7FJf6yNUcnWrPvDHf0h15iOsY3iMxSCk98/Ez/QQOjLP6F0hTCCP7hWUuruoPbjAgQ==} - cpu: [arm64] - os: [win32] - '@rollup/rollup-win32-arm64-msvc@4.35.0': resolution: {integrity: sha512-OUOlGqPkVJCdJETKOCEf1mw848ZyJ5w50/rZ/3IBQVdLfR5jk/6Sr5m3iO2tdPgwo0x7VcncYuOvMhBWZq8ayg==} cpu: [arm64] os: [win32] - '@rollup/rollup-win32-ia32-msvc@4.33.0': - resolution: {integrity: sha512-9IhxrTkZzFlCx9+odRlDYPBCK7E/ThQQ1JulZYAuwTkoKalXT5Roy46+B2aOfstzIfygwsjmxfJE2Mvcgb1evQ==} - cpu: [ia32] - os: [win32] - '@rollup/rollup-win32-ia32-msvc@4.35.0': resolution: {integrity: sha512-2/lsgejMrtwQe44glq7AFFHLfJBPafpsTa6JvP2NGef/ifOa4KBoglVf7AKN7EV9o32evBPRqfg96fEHzWo5kw==} cpu: [ia32] os: [win32] - '@rollup/rollup-win32-x64-msvc@4.33.0': - resolution: {integrity: sha512-wqYKNnO1Sbfl2/Tn/4gLJbzaye+MhCQWF/ZTe/7zTqq3G8GBAtL746Oj3Eq3VwJD0Mt5Z9uZYCdvMxTV/GJ2+A==} - cpu: [x64] - os: [win32] - '@rollup/rollup-win32-x64-msvc@4.35.0': resolution: {integrity: sha512-PIQeY5XDkrOysbQblSW7v3l1MDZzkTEzAfTPkj5VAu3FW8fS4ynyLg2sINp0fp3SjZ8xkRYpLqoKcYqAkhU1dw==} cpu: [x64] @@ -1147,6 +1045,9 @@ packages: '@rtsao/scc@1.1.0': resolution: {integrity: sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==} + '@standard-schema/spec@1.1.0': + resolution: {integrity: sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w==} + '@tsconfig/node10@1.0.11': resolution: {integrity: sha512-DcRjDCujK/kCk/cUe8Xz8ZSpm8mS3mNNpta+jGCA6USEDfktlNvm1+IuZ9eTcDbNk41BHwpHHeW+N1lKCz4zOw==} @@ -1159,11 +1060,11 @@ packages: '@tsconfig/node16@1.0.4': resolution: {integrity: sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA==} - '@types/cookie@0.6.0': - resolution: {integrity: sha512-4Kh9a6B2bQciAhf7FSuMRRkUWecJgJu9nPnx3yzpsfXX/c50REIqpHY4C82bXP90qrLtXtkDxTZosYO3UpOwlA==} + '@types/chai@5.2.3': + resolution: {integrity: sha512-Mw558oeA9fFbv65/y4mHtXDs9bPnFMZAL/jxdPFUpOHHIXX91mcgEHbS5Lahr+pwZFR8A7GQleRWeI6cGFC2UA==} - '@types/diff-match-patch@1.0.36': - resolution: {integrity: sha512-xFdR6tkm0MWvBfO8xXCSsinYxHcqkQUlcHeSpMC2ukzOb6lwQAfDmW+Qt0AvlGd8HpsS28qKsB+oPeJn9I39jg==} + '@types/deep-eql@4.0.2': + resolution: {integrity: sha512-c9h9dVVMigMPc4bwTvC5dxqtqJZwQPePsWjPlpSOnojbor6pGqdk541lfA7AqFQr5pB1BRdq0juY9db81BwyFw==} '@types/eslint@9.6.1': resolution: {integrity: sha512-FXx2pKgId/WyYo2jXw63kk7/+TY7u7AziEJxJAnSFzHlqTAS3Ync6SvgYAN/k4/PQpnnVuzoMuVnByKK2qp0ag==} @@ -1195,11 +1096,8 @@ packages: '@types/normalize-package-data@2.4.4': resolution: {integrity: sha512-37i+OaWTh9qeK4LSHPsyRC7NahnGotNuZvjLSgcPzblpHB3rrCJxAOgI5gCdKm7coonsaX1Of0ILiTcnZjbfxA==} - '@types/statuses@2.0.5': - resolution: {integrity: sha512-jmIUGWrAiwu3dZpxntxieC+1n/5c3mjrImkmOSQ2NC5uP6cYO4aAZDdSmRcI5C1oiTmqlZGHC+/NmJrKogbP5A==} - - '@types/tough-cookie@4.0.5': - resolution: {integrity: sha512-/Ad8+nIOV7Rl++6f1BdKxFSMgmoqEoYbHRpPcx3JEfv8VRsQe9Z4mCXeJBzxs7mbHY/XOZZuXlRNfhpVPbs6ZA==} + '@types/statuses@2.0.6': + resolution: {integrity: sha512-xMAgYwceFhRA2zY+XbEA7mxYbA093wdiW8Vu6gZPGWy9cmOyU9XesH1tNcEWsKFd5Vzrqx5T3D38PWx1FIIXkA==} '@typescript-eslint/eslint-plugin@8.26.1': resolution: {integrity: sha512-2X3mwqsj9Bd3Ciz508ZUtoQQYpOhU/kWoUqIf49H8Z0+Vbh6UF/y0OEYp0Q0axOGzaBGs7QxRwq0knSQ8khQNA==} @@ -1248,34 +1146,38 @@ packages: resolution: {integrity: sha512-AjOC3zfnxd6S4Eiy3jwktJPclqhFHNyd8L6Gycf9WUPoKZpgM5PjkxY1X7uSy61xVpiJDhhk7XT2NVsN3ALTWg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@vitest/expect@2.1.8': - resolution: {integrity: sha512-8ytZ/fFHq2g4PJVAtDX57mayemKgDR6X3Oa2Foro+EygiOJHUXhCqBAAKQYYajZpFoIfvBCF1j6R6IYRSIUFuw==} + '@vercel/oidc@3.1.0': + resolution: {integrity: sha512-Fw28YZpRnA3cAHHDlkt7xQHiJ0fcL+NRcIqsocZQUSmbzeIKRpwttJjik5ZGanXP+vlA4SbTg+AbA3bP363l+w==} + engines: {node: '>= 20'} - '@vitest/mocker@2.1.8': - resolution: {integrity: sha512-7guJ/47I6uqfttp33mgo6ga5Gr1VnL58rcqYKyShoRK9ebu8T5Rs6HN3s1NABiBeVTdWNrwUMcHH54uXZBN4zA==} + '@vitest/expect@3.2.4': + resolution: {integrity: sha512-Io0yyORnB6sikFlt8QW5K7slY4OjqNX9jmJQ02QDda8lyM6B5oNgVWoSoKPac8/kgnCUzuHQKrSLtu/uOqqrig==} + + '@vitest/mocker@3.2.4': + resolution: {integrity: sha512-46ryTE9RZO/rfDd7pEqFl7etuyzekzEhUbTW3BvmeO/BcCMEgq59BKhek3dXDWgAj4oMK6OZi+vRr1wPW6qjEQ==} peerDependencies: msw: ^2.4.9 - vite: ^5.0.0 + vite: ^5.0.0 || ^6.0.0 || ^7.0.0-0 peerDependenciesMeta: msw: optional: true vite: optional: true - '@vitest/pretty-format@2.1.8': - resolution: {integrity: sha512-9HiSZ9zpqNLKlbIDRWOnAWqgcA7xu+8YxXSekhr0Ykab7PAYFkhkwoqVArPOtJhPmYeE2YHgKZlj3CP36z2AJQ==} + '@vitest/pretty-format@3.2.4': + resolution: {integrity: sha512-IVNZik8IVRJRTr9fxlitMKeJeXFFFN0JaB9PHPGQ8NKQbGpfjlTx9zO4RefN8gp7eqjNy8nyK3NZmBzOPeIxtA==} - '@vitest/runner@2.1.8': - resolution: {integrity: sha512-17ub8vQstRnRlIU5k50bG+QOMLHRhYPAna5tw8tYbj+jzjcspnwnwtPtiOlkuKC4+ixDPTuLZiqiWWQ2PSXHVg==} + '@vitest/runner@3.2.4': + resolution: {integrity: sha512-oukfKT9Mk41LreEW09vt45f8wx7DordoWUZMYdY/cyAk7w5TWkTRCNZYF7sX7n2wB7jyGAl74OxgwhPgKaqDMQ==} - '@vitest/snapshot@2.1.8': - resolution: {integrity: sha512-20T7xRFbmnkfcmgVEz+z3AU/3b0cEzZOt/zmnvZEctg64/QZbSDJEVm9fLnnlSi74KibmRsO9/Qabi+t0vCRPg==} + '@vitest/snapshot@3.2.4': + resolution: {integrity: sha512-dEYtS7qQP2CjU27QBC5oUOxLE/v5eLkGqPE0ZKEIDGMs4vKWe7IjgLOeauHsR0D5YuuycGRO5oSRXnwnmA78fQ==} - '@vitest/spy@2.1.8': - resolution: {integrity: sha512-5swjf2q95gXeYPevtW0BLk6H8+bPlMb4Vw/9Em4hFxDcaOxS+e0LOX4yqNxoHzMR2akEB2xfpnWUzkZokmgWDg==} + '@vitest/spy@3.2.4': + resolution: {integrity: sha512-vAfasCOe6AIK70iP5UD11Ac4siNUNJ9i/9PZ3NKx07sG6sUxeag1LWdNrMWeKKYBLlzuK+Gn65Yd5nyL6ds+nw==} - '@vitest/utils@2.1.8': - resolution: {integrity: sha512-dwSoui6djdwbfFmIgbIjX2ZhIoG7Ex/+xpxyiEgIGzjliY8xGkcpITKTlp6B4MgtGkF2ilvm97cPM96XZaAgcA==} + '@vitest/utils@3.2.4': + resolution: {integrity: sha512-fB2V0JFrQSMsCo9HiSq3Ezpdv4iYaXRG1Sx8edX3MwxfyNn83mKiGzOcH+Fkxt4MHxr3y42fQi1oeAInqgX2QA==} JSONStream@1.3.5: resolution: {integrity: sha512-E+iruNOY8VV9s4JEbe1aNEm6MiszPRr/UfcHMz0TQh1BXSxHK+ASV1R6W4HpjBhSeS+54PIsAMCBmwD06LLsqQ==} @@ -1295,15 +1197,11 @@ packages: engines: {node: '>=0.4.0'} hasBin: true - ai@4.3.16: - resolution: {integrity: sha512-KUDwlThJ5tr2Vw0A1ZkbDKNME3wzWhuVfAOwIvFUzl1TPVDFAXDFTXio3p+jaKneB+dKNCvFFlolYmmgHttG1g==} + ai@6.0.48: + resolution: {integrity: sha512-nON0rHNTEQgzT1HahGl7AeszJh7es5ibZ6LWqm3IiN+bUAQtXkdArXD9vDlVAPBiCd7ERclZ6lUpOE6ltgJb3w==} engines: {node: '>=18'} peerDependencies: - react: ^18 || ^19 || ^19.0.0-rc - zod: ^3.23.8 - peerDependenciesMeta: - react: - optional: true + zod: ^3.25.76 || ^4.1.8 ajv@6.12.6: resolution: {integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==} @@ -1483,18 +1381,14 @@ packages: resolution: {integrity: sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==} engines: {node: '>=6'} - chai@5.1.2: - resolution: {integrity: sha512-aGtmf24DW6MLHHG5gCx4zaI3uBq3KRtxeVs0DjFH6Z0rDNbsvTxFASFvdj79pxjxZ8/5u3PIiN3IwEIQkiiuPw==} - engines: {node: '>=12'} + chai@5.3.3: + resolution: {integrity: sha512-4zNhdJD/iOjSH0A05ea+Ke6MU5mmpQcbQsSOkgdaUMJ9zTlDTD/GYlwohmIE2u0gaxHYiVHEn1Fw9mZ/ktJWgw==} + engines: {node: '>=18'} chalk@4.1.2: resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} engines: {node: '>=10'} - chalk@5.4.1: - resolution: {integrity: sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w==} - engines: {node: ^12.17.0 || ^14.13 || >=16.0.0} - chardet@0.7.0: resolution: {integrity: sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==} @@ -1569,9 +1463,9 @@ packages: engines: {node: '>=14'} hasBin: true - cookie@0.7.2: - resolution: {integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==} - engines: {node: '>= 0.6'} + cookie@1.1.1: + resolution: {integrity: sha512-ei8Aos7ja0weRpFzJnEA9UHJ/7XQmqglbRwnf2ATjcB9Wq874VKH9kfjjirM6UhU2/E5fFYadylyhFldcqSidQ==} + engines: {node: '>=18'} cosmiconfig-typescript-loader@4.4.0: resolution: {integrity: sha512-BabizFdC3wBHhbI4kJh0VkQP9GkBfoHPydD0COMce1nJ1kJAB3F2TmJ/I7diULBKtmEWSwEbuN/KDtgnmUUVmw==} @@ -1658,6 +1552,15 @@ packages: supports-color: optional: true + debug@4.4.3: + resolution: {integrity: sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==} + engines: {node: '>=6.0'} + peerDependencies: + supports-color: '*' + peerDependenciesMeta: + supports-color: + optional: true + decamelize-keys@1.1.1: resolution: {integrity: sha512-WiPxgEirIV0/eIOMcnFBA3/IJZAZqKnwAwWyvvdi4lsr1WCN22nhdf/3db3DoZcUjTV2SqfzIwNyp6y2xs3nmg==} engines: {node: '>=0.10.0'} @@ -1687,10 +1590,6 @@ packages: deprecation@2.3.1: resolution: {integrity: sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ==} - dequal@2.0.3: - resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==} - engines: {node: '>=6'} - destr@2.0.3: resolution: {integrity: sha512-2N3BOUU4gYMpTP24s5rF5iP7BDr7uNTCs4ozw3kf/eKfvWSIu93GEBi5m427YoyJoeOzQ5smuu4nNAPGb8idSQ==} @@ -1703,9 +1602,6 @@ packages: engines: {node: '>=0.10'} hasBin: true - diff-match-patch@1.0.5: - resolution: {integrity: sha512-IayShXAgj/QMXgB0IWmKx+rOPuGMhqm5w6jvFxmVenXKIzRqTAAsbBPT3kWQeGANj3jGgvcvv4yK6SxqYmikgw==} - diff@4.0.2: resolution: {integrity: sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==} engines: {node: '>=0.3.1'} @@ -1782,8 +1678,8 @@ packages: resolution: {integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==} engines: {node: '>= 0.4'} - es-module-lexer@1.6.0: - resolution: {integrity: sha512-qqnD1yMU6tk/jnaMosogGySTZP8YtUgAffA9nMN+E/rjxcfRQ6IEk7IiozUjgxKoFHBGjTLnrHB/YC45r/59EQ==} + es-module-lexer@1.7.0: + resolution: {integrity: sha512-jEQoCwk8hyb2AZziIOLhDqpm5+2ww5uIE6lkO/6jcOCusfk6LhMHpXXfBLXTZ7Ydyt0j4VoUQv6uGNYbdW+kBA==} es-object-atoms@1.0.0: resolution: {integrity: sha512-MZ4iQ6JwHOBQjahnjwaC1ZtIBH+2ohjamzAO3oaHcXYup7qxjF2fixyH+Q71voWHeOkI2q/TnJao/KfXYIZWbw==} @@ -1926,12 +1822,16 @@ packages: resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} engines: {node: '>=0.10.0'} + eventsource-parser@3.0.6: + resolution: {integrity: sha512-Vo1ab+QXPzZ4tCa8SwIHJFaSzy4R6SHf7BY79rFBDf0idraZWAkYrDjDj8uWaSm3S2TK+hJ7/t1CEmZ7jXw+pg==} + engines: {node: '>=18.0.0'} + execa@5.1.1: resolution: {integrity: sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==} engines: {node: '>=10'} - expect-type@1.1.0: - resolution: {integrity: sha512-bFi65yM+xZgk+u/KRIpekdSYkTB5W1pEf0Lt8Q8Msh7b+eQ7LXVtIB1Bkm4fvclDEL1b2CZkMhv2mOeF8tMdkA==} + expect-type@1.3.0: + resolution: {integrity: sha512-knvyeauYhqjOYvQ66MznSMs83wmHrCycNEN6Ao+2AeYEfxUIkuiVxdEa1qlGEPK+We3n0THiDciYSsCcgW/DoA==} engines: {node: '>=12.0.0'} extendable-error@0.1.7: @@ -1960,8 +1860,9 @@ packages: fastq@1.17.1: resolution: {integrity: sha512-sRVD3lWVIXWg6By68ZN7vho9a1pQcN/WBFaAAsDDFzlJjvoGx0P8z7V1t72grFJfJhu3YPZBuu25f7Kaw2jN1w==} - fdir@6.4.3: - resolution: {integrity: sha512-PMXmW2y1hDDfTSRc9gaXIuCCRpuoz3Kaz8cUelp3smouvfT632ozg2vrT6lJsHKKOF59YLbOGfAWGUcKEfRMQw==} + fdir@6.5.0: + resolution: {integrity: sha512-tIbYtZbucOs0BRGqPJkshJUYdL+SDH7dVM8gjy+ERp3WAUjLEFJE+02kanyHtwjWOnwrKYBiwAmM0p4kLJAnXg==} + engines: {node: '>=12.0.0'} peerDependencies: picomatch: ^3 || ^4 peerDependenciesMeta: @@ -1984,6 +1885,9 @@ packages: resolution: {integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==} engines: {node: '>=10'} + fix-dts-default-cjs-exports@1.0.1: + resolution: {integrity: sha512-pVIECanWFC61Hzl2+oOCtoJ3F17kglZC/6N94eRWycFgBH35hHx0Li604ZIzhseh97mf2p0cv7vVrOZGoqhlEg==} + flat-cache@4.0.1: resolution: {integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==} engines: {node: '>=16'} @@ -2125,8 +2029,8 @@ packages: graphemer@1.4.0: resolution: {integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==} - graphql@16.10.0: - resolution: {integrity: sha512-AjqGKbDGUFRKIRCP9tCKiIGHyriz2oHEbPIbEtcSLSs4YjReZOIPQQWek4+6hjw62H9QShXHyaGivGiYVLeYFQ==} + graphql@16.12.0: + resolution: {integrity: sha512-DKKrynuQRne0PNpEbzuEdHlYOMksHSUI8Zc9Unei5gTsMNA2/vMpoMz/yKba50pejK56qj98qM0SjYxAKi13gQ==} engines: {node: ^12.22.0 || ^14.16.0 || ^16.0.0 || >=17.0.0} handlebars@4.7.8: @@ -2431,6 +2335,9 @@ packages: js-tokens@4.0.0: resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} + js-tokens@9.0.1: + resolution: {integrity: sha512-mxa9E9ITFOt0ban3j6L5MpjwegGz6lBQmM1IJkWeBZGcMxto50+eWdjC/52xDbS2vy0k7vIMK0Fe2wfL9OQSpQ==} + js-yaml@3.14.1: resolution: {integrity: sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==} hasBin: true @@ -2466,11 +2373,6 @@ packages: resolution: {integrity: sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==} hasBin: true - jsondiffpatch@0.6.0: - resolution: {integrity: sha512-3QItJOXp2AP1uv7waBkao5nCvhEv+QmJAd38Ybq7wNI74Q+BBmnLn4EDKz6yI9xGAIQoUF87qHt+kc1IVxB4zQ==} - engines: {node: ^18.0.0 || >=20.0.0} - hasBin: true - jsonfile@4.0.0: resolution: {integrity: sha512-m6F1R3z8jjlf2imQHS2Qez5sjKWQzbuuhuJ/FKYFRZvPE3PuHcSMVZzfsLhGVOkfd20obL5SWEBew5ShlquNxg==} @@ -2622,12 +2524,8 @@ packages: lodash@4.17.21: resolution: {integrity: sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==} - loose-envify@1.4.0: - resolution: {integrity: sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==} - hasBin: true - - loupe@3.1.3: - resolution: {integrity: sha512-kkIp7XSkP78ZxJEsSxW3712C6teJVoeHHwgo9zJ380de7IYyJ2ISlxojcH2pC5OFLewESmnRi/+XCDIEEVyoug==} + loupe@3.2.1: + resolution: {integrity: sha512-CdzqowRJCeLU72bHvWqwRBBlLcMEtIvGrlvef74kMnV2AolS9Y8xUv1I0U/MNAWMhBlKIoyuEgoJ0t/bbwHbLQ==} lru-cache@10.4.3: resolution: {integrity: sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==} @@ -2722,8 +2620,8 @@ packages: ms@2.1.3: resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} - msw@2.7.1: - resolution: {integrity: sha512-TVT65uoWt9LE4lMTLBdClHBQVwvZv5ofac1YyE119nCrNyXf4ktdeVnWH9Fyt94Ifmiedhw6Npp4DSuVRSuRpw==} + msw@2.12.4: + resolution: {integrity: sha512-rHNiVfTyKhzc0EjoXUBVGteNKBevdjOlVC6GlIRXpy+/3LHEIGRovnB5WPjcvmNODVQ1TNFnoa7wsGbd0V3epg==} engines: {node: '>=18'} hasBin: true peerDependencies: @@ -2925,8 +2823,8 @@ packages: resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} engines: {node: '>=8.6'} - picomatch@4.0.2: - resolution: {integrity: sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==} + picomatch@4.0.3: + resolution: {integrity: sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==} engines: {node: '>=12'} pify@4.0.1: @@ -2980,16 +2878,10 @@ packages: engines: {node: '>=14'} hasBin: true - psl@1.15.0: - resolution: {integrity: sha512-JZd3gMVBAVQkSs6HdNZo9Sdo0LNcQeMNP3CozBJb3JYC/QUYZTnKxP+f8oWRX4rHP5EurWxqAHTSwUCjlNKa1w==} - punycode@2.3.1: resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} engines: {node: '>=6'} - querystringify@2.2.0: - resolution: {integrity: sha512-FIqgj2EUvTa7R50u0rGsyTftzjYmv/a3hO345bZNrqabNqjtgiDMgmo4mkUjd+nzU5oF3dClKqFIPUKybUyqoQ==} - queue-microtask@1.2.3: resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} @@ -3000,10 +2892,6 @@ packages: rc9@2.1.2: resolution: {integrity: sha512-btXCnMmRIBINM2LDZoEmOogIZU7Qe7zn4BpomSKZ/ykbLObuBdvG+mFq11DL6fjH1DRwHhrlgtYWG96bJiC7Cg==} - react@18.3.1: - resolution: {integrity: sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ==} - engines: {node: '>=0.10.0'} - read-pkg-up@7.0.1: resolution: {integrity: sha512-zK0TB7Xd6JpCLmlLmufqykGE+/TlOePD6qKClNW7hHDKFh/J7/7gCWGR7joEQEW1bKq3a3yUZSObOoWLFQ4ohg==} engines: {node: '>=8'} @@ -3051,9 +2939,6 @@ packages: resolution: {integrity: sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==} engines: {node: '>=0.10.0'} - requires-port@1.0.0: - resolution: {integrity: sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ==} - resolve-from@4.0.0: resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} engines: {node: '>=4'} @@ -3078,15 +2963,13 @@ packages: resolution: {integrity: sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==} hasBin: true + rettime@0.7.0: + resolution: {integrity: sha512-LPRKoHnLKd/r3dVxcwO7vhCW+orkOGj9ViueosEBK6ie89CijnfRlhaDhHq/3Hxu4CkWQtxwlBG0mzTQY6uQjw==} + reusify@1.0.4: resolution: {integrity: sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==} engines: {iojs: '>=1.0.0', node: '>=0.10.0'} - rollup@4.33.0: - resolution: {integrity: sha512-zdkoGsCeuVLKX8jaa3D969EaRP5mvjWx+oZTYDAzvXuFmLlZlhuKKQcpqHcDI5Z6ox9ztInGOJTiJKMwo8kGpw==} - engines: {node: '>=18.0.0', npm: '>=8.0.0'} - hasBin: true - rollup@4.35.0: resolution: {integrity: sha512-kg6oI4g+vc41vePJyO6dHt/yl0Rz3Thv0kJeVQ3D1kS3E5XSuKbPc29G4IpT/Kv1KQwgHVcN+HtyS+HYLNSvQg==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} @@ -3121,9 +3004,6 @@ packages: safer-buffer@2.1.2: resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} - secure-json-parse@2.7.0: - resolution: {integrity: sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==} - semver@5.7.2: resolution: {integrity: sha512-cBznnQ9KjJqU67B52RMC65CMarK2600WFnbkcaiwWq3xy/5haFJlshgnpjovMVJ+Hff49d8GEn0b87C5pDQ10g==} hasBin: true @@ -3203,6 +3083,7 @@ packages: source-map@0.8.0-beta.0: resolution: {integrity: sha512-2ymg6oRBpebeZi9UUNsgQ89bhx01TcTkmNTGnNO88imTmbSgy4nfujrgVEFKWpMTEGA11EDkTt7mqObTPdigIA==} engines: {node: '>= 8'} + deprecated: The work that was done in this beta branch won't be included in future versions spawndamnit@3.0.1: resolution: {integrity: sha512-MmnduQUuHCoFckZoWnXsTg7JaiLBJrKFj9UI2MbRPGaJeVpsLcVBu6P/IGZovziM/YBsellCmsprgNA+w0CzVg==} @@ -3228,12 +3109,12 @@ packages: stackback@0.0.2: resolution: {integrity: sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==} - statuses@2.0.1: - resolution: {integrity: sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==} + statuses@2.0.2: + resolution: {integrity: sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==} engines: {node: '>= 0.8'} - std-env@3.8.0: - resolution: {integrity: sha512-Bc3YwwCB+OzldMxOXJIIvC6cPRWr/LxOp48CdQTOkPyk/t4JWWJbrilwBd7RJzKV8QW7tJkcgAmeuLLJugl5/w==} + std-env@3.10.0: + resolution: {integrity: sha512-5GS12FdOZNliM5mAOxFRg7Ir0pWz8MdpYm6AY6VPkGpbA7ZzmbzNcBJQ0GPvvyWgcY7QAhCgf9Uy89I03faLkg==} strict-event-emitter@0.5.1: resolution: {integrity: sha512-vMgjE/GGEPEFnhFub6pa4FmJBRBVOLpIII2hvCZ8Kzb7K0hlHo7mQv6xYrBvCL2LtAIBwFUK8wvuJgTVSQ5MFQ==} @@ -3296,6 +3177,9 @@ packages: resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} engines: {node: '>=8'} + strip-literal@3.1.0: + resolution: {integrity: sha512-8r3mkIM/2+PpjHoOtiAW8Rg3jJLHaV7xPwG+YRGrv6FP0wwk/toTpATxWYOW0BKdWwl82VT2tFYi5DlROa0Mxg==} + sucrase@3.35.0: resolution: {integrity: sha512-8EbVDiu9iN/nESwxeSxDKe0dunta1GOlHufmSSXxMD2z2/tMZpDMpvXQGsc+ajGo8y2uYUmixaSRUc/QPoQ0GA==} engines: {node: '>=16 || 14 >=14.17'} @@ -3309,10 +3193,9 @@ packages: resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} engines: {node: '>= 0.4'} - swr@2.3.3: - resolution: {integrity: sha512-dshNvs3ExOqtZ6kJBaAsabhPdHyeY4P2cKwRCniDVifBMoG/SVI7tfLWqPXriVspf2Rg4tPzXJTnwaihIeFw2A==} - peerDependencies: - react: ^16.11.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 + tagged-tag@1.0.0: + resolution: {integrity: sha512-yEFYrVhod+hdNyx7g5Bnkkb0G6si8HJurOoOEgC8B/O0uXLHlaey/65KRv6cuWBNhBgHKAROVpc7QyYqE5gFng==} + engines: {node: '>=20'} tar@6.2.1: resolution: {integrity: sha512-DZ4yORTwrbTj/7MZYq2w+/ZFdI6OZ/f9SFHR+71gIVUZhOQPHzVCLpvRnPgyaMpfWxxk/4ONva3GQSyNIKRv6A==} @@ -3333,10 +3216,6 @@ packages: thenify@3.3.1: resolution: {integrity: sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw==} - throttleit@2.1.0: - resolution: {integrity: sha512-nt6AMGKW1p/70DF/hGBdJB57B8Tspmbp5gfJ8ilhLnt7kkr2ye7hzD6NVG8GGErk2HWF34igrL2CXmNIkzKqKw==} - engines: {node: '>=18'} - through2@4.0.2: resolution: {integrity: sha512-iOqSav00cVxEEICeD7TjLB1sueEL+81Wpzp2bY17uZjZN0pWZPuo4suZ/61VujxmqSGFfgOcNuTZ85QJwNZQpw==} @@ -3349,22 +3228,29 @@ packages: tinyexec@0.3.2: resolution: {integrity: sha512-KQQR9yN7R5+OSwaK0XQoj22pwHoTlgYqmUscPYoknOoWCWfj/5/ABTMRi69FrKU5ffPVh5QcFikpWJI/P1ocHA==} - tinyglobby@0.2.12: - resolution: {integrity: sha512-qkf4trmKSIiMTs/E63cxH+ojC2unam7rJ0WrauAzpT3ECNTxGRMlaXxVbfxMUC/w0LaYk6jQ4y/nGR9uBO3tww==} + tinyglobby@0.2.15: + resolution: {integrity: sha512-j2Zq4NyQYG5XMST4cbs02Ak8iJUdxRM0XI5QyxXuZOzKOINmWurp3smXu3y5wDcJrptwpSjgXHzIQxR0omXljQ==} engines: {node: '>=12.0.0'} - tinypool@1.0.2: - resolution: {integrity: sha512-al6n+QEANGFOMf/dmUMsuS5/r9B06uwlyNjZZql/zv8J7ybHCgoihBNORZCY2mzUuAnomQa2JdhyHKzZxPCrFA==} + tinypool@1.1.1: + resolution: {integrity: sha512-Zba82s87IFq9A9XmjiX5uZA/ARWDrB03OHlq+Vw1fSdt0I+4/Kutwy8BP4Y/y/aORMo61FQ0vIb5j44vSo5Pkg==} engines: {node: ^18.0.0 || >=20.0.0} - tinyrainbow@1.2.0: - resolution: {integrity: sha512-weEDEq7Z5eTHPDh4xjX789+fHfF+P8boiFB+0vbWzpbnbsEr/GRaohi/uMKxg8RZMXnl1ItAi/IUHWMsjDV7kQ==} + tinyrainbow@2.0.0: + resolution: {integrity: sha512-op4nsTR47R6p0vMUUoYl/a+ljLFVtlfaXkLQmqfLR1qHma1h/ysYk4hEXZ880bf2CYgTskvTa/e196Vd5dDQXw==} engines: {node: '>=14.0.0'} - tinyspy@3.0.2: - resolution: {integrity: sha512-n1cw8k1k0x4pgA2+9XrOkFydTerNcJ1zWCO5Nn9scWHTD+5tp8dghT2x1uduQePZTZgd3Tupf+x9BxJjeJi77Q==} + tinyspy@4.0.4: + resolution: {integrity: sha512-azl+t0z7pw/z958Gy9svOTuzqIk6xq+NSheJzn5MMWtWTFywIacg2wUlzKFGtt3cthx0r2SxMK0yzJOR0IES7Q==} engines: {node: '>=14.0.0'} + tldts-core@7.0.19: + resolution: {integrity: sha512-lJX2dEWx0SGH4O6p+7FPwYmJ/bu1JbcGJ8RLaG9b7liIgZ85itUVEPbMtWRVrde/0fnDPEPHW10ZsKW3kVsE9A==} + + tldts@7.0.19: + resolution: {integrity: sha512-8PWx8tvC4jDB39BQw1m4x8y5MH1BcQ5xHeL2n7UVFulMPH/3Q0uiamahFJ3lXA0zO2SUyRXuVVbWSDmstlt9YA==} + hasBin: true + tmp@0.0.33: resolution: {integrity: sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==} engines: {node: '>=0.6.0'} @@ -3373,9 +3259,9 @@ packages: resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} engines: {node: '>=8.0'} - tough-cookie@4.1.4: - resolution: {integrity: sha512-Loo5UUvLD9ScZ6jh8beX1T6sO1w2/MpCRpEP7V280GKMVUQ0Jzar2U3UJPsrdbziLEMMhu3Ujnq//rhiFuIeag==} - engines: {node: '>=6'} + tough-cookie@6.0.0: + resolution: {integrity: sha512-kXuRi1mtaKMrsLUxz3sQYvVl37B0Ns6MzfrtV5DvJceE9bPyspOqk9xxv7XbZWcfLWbFmm997vl83qUWVJA64w==} + engines: {node: '>=16'} tr46@0.0.3: resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==} @@ -3427,8 +3313,8 @@ packages: tsconfig-paths@3.15.0: resolution: {integrity: sha512-2Ac2RgzDe/cn48GvOe3M+o82pEFewD3UPbyoUHHdKasHwJKjds4fLXWf/Ux5kATBKN20oaFGu+jbElp1pos0mg==} - tsup@8.4.0: - resolution: {integrity: sha512-b+eZbPCjz10fRryaAA7C8xlIHnf8VnsaRqydheLIqwG/Mcpfk8Z5zp3HayX7GaTygkigHl5cBUs+IhcySiIexQ==} + tsup@8.5.0: + resolution: {integrity: sha512-VmBp77lWNQq6PfuMqCHD3xWl22vEoWsKajkF8t+yMBawlUS8JzEI+vOVMeuNZIuMML8qXRizFKi9oD5glKQVcQ==} engines: {node: '>=18'} hasBin: true peerDependencies: @@ -3513,6 +3399,10 @@ packages: resolution: {integrity: sha512-S/5/0kFftkq27FPNye0XM1e2NsnoD/3FS+pBmbjmmtLT6I+i344KoOf7pvXreaFsDamWeaJX55nczA1m5PsBDg==} engines: {node: '>=16'} + type-fest@5.4.1: + resolution: {integrity: sha512-xygQcmneDyzsEuKZrFbRMne5HDqMs++aFzefrJTgEIKjQ3rekM+RPfFCVq2Gp1VIDqddoYeppCj4Pcb+RZW0GQ==} + engines: {node: '>=20'} + typed-array-buffer@1.0.2: resolution: {integrity: sha512-gEymJYKZtKXzzBzM4jqa9w6Q1Jjm7x2d+sh19AdsD4wqnMPDYyvwpsIc2Q/835kHuo3BEQ7CjelGhfTsoBb2MQ==} engines: {node: '>= 0.4'} @@ -3552,13 +3442,8 @@ packages: eslint: ^8.57.0 || ^9.0.0 typescript: '>=4.8.4 <5.9.0' - typescript@5.6.3: - resolution: {integrity: sha512-hjcS1mhfuyi4WW8IWtjP7brDrG2cuDZukyrYrSauoXGNgx0S7zceP07adYkJycEr56BOUTNPzbInooiN3fn1qw==} - engines: {node: '>=14.17'} - hasBin: true - - typescript@5.7.3: - resolution: {integrity: sha512-84MVSjMEHP+FQRPy3pX9sTVV/INIex71s9TL2Gm5FG/WG1SqXeKyZ0k7/blY/4FdOzI12CBy1vGc4og/eus0fw==} + typescript@5.9.3: + resolution: {integrity: sha512-jl1vZzPDinLr9eUt3J/t7V6FgNEw9QjvBPdysz9KfQDD41fQrC2Y4vKQdiaUpFT4bXlb1RHhLpp8wtm6M5TgSw==} engines: {node: '>=14.17'} hasBin: true @@ -3591,25 +3476,16 @@ packages: resolution: {integrity: sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg==} engines: {node: '>= 4.0.0'} - universalify@0.2.0: - resolution: {integrity: sha512-CJ1QgKmNg3CwvAv/kOFmtnEN05f0D/cn9QntgNOQlQF9dgvVTHj3t+8JPdjqawCHk7V/KA+fbUqzZ9XWhcqPUg==} - engines: {node: '>= 4.0.0'} - universalify@2.0.1: resolution: {integrity: sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==} engines: {node: '>= 10.0.0'} + until-async@3.0.2: + resolution: {integrity: sha512-IiSk4HlzAMqTUseHHe3VhIGyuFmN90zMTpD3Z3y8jeQbzLIq500MVM7Jq2vUAnTKAFPJrqwkzr6PoTcPhGcOiw==} + uri-js@4.4.1: resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} - url-parse@1.5.10: - resolution: {integrity: sha512-WypcfiRhfeUP9vvF0j6rw0J3hrWrw6iZv3+22h6iRMJ/8z1Tj6XfLP4DsUix5MhMPnXpiHDoKyoZ/bdCkwBCiQ==} - - use-sync-external-store@1.4.0: - resolution: {integrity: sha512-9WXSPC5fMv61vaupRkCKCxsPxBocVnwakBEkMIHHpkTTg6icbJtg6jzgtLDm4bl3cSHAca52rYWih0k4K3PfHw==} - peerDependencies: - react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 - util-deprecate@1.0.2: resolution: {integrity: sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==} @@ -3623,9 +3499,9 @@ packages: validate-npm-package-license@3.0.4: resolution: {integrity: sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==} - vite-node@2.1.8: - resolution: {integrity: sha512-uPAwSr57kYjAUux+8E2j0q0Fxpn8M9VoyfGiRI8Kfktz9NcYMCenwY5RnZxnF1WTu3TGiYipirIzacLL3VVGFg==} - engines: {node: ^18.0.0 || >=20.0.0} + vite-node@3.2.4: + resolution: {integrity: sha512-EbKSKh+bh1E1IFxeO0pg1n4dvoOTt0UDiXMd/qn++r98+jPO1xtJilvXldeuQ8giIB5IkpjCgMleHMNEsGH6pg==} + engines: {node: ^18.0.0 || ^20.0.0 || >=22.0.0} hasBin: true vite-tsconfig-paths@5.1.4: @@ -3667,20 +3543,23 @@ packages: terser: optional: true - vitest@2.1.8: - resolution: {integrity: sha512-1vBKTZskHw/aosXqQUlVWWlGUxSJR8YtiyZDJAFeW2kPAeX6S3Sool0mjspO+kXLuxVWlEDDowBAeqeAQefqLQ==} - engines: {node: ^18.0.0 || >=20.0.0} + vitest@3.2.4: + resolution: {integrity: sha512-LUCP5ev3GURDysTWiP47wRRUpLKMOfPh+yKTx3kVIEiu5KOMeqzpnYNsKyOoVrULivR8tLcks4+lga33Whn90A==} + engines: {node: ^18.0.0 || ^20.0.0 || >=22.0.0} hasBin: true peerDependencies: '@edge-runtime/vm': '*' - '@types/node': ^18.0.0 || >=20.0.0 - '@vitest/browser': 2.1.8 - '@vitest/ui': 2.1.8 + '@types/debug': ^4.1.12 + '@types/node': ^18.0.0 || ^20.0.0 || >=22.0.0 + '@vitest/browser': 3.2.4 + '@vitest/ui': 3.2.4 happy-dom: '*' jsdom: '*' peerDependenciesMeta: '@edge-runtime/vm': optional: true + '@types/debug': + optional: true '@types/node': optional: true '@vitest/browser': @@ -3795,13 +3674,8 @@ packages: resolution: {integrity: sha512-cYVsTjKl8b+FrnidjibDWskAv7UKOfcwaVZdp/it9n1s9fU3IkgDbhdIRKCW4JDsAlECJY0ytoVPT3sK6kideA==} engines: {node: '>=18'} - zod-to-json-schema@3.24.4: - resolution: {integrity: sha512-0uNlcvgabyrni9Ag8Vghj21drk7+7tp7VTwwR7KxxXXc/3pbXz2PHlDgj3cICahgF1kHm4dExBFj7BXrZJXzig==} - peerDependencies: - zod: ^3.24.1 - - zod@3.24.2: - resolution: {integrity: sha512-lY7CDW43ECgW9u1TcT3IoXHflywfVqDYze4waEz812jR/bZ8FHDsl7pFQoSZTz5N+2NqRXs8GBwnAwo3ZNxqhQ==} + zod@4.3.6: + resolution: {integrity: sha512-rftlrkhHZOcjDwkGlnUtZZkvaPHCsDATp4pGpuOOMDaTdDDXF91wuVDJoWoPsKX/3YPQ5fHuF3STjcYyKr+Qhg==} snapshots: @@ -3824,33 +3698,23 @@ snapshots: tunnel: 0.0.6 undici: 5.28.5 - '@ai-sdk/provider-utils@2.2.8(zod@3.24.2)': - dependencies: - '@ai-sdk/provider': 1.1.3 - nanoid: 3.3.8 - secure-json-parse: 2.7.0 - zod: 3.24.2 - - '@ai-sdk/provider@1.1.3': + '@ai-sdk/gateway@3.0.22(zod@4.3.6)': dependencies: - json-schema: 0.4.0 + '@ai-sdk/provider': 3.0.5 + '@ai-sdk/provider-utils': 4.0.9(zod@4.3.6) + '@vercel/oidc': 3.1.0 + zod: 4.3.6 - '@ai-sdk/react@1.2.12(react@18.3.1)(zod@3.24.2)': + '@ai-sdk/provider-utils@4.0.9(zod@4.3.6)': dependencies: - '@ai-sdk/provider-utils': 2.2.8(zod@3.24.2) - '@ai-sdk/ui-utils': 1.2.11(zod@3.24.2) - react: 18.3.1 - swr: 2.3.3(react@18.3.1) - throttleit: 2.1.0 - optionalDependencies: - zod: 3.24.2 + '@ai-sdk/provider': 3.0.5 + '@standard-schema/spec': 1.1.0 + eventsource-parser: 3.0.6 + zod: 4.3.6 - '@ai-sdk/ui-utils@1.2.11(zod@3.24.2)': + '@ai-sdk/provider@3.0.5': dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.24.2) - zod: 3.24.2 - zod-to-json-schema: 3.24.4(zod@3.24.2) + json-schema: 0.4.0 '@babel/code-frame@7.26.2': dependencies: @@ -3905,22 +3769,6 @@ snapshots: '@babel/helper-string-parser': 7.25.9 '@babel/helper-validator-identifier': 7.25.9 - '@bundled-es-modules/cookie@2.0.1': - dependencies: - cookie: 0.7.2 - optional: true - - '@bundled-es-modules/statuses@1.0.1': - dependencies: - statuses: 2.0.1 - optional: true - - '@bundled-es-modules/tough-cookie@0.1.6': - dependencies: - '@types/tough-cookie': 4.0.5 - tough-cookie: 4.1.4 - optional: true - '@changesets/apply-release-plan@7.0.8': dependencies: '@changesets/config': 3.0.5 @@ -4141,14 +3989,14 @@ snapshots: '@commitlint/types': 17.8.1 '@types/node': 20.5.1 chalk: 4.1.2 - cosmiconfig: 8.3.6(typescript@5.6.3) - cosmiconfig-typescript-loader: 4.4.0(@types/node@20.5.1)(cosmiconfig@8.3.6(typescript@5.7.3))(ts-node@10.9.2(@types/node@22.13.10)(typescript@5.7.3))(typescript@5.6.3) + cosmiconfig: 8.3.6(typescript@5.9.3) + cosmiconfig-typescript-loader: 4.4.0(@types/node@20.5.1)(cosmiconfig@8.3.6(typescript@5.9.3))(ts-node@10.9.2(@types/node@22.13.10)(typescript@5.9.3))(typescript@5.9.3) lodash.isplainobject: 4.0.6 lodash.merge: 4.6.2 lodash.uniq: 4.5.0 resolve-from: 5.0.0 - ts-node: 10.9.2(@types/node@20.5.1)(typescript@5.6.3) - typescript: 5.6.3 + ts-node: 10.9.2(@types/node@20.5.1)(typescript@5.9.3) + typescript: 5.9.3 transitivePeerDependencies: - '@swc/core' - '@swc/wasm' @@ -4364,7 +4212,7 @@ snapshots: '@eslint/config-array@0.19.1': dependencies: '@eslint/object-schema': 2.1.5 - debug: 4.4.0 + debug: 4.4.3 minimatch: 3.1.2 transitivePeerDependencies: - supports-color @@ -4376,7 +4224,7 @@ snapshots: '@eslint/eslintrc@3.2.0': dependencies: ajv: 6.12.6 - debug: 4.4.0 + debug: 4.4.3 espree: 10.3.0 globals: 14.0.0 ignore: 5.3.1 @@ -4406,13 +4254,13 @@ snapshots: '@types/json-schema': 7.0.15 js-yaml: 4.1.0 - '@hey-api/openapi-ts@0.64.11(typescript@5.7.3)': + '@hey-api/openapi-ts@0.64.11(typescript@5.9.3)': dependencies: '@hey-api/json-schema-ref-parser': 1.0.2 c12: 2.0.1 commander: 13.0.0 handlebars: 4.7.8 - typescript: 5.7.3 + typescript: 5.9.3 transitivePeerDependencies: - magicast @@ -4446,7 +4294,6 @@ snapshots: '@inquirer/type': 3.0.4(@types/node@22.13.10) optionalDependencies: '@types/node': 22.13.10 - optional: true '@inquirer/core@10.1.7(@types/node@22.13.10)': dependencies: @@ -4460,15 +4307,12 @@ snapshots: yoctocolors-cjs: 2.1.2 optionalDependencies: '@types/node': 22.13.10 - optional: true - '@inquirer/figures@1.0.10': - optional: true + '@inquirer/figures@1.0.10': {} '@inquirer/type@3.0.4(@types/node@22.13.10)': optionalDependencies: '@types/node': 22.13.10 - optional: true '@isaacs/cliui@8.0.2': dependencies: @@ -4521,7 +4365,7 @@ snapshots: globby: 11.1.0 read-yaml-file: 1.1.0 - '@mswjs/interceptors@0.37.6': + '@mswjs/interceptors@0.40.0': dependencies: '@open-draft/deferred-promise': 2.2.0 '@open-draft/logger': 0.3.0 @@ -4529,7 +4373,6 @@ snapshots: is-node-process: 1.2.0 outvariant: 1.4.3 strict-event-emitter: 0.5.1 - optional: true '@nodelib/fs.scandir@2.1.5': dependencies: @@ -4607,139 +4450,81 @@ snapshots: dependencies: '@octokit/openapi-types': 12.11.0 - '@open-draft/deferred-promise@2.2.0': - optional: true + '@open-draft/deferred-promise@2.2.0': {} '@open-draft/logger@0.3.0': dependencies: is-node-process: 1.2.0 outvariant: 1.4.3 - optional: true - '@open-draft/until@2.1.0': - optional: true + '@open-draft/until@2.1.0': {} '@opentelemetry/api@1.9.0': {} '@pkgjs/parseargs@0.11.0': optional: true - '@rollup/rollup-android-arm-eabi@4.33.0': - optional: true - '@rollup/rollup-android-arm-eabi@4.35.0': optional: true - '@rollup/rollup-android-arm64@4.33.0': - optional: true - '@rollup/rollup-android-arm64@4.35.0': optional: true - '@rollup/rollup-darwin-arm64@4.33.0': - optional: true - '@rollup/rollup-darwin-arm64@4.35.0': optional: true - '@rollup/rollup-darwin-x64@4.33.0': - optional: true - '@rollup/rollup-darwin-x64@4.35.0': optional: true - '@rollup/rollup-freebsd-arm64@4.33.0': - optional: true - '@rollup/rollup-freebsd-arm64@4.35.0': optional: true - '@rollup/rollup-freebsd-x64@4.33.0': - optional: true - '@rollup/rollup-freebsd-x64@4.35.0': optional: true - '@rollup/rollup-linux-arm-gnueabihf@4.33.0': - optional: true - '@rollup/rollup-linux-arm-gnueabihf@4.35.0': optional: true - '@rollup/rollup-linux-arm-musleabihf@4.33.0': - optional: true - '@rollup/rollup-linux-arm-musleabihf@4.35.0': optional: true - '@rollup/rollup-linux-arm64-gnu@4.33.0': - optional: true - '@rollup/rollup-linux-arm64-gnu@4.35.0': optional: true - '@rollup/rollup-linux-arm64-musl@4.33.0': - optional: true - '@rollup/rollup-linux-arm64-musl@4.35.0': optional: true - '@rollup/rollup-linux-loongarch64-gnu@4.33.0': - optional: true - '@rollup/rollup-linux-loongarch64-gnu@4.35.0': optional: true - '@rollup/rollup-linux-powerpc64le-gnu@4.33.0': - optional: true - '@rollup/rollup-linux-powerpc64le-gnu@4.35.0': optional: true - '@rollup/rollup-linux-riscv64-gnu@4.33.0': - optional: true - '@rollup/rollup-linux-riscv64-gnu@4.35.0': optional: true - '@rollup/rollup-linux-s390x-gnu@4.33.0': - optional: true - '@rollup/rollup-linux-s390x-gnu@4.35.0': optional: true - '@rollup/rollup-linux-x64-gnu@4.33.0': - optional: true - '@rollup/rollup-linux-x64-gnu@4.35.0': optional: true - '@rollup/rollup-linux-x64-musl@4.33.0': - optional: true - '@rollup/rollup-linux-x64-musl@4.35.0': optional: true - '@rollup/rollup-win32-arm64-msvc@4.33.0': - optional: true - '@rollup/rollup-win32-arm64-msvc@4.35.0': optional: true - '@rollup/rollup-win32-ia32-msvc@4.33.0': - optional: true - '@rollup/rollup-win32-ia32-msvc@4.35.0': optional: true - '@rollup/rollup-win32-x64-msvc@4.33.0': - optional: true - '@rollup/rollup-win32-x64-msvc@4.35.0': optional: true '@rtsao/scc@1.1.0': {} + '@standard-schema/spec@1.1.0': {} + '@tsconfig/node10@1.0.11': {} '@tsconfig/node12@1.0.11': {} @@ -4748,10 +4533,12 @@ snapshots: '@tsconfig/node16@1.0.4': {} - '@types/cookie@0.6.0': - optional: true + '@types/chai@5.2.3': + dependencies: + '@types/deep-eql': 4.0.2 + assertion-error: 2.0.1 - '@types/diff-match-patch@1.0.36': {} + '@types/deep-eql@4.0.2': {} '@types/eslint@9.6.1': dependencies: @@ -4780,38 +4567,34 @@ snapshots: '@types/normalize-package-data@2.4.4': {} - '@types/statuses@2.0.5': - optional: true + '@types/statuses@2.0.6': {} - '@types/tough-cookie@4.0.5': - optional: true - - '@typescript-eslint/eslint-plugin@8.26.1(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3))(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3)': + '@typescript-eslint/eslint-plugin@8.26.1(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3))(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3)': dependencies: '@eslint-community/regexpp': 4.12.1 - '@typescript-eslint/parser': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) + '@typescript-eslint/parser': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) '@typescript-eslint/scope-manager': 8.26.1 - '@typescript-eslint/type-utils': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) - '@typescript-eslint/utils': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) + '@typescript-eslint/type-utils': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) + '@typescript-eslint/utils': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) '@typescript-eslint/visitor-keys': 8.26.1 eslint: 9.19.0(jiti@2.4.2) graphemer: 1.4.0 ignore: 5.3.1 natural-compare: 1.4.0 - ts-api-utils: 2.0.1(typescript@5.7.3) - typescript: 5.7.3 + ts-api-utils: 2.0.1(typescript@5.9.3) + typescript: 5.9.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3)': + '@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3)': dependencies: '@typescript-eslint/scope-manager': 8.26.1 '@typescript-eslint/types': 8.26.1 - '@typescript-eslint/typescript-estree': 8.26.1(typescript@5.7.3) + '@typescript-eslint/typescript-estree': 8.26.1(typescript@5.9.3) '@typescript-eslint/visitor-keys': 8.26.1 debug: 4.4.0 eslint: 9.19.0(jiti@2.4.2) - typescript: 5.7.3 + typescript: 5.9.3 transitivePeerDependencies: - supports-color @@ -4820,20 +4603,20 @@ snapshots: '@typescript-eslint/types': 8.26.1 '@typescript-eslint/visitor-keys': 8.26.1 - '@typescript-eslint/type-utils@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3)': + '@typescript-eslint/type-utils@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3)': dependencies: - '@typescript-eslint/typescript-estree': 8.26.1(typescript@5.7.3) - '@typescript-eslint/utils': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) + '@typescript-eslint/typescript-estree': 8.26.1(typescript@5.9.3) + '@typescript-eslint/utils': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) debug: 4.4.0 eslint: 9.19.0(jiti@2.4.2) - ts-api-utils: 2.0.1(typescript@5.7.3) - typescript: 5.7.3 + ts-api-utils: 2.0.1(typescript@5.9.3) + typescript: 5.9.3 transitivePeerDependencies: - supports-color '@typescript-eslint/types@8.26.1': {} - '@typescript-eslint/typescript-estree@8.26.1(typescript@5.7.3)': + '@typescript-eslint/typescript-estree@8.26.1(typescript@5.9.3)': dependencies: '@typescript-eslint/types': 8.26.1 '@typescript-eslint/visitor-keys': 8.26.1 @@ -4842,19 +4625,19 @@ snapshots: is-glob: 4.0.3 minimatch: 9.0.5 semver: 7.7.0 - ts-api-utils: 2.0.1(typescript@5.7.3) - typescript: 5.7.3 + ts-api-utils: 2.0.1(typescript@5.9.3) + typescript: 5.9.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/utils@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3)': + '@typescript-eslint/utils@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3)': dependencies: '@eslint-community/eslint-utils': 4.4.0(eslint@9.19.0(jiti@2.4.2)) '@typescript-eslint/scope-manager': 8.26.1 '@typescript-eslint/types': 8.26.1 - '@typescript-eslint/typescript-estree': 8.26.1(typescript@5.7.3) + '@typescript-eslint/typescript-estree': 8.26.1(typescript@5.9.3) eslint: 9.19.0(jiti@2.4.2) - typescript: 5.7.3 + typescript: 5.9.3 transitivePeerDependencies: - supports-color @@ -4863,46 +4646,50 @@ snapshots: '@typescript-eslint/types': 8.26.1 eslint-visitor-keys: 4.2.0 - '@vitest/expect@2.1.8': + '@vercel/oidc@3.1.0': {} + + '@vitest/expect@3.2.4': dependencies: - '@vitest/spy': 2.1.8 - '@vitest/utils': 2.1.8 - chai: 5.1.2 - tinyrainbow: 1.2.0 + '@types/chai': 5.2.3 + '@vitest/spy': 3.2.4 + '@vitest/utils': 3.2.4 + chai: 5.3.3 + tinyrainbow: 2.0.0 - '@vitest/mocker@2.1.8(msw@2.7.1(@types/node@22.13.10)(typescript@5.7.3))(vite@5.4.14(@types/node@22.13.10)(lightningcss@1.29.1))': + '@vitest/mocker@3.2.4(msw@2.12.4(@types/node@22.13.10)(typescript@5.9.3))(vite@5.4.14(@types/node@22.13.10)(lightningcss@1.29.1))': dependencies: - '@vitest/spy': 2.1.8 + '@vitest/spy': 3.2.4 estree-walker: 3.0.3 magic-string: 0.30.17 optionalDependencies: - msw: 2.7.1(@types/node@22.13.10)(typescript@5.7.3) + msw: 2.12.4(@types/node@22.13.10)(typescript@5.9.3) vite: 5.4.14(@types/node@22.13.10)(lightningcss@1.29.1) - '@vitest/pretty-format@2.1.8': + '@vitest/pretty-format@3.2.4': dependencies: - tinyrainbow: 1.2.0 + tinyrainbow: 2.0.0 - '@vitest/runner@2.1.8': + '@vitest/runner@3.2.4': dependencies: - '@vitest/utils': 2.1.8 - pathe: 1.1.2 + '@vitest/utils': 3.2.4 + pathe: 2.0.3 + strip-literal: 3.1.0 - '@vitest/snapshot@2.1.8': + '@vitest/snapshot@3.2.4': dependencies: - '@vitest/pretty-format': 2.1.8 + '@vitest/pretty-format': 3.2.4 magic-string: 0.30.17 - pathe: 1.1.2 + pathe: 2.0.3 - '@vitest/spy@2.1.8': + '@vitest/spy@3.2.4': dependencies: - tinyspy: 3.0.2 + tinyspy: 4.0.4 - '@vitest/utils@2.1.8': + '@vitest/utils@3.2.4': dependencies: - '@vitest/pretty-format': 2.1.8 - loupe: 3.1.3 - tinyrainbow: 1.2.0 + '@vitest/pretty-format': 3.2.4 + loupe: 3.2.1 + tinyrainbow: 2.0.0 JSONStream@1.3.5: dependencies: @@ -4919,17 +4706,13 @@ snapshots: acorn@8.14.0: {} - ai@4.3.16(react@18.3.1)(zod@3.24.2): + ai@6.0.48(zod@4.3.6): dependencies: - '@ai-sdk/provider': 1.1.3 - '@ai-sdk/provider-utils': 2.2.8(zod@3.24.2) - '@ai-sdk/react': 1.2.12(react@18.3.1)(zod@3.24.2) - '@ai-sdk/ui-utils': 1.2.11(zod@3.24.2) + '@ai-sdk/gateway': 3.0.22(zod@4.3.6) + '@ai-sdk/provider': 3.0.5 + '@ai-sdk/provider-utils': 4.0.9(zod@4.3.6) '@opentelemetry/api': 1.9.0 - jsondiffpatch: 0.6.0 - zod: 3.24.2 - optionalDependencies: - react: 18.3.1 + zod: 4.3.6 ajv@6.12.6: dependencies: @@ -4950,7 +4733,6 @@ snapshots: ansi-escapes@4.3.2: dependencies: type-fest: 0.21.3 - optional: true ansi-regex@5.0.1: {} @@ -5135,12 +4917,12 @@ snapshots: camelcase@5.3.1: {} - chai@5.1.2: + chai@5.3.3: dependencies: assertion-error: 2.0.1 check-error: 2.1.1 deep-eql: 5.0.2 - loupe: 3.1.3 + loupe: 3.2.1 pathval: 2.0.0 chalk@4.1.2: @@ -5148,8 +4930,6 @@ snapshots: ansi-styles: 4.3.0 supports-color: 7.2.0 - chalk@5.4.1: {} - chardet@0.7.0: {} check-error@2.1.1: {} @@ -5166,8 +4946,7 @@ snapshots: dependencies: consola: 3.4.0 - cli-width@4.1.0: - optional: true + cli-width@4.1.0: {} cliui@8.0.1: dependencies: @@ -5213,24 +4992,23 @@ snapshots: meow: 8.1.2 split2: 3.2.2 - cookie@0.7.2: - optional: true + cookie@1.1.1: {} - cosmiconfig-typescript-loader@4.4.0(@types/node@20.5.1)(cosmiconfig@8.3.6(typescript@5.7.3))(ts-node@10.9.2(@types/node@22.13.10)(typescript@5.7.3))(typescript@5.6.3): + cosmiconfig-typescript-loader@4.4.0(@types/node@20.5.1)(cosmiconfig@8.3.6(typescript@5.9.3))(ts-node@10.9.2(@types/node@22.13.10)(typescript@5.9.3))(typescript@5.9.3): dependencies: '@types/node': 20.5.1 - cosmiconfig: 8.3.6(typescript@5.6.3) - ts-node: 10.9.2(@types/node@20.5.1)(typescript@5.6.3) - typescript: 5.6.3 + cosmiconfig: 8.3.6(typescript@5.9.3) + ts-node: 10.9.2(@types/node@20.5.1)(typescript@5.9.3) + typescript: 5.9.3 - cosmiconfig@8.3.6(typescript@5.6.3): + cosmiconfig@8.3.6(typescript@5.9.3): dependencies: import-fresh: 3.3.0 js-yaml: 4.1.0 parse-json: 5.2.0 path-type: 4.0.0 optionalDependencies: - typescript: 5.6.3 + typescript: 5.9.3 create-require@1.1.1: {} @@ -5294,6 +5072,10 @@ snapshots: dependencies: ms: 2.1.3 + debug@4.4.3: + dependencies: + ms: 2.1.3 + decamelize-keys@1.1.1: dependencies: decamelize: 1.2.0 @@ -5321,8 +5103,6 @@ snapshots: deprecation@2.3.1: {} - dequal@2.0.3: {} - destr@2.0.3: {} detect-indent@6.1.0: {} @@ -5330,8 +5110,6 @@ snapshots: detect-libc@1.0.3: optional: true - diff-match-patch@1.0.5: {} - diff@4.0.2: {} dir-glob@3.0.1: @@ -5493,7 +5271,7 @@ snapshots: es-errors@1.3.0: {} - es-module-lexer@1.6.0: {} + es-module-lexer@1.7.0: {} es-object-atoms@1.0.0: dependencies: @@ -5598,17 +5376,17 @@ snapshots: transitivePeerDependencies: - supports-color - eslint-module-utils@2.12.0(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3))(eslint-import-resolver-node@0.3.9)(eslint@9.19.0(jiti@2.4.2)): + eslint-module-utils@2.12.0(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3))(eslint-import-resolver-node@0.3.9)(eslint@9.19.0(jiti@2.4.2)): dependencies: debug: 3.2.7 optionalDependencies: - '@typescript-eslint/parser': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) + '@typescript-eslint/parser': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) eslint: 9.19.0(jiti@2.4.2) eslint-import-resolver-node: 0.3.9 transitivePeerDependencies: - supports-color - eslint-plugin-import@2.31.0(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3))(eslint@9.19.0(jiti@2.4.2)): + eslint-plugin-import@2.31.0(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3))(eslint@9.19.0(jiti@2.4.2)): dependencies: '@rtsao/scc': 1.1.0 array-includes: 3.1.8 @@ -5619,7 +5397,7 @@ snapshots: doctrine: 2.1.0 eslint: 9.19.0(jiti@2.4.2) eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.12.0(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3))(eslint-import-resolver-node@0.3.9)(eslint@9.19.0(jiti@2.4.2)) + eslint-module-utils: 2.12.0(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3))(eslint-import-resolver-node@0.3.9)(eslint@9.19.0(jiti@2.4.2)) hasown: 2.0.2 is-core-module: 2.16.1 is-glob: 4.0.3 @@ -5631,7 +5409,7 @@ snapshots: string.prototype.trimend: 1.0.9 tsconfig-paths: 3.15.0 optionalDependencies: - '@typescript-eslint/parser': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) + '@typescript-eslint/parser': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) transitivePeerDependencies: - eslint-import-resolver-typescript - eslint-import-resolver-webpack @@ -5688,7 +5466,7 @@ snapshots: ajv: 6.12.6 chalk: 4.1.2 cross-spawn: 7.0.6 - debug: 4.4.0 + debug: 4.4.3 escape-string-regexp: 4.0.0 eslint-scope: 8.2.0 eslint-visitor-keys: 4.2.0 @@ -5736,6 +5514,8 @@ snapshots: esutils@2.0.3: {} + eventsource-parser@3.0.6: {} + execa@5.1.1: dependencies: cross-spawn: 7.0.6 @@ -5748,7 +5528,7 @@ snapshots: signal-exit: 3.0.7 strip-final-newline: 2.0.0 - expect-type@1.1.0: {} + expect-type@1.3.0: {} extendable-error@0.1.7: {} @@ -5778,9 +5558,9 @@ snapshots: dependencies: reusify: 1.0.4 - fdir@6.4.3(picomatch@4.0.2): + fdir@6.5.0(picomatch@4.0.3): optionalDependencies: - picomatch: 4.0.2 + picomatch: 4.0.3 file-entry-cache@8.0.0: dependencies: @@ -5800,6 +5580,12 @@ snapshots: locate-path: 6.0.0 path-exists: 4.0.0 + fix-dts-default-cjs-exports@1.0.1: + dependencies: + magic-string: 0.30.17 + mlly: 1.7.4 + rollup: 4.35.0 + flat-cache@4.0.1: dependencies: flatted: 3.3.1 @@ -5980,8 +5766,7 @@ snapshots: graphemer@1.4.0: {} - graphql@16.10.0: - optional: true + graphql@16.12.0: {} handlebars@4.7.8: dependencies: @@ -6022,8 +5807,7 @@ snapshots: dependencies: function-bind: 1.1.2 - headers-polyfill@4.0.3: - optional: true + headers-polyfill@4.0.3: {} hosted-git-info@2.8.9: {} @@ -6153,8 +5937,7 @@ snapshots: is-negative-zero@2.0.3: {} - is-node-process@1.2.0: - optional: true + is-node-process@1.2.0: {} is-number-object@1.0.7: dependencies: @@ -6265,6 +6048,8 @@ snapshots: js-tokens@4.0.0: {} + js-tokens@9.0.1: {} + js-yaml@3.14.1: dependencies: argparse: 1.0.10 @@ -6292,12 +6077,6 @@ snapshots: dependencies: minimist: 1.2.8 - jsondiffpatch@0.6.0: - dependencies: - '@types/diff-match-patch': 1.0.36 - chalk: 5.4.1 - diff-match-patch: 1.0.5 - jsonfile@4.0.0: optionalDependencies: graceful-fs: 4.2.11 @@ -6418,11 +6197,7 @@ snapshots: lodash@4.17.21: {} - loose-envify@1.4.0: - dependencies: - js-tokens: 4.0.0 - - loupe@3.1.3: {} + loupe@3.2.1: {} lru-cache@10.4.3: {} @@ -6511,34 +6286,32 @@ snapshots: ms@2.1.3: {} - msw@2.7.1(@types/node@22.13.10)(typescript@5.7.3): + msw@2.12.4(@types/node@22.13.10)(typescript@5.9.3): dependencies: - '@bundled-es-modules/cookie': 2.0.1 - '@bundled-es-modules/statuses': 1.0.1 - '@bundled-es-modules/tough-cookie': 0.1.6 '@inquirer/confirm': 5.1.6(@types/node@22.13.10) - '@mswjs/interceptors': 0.37.6 + '@mswjs/interceptors': 0.40.0 '@open-draft/deferred-promise': 2.2.0 - '@open-draft/until': 2.1.0 - '@types/cookie': 0.6.0 - '@types/statuses': 2.0.5 - graphql: 16.10.0 + '@types/statuses': 2.0.6 + cookie: 1.1.1 + graphql: 16.12.0 headers-polyfill: 4.0.3 is-node-process: 1.2.0 outvariant: 1.4.3 path-to-regexp: 6.3.0 picocolors: 1.1.1 + rettime: 0.7.0 + statuses: 2.0.2 strict-event-emitter: 0.5.1 - type-fest: 4.37.0 + tough-cookie: 6.0.0 + type-fest: 5.4.1 + until-async: 3.0.2 yargs: 17.7.2 optionalDependencies: - typescript: 5.7.3 + typescript: 5.9.3 transitivePeerDependencies: - '@types/node' - optional: true - mute-stream@2.0.0: - optional: true + mute-stream@2.0.0: {} mz@2.7.0: dependencies: @@ -6652,8 +6425,7 @@ snapshots: outdent@0.5.0: {} - outvariant@1.4.3: - optional: true + outvariant@1.4.3: {} own-keys@1.0.1: dependencies: @@ -6711,8 +6483,7 @@ snapshots: lru-cache: 10.4.3 minipass: 7.1.2 - path-to-regexp@6.3.0: - optional: true + path-to-regexp@6.3.0: {} path-type@4.0.0: {} @@ -6728,7 +6499,7 @@ snapshots: picomatch@2.3.1: {} - picomatch@4.0.2: {} + picomatch@4.0.3: {} pify@4.0.1: {} @@ -6763,16 +6534,8 @@ snapshots: prettier@3.4.2: {} - psl@1.15.0: - dependencies: - punycode: 2.3.1 - optional: true - punycode@2.3.1: {} - querystringify@2.2.0: - optional: true - queue-microtask@1.2.3: {} quick-lru@4.0.1: {} @@ -6782,10 +6545,6 @@ snapshots: defu: 6.1.4 destr: 2.0.3 - react@18.3.1: - dependencies: - loose-envify: 1.4.0 - read-pkg-up@7.0.1: dependencies: find-up: 4.1.0 @@ -6852,9 +6611,6 @@ snapshots: require-from-string@2.0.2: {} - requires-port@1.0.0: - optional: true - resolve-from@4.0.0: {} resolve-from@5.0.0: {} @@ -6877,32 +6633,9 @@ snapshots: path-parse: 1.0.7 supports-preserve-symlinks-flag: 1.0.0 - reusify@1.0.4: {} + rettime@0.7.0: {} - rollup@4.33.0: - dependencies: - '@types/estree': 1.0.6 - optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.33.0 - '@rollup/rollup-android-arm64': 4.33.0 - '@rollup/rollup-darwin-arm64': 4.33.0 - '@rollup/rollup-darwin-x64': 4.33.0 - '@rollup/rollup-freebsd-arm64': 4.33.0 - '@rollup/rollup-freebsd-x64': 4.33.0 - '@rollup/rollup-linux-arm-gnueabihf': 4.33.0 - '@rollup/rollup-linux-arm-musleabihf': 4.33.0 - '@rollup/rollup-linux-arm64-gnu': 4.33.0 - '@rollup/rollup-linux-arm64-musl': 4.33.0 - '@rollup/rollup-linux-loongarch64-gnu': 4.33.0 - '@rollup/rollup-linux-powerpc64le-gnu': 4.33.0 - '@rollup/rollup-linux-riscv64-gnu': 4.33.0 - '@rollup/rollup-linux-s390x-gnu': 4.33.0 - '@rollup/rollup-linux-x64-gnu': 4.33.0 - '@rollup/rollup-linux-x64-musl': 4.33.0 - '@rollup/rollup-win32-arm64-msvc': 4.33.0 - '@rollup/rollup-win32-ia32-msvc': 4.33.0 - '@rollup/rollup-win32-x64-msvc': 4.33.0 - fsevents: 2.3.3 + reusify@1.0.4: {} rollup@4.35.0: dependencies: @@ -6969,8 +6702,6 @@ snapshots: safer-buffer@2.1.2: {} - secure-json-parse@2.7.0: {} - semver@5.7.2: {} semver@6.3.1: {} @@ -7080,13 +6811,11 @@ snapshots: stackback@0.0.2: {} - statuses@2.0.1: - optional: true + statuses@2.0.2: {} - std-env@3.8.0: {} + std-env@3.10.0: {} - strict-event-emitter@0.5.1: - optional: true + strict-event-emitter@0.5.1: {} string-width@4.2.3: dependencies: @@ -7164,6 +6893,10 @@ snapshots: strip-json-comments@3.1.1: {} + strip-literal@3.1.0: + dependencies: + js-tokens: 9.0.1 + sucrase@3.35.0: dependencies: '@jridgewell/gen-mapping': 0.3.8 @@ -7180,11 +6913,7 @@ snapshots: supports-preserve-symlinks-flag@1.0.0: {} - swr@2.3.3(react@18.3.1): - dependencies: - dequal: 2.0.3 - react: 18.3.1 - use-sync-external-store: 1.4.0(react@18.3.1) + tagged-tag@1.0.0: {} tar@6.2.1: dependencies: @@ -7207,8 +6936,6 @@ snapshots: dependencies: any-promise: 1.3.0 - throttleit@2.1.0: {} - through2@4.0.2: dependencies: readable-stream: 3.6.2 @@ -7219,16 +6946,22 @@ snapshots: tinyexec@0.3.2: {} - tinyglobby@0.2.12: + tinyglobby@0.2.15: dependencies: - fdir: 6.4.3(picomatch@4.0.2) - picomatch: 4.0.2 + fdir: 6.5.0(picomatch@4.0.3) + picomatch: 4.0.3 + + tinypool@1.1.1: {} - tinypool@1.0.2: {} + tinyrainbow@2.0.0: {} - tinyrainbow@1.2.0: {} + tinyspy@4.0.4: {} - tinyspy@3.0.2: {} + tldts-core@7.0.19: {} + + tldts@7.0.19: + dependencies: + tldts-core: 7.0.19 tmp@0.0.33: dependencies: @@ -7238,13 +6971,9 @@ snapshots: dependencies: is-number: 7.0.0 - tough-cookie@4.1.4: + tough-cookie@6.0.0: dependencies: - psl: 1.15.0 - punycode: 2.3.1 - universalify: 0.2.0 - url-parse: 1.5.10 - optional: true + tldts: 7.0.19 tr46@0.0.3: {} @@ -7256,13 +6985,13 @@ snapshots: trim-newlines@3.0.1: {} - ts-api-utils@2.0.1(typescript@5.7.3): + ts-api-utils@2.0.1(typescript@5.9.3): dependencies: - typescript: 5.7.3 + typescript: 5.9.3 ts-interface-checker@0.1.13: {} - ts-node@10.9.2(@types/node@20.5.1)(typescript@5.6.3): + ts-node@10.9.2(@types/node@20.5.1)(typescript@5.9.3): dependencies: '@cspotcode/source-map-support': 0.8.1 '@tsconfig/node10': 1.0.11 @@ -7276,13 +7005,13 @@ snapshots: create-require: 1.1.1 diff: 4.0.2 make-error: 1.3.6 - typescript: 5.6.3 + typescript: 5.9.3 v8-compile-cache-lib: 3.0.1 yn: 3.1.1 - tsconfck@3.1.5(typescript@5.7.3): + tsconfck@3.1.5(typescript@5.9.3): optionalDependencies: - typescript: 5.7.3 + typescript: 5.9.3 tsconfig-paths@3.15.0: dependencies: @@ -7291,14 +7020,15 @@ snapshots: minimist: 1.2.8 strip-bom: 3.0.0 - tsup@8.4.0(jiti@2.4.2)(postcss@8.5.1)(tsx@4.19.3)(typescript@5.7.3)(yaml@2.7.0): + tsup@8.5.0(jiti@2.4.2)(postcss@8.5.1)(tsx@4.19.3)(typescript@5.9.3)(yaml@2.7.0): dependencies: bundle-require: 5.1.0(esbuild@0.25.1) cac: 6.7.14 chokidar: 4.0.3 consola: 3.4.0 - debug: 4.4.0 + debug: 4.4.3 esbuild: 0.25.1 + fix-dts-default-cjs-exports: 1.0.1 joycon: 3.1.1 picocolors: 1.1.1 postcss-load-config: 6.0.1(jiti@2.4.2)(postcss@8.5.1)(tsx@4.19.3)(yaml@2.7.0) @@ -7307,11 +7037,11 @@ snapshots: source-map: 0.8.0-beta.0 sucrase: 3.35.0 tinyexec: 0.3.2 - tinyglobby: 0.2.12 + tinyglobby: 0.2.15 tree-kill: 1.2.2 optionalDependencies: postcss: 8.5.1 - typescript: 5.7.3 + typescript: 5.9.3 transitivePeerDependencies: - jiti - supports-color @@ -7360,8 +7090,7 @@ snapshots: type-fest@0.18.1: {} - type-fest@0.21.3: - optional: true + type-fest@0.21.3: {} type-fest@0.6.0: {} @@ -7369,6 +7098,10 @@ snapshots: type-fest@4.37.0: {} + type-fest@5.4.1: + dependencies: + tagged-tag: 1.0.0 + typed-array-buffer@1.0.2: dependencies: call-bind: 1.0.7 @@ -7434,19 +7167,17 @@ snapshots: possible-typed-array-names: 1.0.0 reflect.getprototypeof: 1.0.10 - typescript-eslint@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3): + typescript-eslint@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3): dependencies: - '@typescript-eslint/eslint-plugin': 8.26.1(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3))(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) - '@typescript-eslint/parser': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) - '@typescript-eslint/utils': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.7.3) + '@typescript-eslint/eslint-plugin': 8.26.1(@typescript-eslint/parser@8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3))(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) + '@typescript-eslint/parser': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) + '@typescript-eslint/utils': 8.26.1(eslint@9.19.0(jiti@2.4.2))(typescript@5.9.3) eslint: 9.19.0(jiti@2.4.2) - typescript: 5.7.3 + typescript: 5.9.3 transitivePeerDependencies: - supports-color - typescript@5.6.3: {} - - typescript@5.7.3: {} + typescript@5.9.3: {} ufo@1.5.4: {} @@ -7477,25 +7208,14 @@ snapshots: universalify@0.1.2: {} - universalify@0.2.0: - optional: true - universalify@2.0.1: {} + until-async@3.0.2: {} + uri-js@4.4.1: dependencies: punycode: 2.3.1 - url-parse@1.5.10: - dependencies: - querystringify: 2.2.0 - requires-port: 1.0.0 - optional: true - - use-sync-external-store@1.4.0(react@18.3.1): - dependencies: - react: 18.3.1 - util-deprecate@1.0.2: {} uuid@8.3.2: {} @@ -7507,12 +7227,12 @@ snapshots: spdx-correct: 3.2.0 spdx-expression-parse: 3.0.1 - vite-node@2.1.8(@types/node@22.13.10)(lightningcss@1.29.1): + vite-node@3.2.4(@types/node@22.13.10)(lightningcss@1.29.1): dependencies: cac: 6.7.14 - debug: 4.4.0 - es-module-lexer: 1.6.0 - pathe: 1.1.2 + debug: 4.4.3 + es-module-lexer: 1.7.0 + pathe: 2.0.3 vite: 5.4.14(@types/node@22.13.10)(lightningcss@1.29.1) transitivePeerDependencies: - '@types/node' @@ -7525,11 +7245,11 @@ snapshots: - supports-color - terser - vite-tsconfig-paths@5.1.4(typescript@5.7.3)(vite@5.4.14(@types/node@22.13.10)(lightningcss@1.29.1)): + vite-tsconfig-paths@5.1.4(typescript@5.9.3)(vite@5.4.14(@types/node@22.13.10)(lightningcss@1.29.1)): dependencies: debug: 4.4.0 globrex: 0.1.2 - tsconfck: 3.1.5(typescript@5.7.3) + tsconfck: 3.1.5(typescript@5.9.3) optionalDependencies: vite: 5.4.14(@types/node@22.13.10)(lightningcss@1.29.1) transitivePeerDependencies: @@ -7540,33 +7260,36 @@ snapshots: dependencies: esbuild: 0.21.5 postcss: 8.5.1 - rollup: 4.33.0 + rollup: 4.35.0 optionalDependencies: '@types/node': 22.13.10 fsevents: 2.3.3 lightningcss: 1.29.1 - vitest@2.1.8(@edge-runtime/vm@5.0.0)(@types/node@22.13.10)(lightningcss@1.29.1)(msw@2.7.1(@types/node@22.13.10)(typescript@5.7.3)): - dependencies: - '@vitest/expect': 2.1.8 - '@vitest/mocker': 2.1.8(msw@2.7.1(@types/node@22.13.10)(typescript@5.7.3))(vite@5.4.14(@types/node@22.13.10)(lightningcss@1.29.1)) - '@vitest/pretty-format': 2.1.8 - '@vitest/runner': 2.1.8 - '@vitest/snapshot': 2.1.8 - '@vitest/spy': 2.1.8 - '@vitest/utils': 2.1.8 - chai: 5.1.2 - debug: 4.4.0 - expect-type: 1.1.0 + vitest@3.2.4(@edge-runtime/vm@5.0.0)(@types/node@22.13.10)(lightningcss@1.29.1)(msw@2.12.4(@types/node@22.13.10)(typescript@5.9.3)): + dependencies: + '@types/chai': 5.2.3 + '@vitest/expect': 3.2.4 + '@vitest/mocker': 3.2.4(msw@2.12.4(@types/node@22.13.10)(typescript@5.9.3))(vite@5.4.14(@types/node@22.13.10)(lightningcss@1.29.1)) + '@vitest/pretty-format': 3.2.4 + '@vitest/runner': 3.2.4 + '@vitest/snapshot': 3.2.4 + '@vitest/spy': 3.2.4 + '@vitest/utils': 3.2.4 + chai: 5.3.3 + debug: 4.4.3 + expect-type: 1.3.0 magic-string: 0.30.17 - pathe: 1.1.2 - std-env: 3.8.0 + pathe: 2.0.3 + picomatch: 4.0.3 + std-env: 3.10.0 tinybench: 2.9.0 tinyexec: 0.3.2 - tinypool: 1.0.2 - tinyrainbow: 1.2.0 + tinyglobby: 0.2.15 + tinypool: 1.1.1 + tinyrainbow: 2.0.0 vite: 5.4.14(@types/node@22.13.10)(lightningcss@1.29.1) - vite-node: 2.1.8(@types/node@22.13.10)(lightningcss@1.29.1) + vite-node: 3.2.4(@types/node@22.13.10)(lightningcss@1.29.1) why-is-node-running: 2.3.0 optionalDependencies: '@edge-runtime/vm': 5.0.0 @@ -7671,7 +7394,6 @@ snapshots: ansi-styles: 4.3.0 string-width: 4.2.3 strip-ansi: 6.0.1 - optional: true wrap-ansi@7.0.0: dependencies: @@ -7712,11 +7434,6 @@ snapshots: yocto-queue@0.1.0: {} - yoctocolors-cjs@2.1.2: - optional: true - - zod-to-json-schema@3.24.4(zod@3.24.2): - dependencies: - zod: 3.24.2 + yoctocolors-cjs@2.1.2: {} - zod@3.24.2: {} + zod@4.3.6: {} diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index 9520e6d..73d231e 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -8,4 +8,4 @@ catalog: "@types/node": "^22.10.10" eslint: ^9.19.0 prettier: ^3.4.2 - typescript: ^5.7.3 + typescript: ^5.9.2