{"version":3,"sources":["../../../src/utils/errors.ts","../../../src/models/strategies/CascadingStrategy.ts","../../../src/models/strategies/WeightedStrategy.ts","../../../src/models/strategies/ContextAwareStrategy.ts"],"names":[],"mappings":"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","file":"index.mjs","sourcesContent":["export class OpenRouterError extends Error {\n  constructor(\n    message: string,\n    public code: string,\n    public statusCode?: number,\n    public details?: Record<string, unknown>,\n  ) {\n    super(message);\n    this.name = 'OpenRouterError';\n    Object.setPrototypeOf(this, OpenRouterError.prototype);\n  }\n}\n\nexport class AuthenticationError extends OpenRouterError {\n  constructor(message: string = 'Invalid API key', details?: Record<string, unknown>) {\n    super(message, 'AUTHENTICATION_ERROR', 401, details);\n    this.name = 'AuthenticationError';\n  }\n}\n\nexport class RateLimitError extends OpenRouterError {\n  constructor(\n    message: string = 'Rate limit exceeded',\n    public retryAfter?: number,\n    details?: Record<string, unknown>,\n  ) {\n    super(message, 'RATE_LIMIT_ERROR', 429, details);\n    this.name = 'RateLimitError';\n  }\n}\n\nexport class ModelNotFoundError extends OpenRouterError {\n  constructor(modelId: string) {\n    super(`Model not found: ${modelId}`, 'MODEL_NOT_FOUND', 404, { modelId });\n    this.name = 'ModelNotFoundError';\n  }\n}\n\nexport class InvalidRequestError extends OpenRouterError {\n  constructor(message: string, details?: Record<string, unknown>) {\n    super(message, 'INVALID_REQUEST', 400, details);\n    this.name = 'InvalidRequestError';\n  }\n}\n\nexport class NetworkError extends OpenRouterError {\n  constructor(\n    message: string,\n    public originalError?: Error,\n  ) {\n    super(message, 'NETWORK_ERROR', undefined, { originalError: originalError?.message });\n    this.name = 'NetworkError';\n  }\n}\n\nexport class TimeoutError extends OpenRouterError {\n  constructor(timeout: number) {\n    super(`Request timed out after ${timeout}ms`, 'TIMEOUT_ERROR', 408, { timeout });\n    this.name = 'TimeoutError';\n  }\n}\n\nexport class BudgetExceededError extends OpenRouterError {\n  constructor(current: number, limit: number, period: string) {\n    super(`Budget exceeded: ${current} / ${limit} (${period})`, 'BUDGET_EXCEEDED', 402, {\n      current,\n      limit,\n      period,\n    });\n    this.name = 'BudgetExceededError';\n  }\n}\n\nexport class ModelSelectionError extends OpenRouterError {\n  constructor(message: string, details?: Record<string, unknown>) {\n    super(message, 'MODEL_SELECTION_ERROR', undefined, details);\n    this.name = 'ModelSelectionError';\n  }\n}\n\nexport class StreamError extends OpenRouterError {\n  constructor(message: string, details?: Record<string, unknown>) {\n    super(message, 'STREAM_ERROR', undefined, details);\n    this.name = 'StreamError';\n  }\n}\n\nexport function isRetryableError(error: Error): boolean {\n  if (error instanceof RateLimitError) return true;\n  if (error instanceof NetworkError) return true;\n  if (error instanceof TimeoutError) return true;\n\n  if (error instanceof OpenRouterError) {\n    const retryableCodes = [408, 429, 500, 502, 503, 504];\n    return error.statusCode ? retryableCodes.includes(error.statusCode) : false;\n  }\n\n  return false;\n}\n\nexport function parseOpenRouterError(statusCode: number, body: any): OpenRouterError {\n  const message = body?.error?.message || 'Unknown error';\n  const details = body?.error?.metadata || {};\n\n  switch (statusCode) {\n    case 401:\n    case 403:\n      return new AuthenticationError(message, details);\n    case 404:\n      return new ModelNotFoundError(message);\n    case 429:\n      const retryAfter = body?.error?.metadata?.retry_after;\n      return new RateLimitError(message, retryAfter, details);\n    case 400:\n      return new InvalidRequestError(message, details);\n    default:\n      return new OpenRouterError(message, 'API_ERROR', statusCode, details);\n  }\n}\n","/**\n * Cascading Strategy\n * Tries multiple models in sequence until one succeeds\n */\n\nimport type { ChatCompletionRequest, ChatCompletionResponse } from '../../types/api';\nimport type { ModelCatalog } from '../ModelCatalog';\nimport type { Logger } from '../../utils/logger';\nimport { ModelNotFoundError } from '../../utils/errors';\n\nexport interface CascadingOptions {\n  models: string[]; // Ordered list of models to try\n  maxAttempts?: number; // Maximum number of models to try\n  retryableErrors?: string[]; // Error types that trigger fallback\n  onFallback?: (modelId: string, error: Error) => void;\n}\n\nexport class CascadingStrategy {\n  private catalog: ModelCatalog;\n  private logger: Logger;\n  private options: Required<CascadingOptions>;\n\n  constructor(catalog: ModelCatalog, logger: Logger, options: CascadingOptions) {\n    this.catalog = catalog;\n    this.logger = logger;\n    this.options = {\n      models: options.models,\n      maxAttempts: options.maxAttempts || options.models.length,\n      retryableErrors: options.retryableErrors || [\n        'rate_limit',\n        'timeout',\n        'service_unavailable',\n        'model_unavailable',\n      ],\n      onFallback: options.onFallback || (() => {}),\n    };\n  }\n\n  /**\n   * Execute request with cascading fallback\n   */\n  async execute(\n    request: ChatCompletionRequest,\n    executor: (modelId: string, request: ChatCompletionRequest) => Promise<ChatCompletionResponse>,\n  ): Promise<ChatCompletionResponse> {\n    const attemptedModels: string[] = [];\n    let lastError: Error | null = null;\n\n    // Try each model in sequence\n    for (let i = 0; i < this.options.maxAttempts && i < this.options.models.length; i++) {\n      const modelId = this.options.models[i];\n      attemptedModels.push(modelId);\n\n      try {\n        // Verify model exists\n        const model = this.catalog.getModel(modelId);\n        if (!model) {\n          throw new ModelNotFoundError(`Model ${modelId} not found in catalog`);\n        }\n\n        this.logger.info('Attempting model', { modelId, attempt: i + 1 });\n\n        // Execute request with this model\n        const response = await executor(modelId, {\n          ...request,\n          model: modelId,\n        });\n\n        this.logger.info('Model succeeded', { modelId });\n        return response;\n      } catch (error) {\n        lastError = error instanceof Error ? error : new Error(String(error));\n\n        this.logger.warn('Model failed', {\n          modelId,\n          error: lastError.message,\n          attempt: i + 1,\n        });\n\n        // Check if error is retryable\n        if (!this.isRetryableError(lastError)) {\n          throw lastError;\n        }\n\n        // Call fallback callback\n        this.options.onFallback(modelId, lastError);\n\n        // Continue to next model\n        continue;\n      }\n    }\n\n    // All models failed\n    throw new Error(\n      `All models failed in cascade: ${attemptedModels.join(', ')}. Last error: ${lastError?.message || 'Unknown'}`,\n    );\n  }\n\n  /**\n   * Check if error should trigger fallback\n   */\n  private isRetryableError(error: Error): boolean {\n    const errorMessage = error.message.toLowerCase();\n\n    return this.options.retryableErrors.some((errorType) =>\n      errorMessage.includes(errorType.toLowerCase()),\n    );\n  }\n\n  /**\n   * Get cascade configuration\n   */\n  getConfiguration(): CascadingOptions {\n    return {\n      models: this.options.models,\n      maxAttempts: this.options.maxAttempts,\n      retryableErrors: this.options.retryableErrors,\n    };\n  }\n\n  /**\n   * Update models list\n   */\n  setModels(models: string[]): void {\n    this.options.models = models;\n    this.logger.info('Updated cascade models', { models });\n  }\n\n  /**\n   * Add a model to the cascade\n   */\n  addModel(modelId: string, position?: number): void {\n    if (position !== undefined && position >= 0 && position < this.options.models.length) {\n      this.options.models.splice(position, 0, modelId);\n    } else {\n      this.options.models.push(modelId);\n    }\n\n    this.logger.info('Added model to cascade', { modelId, position });\n  }\n\n  /**\n   * Remove a model from the cascade\n   */\n  removeModel(modelId: string): boolean {\n    const index = this.options.models.indexOf(modelId);\n\n    if (index !== -1) {\n      this.options.models.splice(index, 1);\n      this.logger.info('Removed model from cascade', { modelId });\n      return true;\n    }\n\n    return false;\n  }\n}\n","/**\n * Weighted Strategy\n * Selects models based on custom weighted scoring\n */\n\nimport type { SelectionCriteria, SelectionResult } from '../../types/routing';\nimport type { Model } from '../../types/models';\nimport type { ModelCatalog } from '../ModelCatalog';\nimport type { Logger } from '../../utils/logger';\n\nexport interface WeightConfig {\n  cost: number; // Weight for cost (0-1)\n  performance: number; // Weight for performance/speed (0-1)\n  capability: number; // Weight for capabilities (0-1)\n  reliability: number; // Weight for reliability/rating (0-1)\n}\n\nexport interface WeightedStrategyOptions {\n  weights?: Partial<WeightConfig>;\n  normalize?: boolean; // Auto-normalize weights to sum to 1\n}\n\nexport class WeightedStrategy {\n  private catalog: ModelCatalog;\n  private logger: Logger;\n  private weights: WeightConfig;\n\n  constructor(catalog: ModelCatalog, logger: Logger, options: WeightedStrategyOptions = {}) {\n    this.catalog = catalog;\n    this.logger = logger;\n\n    // Default weights\n    const defaultWeights: WeightConfig = {\n      cost: 0.4,\n      performance: 0.3,\n      capability: 0.2,\n      reliability: 0.1,\n    };\n\n    this.weights = {\n      ...defaultWeights,\n      ...options.weights,\n    };\n\n    // Normalize weights if requested\n    if (options.normalize !== false) {\n      this.normalizeWeights();\n    }\n  }\n\n  /**\n   * Select model using weighted scoring\n   */\n  select(query: string, criteria: SelectionCriteria): SelectionResult {\n    // Get candidate models\n    const candidates = this.catalog.filterModels(criteria);\n\n    if (candidates.length === 0) {\n      throw new Error('No models match the selection criteria');\n    }\n\n    // Score each model\n    const scored = candidates.map((model) => ({\n      model,\n      score: this.calculateScore(model, criteria),\n    }));\n\n    // Sort by score (descending)\n    scored.sort((a, b) => b.score - a.score);\n\n    const best = scored[0];\n\n    this.logger.info('Selected model using weighted strategy', {\n      modelId: best.model.id,\n      score: best.score,\n      weights: this.weights,\n    });\n\n    return {\n      modelId: best.model.id,\n      model: best.model,\n      provider: best.model.provider,\n      expectedCost: this.estimateCost(best.model, query),\n      estimatedLatency: this.estimateLatency(best.model),\n      reason: `Weighted selection (score: ${best.score.toFixed(3)})`,\n      alternatives: scored.slice(1, 4).map((s) => ({\n        modelId: s.model.id,\n        score: s.score,\n        reason: `Score: ${s.score.toFixed(3)}`,\n      })),\n      confidence: this.calculateConfidence(scored),\n    };\n  }\n\n  /**\n   * Calculate weighted score for a model\n   */\n  private calculateScore(model: Model, criteria: SelectionCriteria): number {\n    let score = 0;\n\n    // Cost score (lower is better)\n    const costScore = this.calculateCostScore(model);\n    score += costScore * this.weights.cost;\n\n    // Performance score (faster is better)\n    const performanceScore = this.calculatePerformanceScore(model);\n    score += performanceScore * this.weights.performance;\n\n    // Capability score (more capabilities is better)\n    const capabilityScore = this.calculateCapabilityScore(model, criteria);\n    score += capabilityScore * this.weights.capability;\n\n    // Reliability score (higher rating is better)\n    const reliabilityScore = this.calculateReliabilityScore(model);\n    score += reliabilityScore * this.weights.reliability;\n\n    return score;\n  }\n\n  /**\n   * Calculate cost score (normalized 0-1, lower cost = higher score)\n   */\n  private calculateCostScore(model: Model): number {\n    const avgCost = (model.pricing.inputTokens + model.pricing.outputTokens) / 2;\n\n    // Normalize using a reference cost (e.g., $10 per 1M tokens)\n    const referenceCost = 10;\n    const normalizedCost = Math.min(avgCost / referenceCost, 1);\n\n    // Invert so lower cost = higher score\n    return 1 - normalizedCost;\n  }\n\n  /**\n   * Calculate performance score (normalized 0-1)\n   */\n  private calculatePerformanceScore(model: Model): number {\n    // Simple heuristic based on model type\n    // In production, use actual latency metrics\n    const performanceMap: Record<string, number> = {\n      'gpt-4o-mini': 0.9,\n      'gpt-4o': 0.7,\n      'claude-3-haiku': 0.9,\n      'claude-3-sonnet': 0.7,\n      'claude-3-opus': 0.5,\n      'gemini-flash': 0.95,\n      'gemini-pro': 0.75,\n    };\n\n    return performanceMap[model.id] || 0.6; // Default medium performance\n  }\n\n  /**\n   * Calculate capability score based on requirements\n   */\n  private calculateCapabilityScore(model: Model, criteria: SelectionCriteria): number {\n    if (!criteria.capabilities) {\n      return 1; // No specific requirements\n    }\n\n    let matchedCapabilities = 0;\n    let totalCapabilities = 0;\n\n    const requiredCaps = criteria.capabilities as Record<string, boolean>;\n\n    for (const [capability, required] of Object.entries(requiredCaps)) {\n      if (required) {\n        totalCapabilities++;\n        if (model.capabilities[capability as keyof typeof model.capabilities]) {\n          matchedCapabilities++;\n        }\n      }\n    }\n\n    return totalCapabilities > 0 ? matchedCapabilities / totalCapabilities : 1;\n  }\n\n  /**\n   * Calculate reliability score (normalized 0-1)\n   */\n  private calculateReliabilityScore(model: Model): number {\n    // Use model rating if available, otherwise default\n    return model.rating ? model.rating / 5 : 0.8;\n  }\n\n  /**\n   * Estimate cost for a query\n   */\n  private estimateCost(model: Model, query: string): number {\n    // Rough estimation: ~1 token per 4 characters\n    const estimatedTokens = Math.ceil(query.length / 4);\n    const inputCost = (estimatedTokens / 1000000) * model.pricing.inputTokens;\n    const outputCost = (estimatedTokens / 1000000) * model.pricing.outputTokens; // Assume similar output\n\n    return inputCost + outputCost;\n  }\n\n  /**\n   * Estimate latency for a model\n   */\n  private estimateLatency(model: Model): number {\n    // Simple heuristic - in production, use actual metrics\n    const latencyMap: Record<string, number> = {\n      'gpt-4o-mini': 500,\n      'gpt-4o': 1200,\n      'claude-3-haiku': 600,\n      'claude-3-sonnet': 1000,\n      'claude-3-opus': 2000,\n      'gemini-flash': 400,\n      'gemini-pro': 800,\n    };\n\n    return latencyMap[model.id] || 1000;\n  }\n\n  /**\n   * Calculate confidence based on score distribution\n   */\n  private calculateConfidence(scored: Array<{ model: Model; score: number }>): number {\n    if (scored.length < 2) {\n      return 1;\n    }\n\n    // Confidence based on gap between best and second-best\n    const gap = scored[0].score - scored[1].score;\n    return Math.min(0.5 + gap, 1);\n  }\n\n  /**\n   * Normalize weights to sum to 1\n   */\n  private normalizeWeights(): void {\n    const sum =\n      this.weights.cost +\n      this.weights.performance +\n      this.weights.capability +\n      this.weights.reliability;\n\n    if (sum !== 1 && sum > 0) {\n      this.weights.cost /= sum;\n      this.weights.performance /= sum;\n      this.weights.capability /= sum;\n      this.weights.reliability /= sum;\n\n      this.logger.debug('Normalized weights', { weights: this.weights });\n    }\n  }\n\n  /**\n   * Update weights\n   */\n  setWeights(weights: Partial<WeightConfig>, normalize = true): void {\n    this.weights = {\n      ...this.weights,\n      ...weights,\n    };\n\n    if (normalize) {\n      this.normalizeWeights();\n    }\n\n    this.logger.info('Updated weights', { weights: this.weights });\n  }\n\n  /**\n   * Get current weights\n   */\n  getWeights(): WeightConfig {\n    return { ...this.weights };\n  }\n}\n","/**\n * Context-Aware Strategy\n * Selects models based on query context and requirements\n */\n\nimport type { SelectionCriteria, SelectionResult } from '../../types/routing';\nimport type { ModelCatalog } from '../ModelCatalog';\nimport type { Logger } from '../../utils/logger';\n\nexport interface ContextAnalysis {\n  hasCode: boolean;\n  hasImage: boolean;\n  hasJson: boolean;\n  requiresFunctions: boolean;\n  complexity: 'simple' | 'medium' | 'complex';\n  estimatedTokens: number;\n  language?: string;\n}\n\nexport class ContextAwareStrategy {\n  private catalog: ModelCatalog;\n  private logger: Logger;\n\n  constructor(catalog: ModelCatalog, logger: Logger) {\n    this.catalog = catalog;\n    this.logger = logger;\n  }\n\n  /**\n   * Select model based on query context\n   */\n  select(query: string, criteria: SelectionCriteria = {}): SelectionResult {\n    // Analyze query context\n    const context = this.analyzeContext(query);\n\n    this.logger.debug('Analyzed query context', { context });\n\n    // Build enhanced criteria based on context\n    const enhancedCriteria = this.enhanceCriteria(criteria, context);\n\n    // Get candidate models\n    const candidates = this.catalog.filterModels(enhancedCriteria);\n\n    if (candidates.length === 0) {\n      throw new Error('No models match the context-aware criteria');\n    }\n\n    // Score models based on context fit\n    const scored = candidates.map((model) => ({\n      model,\n      score: this.calculateContextScore(model, context),\n    }));\n\n    // Sort by score\n    scored.sort((a, b) => b.score - a.score);\n\n    const best = scored[0];\n\n    return {\n      modelId: best.model.id,\n      model: best.model,\n      provider: best.model.provider,\n      expectedCost: this.estimateCost(best.model, context),\n      estimatedLatency: this.estimateLatency(best.model, context),\n      reason: `Context-aware selection: ${this.explainSelection(context)}`,\n      alternatives: scored.slice(1, 4).map((s) => ({\n        modelId: s.model.id,\n        score: s.score,\n        reason: `Context score: ${s.score.toFixed(2)}`,\n      })),\n      confidence: best.score,\n    };\n  }\n\n  /**\n   * Analyze query context\n   */\n  private analyzeContext(query: string): ContextAnalysis {\n    const hasCode = this.detectCode(query);\n    const hasImage = this.detectImageRequest(query);\n    const hasJson = this.detectJsonRequest(query);\n    const requiresFunctions = this.detectFunctionNeed(query);\n    const complexity = this.assessComplexity(query);\n    const estimatedTokens = this.estimateTokens(query);\n    const language = this.detectLanguage(query);\n\n    return {\n      hasCode,\n      hasImage,\n      hasJson,\n      requiresFunctions,\n      complexity,\n      estimatedTokens,\n      language,\n    };\n  }\n\n  /**\n   * Enhance criteria based on context\n   */\n  private enhanceCriteria(\n    criteria: SelectionCriteria,\n    context: ContextAnalysis,\n  ): SelectionCriteria {\n    const enhanced = { ...criteria };\n\n    // Add capability requirements based on context\n    if (!enhanced.capabilities) {\n      enhanced.capabilities = {};\n    }\n\n    if (context.hasImage) {\n      enhanced.capabilities.vision = true;\n    }\n\n    if (context.hasJson) {\n      enhanced.capabilities.jsonMode = true;\n    }\n\n    if (context.requiresFunctions) {\n      enhanced.capabilities.functionCalling = true;\n    }\n\n    // Code capability would be handled by other capabilities\n    // (not a standard OpenRouter capability)\n\n    // Adjust tier based on complexity\n    if (!enhanced.tier) {\n      if (context.complexity === 'simple') {\n        enhanced.tier = 'budget';\n      } else if (context.complexity === 'complex') {\n        enhanced.tier = 'premium';\n      } else {\n        enhanced.tier = 'balanced';\n      }\n    }\n\n    return enhanced;\n  }\n\n  /**\n   * Calculate context-based score for model\n   */\n  private calculateContextScore(model: any, context: ContextAnalysis): number {\n    let score = 0.5; // Base score\n\n    // Capability matches\n    if (context.hasImage && model.capabilities.vision) {\n      score += 0.2;\n    }\n    if (context.hasJson && model.capabilities.jsonMode) {\n      score += 0.1;\n    }\n    if (context.requiresFunctions && model.capabilities.functionCalling) {\n      score += 0.1;\n    }\n    if (context.hasCode && model.capabilities.code) {\n      score += 0.1;\n    }\n\n    // Complexity match\n    if (context.complexity === 'simple' && model.pricing.inputTokens < 1.0) {\n      score += 0.1; // Prefer cheaper models for simple tasks\n    } else if (context.complexity === 'complex' && model.contextWindow >= 32000) {\n      score += 0.1; // Prefer larger context for complex tasks\n    }\n\n    // Token capacity match\n    if (context.estimatedTokens < model.contextWindow * 0.5) {\n      score += 0.05; // Good token headroom\n    }\n\n    return Math.min(score, 1);\n  }\n\n  /**\n   * Detect if query involves code\n   */\n  private detectCode(query: string): boolean {\n    const codePatterns = [\n      /```/,\n      /function\\s+\\w+/,\n      /class\\s+\\w+/,\n      /import\\s+/,\n      /const\\s+\\w+\\s*=/,\n      /def\\s+\\w+/,\n      /write.*code/i,\n      /implement/i,\n      /refactor/i,\n    ];\n\n    return codePatterns.some((pattern) => pattern.test(query));\n  }\n\n  /**\n   * Detect if query involves images\n   */\n  private detectImageRequest(query: string): boolean {\n    const imagePatterns = [/image/i, /picture/i, /photo/i, /visual/i, /screenshot/i, /diagram/i];\n\n    return imagePatterns.some((pattern) => pattern.test(query));\n  }\n\n  /**\n   * Detect if query needs JSON output\n   */\n  private detectJsonRequest(query: string): boolean {\n    const jsonPatterns = [/json/i, /structured.*data/i, /format.*as.*object/i, /return.*object/i];\n\n    return jsonPatterns.some((pattern) => pattern.test(query));\n  }\n\n  /**\n   * Detect if query needs function calling\n   */\n  private detectFunctionNeed(query: string): boolean {\n    const functionPatterns = [/call.*function/i, /use.*tool/i, /execute.*action/i, /api.*call/i];\n\n    return functionPatterns.some((pattern) => pattern.test(query));\n  }\n\n  /**\n   * Assess query complexity\n   */\n  private assessComplexity(query: string): 'simple' | 'medium' | 'complex' {\n    const words = query.split(/\\s+/).length;\n    const sentences = query.split(/[.!?]+/).length;\n    const hasMultipleTopics = /and|also|additionally|furthermore/i.test(query);\n    const hasConstraints = /must|should|require|need|ensure/i.test(query);\n\n    if (words < 20 && sentences <= 2 && !hasMultipleTopics) {\n      return 'simple';\n    }\n\n    if (words > 100 || sentences > 5 || (hasMultipleTopics && hasConstraints)) {\n      return 'complex';\n    }\n\n    return 'medium';\n  }\n\n  /**\n   * Estimate tokens in query\n   */\n  private estimateTokens(query: string): number {\n    // Rough estimate: ~1 token per 4 characters\n    return Math.ceil(query.length / 4);\n  }\n\n  /**\n   * Detect language from query\n   */\n  private detectLanguage(query: string): string | undefined {\n    const languagePatterns: Record<string, RegExp> = {\n      python: /python/i,\n      javascript: /javascript|typescript|js|ts/i,\n      java: /\\bjava\\b/i,\n      csharp: /c#|csharp/i,\n      go: /\\bgo\\b|golang/i,\n      rust: /rust/i,\n      ruby: /ruby/i,\n    };\n\n    for (const [lang, pattern] of Object.entries(languagePatterns)) {\n      if (pattern.test(query)) {\n        return lang;\n      }\n    }\n\n    return undefined;\n  }\n\n  /**\n   * Estimate cost based on context\n   */\n  private estimateCost(model: any, context: ContextAnalysis): number {\n    const inputCost = (context.estimatedTokens / 1000000) * model.pricing.inputTokens;\n    const estimatedOutput =\n      context.complexity === 'complex' ? context.estimatedTokens * 2 : context.estimatedTokens;\n    const outputCost = (estimatedOutput / 1000000) * model.pricing.outputTokens;\n\n    return inputCost + outputCost;\n  }\n\n  /**\n   * Estimate latency based on context\n   */\n  private estimateLatency(model: any, context: ContextAnalysis): number {\n    const baseLatency = 1000; // Base 1 second\n    const complexityMultiplier =\n      context.complexity === 'simple' ? 0.5 : context.complexity === 'complex' ? 2 : 1;\n    const tokenMultiplier = Math.log10(context.estimatedTokens + 1) / 2;\n\n    return Math.round(baseLatency * complexityMultiplier * tokenMultiplier);\n  }\n\n  /**\n   * Explain selection reasoning\n   */\n  private explainSelection(context: ContextAnalysis): string {\n    const reasons: string[] = [];\n\n    if (context.hasCode) {\n      reasons.push('code generation');\n    }\n    if (context.hasImage) {\n      reasons.push('vision capability');\n    }\n    if (context.hasJson) {\n      reasons.push('structured output');\n    }\n    if (context.requiresFunctions) {\n      reasons.push('function calling');\n    }\n\n    reasons.push(`${context.complexity} complexity`);\n\n    return reasons.join(', ');\n  }\n}\n"]}