SPB Git

spb/chat-spboucher Public

Private universal chat interface over the OpenRouter ecosystem — 400+ models, branching, streaming, usage tracking. Next.js 16 + SQLite, PWA, deployed on m4m64a at chat.spboucher.ai

TypeScript 78.8% CSS 15.1% JavaScript 4.9% Shell 1.2%
2.0 KB · 58 lines typescript
Raw Blame History
1// Author: Simon-Pierre Boucher2// Contact: contact@spboucher.ai3// Project: chat.spboucher.ai45import type { ORModelRaw } from "./schemas";6import type { ModelDefinition } from "./types";78function toNumber(v: string | number | null | undefined): number | undefined {9  if (v === null || v === undefined) return undefined;10  const n = typeof v === "number" ? v : parseFloat(v);11  return Number.isFinite(n) ? n : undefined;12}1314/** Pricing values are USD per token (per request/image where applicable). */15export function derivePricing(raw: ORModelRaw): ModelDefinition["pricing"] {16  const p = raw.pricing ?? {};17  return {18    prompt: toNumber(p.prompt),19    completion: toNumber(p.completion),20    image: toNumber(p.image),21    request: toNumber(p.request),22  };23}2425/** Estimated cost in USD from token counts and per-token prices. */26export function estimateCost(27  pricing: ModelDefinition["pricing"] | undefined,28  promptTokens: number | undefined,29  completionTokens: number | undefined30): number | undefined {31  if (!pricing) return undefined;32  const inCost = pricing.prompt !== undefined && promptTokens !== undefined ? pricing.prompt * promptTokens : undefined;33  const outCost =34    pricing.completion !== undefined && completionTokens !== undefined35      ? pricing.completion * completionTokens36      : undefined;37  if (inCost === undefined && outCost === undefined) return undefined;38  return (inCost ?? 0) + (outCost ?? 0);39}4041/** Format a USD amount for display: $0.0042, $0.42, $4.20. */42export function formatUsd(v: number | undefined | null): string {43  if (v === undefined || v === null) return "—";44  if (v === 0) return "$0";45  if (v < 0.01) return `$${v.toFixed(4)}`;46  if (v < 1) return `$${v.toFixed(3)}`;47  return `$${v.toFixed(2)}`;48}4950/** Price per 1M tokens for the model rail chip. */51export function perMillion(perToken: number | undefined): string {52  if (perToken === undefined) return "—";53  const v = perToken * 1_000_000;54  if (v === 0) return "free";55  if (v < 1) return `$${v.toFixed(2)}/M`;56  return `$${v.toFixed(v < 10 ? 2 : 0)}/M`;57}58