vibezcheck 0.5.3 → 0.5.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/ai-sdk/index.js +147 -24
- package/dist/ai-sdk/index.js.map +1 -1
- package/dist/ai-sdk/index.mjs +147 -24
- package/dist/ai-sdk/index.mjs.map +1 -1
- package/dist/ai-sdk/middleware.js +142 -23
- package/dist/ai-sdk/middleware.js.map +1 -1
- package/dist/ai-sdk/middleware.mjs +142 -23
- package/dist/ai-sdk/middleware.mjs.map +1 -1
- package/dist/billing/index.js +142 -23
- package/dist/billing/index.js.map +1 -1
- package/dist/billing/index.mjs +142 -23
- package/dist/billing/index.mjs.map +1 -1
- package/dist/cli/index.js +44 -22
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/index.mjs +44 -22
- package/dist/cli/index.mjs.map +1 -1
- package/dist/compat/stripe-meter.js +142 -23
- package/dist/compat/stripe-meter.js.map +1 -1
- package/dist/compat/stripe-meter.mjs +142 -23
- package/dist/compat/stripe-meter.mjs.map +1 -1
- package/dist/compat/stripe-provider.js +147 -24
- package/dist/compat/stripe-provider.js.map +1 -1
- package/dist/compat/stripe-provider.mjs +147 -24
- package/dist/compat/stripe-provider.mjs.map +1 -1
- package/dist/compat/token-meter.js +93 -10
- package/dist/compat/token-meter.js.map +1 -1
- package/dist/compat/token-meter.mjs +93 -10
- package/dist/compat/token-meter.mjs.map +1 -1
- package/dist/index.js +147 -24
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +147 -24
- package/dist/index.mjs.map +1 -1
- package/dist/meter/index.js +93 -10
- package/dist/meter/index.js.map +1 -1
- package/dist/meter/index.mjs +93 -10
- package/dist/meter/index.mjs.map +1 -1
- package/dist/pricing/index.js +32 -1
- package/dist/pricing/index.js.map +1 -1
- package/dist/pricing/index.mjs +32 -1
- package/dist/pricing/index.mjs.map +1 -1
- package/dist/react/index.d.mts +5 -3
- package/dist/react/index.d.ts +5 -3
- package/dist/react/index.js +301 -193
- package/dist/react/index.js.map +1 -1
- package/dist/react/index.mjs +301 -193
- package/dist/react/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/ai-sdk/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/ai-sdk/index.ts","../../src/types.ts","../../src/meter/client.ts","../../src/meter/batcher.ts","../../src/meter/extractors/openai.ts","../../src/meter/extractors/anthropic.ts","../../src/meter/extractors/gemini.ts","../../src/meter/extractors/generic.ts","../../src/meter/extractors/index.ts","../../src/pricing/table.ts","../../src/pricing/calculator.ts","../../src/customers/helpers.ts","../../src/meter/stream.ts","../../src/ai-sdk/with-billing.ts","../../src/ai-sdk/declarative.ts"],"sourcesContent":["export * from './with-billing';\r\nexport * from './declarative';\r\n","import type Stripe from 'stripe';\r\n\r\n/**\r\n * Known supported model identifiers with full IDE autocomplete\r\n */\r\nexport type SupportedOpenAIModel =\r\n | 'openai/gpt-4o'\r\n | 'openai/gpt-4o-mini'\r\n | 'openai/gpt-4.5-preview'\r\n | 'openai/gpt-4.1'\r\n | 'openai/gpt-4.1-nano'\r\n | 'openai/gpt-4-turbo'\r\n | 'openai/gpt-4'\r\n | 'openai/gpt-3.5-turbo'\r\n | 'openai/o1'\r\n | 'openai/o1-mini'\r\n | 'openai/o3'\r\n | 'openai/o3-mini'\r\n | 'openai/gpt-5'\r\n | 'openai/gpt-5-mini'\r\n | 'openai/gpt-5.6-sol'\r\n | 'openai/gpt-5.6-terra'\r\n | 'openai/gpt-5.6-luna'\r\n | 'openai/text-embedding-3-small'\r\n | 'openai/text-embedding-3-large'\r\n | 'gpt-4o'\r\n | 'gpt-4o-mini'\r\n | 'gpt-4.5-preview'\r\n | 'gpt-4.5'\r\n | 'gpt-4.1'\r\n | 'gpt-4.1-nano'\r\n | 'gpt-4-turbo'\r\n | 'gpt-4'\r\n | 'gpt-3.5-turbo'\r\n | 'o1'\r\n | 'o1-mini'\r\n | 'o3'\r\n | 'o3-mini'\r\n | 'gpt-5'\r\n | 'gpt-5-mini'\r\n | 'gpt-5.6-sol'\r\n | 'gpt-5.6-terra'\r\n | 'gpt-5.6-luna';\r\n\r\nexport type SupportedAnthropicModel =\r\n | 'anthropic/claude-3-7-sonnet'\r\n | 'anthropic/claude-3-5-sonnet'\r\n | 'anthropic/claude-3-5-haiku'\r\n | 'anthropic/claude-3-opus'\r\n | 'anthropic/claude-3-haiku'\r\n | 'anthropic/claude-2.1'\r\n | 'anthropic/claude-2.0'\r\n | 'anthropic/claude-opus-5'\r\n | 'anthropic/haiku-4.5'\r\n | 'claude-3-7-sonnet'\r\n | 'claude-3-5-sonnet'\r\n | 'claude-3-5-haiku'\r\n | 'claude-3-opus'\r\n | 'claude-3-haiku'\r\n | 'claude-2.1'\r\n | 'claude-2.0'\r\n | 'claude-opus-5'\r\n | 'haiku-4.5';\r\n\r\nexport type SupportedGoogleModel =\r\n | 'google/gemini-2.5-pro'\r\n | 'google/gemini-2.5-flash'\r\n | 'google/gemini-2.0-flash'\r\n | 'google/gemini-2.0-flash-lite'\r\n | 'google/gemini-2.0-pro'\r\n | 'google/gemini-1.5-pro'\r\n | 'google/gemini-1.5-flash'\r\n | 'google/gemini-1.5-flash-8b'\r\n | 'google/gemini-1.0-pro'\r\n | 'google/gemini-3.7-flash'\r\n | 'google/gemini-3.1-pro'\r\n | 'gemini-2.5-pro'\r\n | 'gemini-2.5-flash'\r\n | 'gemini-2.0-flash'\r\n | 'gemini-2.0-flash-lite'\r\n | 'gemini-2.0-pro'\r\n | 'gemini-1.5-pro'\r\n | 'gemini-1.5-flash'\r\n | 'gemini-1.5-flash-8b'\r\n | 'gemini-1.0-pro'\r\n | 'gemini-3.7-flash'\r\n | 'gemini-3.1-pro';\r\n\r\nexport type SupportedDeepSeekModel =\r\n | 'deepseek/deepseek-chat'\r\n | 'deepseek/deepseek-reasoner'\r\n | 'deepseek/deepseek-v3'\r\n | 'deepseek/deepseek-r1'\r\n | 'deepseek/deepseek-v4-pro'\r\n | 'deepseek-chat'\r\n | 'deepseek-reasoner'\r\n | 'deepseek-v3'\r\n | 'deepseek-r1'\r\n | 'deepseek-v4-pro';\r\n\r\nexport type SupportedXAIModel =\r\n | 'xai/grok-3'\r\n | 'xai/grok-3-mini'\r\n | 'xai/grok-2'\r\n | 'xai/grok-2-vision'\r\n | 'xai/grok-beta'\r\n | 'grok-3'\r\n | 'grok-3-mini'\r\n | 'grok-2'\r\n | 'grok-2-vision'\r\n | 'grok-beta';\r\n\r\nexport type SupportedMistralModel =\r\n | 'mistral/mistral-large-latest'\r\n | 'mistral/codestral-latest'\r\n | 'mistral/mistral-small-latest'\r\n | 'mistral/ministral-8b-latest'\r\n | 'mistral-large-latest'\r\n | 'codestral-latest'\r\n | 'mistral-small-latest'\r\n | 'ministral-8b-latest';\r\n\r\nexport type SupportedGroqModel =\r\n | 'groq/llama-3.3-70b-versatile'\r\n | 'groq/llama-3.1-70b-versatile'\r\n | 'groq/llama-3.1-8b-instant'\r\n | 'groq/deepseek-r1-distill-llama-70b'\r\n | 'llama-3.3-70b-versatile'\r\n | 'llama-3.1-70b-versatile'\r\n | 'llama-3.1-8b-instant'\r\n | 'deepseek-r1-distill-llama-70b';\r\n\r\nexport type SupportedCohereModel =\r\n | 'cohere/command-r-plus'\r\n | 'cohere/command-r'\r\n | 'command-r-plus'\r\n | 'command-r';\r\n\r\nexport type KnownModel =\r\n | SupportedOpenAIModel\r\n | SupportedAnthropicModel\r\n | SupportedGoogleModel\r\n | SupportedDeepSeekModel\r\n | SupportedXAIModel\r\n | SupportedMistralModel\r\n | SupportedGroqModel\r\n | SupportedCohereModel;\r\n\r\n/**\r\n * Union of all known model IDs with loose string fallback for custom / future models\r\n */\r\nexport type SupportedModel = KnownModel | (string & {});\r\n\r\n/**\r\n * Detailed token usage breakdown\r\n */\r\nexport interface TokenUsage {\r\n /** Input/Prompt tokens */\r\n inputTokens: number;\r\n /** Total output/completion tokens (including reasoning) */\r\n outputTokens: number;\r\n /** Total tokens (input + output) */\r\n totalTokens: number;\r\n /** Hidden reasoning / thinking tokens (e.g. o1/o3/GPT-5, Claude 3.7 Thinking, Gemini 3.7 Thoughts) */\r\n reasoningTokens?: number;\r\n /** Visible output tokens (outputTokens - reasoningTokens) */\r\n visibleOutputTokens?: number;\r\n /** Cached input tokens read from KV cache / prompt cache */\r\n cachedTokens?: number;\r\n /** Cache write / creation tokens */\r\n cacheWriteTokens?: number;\r\n}\r\n\r\n/**\r\n * Calculated inference cost breakdown\r\n */\r\nexport interface InferenceCost {\r\n /** Cost for standard input prompt tokens in USD */\r\n inputCostUSD: number;\r\n /** Cost for output completion tokens in USD */\r\n outputCostUSD: number;\r\n /** Cost for reasoning/thinking tokens in USD (if applicable) */\r\n reasoningCostUSD?: number;\r\n /** Savings from prompt caching in USD */\r\n cachedDiscountUSD?: number;\r\n /** Total computed base inference cost in USD */\r\n totalUSD: number;\r\n /** Wholesale provider cost in USD */\r\n wholesaleTotalUSD?: number;\r\n /** Amount billed to customer in USD */\r\n billedUSD?: number;\r\n /** Net developer profit in USD */\r\n profitUSD?: number;\r\n /** Retail price after developer markup (if markup applied) */\r\n retailUSD?: number;\r\n /** Currency (defaults to 'USD') */\r\n currency: string;\r\n}\r\n\r\n/**\r\n * Structured Customer Information with rich metadata, multi-tenancy & billing attributes\r\n */\r\nexport interface CustomerInfo {\r\n /** Internal user ID or Stripe customer ID ('cus_xxx', 'usr_123') */\r\n id?: string;\r\n /** Explicit user ID */\r\n userId?: string;\r\n /** Customer email */\r\n email?: string;\r\n /** Customer full name or business display name */\r\n name?: string;\r\n /** Phone number */\r\n phone?: string;\r\n /** Multi-tenant Organization or Company ID */\r\n orgId?: string;\r\n /** Organization / Company name */\r\n orgName?: string;\r\n /** Multi-tenant Organization ID alias */\r\n organizationId?: string;\r\n /** Team / Workspace identifier */\r\n teamId?: string;\r\n /** Workspace identifier alias */\r\n workspaceId?: string;\r\n /** User Role within organization (e.g. 'admin', 'member', 'owner') */\r\n role?: string;\r\n /** Subscription Plan name (e.g. 'free', 'starter', 'pro', 'enterprise') */\r\n plan?: string;\r\n /** Billing Tier (e.g. 'tier_1', 'growth', 'unlimited') */\r\n tier?: string;\r\n /** Billing currency (defaults to 'usd') */\r\n currency?: string;\r\n /** Current prepaid credit balance in USD */\r\n balanceUSD?: number;\r\n /** Flexible custom metadata (key-value attributes) */\r\n metadata?: Record<string, string | number | boolean | null>;\r\n /** Arbitrary extra developer fields */\r\n [key: string]: any;\r\n}\r\n\r\n/**\r\n * Customer identification parameter: can be a string ('cus_xxx' or 'user@example.com') or a rich structured object\r\n */\r\nexport type CustomerParam = string | CustomerInfo;\r\n\r\n/**\r\n * Full usage event emitted upon completion of an LLM call or stream\r\n */\r\nexport interface UsageEvent {\r\n /** Unique ID for the event */\r\n id?: string;\r\n /** Timestamp ISO string */\r\n timestamp: string;\r\n /** Model name (e.g. 'gpt-5.6-sol', 'claude-3-7-sonnet') */\r\n model: string;\r\n /** Provider (e.g. 'openai', 'anthropic', 'google', 'mistral', 'groq', 'deepseek', 'generic') */\r\n provider: string;\r\n /** Token breakdown */\r\n usage: TokenUsage;\r\n /** Computed cost */\r\n cost: InferenceCost;\r\n /** Customer ID (Stripe customer ID, internal userId, or anonymous) */\r\n customerId?: string;\r\n /** Optional customer email */\r\n customerEmail?: string;\r\n /** Full customer profile snapshot if provided */\r\n customer?: CustomerInfo;\r\n /** Custom developer metadata (e.g. userId, orgId, feature, session) */\r\n metadata?: Record<string, string | number | boolean>;\r\n}\r\n\r\n/**\r\n * Event emitted when a circuit breaker budget or token limit is reached\r\n */\r\nexport interface BudgetExceededEvent {\r\n reason: 'cost_per_call_exceeded' | 'total_budget_exceeded' | 'max_tokens_exceeded';\r\n limit: number;\r\n current: number;\r\n model: string;\r\n customerId?: string;\r\n message: string;\r\n}\r\n\r\n/**\r\n * Error thrown when an Agent Circuit Breaker trips\r\n */\r\nexport class VibezCircuitBreakerError extends Error {\r\n public readonly event: BudgetExceededEvent;\r\n\r\n constructor(event: BudgetExceededEvent) {\r\n super(event.message);\r\n this.name = 'VibezCircuitBreakerError';\r\n this.event = event;\r\n }\r\n}\r\n\r\n/**\r\n * Circuit Breaker / Budget Guardrail Configuration\r\n */\r\nexport interface CircuitBreakerOptions {\r\n /** Maximum allowed USD cost for a single generation or stream (default: 0.50) */\r\n maxCostPerCallUSD?: number;\r\n /** Cumulative budget limit for customer/session in USD (e.g. 5.00) */\r\n maxBudgetUSD?: number;\r\n /** Hard ceiling on total tokens per generation (e.g. 10000) */\r\n maxTokensPerCall?: number;\r\n /** Model to gracefully fall back to if budget limit is exceeded instead of hard erroring */\r\n fallbackModelOnBudget?: string;\r\n /** Callback fired when circuit breaker trips */\r\n onBudgetExceeded?: (event: BudgetExceededEvent) => void | Promise<void>;\r\n /** Whether to throw a VibezCircuitBreakerError if limit exceeded (default: false) */\r\n throwOnBudgetExceeded?: boolean;\r\n}\r\n\r\n/**\r\n * Pluggable Database / Storage Adapter Interface\r\n */\r\nexport interface DatabaseAdapter {\r\n name: string;\r\n save: (event: UsageEvent) => Promise<void> | void;\r\n getBalance?: (customerId: string) => Promise<number | undefined>;\r\n}\r\n\r\n/**\r\n * Pluggable Payment Provider Interface\r\n */\r\nexport interface PaymentProvider {\r\n name: string;\r\n charge?: (costUSD: number, event: UsageEvent) => Promise<void> | void;\r\n checkBalance?: (customerId: string) => Promise<{ ok: boolean; balanceUSD?: number }>;\r\n}\r\n\r\n/**\r\n * Billing Configuration (Universal Auto-Debit, Postpaid metered invoice vs Prepaid credit wallet, Pluggable Providers)\r\n */\r\nexport interface BillingConfig {\r\n /** 'postpaid' = Invoiced at month's end; 'prepaid' = Deducted from credit wallet, locks at $0 */\r\n mode?: 'postpaid' | 'prepaid';\r\n /** Available prepaid credit balance in USD */\r\n balanceUSD?: number;\r\n /** Action when balance is low: 'warn' logs/sends event, 'throw' throws CreditExhaustedError */\r\n onLowBalance?: 'warn' | 'throw';\r\n /** Payment Provider Gateway (default: 'stripe') */\r\n provider?: 'stripe' | 'polar' | 'lemonsqueezy' | 'paystack' | PaymentProvider;\r\n /** Custom charge handler for internal credit wallets / bespoke payment logic */\r\n charge?: (costUSD: number, event: UsageEvent) => Promise<void> | void;\r\n}\r\n\r\n/**\r\n * Profit Pricing & Markup Configuration\r\n */\r\nexport interface PricingConfig {\r\n /** Profit margin multiplier (e.g. 1.5 = Cost + 50% profit margin automatically added) */\r\n margin?: number;\r\n /** Minimum charge in USD for any single call (e.g. 0.01 = at least 1 cent) */\r\n minimumChargeUSD?: number;\r\n}\r\n\r\n/**\r\n * Inline Rate Card Configuration for 1-line custom/newly released model pricing\r\n */\r\nexport interface InlineRateConfig {\r\n /** Input tokens price per 1 Million tokens in USD */\r\n in: number;\r\n /** Output tokens price per 1 Million tokens in USD */\r\n out?: number;\r\n output?: number;\r\n /** Reasoning/thinking tokens price per 1 Million tokens in USD (optional) */\r\n reasoning?: number;\r\n /** Cached input tokens price per 1 Million tokens in USD (optional) */\r\n cached?: number;\r\n}\r\n\r\n/**\r\n * Non-LLM Tool execution metering options\r\n */\r\nexport interface ToolMeterOptions {\r\n /** Fixed cost in USD for this tool execution (e.g. 0.01 for search, 0.04 for image) */\r\n costUSD: number;\r\n /** Customer identifier to attribute tool cost to */\r\n customer?: CustomerParam;\r\n /** Additional metadata */\r\n metadata?: Record<string, string | number | boolean>;\r\n}\r\n\r\n/**\r\n * Configuration options for the VibezCheck Meter\r\n */\r\nexport interface MeterOptions extends CircuitBreakerOptions {\r\n /** Stripe API Key (sk_* or rk_*). If omitted, runs in local telemetry/free mode */\r\n apiKey?: string;\r\n /** Existing Stripe SDK instance (optional) */\r\n stripe?: Stripe;\r\n /** Default Stripe Meter Event Name (default: 'token-billing-tokens') */\r\n eventName?: string;\r\n /** Batching options to optimize Stripe API calls */\r\n batching?: {\r\n /** Max events per batch (default: 50) */\r\n maxBatchSize?: number;\r\n /** Flush interval in milliseconds (default: 50ms) */\r\n flushIntervalMs?: number;\r\n };\r\n /** Callback fired whenever usage is extracted (works with or without Stripe) */\r\n onUsage?: (event: UsageEvent) => void | Promise<void>;\r\n /** Error handler callback */\r\n onError?: (error: Error, events: UsageEvent[]) => void;\r\n /** Markup multiplier for retail price calculations (e.g. 1.3 for 30% profit) */\r\n markupMultiplier?: number;\r\n /** Enable debug console logging (default: false) */\r\n debug?: boolean;\r\n}\r\n\r\n/**\r\n * Stream wrap options\r\n */\r\nexport interface StreamWrapOptions extends CircuitBreakerOptions {\r\n /** Customer identifier or email or object */\r\n customer?: CustomerParam;\r\n /** Direct customer ID string */\r\n customerId?: string;\r\n /** Model override if not automatically detectable */\r\n model?: string;\r\n /** Provider override if not automatically detectable */\r\n provider?: string;\r\n /** Billing mode configuration (postpaid vs prepaid) */\r\n billing?: BillingConfig;\r\n /** Profit margin & minimum charge configuration */\r\n pricing?: PricingConfig;\r\n /** 1-line inline pricing rate card */\r\n rate?: InlineRateConfig;\r\n /** Whether to capture tokens if the client aborts or closes tab mid-stream (default: true) */\r\n captureOnAbort?: boolean;\r\n /** Execution runtime environment (default: 'auto') */\r\n runtime?: 'auto' | 'serverless' | 'edge' | 'node';\r\n /** Custom metadata attached to the usage event */\r\n metadata?: Record<string, string | number | boolean>;\r\n /** Custom usage callback for this specific stream */\r\n onUsage?: (event: UsageEvent) => void | Promise<void>;\r\n}\r\n\r\n/**\r\n * Direct usage recording options\r\n */\r\nexport interface RecordUsageOptions {\r\n model: string;\r\n provider?: string;\r\n inputTokens: number;\r\n outputTokens: number;\r\n reasoningTokens?: number;\r\n cachedTokens?: number;\r\n customer?: CustomerParam;\r\n customerId?: string;\r\n metadata?: Record<string, string | number | boolean>;\r\n}\r\n\r\n/**\r\n * Model Pricing Rates (per 1 Million Tokens in USD)\r\n */\r\nexport interface ModelPricingRates {\r\n inputPer1M: number;\r\n outputPer1M: number;\r\n cachedInputPer1M?: number;\r\n reasoningPer1M?: number;\r\n cacheWritePer1M?: number;\r\n currency?: string;\r\n}\r\n\r\n/**\r\n * Aggregated Usage Summary\r\n */\r\nexport interface UsageSummary {\r\n totalRequests: number;\r\n totalTokens: number;\r\n totalInputTokens: number;\r\n totalOutputTokens: number;\r\n totalReasoningTokens: number;\r\n totalCostUSD: number;\r\n byModel: Record<\r\n string,\r\n {\r\n requests: number;\r\n tokens: number;\r\n costUSD: number;\r\n }\r\n >;\r\n}\r\n","import Stripe from 'stripe';\r\nimport type {\r\n MeterOptions,\r\n StreamWrapOptions,\r\n RecordUsageOptions,\r\n UsageEvent,\r\n UsageSummary,\r\n CustomerParam,\r\n} from '../types';\r\nimport { MeterBatcher } from './batcher';\r\nimport { detectAndExtractUsage } from './extractors';\r\nimport { calculateUsageCost } from '../pricing/calculator';\r\nimport { wrapUniversalStream } from './stream';\r\nimport { normalizeCustomer } from '../customers/helpers';\r\n\r\nexport class VibezMeter {\r\n private batcher: MeterBatcher;\r\n private stripeClient?: Stripe;\r\n private markupMultiplier?: number;\r\n\r\n constructor(options: MeterOptions = {}) {\r\n this.markupMultiplier = options.markupMultiplier;\r\n\r\n // Initialize Stripe client if apiKey or stripe instance is provided\r\n if (options.stripe) {\r\n this.stripeClient = options.stripe;\r\n } else if (options.apiKey || process.env.STRIPE_SECRET_KEY) {\r\n const key = options.apiKey || process.env.STRIPE_SECRET_KEY!;\r\n this.stripeClient = new Stripe(key, {\r\n appInfo: {\r\n name: 'vibezcheck',\r\n version: '0.5.3',\r\n url: 'https://vibezcheck.xyz',\r\n },\r\n });\r\n }\r\n\r\n this.batcher = new MeterBatcher({\r\n ...options,\r\n stripe: this.stripeClient,\r\n });\r\n }\r\n\r\n /**\r\n * Track token usage from a non-streaming response object (OpenAI, Anthropic, Gemini, etc.)\r\n */\r\n public trackUsage(\r\n response: any,\r\n options: {\r\n customer?: CustomerParam;\r\n customerId?: string;\r\n model?: string;\r\n provider?: string;\r\n metadata?: Record<string, string | number | boolean>;\r\n } = {}\r\n ): UsageEvent | null {\r\n const extracted = detectAndExtractUsage(response, options.model, options.provider);\r\n if (!extracted) {\r\n return null;\r\n }\r\n\r\n const model = options.model || extracted.model;\r\n const cost = calculateUsageCost(model, extracted.usage, this.markupMultiplier);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const mergedMeta = {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n };\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model,\r\n provider: extracted.provider,\r\n usage: extracted.usage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: mergedMeta,\r\n };\r\n\r\n this.batcher.enqueue(event);\r\n return event;\r\n }\r\n\r\n /**\r\n * Wrap any LLM stream (OpenAI, Anthropic, Gemini) with zero added latency\r\n */\r\n public wrapStream<T>(stream: T, options: StreamWrapOptions = {}): T {\r\n return wrapUniversalStream(stream, options, (event) => {\r\n this.batcher.enqueue(event);\r\n });\r\n }\r\n\r\n /**\r\n * Directly record token usage manually\r\n */\r\n public recordUsage(options: RecordUsageOptions & { customer?: CustomerParam }): UsageEvent {\r\n const inputTokens = options.inputTokens ?? 0;\r\n const outputTokens = options.outputTokens ?? 0;\r\n const reasoningTokens = options.reasoningTokens;\r\n const cachedTokens = options.cachedTokens;\r\n\r\n const usage = {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens,\r\n visibleOutputTokens:\r\n reasoningTokens !== undefined ? Math.max(0, outputTokens - reasoningTokens) : outputTokens,\r\n cachedTokens,\r\n };\r\n\r\n const cost = calculateUsageCost(options.model, usage, this.markupMultiplier);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const mergedMeta = {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n };\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: options.model,\r\n provider: options.provider || 'custom',\r\n usage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: mergedMeta,\r\n };\r\n\r\n this.batcher.enqueue(event);\r\n return event;\r\n }\r\n\r\n /**\r\n * Flush pending events to Stripe (vital for Serverless & Edge environments)\r\n */\r\n public async flush(): Promise<void> {\r\n await this.batcher.flush();\r\n }\r\n\r\n /**\r\n * Get in-memory aggregated usage statistics\r\n */\r\n public getUsageSummary(): UsageSummary {\r\n return this.batcher.getSummary();\r\n }\r\n\r\n /**\r\n * Reset in-memory ledger\r\n */\r\n public resetSummary(): void {\r\n this.batcher.resetLedger();\r\n }\r\n}\r\n\r\n/**\r\n * Factory function to create a VibezMeter instance\r\n */\r\nexport function createMeter(options: MeterOptions = {}): VibezMeter {\r\n return new VibezMeter(options);\r\n}\r\n","import type Stripe from 'stripe';\r\nimport type { UsageEvent, UsageSummary, MeterOptions } from '../types';\r\n\r\nexport class MeterBatcher {\r\n private queue: UsageEvent[] = [];\r\n private timer: NodeJS.Timeout | null = null;\r\n private isFlushing: boolean = false;\r\n private readonly maxBatchSize: number;\r\n private readonly flushIntervalMs: number;\r\n private readonly stripeClient?: Stripe;\r\n private readonly eventName: string;\r\n private readonly onUsageCallback?: (event: UsageEvent) => void | Promise<void>;\r\n private readonly onErrorCallback?: (error: Error, events: UsageEvent[]) => void;\r\n private readonly debug: boolean;\r\n\r\n // In-memory ledger for local stats\r\n private totalRequests = 0;\r\n private totalTokens = 0;\r\n private totalInputTokens = 0;\r\n private totalOutputTokens = 0;\r\n private totalReasoningTokens = 0;\r\n private totalCostUSD = 0;\r\n private byModel: Record<string, { requests: number; tokens: number; costUSD: number }> = {};\r\n\r\n constructor(options: MeterOptions = {}) {\r\n this.stripeClient = options.stripe;\r\n this.eventName = options.eventName || 'token-billing-tokens';\r\n this.maxBatchSize = options.batching?.maxBatchSize ?? 50;\r\n this.flushIntervalMs = options.batching?.flushIntervalMs ?? 50;\r\n this.onUsageCallback = options.onUsage;\r\n this.onErrorCallback = options.onError;\r\n this.debug = options.debug ?? false;\r\n }\r\n\r\n /**\r\n * Enqueue a usage event for batch dispatching\r\n */\r\n public enqueue(event: UsageEvent): void {\r\n // 1. Update in-memory local ledger\r\n this.recordInLedger(event);\r\n\r\n // 2. Fire onUsage hook immediately\r\n if (this.onUsageCallback) {\r\n try {\r\n const res = this.onUsageCallback(event);\r\n if (res instanceof Promise) {\r\n res.catch((err) => {\r\n if (this.debug) console.error('[vibezcheck] Error in onUsage callback:', err);\r\n });\r\n }\r\n } catch (err) {\r\n if (this.debug) console.error('[vibezcheck] Error in onUsage callback:', err);\r\n }\r\n }\r\n\r\n // 3. If no Stripe client is configured, we're done (local mode)\r\n if (!this.stripeClient) {\r\n if (this.debug) {\r\n console.log(\r\n `[vibezcheck:local] 📊 ${event.model} | Tokens: ${event.usage.totalTokens} | Cost: $${event.cost.totalUSD.toFixed(6)}`\r\n );\r\n }\r\n return;\r\n }\r\n\r\n // 4. Queue for Stripe dispatch\r\n this.queue.push(event);\r\n\r\n if (this.queue.length >= this.maxBatchSize) {\r\n this.flush().catch((err) => {\r\n if (this.debug) console.error('[vibezcheck] Batch flush error:', err);\r\n });\r\n } else if (!this.timer) {\r\n this.timer = setTimeout(() => {\r\n this.timer = null;\r\n this.flush().catch((err) => {\r\n if (this.debug) console.error('[vibezcheck] Debounce flush error:', err);\r\n });\r\n }, this.flushIntervalMs);\r\n }\r\n }\r\n\r\n /**\r\n * Immediately flush all queued events to Stripe\r\n */\r\n public async flush(): Promise<void> {\r\n if (this.timer) {\r\n clearTimeout(this.timer);\r\n this.timer = null;\r\n }\r\n\r\n if (this.queue.length === 0 || !this.stripeClient || this.isFlushing) {\r\n return;\r\n }\r\n\r\n this.isFlushing = true;\r\n const eventsToSend = [...this.queue];\r\n this.queue = [];\r\n\r\n try {\r\n await this.sendEventsToStripe(eventsToSend);\r\n } catch (error) {\r\n const err = error instanceof Error ? error : new Error(String(error));\r\n if (this.debug) {\r\n console.error('[vibezcheck] Failed to send meter events to Stripe:', err);\r\n }\r\n if (this.onErrorCallback) {\r\n this.onErrorCallback(err, eventsToSend);\r\n }\r\n } finally {\r\n this.isFlushing = false;\r\n // If new items were queued while flushing, trigger another flush\r\n if (this.queue.length > 0) {\r\n this.flush().catch(() => {});\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Sends events to Stripe Billing Meter Events API\r\n */\r\n private async sendEventsToStripe(events: UsageEvent[]): Promise<void> {\r\n if (!this.stripeClient) return;\r\n\r\n for (const event of events) {\r\n const customerId = event.customerId;\r\n if (!customerId) {\r\n // Skip events without customer attribution for Stripe billing\r\n continue;\r\n }\r\n\r\n const timestamp = event.timestamp || new Date().toISOString();\r\n const model = `${event.provider}/${event.model}`;\r\n\r\n // 1. Send Input Tokens Meter Event\r\n if (event.usage.inputTokens > 0) {\r\n try {\r\n await this.stripeClient.v2.billing.meterEvents.create({\r\n event_name: this.eventName,\r\n timestamp,\r\n payload: {\r\n stripe_customer_id: customerId,\r\n value: event.usage.inputTokens.toString(),\r\n model,\r\n token_type: 'input',\r\n cached_tokens: (event.usage.cachedTokens ?? 0).toString(),\r\n ...(event.metadata ? (event.metadata as any) : {}),\r\n },\r\n });\r\n } catch (e) {\r\n if (this.debug) console.warn('[vibezcheck] Input meter event error:', e);\r\n }\r\n }\r\n\r\n // 2. Send Output Tokens Meter Event\r\n if (event.usage.outputTokens > 0) {\r\n try {\r\n await this.stripeClient.v2.billing.meterEvents.create({\r\n event_name: this.eventName,\r\n timestamp,\r\n payload: {\r\n stripe_customer_id: customerId,\r\n value: event.usage.outputTokens.toString(),\r\n model,\r\n token_type: 'output',\r\n reasoning_tokens: (event.usage.reasoningTokens ?? 0).toString(),\r\n visible_tokens: (event.usage.visibleOutputTokens ?? event.usage.outputTokens).toString(),\r\n ...(event.metadata ? (event.metadata as any) : {}),\r\n },\r\n });\r\n } catch (e) {\r\n if (this.debug) console.warn('[vibezcheck] Output meter event error:', e);\r\n }\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Updates internal in-memory ledger\r\n */\r\n private recordInLedger(event: UsageEvent): void {\r\n this.totalRequests += 1;\r\n this.totalTokens += event.usage.totalTokens;\r\n this.totalInputTokens += event.usage.inputTokens;\r\n this.totalOutputTokens += event.usage.outputTokens;\r\n this.totalReasoningTokens += event.usage.reasoningTokens ?? 0;\r\n this.totalCostUSD += event.cost.totalUSD;\r\n\r\n const modelKey = event.model;\r\n if (!this.byModel[modelKey]) {\r\n this.byModel[modelKey] = { requests: 0, tokens: 0, costUSD: 0 };\r\n }\r\n this.byModel[modelKey].requests += 1;\r\n this.byModel[modelKey].tokens += event.usage.totalTokens;\r\n this.byModel[modelKey].costUSD += event.cost.totalUSD;\r\n }\r\n\r\n /**\r\n * Get in-memory usage summary\r\n */\r\n public getSummary(): UsageSummary {\r\n return {\r\n totalRequests: this.totalRequests,\r\n totalTokens: this.totalTokens,\r\n totalInputTokens: this.totalInputTokens,\r\n totalOutputTokens: this.totalOutputTokens,\r\n totalReasoningTokens: this.totalReasoningTokens,\r\n totalCostUSD: Number(this.totalCostUSD.toFixed(6)),\r\n byModel: { ...this.byModel },\r\n };\r\n }\r\n\r\n /**\r\n * Reset in-memory ledger\r\n */\r\n public resetLedger(): void {\r\n this.totalRequests = 0;\r\n this.totalTokens = 0;\r\n this.totalInputTokens = 0;\r\n this.totalOutputTokens = 0;\r\n this.totalReasoningTokens = 0;\r\n this.totalCostUSD = 0;\r\n this.byModel = {};\r\n }\r\n}\r\n","import type { TokenUsage } from '../../types';\r\n\r\nexport interface ExtractedUsage {\r\n model: string;\r\n provider: string;\r\n usage: TokenUsage;\r\n}\r\n\r\n/**\r\n * Extracts token usage from OpenAI synchronous responses (ChatCompletion, Responses, Embeddings)\r\n */\r\nexport function extractOpenAIResponseUsage(response: any): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // 1. Standard OpenAI ChatCompletion\r\n if ('choices' in response && 'usage' in response && response.usage) {\r\n const rawUsage = response.usage;\r\n const model = response.model || 'gpt-4o';\r\n\r\n const inputTokens = rawUsage.prompt_tokens ?? 0;\r\n const outputTokens = rawUsage.completion_tokens ?? 0;\r\n const reasoningTokens = rawUsage.completion_tokens_details?.reasoning_tokens ?? 0;\r\n const cachedTokens = rawUsage.prompt_tokens_details?.cached_tokens ?? 0;\r\n\r\n return {\r\n model,\r\n provider: 'openai',\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n // 2. OpenAI Embeddings Response\r\n if ('data' in response && 'usage' in response && response.usage && 'model' in response) {\r\n const rawUsage = response.usage;\r\n const inputTokens = rawUsage.prompt_tokens ?? 0;\r\n\r\n return {\r\n model: response.model || 'text-embedding-3-small',\r\n provider: 'openai',\r\n usage: {\r\n inputTokens,\r\n outputTokens: 0,\r\n totalTokens: inputTokens,\r\n },\r\n };\r\n }\r\n\r\n // 3. OpenAI Responses API (New standard)\r\n if ('status' in response && 'usage' in response && response.usage) {\r\n const rawUsage = response.usage;\r\n const model = response.model || 'gpt-5.6-sol';\r\n\r\n const inputTokens = rawUsage.input_tokens ?? rawUsage.prompt_tokens ?? 0;\r\n const outputTokens = rawUsage.output_tokens ?? rawUsage.completion_tokens ?? 0;\r\n const reasoningTokens =\r\n rawUsage.output_token_details?.reasoning_tokens ??\r\n rawUsage.completion_tokens_details?.reasoning_tokens ??\r\n 0;\r\n const cachedTokens =\r\n rawUsage.input_token_details?.cached_tokens ??\r\n rawUsage.prompt_tokens_details?.cached_tokens ??\r\n 0;\r\n\r\n return {\r\n model,\r\n provider: 'openai',\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n return null;\r\n}\r\n\r\n/**\r\n * Extracts token usage from an individual OpenAI stream chunk or stream accumulator\r\n */\r\nexport function inspectOpenAIStreamChunk(chunk: any): {\r\n model?: string;\r\n usage?: TokenUsage;\r\n} {\r\n if (!chunk || typeof chunk !== 'object') return {};\r\n\r\n const model = chunk.model;\r\n\r\n // Final chunk with usage object (when stream_options: { include_usage: true }, or Groq / DeepSeek / Mistral stream ending)\r\n const rawUsage = chunk.usage || chunk.token_usage || chunk.x_groq?.usage || chunk.usageMetadata;\r\n if (rawUsage) {\r\n const inputTokens =\r\n rawUsage.prompt_tokens ??\r\n rawUsage.input_tokens ??\r\n rawUsage.promptTokens ??\r\n rawUsage.inputTokens ??\r\n rawUsage.promptTokenCount ??\r\n 0;\r\n const outputTokens =\r\n rawUsage.completion_tokens ??\r\n rawUsage.output_tokens ??\r\n rawUsage.completionTokens ??\r\n rawUsage.outputTokens ??\r\n rawUsage.candidatesTokenCount ??\r\n 0;\r\n const reasoningTokens =\r\n rawUsage.completion_tokens_details?.reasoning_tokens ??\r\n rawUsage.output_token_details?.reasoning_tokens ??\r\n rawUsage.reasoning_tokens ??\r\n rawUsage.reasoningTokens ??\r\n rawUsage.thoughtsTokenCount ??\r\n 0;\r\n const cachedTokens =\r\n rawUsage.prompt_tokens_details?.cached_tokens ??\r\n rawUsage.input_token_details?.cached_tokens ??\r\n rawUsage.prompt_cache_hit_tokens ??\r\n rawUsage.cached_tokens ??\r\n rawUsage.cachedTokens ??\r\n rawUsage.cachedContentTokenCount ??\r\n 0;\r\n\r\n return {\r\n model,\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n // Response API stream event (response.completed or response.done)\r\n if (chunk.type === 'response.completed' || chunk.type === 'response.done') {\r\n if (chunk.response?.usage) {\r\n const rawUsage = chunk.response.usage;\r\n const inputTokens = rawUsage.input_tokens ?? 0;\r\n const outputTokens = rawUsage.output_tokens ?? 0;\r\n const reasoningTokens = rawUsage.output_token_details?.reasoning_tokens ?? 0;\r\n const cachedTokens = rawUsage.input_token_details?.cached_tokens ?? 0;\r\n\r\n return {\r\n model: chunk.response.model || model,\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n }\r\n\r\n return { model };\r\n}\r\n","import type { TokenUsage } from '../../types';\r\nimport type { ExtractedUsage } from './openai';\r\n\r\n/**\r\n * Extracts token usage from Anthropic synchronous responses\r\n */\r\nexport function extractAnthropicResponseUsage(response: any): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // Anthropic Message response has type: 'message' or role: 'assistant' with usage\r\n if (response.type === 'message' || ('content' in response && 'usage' in response)) {\r\n const rawUsage = response.usage || {};\r\n const model = response.model || 'claude-3-7-sonnet';\r\n\r\n const inputTokens = rawUsage.input_tokens ?? 0;\r\n const outputTokens = rawUsage.output_tokens ?? 0;\r\n const cachedTokens = rawUsage.cache_read_input_tokens ?? 0;\r\n const cacheWriteTokens = rawUsage.cache_creation_input_tokens ?? 0;\r\n\r\n // Check content blocks for thinking/reasoning tokens count or thinking blocks\r\n let reasoningTokens: number | undefined = undefined;\r\n if (Array.isArray(response.content)) {\r\n const thinkingBlocks = response.content.filter((b: any) => b.type === 'thinking');\r\n if (thinkingBlocks.length > 0) {\r\n // Approximate or extract explicit thinking tokens if present in metadata\r\n reasoningTokens = (rawUsage as any).thinking_tokens ?? undefined;\r\n }\r\n }\r\n\r\n return {\r\n model,\r\n provider: 'anthropic',\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens,\r\n visibleOutputTokens:\r\n reasoningTokens !== undefined ? Math.max(0, outputTokens - reasoningTokens) : outputTokens,\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n cacheWriteTokens: cacheWriteTokens > 0 ? cacheWriteTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n return null;\r\n}\r\n\r\n/**\r\n * Accumulates stream events across an Anthropic raw message stream\r\n */\r\nexport class AnthropicStreamAccumulator {\r\n private model: string = 'claude-3-7-sonnet';\r\n private inputTokens: number = 0;\r\n private outputTokens: number = 0;\r\n private cachedTokens: number = 0;\r\n private cacheWriteTokens: number = 0;\r\n private reasoningTokens: number = 0;\r\n\r\n processEvent(event: any): void {\r\n if (!event || typeof event !== 'object') return;\r\n\r\n // 1. message_start (contains model and initial input usage)\r\n if (event.type === 'message_start' && event.message) {\r\n if (event.message.model) {\r\n this.model = event.message.model;\r\n }\r\n if (event.message.usage) {\r\n this.inputTokens = event.message.usage.input_tokens ?? 0;\r\n this.cachedTokens = event.message.usage.cache_read_input_tokens ?? 0;\r\n this.cacheWriteTokens = event.message.usage.cache_creation_input_tokens ?? 0;\r\n }\r\n }\r\n\r\n // 2. message_delta (contains final output usage)\r\n if (event.type === 'message_delta' && event.usage) {\r\n this.outputTokens = event.usage.output_tokens ?? 0;\r\n if (event.usage.thinking_tokens) {\r\n this.reasoningTokens = event.usage.thinking_tokens;\r\n }\r\n }\r\n\r\n // 3. content_block_start / content_block_delta for thinking blocks\r\n if (event.type === 'content_block_start' && event.content_block?.type === 'thinking') {\r\n // thinking block detected\r\n }\r\n }\r\n\r\n getUsage(): ExtractedUsage {\r\n return {\r\n model: this.model,\r\n provider: 'anthropic',\r\n usage: {\r\n inputTokens: this.inputTokens,\r\n outputTokens: this.outputTokens,\r\n totalTokens: this.inputTokens + this.outputTokens,\r\n reasoningTokens: this.reasoningTokens > 0 ? this.reasoningTokens : undefined,\r\n visibleOutputTokens:\r\n this.reasoningTokens > 0\r\n ? Math.max(0, this.outputTokens - this.reasoningTokens)\r\n : this.outputTokens,\r\n cachedTokens: this.cachedTokens > 0 ? this.cachedTokens : undefined,\r\n cacheWriteTokens: this.cacheWriteTokens > 0 ? this.cacheWriteTokens : undefined,\r\n },\r\n };\r\n }\r\n}\r\n","import type { TokenUsage } from '../../types';\r\nimport type { ExtractedUsage } from './openai';\r\n\r\n/**\r\n * Extracts token usage from Google Gemini API response or chunk\r\n */\r\nexport function extractGeminiResponseUsage(\r\n response: any,\r\n fallbackModel: string = 'gemini-3.7-flash'\r\n): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // Gemini returns usageMetadata on response or GenerateContentResult\r\n const usageMetadata = response.usageMetadata || response.response?.usageMetadata;\r\n\r\n if (usageMetadata) {\r\n const inputTokens = usageMetadata.promptTokenCount ?? 0;\r\n const baseOutputTokens = usageMetadata.candidatesTokenCount ?? 0;\r\n const thoughtsTokenCount =\r\n usageMetadata.thoughtsTokenCount ?? (usageMetadata as any).reasoningTokenCount ?? 0;\r\n const cachedTokens = usageMetadata.cachedContentTokenCount ?? 0;\r\n\r\n const totalOutput = baseOutputTokens + thoughtsTokenCount;\r\n const model = response.model || response.response?.model || fallbackModel;\r\n\r\n return {\r\n model,\r\n provider: 'google',\r\n usage: {\r\n inputTokens,\r\n outputTokens: totalOutput,\r\n totalTokens: inputTokens + totalOutput,\r\n reasoningTokens: thoughtsTokenCount > 0 ? thoughtsTokenCount : undefined,\r\n visibleOutputTokens: baseOutputTokens,\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n return null;\r\n}\r\n","import type { TokenUsage } from '../../types';\r\nimport type { ExtractedUsage } from './openai';\r\n\r\n/**\r\n * Extracts token usage from generic LLM provider objects (DeepSeek, Groq, Mistral, Ollama, Cohere, Together)\r\n */\r\nexport function extractGenericResponseUsage(\r\n response: any,\r\n fallbackModel: string = 'generic-llm',\r\n fallbackProvider: string = 'generic'\r\n): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // Check common usage property locations\r\n const usage = response.usage || response.token_usage || response.usageMetadata;\r\n\r\n if (usage) {\r\n const inputTokens =\r\n usage.prompt_tokens ??\r\n usage.input_tokens ??\r\n usage.promptTokenCount ??\r\n usage.prompt_eval_count ??\r\n 0;\r\n const outputTokens =\r\n usage.completion_tokens ??\r\n usage.output_tokens ??\r\n usage.candidatesTokenCount ??\r\n usage.eval_count ??\r\n 0;\r\n const reasoningTokens =\r\n usage.reasoning_tokens ??\r\n usage.thoughtsTokenCount ??\r\n usage.completion_tokens_details?.reasoning_tokens ??\r\n 0;\r\n const cachedTokens =\r\n usage.prompt_tokens_details?.cached_tokens ??\r\n usage.cached_tokens ??\r\n usage.cachedContentTokenCount ??\r\n 0;\r\n\r\n const model = response.model || fallbackModel;\r\n const provider = response.provider || fallbackProvider;\r\n\r\n return {\r\n model,\r\n provider,\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n return null;\r\n}\r\n","import type { ExtractedUsage } from './openai';\r\nimport { extractOpenAIResponseUsage } from './openai';\r\nimport { extractAnthropicResponseUsage } from './anthropic';\r\nimport { extractGeminiResponseUsage } from './gemini';\r\nimport { extractGenericResponseUsage } from './generic';\r\n\r\nexport * from './openai';\r\nexport * from './anthropic';\r\nexport * from './gemini';\r\nexport * from './generic';\r\n\r\n/**\r\n * Universal polymorphic response detector\r\n */\r\nexport function detectAndExtractUsage(\r\n response: any,\r\n fallbackModel?: string,\r\n fallbackProvider?: string\r\n): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // 1. Try OpenAI\r\n const openaiResult = extractOpenAIResponseUsage(response);\r\n if (openaiResult) return openaiResult;\r\n\r\n // 2. Try Anthropic\r\n const anthropicResult = extractAnthropicResponseUsage(response);\r\n if (anthropicResult) return anthropicResult;\r\n\r\n // 3. Try Gemini\r\n const geminiResult = extractGeminiResponseUsage(response, fallbackModel);\r\n if (geminiResult) return geminiResult;\r\n\r\n // 4. Try Generic\r\n const genericResult = extractGenericResponseUsage(response, fallbackModel, fallbackProvider);\r\n if (genericResult) return genericResult;\r\n\r\n return null;\r\n}\r\n","import type { ModelPricingRates } from '../types';\r\n\r\n/**\r\n * Built-in Registry of Model Pricing (USD per 1 Million Tokens)\r\n * Sourced from official 2026 provider pricing tables.\r\n */\r\nexport const MODEL_PRICING_TABLE: Record<string, ModelPricingRates> = {\r\n // --- OpenAI (Modern & Reasoning) ---\r\n 'gpt-5.6-sol': { inputPer1M: 4.0, outputPer1M: 20.0, cachedInputPer1M: 0.4 },\r\n 'gpt-5.6-terra': { inputPer1M: 2.0, outputPer1M: 12.0, cachedInputPer1M: 0.2 },\r\n 'gpt-5.6-luna': { inputPer1M: 0.2, outputPer1M: 1.2, cachedInputPer1M: 0.02 },\r\n 'gpt-5': { inputPer1M: 4.0, outputPer1M: 20.0, cachedInputPer1M: 0.4 },\r\n 'gpt-5-mini': { inputPer1M: 0.2, outputPer1M: 1.2, cachedInputPer1M: 0.02 },\r\n 'o1': { inputPer1M: 15.0, outputPer1M: 60.0, cachedInputPer1M: 7.5 },\r\n 'o1-mini': { inputPer1M: 1.1, outputPer1M: 4.4, cachedInputPer1M: 0.55 },\r\n 'o3': { inputPer1M: 15.0, outputPer1M: 60.0, cachedInputPer1M: 7.5 },\r\n 'o3-mini': { inputPer1M: 1.1, outputPer1M: 4.4, cachedInputPer1M: 0.55 },\r\n 'gpt-4o': { inputPer1M: 2.5, outputPer1M: 10.0, cachedInputPer1M: 1.25 },\r\n 'gpt-4o-mini': { inputPer1M: 0.15, outputPer1M: 0.6, cachedInputPer1M: 0.075 },\r\n 'gpt-4.5': { inputPer1M: 75.0, outputPer1M: 150.0, cachedInputPer1M: 37.5 },\r\n 'gpt-4.5-preview': { inputPer1M: 75.0, outputPer1M: 150.0, cachedInputPer1M: 37.5 },\r\n 'chatgpt-4o-latest': { inputPer1M: 5.0, outputPer1M: 15.0 },\r\n 'gpt-4.1': { inputPer1M: 2.0, outputPer1M: 8.0, cachedInputPer1M: 1.0 },\r\n 'gpt-4.1-nano': { inputPer1M: 0.1, outputPer1M: 0.4, cachedInputPer1M: 0.05 },\r\n\r\n // --- OpenAI (Legacy & Backward Compatibility) ---\r\n 'gpt-4-turbo': { inputPer1M: 10.0, outputPer1M: 30.0, cachedInputPer1M: 5.0 },\r\n 'gpt-4-turbo-preview': { inputPer1M: 10.0, outputPer1M: 30.0, cachedInputPer1M: 5.0 },\r\n 'gpt-4': { inputPer1M: 30.0, outputPer1M: 60.0 },\r\n 'gpt-4-32k': { inputPer1M: 60.0, outputPer1M: 120.0 },\r\n 'gpt-3.5-turbo': { inputPer1M: 0.5, outputPer1M: 1.5 },\r\n 'gpt-3.5-turbo-16k': { inputPer1M: 3.0, outputPer1M: 4.0 },\r\n 'text-embedding-3-small': { inputPer1M: 0.02, outputPer1M: 0.0 },\r\n 'text-embedding-3-large': { inputPer1M: 0.13, outputPer1M: 0.0 },\r\n 'text-embedding-ada-002': { inputPer1M: 0.10, outputPer1M: 0.0 },\r\n\r\n // --- Anthropic (Modern & Extended Thinking) ---\r\n 'claude-3-7-sonnet': { inputPer1M: 0.59, outputPer1M: 2.93, cachedInputPer1M: 0.3 },\r\n 'claude-sonnet-5': { inputPer1M: 2.0, outputPer1M: 10.0, cachedInputPer1M: 0.3 },\r\n 'claude-3-5-sonnet': { inputPer1M: 3.0, outputPer1M: 15.0, cachedInputPer1M: 0.3 },\r\n 'claude-3-5-haiku': { inputPer1M: 0.8, outputPer1M: 4.0, cachedInputPer1M: 0.08 },\r\n 'haiku-4.5': { inputPer1M: 1.0, outputPer1M: 5.0, cachedInputPer1M: 0.1 },\r\n 'claude-opus-5': { inputPer1M: 5.0, outputPer1M: 25.0, cachedInputPer1M: 1.5 },\r\n 'claude-3-opus': { inputPer1M: 15.0, outputPer1M: 75.0, cachedInputPer1M: 1.5 },\r\n\r\n // --- Anthropic (Legacy & Backward Compatibility) ---\r\n 'claude-3-sonnet': { inputPer1M: 3.0, outputPer1M: 15.0, cachedInputPer1M: 0.3 },\r\n 'claude-3-haiku': { inputPer1M: 0.25, outputPer1M: 1.25, cachedInputPer1M: 0.025 },\r\n 'claude-2.1': { inputPer1M: 8.0, outputPer1M: 24.0 },\r\n 'claude-2.0': { inputPer1M: 8.0, outputPer1M: 24.0 },\r\n 'claude-instant-1.2': { inputPer1M: 1.63, outputPer1M: 5.51 },\r\n\r\n // --- Google Gemini (Modern & Thoughts) ---\r\n 'gemini-3.7-flash': { inputPer1M: 0.75, outputPer1M: 3.75, cachedInputPer1M: 0.18 },\r\n 'gemini-3.1-pro': { inputPer1M: 2.0, outputPer1M: 12.0, cachedInputPer1M: 0.5 },\r\n 'gemini-3.5-flash': { inputPer1M: 1.5, outputPer1M: 9.0, cachedInputPer1M: 0.38 },\r\n 'gemini-3.1-flash-lite': { inputPer1M: 0.25, outputPer1M: 1.5, cachedInputPer1M: 0.06 },\r\n 'gemini-2.5-pro': { inputPer1M: 1.25, outputPer1M: 5.0, cachedInputPer1M: 0.3125 },\r\n 'gemini-2.5-flash': { inputPer1M: 0.15, outputPer1M: 0.6, cachedInputPer1M: 0.0375 },\r\n 'gemini-2.0-flash': { inputPer1M: 0.1, outputPer1M: 0.4, cachedInputPer1M: 0.025 },\r\n 'gemini-2.0-flash-lite': { inputPer1M: 0.075, outputPer1M: 0.3, cachedInputPer1M: 0.01875 },\r\n 'gemini-2.0-pro': { inputPer1M: 1.25, outputPer1M: 5.0, cachedInputPer1M: 0.3125 },\r\n\r\n // --- Google Gemini (Legacy & Backward Compatibility) ---\r\n 'gemini-1.5-pro': { inputPer1M: 1.25, outputPer1M: 5.0, cachedInputPer1M: 0.3125 },\r\n 'gemini-1.5-flash': { inputPer1M: 0.075, outputPer1M: 0.3, cachedInputPer1M: 0.01875 },\r\n 'gemini-1.5-flash-8b': { inputPer1M: 0.0375, outputPer1M: 0.15, cachedInputPer1M: 0.009375 },\r\n 'gemini-1.0-pro': { inputPer1M: 0.5, outputPer1M: 1.5 },\r\n\r\n // --- xAI Grok ---\r\n 'grok-4.6': { inputPer1M: 3.0, outputPer1M: 15.0 },\r\n 'grok-3': { inputPer1M: 3.0, outputPer1M: 15.0 },\r\n 'grok-3-mini': { inputPer1M: 0.3, outputPer1M: 1.5 },\r\n 'grok-2': { inputPer1M: 2.0, outputPer1M: 10.0 },\r\n 'grok-2-vision': { inputPer1M: 2.0, outputPer1M: 10.0 },\r\n 'grok-beta': { inputPer1M: 5.0, outputPer1M: 15.0 },\r\n\r\n // --- Mistral ---\r\n 'mistral-large-3': { inputPer1M: 2.0, outputPer1M: 6.0 },\r\n 'mistral-large-latest': { inputPer1M: 2.0, outputPer1M: 6.0 },\r\n 'mistral-large-2411': { inputPer1M: 2.0, outputPer1M: 6.0 },\r\n 'codestral-latest': { inputPer1M: 0.3, outputPer1M: 0.9 },\r\n 'mistral-medium-latest': { inputPer1M: 2.7, outputPer1M: 8.1 },\r\n 'mistral-small-latest': { inputPer1M: 0.2, outputPer1M: 0.6 },\r\n 'ministral-8b-latest': { inputPer1M: 0.1, outputPer1M: 0.1 },\r\n 'ministral-3b-latest': { inputPer1M: 0.04, outputPer1M: 0.04 },\r\n 'open-mistral-7b': { inputPer1M: 0.2, outputPer1M: 0.2 },\r\n 'open-mixtral-8x7b': { inputPer1M: 0.7, outputPer1M: 0.7 },\r\n 'open-mixtral-8x22b': { inputPer1M: 2.0, outputPer1M: 6.0 },\r\n\r\n // --- Groq & Meta Llama LPUs ---\r\n 'llama-3.3-70b-versatile': { inputPer1M: 0.59, outputPer1M: 0.79 },\r\n 'llama-3.1-405b': { inputPer1M: 3.0, outputPer1M: 3.0 },\r\n 'llama-3.1-70b-versatile': { inputPer1M: 0.59, outputPer1M: 0.79 },\r\n 'llama-3.1-8b-instant': { inputPer1M: 0.05, outputPer1M: 0.08 },\r\n 'llama-3.2-1b-preview': { inputPer1M: 0.04, outputPer1M: 0.04 },\r\n 'llama-3.2-3b-preview': { inputPer1M: 0.06, outputPer1M: 0.06 },\r\n 'llama-3.2-11b-vision': { inputPer1M: 0.18, outputPer1M: 0.18 },\r\n 'llama-3.2-90b-vision': { inputPer1M: 0.90, outputPer1M: 0.90 },\r\n 'deepseek-r1-distill-llama-70b': { inputPer1M: 0.75, outputPer1M: 0.99 },\r\n 'deepseek-r1-distill-qwen-32b': { inputPer1M: 0.49, outputPer1M: 0.49 },\r\n 'qwen-2.5-32b': { inputPer1M: 0.29, outputPer1M: 0.39 },\r\n 'qwen-2.5-72b': { inputPer1M: 0.35, outputPer1M: 0.40 },\r\n 'mixtral-8x7b-32768': { inputPer1M: 0.24, outputPer1M: 0.24 },\r\n 'gemma2-9b-it': { inputPer1M: 0.20, outputPer1M: 0.20 },\r\n\r\n // --- DeepSeek ---\r\n 'deepseek-v4-pro': { inputPer1M: 0.66, outputPer1M: 1.98, cachedInputPer1M: 0.15 },\r\n 'deepseek-v4-flash': { inputPer1M: 0.22, outputPer1M: 0.66, cachedInputPer1M: 0.05 },\r\n 'deepseek-v3': { inputPer1M: 0.14, outputPer1M: 0.28, cachedInputPer1M: 0.014 },\r\n 'deepseek-chat': { inputPer1M: 0.14, outputPer1M: 0.28, cachedInputPer1M: 0.014 },\r\n 'deepseek-r1': { inputPer1M: 0.55, outputPer1M: 2.19, cachedInputPer1M: 0.14 },\r\n 'deepseek-reasoner': { inputPer1M: 0.55, outputPer1M: 2.19, cachedInputPer1M: 0.14 },\r\n\r\n // --- Cohere ---\r\n 'command-r-plus': { inputPer1M: 2.5, outputPer1M: 10.0 },\r\n 'command-r': { inputPer1M: 0.15, outputPer1M: 0.6 },\r\n 'command': { inputPer1M: 1.0, outputPer1M: 2.0 },\r\n 'command-light': { inputPer1M: 0.3, outputPer1M: 0.6 },\r\n 'embed-english-v3.0': { inputPer1M: 0.10, outputPer1M: 0.0 },\r\n\r\n // --- Perplexity ---\r\n 'sonar': { inputPer1M: 1.0, outputPer1M: 1.0 },\r\n 'sonar-pro': { inputPer1M: 3.0, outputPer1M: 15.0 },\r\n 'sonar-reasoning': { inputPer1M: 1.0, outputPer1M: 5.0 },\r\n 'sonar-reasoning-pro': { inputPer1M: 2.0, outputPer1M: 8.0 },\r\n};\r\n\r\n/**\r\n * Common model alias map to normalize nicknames, shorthands, and legacy IDs\r\n */\r\nexport const MODEL_ALIASES: Record<string, string> = {\r\n // OpenAI Shorthands & Aliases\r\n 'gpt4': 'gpt-4',\r\n 'gpt4o': 'gpt-4o',\r\n 'gpt-4-preview': 'gpt-4-turbo',\r\n 'gpt-4-0125-preview': 'gpt-4-turbo',\r\n 'gpt-4-1106-preview': 'gpt-4-turbo',\r\n 'gpt-3.5': 'gpt-3.5-turbo',\r\n 'gpt-3.5-turbo-0125': 'gpt-3.5-turbo',\r\n 'gpt-3.5-turbo-1106': 'gpt-3.5-turbo',\r\n 'gpt-3.5-turbo-16k-0613': 'gpt-3.5-turbo-16k',\r\n\r\n // Anthropic Shorthands\r\n 'sonnet': 'claude-3-5-sonnet',\r\n 'sonnet-3.7': 'claude-3-7-sonnet',\r\n 'sonnet-3.5': 'claude-3-5-sonnet',\r\n 'haiku': 'claude-3-5-haiku',\r\n 'haiku-3.5': 'claude-3-5-haiku',\r\n 'opus': 'claude-3-opus',\r\n 'claude-2': 'claude-2.0',\r\n 'claude-instant': 'claude-instant-1.2',\r\n\r\n // DeepSeek Shorthands\r\n 'r1': 'deepseek-r1',\r\n 'v3': 'deepseek-v3',\r\n\r\n // Gemini Shorthands\r\n 'flash': 'gemini-2.0-flash',\r\n 'pro': 'gemini-1.5-pro',\r\n\r\n // Meta / Groq Shorthands\r\n 'llama-3.3-70b': 'llama-3.3-70b-versatile',\r\n 'llama-3.1-70b': 'llama-3.1-70b-versatile',\r\n 'llama-3.1-8b': 'llama-3.1-8b-instant',\r\n 'llama-3-70b': 'llama-3.1-70b-versatile',\r\n 'llama-3-8b': 'llama-3.1-8b-instant',\r\n\r\n // Mistral Shorthands\r\n 'codestral': 'codestral-latest',\r\n 'mistral-large': 'mistral-large-latest',\r\n 'mistral-small': 'mistral-small-latest',\r\n};\r\n\r\n/**\r\n * Dynamic in-memory registry allowing runtime custom price registration\r\n */\r\nconst customPricingRegistry: Record<string, ModelPricingRates> = {};\r\n\r\n/**\r\n * Normalize model identifier to match pricing table keys:\r\n * - Strips AWS Bedrock prefixes (e.g. 'anthropic.claude-3-5-sonnet-20241022-v2:0' -> 'claude-3-5-sonnet')\r\n * - Strips provider prefixes (e.g. 'openai/gpt-4o' -> 'gpt-4o', 'deepseek/deepseek-r1' -> 'deepseek-r1')\r\n * - Strips date suffixes (e.g. '-20240307', '-20250219')\r\n * - Resolves shorthands and aliases\r\n */\r\nexport function normalizeModelKey(rawModel: string): string {\r\n if (!rawModel) return 'unknown';\r\n\r\n let model = rawModel.toLowerCase().trim();\r\n\r\n // Strip AWS Bedrock model prefix (e.g. 'us.anthropic.claude-3-5-sonnet...', 'meta.llama3-...')\r\n model = model.replace(/^[a-z0-9_-]+\\.(anthropic|meta|amazon|cohere|mistral|ai21)\\./i, '');\r\n model = model.replace(/^(anthropic|meta|amazon|cohere|mistral|ai21)\\./i, '');\r\n\r\n // Strip AWS Bedrock version suffix (e.g. '-v1:0', '-v2:0', ':0')\r\n model = model.replace(/-v\\d+(:\\d+)?$/, '');\r\n model = model.replace(/:\\d+$/, '');\r\n\r\n // Strip provider prefix if present (e.g. 'openai/gpt-4o' -> 'gpt-4o', 'meta-llama/llama-3.3-70b-instruct' -> 'llama-3.3-70b-instruct')\r\n if (model.includes('/')) {\r\n model = model.split('/').slice(1).join('/');\r\n }\r\n\r\n // Remove trailing version/mode tags (e.g. ':latest', ':free', ':beta')\r\n model = model.replace(/:(latest|free|beta)$/, '');\r\n\r\n // Remove date suffixes like -20240307 or -20250219 or -2024-08-06\r\n model = model.replace(/-\\d{8}$/, '');\r\n model = model.replace(/-\\d{4}-\\d{2}-\\d{2}$/, '');\r\n\r\n // Normalize Bedrock Meta format (e.g. llama3-1-70b -> llama-3.1-70b)\r\n model = model.replace(/llama(\\d+)-(\\d+)-/g, 'llama-$1.$2-');\r\n model = model.replace(/llama(\\d+)\\.(\\d+)-/g, 'llama-$1.$2-');\r\n\r\n // Check aliases before fine-tuning\r\n if (MODEL_ALIASES[model]) {\r\n return MODEL_ALIASES[model];\r\n }\r\n\r\n // Remove common modifier suffixes if not directly matching table\r\n if (!MODEL_PRICING_TABLE[model]) {\r\n const withoutInstruct = model.replace(/-(instruct|chat|preview)$/, '');\r\n if (MODEL_PRICING_TABLE[withoutInstruct]) {\r\n return withoutInstruct;\r\n }\r\n if (MODEL_ALIASES[withoutInstruct]) {\r\n return MODEL_ALIASES[withoutInstruct];\r\n }\r\n }\r\n\r\n return model;\r\n}\r\n\r\n/**\r\n * Retrieve pricing rates for a given model\r\n */\r\nexport function getModelPricing(modelName: string): ModelPricingRates {\r\n const normalized = normalizeModelKey(modelName);\r\n\r\n // Check custom registry first\r\n if (customPricingRegistry[normalized]) {\r\n return customPricingRegistry[normalized];\r\n }\r\n if (customPricingRegistry[modelName]) {\r\n return customPricingRegistry[modelName];\r\n }\r\n\r\n // Check built-in table with normalized key\r\n if (MODEL_PRICING_TABLE[normalized]) {\r\n return MODEL_PRICING_TABLE[normalized];\r\n }\r\n // Check built-in table with direct key\r\n if (MODEL_PRICING_TABLE[modelName]) {\r\n return MODEL_PRICING_TABLE[modelName];\r\n }\r\n\r\n // Check alias table fallback\r\n const alias = MODEL_ALIASES[modelName.toLowerCase().trim()];\r\n if (alias && MODEL_PRICING_TABLE[alias]) {\r\n return MODEL_PRICING_TABLE[alias];\r\n }\r\n\r\n // Fallback defaults for unknown models (conservative estimates: $1.00 in, $3.00 out)\r\n return {\r\n inputPer1M: 1.0,\r\n outputPer1M: 3.0,\r\n cachedInputPer1M: 0.5,\r\n };\r\n}\r\n\r\n/**\r\n * Register or override pricing rates for a custom model\r\n */\r\nexport function registerModelPricing(modelName: string, rates: ModelPricingRates): void {\r\n const normalized = normalizeModelKey(modelName);\r\n customPricingRegistry[normalized] = rates;\r\n customPricingRegistry[modelName] = rates;\r\n}\r\n","import type { InferenceCost, TokenUsage, InlineRateConfig, ModelPricingRates } from '../types';\nimport { getModelPricing } from './table';\n\nexport interface CalculateCostParams {\n model: string;\n inputTokens?: number;\n outputTokens?: number;\n reasoningTokens?: number;\n cachedTokens?: number;\n cacheWriteTokens?: number;\n markupMultiplier?: number;\n minimumChargeUSD?: number;\n customRate?: InlineRateConfig;\n}\n\n/**\n * BigInt Nano-Precision Financial Math Engine\n * 1 USD = 1,000,000,000 Nano-USD (10^9)\n * 1 token at $1.00 / 1M = $0.000001 = 1,000 Nano-USD\n * Prevents IEEE 754 floating point precision drift on micro-transactions.\n */\nexport function calculateCost(params: CalculateCostParams): InferenceCost {\n let rates: ModelPricingRates;\n\n if (params.customRate) {\n const outRate = params.customRate.out ?? params.customRate.output ?? 0;\n rates = {\n inputPer1M: params.customRate.in,\n outputPer1M: outRate,\n reasoningPer1M: params.customRate.reasoning ?? outRate,\n cachedInputPer1M: params.customRate.cached ?? params.customRate.in * 0.15,\n currency: 'USD',\n };\n } else {\n rates = getModelPricing(params.model);\n }\n\n const inputTokens = BigInt(Math.max(0, params.inputTokens ?? 0));\n const outputTokens = BigInt(Math.max(0, params.outputTokens ?? 0));\n const reasoningTokens = BigInt(Math.max(0, params.reasoningTokens ?? 0));\n const cachedTokens = BigInt(Math.max(0, params.cachedTokens ?? 0));\n\n // Regular input tokens (minus any cached tokens)\n const regularInputTokens = inputTokens > cachedTokens ? inputTokens - cachedTokens : 0n;\n\n // Convert rate per 1M tokens to integer nano-dollars per single token (rate * 1,000)\n // Using 10^9 nano-precision\n const rateInputNano = BigInt(Math.round(rates.inputPer1M * 1_000));\n const cachedPer1M = rates.cachedInputPer1M ?? rates.inputPer1M * 0.15;\n const rateCachedNano = BigInt(Math.round(cachedPer1M * 1_000));\n const rateOutputNano = BigInt(Math.round(rates.outputPer1M * 1_000));\n const reasoningPer1M = rates.reasoningPer1M ?? rates.outputPer1M;\n const rateReasoningNano = BigInt(Math.round(reasoningPer1M * 1_000));\n\n // Compute component nano costs\n const regularInputCostNano = regularInputTokens * rateInputNano;\n const cachedInputCostNano = cachedTokens * rateCachedNano;\n const inputCostNano = regularInputCostNano + cachedInputCostNano;\n const outputCostNano = outputTokens * rateOutputNano;\n const reasoningCostNano = reasoningTokens * rateReasoningNano;\n\n // Prompt cache savings discount\n const standardCacheCostNano = cachedTokens * rateInputNano;\n const cachedDiscountNano =\n standardCacheCostNano > cachedInputCostNano ? standardCacheCostNano - cachedInputCostNano : 0n;\n\n // Total wholesale cost\n const wholesaleNano = inputCostNano + outputCostNano;\n\n // Retail calculation\n const markup = params.markupMultiplier ?? 1.0;\n let billedNano = wholesaleNano;\n let hasRetail = false;\n\n if (markup !== 1.0 || params.minimumChargeUSD !== undefined) {\n hasRetail = true;\n const markupMultiplierNano = BigInt(Math.round(markup * 1_000));\n billedNano = (wholesaleNano * markupMultiplierNano) / 1_000n;\n\n if (params.minimumChargeUSD !== undefined && params.minimumChargeUSD > 0) {\n const minChargeNano = BigInt(Math.round(params.minimumChargeUSD * 1_000_000_000));\n if (billedNano < minChargeNano) {\n billedNano = minChargeNano;\n }\n }\n }\n\n const inputCostUSD = Number(inputCostNano) / 1_000_000_000;\n const outputCostUSD = Number(outputCostNano) / 1_000_000_000;\n const reasoningCostUSD = Number(reasoningCostNano) / 1_000_000_000;\n const cachedDiscountUSD = Number(cachedDiscountNano) / 1_000_000_000;\n const totalUSD = Number(wholesaleNano) / 1_000_000_000;\n const wholesaleTotalUSD = totalUSD;\n const billedUSD = Number(billedNano) / 1_000_000_000;\n const profitUSD = Math.max(0, billedUSD - wholesaleTotalUSD);\n const retailUSD = hasRetail ? billedUSD : undefined;\n\n return {\n inputCostUSD: Number(inputCostUSD.toFixed(8)),\n outputCostUSD: Number(outputCostUSD.toFixed(8)),\n reasoningCostUSD: reasoningTokens > 0n ? Number(reasoningCostUSD.toFixed(8)) : undefined,\n cachedDiscountUSD: cachedTokens > 0n ? Number(cachedDiscountUSD.toFixed(8)) : undefined,\n totalUSD: Number(totalUSD.toFixed(8)),\n wholesaleTotalUSD: Number(wholesaleTotalUSD.toFixed(8)),\n billedUSD: Number(billedUSD.toFixed(8)),\n profitUSD: Number(profitUSD.toFixed(8)),\n retailUSD: retailUSD !== undefined ? Number(retailUSD.toFixed(8)) : undefined,\n currency: rates.currency || 'USD',\n };\n}\n\n/**\n * Calculates cost directly from a TokenUsage object\n */\nexport function calculateUsageCost(\n model: string,\n usage: TokenUsage,\n optionsOrMarkup?: number | { markupMultiplier?: number; minimumChargeUSD?: number; customRate?: InlineRateConfig }\n): InferenceCost {\n const options =\n typeof optionsOrMarkup === 'number'\n ? { markupMultiplier: optionsOrMarkup }\n : optionsOrMarkup || {};\n\n return calculateCost({\n model,\n inputTokens: usage.inputTokens,\n outputTokens: usage.outputTokens,\n reasoningTokens: usage.reasoningTokens,\n cachedTokens: usage.cachedTokens,\n cacheWriteTokens: usage.cacheWriteTokens,\n markupMultiplier: options.markupMultiplier,\n minimumChargeUSD: options.minimumChargeUSD,\n customRate: options.customRate,\n });\n}\n","import type { CustomerParam, CustomerInfo } from '../types';\r\n\r\nexport interface NormalizedCustomer {\r\n customerId?: string;\r\n customerEmail?: string;\r\n customerObj?: CustomerInfo;\r\n customerMetadata: Record<string, string | number | boolean>;\r\n}\r\n\r\n/**\r\n * Normalizes string or object customer into structured identifiers and metadata\r\n */\r\nexport function normalizeCustomer(customer?: CustomerParam, extraCustomerId?: string): NormalizedCustomer {\r\n if (!customer && !extraCustomerId) {\r\n return {\r\n customerId: undefined,\r\n customerEmail: undefined,\r\n customerObj: undefined,\r\n customerMetadata: {},\r\n };\r\n }\r\n\r\n if (typeof customer === 'string') {\r\n const isEmail = customer.includes('@');\r\n const customerObj: CustomerInfo = {\r\n id: customer,\r\n email: isEmail ? customer : undefined,\r\n };\r\n return {\r\n customerId: customer,\r\n customerEmail: isEmail ? customer : undefined,\r\n customerObj,\r\n customerMetadata: {},\r\n };\r\n }\r\n\r\n const customerObj = customer || (extraCustomerId ? { id: extraCustomerId } : undefined);\r\n const customerId = customerObj?.id || customerObj?.userId || extraCustomerId;\r\n const customerEmail = customerObj?.email;\r\n\r\n const customerMetadata: Record<string, string | number | boolean> = {};\r\n\r\n if (customerObj) {\r\n const orgId = customerObj.orgId || customerObj.organizationId;\r\n if (orgId) customerMetadata.org_id = String(orgId);\r\n\r\n const teamId = customerObj.teamId || customerObj.workspaceId;\r\n if (teamId) customerMetadata.team_id = String(teamId);\r\n\r\n if (customerObj.plan) customerMetadata.plan = String(customerObj.plan);\r\n if (customerObj.tier) customerMetadata.tier = String(customerObj.tier);\r\n if (customerObj.role) customerMetadata.role = String(customerObj.role);\r\n if (customerObj.orgName) customerMetadata.org_name = String(customerObj.orgName);\r\n\r\n if (customerObj.metadata) {\r\n for (const [key, val] of Object.entries(customerObj.metadata)) {\r\n if (val !== null && val !== undefined) {\r\n customerMetadata[key] = val as string | number | boolean;\r\n }\r\n }\r\n }\r\n }\r\n\r\n return {\r\n customerId,\r\n customerEmail,\r\n customerObj,\r\n customerMetadata,\r\n };\r\n}\r\n","import type { UsageEvent, StreamWrapOptions } from '../types';\r\nimport { inspectOpenAIStreamChunk } from './extractors/openai';\r\nimport { AnthropicStreamAccumulator } from './extractors/anthropic';\r\nimport { extractGeminiResponseUsage } from './extractors/gemini';\r\nimport { calculateUsageCost } from '../pricing/calculator';\r\nimport { normalizeCustomer } from '../customers/helpers';\r\n\r\nexport type UsageDispatchedCallback = (event: UsageEvent) => void;\r\n\r\n/**\r\n * Wraps an OpenAI async iterable stream to capture usage at stream conclusion\r\n */\r\nexport function wrapOpenAIStream<T extends AsyncIterable<any>>(\r\n stream: T,\r\n options: StreamWrapOptions,\r\n onComplete: UsageDispatchedCallback\r\n): T {\r\n let detectedModel = options.model || 'gpt-4o';\r\n let finalUsage: any = null;\r\n\r\n const wrappedAsyncIterable = {\r\n async *[Symbol.asyncIterator]() {\r\n try {\r\n for await (const chunk of stream) {\r\n const inspected = inspectOpenAIStreamChunk(chunk);\r\n if (inspected.model) {\r\n detectedModel = inspected.model;\r\n }\r\n if (inspected.usage) {\r\n finalUsage = inspected.usage;\r\n }\r\n yield chunk;\r\n }\r\n } finally {\r\n if (finalUsage) {\r\n const cost = calculateUsageCost(detectedModel, finalUsage);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: detectedModel,\r\n provider: 'openai',\r\n usage: finalUsage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n },\r\n };\r\n\r\n onComplete(event);\r\n if (options.onUsage) {\r\n options.onUsage(event);\r\n }\r\n }\r\n }\r\n },\r\n };\r\n\r\n return wrappedAsyncIterable as unknown as T;\r\n}\r\n\r\n/**\r\n * Wraps an Anthropic message stream to accumulate message_start and message_delta usage\r\n */\r\nexport function wrapAnthropicStream<T extends AsyncIterable<any>>(\r\n stream: T,\r\n options: StreamWrapOptions,\r\n onComplete: UsageDispatchedCallback\r\n): T {\r\n const accumulator = new AnthropicStreamAccumulator();\r\n\r\n const wrappedAsyncIterable = {\r\n async *[Symbol.asyncIterator]() {\r\n try {\r\n for await (const event of stream) {\r\n accumulator.processEvent(event);\r\n yield event;\r\n }\r\n } finally {\r\n const extracted = accumulator.getUsage();\r\n const model = options.model || extracted.model;\r\n const cost = calculateUsageCost(model, extracted.usage);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const usageEvent: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model,\r\n provider: 'anthropic',\r\n usage: extracted.usage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n },\r\n };\r\n\r\n onComplete(usageEvent);\r\n if (options.onUsage) {\r\n options.onUsage(usageEvent);\r\n }\r\n }\r\n },\r\n };\r\n\r\n return wrappedAsyncIterable as unknown as T;\r\n}\r\n\r\n/**\r\n * Wraps a Google Gemini GenerateContentStreamResult\r\n */\r\nexport function wrapGeminiStream(\r\n result: any,\r\n options: StreamWrapOptions,\r\n onComplete: UsageDispatchedCallback\r\n): any {\r\n if (!result || !result.stream) return result;\r\n\r\n const originalStream = result.stream;\r\n const model = options.model || 'gemini-3.7-flash';\r\n let lastChunkWithUsage: any = null;\r\n\r\n const wrappedStream = (async function* () {\r\n try {\r\n for await (const chunk of originalStream) {\r\n if (chunk.usageMetadata) {\r\n lastChunkWithUsage = chunk;\r\n }\r\n yield chunk;\r\n }\r\n } finally {\r\n if (lastChunkWithUsage) {\r\n const extracted = extractGeminiResponseUsage(lastChunkWithUsage, model);\r\n if (extracted) {\r\n const cost = calculateUsageCost(extracted.model, extracted.usage);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: extracted.model,\r\n provider: 'google',\r\n usage: extracted.usage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n },\r\n };\r\n\r\n onComplete(event);\r\n if (options.onUsage) {\r\n options.onUsage(event);\r\n }\r\n }\r\n }\r\n }\r\n })();\r\n\r\n return {\r\n ...result,\r\n stream: wrappedStream,\r\n };\r\n}\r\n\r\n/**\r\n * Universal Stream Wrapper\r\n */\r\nexport function wrapUniversalStream<T>(\r\n stream: T,\r\n options: StreamWrapOptions = {},\r\n onComplete: UsageDispatchedCallback\r\n): T {\r\n if (!stream || typeof stream !== 'object') return stream;\r\n\r\n // 1. Check Gemini stream\r\n if ('stream' in stream && 'response' in stream) {\r\n return wrapGeminiStream(stream, options, onComplete);\r\n }\r\n\r\n // 2. Check if stream is an AsyncIterable\r\n if (Symbol.asyncIterator in stream) {\r\n // If provider is explicitly anthropic or model is claude\r\n if (options.provider === 'anthropic' || options.model?.toLowerCase().includes('claude')) {\r\n return wrapAnthropicStream(stream as any, options, onComplete);\r\n }\r\n // Default to universal stream wrapper which detects usage chunks polymorphically\r\n return wrapOpenAIStream(stream as any, options, onComplete);\r\n }\r\n\r\n return stream;\r\n}\r\n","import type {\r\n CustomerParam,\r\n UsageEvent,\r\n CircuitBreakerOptions,\r\n BudgetExceededEvent,\r\n BillingConfig,\r\n PricingConfig,\r\n InlineRateConfig,\r\n} from '../types';\r\nimport { VibezCircuitBreakerError } from '../types';\r\nimport { createMeter, VibezMeter } from '../meter/client';\r\nimport { calculateUsageCost } from '../pricing/calculator';\r\nimport { normalizeCustomer } from '../customers/helpers';\r\n\r\nexport interface WithBillingOptions extends CircuitBreakerOptions {\r\n /** Customer email, user ID, or rich customer object with metadata */\r\n customer?: CustomerParam;\r\n /** Direct Stripe customer ID */\r\n customerId?: string;\r\n /** Billing mode configuration (Universal Auto-Debit, postpaid vs prepaid, pluggable providers) */\r\n billing?: BillingConfig;\r\n /** Profit margin & minimum charge configuration */\r\n pricing?: PricingConfig;\r\n /** 1-line inline pricing rate card */\r\n rate?: InlineRateConfig;\r\n /** Pluggable Database Sink (Supabase, Postgres, Firebase, or 1-line callback) */\r\n database?: any | ((event: UsageEvent) => void | Promise<void>);\r\n /** Whether to capture tokens if the client aborts or closes tab mid-stream (default: true) */\r\n captureOnAbort?: boolean;\r\n /** Execution runtime environment (default: 'auto') */\r\n runtime?: 'auto' | 'serverless' | 'edge' | 'node';\r\n /** Stripe API Key override (uses STRIPE_SECRET_KEY env by default) */\r\n stripeApiKey?: string;\r\n /** Existing VibezMeter instance (optional) */\r\n meter?: VibezMeter;\r\n /** Custom meter event name */\r\n eventName?: string;\r\n /** Usage callback fired upon generation/stream completion */\r\n onUsage?: (event: UsageEvent) => void | Promise<void>;\r\n /** Custom developer metadata */\r\n metadata?: Record<string, string | number | boolean>;\r\n /** Suppress console warnings (default: true in test environment) */\r\n silent?: boolean;\r\n}\r\n\r\n/**\r\n * Wraps any Vercel AI SDK LanguageModel (v2 or v3) with automated Stripe billing, token metering, and agent circuit breakers.\r\n *\r\n * Sane Defaults Built-In:\r\n * - $0.50 safety ceiling per call (overridable)\r\n * - Automatic in-flight token capture on abort\r\n * - Automatic prompt caching discount parsing\r\n * - Serverless lifecycle preservation\r\n */\r\nexport function withBilling<T extends object>(\r\n model: T,\r\n optionsOrCustomer?: CustomerParam | WithBillingOptions,\r\n extraOptions: WithBillingOptions = {}\r\n): T {\r\n if (!model || typeof model !== 'object') {\r\n return model;\r\n }\r\n\r\n let options: WithBillingOptions = {};\r\n if (typeof optionsOrCustomer === 'string') {\r\n options = { ...extraOptions, customer: optionsOrCustomer };\r\n } else if (typeof optionsOrCustomer === 'object' && optionsOrCustomer !== null) {\r\n if ('userId' in optionsOrCustomer || 'email' in optionsOrCustomer || 'id' in optionsOrCustomer) {\r\n options = { ...extraOptions, customer: optionsOrCustomer as CustomerParam };\r\n } else {\r\n options = { ...(optionsOrCustomer as WithBillingOptions), ...extraOptions };\r\n }\r\n }\r\n\r\n const meter =\r\n options.meter ||\r\n createMeter({\r\n apiKey: options.stripeApiKey,\r\n eventName: options.eventName,\r\n });\r\n\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n const customerId = normalized.customerId;\r\n const customerEmail = normalized.customerEmail;\r\n const customerObj = normalized.customerObj;\r\n const customerMetadata = normalized.customerMetadata;\r\n\r\n const modelId = (model as any).modelId || 'unknown-model';\r\n const provider = (model as any).provider?.replace(/^@ai-sdk\\//, '') || 'ai-sdk';\r\n\r\n // Sane Default: $0.50 circuit breaker ceiling unless explicitly disabled or configured\r\n const maxCostPerCall = options.maxCostPerCallUSD !== undefined ? options.maxCostPerCallUSD : 0.50;\r\n const captureOnAbort = options.captureOnAbort !== false; // Default: true\r\n\r\n // Helper to safely schedule serverless flushes\r\n const scheduleFlush = () => {\r\n try {\r\n const flushPromise = meter.flush();\r\n // Next.js 15+ after() or Cloudflare Workers waitUntil()\r\n if (typeof globalThis !== 'undefined') {\r\n const g = globalThis as any;\r\n if (typeof g.after === 'function') {\r\n g.after(() => flushPromise);\r\n return;\r\n }\r\n }\r\n } catch {\r\n // Fallback in environments without after()\r\n }\r\n };\r\n\r\n // Helper to record usage and enforce circuit breakers\r\n const handleUsage = (rawUsage: any, extraMeta?: Record<string, any>) => {\r\n if (!rawUsage) return;\r\n\r\n const inputTokens =\r\n rawUsage.promptTokens ??\r\n rawUsage.inputTokens ??\r\n rawUsage.prompt_tokens ??\r\n rawUsage.input_tokens ??\r\n rawUsage.promptTokenCount ??\r\n 0;\r\n const outputTokens =\r\n rawUsage.completionTokens ??\r\n rawUsage.outputTokens ??\r\n rawUsage.completion_tokens ??\r\n rawUsage.output_tokens ??\r\n rawUsage.candidatesTokenCount ??\r\n 0;\r\n const reasoningTokens =\r\n rawUsage.reasoningTokens ??\r\n rawUsage.completionTokensDetails?.reasoningTokens ??\r\n rawUsage.outputTokenDetails?.reasoningTokens ??\r\n rawUsage.reasoning_tokens ??\r\n rawUsage.completion_tokens_details?.reasoning_tokens ??\r\n rawUsage.output_token_details?.reasoning_tokens ??\r\n rawUsage.thoughtsTokenCount ??\r\n 0;\r\n const cachedTokens =\r\n rawUsage.promptTokensDetails?.cachedTokens ??\r\n rawUsage.inputTokenDetails?.cachedTokens ??\r\n rawUsage.cachedTokens ??\r\n rawUsage.cached_tokens ??\r\n rawUsage.prompt_tokens_details?.cached_tokens ??\r\n rawUsage.input_token_details?.cached_tokens ??\r\n rawUsage.cachedContentTokenCount ??\r\n rawUsage.cache_read_input_tokens ??\r\n 0;\r\n const cacheWriteTokens =\r\n rawUsage.cacheWriteTokens ??\r\n rawUsage.cache_creation_input_tokens ??\r\n rawUsage.cacheCreationTokens ??\r\n 0;\r\n\r\n const usage = {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n cacheWriteTokens: cacheWriteTokens > 0 ? cacheWriteTokens : undefined,\r\n };\r\n\r\n // Calculate cost with profit margin & minimum charge & custom rates\r\n const cost = calculateUsageCost(modelId, usage, {\r\n markupMultiplier: options.pricing?.margin,\r\n minimumChargeUSD: options.pricing?.minimumChargeUSD,\r\n customRate: options.rate,\r\n });\r\n\r\n // 🛡️ Agent Circuit Breakers Check ($0.50 default safety fuse)\r\n if (maxCostPerCall > 0 && maxCostPerCall !== Infinity && cost.totalUSD > maxCostPerCall) {\r\n const budgetEvent: BudgetExceededEvent = {\r\n reason: 'cost_per_call_exceeded',\r\n limit: maxCostPerCall,\r\n current: cost.totalUSD,\r\n model: modelId,\r\n customerId,\r\n message: `[vibezcheck] Circuit Breaker tripped: Call cost ($${cost.totalUSD.toFixed(4)}) exceeded budget ceiling ($${maxCostPerCall.toFixed(4)}).`,\r\n };\r\n\r\n if (options.onBudgetExceeded) {\r\n options.onBudgetExceeded(budgetEvent);\r\n }\r\n\r\n if (options.throwOnBudgetExceeded) {\r\n throw new VibezCircuitBreakerError(budgetEvent);\r\n }\r\n }\r\n\r\n if (options.maxTokensPerCall && usage.totalTokens > options.maxTokensPerCall) {\r\n const budgetEvent: BudgetExceededEvent = {\r\n reason: 'max_tokens_exceeded',\r\n limit: options.maxTokensPerCall,\r\n current: usage.totalTokens,\r\n model: modelId,\r\n customerId,\r\n message: `[vibezcheck] Circuit Breaker tripped: Token count (${usage.totalTokens}) exceeded maxTokensPerCall limit (${options.maxTokensPerCall}).`,\r\n };\r\n\r\n if (options.onBudgetExceeded) {\r\n options.onBudgetExceeded(budgetEvent);\r\n }\r\n\r\n if (options.throwOnBudgetExceeded) {\r\n throw new VibezCircuitBreakerError(budgetEvent);\r\n }\r\n }\r\n\r\n const mergedMetadata: Record<string, string | number | boolean> = {\r\n ...customerMetadata,\r\n ...options.metadata,\r\n ...extraMeta,\r\n billingMode: options.billing?.mode || 'postpaid',\r\n };\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: modelId,\r\n provider,\r\n usage,\r\n cost,\r\n customerId,\r\n customerEmail,\r\n customer: customerObj,\r\n metadata: mergedMetadata,\r\n };\r\n\r\n // Record via meter batcher\r\n meter.recordUsage({\r\n model: modelId,\r\n provider,\r\n inputTokens,\r\n outputTokens,\r\n reasoningTokens: usage.reasoningTokens,\r\n cachedTokens: usage.cachedTokens,\r\n customerId,\r\n customer: customerObj,\r\n metadata: event.metadata,\r\n });\r\n\r\n if (options.onUsage) {\r\n options.onUsage(event);\r\n }\r\n\r\n // 🛡️ Duck-Typed Database Sink Execution (Airbag Isolated)\r\n if (options.database) {\r\n const dbTarget = options.database;\r\n const executeDbWrite = async () => {\r\n try {\r\n // 1. Direct Supabase client duck-typing (has .from()) or wrapped { client, table }\r\n const supabaseClient = typeof dbTarget === 'object' && dbTarget !== null && typeof dbTarget.from === 'function'\r\n ? dbTarget\r\n : (typeof dbTarget === 'object' && dbTarget !== null && typeof dbTarget.client?.from === 'function' ? dbTarget.client : null);\r\n\r\n if (supabaseClient) {\r\n const tableName = (dbTarget as any)?.table || 'vibez_usage';\r\n await supabaseClient.from(tableName).insert({\r\n customer_id: customerId,\r\n user_id: customerObj?.userId || customerId,\r\n model: modelId,\r\n input_tokens: usage.inputTokens,\r\n output_tokens: usage.outputTokens,\r\n total_tokens: usage.totalTokens,\r\n cached_tokens: usage.cachedTokens,\r\n reasoning_tokens: usage.reasoningTokens,\r\n cost_usd: cost.totalUSD,\r\n created_at: event.timestamp,\r\n metadata: event.metadata,\r\n });\r\n return;\r\n }\r\n\r\n // 2. Typed DatabaseAdapter (has .save())\r\n if (typeof dbTarget === 'object' && dbTarget !== null && typeof dbTarget.save === 'function') {\r\n await dbTarget.save(event);\r\n return;\r\n }\r\n\r\n // 3. 1-line callback function\r\n if (typeof dbTarget === 'function') {\r\n await dbTarget(event);\r\n return;\r\n }\r\n } catch (err: any) {\r\n // Zero Blast Radius: Third-party DB errors never crash the user's stream\r\n if (process.env.NODE_ENV !== 'test' && !options.silent) {\r\n console.warn(`[vibezcheck] Database record failed safely:`, err?.message || err);\r\n }\r\n }\r\n };\r\n\r\n if (typeof globalThis !== 'undefined' && typeof (globalThis as any).after === 'function') {\r\n (globalThis as any).after(() => executeDbWrite());\r\n } else {\r\n executeDbWrite().catch(() => {});\r\n }\r\n }\r\n\r\n // 💳 Pluggable Payment Provider Execution (Airbag Isolated)\r\n if (options.billing?.charge && typeof options.billing.charge === 'function') {\r\n const chargeFn = options.billing.charge;\r\n const executeCharge = async () => {\r\n try {\r\n await chargeFn(cost.totalUSD, event);\r\n } catch (err: any) {\r\n if (process.env.NODE_ENV !== 'test' && !options.silent) {\r\n console.warn(`[vibezcheck] Custom charge handler failed safely:`, err?.message || err);\r\n }\r\n }\r\n };\r\n if (typeof globalThis !== 'undefined' && typeof (globalThis as any).after === 'function') {\r\n (globalThis as any).after(() => executeCharge());\r\n } else {\r\n executeCharge().catch(() => {});\r\n }\r\n } else if (options.billing?.provider && typeof options.billing.provider === 'object' && typeof (options.billing.provider as any).charge === 'function') {\r\n const providerCharge = (options.billing.provider as any).charge;\r\n const executeCharge = async () => {\r\n try {\r\n await providerCharge(cost.totalUSD, event);\r\n } catch (err: any) {\r\n if (process.env.NODE_ENV !== 'test' && !options.silent) {\r\n console.warn(`[vibezcheck] Payment provider charge failed safely:`, err?.message || err);\r\n }\r\n }\r\n };\r\n if (typeof globalThis !== 'undefined' && typeof (globalThis as any).after === 'function') {\r\n (globalThis as any).after(() => executeCharge());\r\n } else {\r\n executeCharge().catch(() => {});\r\n }\r\n }\r\n\r\n scheduleFlush();\r\n };\r\n\r\n // Proxy to intercept LanguageModel calls\r\n const handler: ProxyHandler<any> = {\r\n get(target, prop, receiver) {\r\n const originalValue = Reflect.get(target, prop, receiver);\r\n\r\n // Intercept doStream (Vercel AI SDK v1/v2/v3)\r\n if (prop === 'doStream' && typeof originalValue === 'function') {\r\n return async function (...args: any[]) {\r\n const result = await originalValue.apply(target, args);\r\n if (!result || !result.stream) {\r\n return result;\r\n }\r\n\r\n const originalStream = result.stream;\r\n let streamCompleted = false;\r\n let accumulatedChars = 0;\r\n\r\n // Estimate input prompt tokens from args if available\r\n let estimatedInputTokens = 0;\r\n try {\r\n if (args[0]?.prompt) {\r\n const str = typeof args[0].prompt === 'string' ? args[0].prompt : JSON.stringify(args[0].prompt);\r\n estimatedInputTokens = Math.ceil(str.length / 4);\r\n }\r\n } catch {}\r\n\r\n // In-flight abort signal listener\r\n const abortSignal = args[0]?.abortSignal;\r\n if (abortSignal && captureOnAbort) {\r\n abortSignal.addEventListener(\r\n 'abort',\r\n () => {\r\n if (!streamCompleted && accumulatedChars > 0) {\r\n streamCompleted = true;\r\n const estimatedOutputTokens = Math.ceil(accumulatedChars / 3.8);\r\n handleUsage(\r\n {\r\n inputTokens: estimatedInputTokens,\r\n outputTokens: estimatedOutputTokens,\r\n },\r\n { aborted: true, partial: true }\r\n );\r\n }\r\n },\r\n { once: true }\r\n );\r\n }\r\n\r\n // Wrap stream to capture tokens upon finish chunk or abort\r\n const transformStream = new TransformStream({\r\n transform(chunk, controller) {\r\n controller.enqueue(chunk);\r\n\r\n const delta = chunk.textDelta || chunk.text || chunk.delta;\r\n if (delta && typeof delta === 'string') {\r\n accumulatedChars += delta.length;\r\n } else if (chunk.type === 'reasoning' || chunk.type === 'reasoning-delta') {\r\n const reasoning = chunk.reasoning || chunk.textDelta || chunk.text || chunk.delta || '';\r\n if (typeof reasoning === 'string') {\r\n accumulatedChars += reasoning.length;\r\n }\r\n }\r\n\r\n // AI SDK stream finish chunk or direct usage payload (OpenAI, Anthropic, Gemini, DeepSeek, Groq)\r\n const chunkUsage = chunk.usage || chunk.token_usage || chunk.usageMetadata;\r\n if (chunkUsage) {\r\n streamCompleted = true;\r\n handleUsage(chunkUsage);\r\n }\r\n },\r\n flush() {\r\n // If stream ended without finish chunk (e.g. cancelled/aborted), record partial tokens\r\n if (!streamCompleted && captureOnAbort && accumulatedChars > 0) {\r\n streamCompleted = true;\r\n const estimatedOutputTokens = Math.ceil(accumulatedChars / 3.8);\r\n handleUsage(\r\n {\r\n inputTokens: estimatedInputTokens,\r\n outputTokens: estimatedOutputTokens,\r\n },\r\n { aborted: true, partial: true }\r\n );\r\n }\r\n },\r\n });\r\n\r\n return {\r\n ...result,\r\n stream: originalStream.pipeThrough(transformStream),\r\n };\r\n };\r\n }\r\n\r\n // Intercept doGenerate (Vercel AI SDK v1/v2/v3/v4/v5+)\r\n if (prop === 'doGenerate' && typeof originalValue === 'function') {\r\n return async function (...args: any[]) {\r\n const result = await originalValue.apply(target, args);\r\n const usage = result?.usage || result?.tokenUsage || result?.usageMetadata;\r\n if (usage) {\r\n handleUsage(usage);\r\n }\r\n return result;\r\n };\r\n }\r\n\r\n return originalValue;\r\n },\r\n apply(target, thisArg, argArray) {\r\n if (typeof target === 'function') {\r\n return Reflect.apply(target, thisArg, argArray);\r\n }\r\n return target;\r\n },\r\n has(target, prop) {\r\n return Reflect.has(target, prop);\r\n },\r\n ownKeys(target) {\r\n return Reflect.ownKeys(target);\r\n },\r\n getPrototypeOf(target) {\r\n return Reflect.getPrototypeOf(target);\r\n },\r\n };\r\n\r\n return new Proxy(model, handler);\r\n}\r\n\r\n/**\r\n * Convenient alias for withBilling\r\n */\r\nexport const meteredModel = withBilling;\r\n","import type { CustomerParam, UsageEvent, ToolMeterOptions } from '../types';\r\nimport { withBilling, type WithBillingOptions } from './with-billing';\r\nimport { calculateCost } from '../pricing/calculator';\r\nimport { createMeter, VibezMeter } from '../meter/client';\r\n\r\nexport interface VibezCheckModelOptions extends WithBillingOptions {\r\n /** OpenAI / Anthropic / AI Gateway API Key override */\r\n apiKey?: string;\r\n /** AI Gateway / Provider Base URL override */\r\n baseURL?: string;\r\n}\r\n\r\nexport interface VibezSessionOptions {\r\n customer?: CustomerParam;\r\n stripeApiKey?: string;\r\n pricing?: WithBillingOptions['pricing'];\r\n billing?: WithBillingOptions['billing'];\r\n metadata?: Record<string, string | number | boolean>;\r\n}\r\n\r\nexport interface VibezSession {\r\n /** Creates a metered model bound to this session customer */\r\n model: (modelOrId: any, options?: VibezCheckModelOptions) => any;\r\n /** Tracks a non-LLM tool execution cost (e.g. search, scraper, image gen) */\r\n trackTool: (name: string, options: { costUSD: number; metadata?: Record<string, any> }) => Promise<void>;\r\n /** Underlying meter instance */\r\n meter: VibezMeter;\r\n}\r\n\r\n/**\r\n * Creates or resolves an AI SDK compatible LanguageModel with built-in VibezCheck billing & metering.\r\n *\r\n * Supports:\r\n * - Direct instances: `vibezcheck(openai('gpt-4o'))`, `vibezcheck(anthropic('claude-3-7-sonnet'))`\r\n * - String identifiers: `vibezcheck('openai/gpt-4o-mini')`, `vibezcheck('anthropic/claude-3-5-sonnet')`, `vibezcheck('gpt-4o')`\r\n * - Vercel AI SDK primitives: `generateText`, `streamText`, `generateObject`, `streamObject`\r\n *\r\n * @example\r\n * ```typescript\r\n * import { streamText } from 'ai';\r\n * import { openai } from '@ai-sdk/openai';\r\n * import { anthropic } from '@ai-sdk/anthropic';\r\n * import { vibezcheck } from 'vibezcheck';\r\n *\r\n * // 1. Pass wrapped OpenAI instance:\r\n * const result = streamText({\r\n * model: vibezcheck(openai('gpt-4o-mini'), { customer: 'alex@example.com' }),\r\n * messages,\r\n * });\r\n *\r\n * // 2. Pass wrapped Anthropic instance:\r\n * const result2 = streamText({\r\n * model: vibezcheck(anthropic('claude-3-7-sonnet'), { customer: 'alex@example.com' }),\r\n * messages,\r\n * });\r\n *\r\n * // 3. Use 1-line string identifier:\r\n * const result3 = streamText({\r\n * model: vibezcheck('openai/gpt-4o-mini', { customer: 'alex@example.com' }),\r\n * messages,\r\n * });\r\n * ```\r\n */\r\nexport function createVibezModel(\r\n modelOrId: any,\r\n options: VibezCheckModelOptions = {}\r\n): any {\r\n // If an existing LanguageModel instance is passed (from openai(), anthropic(), etc.), wrap directly\r\n if (typeof modelOrId === 'object' && modelOrId !== null) {\r\n return withBilling(modelOrId, options);\r\n }\r\n\r\n // If a string model identifier is passed (e.g. \"openai/gpt-4o-mini\", \"anthropic/claude-3-7-sonnet\", or \"gpt-4o-mini\")\r\n if (typeof modelOrId === 'string') {\r\n const rawId = modelOrId;\r\n let providerName = 'openai';\r\n let cleanModelId = rawId;\r\n\r\n if (rawId.includes('/')) {\r\n const parts = rawId.split('/');\r\n providerName = parts[0].toLowerCase();\r\n cleanModelId = parts.slice(1).join('/');\r\n } else if (rawId.startsWith('claude-')) {\r\n providerName = 'anthropic';\r\n } else if (rawId.startsWith('gemini-')) {\r\n providerName = 'google';\r\n } else if (rawId.startsWith('deepseek-')) {\r\n providerName = 'deepseek';\r\n } else if (rawId.startsWith('grok-')) {\r\n providerName = 'xai';\r\n } else if (\r\n rawId.startsWith('mistral-') ||\r\n rawId.startsWith('codestral-') ||\r\n rawId.startsWith('ministral-') ||\r\n rawId.startsWith('open-mistral') ||\r\n rawId.startsWith('open-mixtral')\r\n ) {\r\n providerName = 'mistral';\r\n } else if (\r\n rawId.startsWith('llama-') ||\r\n rawId.startsWith('mixtral-') ||\r\n rawId.startsWith('gemma') ||\r\n rawId.startsWith('qwen-')\r\n ) {\r\n providerName = 'groq';\r\n } else if (rawId.startsWith('command-')) {\r\n providerName = 'cohere';\r\n }\r\n\r\n const apiKey =\r\n options.apiKey ||\r\n process.env.AI_GATEWAY_API_KEY ||\r\n (providerName === 'anthropic' ? process.env.ANTHROPIC_API_KEY : undefined) ||\r\n (providerName === 'google' ? process.env.GOOGLE_GENERATIVE_AI_API_KEY : undefined) ||\r\n (providerName === 'mistral' ? process.env.MISTRAL_API_KEY : undefined) ||\r\n (providerName === 'groq' ? process.env.GROQ_API_KEY : undefined) ||\r\n (providerName === 'deepseek' ? process.env.DEEPSEEK_API_KEY : undefined) ||\r\n (providerName === 'xai' ? process.env.XAI_API_KEY : undefined) ||\r\n (providerName === 'cohere' ? process.env.COHERE_API_KEY : undefined) ||\r\n process.env.OPENAI_API_KEY;\r\n\r\n const baseURL =\r\n options.baseURL ||\r\n process.env.AI_GATEWAY_BASE_URL ||\r\n (providerName === 'openai' ? 'https://api.openai.com/v1' : undefined);\r\n\r\n let baseModelInstance: any = null;\r\n\r\n try {\r\n if (providerName === 'openai' || providerName === 'gateway' || !providerName) {\r\n const mod = require('@ai-sdk/openai');\r\n const factory = mod.createOpenAI || mod.openai || mod.default?.createOpenAI || mod.default?.openai;\r\n if (typeof factory === 'function') {\r\n if (mod.createOpenAI) {\r\n const provider = factory({ apiKey, baseURL });\r\n baseModelInstance = provider(cleanModelId);\r\n } else {\r\n baseModelInstance = factory(cleanModelId);\r\n }\r\n }\r\n } else if (providerName === 'anthropic') {\r\n const mod = require('@ai-sdk/anthropic');\r\n const factory = mod.createAnthropic || mod.anthropic || mod.default?.createAnthropic || mod.default?.anthropic;\r\n if (typeof factory === 'function') {\r\n if (mod.createAnthropic) {\r\n const provider = factory({ apiKey, baseURL });\r\n baseModelInstance = provider(cleanModelId);\r\n } else {\r\n baseModelInstance = factory(cleanModelId);\r\n }\r\n }\r\n } else if (providerName === 'google') {\r\n const mod = require('@ai-sdk/google');\r\n const factory = mod.createGoogleGenerativeAI || mod.google || mod.default?.createGoogleGenerativeAI || mod.default?.google;\r\n if (typeof factory === 'function') {\r\n if (mod.createGoogleGenerativeAI) {\r\n const provider = factory({ apiKey, baseURL });\r\n baseModelInstance = provider(cleanModelId);\r\n } else {\r\n baseModelInstance = factory(cleanModelId);\r\n }\r\n }\r\n } else if (providerName === 'mistral') {\r\n const mod = require('@ai-sdk/mistral');\r\n const factory = mod.createMistral || mod.mistral || mod.default?.createMistral || mod.default?.mistral;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createMistral ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n } else if (providerName === 'groq') {\r\n const mod = require('@ai-sdk/groq');\r\n const factory = mod.createGroq || mod.groq || mod.default?.createGroq || mod.default?.groq;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createGroq ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n } else if (providerName === 'deepseek') {\r\n const mod = require('@ai-sdk/deepseek');\r\n const factory = mod.createDeepSeek || mod.deepseek || mod.default?.createDeepSeek || mod.default?.deepseek;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createDeepSeek ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n } else if (providerName === 'xai') {\r\n const mod = require('@ai-sdk/xai');\r\n const factory = mod.createXai || mod.xai || mod.default?.createXai || mod.default?.xai;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createXai ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n } else if (providerName === 'cohere') {\r\n const mod = require('@ai-sdk/cohere');\r\n const factory = mod.createCohere || mod.cohere || mod.default?.createCohere || mod.default?.cohere;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createCohere ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n }\r\n } catch {\r\n // Fallback object implementing LanguageModel shape if provider package not installed\r\n baseModelInstance = {\r\n specificationVersion: 'v2',\r\n provider: providerName,\r\n modelId: cleanModelId,\r\n };\r\n }\r\n\r\n if (!baseModelInstance) {\r\n baseModelInstance = {\r\n specificationVersion: 'v2',\r\n provider: providerName,\r\n modelId: cleanModelId,\r\n };\r\n }\r\n\r\n return withBilling(baseModelInstance, options);\r\n }\r\n\r\n return modelOrId;\r\n}\r\n\r\n/**\r\n * Creates a scoped session for unified multi-call and tool tracking.\r\n */\r\nexport function createVibezSession(sessionOptions: VibezSessionOptions = {}): VibezSession {\r\n const meter = createMeter({\r\n apiKey: sessionOptions.stripeApiKey,\r\n });\r\n\r\n const customerId =\r\n typeof sessionOptions.customer === 'string'\r\n ? sessionOptions.customer\r\n : sessionOptions.customer?.id;\r\n\r\n return {\r\n meter,\r\n model: (modelOrId: any, callOptions: VibezCheckModelOptions = {}) => {\r\n return createVibezModel(modelOrId, {\r\n customer: sessionOptions.customer,\r\n pricing: sessionOptions.pricing,\r\n billing: sessionOptions.billing,\r\n meter,\r\n metadata: {\r\n ...sessionOptions.metadata,\r\n ...callOptions.metadata,\r\n },\r\n ...callOptions,\r\n });\r\n },\r\n trackTool: async (name: string, { costUSD, metadata }: { costUSD: number; metadata?: Record<string, any> }) => {\r\n // Record non-LLM tool usage as a custom usage event\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: `tool:${name}`,\r\n provider: 'tool',\r\n usage: {\r\n inputTokens: 0,\r\n outputTokens: 0,\r\n totalTokens: 0,\r\n },\r\n cost: {\r\n inputCostUSD: 0,\r\n outputCostUSD: costUSD,\r\n totalUSD: costUSD,\r\n currency: 'USD',\r\n },\r\n customerId,\r\n metadata: {\r\n ...sessionOptions.metadata,\r\n ...metadata,\r\n tool: name,\r\n },\r\n };\r\n\r\n meter.recordUsage({\r\n model: `tool:${name}`,\r\n provider: 'tool',\r\n inputTokens: 0,\r\n outputTokens: 0,\r\n customerId,\r\n metadata: event.metadata,\r\n });\r\n\r\n await meter.flush();\r\n },\r\n };\r\n}\r\n\r\n// Attach session helper to createVibezModel function\r\nexport const vibezcheck: typeof createVibezModel & {\r\n session: typeof createVibezSession;\r\n} = Object.assign(createVibezModel, {\r\n session: createVibezSession,\r\n});\r\n"],"mappings":"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","names":["rawUsage","customerObj","Stripe"]}
|
|
1
|
+
{"version":3,"sources":["../../src/ai-sdk/index.ts","../../src/types.ts","../../src/meter/client.ts","../../src/meter/batcher.ts","../../src/meter/extractors/openai.ts","../../src/meter/extractors/anthropic.ts","../../src/meter/extractors/gemini.ts","../../src/meter/extractors/generic.ts","../../src/meter/extractors/index.ts","../../src/pricing/table.ts","../../src/pricing/calculator.ts","../../src/customers/helpers.ts","../../src/meter/stream.ts","../../src/ai-sdk/with-billing.ts","../../src/ai-sdk/declarative.ts"],"sourcesContent":["export * from './with-billing';\r\nexport * from './declarative';\r\n","import type Stripe from 'stripe';\r\n\r\n/**\r\n * Known supported model identifiers with full IDE autocomplete\r\n */\r\nexport type SupportedOpenAIModel =\r\n | 'openai/gpt-4o'\r\n | 'openai/gpt-4o-mini'\r\n | 'openai/gpt-4.5-preview'\r\n | 'openai/gpt-4.1'\r\n | 'openai/gpt-4.1-nano'\r\n | 'openai/gpt-4-turbo'\r\n | 'openai/gpt-4'\r\n | 'openai/gpt-3.5-turbo'\r\n | 'openai/o1'\r\n | 'openai/o1-mini'\r\n | 'openai/o3'\r\n | 'openai/o3-mini'\r\n | 'openai/gpt-5'\r\n | 'openai/gpt-5-mini'\r\n | 'openai/gpt-5.6-sol'\r\n | 'openai/gpt-5.6-terra'\r\n | 'openai/gpt-5.6-luna'\r\n | 'openai/text-embedding-3-small'\r\n | 'openai/text-embedding-3-large'\r\n | 'gpt-4o'\r\n | 'gpt-4o-mini'\r\n | 'gpt-4.5-preview'\r\n | 'gpt-4.5'\r\n | 'gpt-4.1'\r\n | 'gpt-4.1-nano'\r\n | 'gpt-4-turbo'\r\n | 'gpt-4'\r\n | 'gpt-3.5-turbo'\r\n | 'o1'\r\n | 'o1-mini'\r\n | 'o3'\r\n | 'o3-mini'\r\n | 'gpt-5'\r\n | 'gpt-5-mini'\r\n | 'gpt-5.6-sol'\r\n | 'gpt-5.6-terra'\r\n | 'gpt-5.6-luna';\r\n\r\nexport type SupportedAnthropicModel =\r\n | 'anthropic/claude-3-7-sonnet'\r\n | 'anthropic/claude-3-5-sonnet'\r\n | 'anthropic/claude-3-5-haiku'\r\n | 'anthropic/claude-3-opus'\r\n | 'anthropic/claude-3-haiku'\r\n | 'anthropic/claude-2.1'\r\n | 'anthropic/claude-2.0'\r\n | 'anthropic/claude-opus-5'\r\n | 'anthropic/haiku-4.5'\r\n | 'claude-3-7-sonnet'\r\n | 'claude-3-5-sonnet'\r\n | 'claude-3-5-haiku'\r\n | 'claude-3-opus'\r\n | 'claude-3-haiku'\r\n | 'claude-2.1'\r\n | 'claude-2.0'\r\n | 'claude-opus-5'\r\n | 'haiku-4.5';\r\n\r\nexport type SupportedGoogleModel =\r\n | 'google/gemini-2.5-pro'\r\n | 'google/gemini-2.5-flash'\r\n | 'google/gemini-2.0-flash'\r\n | 'google/gemini-2.0-flash-lite'\r\n | 'google/gemini-2.0-pro'\r\n | 'google/gemini-1.5-pro'\r\n | 'google/gemini-1.5-flash'\r\n | 'google/gemini-1.5-flash-8b'\r\n | 'google/gemini-1.0-pro'\r\n | 'google/gemini-3.7-flash'\r\n | 'google/gemini-3.1-pro'\r\n | 'gemini-2.5-pro'\r\n | 'gemini-2.5-flash'\r\n | 'gemini-2.0-flash'\r\n | 'gemini-2.0-flash-lite'\r\n | 'gemini-2.0-pro'\r\n | 'gemini-1.5-pro'\r\n | 'gemini-1.5-flash'\r\n | 'gemini-1.5-flash-8b'\r\n | 'gemini-1.0-pro'\r\n | 'gemini-3.7-flash'\r\n | 'gemini-3.1-pro';\r\n\r\nexport type SupportedDeepSeekModel =\r\n | 'deepseek/deepseek-chat'\r\n | 'deepseek/deepseek-reasoner'\r\n | 'deepseek/deepseek-v3'\r\n | 'deepseek/deepseek-r1'\r\n | 'deepseek/deepseek-v4-pro'\r\n | 'deepseek-chat'\r\n | 'deepseek-reasoner'\r\n | 'deepseek-v3'\r\n | 'deepseek-r1'\r\n | 'deepseek-v4-pro';\r\n\r\nexport type SupportedXAIModel =\r\n | 'xai/grok-3'\r\n | 'xai/grok-3-mini'\r\n | 'xai/grok-2'\r\n | 'xai/grok-2-vision'\r\n | 'xai/grok-beta'\r\n | 'grok-3'\r\n | 'grok-3-mini'\r\n | 'grok-2'\r\n | 'grok-2-vision'\r\n | 'grok-beta';\r\n\r\nexport type SupportedMistralModel =\r\n | 'mistral/mistral-large-latest'\r\n | 'mistral/codestral-latest'\r\n | 'mistral/mistral-small-latest'\r\n | 'mistral/ministral-8b-latest'\r\n | 'mistral-large-latest'\r\n | 'codestral-latest'\r\n | 'mistral-small-latest'\r\n | 'ministral-8b-latest';\r\n\r\nexport type SupportedGroqModel =\r\n | 'groq/llama-3.3-70b-versatile'\r\n | 'groq/llama-3.1-70b-versatile'\r\n | 'groq/llama-3.1-8b-instant'\r\n | 'groq/deepseek-r1-distill-llama-70b'\r\n | 'llama-3.3-70b-versatile'\r\n | 'llama-3.1-70b-versatile'\r\n | 'llama-3.1-8b-instant'\r\n | 'deepseek-r1-distill-llama-70b';\r\n\r\nexport type SupportedCohereModel =\r\n | 'cohere/command-r-plus'\r\n | 'cohere/command-r'\r\n | 'command-r-plus'\r\n | 'command-r';\r\n\r\nexport type KnownModel =\r\n | SupportedOpenAIModel\r\n | SupportedAnthropicModel\r\n | SupportedGoogleModel\r\n | SupportedDeepSeekModel\r\n | SupportedXAIModel\r\n | SupportedMistralModel\r\n | SupportedGroqModel\r\n | SupportedCohereModel;\r\n\r\n/**\r\n * Union of all known model IDs with loose string fallback for custom / future models\r\n */\r\nexport type SupportedModel = KnownModel | (string & {});\r\n\r\n/**\r\n * Detailed token usage breakdown\r\n */\r\nexport interface TokenUsage {\r\n /** Input/Prompt tokens */\r\n inputTokens: number;\r\n /** Total output/completion tokens (including reasoning) */\r\n outputTokens: number;\r\n /** Total tokens (input + output) */\r\n totalTokens: number;\r\n /** Hidden reasoning / thinking tokens (e.g. o1/o3/GPT-5, Claude 3.7 Thinking, Gemini 3.7 Thoughts) */\r\n reasoningTokens?: number;\r\n /** Visible output tokens (outputTokens - reasoningTokens) */\r\n visibleOutputTokens?: number;\r\n /** Cached input tokens read from KV cache / prompt cache */\r\n cachedTokens?: number;\r\n /** Cache write / creation tokens */\r\n cacheWriteTokens?: number;\r\n}\r\n\r\n/**\r\n * Calculated inference cost breakdown\r\n */\r\nexport interface InferenceCost {\r\n /** Cost for standard input prompt tokens in USD */\r\n inputCostUSD: number;\r\n /** Cost for output completion tokens in USD */\r\n outputCostUSD: number;\r\n /** Cost for reasoning/thinking tokens in USD (if applicable) */\r\n reasoningCostUSD?: number;\r\n /** Savings from prompt caching in USD */\r\n cachedDiscountUSD?: number;\r\n /** Total computed base inference cost in USD */\r\n totalUSD: number;\r\n /** Wholesale provider cost in USD */\r\n wholesaleTotalUSD?: number;\r\n /** Amount billed to customer in USD */\r\n billedUSD?: number;\r\n /** Net developer profit in USD */\r\n profitUSD?: number;\r\n /** Retail price after developer markup (if markup applied) */\r\n retailUSD?: number;\r\n /** Currency (defaults to 'USD') */\r\n currency: string;\r\n}\r\n\r\n/**\r\n * Structured Customer Information with rich metadata, multi-tenancy & billing attributes\r\n */\r\nexport interface CustomerInfo {\r\n /** Internal user ID or Stripe customer ID ('cus_xxx', 'usr_123') */\r\n id?: string;\r\n /** Explicit user ID */\r\n userId?: string;\r\n /** Customer email */\r\n email?: string;\r\n /** Customer full name or business display name */\r\n name?: string;\r\n /** Phone number */\r\n phone?: string;\r\n /** Multi-tenant Organization or Company ID */\r\n orgId?: string;\r\n /** Organization / Company name */\r\n orgName?: string;\r\n /** Multi-tenant Organization ID alias */\r\n organizationId?: string;\r\n /** Team / Workspace identifier */\r\n teamId?: string;\r\n /** Workspace identifier alias */\r\n workspaceId?: string;\r\n /** User Role within organization (e.g. 'admin', 'member', 'owner') */\r\n role?: string;\r\n /** Subscription Plan name (e.g. 'free', 'starter', 'pro', 'enterprise') */\r\n plan?: string;\r\n /** Billing Tier (e.g. 'tier_1', 'growth', 'unlimited') */\r\n tier?: string;\r\n /** Billing currency (defaults to 'usd') */\r\n currency?: string;\r\n /** Current prepaid credit balance in USD */\r\n balanceUSD?: number;\r\n /** Flexible custom metadata (key-value attributes) */\r\n metadata?: Record<string, string | number | boolean | null>;\r\n /** Arbitrary extra developer fields */\r\n [key: string]: any;\r\n}\r\n\r\n/**\r\n * Customer identification parameter: can be a string ('cus_xxx' or 'user@example.com') or a rich structured object\r\n */\r\nexport type CustomerParam = string | CustomerInfo;\r\n\r\n/**\r\n * Full usage event emitted upon completion of an LLM call or stream\r\n */\r\nexport interface UsageEvent {\r\n /** Unique ID for the event */\r\n id?: string;\r\n /** Timestamp ISO string */\r\n timestamp: string;\r\n /** Model name (e.g. 'gpt-5.6-sol', 'claude-3-7-sonnet') */\r\n model: string;\r\n /** Provider (e.g. 'openai', 'anthropic', 'google', 'mistral', 'groq', 'deepseek', 'generic') */\r\n provider: string;\r\n /** Token breakdown */\r\n usage: TokenUsage;\r\n /** Computed cost */\r\n cost: InferenceCost;\r\n /** Customer ID (Stripe customer ID, internal userId, or anonymous) */\r\n customerId?: string;\r\n /** Optional customer email */\r\n customerEmail?: string;\r\n /** Full customer profile snapshot if provided */\r\n customer?: CustomerInfo;\r\n /** Custom developer metadata (e.g. userId, orgId, feature, session) */\r\n metadata?: Record<string, string | number | boolean>;\r\n}\r\n\r\n/**\r\n * Event emitted when a circuit breaker budget or token limit is reached\r\n */\r\nexport interface BudgetExceededEvent {\r\n reason: 'cost_per_call_exceeded' | 'total_budget_exceeded' | 'max_tokens_exceeded';\r\n limit: number;\r\n current: number;\r\n model: string;\r\n customerId?: string;\r\n message: string;\r\n}\r\n\r\n/**\r\n * Error thrown when an Agent Circuit Breaker trips\r\n */\r\nexport class VibezCircuitBreakerError extends Error {\r\n public readonly event: BudgetExceededEvent;\r\n\r\n constructor(event: BudgetExceededEvent) {\r\n super(event.message);\r\n this.name = 'VibezCircuitBreakerError';\r\n this.event = event;\r\n }\r\n}\r\n\r\n/**\r\n * Circuit Breaker / Budget Guardrail Configuration\r\n */\r\nexport interface CircuitBreakerOptions {\r\n /** Maximum allowed USD cost for a single generation or stream (default: 0.50) */\r\n maxCostPerCallUSD?: number;\r\n /** Cumulative budget limit for customer/session in USD (e.g. 5.00) */\r\n maxBudgetUSD?: number;\r\n /** Hard ceiling on total tokens per generation (e.g. 10000) */\r\n maxTokensPerCall?: number;\r\n /** Model to gracefully fall back to if budget limit is exceeded instead of hard erroring */\r\n fallbackModelOnBudget?: string;\r\n /** Callback fired when circuit breaker trips */\r\n onBudgetExceeded?: (event: BudgetExceededEvent) => void | Promise<void>;\r\n /** Whether to throw a VibezCircuitBreakerError if limit exceeded (default: false) */\r\n throwOnBudgetExceeded?: boolean;\r\n}\r\n\r\n/**\r\n * Pluggable Database / Storage Adapter Interface\r\n */\r\nexport interface DatabaseAdapter {\r\n name: string;\r\n save: (event: UsageEvent) => Promise<void> | void;\r\n getBalance?: (customerId: string) => Promise<number | undefined>;\r\n}\r\n\r\n/**\r\n * Pluggable Payment Provider Interface\r\n */\r\nexport interface PaymentProvider {\r\n name: string;\r\n charge?: (costUSD: number, event: UsageEvent) => Promise<void> | void;\r\n checkBalance?: (customerId: string) => Promise<{ ok: boolean; balanceUSD?: number }>;\r\n}\r\n\r\n/**\r\n * Billing Configuration (Universal Auto-Debit, Postpaid metered invoice vs Prepaid credit wallet, Pluggable Providers)\r\n */\r\nexport interface BillingConfig {\r\n /** 'postpaid' = Invoiced at month's end; 'prepaid' = Deducted from credit wallet, locks at $0 */\r\n mode?: 'postpaid' | 'prepaid';\r\n /** Available prepaid credit balance in USD */\r\n balanceUSD?: number;\r\n /** Action when balance is low: 'warn' logs/sends event, 'throw' throws CreditExhaustedError */\r\n onLowBalance?: 'warn' | 'throw';\r\n /** Payment Provider Gateway (default: 'stripe') */\r\n provider?: 'stripe' | 'polar' | 'lemonsqueezy' | 'paystack' | PaymentProvider;\r\n /** Custom charge handler for internal credit wallets / bespoke payment logic */\r\n charge?: (costUSD: number, event: UsageEvent) => Promise<void> | void;\r\n}\r\n\r\n/**\r\n * Profit Pricing & Markup Configuration\r\n */\r\nexport interface PricingConfig {\r\n /** Profit margin multiplier (e.g. 1.5 = Cost + 50% profit margin automatically added) */\r\n margin?: number;\r\n /** Minimum charge in USD for any single call (e.g. 0.01 = at least 1 cent) */\r\n minimumChargeUSD?: number;\r\n}\r\n\r\n/**\r\n * Inline Rate Card Configuration for 1-line custom/newly released model pricing\r\n */\r\nexport interface InlineRateConfig {\r\n /** Input tokens price per 1 Million tokens in USD */\r\n in: number;\r\n /** Output tokens price per 1 Million tokens in USD */\r\n out?: number;\r\n output?: number;\r\n /** Reasoning/thinking tokens price per 1 Million tokens in USD (optional) */\r\n reasoning?: number;\r\n /** Cached input tokens price per 1 Million tokens in USD (optional) */\r\n cached?: number;\r\n}\r\n\r\n/**\r\n * Non-LLM Tool execution metering options\r\n */\r\nexport interface ToolMeterOptions {\r\n /** Fixed cost in USD for this tool execution (e.g. 0.01 for search, 0.04 for image) */\r\n costUSD: number;\r\n /** Customer identifier to attribute tool cost to */\r\n customer?: CustomerParam;\r\n /** Additional metadata */\r\n metadata?: Record<string, string | number | boolean>;\r\n}\r\n\r\n/**\r\n * Configuration options for the VibezCheck Meter\r\n */\r\nexport interface MeterOptions extends CircuitBreakerOptions {\r\n /** Stripe API Key (sk_* or rk_*). If omitted, runs in local telemetry/free mode */\r\n apiKey?: string;\r\n /** Existing Stripe SDK instance (optional) */\r\n stripe?: Stripe;\r\n /** Default Stripe Meter Event Name (default: 'token-billing-tokens') */\r\n eventName?: string;\r\n /** Batching options to optimize Stripe API calls */\r\n batching?: {\r\n /** Max events per batch (default: 50) */\r\n maxBatchSize?: number;\r\n /** Flush interval in milliseconds (default: 50ms) */\r\n flushIntervalMs?: number;\r\n };\r\n /** Callback fired whenever usage is extracted (works with or without Stripe) */\r\n onUsage?: (event: UsageEvent) => void | Promise<void>;\r\n /** Error handler callback */\r\n onError?: (error: Error, events: UsageEvent[]) => void;\r\n /** Markup multiplier for retail price calculations (e.g. 1.3 for 30% profit) */\r\n markupMultiplier?: number;\r\n /** Enable debug console logging (default: false) */\r\n debug?: boolean;\r\n}\r\n\r\n/**\r\n * Stream wrap options\r\n */\r\nexport interface StreamWrapOptions extends CircuitBreakerOptions {\r\n /** Customer identifier or email or object */\r\n customer?: CustomerParam;\r\n /** Direct customer ID string */\r\n customerId?: string;\r\n /** Model override if not automatically detectable */\r\n model?: string;\r\n /** Provider override if not automatically detectable */\r\n provider?: string;\r\n /** Billing mode configuration (postpaid vs prepaid) */\r\n billing?: BillingConfig;\r\n /** Profit margin & minimum charge configuration */\r\n pricing?: PricingConfig;\r\n /** 1-line inline pricing rate card */\r\n rate?: InlineRateConfig;\r\n /** Whether to capture tokens if the client aborts or closes tab mid-stream (default: true) */\r\n captureOnAbort?: boolean;\r\n /** Execution runtime environment (default: 'auto') */\r\n runtime?: 'auto' | 'serverless' | 'edge' | 'node';\r\n /** Custom metadata attached to the usage event */\r\n metadata?: Record<string, string | number | boolean>;\r\n /** Custom usage callback for this specific stream */\r\n onUsage?: (event: UsageEvent) => void | Promise<void>;\r\n}\r\n\r\n/**\r\n * Direct usage recording options\r\n */\r\nexport interface RecordUsageOptions {\r\n model: string;\r\n provider?: string;\r\n inputTokens: number;\r\n outputTokens: number;\r\n reasoningTokens?: number;\r\n cachedTokens?: number;\r\n customer?: CustomerParam;\r\n customerId?: string;\r\n metadata?: Record<string, string | number | boolean>;\r\n}\r\n\r\n/**\r\n * Model Pricing Rates (per 1 Million Tokens in USD)\r\n */\r\nexport interface ModelPricingRates {\r\n inputPer1M: number;\r\n outputPer1M: number;\r\n cachedInputPer1M?: number;\r\n reasoningPer1M?: number;\r\n cacheWritePer1M?: number;\r\n currency?: string;\r\n}\r\n\r\n/**\r\n * Aggregated Usage Summary\r\n */\r\nexport interface UsageSummary {\r\n totalRequests: number;\r\n totalTokens: number;\r\n totalInputTokens: number;\r\n totalOutputTokens: number;\r\n totalReasoningTokens: number;\r\n totalCostUSD: number;\r\n byModel: Record<\r\n string,\r\n {\r\n requests: number;\r\n tokens: number;\r\n costUSD: number;\r\n }\r\n >;\r\n}\r\n","import Stripe from 'stripe';\r\nimport type {\r\n MeterOptions,\r\n StreamWrapOptions,\r\n RecordUsageOptions,\r\n UsageEvent,\r\n UsageSummary,\r\n CustomerParam,\r\n} from '../types';\r\nimport { MeterBatcher } from './batcher';\r\nimport { detectAndExtractUsage } from './extractors';\r\nimport { calculateUsageCost } from '../pricing/calculator';\r\nimport { wrapUniversalStream } from './stream';\r\nimport { normalizeCustomer } from '../customers/helpers';\r\n\r\nexport class VibezMeter {\r\n private batcher: MeterBatcher;\r\n private stripeClient?: Stripe;\r\n private markupMultiplier?: number;\r\n\r\n constructor(options: MeterOptions = {}) {\r\n this.markupMultiplier = options.markupMultiplier;\r\n\r\n // Initialize Stripe client if apiKey or stripe instance is provided\r\n if (options.stripe) {\r\n this.stripeClient = options.stripe;\r\n } else if (options.apiKey || process.env.STRIPE_SECRET_KEY) {\r\n const key = options.apiKey || process.env.STRIPE_SECRET_KEY!;\r\n this.stripeClient = new Stripe(key, {\r\n appInfo: {\r\n name: 'vibezcheck',\r\n version: '0.5.3',\r\n url: 'https://vibezcheck.xyz',\r\n },\r\n });\r\n }\r\n\r\n this.batcher = new MeterBatcher({\r\n ...options,\r\n stripe: this.stripeClient,\r\n });\r\n }\r\n\r\n /**\r\n * Track token usage from a non-streaming response object (OpenAI, Anthropic, Gemini, etc.)\r\n */\r\n public trackUsage(\r\n response: any,\r\n options: {\r\n customer?: CustomerParam;\r\n customerId?: string;\r\n model?: string;\r\n provider?: string;\r\n metadata?: Record<string, string | number | boolean>;\r\n } = {}\r\n ): UsageEvent | null {\r\n const extracted = detectAndExtractUsage(response, options.model, options.provider);\r\n if (!extracted) {\r\n return null;\r\n }\r\n\r\n const model = options.model || extracted.model;\r\n const cost = calculateUsageCost(model, extracted.usage, this.markupMultiplier);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const mergedMeta = {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n };\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model,\r\n provider: extracted.provider,\r\n usage: extracted.usage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: mergedMeta,\r\n };\r\n\r\n this.batcher.enqueue(event);\r\n return event;\r\n }\r\n\r\n /**\r\n * Wrap any LLM stream (OpenAI, Anthropic, Gemini) with zero added latency\r\n */\r\n public wrapStream<T>(stream: T, options: StreamWrapOptions = {}): T {\r\n return wrapUniversalStream(stream, options, (event) => {\r\n this.batcher.enqueue(event);\r\n });\r\n }\r\n\r\n /**\r\n * Directly record token usage manually\r\n */\r\n public recordUsage(options: RecordUsageOptions & { customer?: CustomerParam }): UsageEvent {\r\n const inputTokens = options.inputTokens ?? 0;\r\n const outputTokens = options.outputTokens ?? 0;\r\n const reasoningTokens = options.reasoningTokens;\r\n const cachedTokens = options.cachedTokens;\r\n\r\n const usage = {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens,\r\n visibleOutputTokens:\r\n reasoningTokens !== undefined ? Math.max(0, outputTokens - reasoningTokens) : outputTokens,\r\n cachedTokens,\r\n };\r\n\r\n const cost = calculateUsageCost(options.model, usage, this.markupMultiplier);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const mergedMeta = {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n };\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: options.model,\r\n provider: options.provider || 'custom',\r\n usage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: mergedMeta,\r\n };\r\n\r\n this.batcher.enqueue(event);\r\n return event;\r\n }\r\n\r\n /**\r\n * Flush pending events to Stripe (vital for Serverless & Edge environments)\r\n */\r\n public async flush(): Promise<void> {\r\n await this.batcher.flush();\r\n }\r\n\r\n /**\r\n * Get in-memory aggregated usage statistics\r\n */\r\n public getUsageSummary(): UsageSummary {\r\n return this.batcher.getSummary();\r\n }\r\n\r\n /**\r\n * Reset in-memory ledger\r\n */\r\n public resetSummary(): void {\r\n this.batcher.resetLedger();\r\n }\r\n}\r\n\r\n/**\r\n * Factory function to create a VibezMeter instance\r\n */\r\nexport function createMeter(options: MeterOptions = {}): VibezMeter {\r\n return new VibezMeter(options);\r\n}\r\n","import type Stripe from 'stripe';\r\nimport type { UsageEvent, UsageSummary, MeterOptions } from '../types';\r\n\r\nexport class MeterBatcher {\r\n private queue: UsageEvent[] = [];\r\n private timer: NodeJS.Timeout | null = null;\r\n private isFlushing: boolean = false;\r\n private readonly maxBatchSize: number;\r\n private readonly flushIntervalMs: number;\r\n private readonly stripeClient?: Stripe;\r\n private readonly eventName: string;\r\n private readonly onUsageCallback?: (event: UsageEvent) => void | Promise<void>;\r\n private readonly onErrorCallback?: (error: Error, events: UsageEvent[]) => void;\r\n private readonly debug: boolean;\r\n\r\n // In-memory ledger for local stats\r\n private totalRequests = 0;\r\n private totalTokens = 0;\r\n private totalInputTokens = 0;\r\n private totalOutputTokens = 0;\r\n private totalReasoningTokens = 0;\r\n private totalCostUSD = 0;\r\n private byModel: Record<string, { requests: number; tokens: number; costUSD: number }> = {};\r\n\r\n constructor(options: MeterOptions = {}) {\r\n this.stripeClient = options.stripe;\r\n this.eventName = options.eventName || 'token-billing-tokens';\r\n this.maxBatchSize = options.batching?.maxBatchSize ?? 50;\r\n this.flushIntervalMs = options.batching?.flushIntervalMs ?? 50;\r\n this.onUsageCallback = options.onUsage;\r\n this.onErrorCallback = options.onError;\r\n this.debug = options.debug ?? false;\r\n }\r\n\r\n /**\r\n * Enqueue a usage event for batch dispatching\r\n */\r\n public enqueue(event: UsageEvent): void {\r\n // 1. Update in-memory local ledger\r\n this.recordInLedger(event);\r\n\r\n // 2. Fire onUsage hook immediately\r\n if (this.onUsageCallback) {\r\n try {\r\n const res = this.onUsageCallback(event);\r\n if (res instanceof Promise) {\r\n res.catch((err) => {\r\n if (this.debug) console.error('[vibezcheck] Error in onUsage callback:', err);\r\n });\r\n }\r\n } catch (err) {\r\n if (this.debug) console.error('[vibezcheck] Error in onUsage callback:', err);\r\n }\r\n }\r\n\r\n // 3. If no Stripe client is configured, we're done (local mode)\r\n if (!this.stripeClient) {\r\n if (this.debug) {\r\n console.log(\r\n `[vibezcheck:local] 📊 ${event.model} | Tokens: ${event.usage.totalTokens} | Cost: $${event.cost.totalUSD.toFixed(6)}`\r\n );\r\n }\r\n return;\r\n }\r\n\r\n // 4. Queue for Stripe dispatch\r\n this.queue.push(event);\r\n\r\n if (this.queue.length >= this.maxBatchSize) {\r\n this.flush().catch((err) => {\r\n if (this.debug) console.error('[vibezcheck] Batch flush error:', err);\r\n });\r\n } else if (!this.timer) {\r\n this.timer = setTimeout(() => {\r\n this.timer = null;\r\n this.flush().catch((err) => {\r\n if (this.debug) console.error('[vibezcheck] Debounce flush error:', err);\r\n });\r\n }, this.flushIntervalMs);\r\n }\r\n }\r\n\r\n /**\r\n * Immediately flush all queued events to Stripe\r\n */\r\n public async flush(): Promise<void> {\r\n if (this.timer) {\r\n clearTimeout(this.timer);\r\n this.timer = null;\r\n }\r\n\r\n if (this.queue.length === 0 || !this.stripeClient || this.isFlushing) {\r\n return;\r\n }\r\n\r\n this.isFlushing = true;\r\n const eventsToSend = [...this.queue];\r\n this.queue = [];\r\n\r\n try {\r\n await this.sendEventsToStripe(eventsToSend);\r\n } catch (error) {\r\n const err = error instanceof Error ? error : new Error(String(error));\r\n if (this.debug) {\r\n console.error('[vibezcheck] Failed to send meter events to Stripe:', err);\r\n }\r\n if (this.onErrorCallback) {\r\n this.onErrorCallback(err, eventsToSend);\r\n }\r\n } finally {\r\n this.isFlushing = false;\r\n // If new items were queued while flushing, trigger another flush\r\n if (this.queue.length > 0) {\r\n this.flush().catch(() => {});\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Sends events to Stripe Billing Meter Events API\r\n */\r\n private async sendEventsToStripe(events: UsageEvent[]): Promise<void> {\r\n if (!this.stripeClient) return;\r\n\r\n for (const event of events) {\r\n const customerId = event.customerId;\r\n if (!customerId) {\r\n // Skip events without customer attribution for Stripe billing\r\n continue;\r\n }\r\n\r\n const timestamp = event.timestamp || new Date().toISOString();\r\n const model = `${event.provider}/${event.model}`;\r\n\r\n // 1. Send Input Tokens Meter Event\r\n if (event.usage.inputTokens > 0) {\r\n try {\r\n await this.stripeClient.v2.billing.meterEvents.create({\r\n event_name: this.eventName,\r\n timestamp,\r\n payload: {\r\n stripe_customer_id: customerId,\r\n value: event.usage.inputTokens.toString(),\r\n model,\r\n token_type: 'input',\r\n cached_tokens: (event.usage.cachedTokens ?? 0).toString(),\r\n ...(event.metadata ? (event.metadata as any) : {}),\r\n },\r\n });\r\n } catch (e) {\r\n if (this.debug) console.warn('[vibezcheck] Input meter event error:', e);\r\n }\r\n }\r\n\r\n // 2. Send Output Tokens Meter Event\r\n if (event.usage.outputTokens > 0) {\r\n try {\r\n await this.stripeClient.v2.billing.meterEvents.create({\r\n event_name: this.eventName,\r\n timestamp,\r\n payload: {\r\n stripe_customer_id: customerId,\r\n value: event.usage.outputTokens.toString(),\r\n model,\r\n token_type: 'output',\r\n reasoning_tokens: (event.usage.reasoningTokens ?? 0).toString(),\r\n visible_tokens: (event.usage.visibleOutputTokens ?? event.usage.outputTokens).toString(),\r\n ...(event.metadata ? (event.metadata as any) : {}),\r\n },\r\n });\r\n } catch (e) {\r\n if (this.debug) console.warn('[vibezcheck] Output meter event error:', e);\r\n }\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Updates internal in-memory ledger\r\n */\r\n private recordInLedger(event: UsageEvent): void {\r\n this.totalRequests += 1;\r\n this.totalTokens += event.usage.totalTokens;\r\n this.totalInputTokens += event.usage.inputTokens;\r\n this.totalOutputTokens += event.usage.outputTokens;\r\n this.totalReasoningTokens += event.usage.reasoningTokens ?? 0;\r\n this.totalCostUSD += event.cost.totalUSD;\r\n\r\n const modelKey = event.model;\r\n if (!this.byModel[modelKey]) {\r\n this.byModel[modelKey] = { requests: 0, tokens: 0, costUSD: 0 };\r\n }\r\n this.byModel[modelKey].requests += 1;\r\n this.byModel[modelKey].tokens += event.usage.totalTokens;\r\n this.byModel[modelKey].costUSD += event.cost.totalUSD;\r\n }\r\n\r\n /**\r\n * Get in-memory usage summary\r\n */\r\n public getSummary(): UsageSummary {\r\n return {\r\n totalRequests: this.totalRequests,\r\n totalTokens: this.totalTokens,\r\n totalInputTokens: this.totalInputTokens,\r\n totalOutputTokens: this.totalOutputTokens,\r\n totalReasoningTokens: this.totalReasoningTokens,\r\n totalCostUSD: Number(this.totalCostUSD.toFixed(6)),\r\n byModel: { ...this.byModel },\r\n };\r\n }\r\n\r\n /**\r\n * Reset in-memory ledger\r\n */\r\n public resetLedger(): void {\r\n this.totalRequests = 0;\r\n this.totalTokens = 0;\r\n this.totalInputTokens = 0;\r\n this.totalOutputTokens = 0;\r\n this.totalReasoningTokens = 0;\r\n this.totalCostUSD = 0;\r\n this.byModel = {};\r\n }\r\n}\r\n","import type { TokenUsage } from '../../types';\r\n\r\nexport interface ExtractedUsage {\r\n model: string;\r\n provider: string;\r\n usage: TokenUsage;\r\n}\r\n\r\n/**\r\n * Extracts token usage from OpenAI synchronous responses (ChatCompletion, Responses, Embeddings)\r\n */\r\nexport function extractOpenAIResponseUsage(response: any): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // 1. Standard OpenAI ChatCompletion\r\n if ('choices' in response && 'usage' in response && response.usage) {\r\n const rawUsage = response.usage;\r\n const model = response.model || 'gpt-4o';\r\n\r\n const inputTokens = rawUsage.prompt_tokens ?? 0;\r\n const outputTokens = rawUsage.completion_tokens ?? 0;\r\n const reasoningTokens = rawUsage.completion_tokens_details?.reasoning_tokens ?? 0;\r\n const cachedTokens = rawUsage.prompt_tokens_details?.cached_tokens ?? 0;\r\n\r\n return {\r\n model,\r\n provider: 'openai',\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n // 2. OpenAI Embeddings Response\r\n if ('data' in response && 'usage' in response && response.usage && 'model' in response) {\r\n const rawUsage = response.usage;\r\n const inputTokens = rawUsage.prompt_tokens ?? 0;\r\n\r\n return {\r\n model: response.model || 'text-embedding-3-small',\r\n provider: 'openai',\r\n usage: {\r\n inputTokens,\r\n outputTokens: 0,\r\n totalTokens: inputTokens,\r\n },\r\n };\r\n }\r\n\r\n // 3. OpenAI Responses API (New standard)\r\n if ('status' in response && 'usage' in response && response.usage) {\r\n const rawUsage = response.usage;\r\n const model = response.model || 'gpt-5.6-sol';\r\n\r\n const inputTokens = rawUsage.input_tokens ?? rawUsage.prompt_tokens ?? 0;\r\n const outputTokens = rawUsage.output_tokens ?? rawUsage.completion_tokens ?? 0;\r\n const reasoningTokens =\r\n rawUsage.output_token_details?.reasoning_tokens ??\r\n rawUsage.completion_tokens_details?.reasoning_tokens ??\r\n 0;\r\n const cachedTokens =\r\n rawUsage.input_token_details?.cached_tokens ??\r\n rawUsage.prompt_tokens_details?.cached_tokens ??\r\n 0;\r\n\r\n return {\r\n model,\r\n provider: 'openai',\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n return null;\r\n}\r\n\r\n/**\r\n * Extracts token usage from an individual OpenAI stream chunk or stream accumulator\r\n */\r\nexport function inspectOpenAIStreamChunk(chunk: any): {\r\n model?: string;\r\n usage?: TokenUsage;\r\n} {\r\n if (!chunk || typeof chunk !== 'object') return {};\r\n\r\n const model = chunk.model;\r\n\r\n // Final chunk with usage object (when stream_options: { include_usage: true }, finish chunk, or Groq / DeepSeek / Mistral stream ending)\r\n const rawUsage =\r\n (chunk.type === 'finish' ? chunk.usage : null) ||\r\n chunk.usage ||\r\n chunk.token_usage ||\r\n chunk.x_groq?.usage ||\r\n chunk.usageMetadata;\r\n if (rawUsage) {\r\n let inputTokens = 0;\r\n let outputTokens = 0;\r\n let reasoningTokens = 0;\r\n let cachedTokens = 0;\r\n\r\n if (typeof rawUsage.inputTokens === 'object' && rawUsage.inputTokens !== null) {\r\n inputTokens = rawUsage.inputTokens.total ?? rawUsage.inputTokens.noCache ?? 0;\r\n cachedTokens = rawUsage.inputTokens.cacheRead ?? 0;\r\n } else if (typeof rawUsage.promptTokens === 'number') {\r\n inputTokens = rawUsage.promptTokens;\r\n } else if (typeof rawUsage.inputTokens === 'number') {\r\n inputTokens = rawUsage.inputTokens;\r\n } else {\r\n inputTokens =\r\n rawUsage.prompt_tokens ??\r\n rawUsage.input_tokens ??\r\n rawUsage.promptTokenCount ??\r\n 0;\r\n }\r\n\r\n if (typeof rawUsage.outputTokens === 'object' && rawUsage.outputTokens !== null) {\r\n outputTokens = rawUsage.outputTokens.total ?? rawUsage.outputTokens.text ?? 0;\r\n reasoningTokens = rawUsage.outputTokens.reasoning ?? 0;\r\n } else if (typeof rawUsage.completionTokens === 'number') {\r\n outputTokens = rawUsage.completionTokens;\r\n } else if (typeof rawUsage.outputTokens === 'number') {\r\n outputTokens = rawUsage.outputTokens;\r\n } else {\r\n outputTokens =\r\n rawUsage.completion_tokens ??\r\n rawUsage.output_tokens ??\r\n rawUsage.candidatesTokenCount ??\r\n 0;\r\n }\r\n\r\n if (!reasoningTokens) {\r\n reasoningTokens =\r\n rawUsage.completion_tokens_details?.reasoning_tokens ??\r\n rawUsage.output_token_details?.reasoning_tokens ??\r\n rawUsage.reasoning_tokens ??\r\n rawUsage.reasoningTokens ??\r\n rawUsage.thoughtsTokenCount ??\r\n 0;\r\n }\r\n\r\n if (!cachedTokens) {\r\n cachedTokens =\r\n rawUsage.prompt_tokens_details?.cached_tokens ??\r\n rawUsage.input_token_details?.cached_tokens ??\r\n rawUsage.prompt_cache_hit_tokens ??\r\n rawUsage.cached_tokens ??\r\n rawUsage.cachedTokens ??\r\n rawUsage.cachedContentTokenCount ??\r\n 0;\r\n }\r\n\r\n return {\r\n model,\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n // Response API stream event (response.completed or response.done)\r\n if (chunk.type === 'response.completed' || chunk.type === 'response.done') {\r\n if (chunk.response?.usage) {\r\n const rawUsage = chunk.response.usage;\r\n const inputTokens = rawUsage.input_tokens ?? 0;\r\n const outputTokens = rawUsage.output_tokens ?? 0;\r\n const reasoningTokens = rawUsage.output_token_details?.reasoning_tokens ?? 0;\r\n const cachedTokens = rawUsage.input_token_details?.cached_tokens ?? 0;\r\n\r\n return {\r\n model: chunk.response.model || model,\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n }\r\n\r\n return { model };\r\n}\r\n","import type { TokenUsage } from '../../types';\r\nimport type { ExtractedUsage } from './openai';\r\n\r\n/**\r\n * Extracts token usage from Anthropic synchronous responses\r\n */\r\nexport function extractAnthropicResponseUsage(response: any): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // Anthropic Message response has type: 'message' or role: 'assistant' with usage\r\n if (response.type === 'message' || ('content' in response && 'usage' in response)) {\r\n const rawUsage = response.usage || {};\r\n const model = response.model || 'claude-3-7-sonnet';\r\n\r\n const inputTokens = rawUsage.input_tokens ?? 0;\r\n const outputTokens = rawUsage.output_tokens ?? 0;\r\n const cachedTokens = rawUsage.cache_read_input_tokens ?? 0;\r\n const cacheWriteTokens = rawUsage.cache_creation_input_tokens ?? 0;\r\n\r\n // Check content blocks for thinking/reasoning tokens count or thinking blocks\r\n let reasoningTokens: number | undefined = undefined;\r\n if (Array.isArray(response.content)) {\r\n const thinkingBlocks = response.content.filter((b: any) => b.type === 'thinking');\r\n if (thinkingBlocks.length > 0) {\r\n // Approximate or extract explicit thinking tokens if present in metadata\r\n reasoningTokens = (rawUsage as any).thinking_tokens ?? undefined;\r\n }\r\n }\r\n\r\n return {\r\n model,\r\n provider: 'anthropic',\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens,\r\n visibleOutputTokens:\r\n reasoningTokens !== undefined ? Math.max(0, outputTokens - reasoningTokens) : outputTokens,\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n cacheWriteTokens: cacheWriteTokens > 0 ? cacheWriteTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n return null;\r\n}\r\n\r\n/**\r\n * Accumulates stream events across an Anthropic raw message stream\r\n */\r\nexport class AnthropicStreamAccumulator {\r\n private model: string = 'claude-3-7-sonnet';\r\n private inputTokens: number = 0;\r\n private outputTokens: number = 0;\r\n private cachedTokens: number = 0;\r\n private cacheWriteTokens: number = 0;\r\n private reasoningTokens: number = 0;\r\n\r\n processEvent(event: any): void {\r\n if (!event || typeof event !== 'object') return;\r\n\r\n // 1. message_start (contains model and initial input usage)\r\n if (event.type === 'message_start' && event.message) {\r\n if (event.message.model) {\r\n this.model = event.message.model;\r\n }\r\n if (event.message.usage) {\r\n this.inputTokens = event.message.usage.input_tokens ?? 0;\r\n this.cachedTokens = event.message.usage.cache_read_input_tokens ?? 0;\r\n this.cacheWriteTokens = event.message.usage.cache_creation_input_tokens ?? 0;\r\n }\r\n }\r\n\r\n // 2. message_delta (contains final output usage)\r\n if (event.type === 'message_delta' && event.usage) {\r\n this.outputTokens = event.usage.output_tokens ?? 0;\r\n if (event.usage.thinking_tokens) {\r\n this.reasoningTokens = event.usage.thinking_tokens;\r\n }\r\n }\r\n\r\n // 3. content_block_start / content_block_delta for thinking blocks\r\n if (event.type === 'content_block_start' && event.content_block?.type === 'thinking') {\r\n // thinking block detected\r\n }\r\n }\r\n\r\n getUsage(): ExtractedUsage {\r\n return {\r\n model: this.model,\r\n provider: 'anthropic',\r\n usage: {\r\n inputTokens: this.inputTokens,\r\n outputTokens: this.outputTokens,\r\n totalTokens: this.inputTokens + this.outputTokens,\r\n reasoningTokens: this.reasoningTokens > 0 ? this.reasoningTokens : undefined,\r\n visibleOutputTokens:\r\n this.reasoningTokens > 0\r\n ? Math.max(0, this.outputTokens - this.reasoningTokens)\r\n : this.outputTokens,\r\n cachedTokens: this.cachedTokens > 0 ? this.cachedTokens : undefined,\r\n cacheWriteTokens: this.cacheWriteTokens > 0 ? this.cacheWriteTokens : undefined,\r\n },\r\n };\r\n }\r\n}\r\n","import type { TokenUsage } from '../../types';\r\nimport type { ExtractedUsage } from './openai';\r\n\r\n/**\r\n * Extracts token usage from Google Gemini API response or chunk\r\n */\r\nexport function extractGeminiResponseUsage(\r\n response: any,\r\n fallbackModel: string = 'gemini-3.7-flash'\r\n): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // Gemini returns usageMetadata on response or GenerateContentResult\r\n const usageMetadata = response.usageMetadata || response.response?.usageMetadata;\r\n\r\n if (usageMetadata) {\r\n const inputTokens = usageMetadata.promptTokenCount ?? 0;\r\n const baseOutputTokens = usageMetadata.candidatesTokenCount ?? 0;\r\n const thoughtsTokenCount =\r\n usageMetadata.thoughtsTokenCount ?? (usageMetadata as any).reasoningTokenCount ?? 0;\r\n const cachedTokens = usageMetadata.cachedContentTokenCount ?? 0;\r\n\r\n const totalOutput = baseOutputTokens + thoughtsTokenCount;\r\n const model = response.model || response.response?.model || fallbackModel;\r\n\r\n return {\r\n model,\r\n provider: 'google',\r\n usage: {\r\n inputTokens,\r\n outputTokens: totalOutput,\r\n totalTokens: inputTokens + totalOutput,\r\n reasoningTokens: thoughtsTokenCount > 0 ? thoughtsTokenCount : undefined,\r\n visibleOutputTokens: baseOutputTokens,\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n return null;\r\n}\r\n","import type { TokenUsage } from '../../types';\r\nimport type { ExtractedUsage } from './openai';\r\n\r\n/**\r\n * Extracts token usage from generic LLM provider objects (DeepSeek, Groq, Mistral, Ollama, Cohere, Together)\r\n */\r\nexport function extractGenericResponseUsage(\r\n response: any,\r\n fallbackModel: string = 'generic-llm',\r\n fallbackProvider: string = 'generic'\r\n): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // Check common usage property locations\r\n const usage = response.usage || response.token_usage || response.usageMetadata;\r\n\r\n if (usage) {\r\n let inputTokens = 0;\r\n let outputTokens = 0;\r\n let reasoningTokens = 0;\r\n let cachedTokens = 0;\r\n\r\n if (typeof usage.inputTokens === 'object' && usage.inputTokens !== null) {\r\n inputTokens = usage.inputTokens.total ?? usage.inputTokens.noCache ?? 0;\r\n cachedTokens = usage.inputTokens.cacheRead ?? 0;\r\n } else if (typeof usage.promptTokens === 'number') {\r\n inputTokens = usage.promptTokens;\r\n } else if (typeof usage.inputTokens === 'number') {\r\n inputTokens = usage.inputTokens;\r\n } else {\r\n inputTokens =\r\n usage.prompt_tokens ??\r\n usage.input_tokens ??\r\n usage.promptTokenCount ??\r\n usage.prompt_eval_count ??\r\n 0;\r\n }\r\n\r\n if (typeof usage.outputTokens === 'object' && usage.outputTokens !== null) {\r\n outputTokens = usage.outputTokens.total ?? usage.outputTokens.text ?? 0;\r\n reasoningTokens = usage.outputTokens.reasoning ?? 0;\r\n } else if (typeof usage.completionTokens === 'number') {\r\n outputTokens = usage.completionTokens;\r\n } else if (typeof usage.outputTokens === 'number') {\r\n outputTokens = usage.outputTokens;\r\n } else {\r\n outputTokens =\r\n usage.completion_tokens ??\r\n usage.output_tokens ??\r\n usage.candidatesTokenCount ??\r\n usage.eval_count ??\r\n 0;\r\n }\r\n\r\n if (!reasoningTokens) {\r\n reasoningTokens =\r\n usage.reasoning_tokens ??\r\n usage.thoughtsTokenCount ??\r\n usage.completion_tokens_details?.reasoning_tokens ??\r\n 0;\r\n }\r\n\r\n if (!cachedTokens) {\r\n cachedTokens =\r\n usage.prompt_tokens_details?.cached_tokens ??\r\n usage.cached_tokens ??\r\n usage.cachedContentTokenCount ??\r\n 0;\r\n }\r\n\r\n const model = response.model || fallbackModel;\r\n const provider = response.provider || fallbackProvider;\r\n\r\n return {\r\n model,\r\n provider,\r\n usage: {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n },\r\n };\r\n }\r\n\r\n return null;\r\n}\r\n","import type { ExtractedUsage } from './openai';\r\nimport { extractOpenAIResponseUsage } from './openai';\r\nimport { extractAnthropicResponseUsage } from './anthropic';\r\nimport { extractGeminiResponseUsage } from './gemini';\r\nimport { extractGenericResponseUsage } from './generic';\r\n\r\nexport * from './openai';\r\nexport * from './anthropic';\r\nexport * from './gemini';\r\nexport * from './generic';\r\n\r\n/**\r\n * Universal polymorphic response detector\r\n */\r\nexport function detectAndExtractUsage(\r\n response: any,\r\n fallbackModel?: string,\r\n fallbackProvider?: string\r\n): ExtractedUsage | null {\r\n if (!response || typeof response !== 'object') return null;\r\n\r\n // 1. Try OpenAI\r\n const openaiResult = extractOpenAIResponseUsage(response);\r\n if (openaiResult) return openaiResult;\r\n\r\n // 2. Try Anthropic\r\n const anthropicResult = extractAnthropicResponseUsage(response);\r\n if (anthropicResult) return anthropicResult;\r\n\r\n // 3. Try Gemini\r\n const geminiResult = extractGeminiResponseUsage(response, fallbackModel);\r\n if (geminiResult) return geminiResult;\r\n\r\n // 4. Try Generic\r\n const genericResult = extractGenericResponseUsage(response, fallbackModel, fallbackProvider);\r\n if (genericResult) return genericResult;\r\n\r\n return null;\r\n}\r\n","import type { ModelPricingRates } from '../types';\r\n\r\n/**\r\n * Built-in Registry of Model Pricing (USD per 1 Million Tokens)\r\n * Sourced from official 2026 provider pricing tables.\r\n */\r\nexport const MODEL_PRICING_TABLE: Record<string, ModelPricingRates> = {\r\n // --- OpenAI (Modern & Reasoning) ---\r\n 'gpt-5.6-sol': { inputPer1M: 4.0, outputPer1M: 20.0, cachedInputPer1M: 0.4 },\r\n 'gpt-5.6-terra': { inputPer1M: 2.0, outputPer1M: 12.0, cachedInputPer1M: 0.2 },\r\n 'gpt-5.6-luna': { inputPer1M: 0.2, outputPer1M: 1.2, cachedInputPer1M: 0.02 },\r\n 'gpt-5': { inputPer1M: 4.0, outputPer1M: 20.0, cachedInputPer1M: 0.4 },\r\n 'gpt-5-mini': { inputPer1M: 0.2, outputPer1M: 1.2, cachedInputPer1M: 0.02 },\r\n 'o1': { inputPer1M: 15.0, outputPer1M: 60.0, cachedInputPer1M: 7.5 },\r\n 'o1-mini': { inputPer1M: 1.1, outputPer1M: 4.4, cachedInputPer1M: 0.55 },\r\n 'o3': { inputPer1M: 15.0, outputPer1M: 60.0, cachedInputPer1M: 7.5 },\r\n 'o3-mini': { inputPer1M: 1.1, outputPer1M: 4.4, cachedInputPer1M: 0.55 },\r\n 'gpt-4o': { inputPer1M: 2.5, outputPer1M: 10.0, cachedInputPer1M: 1.25 },\r\n 'gpt-4o-mini': { inputPer1M: 0.15, outputPer1M: 0.6, cachedInputPer1M: 0.075 },\r\n 'gpt-4.5': { inputPer1M: 75.0, outputPer1M: 150.0, cachedInputPer1M: 37.5 },\r\n 'gpt-4.5-preview': { inputPer1M: 75.0, outputPer1M: 150.0, cachedInputPer1M: 37.5 },\r\n 'chatgpt-4o-latest': { inputPer1M: 5.0, outputPer1M: 15.0 },\r\n 'gpt-4.1': { inputPer1M: 2.0, outputPer1M: 8.0, cachedInputPer1M: 1.0 },\r\n 'gpt-4.1-nano': { inputPer1M: 0.1, outputPer1M: 0.4, cachedInputPer1M: 0.05 },\r\n 'gpt-6-astra': { inputPer1M: 5.0, outputPer1M: 25.0, cachedInputPer1M: 0.5 },\r\n 'gpt-6-astra-fast': { inputPer1M: 3.0, outputPer1M: 15.0, cachedInputPer1M: 0.3 },\r\n 'gpt-image-2.5-flare': { inputPer1M: 0.0, outputPer1M: 0.04 },\r\n 'gpt-image-2.5-sunburst': { inputPer1M: 0.0, outputPer1M: 0.08 },\r\n\r\n // --- OpenAI (Legacy & Backward Compatibility) ---\r\n 'gpt-4-turbo': { inputPer1M: 10.0, outputPer1M: 30.0, cachedInputPer1M: 5.0 },\r\n 'gpt-4-turbo-preview': { inputPer1M: 10.0, outputPer1M: 30.0, cachedInputPer1M: 5.0 },\r\n 'gpt-4': { inputPer1M: 30.0, outputPer1M: 60.0 },\r\n 'gpt-4-32k': { inputPer1M: 60.0, outputPer1M: 120.0 },\r\n 'gpt-3.5-turbo': { inputPer1M: 0.5, outputPer1M: 1.5 },\r\n 'gpt-3.5-turbo-16k': { inputPer1M: 3.0, outputPer1M: 4.0 },\r\n 'text-embedding-3-small': { inputPer1M: 0.02, outputPer1M: 0.0 },\r\n 'text-embedding-3-large': { inputPer1M: 0.13, outputPer1M: 0.0 },\r\n 'text-embedding-ada-002': { inputPer1M: 0.10, outputPer1M: 0.0 },\r\n\r\n // --- Anthropic (Modern & Extended Thinking) ---\r\n 'claude-3-7-sonnet': { inputPer1M: 0.59, outputPer1M: 2.93, cachedInputPer1M: 0.3 },\r\n 'claude-sonnet-5': { inputPer1M: 2.0, outputPer1M: 10.0, cachedInputPer1M: 0.3 },\r\n 'claude-3-5-sonnet': { inputPer1M: 3.0, outputPer1M: 15.0, cachedInputPer1M: 0.3 },\r\n 'claude-3-5-haiku': { inputPer1M: 0.8, outputPer1M: 4.0, cachedInputPer1M: 0.08 },\r\n 'haiku-4.5': { inputPer1M: 1.0, outputPer1M: 5.0, cachedInputPer1M: 0.1 },\r\n 'claude-opus-5': { inputPer1M: 5.0, outputPer1M: 25.0, cachedInputPer1M: 1.5 },\r\n 'claude-3-opus': { inputPer1M: 15.0, outputPer1M: 75.0, cachedInputPer1M: 1.5 },\r\n\r\n // --- Anthropic (Legacy & Backward Compatibility) ---\r\n 'claude-3-sonnet': { inputPer1M: 3.0, outputPer1M: 15.0, cachedInputPer1M: 0.3 },\r\n 'claude-3-haiku': { inputPer1M: 0.25, outputPer1M: 1.25, cachedInputPer1M: 0.025 },\r\n 'claude-2.1': { inputPer1M: 8.0, outputPer1M: 24.0 },\r\n 'claude-2.0': { inputPer1M: 8.0, outputPer1M: 24.0 },\r\n 'claude-instant-1.2': { inputPer1M: 1.63, outputPer1M: 5.51 },\r\n\r\n // --- Google Gemini (Modern & Thoughts) ---\r\n 'gemini-3.7-flash': { inputPer1M: 0.75, outputPer1M: 3.75, cachedInputPer1M: 0.18 },\r\n 'gemini-3.1-pro': { inputPer1M: 2.0, outputPer1M: 12.0, cachedInputPer1M: 0.5 },\r\n 'gemini-3.5-flash': { inputPer1M: 1.5, outputPer1M: 9.0, cachedInputPer1M: 0.38 },\r\n 'gemini-3.1-flash-lite': { inputPer1M: 0.25, outputPer1M: 1.5, cachedInputPer1M: 0.06 },\r\n 'gemini-2.5-pro': { inputPer1M: 1.25, outputPer1M: 5.0, cachedInputPer1M: 0.3125 },\r\n 'gemini-2.5-flash': { inputPer1M: 0.15, outputPer1M: 0.6, cachedInputPer1M: 0.0375 },\r\n 'gemini-2.0-flash': { inputPer1M: 0.1, outputPer1M: 0.4, cachedInputPer1M: 0.025 },\r\n 'gemini-2.0-flash-lite': { inputPer1M: 0.075, outputPer1M: 0.3, cachedInputPer1M: 0.01875 },\r\n 'gemini-2.0-pro': { inputPer1M: 1.25, outputPer1M: 5.0, cachedInputPer1M: 0.3125 },\r\n\r\n // --- Google Gemini (Legacy & Backward Compatibility) ---\r\n 'gemini-1.5-pro': { inputPer1M: 1.25, outputPer1M: 5.0, cachedInputPer1M: 0.3125 },\r\n 'gemini-1.5-flash': { inputPer1M: 0.075, outputPer1M: 0.3, cachedInputPer1M: 0.01875 },\r\n 'gemini-1.5-flash-8b': { inputPer1M: 0.0375, outputPer1M: 0.15, cachedInputPer1M: 0.009375 },\r\n 'gemini-1.0-pro': { inputPer1M: 0.5, outputPer1M: 1.5 },\r\n\r\n // --- xAI Grok ---\r\n 'grok-4.6': { inputPer1M: 3.0, outputPer1M: 15.0 },\r\n 'grok-3': { inputPer1M: 3.0, outputPer1M: 15.0 },\r\n 'grok-3-mini': { inputPer1M: 0.3, outputPer1M: 1.5 },\r\n 'grok-2': { inputPer1M: 2.0, outputPer1M: 10.0 },\r\n 'grok-2-vision': { inputPer1M: 2.0, outputPer1M: 10.0 },\r\n 'grok-beta': { inputPer1M: 5.0, outputPer1M: 15.0 },\r\n\r\n // --- Mistral ---\r\n 'mistral-large-3': { inputPer1M: 2.0, outputPer1M: 6.0 },\r\n 'mistral-large-latest': { inputPer1M: 2.0, outputPer1M: 6.0 },\r\n 'mistral-large-2411': { inputPer1M: 2.0, outputPer1M: 6.0 },\r\n 'codestral-latest': { inputPer1M: 0.3, outputPer1M: 0.9 },\r\n 'mistral-medium-latest': { inputPer1M: 2.7, outputPer1M: 8.1 },\r\n 'mistral-medium-3-5': { inputPer1M: 2.0, outputPer1M: 6.0, cachedInputPer1M: 0.4 },\r\n 'mistral-medium-2604': { inputPer1M: 2.0, outputPer1M: 6.0, cachedInputPer1M: 0.4 },\r\n 'magistral-small-latest': { inputPer1M: 0.5, outputPer1M: 1.5, cachedInputPer1M: 0.1 },\r\n 'magistral-medium-latest': { inputPer1M: 2.0, outputPer1M: 6.0, cachedInputPer1M: 0.4 },\r\n 'mistral-small-latest': { inputPer1M: 0.2, outputPer1M: 0.6 },\r\n 'mistral-small-2603': { inputPer1M: 0.2, outputPer1M: 0.6, cachedInputPer1M: 0.05 },\r\n 'mistral-vibe-cli-fast': { inputPer1M: 0.2, outputPer1M: 0.6, cachedInputPer1M: 0.05 },\r\n 'mistral-vibe-cli-latest': { inputPer1M: 0.2, outputPer1M: 0.6, cachedInputPer1M: 0.05 },\r\n 'codestral-2508': { inputPer1M: 0.3, outputPer1M: 0.9, cachedInputPer1M: 0.08 },\r\n 'codestral-embed': { inputPer1M: 0.1, outputPer1M: 0.0 },\r\n 'mistral-embed-2312': { inputPer1M: 0.1, outputPer1M: 0.0 },\r\n 'zai-glm-5-2': { inputPer1M: 0.6, outputPer1M: 2.2, cachedInputPer1M: 0.15 },\r\n 'glm-5-2': { inputPer1M: 0.6, outputPer1M: 2.2, cachedInputPer1M: 0.15 },\r\n 'labs-leanstral-1-5': { inputPer1M: 0.2, outputPer1M: 0.6, cachedInputPer1M: 0.05 },\r\n 'ministral-8b-latest': { inputPer1M: 0.1, outputPer1M: 0.1 },\r\n 'ministral-3b-latest': { inputPer1M: 0.04, outputPer1M: 0.04 },\r\n 'open-mistral-7b': { inputPer1M: 0.2, outputPer1M: 0.2 },\r\n 'open-mixtral-8x7b': { inputPer1M: 0.7, outputPer1M: 0.7 },\r\n 'open-mixtral-8x22b': { inputPer1M: 2.0, outputPer1M: 6.0 },\r\n\r\n // --- Groq & Meta Llama LPUs ---\r\n 'llama-3.3-70b-versatile': { inputPer1M: 0.59, outputPer1M: 0.79 },\r\n 'llama-3.1-405b': { inputPer1M: 3.0, outputPer1M: 3.0 },\r\n 'llama-3.1-70b-versatile': { inputPer1M: 0.59, outputPer1M: 0.79 },\r\n 'llama-3.1-8b-instant': { inputPer1M: 0.05, outputPer1M: 0.08 },\r\n 'llama-3.2-1b-preview': { inputPer1M: 0.04, outputPer1M: 0.04 },\r\n 'llama-3.2-3b-preview': { inputPer1M: 0.06, outputPer1M: 0.06 },\r\n 'llama-3.2-11b-vision': { inputPer1M: 0.18, outputPer1M: 0.18 },\r\n 'llama-3.2-90b-vision': { inputPer1M: 0.90, outputPer1M: 0.90 },\r\n 'deepseek-r1-distill-llama-70b': { inputPer1M: 0.75, outputPer1M: 0.99 },\r\n 'deepseek-r1-distill-qwen-32b': { inputPer1M: 0.49, outputPer1M: 0.49 },\r\n 'qwen-2.5-32b': { inputPer1M: 0.29, outputPer1M: 0.39 },\r\n 'qwen-2.5-72b': { inputPer1M: 0.35, outputPer1M: 0.40 },\r\n 'mixtral-8x7b-32768': { inputPer1M: 0.24, outputPer1M: 0.24 },\r\n 'gemma2-9b-it': { inputPer1M: 0.20, outputPer1M: 0.20 },\r\n\r\n // --- DeepSeek ---\r\n 'deepseek-v4-pro': { inputPer1M: 0.66, outputPer1M: 1.98, cachedInputPer1M: 0.15 },\r\n 'deepseek-v4.1-flash': { inputPer1M: 0.20, outputPer1M: 0.60, cachedInputPer1M: 0.05 },\r\n 'deepseek-v4-flash': { inputPer1M: 0.22, outputPer1M: 0.66, cachedInputPer1M: 0.05 },\r\n 'deepseek-v3': { inputPer1M: 0.14, outputPer1M: 0.28, cachedInputPer1M: 0.014 },\r\n 'deepseek-chat': { inputPer1M: 0.14, outputPer1M: 0.28, cachedInputPer1M: 0.014 },\r\n 'deepseek-r1': { inputPer1M: 0.55, outputPer1M: 2.19, cachedInputPer1M: 0.14 },\r\n 'deepseek-reasoner': { inputPer1M: 0.55, outputPer1M: 2.19, cachedInputPer1M: 0.14 },\r\n\r\n // --- Gateway, Inception & InclusionAI Models ---\r\n 'mercury-2.5': { inputPer1M: 0.25, outputPer1M: 0.75, cachedInputPer1M: 0.05 },\r\n 'mercury-2': { inputPer1M: 0.25, outputPer1M: 0.75, cachedInputPer1M: 0.05 },\r\n 'ling-3.0-flash-sante': { inputPer1M: 0.15, outputPer1M: 0.45, cachedInputPer1M: 0.03 },\r\n 'ling-3.0-flash': { inputPer1M: 0.15, outputPer1M: 0.45, cachedInputPer1M: 0.03 },\r\n\r\n // --- Cohere ---\r\n 'command-r-plus': { inputPer1M: 2.5, outputPer1M: 10.0 },\r\n 'command-r': { inputPer1M: 0.15, outputPer1M: 0.6 },\r\n 'command': { inputPer1M: 1.0, outputPer1M: 2.0 },\r\n 'command-light': { inputPer1M: 0.3, outputPer1M: 0.6 },\r\n 'embed-english-v3.0': { inputPer1M: 0.10, outputPer1M: 0.0 },\r\n\r\n // --- Perplexity ---\r\n 'sonar': { inputPer1M: 1.0, outputPer1M: 1.0 },\r\n 'sonar-pro': { inputPer1M: 3.0, outputPer1M: 15.0 },\r\n 'sonar-reasoning': { inputPer1M: 1.0, outputPer1M: 5.0 },\r\n 'sonar-reasoning-pro': { inputPer1M: 2.0, outputPer1M: 8.0 },\r\n};\r\n\r\n/**\r\n * Common model alias map to normalize nicknames, shorthands, and legacy IDs\r\n */\r\nexport const MODEL_ALIASES: Record<string, string> = {\r\n // OpenAI Shorthands & Aliases\r\n 'gpt4': 'gpt-4',\r\n 'gpt4o': 'gpt-4o',\r\n 'gpt-4-preview': 'gpt-4-turbo',\r\n 'gpt-4-0125-preview': 'gpt-4-turbo',\r\n 'gpt-4-1106-preview': 'gpt-4-turbo',\r\n 'gpt-3.5': 'gpt-3.5-turbo',\r\n 'gpt-3.5-turbo-0125': 'gpt-3.5-turbo',\r\n 'gpt-3.5-turbo-1106': 'gpt-3.5-turbo',\r\n 'gpt-3.5-turbo-16k-0613': 'gpt-3.5-turbo-16k',\r\n\r\n // Anthropic Shorthands\r\n 'sonnet': 'claude-3-5-sonnet',\r\n 'sonnet-3.7': 'claude-3-7-sonnet',\r\n 'sonnet-3.5': 'claude-3-5-sonnet',\r\n 'haiku': 'claude-3-5-haiku',\r\n 'haiku-3.5': 'claude-3-5-haiku',\r\n 'opus': 'claude-3-opus',\r\n 'claude-2': 'claude-2.0',\r\n 'claude-instant': 'claude-instant-1.2',\r\n\r\n // DeepSeek Shorthands\r\n 'r1': 'deepseek-r1',\r\n 'v3': 'deepseek-v3',\r\n\r\n // Gemini Shorthands\r\n 'flash': 'gemini-2.0-flash',\r\n 'pro': 'gemini-1.5-pro',\r\n\r\n // Meta / Groq Shorthands\r\n 'llama-3.3-70b': 'llama-3.3-70b-versatile',\r\n 'llama-3.1-70b': 'llama-3.1-70b-versatile',\r\n 'llama-3.1-8b': 'llama-3.1-8b-instant',\r\n 'llama-3-70b': 'llama-3.1-70b-versatile',\r\n 'llama-3-8b': 'llama-3.1-8b-instant',\r\n\r\n // Mistral Shorthands\r\n 'codestral': 'codestral-latest',\r\n 'mistral-large': 'mistral-large-latest',\r\n 'mistral-small': 'mistral-small-latest',\r\n 'magistral': 'magistral-small-latest',\r\n 'magistral-small': 'magistral-small-latest',\r\n 'magistral-medium': 'magistral-medium-latest',\r\n 'mistral-3.5': 'mistral-medium-3-5',\r\n 'mistral-medium-3.5': 'mistral-medium-3-5',\r\n 'gpt-image-2.5': 'gpt-image-2.5-flare',\r\n 'gpt-image-sunburst': 'gpt-image-2.5-sunburst',\r\n 'gpt-image-flare': 'gpt-image-2.5-flare',\r\n};\r\n\r\n/**\r\n * Dynamic in-memory registry allowing runtime custom price registration\r\n */\r\nconst customPricingRegistry: Record<string, ModelPricingRates> = {};\r\n\r\n/**\r\n * Normalize model identifier to match pricing table keys:\r\n * - Strips AWS Bedrock prefixes (e.g. 'anthropic.claude-3-5-sonnet-20241022-v2:0' -> 'claude-3-5-sonnet')\r\n * - Strips provider prefixes (e.g. 'openai/gpt-4o' -> 'gpt-4o', 'deepseek/deepseek-r1' -> 'deepseek-r1')\r\n * - Strips date suffixes (e.g. '-20240307', '-20250219')\r\n * - Resolves shorthands and aliases\r\n */\r\nexport function normalizeModelKey(rawModel: string): string {\r\n if (!rawModel) return 'unknown';\r\n\r\n let model = rawModel.toLowerCase().trim();\r\n\r\n // Strip AWS Bedrock model prefix (e.g. 'us.anthropic.claude-3-5-sonnet...', 'meta.llama3-...')\r\n model = model.replace(/^[a-z0-9_-]+\\.(anthropic|meta|amazon|cohere|mistral|ai21)\\./i, '');\r\n model = model.replace(/^(anthropic|meta|amazon|cohere|mistral|ai21)\\./i, '');\r\n\r\n // Strip AWS Bedrock version suffix (e.g. '-v1:0', '-v2:0', ':0')\r\n model = model.replace(/-v\\d+(:\\d+)?$/, '');\r\n model = model.replace(/:\\d+$/, '');\r\n\r\n // Strip provider prefix if present (e.g. 'openai/gpt-4o' -> 'gpt-4o', 'meta-llama/llama-3.3-70b-instruct' -> 'llama-3.3-70b-instruct')\r\n if (model.includes('/')) {\r\n model = model.split('/').slice(1).join('/');\r\n }\r\n\r\n // Remove trailing version/mode tags (e.g. ':latest', ':free', ':beta')\r\n model = model.replace(/:(latest|free|beta)$/, '');\r\n\r\n // Remove date suffixes like -20240307 or -20250219 or -2024-08-06\r\n model = model.replace(/-\\d{8}$/, '');\r\n model = model.replace(/-\\d{4}-\\d{2}-\\d{2}$/, '');\r\n\r\n // Normalize Bedrock Meta format (e.g. llama3-1-70b -> llama-3.1-70b)\r\n model = model.replace(/llama(\\d+)-(\\d+)-/g, 'llama-$1.$2-');\r\n model = model.replace(/llama(\\d+)\\.(\\d+)-/g, 'llama-$1.$2-');\r\n\r\n // Check aliases before fine-tuning\r\n if (MODEL_ALIASES[model]) {\r\n return MODEL_ALIASES[model];\r\n }\r\n\r\n // Remove common modifier suffixes if not directly matching table\r\n if (!MODEL_PRICING_TABLE[model]) {\r\n const withoutInstruct = model.replace(/-(instruct|chat|preview)$/, '');\r\n if (MODEL_PRICING_TABLE[withoutInstruct]) {\r\n return withoutInstruct;\r\n }\r\n if (MODEL_ALIASES[withoutInstruct]) {\r\n return MODEL_ALIASES[withoutInstruct];\r\n }\r\n }\r\n\r\n return model;\r\n}\r\n\r\n/**\r\n * Retrieve pricing rates for a given model\r\n */\r\nexport function getModelPricing(modelName: string): ModelPricingRates {\r\n const normalized = normalizeModelKey(modelName);\r\n\r\n // Check custom registry first\r\n if (customPricingRegistry[normalized]) {\r\n return customPricingRegistry[normalized];\r\n }\r\n if (customPricingRegistry[modelName]) {\r\n return customPricingRegistry[modelName];\r\n }\r\n\r\n // Check built-in table with normalized key\r\n if (MODEL_PRICING_TABLE[normalized]) {\r\n return MODEL_PRICING_TABLE[normalized];\r\n }\r\n // Check built-in table with direct key\r\n if (MODEL_PRICING_TABLE[modelName]) {\r\n return MODEL_PRICING_TABLE[modelName];\r\n }\r\n\r\n // Check alias table fallback\r\n const alias = MODEL_ALIASES[modelName.toLowerCase().trim()];\r\n if (alias && MODEL_PRICING_TABLE[alias]) {\r\n return MODEL_PRICING_TABLE[alias];\r\n }\r\n\r\n // Fallback defaults for unknown models (conservative estimates: $1.00 in, $3.00 out)\r\n return {\r\n inputPer1M: 1.0,\r\n outputPer1M: 3.0,\r\n cachedInputPer1M: 0.5,\r\n };\r\n}\r\n\r\n/**\r\n * Register or override pricing rates for a custom model\r\n */\r\nexport function registerModelPricing(modelName: string, rates: ModelPricingRates): void {\r\n const normalized = normalizeModelKey(modelName);\r\n customPricingRegistry[normalized] = rates;\r\n customPricingRegistry[modelName] = rates;\r\n}\r\n","import type { InferenceCost, TokenUsage, InlineRateConfig, ModelPricingRates } from '../types';\nimport { getModelPricing } from './table';\n\nexport interface CalculateCostParams {\n model: string;\n inputTokens?: number;\n outputTokens?: number;\n reasoningTokens?: number;\n cachedTokens?: number;\n cacheWriteTokens?: number;\n markupMultiplier?: number;\n minimumChargeUSD?: number;\n customRate?: InlineRateConfig;\n}\n\n/**\n * BigInt Nano-Precision Financial Math Engine\n * 1 USD = 1,000,000,000 Nano-USD (10^9)\n * 1 token at $1.00 / 1M = $0.000001 = 1,000 Nano-USD\n * Prevents IEEE 754 floating point precision drift on micro-transactions.\n */\nexport function calculateCost(params: CalculateCostParams): InferenceCost {\n let rates: ModelPricingRates;\n\n if (params.customRate) {\n const outRate = params.customRate.out ?? params.customRate.output ?? 0;\n rates = {\n inputPer1M: params.customRate.in,\n outputPer1M: outRate,\n reasoningPer1M: params.customRate.reasoning ?? outRate,\n cachedInputPer1M: params.customRate.cached ?? params.customRate.in * 0.15,\n currency: 'USD',\n };\n } else {\n rates = getModelPricing(params.model);\n }\n\n const inputTokens = BigInt(Math.max(0, params.inputTokens ?? 0));\n const outputTokens = BigInt(Math.max(0, params.outputTokens ?? 0));\n const reasoningTokens = BigInt(Math.max(0, params.reasoningTokens ?? 0));\n const cachedTokens = BigInt(Math.max(0, params.cachedTokens ?? 0));\n\n // Regular input tokens (minus any cached tokens)\n const regularInputTokens = inputTokens > cachedTokens ? inputTokens - cachedTokens : 0n;\n\n // Convert rate per 1M tokens to integer nano-dollars per single token (rate * 1,000)\n // Using 10^9 nano-precision\n const rateInputNano = BigInt(Math.round(rates.inputPer1M * 1_000));\n const cachedPer1M = rates.cachedInputPer1M ?? rates.inputPer1M * 0.15;\n const rateCachedNano = BigInt(Math.round(cachedPer1M * 1_000));\n const rateOutputNano = BigInt(Math.round(rates.outputPer1M * 1_000));\n const reasoningPer1M = rates.reasoningPer1M ?? rates.outputPer1M;\n const rateReasoningNano = BigInt(Math.round(reasoningPer1M * 1_000));\n\n // Compute component nano costs\n const regularInputCostNano = regularInputTokens * rateInputNano;\n const cachedInputCostNano = cachedTokens * rateCachedNano;\n const inputCostNano = regularInputCostNano + cachedInputCostNano;\n const outputCostNano = outputTokens * rateOutputNano;\n const reasoningCostNano = reasoningTokens * rateReasoningNano;\n\n // Prompt cache savings discount\n const standardCacheCostNano = cachedTokens * rateInputNano;\n const cachedDiscountNano =\n standardCacheCostNano > cachedInputCostNano ? standardCacheCostNano - cachedInputCostNano : 0n;\n\n // Total wholesale cost\n const wholesaleNano = inputCostNano + outputCostNano;\n\n // Retail calculation\n const markup = params.markupMultiplier ?? 1.0;\n let billedNano = wholesaleNano;\n let hasRetail = false;\n\n if (markup !== 1.0 || params.minimumChargeUSD !== undefined) {\n hasRetail = true;\n const markupMultiplierNano = BigInt(Math.round(markup * 1_000));\n billedNano = (wholesaleNano * markupMultiplierNano) / 1_000n;\n\n if (params.minimumChargeUSD !== undefined && params.minimumChargeUSD > 0) {\n const minChargeNano = BigInt(Math.round(params.minimumChargeUSD * 1_000_000_000));\n if (billedNano < minChargeNano) {\n billedNano = minChargeNano;\n }\n }\n }\n\n const inputCostUSD = Number(inputCostNano) / 1_000_000_000;\n const outputCostUSD = Number(outputCostNano) / 1_000_000_000;\n const reasoningCostUSD = Number(reasoningCostNano) / 1_000_000_000;\n const cachedDiscountUSD = Number(cachedDiscountNano) / 1_000_000_000;\n const totalUSD = Number(wholesaleNano) / 1_000_000_000;\n const wholesaleTotalUSD = totalUSD;\n const billedUSD = Number(billedNano) / 1_000_000_000;\n const profitUSD = Math.max(0, billedUSD - wholesaleTotalUSD);\n const retailUSD = hasRetail ? billedUSD : undefined;\n\n return {\n inputCostUSD: Number(inputCostUSD.toFixed(8)),\n outputCostUSD: Number(outputCostUSD.toFixed(8)),\n reasoningCostUSD: reasoningTokens > 0n ? Number(reasoningCostUSD.toFixed(8)) : undefined,\n cachedDiscountUSD: cachedTokens > 0n ? Number(cachedDiscountUSD.toFixed(8)) : undefined,\n totalUSD: Number(totalUSD.toFixed(8)),\n wholesaleTotalUSD: Number(wholesaleTotalUSD.toFixed(8)),\n billedUSD: Number(billedUSD.toFixed(8)),\n profitUSD: Number(profitUSD.toFixed(8)),\n retailUSD: retailUSD !== undefined ? Number(retailUSD.toFixed(8)) : undefined,\n currency: rates.currency || 'USD',\n };\n}\n\n/**\n * Calculates cost directly from a TokenUsage object\n */\nexport function calculateUsageCost(\n model: string,\n usage: TokenUsage,\n optionsOrMarkup?: number | { markupMultiplier?: number; minimumChargeUSD?: number; customRate?: InlineRateConfig }\n): InferenceCost {\n const options =\n typeof optionsOrMarkup === 'number'\n ? { markupMultiplier: optionsOrMarkup }\n : optionsOrMarkup || {};\n\n return calculateCost({\n model,\n inputTokens: usage.inputTokens,\n outputTokens: usage.outputTokens,\n reasoningTokens: usage.reasoningTokens,\n cachedTokens: usage.cachedTokens,\n cacheWriteTokens: usage.cacheWriteTokens,\n markupMultiplier: options.markupMultiplier,\n minimumChargeUSD: options.minimumChargeUSD,\n customRate: options.customRate,\n });\n}\n","import type { CustomerParam, CustomerInfo } from '../types';\r\n\r\nexport interface NormalizedCustomer {\r\n customerId?: string;\r\n customerEmail?: string;\r\n customerObj?: CustomerInfo;\r\n customerMetadata: Record<string, string | number | boolean>;\r\n}\r\n\r\n/**\r\n * Normalizes string or object customer into structured identifiers and metadata\r\n */\r\nexport function normalizeCustomer(customer?: CustomerParam, extraCustomerId?: string): NormalizedCustomer {\r\n if (!customer && !extraCustomerId) {\r\n return {\r\n customerId: undefined,\r\n customerEmail: undefined,\r\n customerObj: undefined,\r\n customerMetadata: {},\r\n };\r\n }\r\n\r\n if (typeof customer === 'string') {\r\n const isEmail = customer.includes('@');\r\n const customerObj: CustomerInfo = {\r\n id: customer,\r\n email: isEmail ? customer : undefined,\r\n };\r\n return {\r\n customerId: customer,\r\n customerEmail: isEmail ? customer : undefined,\r\n customerObj,\r\n customerMetadata: {},\r\n };\r\n }\r\n\r\n const customerObj = customer || (extraCustomerId ? { id: extraCustomerId } : undefined);\r\n const customerId = customerObj?.id || customerObj?.userId || extraCustomerId;\r\n const customerEmail = customerObj?.email;\r\n\r\n const customerMetadata: Record<string, string | number | boolean> = {};\r\n\r\n if (customerObj) {\r\n const orgId = customerObj.orgId || customerObj.organizationId;\r\n if (orgId) customerMetadata.org_id = String(orgId);\r\n\r\n const teamId = customerObj.teamId || customerObj.workspaceId;\r\n if (teamId) customerMetadata.team_id = String(teamId);\r\n\r\n if (customerObj.plan) customerMetadata.plan = String(customerObj.plan);\r\n if (customerObj.tier) customerMetadata.tier = String(customerObj.tier);\r\n if (customerObj.role) customerMetadata.role = String(customerObj.role);\r\n if (customerObj.orgName) customerMetadata.org_name = String(customerObj.orgName);\r\n\r\n if (customerObj.metadata) {\r\n for (const [key, val] of Object.entries(customerObj.metadata)) {\r\n if (val !== null && val !== undefined) {\r\n customerMetadata[key] = val as string | number | boolean;\r\n }\r\n }\r\n }\r\n }\r\n\r\n return {\r\n customerId,\r\n customerEmail,\r\n customerObj,\r\n customerMetadata,\r\n };\r\n}\r\n","import type { UsageEvent, StreamWrapOptions } from '../types';\r\nimport { inspectOpenAIStreamChunk } from './extractors/openai';\r\nimport { AnthropicStreamAccumulator } from './extractors/anthropic';\r\nimport { extractGeminiResponseUsage } from './extractors/gemini';\r\nimport { calculateUsageCost } from '../pricing/calculator';\r\nimport { normalizeCustomer } from '../customers/helpers';\r\n\r\nexport type UsageDispatchedCallback = (event: UsageEvent) => void;\r\n\r\n/**\r\n * Wraps an OpenAI async iterable stream to capture usage at stream conclusion\r\n */\r\nexport function wrapOpenAIStream<T extends AsyncIterable<any>>(\r\n stream: T,\r\n options: StreamWrapOptions,\r\n onComplete: UsageDispatchedCallback\r\n): T {\r\n let detectedModel = options.model || 'gpt-4o';\r\n let finalUsage: any = null;\r\n\r\n const wrappedAsyncIterable = {\r\n async *[Symbol.asyncIterator]() {\r\n try {\r\n for await (const chunk of stream) {\r\n const inspected = inspectOpenAIStreamChunk(chunk);\r\n if (inspected.model) {\r\n detectedModel = inspected.model;\r\n }\r\n if (inspected.usage) {\r\n finalUsage = inspected.usage;\r\n }\r\n yield chunk;\r\n }\r\n } finally {\r\n if (finalUsage) {\r\n const cost = calculateUsageCost(detectedModel, finalUsage);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: detectedModel,\r\n provider: 'openai',\r\n usage: finalUsage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n },\r\n };\r\n\r\n onComplete(event);\r\n if (options.onUsage) {\r\n options.onUsage(event);\r\n }\r\n }\r\n }\r\n },\r\n };\r\n\r\n return wrappedAsyncIterable as unknown as T;\r\n}\r\n\r\n/**\r\n * Wraps an Anthropic message stream to accumulate message_start and message_delta usage\r\n */\r\nexport function wrapAnthropicStream<T extends AsyncIterable<any>>(\r\n stream: T,\r\n options: StreamWrapOptions,\r\n onComplete: UsageDispatchedCallback\r\n): T {\r\n const accumulator = new AnthropicStreamAccumulator();\r\n\r\n const wrappedAsyncIterable = {\r\n async *[Symbol.asyncIterator]() {\r\n try {\r\n for await (const event of stream) {\r\n accumulator.processEvent(event);\r\n yield event;\r\n }\r\n } finally {\r\n const extracted = accumulator.getUsage();\r\n const model = options.model || extracted.model;\r\n const cost = calculateUsageCost(model, extracted.usage);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const usageEvent: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model,\r\n provider: 'anthropic',\r\n usage: extracted.usage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n },\r\n };\r\n\r\n onComplete(usageEvent);\r\n if (options.onUsage) {\r\n options.onUsage(usageEvent);\r\n }\r\n }\r\n },\r\n };\r\n\r\n return wrappedAsyncIterable as unknown as T;\r\n}\r\n\r\n/**\r\n * Wraps a Google Gemini GenerateContentStreamResult\r\n */\r\nexport function wrapGeminiStream(\r\n result: any,\r\n options: StreamWrapOptions,\r\n onComplete: UsageDispatchedCallback\r\n): any {\r\n if (!result || !result.stream) return result;\r\n\r\n const originalStream = result.stream;\r\n const model = options.model || 'gemini-3.7-flash';\r\n let lastChunkWithUsage: any = null;\r\n\r\n const wrappedStream = (async function* () {\r\n try {\r\n for await (const chunk of originalStream) {\r\n if (chunk.usageMetadata) {\r\n lastChunkWithUsage = chunk;\r\n }\r\n yield chunk;\r\n }\r\n } finally {\r\n if (lastChunkWithUsage) {\r\n const extracted = extractGeminiResponseUsage(lastChunkWithUsage, model);\r\n if (extracted) {\r\n const cost = calculateUsageCost(extracted.model, extracted.usage);\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: extracted.model,\r\n provider: 'google',\r\n usage: extracted.usage,\r\n cost,\r\n customerId: normalized.customerId,\r\n customerEmail: normalized.customerEmail,\r\n customer: normalized.customerObj,\r\n metadata: {\r\n ...normalized.customerMetadata,\r\n ...options.metadata,\r\n },\r\n };\r\n\r\n onComplete(event);\r\n if (options.onUsage) {\r\n options.onUsage(event);\r\n }\r\n }\r\n }\r\n }\r\n })();\r\n\r\n return {\r\n ...result,\r\n stream: wrappedStream,\r\n };\r\n}\r\n\r\n/**\r\n * Universal Stream Wrapper\r\n */\r\nexport function wrapUniversalStream<T>(\r\n stream: T,\r\n options: StreamWrapOptions = {},\r\n onComplete: UsageDispatchedCallback\r\n): T {\r\n if (!stream || typeof stream !== 'object') return stream;\r\n\r\n // 1. Check Gemini stream\r\n if ('stream' in stream && 'response' in stream) {\r\n return wrapGeminiStream(stream, options, onComplete);\r\n }\r\n\r\n // 2. Check if stream is an AsyncIterable\r\n if (Symbol.asyncIterator in stream) {\r\n // If provider is explicitly anthropic or model is claude\r\n if (options.provider === 'anthropic' || options.model?.toLowerCase().includes('claude')) {\r\n return wrapAnthropicStream(stream as any, options, onComplete);\r\n }\r\n // Default to universal stream wrapper which detects usage chunks polymorphically\r\n return wrapOpenAIStream(stream as any, options, onComplete);\r\n }\r\n\r\n return stream;\r\n}\r\n","import type {\r\n CustomerParam,\r\n UsageEvent,\r\n CircuitBreakerOptions,\r\n BudgetExceededEvent,\r\n BillingConfig,\r\n PricingConfig,\r\n InlineRateConfig,\r\n} from '../types';\r\nimport { VibezCircuitBreakerError } from '../types';\r\nimport { createMeter, VibezMeter } from '../meter/client';\r\nimport { calculateUsageCost } from '../pricing/calculator';\r\nimport { normalizeCustomer } from '../customers/helpers';\r\n\r\nexport interface WithBillingOptions extends CircuitBreakerOptions {\r\n /** Customer email, user ID, or rich customer object with metadata */\r\n customer?: CustomerParam;\r\n /** Direct Stripe customer ID */\r\n customerId?: string;\r\n /** Billing mode configuration (Universal Auto-Debit, postpaid vs prepaid, pluggable providers) */\r\n billing?: BillingConfig;\r\n /** Profit margin & minimum charge configuration */\r\n pricing?: PricingConfig;\r\n /** 1-line inline pricing rate card */\r\n rate?: InlineRateConfig;\r\n /** Pluggable Database Sink (Supabase, Postgres, Firebase, or 1-line callback) */\r\n database?: any | ((event: UsageEvent) => void | Promise<void>);\r\n /** Whether to capture tokens if the client aborts or closes tab mid-stream (default: true) */\r\n captureOnAbort?: boolean;\r\n /** Execution runtime environment (default: 'auto') */\r\n runtime?: 'auto' | 'serverless' | 'edge' | 'node';\r\n /** Stripe API Key override (uses STRIPE_SECRET_KEY env by default) */\r\n stripeApiKey?: string;\r\n /** Existing VibezMeter instance (optional) */\r\n meter?: VibezMeter;\r\n /** Custom meter event name */\r\n eventName?: string;\r\n /** Usage callback fired upon generation/stream completion */\r\n onUsage?: (event: UsageEvent) => void | Promise<void>;\r\n /** Custom developer metadata */\r\n metadata?: Record<string, string | number | boolean>;\r\n /** Suppress console warnings (default: true in test environment) */\r\n silent?: boolean;\r\n}\r\n\r\n/**\r\n * Wraps any Vercel AI SDK LanguageModel (v2 or v3) with automated Stripe billing, token metering, and agent circuit breakers.\r\n *\r\n * Sane Defaults Built-In:\r\n * - $0.50 safety ceiling per call (overridable)\r\n * - Automatic in-flight token capture on abort\r\n * - Automatic prompt caching discount parsing\r\n * - Serverless lifecycle preservation\r\n */\r\nexport function withBilling<T extends object>(\r\n model: T,\r\n optionsOrCustomer?: CustomerParam | WithBillingOptions,\r\n extraOptions: WithBillingOptions = {}\r\n): T {\r\n if (!model || typeof model !== 'object') {\r\n return model;\r\n }\r\n\r\n let options: WithBillingOptions = {};\r\n if (typeof optionsOrCustomer === 'string') {\r\n options = { ...extraOptions, customer: optionsOrCustomer };\r\n } else if (typeof optionsOrCustomer === 'object' && optionsOrCustomer !== null) {\r\n if ('userId' in optionsOrCustomer || 'email' in optionsOrCustomer || 'id' in optionsOrCustomer) {\r\n options = { ...extraOptions, customer: optionsOrCustomer as CustomerParam };\r\n } else {\r\n options = { ...(optionsOrCustomer as WithBillingOptions), ...extraOptions };\r\n }\r\n }\r\n\r\n const meter =\r\n options.meter ||\r\n createMeter({\r\n apiKey: options.stripeApiKey,\r\n eventName: options.eventName,\r\n });\r\n\r\n const normalized = normalizeCustomer(options.customer, options.customerId);\r\n const customerId = normalized.customerId;\r\n const customerEmail = normalized.customerEmail;\r\n const customerObj = normalized.customerObj;\r\n const customerMetadata = normalized.customerMetadata;\r\n\r\n const modelId = (model as any).modelId || 'unknown-model';\r\n const provider = (model as any).provider?.replace(/^@ai-sdk\\//, '') || 'ai-sdk';\r\n\r\n // Sane Default: $0.50 circuit breaker ceiling unless explicitly disabled or configured\r\n const maxCostPerCall = options.maxCostPerCallUSD !== undefined ? options.maxCostPerCallUSD : 0.50;\r\n const captureOnAbort = options.captureOnAbort !== false; // Default: true\r\n\r\n // Helper to safely schedule serverless flushes\r\n const scheduleFlush = () => {\r\n try {\r\n const flushPromise = meter.flush();\r\n // Next.js 15+ after() or Cloudflare Workers waitUntil()\r\n if (typeof globalThis !== 'undefined') {\r\n const g = globalThis as any;\r\n if (typeof g.after === 'function') {\r\n g.after(() => flushPromise);\r\n return;\r\n }\r\n }\r\n } catch {\r\n // Fallback in environments without after()\r\n }\r\n };\r\n\r\n // Helper to record usage and enforce circuit breakers\r\n const handleUsage = (rawUsage: any, extraMeta?: Record<string, any>) => {\r\n if (!rawUsage) return;\r\n\r\n let inputTokens = 0;\r\n let outputTokens = 0;\r\n let reasoningTokens = 0;\r\n let cachedTokens = 0;\r\n let cacheWriteTokens = 0;\r\n\r\n // AI SDK v4+ (LanguageModelV4Usage) structured object or legacy flat number\r\n if (typeof rawUsage.inputTokens === 'object' && rawUsage.inputTokens !== null) {\r\n inputTokens = rawUsage.inputTokens.total ?? rawUsage.inputTokens.noCache ?? 0;\r\n cachedTokens = rawUsage.inputTokens.cacheRead ?? 0;\r\n cacheWriteTokens = rawUsage.inputTokens.cacheWrite ?? 0;\r\n } else if (typeof rawUsage.promptTokens === 'number') {\r\n inputTokens = rawUsage.promptTokens;\r\n } else if (typeof rawUsage.inputTokens === 'number') {\r\n inputTokens = rawUsage.inputTokens;\r\n } else {\r\n inputTokens =\r\n rawUsage.prompt_tokens ??\r\n rawUsage.input_tokens ??\r\n rawUsage.promptTokenCount ??\r\n 0;\r\n }\r\n\r\n if (typeof rawUsage.outputTokens === 'object' && rawUsage.outputTokens !== null) {\r\n outputTokens = rawUsage.outputTokens.total ?? rawUsage.outputTokens.text ?? 0;\r\n reasoningTokens = rawUsage.outputTokens.reasoning ?? 0;\r\n } else if (typeof rawUsage.completionTokens === 'number') {\r\n outputTokens = rawUsage.completionTokens;\r\n } else if (typeof rawUsage.outputTokens === 'number') {\r\n outputTokens = rawUsage.outputTokens;\r\n } else {\r\n outputTokens =\r\n rawUsage.completion_tokens ??\r\n rawUsage.output_tokens ??\r\n rawUsage.candidatesTokenCount ??\r\n 0;\r\n }\r\n\r\n if (!reasoningTokens) {\r\n reasoningTokens =\r\n rawUsage.reasoningTokens ??\r\n rawUsage.completionTokensDetails?.reasoningTokens ??\r\n rawUsage.outputTokenDetails?.reasoningTokens ??\r\n rawUsage.reasoning_tokens ??\r\n rawUsage.completion_tokens_details?.reasoning_tokens ??\r\n rawUsage.output_token_details?.reasoning_tokens ??\r\n rawUsage.thoughtsTokenCount ??\r\n 0;\r\n }\r\n\r\n if (!cachedTokens) {\r\n cachedTokens =\r\n rawUsage.promptTokensDetails?.cachedTokens ??\r\n rawUsage.inputTokenDetails?.cachedTokens ??\r\n rawUsage.cachedTokens ??\r\n rawUsage.cached_tokens ??\r\n rawUsage.prompt_tokens_details?.cached_tokens ??\r\n rawUsage.input_token_details?.cached_tokens ??\r\n rawUsage.cachedContentTokenCount ??\r\n rawUsage.cache_read_input_tokens ??\r\n 0;\r\n }\r\n\r\n if (!cacheWriteTokens) {\r\n cacheWriteTokens =\r\n rawUsage.cacheWriteTokens ??\r\n rawUsage.cache_creation_input_tokens ??\r\n rawUsage.cacheCreationTokens ??\r\n 0;\r\n }\r\n\r\n const usage = {\r\n inputTokens,\r\n outputTokens,\r\n totalTokens: inputTokens + outputTokens,\r\n reasoningTokens: reasoningTokens > 0 ? reasoningTokens : undefined,\r\n visibleOutputTokens: Math.max(0, outputTokens - reasoningTokens),\r\n cachedTokens: cachedTokens > 0 ? cachedTokens : undefined,\r\n cacheWriteTokens: cacheWriteTokens > 0 ? cacheWriteTokens : undefined,\r\n };\r\n\r\n // Calculate cost with profit margin & minimum charge & custom rates\r\n const cost = calculateUsageCost(modelId, usage, {\r\n markupMultiplier: options.pricing?.margin,\r\n minimumChargeUSD: options.pricing?.minimumChargeUSD,\r\n customRate: options.rate,\r\n });\r\n\r\n // 🛡️ Agent Circuit Breakers Check ($0.50 default safety fuse)\r\n if (maxCostPerCall > 0 && maxCostPerCall !== Infinity && cost.totalUSD > maxCostPerCall) {\r\n const budgetEvent: BudgetExceededEvent = {\r\n reason: 'cost_per_call_exceeded',\r\n limit: maxCostPerCall,\r\n current: cost.totalUSD,\r\n model: modelId,\r\n customerId,\r\n message: `[vibezcheck] Circuit Breaker tripped: Call cost ($${cost.totalUSD.toFixed(4)}) exceeded budget ceiling ($${maxCostPerCall.toFixed(4)}).`,\r\n };\r\n\r\n if (options.onBudgetExceeded) {\r\n options.onBudgetExceeded(budgetEvent);\r\n }\r\n\r\n if (options.throwOnBudgetExceeded) {\r\n throw new VibezCircuitBreakerError(budgetEvent);\r\n }\r\n }\r\n\r\n if (options.maxTokensPerCall && usage.totalTokens > options.maxTokensPerCall) {\r\n const budgetEvent: BudgetExceededEvent = {\r\n reason: 'max_tokens_exceeded',\r\n limit: options.maxTokensPerCall,\r\n current: usage.totalTokens,\r\n model: modelId,\r\n customerId,\r\n message: `[vibezcheck] Circuit Breaker tripped: Token count (${usage.totalTokens}) exceeded maxTokensPerCall limit (${options.maxTokensPerCall}).`,\r\n };\r\n\r\n if (options.onBudgetExceeded) {\r\n options.onBudgetExceeded(budgetEvent);\r\n }\r\n\r\n if (options.throwOnBudgetExceeded) {\r\n throw new VibezCircuitBreakerError(budgetEvent);\r\n }\r\n }\r\n\r\n const mergedMetadata: Record<string, string | number | boolean> = {\r\n ...customerMetadata,\r\n ...options.metadata,\r\n ...extraMeta,\r\n billingMode: options.billing?.mode || 'postpaid',\r\n };\r\n\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: modelId,\r\n provider,\r\n usage,\r\n cost,\r\n customerId,\r\n customerEmail,\r\n customer: customerObj,\r\n metadata: mergedMetadata,\r\n };\r\n\r\n // Record via meter batcher\r\n meter.recordUsage({\r\n model: modelId,\r\n provider,\r\n inputTokens,\r\n outputTokens,\r\n reasoningTokens: usage.reasoningTokens,\r\n cachedTokens: usage.cachedTokens,\r\n customerId,\r\n customer: customerObj,\r\n metadata: event.metadata,\r\n });\r\n\r\n if (options.onUsage) {\r\n options.onUsage(event);\r\n }\r\n\r\n // 🛡️ Duck-Typed Database Sink Execution (Airbag Isolated)\r\n if (options.database) {\r\n const dbTarget = options.database;\r\n const executeDbWrite = async () => {\r\n try {\r\n // 1. Direct Supabase client duck-typing (has .from()) or wrapped { client, table }\r\n const supabaseClient = typeof dbTarget === 'object' && dbTarget !== null && typeof dbTarget.from === 'function'\r\n ? dbTarget\r\n : (typeof dbTarget === 'object' && dbTarget !== null && typeof dbTarget.client?.from === 'function' ? dbTarget.client : null);\r\n\r\n if (supabaseClient) {\r\n const tableName = (dbTarget as any)?.table || 'vibez_usage';\r\n await supabaseClient.from(tableName).insert({\r\n customer_id: customerId,\r\n user_id: customerObj?.userId || customerId,\r\n model: modelId,\r\n input_tokens: usage.inputTokens,\r\n output_tokens: usage.outputTokens,\r\n total_tokens: usage.totalTokens,\r\n cached_tokens: usage.cachedTokens,\r\n reasoning_tokens: usage.reasoningTokens,\r\n cost_usd: cost.totalUSD,\r\n created_at: event.timestamp,\r\n metadata: event.metadata,\r\n });\r\n return;\r\n }\r\n\r\n // 2. Typed DatabaseAdapter (has .save())\r\n if (typeof dbTarget === 'object' && dbTarget !== null && typeof dbTarget.save === 'function') {\r\n await dbTarget.save(event);\r\n return;\r\n }\r\n\r\n // 3. 1-line callback function\r\n if (typeof dbTarget === 'function') {\r\n await dbTarget(event);\r\n return;\r\n }\r\n } catch (err: any) {\r\n // Zero Blast Radius: Third-party DB errors never crash the user's stream\r\n if (process.env.NODE_ENV !== 'test' && !options.silent) {\r\n console.warn(`[vibezcheck] Database record failed safely:`, err?.message || err);\r\n }\r\n }\r\n };\r\n\r\n if (typeof globalThis !== 'undefined' && typeof (globalThis as any).after === 'function') {\r\n (globalThis as any).after(() => executeDbWrite());\r\n } else {\r\n executeDbWrite().catch(() => {});\r\n }\r\n }\r\n\r\n // 💳 Pluggable Payment Provider Execution (Airbag Isolated)\r\n if (options.billing?.charge && typeof options.billing.charge === 'function') {\r\n const chargeFn = options.billing.charge;\r\n const executeCharge = async () => {\r\n try {\r\n await chargeFn(cost.totalUSD, event);\r\n } catch (err: any) {\r\n if (process.env.NODE_ENV !== 'test' && !options.silent) {\r\n console.warn(`[vibezcheck] Custom charge handler failed safely:`, err?.message || err);\r\n }\r\n }\r\n };\r\n if (typeof globalThis !== 'undefined' && typeof (globalThis as any).after === 'function') {\r\n (globalThis as any).after(() => executeCharge());\r\n } else {\r\n executeCharge().catch(() => {});\r\n }\r\n } else if (options.billing?.provider && typeof options.billing.provider === 'object' && typeof (options.billing.provider as any).charge === 'function') {\r\n const providerCharge = (options.billing.provider as any).charge;\r\n const executeCharge = async () => {\r\n try {\r\n await providerCharge(cost.totalUSD, event);\r\n } catch (err: any) {\r\n if (process.env.NODE_ENV !== 'test' && !options.silent) {\r\n console.warn(`[vibezcheck] Payment provider charge failed safely:`, err?.message || err);\r\n }\r\n }\r\n };\r\n if (typeof globalThis !== 'undefined' && typeof (globalThis as any).after === 'function') {\r\n (globalThis as any).after(() => executeCharge());\r\n } else {\r\n executeCharge().catch(() => {});\r\n }\r\n }\r\n\r\n scheduleFlush();\r\n };\r\n\r\n // Proxy to intercept LanguageModel calls\r\n const handler: ProxyHandler<any> = {\r\n get(target, prop, receiver) {\r\n const originalValue = Reflect.get(target, prop, receiver);\r\n\r\n // Intercept doStream (Vercel AI SDK v1/v2/v3)\r\n if (prop === 'doStream' && typeof originalValue === 'function') {\r\n return async function (...args: any[]) {\r\n const result = await originalValue.apply(target, args);\r\n if (!result || !result.stream) {\r\n return result;\r\n }\r\n\r\n const originalStream = result.stream;\r\n let streamCompleted = false;\r\n let accumulatedChars = 0;\r\n\r\n // Estimate input prompt tokens from args if available\r\n let estimatedInputTokens = 0;\r\n try {\r\n if (args[0]?.prompt) {\r\n const str = typeof args[0].prompt === 'string' ? args[0].prompt : JSON.stringify(args[0].prompt);\r\n estimatedInputTokens = Math.ceil(str.length / 4);\r\n }\r\n } catch {}\r\n\r\n // In-flight abort signal listener\r\n const abortSignal = args[0]?.abortSignal;\r\n if (abortSignal && captureOnAbort) {\r\n abortSignal.addEventListener(\r\n 'abort',\r\n () => {\r\n if (!streamCompleted && accumulatedChars > 0) {\r\n streamCompleted = true;\r\n const estimatedOutputTokens = Math.ceil(accumulatedChars / 3.8);\r\n handleUsage(\r\n {\r\n inputTokens: estimatedInputTokens,\r\n outputTokens: estimatedOutputTokens,\r\n },\r\n { aborted: true, partial: true }\r\n );\r\n }\r\n },\r\n { once: true }\r\n );\r\n }\r\n\r\n // Wrap stream to capture tokens upon finish chunk or abort\r\n const transformStream = new TransformStream({\r\n transform(chunk, controller) {\r\n controller.enqueue(chunk);\r\n\r\n if (chunk.type === 'text-delta' && typeof chunk.delta === 'string') {\r\n accumulatedChars += chunk.delta.length;\r\n } else if (chunk.type === 'reasoning-delta' && typeof chunk.delta === 'string') {\r\n accumulatedChars += chunk.delta.length;\r\n } else {\r\n const delta = chunk.textDelta || chunk.text || chunk.delta;\r\n if (delta && typeof delta === 'string') {\r\n accumulatedChars += delta.length;\r\n } else if (chunk.type === 'reasoning' || chunk.type === 'reasoning-delta') {\r\n const reasoning = chunk.reasoning || chunk.textDelta || chunk.text || chunk.delta || '';\r\n if (typeof reasoning === 'string') {\r\n accumulatedChars += reasoning.length;\r\n }\r\n }\r\n }\r\n\r\n // AI SDK stream finish chunk or direct usage payload (OpenAI, Anthropic, Gemini, DeepSeek, Groq, Mistral)\r\n const chunkUsage =\r\n (chunk.type === 'finish' ? chunk.usage : null) ||\r\n chunk.usage ||\r\n chunk.token_usage ||\r\n chunk.usageMetadata;\r\n if (chunkUsage) {\r\n streamCompleted = true;\r\n handleUsage(chunkUsage);\r\n }\r\n },\r\n flush() {\r\n // If stream ended without finish chunk (e.g. cancelled/aborted), record partial tokens\r\n if (!streamCompleted && captureOnAbort && accumulatedChars > 0) {\r\n streamCompleted = true;\r\n const estimatedOutputTokens = Math.ceil(accumulatedChars / 3.8);\r\n handleUsage(\r\n {\r\n inputTokens: estimatedInputTokens,\r\n outputTokens: estimatedOutputTokens,\r\n },\r\n { aborted: true, partial: true }\r\n );\r\n }\r\n },\r\n });\r\n\r\n return {\r\n ...result,\r\n stream: originalStream.pipeThrough(transformStream),\r\n };\r\n };\r\n }\r\n\r\n // Intercept doGenerate (Vercel AI SDK v1/v2/v3/v4/v5+)\r\n if (prop === 'doGenerate' && typeof originalValue === 'function') {\r\n return async function (...args: any[]) {\r\n const result = await originalValue.apply(target, args);\r\n const usage = result?.usage || result?.tokenUsage || result?.usageMetadata;\r\n if (usage) {\r\n handleUsage(usage);\r\n }\r\n return result;\r\n };\r\n }\r\n\r\n return originalValue;\r\n },\r\n apply(target, thisArg, argArray) {\r\n if (typeof target === 'function') {\r\n return Reflect.apply(target, thisArg, argArray);\r\n }\r\n return target;\r\n },\r\n has(target, prop) {\r\n return Reflect.has(target, prop);\r\n },\r\n ownKeys(target) {\r\n return Reflect.ownKeys(target);\r\n },\r\n getPrototypeOf(target) {\r\n return Reflect.getPrototypeOf(target);\r\n },\r\n };\r\n\r\n return new Proxy(model, handler);\r\n}\r\n\r\n/**\r\n * Convenient alias for withBilling\r\n */\r\nexport const meteredModel = withBilling;\r\n","import type { CustomerParam, UsageEvent, ToolMeterOptions } from '../types';\r\nimport { withBilling, type WithBillingOptions } from './with-billing';\r\nimport { calculateCost } from '../pricing/calculator';\r\nimport { createMeter, VibezMeter } from '../meter/client';\r\n\r\nexport interface VibezCheckModelOptions extends WithBillingOptions {\r\n /** OpenAI / Anthropic / AI Gateway API Key override */\r\n apiKey?: string;\r\n /** AI Gateway / Provider Base URL override */\r\n baseURL?: string;\r\n}\r\n\r\nexport interface VibezSessionOptions {\r\n customer?: CustomerParam;\r\n stripeApiKey?: string;\r\n pricing?: WithBillingOptions['pricing'];\r\n billing?: WithBillingOptions['billing'];\r\n metadata?: Record<string, string | number | boolean>;\r\n}\r\n\r\nexport interface VibezSession {\r\n /** Creates a metered model bound to this session customer */\r\n model: (modelOrId: any, options?: VibezCheckModelOptions) => any;\r\n /** Tracks a non-LLM tool execution cost (e.g. search, scraper, image gen) */\r\n trackTool: (name: string, options: { costUSD: number; metadata?: Record<string, any> }) => Promise<void>;\r\n /** Underlying meter instance */\r\n meter: VibezMeter;\r\n}\r\n\r\n/**\r\n * Creates or resolves an AI SDK compatible LanguageModel with built-in VibezCheck billing & metering.\r\n *\r\n * Supports:\r\n * - Direct instances: `vibezcheck(openai('gpt-4o'))`, `vibezcheck(anthropic('claude-3-7-sonnet'))`\r\n * - String identifiers: `vibezcheck('openai/gpt-4o-mini')`, `vibezcheck('anthropic/claude-3-5-sonnet')`, `vibezcheck('gpt-4o')`\r\n * - Vercel AI SDK primitives: `generateText`, `streamText`, `generateObject`, `streamObject`\r\n *\r\n * @example\r\n * ```typescript\r\n * import { streamText } from 'ai';\r\n * import { openai } from '@ai-sdk/openai';\r\n * import { anthropic } from '@ai-sdk/anthropic';\r\n * import { vibezcheck } from 'vibezcheck';\r\n *\r\n * // 1. Pass wrapped OpenAI instance:\r\n * const result = streamText({\r\n * model: vibezcheck(openai('gpt-4o-mini'), { customer: 'alex@example.com' }),\r\n * messages,\r\n * });\r\n *\r\n * // 2. Pass wrapped Anthropic instance:\r\n * const result2 = streamText({\r\n * model: vibezcheck(anthropic('claude-3-7-sonnet'), { customer: 'alex@example.com' }),\r\n * messages,\r\n * });\r\n *\r\n * // 3. Use 1-line string identifier:\r\n * const result3 = streamText({\r\n * model: vibezcheck('openai/gpt-4o-mini', { customer: 'alex@example.com' }),\r\n * messages,\r\n * });\r\n * ```\r\n */\r\nexport function createVibezModel(\r\n modelOrId: any,\r\n options: VibezCheckModelOptions = {}\r\n): any {\r\n // If an existing LanguageModel instance is passed (from openai(), anthropic(), etc.), wrap directly\r\n if (typeof modelOrId === 'object' && modelOrId !== null) {\r\n return withBilling(modelOrId, options);\r\n }\r\n\r\n // If a string model identifier is passed (e.g. \"openai/gpt-4o-mini\", \"anthropic/claude-3-7-sonnet\", or \"gpt-4o-mini\")\r\n if (typeof modelOrId === 'string') {\r\n const rawId = modelOrId;\r\n let providerName = 'openai';\r\n let cleanModelId = rawId;\r\n\r\n if (rawId.includes('/')) {\r\n const parts = rawId.split('/');\r\n providerName = parts[0].toLowerCase();\r\n cleanModelId = parts.slice(1).join('/');\r\n } else if (rawId.startsWith('claude-')) {\r\n providerName = 'anthropic';\r\n } else if (rawId.startsWith('gemini-')) {\r\n providerName = 'google';\r\n } else if (rawId.startsWith('deepseek-')) {\r\n providerName = 'deepseek';\r\n } else if (rawId.startsWith('grok-')) {\r\n providerName = 'xai';\r\n } else if (\r\n rawId.startsWith('mistral-') ||\r\n rawId.startsWith('codestral-') ||\r\n rawId.startsWith('ministral-') ||\r\n rawId.startsWith('magistral-') ||\r\n rawId.startsWith('voxtral-') ||\r\n rawId.startsWith('devstral-') ||\r\n rawId.startsWith('open-mistral') ||\r\n rawId.startsWith('open-mixtral')\r\n ) {\r\n providerName = 'mistral';\r\n } else if (\r\n rawId.startsWith('llama-') ||\r\n rawId.startsWith('mixtral-') ||\r\n rawId.startsWith('gemma') ||\r\n rawId.startsWith('qwen-')\r\n ) {\r\n providerName = 'groq';\r\n } else if (rawId.startsWith('command-')) {\r\n providerName = 'cohere';\r\n } else if (rawId.startsWith('mercury-') || rawId.startsWith('ling-')) {\r\n providerName = 'gateway';\r\n } else if (rawId.startsWith('gpt-image-') || rawId.startsWith('gpt-6-')) {\r\n providerName = 'openai';\r\n }\r\n\r\n const apiKey =\r\n options.apiKey ||\r\n process.env.AI_GATEWAY_API_KEY ||\r\n (providerName === 'anthropic' ? process.env.ANTHROPIC_API_KEY : undefined) ||\r\n (providerName === 'google' ? process.env.GOOGLE_GENERATIVE_AI_API_KEY : undefined) ||\r\n (providerName === 'mistral' ? process.env.MISTRAL_API_KEY : undefined) ||\r\n (providerName === 'groq' ? process.env.GROQ_API_KEY : undefined) ||\r\n (providerName === 'deepseek' ? process.env.DEEPSEEK_API_KEY : undefined) ||\r\n (providerName === 'xai' ? process.env.XAI_API_KEY : undefined) ||\r\n (providerName === 'cohere' ? process.env.COHERE_API_KEY : undefined) ||\r\n process.env.OPENAI_API_KEY;\r\n\r\n const baseURL =\r\n options.baseURL ||\r\n process.env.AI_GATEWAY_BASE_URL ||\r\n (providerName === 'openai' ? 'https://api.openai.com/v1' : undefined);\r\n\r\n let baseModelInstance: any = null;\r\n\r\n try {\r\n if (providerName === 'openai' || providerName === 'gateway' || !providerName) {\r\n const mod = require('@ai-sdk/openai');\r\n const factory = mod.createOpenAI || mod.openai || mod.default?.createOpenAI || mod.default?.openai;\r\n if (typeof factory === 'function') {\r\n if (mod.createOpenAI) {\r\n const provider = factory({ apiKey, baseURL });\r\n baseModelInstance = provider(cleanModelId);\r\n } else {\r\n baseModelInstance = factory(cleanModelId);\r\n }\r\n }\r\n } else if (providerName === 'anthropic') {\r\n const mod = require('@ai-sdk/anthropic');\r\n const factory = mod.createAnthropic || mod.anthropic || mod.default?.createAnthropic || mod.default?.anthropic;\r\n if (typeof factory === 'function') {\r\n if (mod.createAnthropic) {\r\n const provider = factory({ apiKey, baseURL });\r\n baseModelInstance = provider(cleanModelId);\r\n } else {\r\n baseModelInstance = factory(cleanModelId);\r\n }\r\n }\r\n } else if (providerName === 'google') {\r\n const mod = require('@ai-sdk/google');\r\n const factory = mod.createGoogleGenerativeAI || mod.google || mod.default?.createGoogleGenerativeAI || mod.default?.google;\r\n if (typeof factory === 'function') {\r\n if (mod.createGoogleGenerativeAI) {\r\n const provider = factory({ apiKey, baseURL });\r\n baseModelInstance = provider(cleanModelId);\r\n } else {\r\n baseModelInstance = factory(cleanModelId);\r\n }\r\n }\r\n } else if (providerName === 'mistral') {\r\n const mod = require('@ai-sdk/mistral');\r\n const factory = mod.createMistral || mod.mistral || mod.default?.createMistral || mod.default?.mistral;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createMistral ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n } else if (providerName === 'groq') {\r\n const mod = require('@ai-sdk/groq');\r\n const factory = mod.createGroq || mod.groq || mod.default?.createGroq || mod.default?.groq;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createGroq ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n } else if (providerName === 'deepseek') {\r\n const mod = require('@ai-sdk/deepseek');\r\n const factory = mod.createDeepSeek || mod.deepseek || mod.default?.createDeepSeek || mod.default?.deepseek;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createDeepSeek ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n } else if (providerName === 'xai') {\r\n const mod = require('@ai-sdk/xai');\r\n const factory = mod.createXai || mod.xai || mod.default?.createXai || mod.default?.xai;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createXai ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n } else if (providerName === 'cohere') {\r\n const mod = require('@ai-sdk/cohere');\r\n const factory = mod.createCohere || mod.cohere || mod.default?.createCohere || mod.default?.cohere;\r\n if (typeof factory === 'function') {\r\n baseModelInstance = mod.createCohere ? factory({ apiKey, baseURL })(cleanModelId) : factory(cleanModelId);\r\n }\r\n }\r\n } catch {\r\n // Fallback object implementing LanguageModel shape if provider package not installed\r\n baseModelInstance = {\r\n specificationVersion: 'v2',\r\n provider: providerName,\r\n modelId: cleanModelId,\r\n };\r\n }\r\n\r\n if (!baseModelInstance) {\r\n baseModelInstance = {\r\n specificationVersion: 'v2',\r\n provider: providerName,\r\n modelId: cleanModelId,\r\n };\r\n }\r\n\r\n return withBilling(baseModelInstance, options);\r\n }\r\n\r\n return modelOrId;\r\n}\r\n\r\n/**\r\n * Creates a scoped session for unified multi-call and tool tracking.\r\n */\r\nexport function createVibezSession(sessionOptions: VibezSessionOptions = {}): VibezSession {\r\n const meter = createMeter({\r\n apiKey: sessionOptions.stripeApiKey,\r\n });\r\n\r\n const customerId =\r\n typeof sessionOptions.customer === 'string'\r\n ? sessionOptions.customer\r\n : sessionOptions.customer?.id;\r\n\r\n return {\r\n meter,\r\n model: (modelOrId: any, callOptions: VibezCheckModelOptions = {}) => {\r\n return createVibezModel(modelOrId, {\r\n customer: sessionOptions.customer,\r\n pricing: sessionOptions.pricing,\r\n billing: sessionOptions.billing,\r\n meter,\r\n metadata: {\r\n ...sessionOptions.metadata,\r\n ...callOptions.metadata,\r\n },\r\n ...callOptions,\r\n });\r\n },\r\n trackTool: async (name: string, { costUSD, metadata }: { costUSD: number; metadata?: Record<string, any> }) => {\r\n // Record non-LLM tool usage as a custom usage event\r\n const event: UsageEvent = {\r\n timestamp: new Date().toISOString(),\r\n model: `tool:${name}`,\r\n provider: 'tool',\r\n usage: {\r\n inputTokens: 0,\r\n outputTokens: 0,\r\n totalTokens: 0,\r\n },\r\n cost: {\r\n inputCostUSD: 0,\r\n outputCostUSD: costUSD,\r\n totalUSD: costUSD,\r\n currency: 'USD',\r\n },\r\n customerId,\r\n metadata: {\r\n ...sessionOptions.metadata,\r\n ...metadata,\r\n tool: name,\r\n },\r\n };\r\n\r\n meter.recordUsage({\r\n model: `tool:${name}`,\r\n provider: 'tool',\r\n inputTokens: 0,\r\n outputTokens: 0,\r\n customerId,\r\n metadata: event.metadata,\r\n });\r\n\r\n await meter.flush();\r\n },\r\n };\r\n}\r\n\r\n// Attach session helper to createVibezModel function\r\nexport const vibezcheck: typeof createVibezModel & {\r\n session: typeof createVibezSession;\r\n} = Object.assign(createVibezModel, {\r\n session: createVibezSession,\r\n});\r\n"],"mappings":"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","names":["rawUsage","customerObj","Stripe"]}
|