@happyvertical/ai 0.78.2 → 0.79.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +63 -5
- package/dist/chunks/{anthropic-BRwbhwIl.js → anthropic-2z-82zgr.js} +75 -8
- package/dist/chunks/anthropic-2z-82zgr.js.map +1 -0
- package/dist/chunks/{bedrock-Cf1xUerN.js → bedrock-Dc2eVPUD.js} +153 -41
- package/dist/chunks/bedrock-Dc2eVPUD.js.map +1 -0
- package/dist/chunks/{bifrost-3mXtQsTj.js → bifrost-CEnCsciy.js} +36 -11
- package/dist/chunks/bifrost-CEnCsciy.js.map +1 -0
- package/dist/chunks/{claude-cli-BrHRfkry.js → claude-cli-X1ONjE8K.js} +3 -3
- package/dist/chunks/{claude-cli-BrHRfkry.js.map → claude-cli-X1ONjE8K.js.map} +1 -1
- package/dist/chunks/{gateway-admin-C4GFPbZF.js → gateway-admin-BUhBzXZb.js} +2 -2
- package/dist/chunks/{gateway-admin-C4GFPbZF.js.map → gateway-admin-BUhBzXZb.js.map} +1 -1
- package/dist/chunks/{gemini-BfpHXDIQ.js → gemini-CS56gY0D.js} +138 -32
- package/dist/chunks/gemini-CS56gY0D.js.map +1 -0
- package/dist/chunks/{huggingface-280qv9iv.js → huggingface-wQSfO5xA.js} +64 -19
- package/dist/chunks/huggingface-wQSfO5xA.js.map +1 -0
- package/dist/chunks/{index-BT4thAvS.js → index-DCXO0nZA.js} +383 -24
- package/dist/chunks/index-DCXO0nZA.js.map +1 -0
- package/dist/chunks/{litellm-DhPKa_Jz.js → litellm-BMFTYbWc.js} +36 -11
- package/dist/chunks/litellm-BMFTYbWc.js.map +1 -0
- package/dist/chunks/{ollama-Di1ldur0.js → ollama-DsGDrA-c.js} +171 -60
- package/dist/chunks/ollama-DsGDrA-c.js.map +1 -0
- package/dist/chunks/{openai-5snI2diE.js → openai-CJEo69jb.js} +145 -12
- package/dist/chunks/openai-CJEo69jb.js.map +1 -0
- package/dist/chunks/{qwen-tts-DgPgdXxG.js → qwen-tts-BLYZ6d9s.js} +2 -2
- package/dist/chunks/{qwen-tts-DgPgdXxG.js.map → qwen-tts-BLYZ6d9s.js.map} +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +15 -12
- package/dist/shared/factory.d.ts.map +1 -1
- package/dist/shared/providers/anthropic.d.ts.map +1 -1
- package/dist/shared/providers/bedrock.d.ts.map +1 -1
- package/dist/shared/providers/bifrost.d.ts.map +1 -1
- package/dist/shared/providers/gemini.d.ts +0 -5
- package/dist/shared/providers/gemini.d.ts.map +1 -1
- package/dist/shared/providers/huggingface.d.ts.map +1 -1
- package/dist/shared/providers/litellm.d.ts.map +1 -1
- package/dist/shared/providers/ollama.d.ts +0 -1
- package/dist/shared/providers/ollama.d.ts.map +1 -1
- package/dist/shared/providers/openai.d.ts +2 -2
- package/dist/shared/providers/openai.d.ts.map +1 -1
- package/dist/shared/safety.d.ts +55 -0
- package/dist/shared/safety.d.ts.map +1 -0
- package/dist/shared/types.d.ts +74 -6
- package/dist/shared/types.d.ts.map +1 -1
- package/package.json +2 -2
- package/dist/chunks/anthropic-BRwbhwIl.js.map +0 -1
- package/dist/chunks/bedrock-Cf1xUerN.js.map +0 -1
- package/dist/chunks/bifrost-3mXtQsTj.js.map +0 -1
- package/dist/chunks/gemini-BfpHXDIQ.js.map +0 -1
- package/dist/chunks/huggingface-280qv9iv.js.map +0 -1
- package/dist/chunks/index-BT4thAvS.js.map +0 -1
- package/dist/chunks/litellm-DhPKa_Jz.js.map +0 -1
- package/dist/chunks/ollama-Di1ldur0.js.map +0 -1
- package/dist/chunks/openai-5snI2diE.js.map +0 -1
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"ollama-Di1ldur0.js","sources":["../../src/shared/providers/ollama.ts"],"sourcesContent":["/**\n * Ollama provider implementation.\n *\n * Uses Ollama's native `/api/*` endpoints for chat, completions, embeddings,\n * and model discovery, while bridging to the experimental OpenAI-compatible\n * image-generation endpoint when available.\n */\n\nimport { ValidationError } from '@happyvertical/utils';\n\nimport type {\n AICapabilities,\n AIInterface,\n AIMessage,\n AIModel,\n AIResponse,\n ChatOptions,\n CompletionOptions,\n EmbeddingOptions,\n EmbeddingResponse,\n ImageDescriptionOptions,\n ImageEmbeddingOptions,\n ImageGenerationOptions,\n ImageGenerationResponse,\n MessageOptions,\n OllamaOptions,\n TokenUsage,\n TTSOptions,\n TTSResponse,\n Voice,\n VoiceCloneOptions,\n VoiceDesignOptions,\n VoiceListOptions,\n} from '../types';\nimport {\n AIError,\n AuthenticationError,\n ContentFilterError,\n ContextLengthError,\n extractTextContent,\n ModelNotFoundError,\n RateLimitError,\n} from '../types';\nimport { emitUsage } from './usage';\n\nconst DEFAULT_OLLAMA_HOST = 'http://localhost:11434';\n\nconst OLLAMA_CAPABILITIES: AICapabilities = {\n chat: true,\n completion: true,\n embeddings: true,\n streaming: true,\n functions: true,\n vision: true,\n fineTuning: false,\n imageEmbeddings: true,\n imageGeneration: true,\n tts: false,\n voiceCloning: false,\n voiceDesign: false,\n maxContextLength: 131072,\n supportedOperations: [\n 'chat',\n 'completion',\n 'embedding',\n 'streaming',\n 'functions',\n 'vision',\n 'image_embedding',\n 'image_generation',\n ],\n};\n\ntype ResolvedOllamaCapability =\n | 'chat'\n | 'vision'\n | 'embedding'\n | 'image_generation';\n\ninterface OllamaModelSummary {\n name?: string;\n model?: string;\n modified_at?: string;\n size?: number;\n details?: {\n family?: string;\n families?: string[];\n format?: string;\n parameter_size?: string;\n quantization_level?: string;\n };\n}\n\ninterface OllamaTagsResponse {\n models?: OllamaModelSummary[];\n}\n\ninterface OllamaShowResponse {\n capabilities?: string[];\n parameters?: string;\n modified_at?: string;\n details?: {\n parent_model?: string;\n format?: string;\n family?: string;\n families?: string[];\n parameter_size?: string;\n quantization_level?: string;\n };\n model_info?: Record<string, unknown>;\n}\n\ninterface OllamaToolCall {\n type?: 'function';\n function?: {\n index?: number;\n name?: string;\n arguments?: Record<string, unknown>;\n };\n}\n\ninterface OllamaMessage {\n role: 'system' | 'user' | 'assistant' | 'tool';\n content?: string;\n thinking?: string;\n images?: string[];\n tool_name?: string;\n tool_calls?: OllamaToolCall[];\n}\n\ninterface OllamaChatResponse {\n model?: string;\n message?: OllamaMessage;\n done?: boolean;\n done_reason?: string;\n prompt_eval_count?: number;\n eval_count?: number;\n}\n\ninterface OllamaGenerateResponse {\n model?: string;\n response?: string;\n thinking?: string;\n done?: boolean;\n done_reason?: string;\n prompt_eval_count?: number;\n eval_count?: number;\n}\n\ninterface OllamaEmbedResponse {\n model?: string;\n embeddings?: number[][];\n embedding?: number[];\n prompt_eval_count?: number;\n}\n\ninterface OllamaImageGenerationResponse {\n created?: number;\n data?: Array<{\n b64_json?: string;\n revised_prompt?: string;\n }>;\n}\n\nfunction stripTrailingSlash(value: string): string {\n return value.replace(/\\/+$/, '');\n}\n\nfunction normalizeHost(baseUrl?: string): string {\n const rawBase = baseUrl?.trim() || DEFAULT_OLLAMA_HOST;\n const withScheme = /^[a-z][a-z0-9+.-]*:\\/\\//i.test(rawBase)\n ? rawBase\n : `http://${rawBase}`;\n const base = stripTrailingSlash(withScheme);\n if (base.endsWith('/api')) return base.slice(0, -4);\n if (base.endsWith('/v1')) return base.slice(0, -3);\n return base;\n}\n\nfunction isEmbeddingModel(modelId: string): boolean {\n return /(?:^|[-_:/])(?:embed|embedding)|nomic-embed|mxbai-embed/i.test(\n modelId,\n );\n}\n\nfunction isImageGenerationModel(modelId: string): boolean {\n return /(?:^|[-_:/])(flux|sdxl|stable(?:[-_ ]?diffusion)?|z-image|image(?:[-_ ]?(?:turbo|gen|generator)))/i.test(\n modelId,\n );\n}\n\nfunction inferVisionSupport(\n modelId: string,\n capabilities: Set<string>,\n): boolean {\n if (capabilities.has('vision')) return true;\n return /vision|llava|bakllava|moondream|pixtral|qwen.*vl|vl-|gemma3/i.test(\n modelId,\n );\n}\n\nfunction inferFunctionSupport(\n modelId: string,\n capabilities: Set<string>,\n): boolean {\n if (\n capabilities.has('tools') ||\n capabilities.has('tool_calling') ||\n capabilities.has('function_calling')\n ) {\n return true;\n }\n\n if (isEmbeddingModel(modelId) || isImageGenerationModel(modelId)) {\n return false;\n }\n\n return /qwen|llama3|gpt-oss|mistral|deepseek|command-r|phi4/i.test(modelId);\n}\n\nfunction parseCapabilities(\n modelId: string,\n show?: OllamaShowResponse | null,\n): string[] {\n const capabilities = new Set(\n (show?.capabilities || []).map((capability) => capability.toLowerCase()),\n );\n\n if (isImageGenerationModel(modelId)) {\n return ['image_generation'];\n }\n\n if (\n capabilities.has('embedding') ||\n capabilities.has('embeddings') ||\n isEmbeddingModel(modelId)\n ) {\n return ['embeddings'];\n }\n\n const supported = new Set<string>(['text', 'chat']);\n\n if (inferVisionSupport(modelId, capabilities)) {\n supported.add('vision');\n }\n\n if (inferFunctionSupport(modelId, capabilities)) {\n supported.add('functions');\n }\n\n return [...supported];\n}\n\nfunction parseContextLength(\n modelId: string,\n show?: OllamaShowResponse | null,\n): number {\n const modelInfo = show?.model_info || {};\n\n for (const [key, value] of Object.entries(modelInfo)) {\n if (key.endsWith('.context_length') && typeof value === 'number') {\n return value;\n }\n }\n\n const numCtxMatch = show?.parameters?.match(/\\bnum_ctx\\s+(\\d+)/);\n if (numCtxMatch?.[1]) {\n return Number(numCtxMatch[1]);\n }\n\n if (isEmbeddingModel(modelId)) return 8192;\n if (/gemma3|qwen3|gpt-oss|llama3/i.test(modelId)) return 131072;\n return 32768;\n}\n\nfunction mapUsage(\n promptTokens?: number,\n completionTokens?: number,\n): TokenUsage | undefined {\n if (\n typeof promptTokens !== 'number' &&\n typeof completionTokens !== 'number'\n ) {\n return undefined;\n }\n\n const prompt = promptTokens || 0;\n const completion = completionTokens || 0;\n return {\n promptTokens: prompt,\n completionTokens: completion,\n totalTokens: prompt + completion,\n };\n}\n\nfunction mapFinishReason(reason?: string): AIResponse['finishReason'] {\n switch (reason) {\n case 'stop':\n return 'stop';\n case 'length':\n return 'length';\n case 'content_filter':\n return 'content_filter';\n default:\n return 'stop';\n }\n}\n\nfunction scoreModelForCapability(\n model: AIModel,\n capability: ResolvedOllamaCapability,\n): number {\n const id = model.id.toLowerCase();\n let score = 0;\n\n if (id.includes(':latest')) score += 6;\n if (id.includes('instruct') || id.includes('-it')) score += 6;\n if (id.startsWith('hf.co/')) score -= 8;\n if (/ocr|rerank|embed|image|diffusion|flux/.test(id)) score -= 12;\n\n switch (capability) {\n case 'vision':\n if (model.supportsVision) score += 25;\n if (/gemma4|gemma3/.test(id)) score += 12;\n if (/qwen.*vl|llava|moondream|vision/.test(id)) score += 8;\n if (/ocr/.test(id)) score -= 10;\n break;\n case 'embedding':\n if (model.capabilities.includes('embeddings')) score += 20;\n if (/nomic|mxbai|embed/.test(id)) score += 6;\n break;\n case 'image_generation':\n if (model.capabilities.includes('image_generation')) score += 20;\n if (/flux|sdxl|stable/.test(id)) score += 8;\n break;\n case 'chat':\n default:\n if (model.capabilities.includes('chat')) score += 12;\n if (model.supportsFunctions) score += 4;\n if (/llama|mistral|qwen|gemma|phi|command-r|deepseek-coder/.test(id)) {\n score += 8;\n }\n if (/gpt-oss/.test(id)) score -= 3;\n break;\n }\n\n return score;\n}\n\nexport class OllamaProvider implements AIInterface {\n private readonly options: OllamaOptions;\n private readonly host: string;\n private readonly configuredDefaultModel?: string;\n private modelListPromise?: Promise<AIModel[]>;\n private readonly modelShowCache = new Map<\n string,\n Promise<OllamaShowResponse | null>\n >();\n private readonly resolvedModelCache = new Map<\n ResolvedOllamaCapability,\n Promise<string>\n >();\n\n constructor(options: OllamaOptions) {\n this.host = normalizeHost(options.baseUrl);\n this.options = {\n ...options,\n baseUrl: this.host,\n };\n this.configuredDefaultModel = options.defaultModel;\n }\n\n private get nativeBaseUrl(): string {\n return `${this.host}/api`;\n }\n\n private get compatibilityBaseUrl(): string {\n return `${this.host}/v1`;\n }\n\n private buildHeaders(stream = false): Headers {\n const headers = new Headers(this.options.headers);\n headers.set('Content-Type', 'application/json');\n headers.set(\n 'Accept',\n stream ? 'application/x-ndjson, application/json' : 'application/json',\n );\n if (this.options.apiKey) {\n headers.set('Authorization', `Bearer ${this.options.apiKey}`);\n }\n return headers;\n }\n\n private async fetchWithTimeout(\n url: string,\n init: RequestInit,\n ): Promise<Response> {\n const controller = new AbortController();\n const timeout =\n typeof this.options.timeout === 'number' ? this.options.timeout : 0;\n const timer = timeout\n ? setTimeout(() => controller.abort(), timeout)\n : undefined;\n\n try {\n return await fetch(url, {\n ...init,\n signal: controller.signal,\n });\n } finally {\n if (timer) clearTimeout(timer);\n }\n }\n\n private async buildHttpError(response: Response): Promise<AIError> {\n const text = await response.text();\n const message =\n text && text.trim().length > 0\n ? text.trim()\n : `Ollama request failed with status ${response.status}`;\n\n switch (response.status) {\n case 401:\n case 403:\n return new AuthenticationError('ollama');\n case 404:\n return new ModelNotFoundError(message, 'ollama');\n case 413:\n return new ContextLengthError('ollama');\n case 429:\n return new RateLimitError('ollama');\n default:\n if (/content[_ -]?filter/i.test(message)) {\n return new ContentFilterError('ollama');\n }\n if (/context|too long|maximum context/i.test(message)) {\n return new ContextLengthError('ollama');\n }\n return new AIError(message, 'API_ERROR', 'ollama');\n }\n }\n\n private mapError(error: unknown): AIError {\n if (error instanceof AIError) {\n return error;\n }\n\n if (error instanceof Error && error.name === 'AbortError') {\n return new AIError('Ollama request timed out', 'TIMEOUT', 'ollama');\n }\n\n const message =\n error instanceof Error ? error.message : 'Unknown error occurred';\n return new AIError(message, 'UNKNOWN_ERROR', 'ollama');\n }\n\n private async requestJson<T>(\n path: string,\n body?: Record<string, unknown>,\n options: { compatibility?: boolean } = {},\n ): Promise<T> {\n const baseUrl = options.compatibility\n ? this.compatibilityBaseUrl\n : this.nativeBaseUrl;\n const response = await this.fetchWithTimeout(`${baseUrl}${path}`, {\n method: body ? 'POST' : 'GET',\n headers: this.buildHeaders(),\n body: body ? JSON.stringify(body) : undefined,\n });\n\n if (!response.ok) {\n throw await this.buildHttpError(response);\n }\n\n return (await response.json()) as T;\n }\n\n private async requestStream(\n path: string,\n body: Record<string, unknown>,\n ): Promise<Response> {\n const response = await this.fetchWithTimeout(\n `${this.nativeBaseUrl}${path}`,\n {\n method: 'POST',\n headers: this.buildHeaders(true),\n body: JSON.stringify(body),\n },\n );\n\n if (!response.ok) {\n throw await this.buildHttpError(response);\n }\n\n return response;\n }\n\n private async *parseNdjson<T>(response: Response): AsyncIterable<T> {\n const reader = response.body?.getReader();\n if (!reader) {\n return;\n }\n\n const decoder = new TextDecoder();\n let buffer = '';\n\n while (true) {\n const { value, done } = await reader.read();\n if (done) break;\n\n buffer += decoder.decode(value, { stream: true });\n\n let newlineIndex = buffer.indexOf('\\n');\n while (newlineIndex !== -1) {\n const line = buffer.slice(0, newlineIndex).trim();\n buffer = buffer.slice(newlineIndex + 1);\n if (line) {\n yield JSON.parse(line) as T;\n }\n newlineIndex = buffer.indexOf('\\n');\n }\n }\n\n buffer += decoder.decode();\n const line = buffer.trim();\n if (line) {\n yield JSON.parse(line) as T;\n }\n }\n\n private async showModel(model: string): Promise<OllamaShowResponse | null> {\n const cached = this.modelShowCache.get(model);\n if (cached) {\n return cached;\n }\n\n const pending = this.requestJson<OllamaShowResponse>('/show', {\n model,\n verbose: false,\n }).catch((_error) => null);\n\n this.modelShowCache.set(model, pending);\n return pending;\n }\n\n private async resolveModel(\n capability: ResolvedOllamaCapability,\n explicitModel?: string,\n ): Promise<string> {\n if (explicitModel) {\n return explicitModel;\n }\n\n if (\n this.configuredDefaultModel &&\n (capability === 'chat' || capability === 'vision')\n ) {\n return this.configuredDefaultModel;\n }\n\n const cached = this.resolvedModelCache.get(capability);\n if (cached) {\n return cached;\n }\n\n const pending = this.selectModel(capability).catch((error) => {\n this.resolvedModelCache.delete(capability);\n throw error;\n });\n this.resolvedModelCache.set(capability, pending);\n return pending;\n }\n\n private async selectModel(\n capability: ResolvedOllamaCapability,\n ): Promise<string> {\n const models = await this.getModels();\n const candidates = models.filter((candidate) => {\n switch (capability) {\n case 'vision':\n return (\n candidate.capabilities.includes('vision') ||\n candidate.supportsVision === true\n );\n case 'embedding':\n return candidate.capabilities.includes('embeddings');\n case 'image_generation':\n return candidate.capabilities.includes('image_generation');\n case 'chat':\n default:\n return candidate.capabilities.includes('chat');\n }\n });\n\n const model = candidates.sort(\n (left, right) =>\n scoreModelForCapability(right, capability) -\n scoreModelForCapability(left, capability),\n )[0];\n\n if (!model) {\n throw new ValidationError(\n `No ${capability} model is available from the Ollama host`,\n {\n provider: 'ollama',\n capability,\n hint: 'Pass model/defaultModel explicitly or make sure the Ollama host has a compatible model installed',\n },\n );\n }\n\n return model.id;\n }\n\n private isVisionRequest(messages: AIMessage[]): boolean {\n return messages.some(\n (message) =>\n Array.isArray(message.content) &&\n message.content.some((part) => part.type === 'image_url'),\n );\n }\n\n private async imageToBase64Payload(image: string | Buffer): Promise<string> {\n if (Buffer.isBuffer(image)) {\n return image.toString('base64');\n }\n\n if (image.startsWith('data:')) {\n const commaIndex = image.indexOf(',');\n return commaIndex === -1 ? image : image.slice(commaIndex + 1);\n }\n\n const response = await fetch(image);\n if (!response.ok) {\n throw new AIError(\n `Failed to fetch image: ${response.status} ${response.statusText}`,\n 'IMAGE_FETCH_ERROR',\n 'ollama',\n );\n }\n\n const arrayBuffer = await response.arrayBuffer();\n return Buffer.from(arrayBuffer).toString('base64');\n }\n\n private async imageToDataUrl(image: string | Buffer): Promise<string> {\n if (Buffer.isBuffer(image)) {\n return `data:image/png;base64,${image.toString('base64')}`;\n }\n\n if (image.startsWith('data:')) {\n return image;\n }\n\n const response = await fetch(image);\n if (!response.ok) {\n throw new AIError(\n `Failed to fetch image: ${response.status} ${response.statusText}`,\n 'IMAGE_FETCH_ERROR',\n 'ollama',\n );\n }\n\n const contentType = response.headers.get('content-type') || 'image/png';\n const arrayBuffer = await response.arrayBuffer();\n return `data:${contentType};base64,${Buffer.from(arrayBuffer).toString('base64')}`;\n }\n\n private parseToolArguments(argumentsText?: string): Record<string, unknown> {\n if (!argumentsText) {\n return {};\n }\n\n try {\n const parsed = JSON.parse(argumentsText);\n return parsed && typeof parsed === 'object' ? parsed : {};\n } catch {\n return {};\n }\n }\n\n private async mapMessagesToOllama(\n messages: AIMessage[],\n ): Promise<OllamaMessage[]> {\n const mappedMessages = await Promise.all(\n messages.map(async (message) => {\n const content = extractTextContent(message.content);\n const mapped: OllamaMessage = {\n role:\n message.role === 'function'\n ? 'tool'\n : (message.role as OllamaMessage['role']),\n content,\n };\n\n if (Array.isArray(message.content)) {\n const imageParts = message.content.filter(\n (part) => part.type === 'image_url',\n );\n if (imageParts.length > 0) {\n mapped.images = await Promise.all(\n imageParts.map((part) =>\n this.imageToBase64Payload(part.image_url.url),\n ),\n );\n }\n }\n\n if (\n mapped.role === 'assistant' &&\n Array.isArray(message.tool_calls) &&\n message.tool_calls.length > 0\n ) {\n mapped.tool_calls = message.tool_calls.map((toolCall, index) => ({\n type: 'function',\n function: {\n index,\n name: toolCall.function.name,\n arguments: this.parseToolArguments(toolCall.function.arguments),\n },\n }));\n }\n\n if (mapped.role === 'tool' && message.name) {\n mapped.tool_name = message.name;\n }\n\n return mapped;\n }),\n );\n\n return mappedMessages;\n }\n\n private mapTools(\n tools: ChatOptions['tools'],\n toolChoice: ChatOptions['toolChoice'],\n ): Array<Record<string, unknown>> | undefined {\n if (!tools || tools.length === 0 || toolChoice === 'none') {\n return undefined;\n }\n\n const scopedTools =\n toolChoice && typeof toolChoice === 'object'\n ? tools.filter(\n (tool) => tool.function.name === toolChoice.function.name,\n )\n : tools;\n\n if (scopedTools.length === 0) {\n return undefined;\n }\n\n return scopedTools.map((tool) => ({\n type: 'function',\n function: {\n name: tool.function.name,\n description: tool.function.description,\n parameters: tool.function.parameters || { type: 'object' },\n },\n }));\n }\n\n private buildRuntimeOptions(options: {\n maxTokens?: number;\n temperature?: number;\n topP?: number;\n stop?: string | string[];\n seed?: number;\n }): Record<string, unknown> | undefined {\n const runtimeOptions: Record<string, unknown> = {};\n\n if (typeof options.maxTokens === 'number') {\n runtimeOptions.num_predict = options.maxTokens;\n }\n if (typeof options.temperature === 'number') {\n runtimeOptions.temperature = options.temperature;\n }\n if (typeof options.topP === 'number') {\n runtimeOptions.top_p = options.topP;\n }\n if (options.stop) {\n runtimeOptions.stop = Array.isArray(options.stop)\n ? options.stop\n : [options.stop];\n }\n if (typeof options.seed === 'number') {\n runtimeOptions.seed = options.seed;\n }\n\n return Object.keys(runtimeOptions).length > 0 ? runtimeOptions : undefined;\n }\n\n private mapThink(\n options: Pick<ChatOptions, 'thinkingLevel'>,\n ): boolean | string | undefined {\n if (!Object.hasOwn(options, 'thinkingLevel')) {\n return undefined;\n }\n\n return options.thinkingLevel;\n }\n\n async chat(\n messages: AIMessage[],\n options: ChatOptions = {},\n ): Promise<AIResponse> {\n const startTime = Date.now();\n try {\n const model = await this.resolveModel(\n this.isVisionRequest(messages) ? 'vision' : 'chat',\n options.model,\n );\n\n const response = await this.requestJson<OllamaChatResponse>('/chat', {\n model,\n messages: await this.mapMessagesToOllama(messages),\n stream: false,\n format:\n options.responseFormat?.type === 'json_object' ? 'json' : undefined,\n tools: this.mapTools(options.tools, options.toolChoice),\n think: this.mapThink(options),\n keep_alive: this.options.keepAlive,\n options: this.buildRuntimeOptions(options),\n });\n\n const usage = mapUsage(response.prompt_eval_count, response.eval_count);\n\n emitUsage(\n this.options,\n 'ollama',\n 'chat',\n response.model || model,\n usage,\n startTime,\n options.usageTags,\n );\n\n const toolCalls =\n response.message?.tool_calls\n ?.filter((call) => call.function?.name)\n .map((call, index) => ({\n id: `${response.model || model}-tool-${index + 1}`,\n type: 'function' as const,\n function: {\n name: call.function?.name || '',\n arguments: JSON.stringify(call.function?.arguments || {}),\n },\n })) || undefined;\n\n return {\n content: response.message?.content || '',\n model: response.model || model,\n usage,\n finishReason:\n toolCalls && toolCalls.length > 0\n ? 'tool_calls'\n : mapFinishReason(response.done_reason),\n toolCalls: toolCalls && toolCalls.length > 0 ? toolCalls : undefined,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async complete(\n prompt: string,\n options: CompletionOptions = {},\n ): Promise<AIResponse> {\n const startTime = Date.now();\n try {\n const model = await this.resolveModel('chat', options.model);\n const response = await this.requestJson<OllamaGenerateResponse>(\n '/generate',\n {\n model,\n prompt,\n stream: false,\n keep_alive: this.options.keepAlive,\n options: this.buildRuntimeOptions(options),\n },\n );\n\n const usage = mapUsage(response.prompt_eval_count, response.eval_count);\n\n emitUsage(\n this.options,\n 'ollama',\n 'complete',\n response.model || model,\n usage,\n startTime,\n options.usageTags,\n );\n\n return {\n content: response.response || '',\n model: response.model || model,\n usage,\n finishReason: mapFinishReason(response.done_reason),\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async message(text: string, options: MessageOptions = {}): Promise<string> {\n const messages: AIMessage[] = [\n ...(options.history || []),\n { role: options.role || 'user', content: text },\n ];\n\n const response = await this.chat(messages, {\n model: options.model,\n maxTokens: options.maxTokens,\n temperature: options.temperature,\n topP: options.topP,\n stop: options.stop,\n stream: options.stream,\n frequencyPenalty: options.frequencyPenalty,\n presencePenalty: options.presencePenalty,\n responseFormat: options.responseFormat,\n seed: options.seed,\n tools: options.tools,\n toolChoice: options.toolChoice,\n onProgress: options.onProgress,\n usageTags: options.usageTags,\n });\n\n return response.content;\n }\n\n async embed(\n text: string | string[],\n options: EmbeddingOptions = {},\n ): Promise<EmbeddingResponse> {\n const startTime = Date.now();\n try {\n const model = await this.resolveModel('embedding', options.model);\n const input = Array.isArray(text) ? text : [text];\n const response = await this.requestJson<OllamaEmbedResponse>('/embed', {\n model,\n input,\n keep_alive: this.options.keepAlive,\n });\n\n const embeddings =\n response.embeddings ||\n (response.embedding ? [response.embedding] : undefined);\n\n if (!embeddings || embeddings.length === 0) {\n throw new AIError(\n 'Invalid embedding response from Ollama',\n 'INVALID_RESPONSE',\n 'ollama',\n );\n }\n\n const usage = mapUsage(response.prompt_eval_count, 0);\n emitUsage(\n this.options,\n 'ollama',\n 'embed',\n response.model || model,\n usage,\n startTime,\n options.usageTags,\n );\n\n return {\n embeddings,\n usage,\n model: response.model || model,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async embedImage(\n image: string | Buffer,\n options: ImageEmbeddingOptions = {},\n ): Promise<EmbeddingResponse> {\n const description = await this.describeImage(\n image,\n 'Describe this image in detail for semantic embedding. Include objects, people, text, setting, colors, composition, and notable visual relationships.',\n );\n\n return this.embed(description, {\n model: options.model,\n dimensions: options.dimensions,\n user: options.user,\n });\n }\n\n async describeImage(\n image: string | Buffer,\n prompt?: string,\n options: ImageDescriptionOptions = {},\n ): Promise<string> {\n const defaultPrompt =\n 'Describe this image for a search index. Include objects, mood, lighting, and any visible text.';\n\n const imageUrl = await this.imageToDataUrl(image);\n const response = await this.chat(\n [\n {\n role: 'user',\n content: [\n {\n type: 'text',\n text: prompt || defaultPrompt,\n },\n {\n type: 'image_url',\n image_url: {\n url: imageUrl,\n detail: options.detail || 'auto',\n },\n },\n ],\n },\n ],\n {\n model: options.model,\n maxTokens: options.maxTokens || 500,\n thinkingLevel: false,\n },\n );\n\n return response.content;\n }\n\n async generateImage(\n prompt: string,\n options: ImageGenerationOptions = {},\n ): Promise<ImageGenerationResponse> {\n try {\n if (options.imageInput) {\n throw new AIError(\n 'Ollama image generation does not support imageInput in this adapter yet.',\n 'NOT_IMPLEMENTED',\n 'ollama',\n );\n }\n\n if (options.outputFormat === 'url') {\n throw new AIError(\n 'Ollama image generation only supports buffer or base64 outputs in this adapter.',\n 'NOT_SUPPORTED',\n 'ollama',\n );\n }\n\n const model = await this.resolveModel('image_generation', options.model);\n const response = await this.requestJson<OllamaImageGenerationResponse>(\n '/images/generations',\n {\n model,\n prompt,\n n: options.n || 1,\n size: options.size || '1024x1024',\n response_format: 'b64_json',\n quality: options.quality,\n style: options.style,\n },\n { compatibility: true },\n );\n\n const images = (response.data || []).map((item) => {\n const b64 = item.b64_json || '';\n return {\n data:\n options.outputFormat === 'base64'\n ? b64\n : Buffer.from(b64, 'base64'),\n mimeType: 'image/png',\n revisedPrompt: item.revised_prompt,\n };\n });\n\n return {\n images,\n model,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async *stream(\n messages: AIMessage[],\n options: ChatOptions = {},\n ): AsyncIterable<string> {\n const startTime = Date.now();\n try {\n const model = await this.resolveModel(\n this.isVisionRequest(messages) ? 'vision' : 'chat',\n options.model,\n );\n\n const response = await this.requestStream('/chat', {\n model,\n messages: await this.mapMessagesToOllama(messages),\n stream: true,\n format:\n options.responseFormat?.type === 'json_object' ? 'json' : undefined,\n tools: this.mapTools(options.tools, options.toolChoice),\n think: this.mapThink(options),\n keep_alive: this.options.keepAlive,\n options: this.buildRuntimeOptions(options),\n });\n\n let finalUsage: TokenUsage | undefined;\n let finalModel = model;\n\n for await (const chunk of this.parseNdjson<OllamaChatResponse>(\n response,\n )) {\n if (chunk.model) {\n finalModel = chunk.model;\n }\n\n if (\n typeof chunk.message?.content === 'string' &&\n chunk.message.content\n ) {\n if (options.onProgress) {\n options.onProgress(chunk.message.content);\n }\n yield chunk.message.content;\n }\n\n if (chunk.done) {\n finalUsage = mapUsage(chunk.prompt_eval_count, chunk.eval_count);\n }\n }\n\n emitUsage(\n this.options,\n 'ollama',\n 'stream',\n finalModel,\n finalUsage,\n startTime,\n options.usageTags,\n );\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n async countTokens(text: string): Promise<number> {\n return Math.ceil(text.length / 4);\n }\n\n async getModels(): Promise<AIModel[]> {\n if (this.modelListPromise) {\n return this.modelListPromise;\n }\n\n this.modelListPromise = (async () => {\n const response = await this.requestJson<OllamaTagsResponse>('/tags');\n const summaries = response.models || [];\n\n return Promise.all(\n summaries.map(async (summary) => {\n const modelId = summary.name || summary.model;\n if (!modelId) {\n throw new AIError(\n 'Ollama returned a model without an identifier',\n 'INVALID_RESPONSE',\n 'ollama',\n );\n }\n\n const show = await this.showModel(modelId);\n const capabilities = parseCapabilities(modelId, show);\n const vision = capabilities.includes('vision');\n const functions = capabilities.includes('functions');\n const parameterSize =\n show?.details?.parameter_size || summary.details?.parameter_size;\n const family = show?.details?.family || summary.details?.family;\n\n return {\n id: modelId,\n name: modelId,\n description:\n parameterSize || family\n ? `${family || 'Ollama'} ${parameterSize || ''}`.trim()\n : `Ollama model: ${modelId}`,\n contextLength: parseContextLength(modelId, show),\n capabilities,\n supportsFunctions: functions,\n supportsVision: vision,\n } satisfies AIModel;\n }),\n );\n })().catch((error) => {\n this.modelListPromise = undefined;\n throw this.mapError(error);\n });\n\n return this.modelListPromise;\n }\n\n async getCapabilities(): Promise<AICapabilities> {\n return { ...OLLAMA_CAPABILITIES };\n }\n\n async synthesizeSpeech(\n _text: string,\n _options?: TTSOptions,\n ): Promise<TTSResponse> {\n throw new AIError(\n 'TTS is not supported by the Ollama provider.',\n 'NOT_IMPLEMENTED',\n 'ollama',\n );\n }\n\n streamSpeech(_text: string, _options?: TTSOptions): AsyncIterable<Buffer> {\n const error = new AIError(\n 'TTS streaming is not supported by the Ollama provider.',\n 'NOT_IMPLEMENTED',\n 'ollama',\n );\n return {\n [Symbol.asyncIterator]: () => ({\n next: () => Promise.reject(error),\n }),\n };\n }\n\n async cloneVoice(_options: VoiceCloneOptions): Promise<Voice> {\n throw new AIError(\n 'Voice cloning is not supported by the Ollama provider.',\n 'NOT_IMPLEMENTED',\n 'ollama',\n );\n }\n\n async designVoice(_options: VoiceDesignOptions): Promise<Voice> {\n throw new AIError(\n 'Voice design is not supported by the Ollama provider.',\n 'NOT_IMPLEMENTED',\n 'ollama',\n );\n }\n\n async getVoices(_options?: VoiceListOptions): Promise<Voice[]> {\n throw new AIError(\n 'Voice listing is not supported by the Ollama provider.',\n 'NOT_IMPLEMENTED',\n 'ollama',\n );\n }\n}\n"],"names":["line"],"mappings":";;;AA6CA,MAAM,sBAAsB;AAE5B,MAAM,sBAAsC;AAAA,EAC1C,MAAM;AAAA,EACN,YAAY;AAAA,EACZ,YAAY;AAAA,EACZ,WAAW;AAAA,EACX,WAAW;AAAA,EACX,QAAQ;AAAA,EACR,YAAY;AAAA,EACZ,iBAAiB;AAAA,EACjB,iBAAiB;AAAA,EACjB,KAAK;AAAA,EACL,cAAc;AAAA,EACd,aAAa;AAAA,EACb,kBAAkB;AAAA,EAClB,qBAAqB;AAAA,IACnB;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EAAA;AAEJ;AA6FA,SAAS,mBAAmB,OAAuB;AACjD,SAAO,MAAM,QAAQ,QAAQ,EAAE;AACjC;AAEA,SAAS,cAAc,SAA0B;AAC/C,QAAM,UAAU,SAAS,KAAA,KAAU;AACnC,QAAM,aAAa,2BAA2B,KAAK,OAAO,IACtD,UACA,UAAU,OAAO;AACrB,QAAM,OAAO,mBAAmB,UAAU;AAC1C,MAAI,KAAK,SAAS,MAAM,UAAU,KAAK,MAAM,GAAG,EAAE;AAClD,MAAI,KAAK,SAAS,KAAK,UAAU,KAAK,MAAM,GAAG,EAAE;AACjD,SAAO;AACT;AAEA,SAAS,iBAAiB,SAA0B;AAClD,SAAO,2DAA2D;AAAA,IAChE;AAAA,EAAA;AAEJ;AAEA,SAAS,uBAAuB,SAA0B;AACxD,SAAO,qGAAqG;AAAA,IAC1G;AAAA,EAAA;AAEJ;AAEA,SAAS,mBACP,SACA,cACS;AACT,MAAI,aAAa,IAAI,QAAQ,EAAG,QAAO;AACvC,SAAO,+DAA+D;AAAA,IACpE;AAAA,EAAA;AAEJ;AAEA,SAAS,qBACP,SACA,cACS;AACT,MACE,aAAa,IAAI,OAAO,KACxB,aAAa,IAAI,cAAc,KAC/B,aAAa,IAAI,kBAAkB,GACnC;AACA,WAAO;AAAA,EACT;AAEA,MAAI,iBAAiB,OAAO,KAAK,uBAAuB,OAAO,GAAG;AAChE,WAAO;AAAA,EACT;AAEA,SAAO,uDAAuD,KAAK,OAAO;AAC5E;AAEA,SAAS,kBACP,SACA,MACU;AACV,QAAM,eAAe,IAAI;AAAA,KACtB,MAAM,gBAAgB,CAAA,GAAI,IAAI,CAAC,eAAe,WAAW,YAAA,CAAa;AAAA,EAAA;AAGzE,MAAI,uBAAuB,OAAO,GAAG;AACnC,WAAO,CAAC,kBAAkB;AAAA,EAC5B;AAEA,MACE,aAAa,IAAI,WAAW,KAC5B,aAAa,IAAI,YAAY,KAC7B,iBAAiB,OAAO,GACxB;AACA,WAAO,CAAC,YAAY;AAAA,EACtB;AAEA,QAAM,YAAY,oBAAI,IAAY,CAAC,QAAQ,MAAM,CAAC;AAElD,MAAI,mBAAmB,SAAS,YAAY,GAAG;AAC7C,cAAU,IAAI,QAAQ;AAAA,EACxB;AAEA,MAAI,qBAAqB,SAAS,YAAY,GAAG;AAC/C,cAAU,IAAI,WAAW;AAAA,EAC3B;AAEA,SAAO,CAAC,GAAG,SAAS;AACtB;AAEA,SAAS,mBACP,SACA,MACQ;AACR,QAAM,YAAY,MAAM,cAAc,CAAA;AAEtC,aAAW,CAAC,KAAK,KAAK,KAAK,OAAO,QAAQ,SAAS,GAAG;AACpD,QAAI,IAAI,SAAS,iBAAiB,KAAK,OAAO,UAAU,UAAU;AAChE,aAAO;AAAA,IACT;AAAA,EACF;AAEA,QAAM,cAAc,MAAM,YAAY,MAAM,mBAAmB;AAC/D,MAAI,cAAc,CAAC,GAAG;AACpB,WAAO,OAAO,YAAY,CAAC,CAAC;AAAA,EAC9B;AAEA,MAAI,iBAAiB,OAAO,EAAG,QAAO;AACtC,MAAI,+BAA+B,KAAK,OAAO,EAAG,QAAO;AACzD,SAAO;AACT;AAEA,SAAS,SACP,cACA,kBACwB;AACxB,MACE,OAAO,iBAAiB,YACxB,OAAO,qBAAqB,UAC5B;AACA,WAAO;AAAA,EACT;AAEA,QAAM,SAAS,gBAAgB;AAC/B,QAAM,aAAa,oBAAoB;AACvC,SAAO;AAAA,IACL,cAAc;AAAA,IACd,kBAAkB;AAAA,IAClB,aAAa,SAAS;AAAA,EAAA;AAE1B;AAEA,SAAS,gBAAgB,QAA6C;AACpE,UAAQ,QAAA;AAAA,IACN,KAAK;AACH,aAAO;AAAA,IACT,KAAK;AACH,aAAO;AAAA,IACT,KAAK;AACH,aAAO;AAAA,IACT;AACE,aAAO;AAAA,EAAA;AAEb;AAEA,SAAS,wBACP,OACA,YACQ;AACR,QAAM,KAAK,MAAM,GAAG,YAAA;AACpB,MAAI,QAAQ;AAEZ,MAAI,GAAG,SAAS,SAAS,EAAG,UAAS;AACrC,MAAI,GAAG,SAAS,UAAU,KAAK,GAAG,SAAS,KAAK,EAAG,UAAS;AAC5D,MAAI,GAAG,WAAW,QAAQ,EAAG,UAAS;AACtC,MAAI,wCAAwC,KAAK,EAAE,EAAG,UAAS;AAE/D,UAAQ,YAAA;AAAA,IACN,KAAK;AACH,UAAI,MAAM,eAAgB,UAAS;AACnC,UAAI,gBAAgB,KAAK,EAAE,EAAG,UAAS;AACvC,UAAI,kCAAkC,KAAK,EAAE,EAAG,UAAS;AACzD,UAAI,MAAM,KAAK,EAAE,EAAG,UAAS;AAC7B;AAAA,IACF,KAAK;AACH,UAAI,MAAM,aAAa,SAAS,YAAY,EAAG,UAAS;AACxD,UAAI,oBAAoB,KAAK,EAAE,EAAG,UAAS;AAC3C;AAAA,IACF,KAAK;AACH,UAAI,MAAM,aAAa,SAAS,kBAAkB,EAAG,UAAS;AAC9D,UAAI,mBAAmB,KAAK,EAAE,EAAG,UAAS;AAC1C;AAAA,IACF,KAAK;AAAA,IACL;AACE,UAAI,MAAM,aAAa,SAAS,MAAM,EAAG,UAAS;AAClD,UAAI,MAAM,kBAAmB,UAAS;AACtC,UAAI,wDAAwD,KAAK,EAAE,GAAG;AACpE,iBAAS;AAAA,MACX;AACA,UAAI,UAAU,KAAK,EAAE,EAAG,UAAS;AACjC;AAAA,EAAA;AAGJ,SAAO;AACT;AAEO,MAAM,eAAsC;AAAA,EAChC;AAAA,EACA;AAAA,EACA;AAAA,EACT;AAAA,EACS,qCAAqB,IAAA;AAAA,EAIrB,yCAAyB,IAAA;AAAA,EAK1C,YAAY,SAAwB;AAClC,SAAK,OAAO,cAAc,QAAQ,OAAO;AACzC,SAAK,UAAU;AAAA,MACb,GAAG;AAAA,MACH,SAAS,KAAK;AAAA,IAAA;AAEhB,SAAK,yBAAyB,QAAQ;AAAA,EACxC;AAAA,EAEA,IAAY,gBAAwB;AAClC,WAAO,GAAG,KAAK,IAAI;AAAA,EACrB;AAAA,EAEA,IAAY,uBAA+B;AACzC,WAAO,GAAG,KAAK,IAAI;AAAA,EACrB;AAAA,EAEQ,aAAa,SAAS,OAAgB;AAC5C,UAAM,UAAU,IAAI,QAAQ,KAAK,QAAQ,OAAO;AAChD,YAAQ,IAAI,gBAAgB,kBAAkB;AAC9C,YAAQ;AAAA,MACN;AAAA,MACA,SAAS,2CAA2C;AAAA,IAAA;AAEtD,QAAI,KAAK,QAAQ,QAAQ;AACvB,cAAQ,IAAI,iBAAiB,UAAU,KAAK,QAAQ,MAAM,EAAE;AAAA,IAC9D;AACA,WAAO;AAAA,EACT;AAAA,EAEA,MAAc,iBACZ,KACA,MACmB;AACnB,UAAM,aAAa,IAAI,gBAAA;AACvB,UAAM,UACJ,OAAO,KAAK,QAAQ,YAAY,WAAW,KAAK,QAAQ,UAAU;AACpE,UAAM,QAAQ,UACV,WAAW,MAAM,WAAW,MAAA,GAAS,OAAO,IAC5C;AAEJ,QAAI;AACF,aAAO,MAAM,MAAM,KAAK;AAAA,QACtB,GAAG;AAAA,QACH,QAAQ,WAAW;AAAA,MAAA,CACpB;AAAA,IACH,UAAA;AACE,UAAI,oBAAoB,KAAK;AAAA,IAC/B;AAAA,EACF;AAAA,EAEA,MAAc,eAAe,UAAsC;AACjE,UAAM,OAAO,MAAM,SAAS,KAAA;AAC5B,UAAM,UACJ,QAAQ,KAAK,KAAA,EAAO,SAAS,IACzB,KAAK,KAAA,IACL,qCAAqC,SAAS,MAAM;AAE1D,YAAQ,SAAS,QAAA;AAAA,MACf,KAAK;AAAA,MACL,KAAK;AACH,eAAO,IAAI,oBAAoB,QAAQ;AAAA,MACzC,KAAK;AACH,eAAO,IAAI,mBAAmB,SAAS,QAAQ;AAAA,MACjD,KAAK;AACH,eAAO,IAAI,mBAAmB,QAAQ;AAAA,MACxC,KAAK;AACH,eAAO,IAAI,eAAe,QAAQ;AAAA,MACpC;AACE,YAAI,uBAAuB,KAAK,OAAO,GAAG;AACxC,iBAAO,IAAI,mBAAmB,QAAQ;AAAA,QACxC;AACA,YAAI,oCAAoC,KAAK,OAAO,GAAG;AACrD,iBAAO,IAAI,mBAAmB,QAAQ;AAAA,QACxC;AACA,eAAO,IAAI,QAAQ,SAAS,aAAa,QAAQ;AAAA,IAAA;AAAA,EAEvD;AAAA,EAEQ,SAAS,OAAyB;AACxC,QAAI,iBAAiB,SAAS;AAC5B,aAAO;AAAA,IACT;AAEA,QAAI,iBAAiB,SAAS,MAAM,SAAS,cAAc;AACzD,aAAO,IAAI,QAAQ,4BAA4B,WAAW,QAAQ;AAAA,IACpE;AAEA,UAAM,UACJ,iBAAiB,QAAQ,MAAM,UAAU;AAC3C,WAAO,IAAI,QAAQ,SAAS,iBAAiB,QAAQ;AAAA,EACvD;AAAA,EAEA,MAAc,YACZ,MACA,MACA,UAAuC,CAAA,GAC3B;AACZ,UAAM,UAAU,QAAQ,gBACpB,KAAK,uBACL,KAAK;AACT,UAAM,WAAW,MAAM,KAAK,iBAAiB,GAAG,OAAO,GAAG,IAAI,IAAI;AAAA,MAChE,QAAQ,OAAO,SAAS;AAAA,MACxB,SAAS,KAAK,aAAA;AAAA,MACd,MAAM,OAAO,KAAK,UAAU,IAAI,IAAI;AAAA,IAAA,CACrC;AAED,QAAI,CAAC,SAAS,IAAI;AAChB,YAAM,MAAM,KAAK,eAAe,QAAQ;AAAA,IAC1C;AAEA,WAAQ,MAAM,SAAS,KAAA;AAAA,EACzB;AAAA,EAEA,MAAc,cACZ,MACA,MACmB;AACnB,UAAM,WAAW,MAAM,KAAK;AAAA,MAC1B,GAAG,KAAK,aAAa,GAAG,IAAI;AAAA,MAC5B;AAAA,QACE,QAAQ;AAAA,QACR,SAAS,KAAK,aAAa,IAAI;AAAA,QAC/B,MAAM,KAAK,UAAU,IAAI;AAAA,MAAA;AAAA,IAC3B;AAGF,QAAI,CAAC,SAAS,IAAI;AAChB,YAAM,MAAM,KAAK,eAAe,QAAQ;AAAA,IAC1C;AAEA,WAAO;AAAA,EACT;AAAA,EAEA,OAAe,YAAe,UAAsC;AAClE,UAAM,SAAS,SAAS,MAAM,UAAA;AAC9B,QAAI,CAAC,QAAQ;AACX;AAAA,IACF;AAEA,UAAM,UAAU,IAAI,YAAA;AACpB,QAAI,SAAS;AAEb,WAAO,MAAM;AACX,YAAM,EAAE,OAAO,KAAA,IAAS,MAAM,OAAO,KAAA;AACrC,UAAI,KAAM;AAEV,gBAAU,QAAQ,OAAO,OAAO,EAAE,QAAQ,MAAM;AAEhD,UAAI,eAAe,OAAO,QAAQ,IAAI;AACtC,aAAO,iBAAiB,IAAI;AAC1B,cAAMA,QAAO,OAAO,MAAM,GAAG,YAAY,EAAE,KAAA;AAC3C,iBAAS,OAAO,MAAM,eAAe,CAAC;AACtC,YAAIA,OAAM;AACR,gBAAM,KAAK,MAAMA,KAAI;AAAA,QACvB;AACA,uBAAe,OAAO,QAAQ,IAAI;AAAA,MACpC;AAAA,IACF;AAEA,cAAU,QAAQ,OAAA;AAClB,UAAM,OAAO,OAAO,KAAA;AACpB,QAAI,MAAM;AACR,YAAM,KAAK,MAAM,IAAI;AAAA,IACvB;AAAA,EACF;AAAA,EAEA,MAAc,UAAU,OAAmD;AACzE,UAAM,SAAS,KAAK,eAAe,IAAI,KAAK;AAC5C,QAAI,QAAQ;AACV,aAAO;AAAA,IACT;AAEA,UAAM,UAAU,KAAK,YAAgC,SAAS;AAAA,MAC5D;AAAA,MACA,SAAS;AAAA,IAAA,CACV,EAAE,MAAM,CAAC,WAAW,IAAI;AAEzB,SAAK,eAAe,IAAI,OAAO,OAAO;AACtC,WAAO;AAAA,EACT;AAAA,EAEA,MAAc,aACZ,YACA,eACiB;AACjB,QAAI,eAAe;AACjB,aAAO;AAAA,IACT;AAEA,QACE,KAAK,2BACJ,eAAe,UAAU,eAAe,WACzC;AACA,aAAO,KAAK;AAAA,IACd;AAEA,UAAM,SAAS,KAAK,mBAAmB,IAAI,UAAU;AACrD,QAAI,QAAQ;AACV,aAAO;AAAA,IACT;AAEA,UAAM,UAAU,KAAK,YAAY,UAAU,EAAE,MAAM,CAAC,UAAU;AAC5D,WAAK,mBAAmB,OAAO,UAAU;AACzC,YAAM;AAAA,IACR,CAAC;AACD,SAAK,mBAAmB,IAAI,YAAY,OAAO;AAC/C,WAAO;AAAA,EACT;AAAA,EAEA,MAAc,YACZ,YACiB;AACjB,UAAM,SAAS,MAAM,KAAK,UAAA;AAC1B,UAAM,aAAa,OAAO,OAAO,CAAC,cAAc;AAC9C,cAAQ,YAAA;AAAA,QACN,KAAK;AACH,iBACE,UAAU,aAAa,SAAS,QAAQ,KACxC,UAAU,mBAAmB;AAAA,QAEjC,KAAK;AACH,iBAAO,UAAU,aAAa,SAAS,YAAY;AAAA,QACrD,KAAK;AACH,iBAAO,UAAU,aAAa,SAAS,kBAAkB;AAAA,QAC3D,KAAK;AAAA,QACL;AACE,iBAAO,UAAU,aAAa,SAAS,MAAM;AAAA,MAAA;AAAA,IAEnD,CAAC;AAED,UAAM,QAAQ,WAAW;AAAA,MACvB,CAAC,MAAM,UACL,wBAAwB,OAAO,UAAU,IACzC,wBAAwB,MAAM,UAAU;AAAA,IAAA,EAC1C,CAAC;AAEH,QAAI,CAAC,OAAO;AACV,YAAM,IAAI;AAAA,QACR,MAAM,UAAU;AAAA,QAChB;AAAA,UACE,UAAU;AAAA,UACV;AAAA,UACA,MAAM;AAAA,QAAA;AAAA,MACR;AAAA,IAEJ;AAEA,WAAO,MAAM;AAAA,EACf;AAAA,EAEQ,gBAAgB,UAAgC;AACtD,WAAO,SAAS;AAAA,MACd,CAAC,YACC,MAAM,QAAQ,QAAQ,OAAO,KAC7B,QAAQ,QAAQ,KAAK,CAAC,SAAS,KAAK,SAAS,WAAW;AAAA,IAAA;AAAA,EAE9D;AAAA,EAEA,MAAc,qBAAqB,OAAyC;AAC1E,QAAI,OAAO,SAAS,KAAK,GAAG;AAC1B,aAAO,MAAM,SAAS,QAAQ;AAAA,IAChC;AAEA,QAAI,MAAM,WAAW,OAAO,GAAG;AAC7B,YAAM,aAAa,MAAM,QAAQ,GAAG;AACpC,aAAO,eAAe,KAAK,QAAQ,MAAM,MAAM,aAAa,CAAC;AAAA,IAC/D;AAEA,UAAM,WAAW,MAAM,MAAM,KAAK;AAClC,QAAI,CAAC,SAAS,IAAI;AAChB,YAAM,IAAI;AAAA,QACR,0BAA0B,SAAS,MAAM,IAAI,SAAS,UAAU;AAAA,QAChE;AAAA,QACA;AAAA,MAAA;AAAA,IAEJ;AAEA,UAAM,cAAc,MAAM,SAAS,YAAA;AACnC,WAAO,OAAO,KAAK,WAAW,EAAE,SAAS,QAAQ;AAAA,EACnD;AAAA,EAEA,MAAc,eAAe,OAAyC;AACpE,QAAI,OAAO,SAAS,KAAK,GAAG;AAC1B,aAAO,yBAAyB,MAAM,SAAS,QAAQ,CAAC;AAAA,IAC1D;AAEA,QAAI,MAAM,WAAW,OAAO,GAAG;AAC7B,aAAO;AAAA,IACT;AAEA,UAAM,WAAW,MAAM,MAAM,KAAK;AAClC,QAAI,CAAC,SAAS,IAAI;AAChB,YAAM,IAAI;AAAA,QACR,0BAA0B,SAAS,MAAM,IAAI,SAAS,UAAU;AAAA,QAChE;AAAA,QACA;AAAA,MAAA;AAAA,IAEJ;AAEA,UAAM,cAAc,SAAS,QAAQ,IAAI,cAAc,KAAK;AAC5D,UAAM,cAAc,MAAM,SAAS,YAAA;AACnC,WAAO,QAAQ,WAAW,WAAW,OAAO,KAAK,WAAW,EAAE,SAAS,QAAQ,CAAC;AAAA,EAClF;AAAA,EAEQ,mBAAmB,eAAiD;AAC1E,QAAI,CAAC,eAAe;AAClB,aAAO,CAAA;AAAA,IACT;AAEA,QAAI;AACF,YAAM,SAAS,KAAK,MAAM,aAAa;AACvC,aAAO,UAAU,OAAO,WAAW,WAAW,SAAS,CAAA;AAAA,IACzD,QAAQ;AACN,aAAO,CAAA;AAAA,IACT;AAAA,EACF;AAAA,EAEA,MAAc,oBACZ,UAC0B;AAC1B,UAAM,iBAAiB,MAAM,QAAQ;AAAA,MACnC,SAAS,IAAI,OAAO,YAAY;AAC9B,cAAM,UAAU,mBAAmB,QAAQ,OAAO;AAClD,cAAM,SAAwB;AAAA,UAC5B,MACE,QAAQ,SAAS,aACb,SACC,QAAQ;AAAA,UACf;AAAA,QAAA;AAGF,YAAI,MAAM,QAAQ,QAAQ,OAAO,GAAG;AAClC,gBAAM,aAAa,QAAQ,QAAQ;AAAA,YACjC,CAAC,SAAS,KAAK,SAAS;AAAA,UAAA;AAE1B,cAAI,WAAW,SAAS,GAAG;AACzB,mBAAO,SAAS,MAAM,QAAQ;AAAA,cAC5B,WAAW;AAAA,gBAAI,CAAC,SACd,KAAK,qBAAqB,KAAK,UAAU,GAAG;AAAA,cAAA;AAAA,YAC9C;AAAA,UAEJ;AAAA,QACF;AAEA,YACE,OAAO,SAAS,eAChB,MAAM,QAAQ,QAAQ,UAAU,KAChC,QAAQ,WAAW,SAAS,GAC5B;AACA,iBAAO,aAAa,QAAQ,WAAW,IAAI,CAAC,UAAU,WAAW;AAAA,YAC/D,MAAM;AAAA,YACN,UAAU;AAAA,cACR;AAAA,cACA,MAAM,SAAS,SAAS;AAAA,cACxB,WAAW,KAAK,mBAAmB,SAAS,SAAS,SAAS;AAAA,YAAA;AAAA,UAChE,EACA;AAAA,QACJ;AAEA,YAAI,OAAO,SAAS,UAAU,QAAQ,MAAM;AAC1C,iBAAO,YAAY,QAAQ;AAAA,QAC7B;AAEA,eAAO;AAAA,MACT,CAAC;AAAA,IAAA;AAGH,WAAO;AAAA,EACT;AAAA,EAEQ,SACN,OACA,YAC4C;AAC5C,QAAI,CAAC,SAAS,MAAM,WAAW,KAAK,eAAe,QAAQ;AACzD,aAAO;AAAA,IACT;AAEA,UAAM,cACJ,cAAc,OAAO,eAAe,WAChC,MAAM;AAAA,MACJ,CAAC,SAAS,KAAK,SAAS,SAAS,WAAW,SAAS;AAAA,IAAA,IAEvD;AAEN,QAAI,YAAY,WAAW,GAAG;AAC5B,aAAO;AAAA,IACT;AAEA,WAAO,YAAY,IAAI,CAAC,UAAU;AAAA,MAChC,MAAM;AAAA,MACN,UAAU;AAAA,QACR,MAAM,KAAK,SAAS;AAAA,QACpB,aAAa,KAAK,SAAS;AAAA,QAC3B,YAAY,KAAK,SAAS,cAAc,EAAE,MAAM,SAAA;AAAA,MAAS;AAAA,IAC3D,EACA;AAAA,EACJ;AAAA,EAEQ,oBAAoB,SAMY;AACtC,UAAM,iBAA0C,CAAA;AAEhD,QAAI,OAAO,QAAQ,cAAc,UAAU;AACzC,qBAAe,cAAc,QAAQ;AAAA,IACvC;AACA,QAAI,OAAO,QAAQ,gBAAgB,UAAU;AAC3C,qBAAe,cAAc,QAAQ;AAAA,IACvC;AACA,QAAI,OAAO,QAAQ,SAAS,UAAU;AACpC,qBAAe,QAAQ,QAAQ;AAAA,IACjC;AACA,QAAI,QAAQ,MAAM;AAChB,qBAAe,OAAO,MAAM,QAAQ,QAAQ,IAAI,IAC5C,QAAQ,OACR,CAAC,QAAQ,IAAI;AAAA,IACnB;AACA,QAAI,OAAO,QAAQ,SAAS,UAAU;AACpC,qBAAe,OAAO,QAAQ;AAAA,IAChC;AAEA,WAAO,OAAO,KAAK,cAAc,EAAE,SAAS,IAAI,iBAAiB;AAAA,EACnE;AAAA,EAEQ,SACN,SAC8B;AAC9B,QAAI,CAAC,OAAO,OAAO,SAAS,eAAe,GAAG;AAC5C,aAAO;AAAA,IACT;AAEA,WAAO,QAAQ;AAAA,EACjB;AAAA,EAEA,MAAM,KACJ,UACA,UAAuB,IACF;AACrB,UAAM,YAAY,KAAK,IAAA;AACvB,QAAI;AACF,YAAM,QAAQ,MAAM,KAAK;AAAA,QACvB,KAAK,gBAAgB,QAAQ,IAAI,WAAW;AAAA,QAC5C,QAAQ;AAAA,MAAA;AAGV,YAAM,WAAW,MAAM,KAAK,YAAgC,SAAS;AAAA,QACnE;AAAA,QACA,UAAU,MAAM,KAAK,oBAAoB,QAAQ;AAAA,QACjD,QAAQ;AAAA,QACR,QACE,QAAQ,gBAAgB,SAAS,gBAAgB,SAAS;AAAA,QAC5D,OAAO,KAAK,SAAS,QAAQ,OAAO,QAAQ,UAAU;AAAA,QACtD,OAAO,KAAK,SAAS,OAAO;AAAA,QAC5B,YAAY,KAAK,QAAQ;AAAA,QACzB,SAAS,KAAK,oBAAoB,OAAO;AAAA,MAAA,CAC1C;AAED,YAAM,QAAQ,SAAS,SAAS,mBAAmB,SAAS,UAAU;AAEtE;AAAA,QACE,KAAK;AAAA,QACL;AAAA,QACA;AAAA,QACA,SAAS,SAAS;AAAA,QAClB;AAAA,QACA;AAAA,QACA,QAAQ;AAAA,MAAA;AAGV,YAAM,YACJ,SAAS,SAAS,YACd,OAAO,CAAC,SAAS,KAAK,UAAU,IAAI,EACrC,IAAI,CAAC,MAAM,WAAW;AAAA,QACrB,IAAI,GAAG,SAAS,SAAS,KAAK,SAAS,QAAQ,CAAC;AAAA,QAChD,MAAM;AAAA,QACN,UAAU;AAAA,UACR,MAAM,KAAK,UAAU,QAAQ;AAAA,UAC7B,WAAW,KAAK,UAAU,KAAK,UAAU,aAAa,CAAA,CAAE;AAAA,QAAA;AAAA,MAC1D,EACA,KAAK;AAEX,aAAO;AAAA,QACL,SAAS,SAAS,SAAS,WAAW;AAAA,QACtC,OAAO,SAAS,SAAS;AAAA,QACzB;AAAA,QACA,cACE,aAAa,UAAU,SAAS,IAC5B,eACA,gBAAgB,SAAS,WAAW;AAAA,QAC1C,WAAW,aAAa,UAAU,SAAS,IAAI,YAAY;AAAA,MAAA;AAAA,IAE/D,SAAS,OAAO;AACd,YAAM,KAAK,SAAS,KAAK;AAAA,IAC3B;AAAA,EACF;AAAA,EAEA,MAAM,SACJ,QACA,UAA6B,IACR;AACrB,UAAM,YAAY,KAAK,IAAA;AACvB,QAAI;AACF,YAAM,QAAQ,MAAM,KAAK,aAAa,QAAQ,QAAQ,KAAK;AAC3D,YAAM,WAAW,MAAM,KAAK;AAAA,QAC1B;AAAA,QACA;AAAA,UACE;AAAA,UACA;AAAA,UACA,QAAQ;AAAA,UACR,YAAY,KAAK,QAAQ;AAAA,UACzB,SAAS,KAAK,oBAAoB,OAAO;AAAA,QAAA;AAAA,MAC3C;AAGF,YAAM,QAAQ,SAAS,SAAS,mBAAmB,SAAS,UAAU;AAEtE;AAAA,QACE,KAAK;AAAA,QACL;AAAA,QACA;AAAA,QACA,SAAS,SAAS;AAAA,QAClB;AAAA,QACA;AAAA,QACA,QAAQ;AAAA,MAAA;AAGV,aAAO;AAAA,QACL,SAAS,SAAS,YAAY;AAAA,QAC9B,OAAO,SAAS,SAAS;AAAA,QACzB;AAAA,QACA,cAAc,gBAAgB,SAAS,WAAW;AAAA,MAAA;AAAA,IAEtD,SAAS,OAAO;AACd,YAAM,KAAK,SAAS,KAAK;AAAA,IAC3B;AAAA,EACF;AAAA,EAEA,MAAM,QAAQ,MAAc,UAA0B,IAAqB;AACzE,UAAM,WAAwB;AAAA,MAC5B,GAAI,QAAQ,WAAW,CAAA;AAAA,MACvB,EAAE,MAAM,QAAQ,QAAQ,QAAQ,SAAS,KAAA;AAAA,IAAK;AAGhD,UAAM,WAAW,MAAM,KAAK,KAAK,UAAU;AAAA,MACzC,OAAO,QAAQ;AAAA,MACf,WAAW,QAAQ;AAAA,MACnB,aAAa,QAAQ;AAAA,MACrB,MAAM,QAAQ;AAAA,MACd,MAAM,QAAQ;AAAA,MACd,QAAQ,QAAQ;AAAA,MAChB,kBAAkB,QAAQ;AAAA,MAC1B,iBAAiB,QAAQ;AAAA,MACzB,gBAAgB,QAAQ;AAAA,MACxB,MAAM,QAAQ;AAAA,MACd,OAAO,QAAQ;AAAA,MACf,YAAY,QAAQ;AAAA,MACpB,YAAY,QAAQ;AAAA,MACpB,WAAW,QAAQ;AAAA,IAAA,CACpB;AAED,WAAO,SAAS;AAAA,EAClB;AAAA,EAEA,MAAM,MACJ,MACA,UAA4B,IACA;AAC5B,UAAM,YAAY,KAAK,IAAA;AACvB,QAAI;AACF,YAAM,QAAQ,MAAM,KAAK,aAAa,aAAa,QAAQ,KAAK;AAChE,YAAM,QAAQ,MAAM,QAAQ,IAAI,IAAI,OAAO,CAAC,IAAI;AAChD,YAAM,WAAW,MAAM,KAAK,YAAiC,UAAU;AAAA,QACrE;AAAA,QACA;AAAA,QACA,YAAY,KAAK,QAAQ;AAAA,MAAA,CAC1B;AAED,YAAM,aACJ,SAAS,eACR,SAAS,YAAY,CAAC,SAAS,SAAS,IAAI;AAE/C,UAAI,CAAC,cAAc,WAAW,WAAW,GAAG;AAC1C,cAAM,IAAI;AAAA,UACR;AAAA,UACA;AAAA,UACA;AAAA,QAAA;AAAA,MAEJ;AAEA,YAAM,QAAQ,SAAS,SAAS,mBAAmB,CAAC;AACpD;AAAA,QACE,KAAK;AAAA,QACL;AAAA,QACA;AAAA,QACA,SAAS,SAAS;AAAA,QAClB;AAAA,QACA;AAAA,QACA,QAAQ;AAAA,MAAA;AAGV,aAAO;AAAA,QACL;AAAA,QACA;AAAA,QACA,OAAO,SAAS,SAAS;AAAA,MAAA;AAAA,IAE7B,SAAS,OAAO;AACd,YAAM,KAAK,SAAS,KAAK;AAAA,IAC3B;AAAA,EACF;AAAA,EAEA,MAAM,WACJ,OACA,UAAiC,IACL;AAC5B,UAAM,cAAc,MAAM,KAAK;AAAA,MAC7B;AAAA,MACA;AAAA,IAAA;AAGF,WAAO,KAAK,MAAM,aAAa;AAAA,MAC7B,OAAO,QAAQ;AAAA,MACf,YAAY,QAAQ;AAAA,MACpB,MAAM,QAAQ;AAAA,IAAA,CACf;AAAA,EACH;AAAA,EAEA,MAAM,cACJ,OACA,QACA,UAAmC,CAAA,GAClB;AACjB,UAAM,gBACJ;AAEF,UAAM,WAAW,MAAM,KAAK,eAAe,KAAK;AAChD,UAAM,WAAW,MAAM,KAAK;AAAA,MAC1B;AAAA,QACE;AAAA,UACE,MAAM;AAAA,UACN,SAAS;AAAA,YACP;AAAA,cACE,MAAM;AAAA,cACN,MAAM,UAAU;AAAA,YAAA;AAAA,YAElB;AAAA,cACE,MAAM;AAAA,cACN,WAAW;AAAA,gBACT,KAAK;AAAA,gBACL,QAAQ,QAAQ,UAAU;AAAA,cAAA;AAAA,YAC5B;AAAA,UACF;AAAA,QACF;AAAA,MACF;AAAA,MAEF;AAAA,QACE,OAAO,QAAQ;AAAA,QACf,WAAW,QAAQ,aAAa;AAAA,QAChC,eAAe;AAAA,MAAA;AAAA,IACjB;AAGF,WAAO,SAAS;AAAA,EAClB;AAAA,EAEA,MAAM,cACJ,QACA,UAAkC,IACA;AAClC,QAAI;AACF,UAAI,QAAQ,YAAY;AACtB,cAAM,IAAI;AAAA,UACR;AAAA,UACA;AAAA,UACA;AAAA,QAAA;AAAA,MAEJ;AAEA,UAAI,QAAQ,iBAAiB,OAAO;AAClC,cAAM,IAAI;AAAA,UACR;AAAA,UACA;AAAA,UACA;AAAA,QAAA;AAAA,MAEJ;AAEA,YAAM,QAAQ,MAAM,KAAK,aAAa,oBAAoB,QAAQ,KAAK;AACvE,YAAM,WAAW,MAAM,KAAK;AAAA,QAC1B;AAAA,QACA;AAAA,UACE;AAAA,UACA;AAAA,UACA,GAAG,QAAQ,KAAK;AAAA,UAChB,MAAM,QAAQ,QAAQ;AAAA,UACtB,iBAAiB;AAAA,UACjB,SAAS,QAAQ;AAAA,UACjB,OAAO,QAAQ;AAAA,QAAA;AAAA,QAEjB,EAAE,eAAe,KAAA;AAAA,MAAK;AAGxB,YAAM,UAAU,SAAS,QAAQ,CAAA,GAAI,IAAI,CAAC,SAAS;AACjD,cAAM,MAAM,KAAK,YAAY;AAC7B,eAAO;AAAA,UACL,MACE,QAAQ,iBAAiB,WACrB,MACA,OAAO,KAAK,KAAK,QAAQ;AAAA,UAC/B,UAAU;AAAA,UACV,eAAe,KAAK;AAAA,QAAA;AAAA,MAExB,CAAC;AAED,aAAO;AAAA,QACL;AAAA,QACA;AAAA,MAAA;AAAA,IAEJ,SAAS,OAAO;AACd,YAAM,KAAK,SAAS,KAAK;AAAA,IAC3B;AAAA,EACF;AAAA,EAEA,OAAO,OACL,UACA,UAAuB,IACA;AACvB,UAAM,YAAY,KAAK,IAAA;AACvB,QAAI;AACF,YAAM,QAAQ,MAAM,KAAK;AAAA,QACvB,KAAK,gBAAgB,QAAQ,IAAI,WAAW;AAAA,QAC5C,QAAQ;AAAA,MAAA;AAGV,YAAM,WAAW,MAAM,KAAK,cAAc,SAAS;AAAA,QACjD;AAAA,QACA,UAAU,MAAM,KAAK,oBAAoB,QAAQ;AAAA,QACjD,QAAQ;AAAA,QACR,QACE,QAAQ,gBAAgB,SAAS,gBAAgB,SAAS;AAAA,QAC5D,OAAO,KAAK,SAAS,QAAQ,OAAO,QAAQ,UAAU;AAAA,QACtD,OAAO,KAAK,SAAS,OAAO;AAAA,QAC5B,YAAY,KAAK,QAAQ;AAAA,QACzB,SAAS,KAAK,oBAAoB,OAAO;AAAA,MAAA,CAC1C;AAED,UAAI;AACJ,UAAI,aAAa;AAEjB,uBAAiB,SAAS,KAAK;AAAA,QAC7B;AAAA,MAAA,GACC;AACD,YAAI,MAAM,OAAO;AACf,uBAAa,MAAM;AAAA,QACrB;AAEA,YACE,OAAO,MAAM,SAAS,YAAY,YAClC,MAAM,QAAQ,SACd;AACA,cAAI,QAAQ,YAAY;AACtB,oBAAQ,WAAW,MAAM,QAAQ,OAAO;AAAA,UAC1C;AACA,gBAAM,MAAM,QAAQ;AAAA,QACtB;AAEA,YAAI,MAAM,MAAM;AACd,uBAAa,SAAS,MAAM,mBAAmB,MAAM,UAAU;AAAA,QACjE;AAAA,MACF;AAEA;AAAA,QACE,KAAK;AAAA,QACL;AAAA,QACA;AAAA,QACA;AAAA,QACA;AAAA,QACA;AAAA,QACA,QAAQ;AAAA,MAAA;AAAA,IAEZ,SAAS,OAAO;AACd,YAAM,KAAK,SAAS,KAAK;AAAA,IAC3B;AAAA,EACF;AAAA,EAEA,MAAM,YAAY,MAA+B;AAC/C,WAAO,KAAK,KAAK,KAAK,SAAS,CAAC;AAAA,EAClC;AAAA,EAEA,MAAM,YAAgC;AACpC,QAAI,KAAK,kBAAkB;AACzB,aAAO,KAAK;AAAA,IACd;AAEA,SAAK,oBAAoB,YAAY;AACnC,YAAM,WAAW,MAAM,KAAK,YAAgC,OAAO;AACnE,YAAM,YAAY,SAAS,UAAU,CAAA;AAErC,aAAO,QAAQ;AAAA,QACb,UAAU,IAAI,OAAO,YAAY;AAC/B,gBAAM,UAAU,QAAQ,QAAQ,QAAQ;AACxC,cAAI,CAAC,SAAS;AACZ,kBAAM,IAAI;AAAA,cACR;AAAA,cACA;AAAA,cACA;AAAA,YAAA;AAAA,UAEJ;AAEA,gBAAM,OAAO,MAAM,KAAK,UAAU,OAAO;AACzC,gBAAM,eAAe,kBAAkB,SAAS,IAAI;AACpD,gBAAM,SAAS,aAAa,SAAS,QAAQ;AAC7C,gBAAM,YAAY,aAAa,SAAS,WAAW;AACnD,gBAAM,gBACJ,MAAM,SAAS,kBAAkB,QAAQ,SAAS;AACpD,gBAAM,SAAS,MAAM,SAAS,UAAU,QAAQ,SAAS;AAEzD,iBAAO;AAAA,YACL,IAAI;AAAA,YACJ,MAAM;AAAA,YACN,aACE,iBAAiB,SACb,GAAG,UAAU,QAAQ,IAAI,iBAAiB,EAAE,GAAG,KAAA,IAC/C,iBAAiB,OAAO;AAAA,YAC9B,eAAe,mBAAmB,SAAS,IAAI;AAAA,YAC/C;AAAA,YACA,mBAAmB;AAAA,YACnB,gBAAgB;AAAA,UAAA;AAAA,QAEpB,CAAC;AAAA,MAAA;AAAA,IAEL,GAAA,EAAK,MAAM,CAAC,UAAU;AACpB,WAAK,mBAAmB;AACxB,YAAM,KAAK,SAAS,KAAK;AAAA,IAC3B,CAAC;AAED,WAAO,KAAK;AAAA,EACd;AAAA,EAEA,MAAM,kBAA2C;AAC/C,WAAO,EAAE,GAAG,oBAAA;AAAA,EACd;AAAA,EAEA,MAAM,iBACJ,OACA,UACsB;AACtB,UAAM,IAAI;AAAA,MACR;AAAA,MACA;AAAA,MACA;AAAA,IAAA;AAAA,EAEJ;AAAA,EAEA,aAAa,OAAe,UAA8C;AACxE,UAAM,QAAQ,IAAI;AAAA,MAChB;AAAA,MACA;AAAA,MACA;AAAA,IAAA;AAEF,WAAO;AAAA,MACL,CAAC,OAAO,aAAa,GAAG,OAAO;AAAA,QAC7B,MAAM,MAAM,QAAQ,OAAO,KAAK;AAAA,MAAA;AAAA,IAClC;AAAA,EAEJ;AAAA,EAEA,MAAM,WAAW,UAA6C;AAC5D,UAAM,IAAI;AAAA,MACR;AAAA,MACA;AAAA,MACA;AAAA,IAAA;AAAA,EAEJ;AAAA,EAEA,MAAM,YAAY,UAA8C;AAC9D,UAAM,IAAI;AAAA,MACR;AAAA,MACA;AAAA,MACA;AAAA,IAAA;AAAA,EAEJ;AAAA,EAEA,MAAM,UAAU,UAA+C;AAC7D,UAAM,IAAI;AAAA,MACR;AAAA,MACA;AAAA,MACA;AAAA,IAAA;AAAA,EAEJ;AACF;"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"openai-5snI2diE.js","sources":["../../src/shared/providers/openai.ts"],"sourcesContent":["/**\n * OpenAI provider implementation\n *\n * Provides a standardized interface for interacting with OpenAI's GPT models,\n * including chat completions, text completions, embeddings, and streaming responses.\n * Supports all major OpenAI features including function calling, vision models,\n * and custom fine-tuned models.\n */\n\nimport OpenAI from 'openai';\nimport { extractRetryAfterSeconds } from '../rate-limit';\nimport type {\n AICapabilities,\n AIInterface,\n AIMessage,\n AIModel,\n AIResponse,\n BaseAIOptions,\n ChatOptions,\n CompletionOptions,\n ContentPart,\n EmbeddingOptions,\n EmbeddingResponse,\n ImageDescriptionOptions,\n ImageEmbeddingOptions,\n ImageGenerationOptions,\n ImageGenerationResponse,\n MessageOptions,\n TokenUsage,\n TTSOptions,\n TTSResponse,\n Voice,\n VoiceCloneOptions,\n VoiceDesignOptions,\n VoiceListOptions,\n} from '../types';\nimport {\n AIError,\n AuthenticationError,\n ContentFilterError,\n ContextLengthError,\n ModelNotFoundError,\n RateLimitError,\n} from '../types';\nimport { emitUsage } from './usage';\n\n/**\n * Shared profile for OpenAI-compatible providers\n */\nexport interface OpenAICompatibleProfile {\n providerLabel: string;\n providerName: string;\n defaultModel: string;\n capabilities: AICapabilities;\n describeModel(modelId: string): string;\n getContextLength(modelId: string): number;\n getModelCapabilities(modelId: string): string[];\n shouldIncludeModel(modelId: string): boolean;\n supportsFunctions(modelId: string): boolean;\n supportsVision(modelId: string): boolean;\n}\n\nconst OPENAI_PROFILE: OpenAICompatibleProfile = {\n providerLabel: 'OpenAI',\n providerName: 'openai',\n defaultModel: 'gpt-4o',\n capabilities: {\n chat: true,\n completion: true,\n embeddings: true,\n streaming: true,\n functions: true,\n vision: true,\n fineTuning: true,\n imageEmbeddings: true,\n imageGeneration: true,\n tts: false,\n voiceCloning: false,\n voiceDesign: false,\n maxContextLength: 128000,\n supportedOperations: [\n 'chat',\n 'completion',\n 'embedding',\n 'streaming',\n 'functions',\n 'vision',\n 'image_embedding',\n 'image_generation',\n ],\n },\n describeModel: (modelId) => `OpenAI model: ${modelId}`,\n getContextLength(modelId) {\n if (modelId.includes('gpt-4o')) return 128000;\n if (modelId.includes('gpt-4.1')) return 128000;\n if (modelId.includes('gpt-4-turbo')) return 128000;\n if (modelId.includes('gpt-4')) return 8192;\n if (modelId.includes('gpt-3.5-turbo')) return 16385;\n if (modelId.includes('text-embedding')) return 8192;\n return 4096;\n },\n getModelCapabilities(modelId) {\n const capabilities = ['text'];\n if (modelId.includes('gpt')) {\n capabilities.push('chat', 'functions');\n }\n if (\n modelId.includes('vision') ||\n modelId === 'gpt-4o' ||\n modelId.includes('gpt-4.1')\n ) {\n capabilities.push('vision');\n }\n if (modelId.includes('embedding')) {\n capabilities.push('embeddings');\n }\n return capabilities;\n },\n shouldIncludeModel(modelId) {\n return modelId.includes('gpt') || modelId.includes('text-embedding');\n },\n supportsFunctions(modelId) {\n return modelId.includes('gpt-4') || modelId.includes('gpt-3.5');\n },\n supportsVision(modelId) {\n return (\n modelId.includes('vision') ||\n modelId === 'gpt-4o' ||\n modelId.includes('gpt-4.1')\n );\n },\n};\n\nexport interface OpenAICompatibleOptions extends BaseAIOptions {\n type?: string;\n apiKey?: string;\n baseUrl?: string;\n organization?: string;\n}\n\n/**\n * OpenAI provider implementation that handles all interactions with OpenAI's API.\n * Supports GPT models, embeddings, function calling, streaming, and vision capabilities.\n */\nexport class OpenAIProvider implements AIInterface {\n private client: OpenAI;\n private options: OpenAICompatibleOptions;\n private readonly profile: OpenAICompatibleProfile;\n\n /**\n * Creates a new OpenAI provider instance\n * @param options - Configuration options for the OpenAI provider\n */\n constructor(\n options: OpenAICompatibleOptions,\n profile: OpenAICompatibleProfile = OPENAI_PROFILE,\n ) {\n this.profile = profile;\n this.options = {\n defaultModel: this.profile.defaultModel,\n ...options,\n };\n\n this.client = new OpenAI({\n apiKey: this.options.apiKey,\n baseURL: this.options.baseUrl,\n organization: this.options.organization,\n timeout: this.options.timeout,\n maxRetries: this.options.maxRetries,\n defaultHeaders: this.options.headers,\n });\n }\n\n /**\n * Generate a chat completion using OpenAI's chat models\n * @param messages - Array of conversation messages\n * @param options - Optional configuration for the chat completion\n * @returns Promise resolving to the AI response with content and metadata\n * @throws {AIError} When the API request fails or returns invalid data\n *\n * @example\n * ```typescript\n * const response = await provider.chat([\n * { role: 'system', content: 'You are a helpful assistant.' },\n * { role: 'user', content: 'What is the capital of France?' }\n * ], {\n * model: 'gpt-4o',\n * temperature: 0.7,\n * maxTokens: 150\n * });\n * console.log(response.content); // \"Paris is the capital of France.\"\n * ```\n */\n async chat(\n messages: AIMessage[],\n options: ChatOptions = {},\n ): Promise<AIResponse> {\n const startTime = Date.now();\n try {\n const model =\n options.model || this.options.defaultModel || this.profile.defaultModel;\n const response = await this.client.chat.completions.create({\n model,\n messages: this.mapMessagesToOpenAI(messages),\n max_tokens: options.maxTokens,\n temperature: options.temperature,\n top_p: options.topP,\n n: options.n,\n stop: options.stop,\n frequency_penalty: options.frequencyPenalty,\n presence_penalty: options.presencePenalty,\n user: options.user,\n tools: options.tools?.map((tool) => ({\n type: 'function' as const,\n function: {\n name: tool.function.name,\n description: tool.function.description,\n parameters: tool.function.parameters,\n },\n })),\n tool_choice: this.mapToolChoice(options.toolChoice),\n response_format: options.responseFormat,\n seed: options.seed,\n stream: false,\n });\n\n const choice = response.choices[0];\n if (!choice) {\n throw new AIError(\n `No choices returned from ${this.profile.providerLabel}`,\n 'NO_CHOICES',\n this.profile.providerName,\n );\n }\n\n const usage = this.mapUsage(response.usage);\n emitUsage(\n this.options,\n this.profile.providerName,\n 'chat',\n response.model || model,\n usage,\n startTime,\n options.usageTags,\n );\n\n return {\n content: choice.message.content || '',\n usage,\n model: response.model,\n finishReason: this.mapFinishReason(choice.finish_reason),\n toolCalls: choice.message.tool_calls\n ?.filter((call) => call.type === 'function')\n .map((call) => ({\n id: call.id,\n type: 'function' as const,\n function: {\n name: call.function.name,\n arguments: call.function.arguments,\n },\n })),\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n /**\n * Generate a text completion for a given prompt\n * @param prompt - The text prompt to complete\n * @param options - Optional configuration for the completion\n * @returns Promise resolving to the AI response\n * @throws {AIError} When the API request fails\n *\n * @example\n * ```typescript\n * const response = await provider.complete('The weather today is', {\n * model: 'gpt-4o',\n * maxTokens: 50,\n * temperature: 0.5\n * });\n * ```\n */\n async complete(\n prompt: string,\n options: CompletionOptions = {},\n ): Promise<AIResponse> {\n return this.chat([{ role: 'user', content: prompt }], {\n model: options.model,\n maxTokens: options.maxTokens,\n temperature: options.temperature,\n topP: options.topP,\n n: options.n,\n stop: options.stop,\n stream: options.stream,\n onProgress: options.onProgress,\n usageTags: options.usageTags,\n });\n }\n\n /**\n * Simple message interface for single-turn interactions with optional history\n *\n * @param text - The message text to send\n * @param options - Configuration options including history, model, etc.\n * @returns Promise resolving to the response content string\n *\n * @example\n * ```typescript\n * // Simple usage\n * const response = await provider.message('Hello!');\n *\n * // With options\n * const response = await provider.message('Analyze this', {\n * model: 'gpt-4o',\n * responseFormat: { type: 'json_object' }\n * });\n *\n * // With history\n * const response = await provider.message('What was my question?', {\n * history: [\n * { role: 'user', content: 'What is 2+2?' },\n * { role: 'assistant', content: '4' }\n * ]\n * });\n * ```\n */\n async message(text: string, options: MessageOptions = {}): Promise<string> {\n // Build messages array from history + current message\n const messages: AIMessage[] = [\n ...(options.history || []),\n { role: options.role || 'user', content: text },\n ];\n\n const response = await this.chat(messages, {\n model: options.model,\n maxTokens: options.maxTokens,\n temperature: options.temperature,\n topP: options.topP,\n stop: options.stop,\n stream: options.stream,\n frequencyPenalty: options.frequencyPenalty,\n presencePenalty: options.presencePenalty,\n responseFormat: options.responseFormat,\n seed: options.seed,\n tools: options.tools,\n toolChoice: options.toolChoice,\n onProgress: options.onProgress,\n usageTags: options.usageTags,\n });\n\n return response.content;\n }\n\n /**\n * Generate embeddings for the given text(s)\n * @param text - Single text string or array of texts to embed\n * @param options - Optional configuration for embeddings\n * @returns Promise resolving to embeddings response with vector arrays\n * @throws {AIError} When the API request fails\n *\n * @example\n * ```typescript\n * // Single text embedding\n * const response1 = await provider.embed('Hello world');\n * console.log(response1.embeddings[0]); // Array of numbers\n *\n * // Multiple text embeddings\n * const response2 = await provider.embed(['Text 1', 'Text 2']);\n * console.log(response2.embeddings.length); // 2\n * ```\n */\n async embed(\n text: string | string[],\n options: EmbeddingOptions = {},\n ): Promise<EmbeddingResponse> {\n const startTime = Date.now();\n try {\n const model = options.model || 'text-embedding-3-small';\n const input = Array.isArray(text) ? text : [text];\n const response = await this.client.embeddings.create({\n model,\n input,\n encoding_format: options.encodingFormat,\n dimensions: options.dimensions,\n user: options.user,\n });\n\n const usage = this.mapUsage(response.usage);\n emitUsage(\n this.options,\n this.profile.providerName,\n 'embed',\n response.model || model,\n usage,\n startTime,\n options.usageTags,\n );\n\n return {\n embeddings: response.data.map((item) => item.embedding),\n usage,\n model: response.model,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n /**\n * Convert an image to a base64 data URL\n * @param image - Image as URL, base64 data URL, or Buffer\n * @returns base64 data URL string\n * @private\n */\n private async imageToBase64(image: string | Buffer): Promise<string> {\n if (Buffer.isBuffer(image)) {\n return `data:image/png;base64,${image.toString('base64')}`;\n }\n if (image.startsWith('data:')) {\n return image; // Already base64 data URL\n }\n // It's a URL - fetch and convert\n const response = await fetch(image);\n if (!response.ok) {\n throw new AIError(\n `Failed to fetch image: ${response.status} ${response.statusText}`,\n 'IMAGE_FETCH_ERROR',\n this.profile.providerName,\n );\n }\n const arrayBuffer = await response.arrayBuffer();\n const buffer = Buffer.from(arrayBuffer);\n const contentType = response.headers.get('content-type') || 'image/png';\n return `data:${contentType};base64,${buffer.toString('base64')}`;\n }\n\n /**\n * Generate a text description of an image\n * @param image - Image as URL, base64 data URL, or Buffer\n * @param prompt - Custom prompt for description (optional)\n * @param options - Optional configuration\n * @returns Promise resolving to the description string\n *\n * @example\n * ```typescript\n * const description = await provider.describeImage('https://example.com/image.jpg');\n * ```\n */\n async describeImage(\n image: string | Buffer,\n prompt?: string,\n options: ImageDescriptionOptions = {},\n ): Promise<string> {\n try {\n const defaultPrompt =\n 'Describe this image for a search index. Include objects, mood, lighting, and any visible text.';\n\n const imageUrl = await this.imageToBase64(image);\n\n const response = await this.chat(\n [\n {\n role: 'user',\n content: [\n { type: 'text', text: prompt || defaultPrompt },\n {\n type: 'image_url',\n image_url: {\n url: imageUrl,\n detail: options.detail || 'auto',\n },\n },\n ],\n },\n ],\n {\n model:\n options.model ||\n this.options.defaultModel ||\n this.profile.defaultModel,\n maxTokens: options.maxTokens || 500,\n },\n );\n\n return response.content;\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n /**\n * Generate embeddings for an image using describe-then-embed pattern\n * @param image - Image as URL, base64 data URL, or Buffer\n * @param options - Optional configuration for image embeddings\n * @returns Promise resolving to embeddings response\n *\n * @example\n * ```typescript\n * const embedding = await provider.embedImage('https://example.com/image.jpg');\n * ```\n */\n async embedImage(\n image: string | Buffer,\n options: ImageEmbeddingOptions = {},\n ): Promise<EmbeddingResponse> {\n try {\n // OpenAI doesn't have native image embeddings - use describe-then-embed\n const description = await this.describeImage(\n image,\n 'Describe this image in detail for semantic embedding. Include all visible objects, colors, textures, composition, text, people, actions, and overall scene context.',\n );\n\n return this.embed(description, {\n model: options.model || 'text-embedding-3-small',\n dimensions: options.dimensions,\n user: options.user,\n });\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n /**\n * Generate an image from a text prompt using DALL-E\n * @param prompt - Text description of the image to generate\n * @param options - Optional configuration for image generation\n * @returns Promise resolving to generated image(s)\n *\n * @example\n * ```typescript\n * const result = await provider.generateImage('A sunset over mountains');\n * fs.writeFileSync('image.png', result.images[0].data);\n * ```\n */\n async generateImage(\n prompt: string,\n options: ImageGenerationOptions = {},\n ): Promise<ImageGenerationResponse> {\n try {\n const model = options.model || 'dall-e-3';\n\n const requestParams: OpenAI.Images.ImageGenerateParams = {\n model,\n prompt,\n n: model === 'dall-e-3' ? 1 : options.n || 1,\n size:\n (options.size as OpenAI.Images.ImageGenerateParams['size']) ||\n '1024x1024',\n response_format: options.outputFormat === 'url' ? 'url' : 'b64_json',\n };\n\n if (model === 'dall-e-3') {\n if (options.style) {\n requestParams.style = options.style;\n }\n if (options.quality) {\n requestParams.quality =\n options.quality as OpenAI.Images.ImageGenerateParams['quality'];\n }\n }\n\n const response = await this.client.images.generate(requestParams);\n\n const images = (response.data || []).map((item) => {\n let data: Buffer | string;\n const mimeType = 'image/png';\n\n if (options.outputFormat === 'url') {\n data = item.url || '';\n } else if (options.outputFormat === 'base64') {\n data = item.b64_json || '';\n } else {\n // Default: buffer\n data = Buffer.from(item.b64_json || '', 'base64');\n }\n\n return {\n data,\n mimeType,\n revisedPrompt: item.revised_prompt,\n };\n });\n\n return {\n images,\n model,\n };\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n /**\n * Stream a chat completion response in real-time\n * @param messages - Array of conversation messages\n * @param options - Optional configuration for the chat completion\n * @yields Individual content chunks as they arrive\n * @throws {AIError} When the streaming request fails\n *\n * @example\n * ```typescript\n * for await (const chunk of provider.stream([\n * { role: 'user', content: 'Write a story about AI' }\n * ])) {\n * process.stdout.write(chunk);\n * }\n * ```\n */\n async *stream(\n messages: AIMessage[],\n options: ChatOptions = {},\n ): AsyncIterable<string> {\n const startTime = Date.now();\n try {\n const model =\n options.model || this.options.defaultModel || this.profile.defaultModel;\n const stream = await this.client.chat.completions.create({\n model,\n messages: this.mapMessagesToOpenAI(messages),\n max_tokens: options.maxTokens,\n temperature: options.temperature,\n top_p: options.topP,\n stop: options.stop,\n frequency_penalty: options.frequencyPenalty,\n presence_penalty: options.presencePenalty,\n user: options.user,\n stream: true,\n });\n\n for await (const chunk of stream) {\n const content = chunk.choices[0]?.delta?.content;\n if (content) {\n if (options.onProgress) {\n options.onProgress(content);\n }\n yield content;\n }\n }\n\n emitUsage(\n this.options,\n this.profile.providerName,\n 'stream',\n model,\n undefined,\n startTime,\n options.usageTags,\n );\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n /**\n * Count the number of tokens in the given text\n * @param text - The text to count tokens for\n * @returns Promise resolving to the estimated token count\n *\n * @remarks\n * OpenAI doesn't provide a direct token counting API, so this is an approximation\n * based on the general rule of ~4 characters per token. For precise counting,\n * consider using a dedicated tokenizer library.\n *\n * @example\n * ```typescript\n * const count = await provider.countTokens('Hello, world!');\n * console.log(count); // Approximately 4 tokens\n * ```\n */\n async countTokens(text: string): Promise<number> {\n // OpenAI doesn't provide a direct token counting API\n // This is an approximation based on the general rule of ~4 characters per token\n return Math.ceil(text.length / 4);\n }\n\n /**\n * Get a list of available OpenAI models\n * @returns Promise resolving to an array of model information\n * @throws {AIError} When the API request fails\n *\n * @example\n * ```typescript\n * const models = await provider.getModels();\n * const gptModels = models.filter(m => m.id.includes('gpt'));\n * ```\n */\n async getModels(): Promise<AIModel[]> {\n try {\n const response = await this.client.models.list();\n return response.data\n .filter((model) => this.profile.shouldIncludeModel(model.id))\n .map((model) => ({\n id: model.id,\n name: model.id,\n description: this.profile.describeModel(model.id),\n contextLength: this.profile.getContextLength(model.id),\n capabilities: this.profile.getModelCapabilities(model.id),\n supportsFunctions: this.profile.supportsFunctions(model.id),\n supportsVision: this.profile.supportsVision(model.id),\n }));\n } catch (error) {\n throw this.mapError(error);\n }\n }\n\n /**\n * Get the capabilities supported by this OpenAI provider\n * @returns Promise resolving to provider capabilities\n *\n * @example\n * ```typescript\n * const caps = await provider.getCapabilities();\n * if (caps.functions) {\n * // Provider supports function calling\n * }\n * ```\n */\n async getCapabilities(): Promise<AICapabilities> {\n return { ...this.profile.capabilities };\n }\n\n // ============================================================================\n // TTS Methods (Not supported - use Qwen3-TTS provider)\n // ============================================================================\n\n async synthesizeSpeech(\n _text: string,\n _options?: TTSOptions,\n ): Promise<TTSResponse> {\n throw new AIError(\n `TTS is not supported by ${this.profile.providerLabel} provider. Use Qwen3-TTS provider.`,\n 'NOT_IMPLEMENTED',\n this.profile.providerName,\n );\n }\n\n streamSpeech(_text: string, _options?: TTSOptions): AsyncIterable<Buffer> {\n const error = new AIError(\n `TTS streaming is not supported by ${this.profile.providerLabel} provider. Use Qwen3-TTS provider.`,\n 'NOT_IMPLEMENTED',\n this.profile.providerName,\n );\n return {\n [Symbol.asyncIterator]: () => ({\n next: () => Promise.reject(error),\n }),\n };\n }\n\n async cloneVoice(_options: VoiceCloneOptions): Promise<Voice> {\n throw new AIError(\n `Voice cloning is not supported by ${this.profile.providerLabel} provider. Use Qwen3-TTS provider.`,\n 'NOT_IMPLEMENTED',\n this.profile.providerName,\n );\n }\n\n async designVoice(_options: VoiceDesignOptions): Promise<Voice> {\n throw new AIError(\n `Voice design is not supported by ${this.profile.providerLabel} provider. Use Qwen3-TTS provider.`,\n 'NOT_IMPLEMENTED',\n this.profile.providerName,\n );\n }\n\n async getVoices(_options?: VoiceListOptions): Promise<Voice[]> {\n throw new AIError(\n `Voice listing is not supported by ${this.profile.providerLabel} provider. Use Qwen3-TTS provider.`,\n 'NOT_IMPLEMENTED',\n this.profile.providerName,\n );\n }\n\n /**\n * Maps internal AI messages to OpenAI's message format\n * @param messages - Array of internal AI messages\n * @returns Array of OpenAI-compatible message parameters\n * @private\n */\n private mapMessagesToOpenAI(\n messages: AIMessage[],\n ): OpenAI.Chat.ChatCompletionMessageParam[] {\n return messages.map((message) => {\n // Handle content that can be string or ContentPart[]\n let content: string | OpenAI.Chat.ChatCompletionContentPart[];\n\n if (typeof message.content === 'string') {\n content = message.content;\n } else {\n // Array of content parts - map to OpenAI format\n content = message.content.map((part: ContentPart) => {\n if (part.type === 'text') {\n return { type: 'text' as const, text: part.text };\n }\n // Image content part\n return {\n type: 'image_url' as const,\n image_url: {\n url: part.image_url.url,\n detail: part.image_url.detail,\n },\n };\n });\n }\n\n // Build message based on role and content\n const baseMessage = {\n role: message.role as OpenAI.Chat.ChatCompletionRole,\n content,\n };\n\n // Add optional fields based on role and availability\n if (\n message.name &&\n (message.role === 'system' ||\n message.role === 'user' ||\n message.role === 'function')\n ) {\n (baseMessage as any).name = message.name;\n }\n\n if (message.tool_calls && message.role === 'assistant') {\n (baseMessage as any).tool_calls = message.tool_calls;\n }\n\n return baseMessage as OpenAI.Chat.ChatCompletionMessageParam;\n });\n }\n\n /**\n * Maps internal tool choice format to OpenAI's tool choice format\n * @param toolChoice - Internal tool choice specification\n * @returns OpenAI-compatible tool choice option or undefined\n * @private\n */\n private mapToolChoice(\n toolChoice?:\n | 'auto'\n | 'none'\n | { type: 'function'; function: { name: string } },\n ): OpenAI.Chat.ChatCompletionToolChoiceOption | undefined {\n if (!toolChoice) return undefined;\n if (typeof toolChoice === 'string') return toolChoice;\n return {\n type: 'function',\n function: { name: toolChoice.function.name },\n };\n }\n\n /**\n * Maps OpenAI usage information to internal token usage format\n * @param usage - OpenAI usage object from API response\n * @returns Internal token usage object or undefined\n * @private\n */\n private mapUsage(\n usage?:\n | OpenAI.CompletionUsage\n | OpenAI.Completions.CompletionUsage\n | OpenAI.Embeddings.CreateEmbeddingResponse.Usage,\n ): TokenUsage | undefined {\n if (!usage) return undefined;\n return {\n promptTokens: usage.prompt_tokens || 0,\n completionTokens: (usage as any).completion_tokens || 0,\n totalTokens: usage.total_tokens || 0,\n };\n }\n\n /**\n * Maps OpenAI finish reason to internal finish reason format\n * @param reason - OpenAI finish reason from API response\n * @returns Internal finish reason\n * @private\n */\n private mapFinishReason(reason: string | null): AIResponse['finishReason'] {\n switch (reason) {\n case 'stop':\n return 'stop';\n case 'length':\n return 'length';\n case 'tool_calls':\n return 'tool_calls';\n case 'content_filter':\n return 'content_filter';\n default:\n return 'stop';\n }\n }\n\n /**\n * Gets the context length for a given OpenAI model\n * @param modelId - The OpenAI model identifier\n * @returns Maximum context length in tokens\n * @private\n */\n /**\n * Maps OpenAI API errors to internal AI error types\n * @param error - The error object from OpenAI API\n * @returns Appropriate internal AI error instance\n * @private\n */\n\n private mapError(error: unknown): AIError {\n if (error instanceof OpenAI.APIError) {\n switch (error.status) {\n case 401:\n return new AuthenticationError(this.profile.providerName);\n case 429: {\n return new RateLimitError(\n this.profile.providerName,\n extractRetryAfterSeconds(error),\n );\n }\n case 404:\n return new ModelNotFoundError(\n error.message,\n this.profile.providerName,\n );\n case 413:\n return new ContextLengthError(this.profile.providerName);\n default:\n if (error.message.includes('content_filter')) {\n return new ContentFilterError(this.profile.providerName);\n }\n return new AIError(\n error.message,\n 'API_ERROR',\n this.profile.providerName,\n );\n }\n }\n\n if (error instanceof AIError) {\n return error;\n }\n\n const errorMessage =\n error instanceof Error ? error.message : 'Unknown error occurred';\n return new AIError(\n errorMessage,\n 'UNKNOWN_ERROR',\n this.profile.providerName,\n );\n }\n}\n"],"names":[],"mappings":"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"}
|