/** * Access to the synced capability snapshot (`docs/tier-data.json`, written by * `npm run sync:tiers` from OpenRouter + BFCL + LMArena + Aider). * * Its own module so both `registry.ts` (the /registry view) and `benchmarks.ts` (pool ranking) * can read it without an import cycle — `config.ts` imports `benchmarks.ts`, so anything * `benchmarks.ts` pulls in must not reach back into `config.ts`. */ export interface TierModel extends Record { name?: string; norm: string; sources?: string[]; strength?: number | null; strength_rank?: number | null; signals?: string[]; signal_count?: number; /** Fixed-weight capability dimensions, already calibrated to 0-1. */ dimensions?: Partial>; direct_dimensions?: string[]; imputed_dimensions?: string[]; capability_confidence?: number; task_fit_score?: number | null; task_fit_signals?: string[]; task_fit_signal_count?: number; /** Capability and behavioral publications combined; used only for the evidence minimum. */ published_signal_count?: number; /** Capability-floor bands materialized by sync, including persisted exit hysteresis. */ effort_eligibility?: string[]; /** * Context window in tokens as OpenRouter publishes it for this model id. * * A real published measurement, not a capability score — which is why it can back a context * window when the SERVING provider publishes nothing. It is still a different host's figure for * the same model, so it must never be presented as the serving provider's own number. */ context_length?: number | null; } export interface TierData { synced_at?: string; models: TierModel[]; /** Lower-cased rows used only for fuzzy containment misses. */ byNorm: Array<{ norm: string; rec: TierModel; }>; /** Exact lower-cased SKU lookup. Optional so injected legacy snapshots remain valid. */ exactByNorm?: ReadonlyMap; /** File revision behind this snapshot, for routing-cache invalidation. */ revision?: string; } /** * Memoized on the file's mtime so `npm run sync:tiers` is picked up without a restart. The file is * ~770 rows and three endpoints need it per request; re-reading and re-indexing each time is pure * waste. Negative results are cached too, so a missing file is not a stat+throw per request. */ export declare const DEFAULT_TIER_RECHECK_MS = 30000; export declare function loadTierData(opts?: { now?: number; force?: boolean; recheckMs?: number; }): TierData | null; export interface TierMatch { rec: TierModel; /** `fuzzy` means a DIFFERENT model's row whose name contains this one's — indicative, not measured. */ match: "exact" | "fuzzy"; /** * Price suffix stripped to reach the row, or null when the id matched as written. * * A price suffix names what the deployment COSTS, not what the model CAN DO — unlike an * effort suffix (`-high`), which `normName()` rightly never strips. So a suffixed id that * resolves through its base still reports `match: "exact"`: the base id matched exactly. * The deployment's own PRICE still comes from `resolveMetadata`/the catalog — the tier row * lends weights, never a price. */ priceSuffix: PriceSuffix | null; } /** * Closed list of trailing PRICE suffixes `findTierModel` may strip — longest first, so * `-contributor-free` wins over `-free` on an id carrying the longer one. * * ⚠ ONE suffix is stripped, never two, and never from the middle: `foo-free-high` keeps its * effort tail and resolves as written (or not at all). An effort suffix names a different * capability and is never a price suffix — stripping it would be the borrowed-score bug. */ export declare const PRICE_SUFFIXES: readonly ["-contributor-free", "-free"]; /** One member of `PRICE_SUFFIXES` — the suffix a suffixed id was resolved through. */ export type PriceSuffix = (typeof PRICE_SUFFIXES)[number]; /** * Look a routing spec up in the snapshot. Matches on the id's last segment, which is exactly the * key `sync-tiers.mjs` stores for OpenRouter models — so a spec like `nim/z-ai/glm-5.2` hits the * `glm-5.2` row exactly rather than fuzzily landing on `glm-5.2-max`. * * Generic over the record type so callers holding looser row shapes (registry's raw * leaderboard records) can share this one matcher instead of reimplementing it. */ export declare function findTierModel(modelId: string, byNorm: Array<{ norm: string; rec: T; }>, exactByNorm?: ReadonlyMap): { rec: T; match: "exact" | "fuzzy"; priceSuffix: PriceSuffix | null; } | null; /** * Context window the synced snapshot publishes for a spec, with how it was matched. * * Cheap to call per pool member: `loadTierData` is memoized on the file's mtime, and the caller * decides what to do with a `fuzzy` match. `contextWindowResolver` in metadata.ts rejects fuzzy — * a borrowed SKU's context window tells a client it may send tokens the backend will reject. */ export declare function snapshotContextWindow(spec: string): { tokens: number; match: "exact" | "fuzzy"; } | null;