TypeScript 97.4%
SQL 1%
JavaScript 0.9%
CSS 0.6%
1import type { ModelPricing, Usage } from "./types";23export interface CostBreakdown {4 inputUsd: number;5 cachedInputUsd: number;6 outputUsd: number;7 totalUsd: number;8 /** false when pricing is missing → totalUsd is 0 and should be shown as "n/a". */9 known: boolean;10}1112/**13 * Estimate the cost of one request. Reasoning tokens are billed as output tokens by14 * every current provider; cached input tokens are billed at the cached rate when known15 * (otherwise at the normal input rate). Long-context tiers apply when the prompt exceeds16 * the provider's threshold.17 */18export function estimateCost(usage: Usage | undefined | null, pricing: ModelPricing | null | undefined): CostBreakdown {19 if (!usage || !pricing || (pricing.inputPerMillion === undefined && pricing.outputPerMillion === undefined)) {20 return { inputUsd: 0, cachedInputUsd: 0, outputUsd: 0, totalUsd: 0, known: false };21 }22 let inRate = pricing.inputPerMillion ?? 0;23 let outRate = pricing.outputPerMillion ?? 0;24 let cachedRate = pricing.cachedInputPerMillion ?? inRate;25 if (pricing.longContext && usage.inputTokens > pricing.longContext.thresholdTokens) {26 inRate = pricing.longContext.inputPerMillion ?? inRate;27 outRate = pricing.longContext.outputPerMillion ?? outRate;28 cachedRate = pricing.longContext.cachedInputPerMillion ?? cachedRate;29 }30 const cached = Math.min(usage.cachedInputTokens ?? 0, usage.inputTokens);31 const uncached = Math.max(0, usage.inputTokens - cached);32 const inputUsd = (uncached / 1_000_000) * inRate;33 const cachedInputUsd = (cached / 1_000_000) * cachedRate;34 const outputUsd = (usage.outputTokens / 1_000_000) * outRate;35 const totalUsd = inputUsd + cachedInputUsd + outputUsd;36 return { inputUsd, cachedInputUsd, outputUsd, totalUsd: round(totalUsd), known: true };37}3839function round(n: number): number {40 return Math.round(n * 1e8) / 1e8;41}4243export function tokensPerSecond(outputTokens: number | undefined, latencyMs: number | undefined, ttftMs?: number | undefined): number | null {44 if (!outputTokens || !latencyMs) return null;45 const gen = Math.max(1, latencyMs - (ttftMs ?? 0));46 return Math.round((outputTokens / gen) * 1000 * 10) / 10;47}48