OmniRoute v3.8.53
1,189 documented changes from 1,162 commits in the cycle, with 222 people contributing. Thank you all.
📄 Complete release notes (every entry, full description and credit): attached below as CHANGELOG-v3.8.53.md, and in CHANGELOG.md → [3.8.53].
⚠️ Known at release time: providers.apiRegionLabel (fi, ko, pl, pt, pt-BR, zh-CN, zh-TW) and providers.apiRegionInternational (fi) show their English text until they are retranslated in v3.8.54.
📊 Release by the numbers
| 👥 People who contributed | 222 |
| 📝 Commits in the cycle | 1,162 |
| 🔀 Pull requests referenced | 847 |
| 📋 Changelog entries | 1,189 |
| 🙌 Contributors credited in entries | 221 |
| 🤖 Automated dependency commits | 11 |
Entries by type
| Type | Count |
|---|---|
| 🐛 Fixes | 588 |
| ♻️ Refactor | 204 |
| ✨ Features | 146 |
| 🧪 Tests | 93 |
| 📚 Docs | 70 |
| 🧹 Chore | 51 |
| ⚙️ CI | 18 |
| ⚡ Performance | 10 |
| 📦 Dependencies | 7 |
| 🏗️ Build | 2 |
🏆 Top 25 contributors this cycle
By commits in c754707d0e..616801a2b6, author identities consolidated via .mailmap and the merged PR's GitHub login. Bots excluded.
| # | Contributor | Commits |
|---|---|---|
| 🥇 | diegosouzapw | 607 |
| 🥈 | Jan Leon (@JxnLexn) | 47 |
| 🥉 | Dizzle (@maxmad64bis) | 44 |
| 4 | Minxi Hou (@HouMinXi) | 40 |
| 5 | Paco Cartones (@pacocartones) | 39 |
| 6 | Ai Captain 357 (@AiCaptain357) | 27 |
| 7 | Andres Felipe Diago Matta (@AndresDiagoM) | 17 |
| 8 | Sean Ford (@seanford) | 16 |
| 9 | Fabio Junior Gruchovski (@fabioKoruja00) | 15 |
| 10 | Praveen K Palaniswamy (@yourspraveen) | 14 |
| 11 | 小妍儿 ✨ (@xiaoyaner0201) | 13 |
| 12 | Aldo (@aldoeliacim) | 11 |
| 13 | Junior-HJ | 9 |
| 14 | shin (@jjxyxsjr) | 8 |
| 15 | serenity (@serenity-X) | 8 |
| 16 | shevar0 | 8 |
| 17 | Bl0ck (@Bl0ck154) | 7 |
| 18 | opensource-elearning | 7 |
| 19 | Rafa Martins (@rafacpti23) | 7 |
| 20 | skygunner | 7 |
| 21 | trespassmk | 7 |
| 22 | Innokentiy Solntsev (@insoln) | 6 |
| 23 | Calvin Chen (@DarknessKiller) | 5 |
| 24 | Fouad Salkini (@fouadSalkini) | 5 |
| 25 | Kiaro-Sama (@KiaroSama) | 4 |
✨ New Features
- feat(dashboard): the dashboard and the standalone pages (login, status, error, legal, docs) run on the Keak CI UI Kit (KEA-7886), vendored as the
packages/ui-kitworkspace at a pinned upstream commit (packages/ui-kit/UPSTREAM.md, byte-identity guarded bynpm run check:ui-kit-snapshot). The Keak identity replaces the old one — lime accent, self-hosted Inter / Instrument Serif / IBM Plex Mono, kit radius… - feat(teams): add billing cost centers with temporal API-key assignments, shared soft budgets, and team usage reporting (#10409) — thanks @hartmark / @xiaoyaner0201
- feat(gemini): add an opt-in
geminiPromptCacheModesetting (offby default,implicit) scoped to Antigravity/AGY Gemini targets that preserves Gemini implicit prompt-cache evidence (hit/miss/unreported/invalid) across streaming, non-streaming, wrapped/unwrapped, OpenAI and Claude paths, never reports a cached count larger than the prompt, keeps prompt-cache affinity from reusing… - feat(release):
npm run bun:release(scripts/release/bun-pack.mjs) packs the already-builtdist/into an npm-compatible tarball withbun pm pack(falling back tonpm pack) for bun-first global installs; the Next.js build and prepublish step stay on Node. Thanks to @opensource-elearning (#12801). - feat(oauth): GitHub Copilot connections record the account's plan, model-selection mode and quota state, and the dashboard shows a policy disclosure before the device-code login; Free / Student accounts use the catalog's
automodel (#12833) — thanks @ScottyAmr - feat(api): Bifrost sidecar fast-path for
/v1/chat/completionsand/v1/messageswith native fallback. The fast-path runs the API-key policy first, sends/v1/messagesto the sidecar's Anthropic-compatible endpoint, never relays echoed credential or cookie headers, and falls back to the native pipeline on 5xx, network errors, or an unsupported endpoint (#12953 — thanks @rqzbeh) - feat(services): sing-box embedded service — a supervised TPROXY sidecar installed from the official SagerNet release (pinned v1.14.1, SHA256-verified per platform; any other version or a checksum mismatch is refused). It gets the full embedded-service surface (8 loopback-only
/api/services/singbox/*routes, dashboard tab,SINGBOX_PORT, seed migration 221). When TPROXY capture is applied, sing-box listens… - feat(routing): add per-API-key ordered
preferredConnections, allowing each project to pin a primary provider account with quota/cooldown-aware automatic fallback to the next eligible account without changing global connection priority. (#13102 - thanks @Bl0ck154) - feat(providers): improve Antigravity and Cursor request handling and resilience (#13125) — thanks @tuandinh0801
- feat(providers): Added ainetcafe as an OpenAI-compatible API-key provider (
https://microquickjs.com/v1, Kimi K3 served from its own cluster), with live model discovery viapassthroughModels(#13862) — thanks @mario03690 - feat(combo): add an opt-in agentic-stall failover (
OMNIROUTE_AGENTIC_STALL_FAILOVER=1, default OFF): a combo member that answers a tool-result turn withfinish: stop, narration and no tool call now fails over to the next target, and its answer is returned only if no target does better (#13954 - thanks @patrykkopycinski) - feat(backend): the proxy-registry bulk import ceiling is now an operator setting (
proxyBulkImportLimit, default 100, hard cap 10,000) instead of a constant hardcoded in two places. It is written throughPATCH /api/settings({"proxyBulkImportLimit": 500}, integer 1–10,000). PreviouslybulkImportProxiesSchemaand the dashboard's pre-flight check each carried their own literal100, so raising the limit… (#14074) — thanks @abhisheksharma2411 - feat(cli-agents): add WhyCodes as a first-class CLI Agent (
category: "agent", Chat Completions/v1) with catalog detection,omniroute setup-whycodes/configure whycodes,omniroute run whycodes -P omniroute -m <id>, and a dashboard apply path.whycodes acpis not implemented, soacpSpawnablestays false. (#14096) (#14107) — thanks @mrnasil - feat(providers): add Kimi (Moonshot) as a web search provider via
POST /v1/tools/search, joining the search gateway's failover ring (#14292) — thanks @yourspraveen - feat(api):
UNPRICED_USAGE_BUDGET_POLICYfeature flag chooses how per-key daily/weekly USD limits treat usage of a model with no configured price.fail_closedstays the default and keeps the #13257 verdict;count_as_zerocounts that usage as $0 and still enforces priced spend. A key blocked only by unpriced usage now gets a 400 that names the unpriced models instead of a low "quota reached (N%)". Admins… (#14608, closes #14604) — thanks @xiaoyaner0201 - feat(api): authenticate Claude Code (and any client) to
/v1/*with a Microsoft Entra ID token instead of a static API key — Entra security groups map onto existing OmniRoute key groups (model allow/deny rules; per-key budgets and rate limits are unaffected by group membership) and usage is attributed per person. Ships a dependency-free sign-in helper (scripts/cli/omniroute-sso.mjs) for Claude Code's… — thanks @BenjaminAronsson - feat(usage): display and claim Anthropic reset credits in the dashboard — parse banked usage grants (
cedar_ember) and weekly 5-hour session resets (juniper_tide) from Claude OAuth usage, show available reset credits on Claude provider limit cards, and enable redemption via/api/usage/codex-reset-credit(#14728). — thanks @fouadSalkini - Enrich routing events with
apiKeyIdand the real streaming cost: OTel spans now carryomniroute.api_key.idandgen_ai.usage.cost/.currency, and the stream routing event is emitted once the cost lookup lands (null on failure). (#14736 — thanks @kenny000666 / @adevwithpurpose) - feat(providers): dashboard control for the advertised Claude Code / Codex CLI client version, so operators can get past upstream model gates (Anthropic tiers, and OpenAI's "The 'gpt-6-astra' model requires a newer version of Codex") without an env var and a restart. One global override per provider kind; it sits above the env var and the automatic npm/GitHub version discovery, and the API/card surface the… (#14817) — thanks @adivekar-utexas
- feat(dashboard): assign selected models and combos to API keys from the catalog, with explicit confirmation before restricting an allow-all key. (#14890) — thanks @fouadSalkini
- feat(dashboard): the combo test results modal gets a "Delete N failed model(s)" button that removes, after a confirmation, the combo's own steps whose every probe failed with a non-transient 4xx (timeouts, 408/429 and 5xx never count, and steps inside a nested combo are left alone); each result row now leads with the model id, with the account label and id underneath (#14944, thanks @skymanbj)
- feat(providers): the ChatGPT Web (Clean Room) adapter now supports client tool calls in bounded turns:
tools, assistanttool_callsandrole: "tool"continuations are accepted instead of rejected, emulated through the shared<tool>{json}</tool>envelope and returned as canonicaltool_calls(JSON and SSE); each turn settles on the closing</tool>, is capped byCHATGPT_WEB_TOOL_TURN_TIMEOUT_MS/… (#14948) — thanks @arashashrafii - feat(api): opt-in quota session recovery: a non-streaming chat/responses turn that hits a terminal quota error can be parked (encrypted, 24 h) with
x-omniroute-quota-recovery: autoand polled atGET /api/v1/quota-recoveries/{id}instead of failing (#14982, closes #14981) — thanks @dongwook-chan - feat(muse): session-level two-account rotation with caller-bound reasoning ownership — fresh sessions round-robin across native OAuth accounts while continuations and tool-result turns stay pinned to owner connection, account identity, and credential generation (hashes only), failing closed on unknown owners or generation changes instead of silent cross-account replay; OAuth-narrowed (API-key operation… (#15521) — thanks @kalpakprod / @mdc2122 / @SIGTERM-015 / @KSonny4 / @caniko / @Chewji9875
- feat(oauth): Route video generation, speech and transcription through the existing Grok Build OAuth connection, and image generation too when
GROK_SUBSCRIPTION_IMAGES_ENABLEDis on (same opt-in and request contract as the other Grok subscription image routes) (#15305) — thanks @Kizuno18 - feat(oauth): Freebuff browser login on the existing
freebuffprovider card (#15343) — mirrorsfreebuff login(fingerprint code → freebuff.com sign-in → status poll) and stores the resulting Codebuff auth token as an OAuth connection. Dual-auth keeps the pasted-token path. The token has no refresh grant, so it is marked non-refreshable and an expired token means signing in again. Closes #15336 — thanks… #15336 — thanks @PranavD2905 - feat(muse-code): consolidate open Muse Code PRs — opencode-go sends
reasoning.effort=maxverbatim for muse-spark-1.3+ with onexhighretry on the upstream unsupported-effort 400 (#12687);MuseCodeExecutorrestores the 24hprompt_cache_retentionwindow the generic sanitizer strips (#13634); device-flow hardening: origin-pinned verification URLs, 24h expiry cap, allowlisted poll errors with fixed… (#15521) — thanks @Chewji9875 / @KSonny4 / @caniko / @SIGTERM-015 / @kalpakprod / @mdc2122 - feat(oauth): Import Antigravity Manager account exports with verified identities, bounded request bodies, account selection, and per-account results (#15746). — thanks @mertcandrks
- feat(resilience): opt-in anti-avalanche failover guard (
OMNIROUTE_AVALANCHE_PROTECTION_ENABLED=true, off by default) — when enabled, a 429 that names a tokens-per-minute limit no longer cascades over the provider's remaining keys and the model lockout uses a short cooldown instead of escalating, while a longer upstream reset always wins; quota-exhausted 429s keep failing over however large the prompt is and… (#15775 — thanks @ggdayup) - feat(combos): the combo editor marks steps whose model is no longer in the provider's live catalog with a "Not in live catalog" badge, using the stale refs that
GET /api/combos/builder/optionsnow returns (#15923) — thanks @tiagovilasboas - Declare protection domains for existing CI job groups and reject missing or invalid declarations before dependency installation. Preserve current job scheduling and required checks while preparing the unified-policy transition. Refs #16075. (#16142)
- feat(providers): complete
claude-haiku-5-5catalog wiring across Anthropic, Claude OAuth, Bedrock, and Vertex registries with length-tiered pricing ($0.10/$0.50 per MTok, $0.50/$2.50 above 100k prompt tokens) and Haiku 4.5 family fallback (#16159) — thanks @tuandinh0801 - feat(proxy): accept selector-only subscriptions with no feed URL (#16165) — thanks @maxmad64bis
- feat(v1-models): publish the routable
autoandauto/lkgpids inGET /v1/modelswith the pool limits (#16224) — thanks @maxmad64bis - feat(api): add read-only GET /v1/models/health reporting per-model pause state for the caller's key (#16247) — thanks @maxmad64bis
- feat(models-health): report whether reasoning_effort none was honored per model on GET /v1/models/health (#16253) — thanks @maxmad64bis
- feat(dashboard): the provider detail page now shows a badge on each model row listing the combos that use that model, built from a single
/api/combosfetch (#16307 — thanks @farshadasadpour) - feat(providers): add Token Harbor (
tokenharbor) as an OpenAI-compatible API-key gateway with Bearer-key authentication, live model discovery from/v1/models, and a free-tier catalog entry forclaude-haiku-5.5:free(#16315 - thanks @turbolego) - Free-model catalog: add onomeo's 13 currently served free models (
auto, DeepSeek V4 Flash, GLM 5.2/5.3/4.5/4.6v/4.7 Flash, Gemini 3.1 Flash Lite, GPT-OSS 20B, Muse Glimmer 30B, Codestral, Ministral 14B, HY4 Preview) asrecurring-uncappedrows with no invented token figure (30 calls per 5 h in a shared pool), backed by per-model evidence records (#16318, thanks @opensource-elearning). (#16325) - feat(usage): StepFun account balance is shown as a credits-style quota in Provider Limits, with the China (CNY) or international (USD) platform picked from the connection base URL (#16348 - thanks @Neuron-Mr-White)
- feat(cli-tools): the Pi setup flow now writes OmniRoute into Pi's current
~/.pi/agent/models.jsonprovider format (PI_CODING_AGENT_DIRhonoured) instead of the legacy flat~/.pi/config.json, with a dedicated Pi card (endpoint, key, model, preview, apply, reset, backups), runtime/config-state detection, and ownership-marker safety so only the OmniRoute-owned provider is ever rewritten or removed; an… (#16381) — thanks @arashashrafii - feat(proxy): Operator-reported outages set a pool member aside briefly, with automatic return at expiry or on served traffic (#16385) — thanks @maxmad64bis
- feat(db): a refused egress address is skipped on every pool member sharing it inside the same egress-bucketed provider scope (#16421) — thanks @maxmad64bis
- feat(core-config): translate subscription URI and Clash nodes into outbounds instead of skipping them (#16432) (#16435) — thanks @maxmad64bis
- feat(core-config): render owned subscriptions to Mihomo YAML in addition to sing-box JSON (#16435) — thanks @maxmad64bis
- feat(core-config): a subscription can now ingest several feeds with per-source isolation: a failing feed only skips its own nodes while the others still render (#16439) — thanks @maxmad64bis
- feat(proxy): accept explicitly named host-first bulk proxy rows while preserving existing import formats, credential fields and safe validation errors (#16450) — thanks @KiaroSama
- feat(guardrails): PII masking covers GDPR and POPIA identifiers (IBAN, EU VAT, Spanish DNI/NIE, Italian Codice Fiscale, Polish PESEL, Dutch BSN, German Steuer-ID, Swedish personnummer, South African ID/phone/VAT/tax reference). Every match must pass its checksum, structure or context validator before it is redacted on the request and response sides, so order numbers, timestamps and identifiers such as
gpt4o… (#16461) — thanks @zerotraceio - feat(dashboard): no-auth provider cards now show a working inline toggle even when they have no connection rows, and the No Auth section gains Disable all / Enable all actions. Both write
settings.blockedProvidersthrough the alias-awarecomputeNextBlockedProvidershelper (canonical id and alias stay in sync) and still forward the change to the existing connection toggle (#16553 — thanks @Junior-HJ). - feat(affinity): optional Redis store (
OMNIROUTE_SESSION_AFFINITY_STORE=redis) so multiple instances share session-to-account affinity by hashed account identity; default SQLite behaviour is unchanged (#16569) — thanks @xiaoyaner0201 - feat(combo): Opt-in
quotaWeightedScoring: "pace"for thequota-weightedstrategy weights each account by its latest-resetting window's leftover per hour until that reset, so quota that is about to expire is spent first while the draw stays proportional and each account is weighted by its live plan's capacity (monthly price ratio); the default"leftover"scoring is unchanged (#16572, closes #16458) —… (#16572, closes #16458) — thanks @xiaoyaner0201 - Added opt-in passive Codex token refresh for replicas via
OMNIROUTE_TOKEN_REFRESH_PASSIVE_PROVIDERS=codex(aliascx): reread synchronized tokens without rotation or terminal refresh failures, preserve normal upstream authentication cooldowns, store imports without a token exchange, and report a clear error for manual refresh. (#16577) — thanks @xiaoyaner0201 - feat(logs): Export persisted call logs as OTLP/HTTP JSON traces, with optional Langfuse generation mapping, encrypted headers, per-destination pseudonymous identities, bounded requests and retries, and a create-time option to skip retained-history backfill. Optional
requestHeaderAllowlistcaptures saved client request headers as standard OTLP string-array attributes (requiresincludeBodiesand saved… (#16664) — thanks @xiaoyaner0201 - feat(routing): opt-in per-connection latency signal for p2c account selection (
resilienceSettings.p2cLatency.weight, default off) (#16737) — thanks @berthojoris - feat(resilience): per-provider rate-limit retry delay — a "Retry delay" select on the provider page sets a fixed connection cooldown used when a rate-limit error carries no upstream retry hint (#16741) — thanks @MuhammadUsamaMX
- feat(api): the API-only port (
API_PORT) now also relays Gemini-native/v1beta/*routes, so Gemini CLI and google-genai SDK clients work against it (#16745) — thanks @MuhammadUsamaMX - feat(api):
GET /api/monitoring/model-healthreports a health state for every synced model on every provider connection (HEALTHY, DEGRADED, RATE_LIMITED, AUTH_FAILED, PROVIDER_DOWN, CONNECTION_BLOCKED, MODEL_LOCKED, UNKNOWN) from the connection state, the provider circuit breaker and the per-model lockout, withprovider,stateandunhealthy=1filters. Management-only, since the report carries connection… (#16746 — thanks @Longvt1164) - feat(combos): export/import combos as a standalone, secret-free JSON file — merge by default, explicit transactional replace, connections and credentials never travel (#16747) — thanks @vianhanif
- feat(dashboard): per-step Test button in the combo create/edit modal — probes one model step (pinned account included) and shows latency or the error inline (#16748) — thanks @smserwan
- feat(dashboard): hide/show models across all providers from the Models catalog — a Visible toggle, an All/Visible/Hidden filter and "Hide/Show filtered" bulk actions write the same per-provider visibility that
/v1/modelshonors (#16749) — thanks @MuhammadUsamaMX - feat(providers): edit manual vision overrides on synced models and clear legacy vision overrides explicitly. (#16765) (#16794)
- feat(plugin):
@omniroute/opencode-plugin-v2gains an opt-infreeSignalsoption sofreeOnlycan also admit models the pricing table prices at zero, ids ending in-free/:free, and*-freeproviders, labelled(free, inferred)(#16800) — thanks @maxmad64bis - feat(cli-tools): add OpenClaude setup guide card to the CLI Code catalog (OpenAI-compatible env vars +
openclaude --provider openai) (#16844) — thanks @ntdatt812 - feat(api): opt-in "expose combos only" setting so
/v1/modelsadvertises only combos (user combos +auto/*) while explicit provider/model ids keep routing (#16846) — thanks @snower - feat(sse): opt-in relevance-based tool disclosure (
settings.toolDisclosure) keeps the client tools most relevant to the current turn (BM25) before the provider tool cap, never dropping tools already used, forced, pinned or named in the prompt; fails open on errors and offers a conservativemode: "zeroOverlap"that drops only tools sharing no word with recent messages (#16861) — thanks @nitsuah / @vianhanif - feat(providers): Amazon Bedrock embedding models are now reachable through
POST /v1/embeddings— Titan Text V2/G1, Titan Multimodal G1, and Cohere Embed v4/English v3/Multilingual v3, including image embeddings,dimensionsmapping, and OpenAI-shaped batching over Bedrock's per-familyInvokeModelpayloads (#16869) — thanks @qwer2003tw - feat(dashboard): Add an account-availability quota overview with per-pool capsule rows, cooldown recovery, account details, and browser-persisted provider reordering across layouts. (#17026 — thanks @xiaoyaner0201)
- feat(sse): opt-in
OMNIROUTE_EGRESS_QUOTA_ROTATION_PROVIDERS=allsets a proxy-pool member aside after a429for every provider, not only the IP-bucketed opencode family, so free and keyless providers stop re-picking the member that just answered429; unset keeps today's behaviour byte-for-byte, and the clear-on-success arm and sibling-connection lockout stay narrow (#17074) — thanks @opensource-elearning - feat(compression): New opt-in flag
COMPRESSION_CACHE_AUTOMATIC_PREFIX_ESTIMATE(default off): compression cache stats then count a request to an automatic-prefix-caching provider (OpenAI, Codex, Azure) as an estimated cache hit withoutcache_controlmarkers. The estimate is a cache-eligibility signal, not an observed hit. With the flag off the stats are unchanged (#17114) — thanks @aldoeliacim - feat(logs): call-log rows record the client's own session id (
client_session_id: opencodex-opencode-session, Claude Codex-claude-code-session-id/metadata.user_id, Codexsession_id) next to OmniRoute'ssession_tag, so requests can be joined to the agent session that sent them (#17125) — thanks @AndresDiagoM - feat(providers): custom OpenAI chat-format compatible connections can set
providerSpecificData.toolNameMaxLengthto alias over-length tool names (e.g. a gateway in front of Bedrock Converse, 64 chars), andanthropic-compatible-*connections honor a declaredquotaEndpointfor quota polling and quota-aware routing (#17136) — thanks @guiguan - feat(dashboard): the Custom Models editor can set a per-model Max Output Tokens override (blank clears it), wired to the existing
maxOutputTokenOverridefield ofPUT /api/provider-modelsso/v1/modelsreports it for strict OpenAI-compatible clients (#17140) — thanks @SaebAmini - feat(i18n): the translation backend falls through a model chain —
OMNIROUTE_TRANSLATION_FALLBACK_MODELS(comma-separated) backs the primary model in the docs wave and the UI-key translators: a request moves to the next model on 429 quota, 401/402, 5xx, timeout or network failure (never on a malformed request), each model keeping its own transient retry, with the per-chunk validator unchanged (#17255) - feat(api):
GET /v1/modelsentries carry an OpenRouter-compatiblepricingobject (prompt,completion,input_cache_read,input_cache_writeas USD-per-token decimal strings). The existing per-1M numeric fields stay in the same object. Prices come from the pricing table cost accounting uses. Combos are now priced as their first visible target, synthetic variants copy their base model's price, free… (#17259) — thanks @fouadSalkini - feat(audio): Add ElevenLabs sound effects, music composition, streaming, detailed responses and composition plans with key-scoped credentials, plus unified music generation and model discovery (#17287) — thanks @felipemarques
- feat(mcp):
omniroute_perplexity_researchruns one Perplexity Deep Research report through the active perplexity-web connection named byconnectionId(any other connection is refused). It is off by default and registered only whenOMNIROUTE_PPLX_RESEARCH_ENABLED=1; each connection runs one report at a time with a one minute cooldown after a finished report, the remaining Deep Research quota is checked… (#17317) — thanks @HouMinXi omniroute autostart enableandtoggleaccept--tray/--no-tray, persist a successful explicit choice, and reuse it for future desktop launches.serveuses that preference unless explicitly overridden; systemd autostart remains without a tray. Tray hide guidance now recommends restarting with--no-trayinstead of sending an unsupported signal. This is the CLI portion of #17330; dashboard controls and…- feat(config): refresh the OpenCode Zen free-model catalog to the 10 free ids the live
/zen/v1/modelsendpoint serves today (8 added, 4 retired), with sourced evidence records for the new rows and the free-tier counts updated to 471 (#17345 — thanks @leoplife) - feat(discovery): the provider page now shows the outcome of the last model discovery of each connection — a failed discovery keeps its cause and its age on the connection row instead of looking healthy on the next read (#17346) — thanks @maxmad64bis / @marian-paun
- Show separately labeled post-first-token and end-to-end token rates in request logs, with a keyboard-accessible explanation of buffered delivery. Both use the same reasoning-aware token count; existing TPS sorting and missing-TTFT fallback keep their generation-rate semantics. (#17349) (#17847) — thanks @morpheus9393
- feat(search): Exa 3.0
type: "lite"is billed at $0.004 per call (legacyinstanttoo) and drops the fields lite rejects instead of failing with a 400; the deprecatedsubpages,subpageTarget,highlights.numSentencesandhighlights.highlightsPerUrlare no longer forwarded (#17394) — thanks @yourspraveen - feat(search): Exa search cost now follows Exa's billing: 10 results included, $0.001 per extra result, and $0.001 per result when
contents.summaryis set (#17396) — thanks @yourspraveen - feat(chatgpt-web): the clean-room provider reaches the GPT-6 family —
gpt-6(Sol Instant),gpt-6-thinking(Sol Thinking, aliasgpt-6-sol) andgpt-6-pro(Astra Pro) — alongside the existing GPT-5.6 and GPT-5.5 lanes, mapped onto the same first-party picker families (GPT-6 Sol/GPT-5.6 Sol/GPT-5.5) (#17840) — thanks @skygunner - feat(sse): key-based OpenCode Zen and Go requests follow the published endpoint, relay the client's own
x-opencode-*headers and replay the tool parameter schemas the client already sent whenOPENCODE_PUBLISHED_CATALOG_ROUTING_ENABLEDis on, and keep the registry values unchanged while it is off (#17864) — thanks @maxmad64bis - feat(search): Tavily
search_depth: "advanced"is recorded at 2 credits ($0.016) instead of 1 (#17902) — thanks @yourspraveen - feat(search): Linkup
depth: "deep"is recorded at $0.05 per call instead of $0.005 (#17903) — thanks @yourspraveen - feat(search): Firecrawl search is recorded per started block of 10 results ($0.002 each), so 11 or more results are no longer under-recorded (#17904) — thanks @yourspraveen
- feat(providers): CodeBuddy CN now imports its authenticated live model catalog while keeping a registry fallback (#17916) — thanks @AStupidBear
- feat(db): Maintain SQLite query-planner statistics from the background cleanup scheduler (
PRAGMA optimizewith a boundedanalysis_limit, never on a request path) so composite indexes are used with skip-scan instead of full scans; configurable viaOMNIROUTE_SQLITE_OPTIMIZE_ENABLEDandOMNIROUTE_SQLITE_ANALYSIS_LIMIT(#17936) — thanks @xiaoyaner0201 - feat(db): Prune expired
semantic_cacherows from SQLite in bounded background batches (yielding between batches, optional oldest-row cap, newexpires_atindex); previously expired rows were never deleted. Configurable viaOMNIROUTE_SEMANTIC_CACHE_PRUNE_INTERVAL_MS(0disables),OMNIROUTE_SEMANTIC_CACHE_PRUNE_BATCH_SIZE,OMNIROUTE_SEMANTIC_CACHE_PRUNE_MAX_BATCHESand… (#17939) — thanks @xiaoyaner0201 - feat(settings):
outputLimitAdvisorycan be set once as a global setting instead of per combo — the combo resolver already read it from the settings row, but the key was missing from the settings schema and had no declared default, so the API stripped it and a fresh install handed the resolverundefined; the flag's semantics are unchanged (#17958) — thanks @HouMinXi - feat(search): Nimble search is recorded at the
liteprice it is sent at ($0.0011 per call) instead of $0.005 (#17965) — thanks @yourspraveen - feat(api-keys): add a per-key control for Claude Code discovery aliases so operators can keep compatibility aliases visible only where needed without widening the key's underlying model authorization (#17979) - thanks @seanford
- feat(i18n): hardcoded English strings on the Conversations page, Log export, the CLIProxyAPI account health card, the Dario (Claude accounts) panel, the Telegram miniapp and eight other dashboard components now go through the message catalogs, with new keys translated for all 66 locales (#17987) — thanks @HouMinXi
- feat(api): Added System One typed-decision models as a first-class model kind (
decisions) with a publicPOST /v1/systemoneroute (#13987). The backend is selected by model id:typesafe/jev-*or a barejev-*alias routes natively to api.typesafe.ai,openrouter/<vendor>/<model>routes to OpenRouter's alpha decisions endpoint using existing gateway credentials, quota preflight, cooldowns, call logs and… (#17994) — thanks @Neuron-Mr-White - feat(api): CLIProxyAPI management compatibility endpoints
GET /v0/management/auth-files,POST /v0/management/api-callandPOST /v0/management/reset-quota, so clients built for a CLIProxyAPI hub (such as T3 Code'scliproxyusage source) can read Claude/Codex subscription usage from OmniRoute with amanage-scoped key.api-callonly allows the four Claude/Codex usage and reset-credit requests and… (#17999) — thanks @rbansal42 - feat(auth): dashboard OIDC login can now be admitted by a role/group claim in addition to the subject/email allowlist. A new optional
oidcAdmissionClaimsetting ({ path, values }, written throughPATCH /api/settings) is checked against the verified ID token before the dashboard session is minted; it fails closed on a missing, malformed or non-array claim, and when both the subject allowlist and the claim… (#18001) — thanks @insoln - feat(antigravity): add
gemini_4_argon(argon) quota family, weekly quota summary normalization (gemini_4_argon_weekly/argon_weekly),detectAntigravityArgonEligibilityentitlement sync, and 404 retry short-circuiting for Gemini 4 Argon models (#18026) — thanks @MrSiB - feat(audio):
/v1/audio/transcriptionsaccepts a multiparturlas an alternative tofile— OmniRoute downloads it through the SSRF-hardened remote media fetcher (public HTTPS only, DNS pinning, 2 redirects, 25 MiB and 15 s caps) and sends only the audio bytes to the provider, never the caller's URL (#18040). — thanks @Bl0ck154 - feat(providers): add Runcrate (
runcrate), an OpenAI-compatible API-key provider (api.runcrate.ai) with six models (#18061) — thanks @heydryft - feat(compression): compression combos can select their own output styles (the unified output-style catalog with a level per style, previewed with the same builder the runtime uses); an empty selection inherits the Compression Engine panel, and a non-empty one supersedes the legacy output mode. A combo selected as the active profile now also applies its own output settings and language packs, not only its… (#18107) — thanks @DarknessKiller
- feat(providers): add
MiniMax-M3.1-Flashto theminimaxandminimax-cnregistries (after the defaultMiniMax-M3, 1M context, effort up tomax) with pricing from MiniMax's pricing page, and updateMiniMax-M3to its current base-tier price (0.30 / 1.20 / 0.06 per 1M tokens; the separate reasoning and cache-write rows are dropped, so MiniMax-M3 reasoning tokens now bill at the output price and cache… (#18110) — thanks @octo-patch - feat(providers): Add Gisoo (
gisoo), a prepaid OpenAI-compatible multi-model relay, as an API-key provider with live model discovery from/api/v1/models(#18112) — thanks @netarz / @heydryft - feat(opencode-plugin-v2): publish one catalog branch with
prefix/*and hide every combo withcombos: false(#18135) — thanks @maxmad64bis - feat(zcode): an opt-in
ZCODE_TRANSPORT=gatewaystreams native Anthropic responses from the Z.AI Individual Coding Plan straight to the client instead of buffering the whole turn through the ZCode app-server; it reads the plan's API key from the local ZCode profile (~/.zcode/v2/config.json, owner-only file, pinnedapi.z.aiorigin) and is experimental / unsupported, since it reproduces the ZCode client… - feat(providers): Command Code lists Kimi K3.1 Pro (
moonshotai/Kimi-K3.1-Pro) in its static catalog with reasoning-effort variants, 1M context and a 384K output ceiling, so fresh or unsynced installs can route to it (#18292) — thanks @berthojoris - feat(providers): OpenCode Go serves Kimi K3.1 Pro (
kimi-k3.1-pro): 1M context, 131K output, always-on thinking, with default pricing (#18295) — thanks @cristianob - feat(compression): RTK filter for PHPUnit test output — drops the banner, runtime header and dot progress, keeps failure headings, messages, diffs and the result summary (#18317) — thanks @itseasy21
- feat(providers): Cloudflare Workers AI model discovery reads every page of the catalog and leaves embeddings, speech, classifier and guard models out of the chat list (#18321) — thanks @askidmobile
- feat(api):
GET /api/models?withLimits=1adds each model's resolvedcontextWindow,maxInputTokensandmaxOutputTokenspluscapsSource, naming the source each limit came from (persisted override, static authoritative table, models.dev sync, provider registry or static spec). The parameter is opt-in and resolved values are unchanged (#18327) — thanks @mj10612 - feat(dashboard): the analytics Overview counters (tokens and estimated cost) animate toward their new value when the range or filters change; cost keeps its cents and
prefers-reduced-motionis respected (#18340) — thanks @F0Rextasy - feat(api):
/v1/modelsgives built-in and synced models a human-readablename(registry name first, then the synced name, else one derived from the id), and the Crush and OpenClaw config writers use the same label (#18354) — thanks @asterxsk - feat(dashboard): Persian, Arabic and Urdu now render in the self-hosted Vazirmatn font (
@fontsource/vazirmatn, OFL-1.1). The font is named only underhtml[dir="rtl"], so LTR locales never download it (#18355) — thanks @m4tinbeigi-official - feat(db): call log rows now persist
queue_wait_ms— the wait from execution start to the first upstream dispatch (#18402) — thanks @jjxyxsjr - feat(deploy): the standalone launcher can keep a Render free web service awake by pinging its own public URL; inert unless
SELF_PING_URLorRENDER_EXTERNAL_URLis set, withSELF_PING_ENABLED=falseto opt out (#18656) — thanks @Seizethewind - feat(providers): extend
expiry-firstaccount rotation with requested quota-family scoping, plan-capacity weights, and observed reset-window burn metrics. Gemini and Claude windows no longer compete across families; Codex Spark uses its own quota windows. Accounts without burn history retain the existing quota/reset scoring. (#16352) — thanks @Junior-HJ - feat(deploy): first-class Kubernetes support — Kustomize base with k3s (Traefik +
local-path) and generic k8s (ingress-nginx) overlays underdeploy/kubernetes/, plus a Helm chart atdeploy/helm/omniroute/. Both pin the single-SQLite-writer topology (replicas: 1,Recreate, ReadWriteOnce) and the chart refuses to render a configuration that would corrupt the database. Ingress defaults keep SSE… (#12400) — thanks @PauloFH / @insoln - feat(dashboard): adapter with Material→Lucide map and fallback (KEA-7886, trilha B) (direct commit
f7cff7980a) - feat(dashboard): Keak lockup and accent ink on the 404 page (KEA-7886, trilha E) (direct commit
f6d522e69f) - feat(dashboard): DashboardLayout on SidebarProvider/SidebarInset with the legacy shell behind UI_KIT_SHELL (KEA-7886, trilha F) (direct commit
1f3d69de2a) - feat(dashboard): UI_KIT_SHELL runtime flag (kill switch for the kit shell) (KEA-7886) (direct commit
548608e860) - feat(dashboard): Keak lockup on login, error, status, maintenance and offline pages (KEA-7886, trilha E) (direct commit
6419eb1722) - feat(dashboard): Keak brand wrappers (ProductIcon/ProductLockup) and product switcher links (KEA-7886, trilha E) (direct commit
87c3d70669) - feat(dashboard): theme bridge sets data-theme for the kit and retires the accent presets (KEA-7886, D4) (direct commit
d8faae192e) - feat(dashboard): size dialogs to 70% of the viewport (#14091) — thanks @zhiru
- feat(opencode): sanitize the OpenCode PR 4145 fingerprint (#14142) — thanks @rafacpti23
- feat(electron): low-frequency health watchdog with auto-restart (#17015) — thanks @for-the-zero
- feat(i18n): structure-safe Google Translate engine for the docs pipeline + ENVIRONMENT re-sync (#18429)
- feat(i18n): Google fallback and quota circuit breaker for every translation entry point (#18461)
- feat(audio): Gemini Live file-mode transcription —
gemini/gemini-3.5-transcribe-liveon/v1/audio/transcriptionsconverts the upload to 16 kHz PCM with a hardenedffmpeg(no stdin, pipe-only protocol whitelist, 25 MiB / 10 min caps, 60 s kill timeout) and transcribes it over the Gemini Live WebSocket, authenticating by header only (#15776 — thanks @ggdayup) - feat(auth): opt-in TOTP two-factor authentication with single-use recovery codes for dashboard login; while it is on,
/api/cli/connectalso requires the code (omniroute connect --totp), andOMNIROUTE_DISABLE_MFA=truegives a host-only recovery path (#16619) — thanks @tugrultamerc - feat(github): Track GitHub Copilot AI Credits (
credits_used) on the Provider Limits card and add an optional per-connection AI Credits limit that skips the account once the reported usage reaches it (fail-open on missing or stale readings; a local safeguard, not a guaranteed spending ceiling). (#16688) — thanks @Primexz - feat(dashboard): the home Provider Topology now shows live per-model sub-nodes with an On/Auto/Off toolbar (Auto, the default, draws only in-flight models) (#16739) — thanks @maulinul
- feat(command-code): per-connection Zero Data Retention toggle for Command Code API keys — when on, every upstream call and the key-validation probe send
x-cmd-zdr: 1(#16751) — thanks @ZeroOttantotto - feat(usage): TokenRouter quota tracker via an optional Management Key — wallet balance plus per-key quota on Provider Limits; the key is set in the connection modal (#16837) — thanks @dasepmoch
- feat(oauth): Devin Desktop browser sign-in (Devin CLI PKCE login, fixed 127.0.0.1:59653 callback with paste-URL fallback) and live per-account model discovery via GetCliModelConfigs with a curated-catalog fallback (#16843) — thanks @fadlee @kl3inIT
- feat(audio): support Gemini 3.8 TTS style metadata (
instructions,style,delivery,prompt), pacing viaspeed, clean audio normalization (C2PA trailer strip and single WAV framing), andresponse_format: "pcm"(#17265) — thanks @dkmscc - feat(sse): add Kimi K3.1 Pro and Highspeed support across Moonshot and Kimi Coding, including 1M context/output, multimodal capabilities, and low/high/max reasoning-effort normalization (#18038) — thanks @ysntony
- feat(dashboard): the home page gets two cards with host and OmniRoute process CPU and memory, served by the new management-tier
GET /api/system/metrics; the cards poll every 3.5 s and pause while the tab is hidden (#18393) — thanks @rafacpti23 - feat(sse): A combo can pin an OpenAI tier with
config.service_tier(orserviceTier). It reachesopenai,azure-openaiandcodextargets on every attempt, replacing the client's tier there, and other targets get the request as the client sent it. API writes reject values outsideauto,default,flex,priorityandscale. (#18553) — thanks @dankarization - feat(docs): npm and Docker installs now serve the translated
/docspages. The npm package (underdist/docs/i18n/) and the Docker image ship the 8,885 page mirrors the docs route can read, without the README/CHANGELOG/agent-guide mirrors or the operator-internal security pages, andjsdom, which renders them, is now a runtime dependency. The npm tarball grows from about 112 MB to 191 MB (#18869) - feat(dashboard): the CI UI Kit's Editions palette (warm neutrals, copper accent) is now the default look in light and dark, across the dashboard, login,
/status, error pages,/docsand the PWA; Settings → Appearance → Color palette keeps the previous lime look as Classic, and the README diagrams use the Editions palette (#18901) - feat(ci): choose the docker-publish amd64 runner with DOCKER_AMD64_RUNNER (#18858)
- feat(ci): run docker-publish's prepare and merge jobs on Blacksmith too (#18882)
- feat(ci): fall back to hosted when the Blacksmith monthly minutes run out (#18893)
🐛 Bug Fixes and 📝 Maintenance
587 fixes and 457 maintenance entries. The full list is in the attached CHANGELOG-v3.8.53.md.
🙌 Contributors
Thanks to everyone whose work landed in v3.8.53: