Skip to content

fix(api-manager): preserve API key expiration local time - #3146

Merged
diegosouzapw merged 3 commits into
diegosouzapw:release/v3.8.10from
xz-dev:fix-api-key-expiration-local-time
Jun 4, 2026
Merged

diegosouzapw merged 3 commits into
diegosouzapw:release/v3.8.10from
xz-dev:fix-api-key-expiration-local-time

Conversation

@xz-dev

@xz-dev xz-dev commented Jun 4, 2026 •

Copy link
Copy Markdown
Contributor

Summary

  • Render API key expiration ISO timestamps as local datetime-local values instead of slicing UTC text.
  • Keep saving valid local datetime-local input values as UTC ISO timestamps.
  • Add a Clear button so users can remove an API key expiration date.
  • Harden two flaky CI test paths exposed by the PR run:
    • make console-log tmpdir cleanup best-effort,
    • remove unnecessary SQLite access from pure batch-expiration arithmetic tests.

Related Issues

  • Related to user-reported API key expiration calendar timezone drift.

Validation

  • npm run lint
  • npm run test:unit
  • npm run test:coverage
  • Coverage is still >= 60% for statements, lines, functions, and branches
  • SonarQube PR analysis is green or any remaining issues are explicitly documented below

Additional validation run in this checkout:

  • node --test tests/unit/api-manager-page-static.test.ts
  • node --test tests/unit/api-manager-page-static.test.ts tests/unit/batch-processor-expiration.test.ts
  • git diff --check

Full project commands requiring tsx/installed dependencies were not run locally because this checkout does not have node_modules installed. The PR CI run is used for full dependency-backed validation.

Tests Added Or Updated

  • Updated tests/unit/api-manager-page-static.test.ts to cover API key expiration input rendering and prevent the expiresAt.slice(0, 16) regression.
  • Updated tests/unit/batch-processor-expiration.test.ts to keep its pure arithmetic tests from touching shared SQLite state.
  • Updated tests/unit/console-log-levels.test.ts so temporary directory cleanup cannot fail otherwise-passing tests on Node 24.

Coverage Notes

  • This PR changes src/app/(dashboard)/dashboard/api-manager/ApiManagerPageClient.tsx.
  • Coverage comes from the existing static API manager page test, updated to assert:
    • expiration values use local datetime-local formatting,
    • save path still writes ISO strings for valid input,
    • Clear button resets expiration state,
    • UTC string slicing is not reintroduced.
  • The CI hardening changes are test-only and should not reduce production coverage.

Reviewer Notes

  • Root cause: <input type="datetime-local"> has no timezone, but the old UI used expiresAt.slice(0, 16) on UTC ISO strings. That displayed UTC wall-clock fields as local fields, causing a shift after saving.
  • Expiration enforcement already uses absolute epoch milliseconds (new Date(expiresAt).getTime() vs Date.now()), so the product fix is UI formatting only.
  • No database migrations or feature flags.

@xz-dev
xz-dev requested a review from diegosouzapw as a code owner June 4, 2026 13:12

@gemini-code-assist gemini-code-assist Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request introduces a helper function toLocalDateTimeInputValue to properly format API key expiration dates for the datetime-local input, adds a "clear" button to reset the expiration date, and includes corresponding unit tests. The reviewer suggests wrapping the new Date(val).toISOString() call in a try-catch block to prevent potential UI crashes caused by RangeError exceptions when users enter invalid or incomplete dates.

Important

The consumer version of Gemini Code Assist on GitHub is being sunset. Starting June 18, 2026, new organization installations will be blocked, and all code review activity will officially cease on July 17, 2026.
For more details on the timeline and next steps, please review the Help Documentation.

Comment thread src/app/(dashboard)/dashboard/api-manager/ApiManagerPageClient.tsx
xz-dev and others added 2 commits June 4, 2026 21:17
Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com>
@diegosouzapw
diegosouzapw changed the base branch from main to release/v3.8.10 June 4, 2026 17:09
@diegosouzapw

Copy link
Copy Markdown
Owner

Thanks @xz-dev! Preserving the API key expiration in local time (instead of letting the datetime-local input silently shift to UTC) is a real UX bug fix, and the clear button is a nice touch. Merging into release/v3.8.10. 🙏

@diegosouzapw
diegosouzapw merged commit 3fd8f2c into diegosouzapw:release/v3.8.10 Jun 4, 2026
84 checks passed
@diegosouzapw diegosouzapw mentioned this pull request Jun 4, 2026
diegosouzapw added a commit that referenced this pull request Jun 4, 2026
* chore(release): open v3.8.10 development cycle

Bump 3.8.9 → 3.8.10 across package.json, lockfile, electron, open-sse, and
docs/reference/openapi.yaml; add the [3.8.10] CHANGELOG section (root + 41 i18n
mirrors) as the integration target for the cycle. Entries land here as work
merges into release/v3.8.10; finalized by the release flow.

* fix(providers): resolve web provider alias collisions

Assign unique aliases to HuggingChat, Kimi Web, and Qwen Web so they no longer shadow primary providers or trigger startup warnings.

Add a unit test to enforce provider alias uniqueness and prevent future collisions. Also expand local ignore and VS Code exclude rules for agent, build, and worktree artifacts.

* fix(responses): normalize image_url parts across input paths (#3150)

Normalize image_url parts across all Responses input paths. Integrated into release/v3.8.10.

* fix(api-manager): preserve API key expiration local time (#3146)

Preserve API key expiration local time + clear button. Integrated into release/v3.8.10.

* Strip previous_response_id for stateless Responses upstreams (#3143)

Strip previous_response_id for stateless Responses upstreams (auto/strip/preserve). Integrated into release/v3.8.10.

* fix(opencode-plugin): map thinking cap to interleaved in model+combo (#3138)

Map caps.thinking to ModelV2.capabilities.interleaved for opencode-plugin. Integrated into release/v3.8.10.

* fix(providers): use synced models as fallback for all providers (#3148)

Use synced models as authoritative local catalog for all providers (+regression test). Integrated into release/v3.8.10.

* fix(qoder): bifurcate validation by token type — PAT→Cosy, regular API key→dashscope (#3149)

Bifurcate Qoder validation by token type (PAT→Cosy, regular→dashscope) +regression test. Integrated into release/v3.8.10.

* fix(antigravity): dynamic model resolution via MITM alias table (#3144)

Dynamic antigravity MITM model resolution in the executor (+bug fix +regression test; DB import dropped from client-reachable config). Integrated into release/v3.8.10.

* Feature/batch allow big (#3128)

Podman deployment options + larger upload body-size limits (+CONTAINER_HOST docs). Integrated into release/v3.8.10.

* fix(fireworks): preserve fully-qualified router/model IDs (#3133) (#3160)

Fireworks router IDs (accounts/fireworks/routers/...) were double-prefixed
with accounts/fireworks/models/ → upstream 404. Add optional
acceptedModelIdPrefixes to the registry entry and skip the prepend when the
model already starts with an accepted prefix.

Co-authored-by: KooshaPari <KooshaPari@users.noreply.github.com>

* fix(llama-cpp): route to configured local baseUrl instead of OpenAI (#3136) (#3161)

llama-cpp was missing from the local-provider group in buildUrl(), so it
fell through to the OpenAI baseUrl and returned an OpenAI 401. Add the
case to resolve the connection's providerSpecificData.baseUrl.

Co-authored-by: tjengbudi <tjengbudi@users.noreply.github.com>

* fix(t3-chat-web): parse cookies + convexSessionId from stored credential (#3007) (#3162)

The executor read credentials.cookies/convexSessionId, but the pipeline
only stores the pasted string under apiKey → t3.chat always 400'd. Parse
both values from apiKey (fallback accessToken), mirroring validation.ts.

Co-authored-by: minhtran162 <minhtran162@users.noreply.github.com>

* fix(minimax): stop capping MiniMax-M3 / M2.7 max_tokens at 8192 (#3141) (#3163)

MiniMax-M3 had no MODEL_SPECS entry and capitalized MiniMax-M2.7 missed
its lowercase spec (case-sensitive lookup) → both fell to the 8192 default
cap. Add the M3 spec (512K output), alias the capitalized ids, and make
getModelSpec lookups case-insensitive.

Co-authored-by: totaltube <totaltube@users.noreply.github.com>

* fix(github-copilot): discover model catalog live from api.githubcopilot.com (#3120, #3121) (#3164)

The github (Copilot) provider had a static hardcoded catalog with no
discovery source, so Import Models never refreshed (#3120) and advertised
non-entitled models that 400 on use (#3121). Add a live /models fetch with
fallback to the static list.

Co-authored-by: gabrielmoreira <gabrielmoreira@users.noreply.github.com>

* fix(combo): invalidate nested-combo cache on edits + log DATA_DIR (#3147) (#3165)

Editing a combo did not invalidate the 10s nested-combo expansion caches
(chat.ts getCombosCachedForChat + chatCore.ts getCombosCached; the exported
clearCombosCache was dead code), so a removed nested target/model could be
served as a phantom for up to 10s. Wire a shared monotonic combos-cache
version in readCache (bumped by invalidateDbCache("combos") on every combo
write); both cache layers treat a version mismatch as a miss.

Also log the resolved DATA_DIR/SQLITE_FILE absolute path at DB init so the
reporter's 'persists across restart + volume wipe' symptom (a multi-replica
Docker volume/DATA_DIR mismatch, not a routing bug) is diagnosable from logs.

Includes consolidated CHANGELOG entries for #3133/#3136/#3007/#3141/#3120/#3121.

Co-authored-by: ViFigueiredo <ViFigueiredo@users.noreply.github.com>

* fix(web-tools): parse bare JSON tool calls (#3157)

Parse bare JSON tool calls for deepseek-web (#2820) + fuzzy tool-name matching. Integrated into release/v3.8.10.

* fix(misc): minor fixes across reasoning cache, account fallback, binary manager (#3177)

Misc: ProviderProfile export, DeepSeek reasoning regex, binary guard. Integrated into release/v3.8.10.

* fix(kiro): minor OAuth social exchange tweaks (#3176)

Kiro social OAuth: optional targetProvider passthrough. Integrated into release/v3.8.10.

* deps: bump hono from 4.12.18 to 4.12.23 (#3179)

Bump hono to 4.12.23. Integrated into release/v3.8.10.

* fix(providerRegistry): update kilocode format and executor (#3166)

kilocode: openai format + default executor (matches kilo-gateway) + registry test. Integrated into release/v3.8.10.

* feat(metrics): cross-request TTFT and gap latency after tool calls (#3173)

Cross-request TTFT + gap-after-tool latency metrics (+test). Integrated into release/v3.8.10.

* feat(dashboard): provider stats API endpoint and dashboard page (#3175)

Provider stats dashboard + API (SQL moved to db module per Hard Rule #5, +test). Integrated into release/v3.8.10.

* fix(usage): sequential+spaced OAuth quota sync, reactive force-refresh, actionable 401 (#3156)

Sequential+spaced OAuth quota sync, reactive force-refresh on 401, actionable 401 in UI. Integrated into release/v3.8.10.

* fix(healthcheck): per-provider proactive-refresh skip list (rescue short-TTL OAuth) (#3159)

Per-provider proactive-refresh skip list (OMNIROUTE_HEALTHCHECK_SKIP_PROVIDERS) to rescue short-TTL OAuth. Integrated into release/v3.8.10.

* feat(quota): show OAuth token expiry on provider cards (small, blue, informative) (#3178)

Show OAuth token expiry on provider cards (small, blue, informative). Integrated into release/v3.8.10.

* fix(providers): empty refresh must not resurface just-cleared synced models (#3181)

Empty refresh must not resurface just-cleared synced models (fixes the release-blocking provider-models-route test). Integrated into release/v3.8.10.

* chore(release): v3.8.10 — 2026-06-04 (finalize CHANGELOG)

---------

Co-authored-by: Wilson <pedbookmed@gmail.com>
Co-authored-by: Xiangzhe <32761048+xz-dev@users.noreply.github.com>
Co-authored-by: Jan Leon <Jan.gaschler@gmail.com>
Co-authored-by: M.M <mr.maatoug@gmail.com>
Co-authored-by: Hernan Javier Ardila Sanchez <hjasgr@gmail.com>
Co-authored-by: Markus Hartung <mail@hartmark.se>
Co-authored-by: KooshaPari <KooshaPari@users.noreply.github.com>
Co-authored-by: tjengbudi <tjengbudi@users.noreply.github.com>
Co-authored-by: minhtran162 <minhtran162@users.noreply.github.com>
Co-authored-by: totaltube <totaltube@users.noreply.github.com>
Co-authored-by: gabrielmoreira <gabrielmoreira@users.noreply.github.com>
Co-authored-by: ViFigueiredo <ViFigueiredo@users.noreply.github.com>
Co-authored-by: PizzaV <103120356+pizzav-xyz@users.noreply.github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Nicolas Lorin <androw95220@gmail.com>
HouMinXi pushed a commit to HouMinXi/OmniRoute that referenced this pull request Aug 2, 2026
* chore(release): open v3.8.10 development cycle

Bump 3.8.9 → 3.8.10 across package.json, lockfile, electron, open-sse, and
docs/reference/openapi.yaml; add the [3.8.10] CHANGELOG section (root + 41 i18n
mirrors) as the integration target for the cycle. Entries land here as work
merges into release/v3.8.10; finalized by the release flow.

* fix(providers): resolve web provider alias collisions

Assign unique aliases to HuggingChat, Kimi Web, and Qwen Web so they no longer shadow primary providers or trigger startup warnings.

Add a unit test to enforce provider alias uniqueness and prevent future collisions. Also expand local ignore and VS Code exclude rules for agent, build, and worktree artifacts.

* fix(responses): normalize image_url parts across input paths (diegosouzapw#3150)

Normalize image_url parts across all Responses input paths. Integrated into release/v3.8.10.

* fix(api-manager): preserve API key expiration local time (diegosouzapw#3146)

Preserve API key expiration local time + clear button. Integrated into release/v3.8.10.

* Strip previous_response_id for stateless Responses upstreams (diegosouzapw#3143)

Strip previous_response_id for stateless Responses upstreams (auto/strip/preserve). Integrated into release/v3.8.10.

* fix(opencode-plugin): map thinking cap to interleaved in model+combo (diegosouzapw#3138)

Map caps.thinking to ModelV2.capabilities.interleaved for opencode-plugin. Integrated into release/v3.8.10.

* fix(providers): use synced models as fallback for all providers (diegosouzapw#3148)

Use synced models as authoritative local catalog for all providers (+regression test). Integrated into release/v3.8.10.

* fix(qoder): bifurcate validation by token type — PAT→Cosy, regular API key→dashscope (diegosouzapw#3149)

Bifurcate Qoder validation by token type (PAT→Cosy, regular→dashscope) +regression test. Integrated into release/v3.8.10.

* fix(antigravity): dynamic model resolution via MITM alias table (diegosouzapw#3144)

Dynamic antigravity MITM model resolution in the executor (+bug fix +regression test; DB import dropped from client-reachable config). Integrated into release/v3.8.10.

* Feature/batch allow big (diegosouzapw#3128)

Podman deployment options + larger upload body-size limits (+CONTAINER_HOST docs). Integrated into release/v3.8.10.

* fix(fireworks): preserve fully-qualified router/model IDs (diegosouzapw#3133) (diegosouzapw#3160)

Fireworks router IDs (accounts/fireworks/routers/...) were double-prefixed
with accounts/fireworks/models/ → upstream 404. Add optional
acceptedModelIdPrefixes to the registry entry and skip the prepend when the
model already starts with an accepted prefix.

Co-authored-by: KooshaPari <KooshaPari@users.noreply.github.com>

* fix(llama-cpp): route to configured local baseUrl instead of OpenAI (diegosouzapw#3136) (diegosouzapw#3161)

llama-cpp was missing from the local-provider group in buildUrl(), so it
fell through to the OpenAI baseUrl and returned an OpenAI 401. Add the
case to resolve the connection's providerSpecificData.baseUrl.

Co-authored-by: tjengbudi <tjengbudi@users.noreply.github.com>

* fix(t3-chat-web): parse cookies + convexSessionId from stored credential (diegosouzapw#3007) (diegosouzapw#3162)

The executor read credentials.cookies/convexSessionId, but the pipeline
only stores the pasted string under apiKey → t3.chat always 400'd. Parse
both values from apiKey (fallback accessToken), mirroring validation.ts.

Co-authored-by: minhtran162 <minhtran162@users.noreply.github.com>

* fix(minimax): stop capping MiniMax-M3 / M2.7 max_tokens at 8192 (diegosouzapw#3141) (diegosouzapw#3163)

MiniMax-M3 had no MODEL_SPECS entry and capitalized MiniMax-M2.7 missed
its lowercase spec (case-sensitive lookup) → both fell to the 8192 default
cap. Add the M3 spec (512K output), alias the capitalized ids, and make
getModelSpec lookups case-insensitive.

Co-authored-by: totaltube <totaltube@users.noreply.github.com>

* fix(github-copilot): discover model catalog live from api.githubcopilot.com (diegosouzapw#3120, diegosouzapw#3121) (diegosouzapw#3164)

The github (Copilot) provider had a static hardcoded catalog with no
discovery source, so Import Models never refreshed (diegosouzapw#3120) and advertised
non-entitled models that 400 on use (diegosouzapw#3121). Add a live /models fetch with
fallback to the static list.

Co-authored-by: gabrielmoreira <gabrielmoreira@users.noreply.github.com>

* fix(combo): invalidate nested-combo cache on edits + log DATA_DIR (diegosouzapw#3147) (diegosouzapw#3165)

Editing a combo did not invalidate the 10s nested-combo expansion caches
(chat.ts getCombosCachedForChat + chatCore.ts getCombosCached; the exported
clearCombosCache was dead code), so a removed nested target/model could be
served as a phantom for up to 10s. Wire a shared monotonic combos-cache
version in readCache (bumped by invalidateDbCache("combos") on every combo
write); both cache layers treat a version mismatch as a miss.

Also log the resolved DATA_DIR/SQLITE_FILE absolute path at DB init so the
reporter's 'persists across restart + volume wipe' symptom (a multi-replica
Docker volume/DATA_DIR mismatch, not a routing bug) is diagnosable from logs.

Includes consolidated CHANGELOG entries for diegosouzapw#3133/diegosouzapw#3136/diegosouzapw#3007/diegosouzapw#3141/diegosouzapw#3120/diegosouzapw#3121.

Co-authored-by: ViFigueiredo <ViFigueiredo@users.noreply.github.com>

* fix(web-tools): parse bare JSON tool calls (diegosouzapw#3157)

Parse bare JSON tool calls for deepseek-web (diegosouzapw#2820) + fuzzy tool-name matching. Integrated into release/v3.8.10.

* fix(misc): minor fixes across reasoning cache, account fallback, binary manager (diegosouzapw#3177)

Misc: ProviderProfile export, DeepSeek reasoning regex, binary guard. Integrated into release/v3.8.10.

* fix(kiro): minor OAuth social exchange tweaks (diegosouzapw#3176)

Kiro social OAuth: optional targetProvider passthrough. Integrated into release/v3.8.10.

* deps: bump hono from 4.12.18 to 4.12.23 (diegosouzapw#3179)

Bump hono to 4.12.23. Integrated into release/v3.8.10.

* fix(providerRegistry): update kilocode format and executor (diegosouzapw#3166)

kilocode: openai format + default executor (matches kilo-gateway) + registry test. Integrated into release/v3.8.10.

* feat(metrics): cross-request TTFT and gap latency after tool calls (diegosouzapw#3173)

Cross-request TTFT + gap-after-tool latency metrics (+test). Integrated into release/v3.8.10.

* feat(dashboard): provider stats API endpoint and dashboard page (diegosouzapw#3175)

Provider stats dashboard + API (SQL moved to db module per Hard Rule diegosouzapw#5, +test). Integrated into release/v3.8.10.

* fix(usage): sequential+spaced OAuth quota sync, reactive force-refresh, actionable 401 (diegosouzapw#3156)

Sequential+spaced OAuth quota sync, reactive force-refresh on 401, actionable 401 in UI. Integrated into release/v3.8.10.

* fix(healthcheck): per-provider proactive-refresh skip list (rescue short-TTL OAuth) (diegosouzapw#3159)

Per-provider proactive-refresh skip list (OMNIROUTE_HEALTHCHECK_SKIP_PROVIDERS) to rescue short-TTL OAuth. Integrated into release/v3.8.10.

* feat(quota): show OAuth token expiry on provider cards (small, blue, informative) (diegosouzapw#3178)

Show OAuth token expiry on provider cards (small, blue, informative). Integrated into release/v3.8.10.

* fix(providers): empty refresh must not resurface just-cleared synced models (diegosouzapw#3181)

Empty refresh must not resurface just-cleared synced models (fixes the release-blocking provider-models-route test). Integrated into release/v3.8.10.

* chore(release): v3.8.10 — 2026-06-04 (finalize CHANGELOG)

---------

Co-authored-by: Wilson <pedbookmed@gmail.com>
Co-authored-by: Xiangzhe <32761048+xz-dev@users.noreply.github.com>
Co-authored-by: Jan Leon <Jan.gaschler@gmail.com>
Co-authored-by: M.M <mr.maatoug@gmail.com>
Co-authored-by: Hernan Javier Ardila Sanchez <hjasgr@gmail.com>
Co-authored-by: Markus Hartung <mail@hartmark.se>
Co-authored-by: KooshaPari <KooshaPari@users.noreply.github.com>
Co-authored-by: tjengbudi <tjengbudi@users.noreply.github.com>
Co-authored-by: minhtran162 <minhtran162@users.noreply.github.com>
Co-authored-by: totaltube <totaltube@users.noreply.github.com>
Co-authored-by: gabrielmoreira <gabrielmoreira@users.noreply.github.com>
Co-authored-by: ViFigueiredo <ViFigueiredo@users.noreply.github.com>
Co-authored-by: PizzaV <103120356+pizzav-xyz@users.noreply.github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Nicolas Lorin <androw95220@gmail.com>
Poid-ZA pushed a commit to Poid-ZA/OmniRoute that referenced this pull request Aug 5, 2026
* chore(release): open v3.8.10 development cycle

Bump 3.8.9 → 3.8.10 across package.json, lockfile, electron, open-sse, and
docs/reference/openapi.yaml; add the [3.8.10] CHANGELOG section (root + 41 i18n
mirrors) as the integration target for the cycle. Entries land here as work
merges into release/v3.8.10; finalized by the release flow.

* fix(providers): resolve web provider alias collisions

Assign unique aliases to HuggingChat, Kimi Web, and Qwen Web so they no longer shadow primary providers or trigger startup warnings.

Add a unit test to enforce provider alias uniqueness and prevent future collisions. Also expand local ignore and VS Code exclude rules for agent, build, and worktree artifacts.

* fix(responses): normalize image_url parts across input paths (diegosouzapw#3150)

Normalize image_url parts across all Responses input paths. Integrated into release/v3.8.10.

* fix(api-manager): preserve API key expiration local time (diegosouzapw#3146)

Preserve API key expiration local time + clear button. Integrated into release/v3.8.10.

* Strip previous_response_id for stateless Responses upstreams (diegosouzapw#3143)

Strip previous_response_id for stateless Responses upstreams (auto/strip/preserve). Integrated into release/v3.8.10.

* fix(opencode-plugin): map thinking cap to interleaved in model+combo (diegosouzapw#3138)

Map caps.thinking to ModelV2.capabilities.interleaved for opencode-plugin. Integrated into release/v3.8.10.

* fix(providers): use synced models as fallback for all providers (diegosouzapw#3148)

Use synced models as authoritative local catalog for all providers (+regression test). Integrated into release/v3.8.10.

* fix(qoder): bifurcate validation by token type — PAT→Cosy, regular API key→dashscope (diegosouzapw#3149)

Bifurcate Qoder validation by token type (PAT→Cosy, regular→dashscope) +regression test. Integrated into release/v3.8.10.

* fix(antigravity): dynamic model resolution via MITM alias table (diegosouzapw#3144)

Dynamic antigravity MITM model resolution in the executor (+bug fix +regression test; DB import dropped from client-reachable config). Integrated into release/v3.8.10.

* Feature/batch allow big (diegosouzapw#3128)

Podman deployment options + larger upload body-size limits (+CONTAINER_HOST docs). Integrated into release/v3.8.10.

* fix(fireworks): preserve fully-qualified router/model IDs (diegosouzapw#3133) (diegosouzapw#3160)

Fireworks router IDs (accounts/fireworks/routers/...) were double-prefixed
with accounts/fireworks/models/ → upstream 404. Add optional
acceptedModelIdPrefixes to the registry entry and skip the prepend when the
model already starts with an accepted prefix.

Co-authored-by: KooshaPari <KooshaPari@users.noreply.github.com>

* fix(llama-cpp): route to configured local baseUrl instead of OpenAI (diegosouzapw#3136) (diegosouzapw#3161)

llama-cpp was missing from the local-provider group in buildUrl(), so it
fell through to the OpenAI baseUrl and returned an OpenAI 401. Add the
case to resolve the connection's providerSpecificData.baseUrl.

Co-authored-by: tjengbudi <tjengbudi@users.noreply.github.com>

* fix(t3-chat-web): parse cookies + convexSessionId from stored credential (diegosouzapw#3007) (diegosouzapw#3162)

The executor read credentials.cookies/convexSessionId, but the pipeline
only stores the pasted string under apiKey → t3.chat always 400'd. Parse
both values from apiKey (fallback accessToken), mirroring validation.ts.

Co-authored-by: minhtran162 <minhtran162@users.noreply.github.com>

* fix(minimax): stop capping MiniMax-M3 / M2.7 max_tokens at 8192 (diegosouzapw#3141) (diegosouzapw#3163)

MiniMax-M3 had no MODEL_SPECS entry and capitalized MiniMax-M2.7 missed
its lowercase spec (case-sensitive lookup) → both fell to the 8192 default
cap. Add the M3 spec (512K output), alias the capitalized ids, and make
getModelSpec lookups case-insensitive.

Co-authored-by: totaltube <totaltube@users.noreply.github.com>

* fix(github-copilot): discover model catalog live from api.githubcopilot.com (diegosouzapw#3120, diegosouzapw#3121) (diegosouzapw#3164)

The github (Copilot) provider had a static hardcoded catalog with no
discovery source, so Import Models never refreshed (diegosouzapw#3120) and advertised
non-entitled models that 400 on use (diegosouzapw#3121). Add a live /models fetch with
fallback to the static list.

Co-authored-by: gabrielmoreira <gabrielmoreira@users.noreply.github.com>

* fix(combo): invalidate nested-combo cache on edits + log DATA_DIR (diegosouzapw#3147) (diegosouzapw#3165)

Editing a combo did not invalidate the 10s nested-combo expansion caches
(chat.ts getCombosCachedForChat + chatCore.ts getCombosCached; the exported
clearCombosCache was dead code), so a removed nested target/model could be
served as a phantom for up to 10s. Wire a shared monotonic combos-cache
version in readCache (bumped by invalidateDbCache("combos") on every combo
write); both cache layers treat a version mismatch as a miss.

Also log the resolved DATA_DIR/SQLITE_FILE absolute path at DB init so the
reporter's 'persists across restart + volume wipe' symptom (a multi-replica
Docker volume/DATA_DIR mismatch, not a routing bug) is diagnosable from logs.

Includes consolidated CHANGELOG entries for diegosouzapw#3133/diegosouzapw#3136/diegosouzapw#3007/diegosouzapw#3141/diegosouzapw#3120/diegosouzapw#3121.

Co-authored-by: ViFigueiredo <ViFigueiredo@users.noreply.github.com>

* fix(web-tools): parse bare JSON tool calls (diegosouzapw#3157)

Parse bare JSON tool calls for deepseek-web (diegosouzapw#2820) + fuzzy tool-name matching. Integrated into release/v3.8.10.

* fix(misc): minor fixes across reasoning cache, account fallback, binary manager (diegosouzapw#3177)

Misc: ProviderProfile export, DeepSeek reasoning regex, binary guard. Integrated into release/v3.8.10.

* fix(kiro): minor OAuth social exchange tweaks (diegosouzapw#3176)

Kiro social OAuth: optional targetProvider passthrough. Integrated into release/v3.8.10.

* deps: bump hono from 4.12.18 to 4.12.23 (diegosouzapw#3179)

Bump hono to 4.12.23. Integrated into release/v3.8.10.

* fix(providerRegistry): update kilocode format and executor (diegosouzapw#3166)

kilocode: openai format + default executor (matches kilo-gateway) + registry test. Integrated into release/v3.8.10.

* feat(metrics): cross-request TTFT and gap latency after tool calls (diegosouzapw#3173)

Cross-request TTFT + gap-after-tool latency metrics (+test). Integrated into release/v3.8.10.

* feat(dashboard): provider stats API endpoint and dashboard page (diegosouzapw#3175)

Provider stats dashboard + API (SQL moved to db module per Hard Rule diegosouzapw#5, +test). Integrated into release/v3.8.10.

* fix(usage): sequential+spaced OAuth quota sync, reactive force-refresh, actionable 401 (diegosouzapw#3156)

Sequential+spaced OAuth quota sync, reactive force-refresh on 401, actionable 401 in UI. Integrated into release/v3.8.10.

* fix(healthcheck): per-provider proactive-refresh skip list (rescue short-TTL OAuth) (diegosouzapw#3159)

Per-provider proactive-refresh skip list (OMNIROUTE_HEALTHCHECK_SKIP_PROVIDERS) to rescue short-TTL OAuth. Integrated into release/v3.8.10.

* feat(quota): show OAuth token expiry on provider cards (small, blue, informative) (diegosouzapw#3178)

Show OAuth token expiry on provider cards (small, blue, informative). Integrated into release/v3.8.10.

* fix(providers): empty refresh must not resurface just-cleared synced models (diegosouzapw#3181)

Empty refresh must not resurface just-cleared synced models (fixes the release-blocking provider-models-route test). Integrated into release/v3.8.10.

* chore(release): v3.8.10 — 2026-06-04 (finalize CHANGELOG)

---------

Co-authored-by: Wilson <pedbookmed@gmail.com>
Co-authored-by: Xiangzhe <32761048+xz-dev@users.noreply.github.com>
Co-authored-by: Jan Leon <Jan.gaschler@gmail.com>
Co-authored-by: M.M <mr.maatoug@gmail.com>
Co-authored-by: Hernan Javier Ardila Sanchez <hjasgr@gmail.com>
Co-authored-by: Markus Hartung <mail@hartmark.se>
Co-authored-by: KooshaPari <KooshaPari@users.noreply.github.com>
Co-authored-by: tjengbudi <tjengbudi@users.noreply.github.com>
Co-authored-by: minhtran162 <minhtran162@users.noreply.github.com>
Co-authored-by: totaltube <totaltube@users.noreply.github.com>
Co-authored-by: gabrielmoreira <gabrielmoreira@users.noreply.github.com>
Co-authored-by: ViFigueiredo <ViFigueiredo@users.noreply.github.com>
Co-authored-by: PizzaV <103120356+pizzav-xyz@users.noreply.github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Nicolas Lorin <androw95220@gmail.com>
tkgo11 pushed a commit to tkgo11/OmniRoute that referenced this pull request Sep 23, 2026
…w#3146)

Preserve API key expiration local time + clear button. Integrated into release/v3.8.10.
muhamadgalihsaputra pushed a commit to niyatna/NiyatnaRoute that referenced this pull request Sep 27, 2026
* chore(release): open v3.8.10 development cycle

Bump 3.8.9 → 3.8.10 across package.json, lockfile, electron, open-sse, and
docs/reference/openapi.yaml; add the [3.8.10] CHANGELOG section (root + 41 i18n
mirrors) as the integration target for the cycle. Entries land here as work
merges into release/v3.8.10; finalized by the release flow.

* fix(providers): resolve web provider alias collisions

Assign unique aliases to HuggingChat, Kimi Web, and Qwen Web so they no longer shadow primary providers or trigger startup warnings.

Add a unit test to enforce provider alias uniqueness and prevent future collisions. Also expand local ignore and VS Code exclude rules for agent, build, and worktree artifacts.

* fix(responses): normalize image_url parts across input paths (diegosouzapw#3150)

Normalize image_url parts across all Responses input paths. Integrated into release/v3.8.10.

* fix(api-manager): preserve API key expiration local time (diegosouzapw#3146)

Preserve API key expiration local time + clear button. Integrated into release/v3.8.10.

* Strip previous_response_id for stateless Responses upstreams (diegosouzapw#3143)

Strip previous_response_id for stateless Responses upstreams (auto/strip/preserve). Integrated into release/v3.8.10.

* fix(opencode-plugin): map thinking cap to interleaved in model+combo (diegosouzapw#3138)

Map caps.thinking to ModelV2.capabilities.interleaved for opencode-plugin. Integrated into release/v3.8.10.

* fix(providers): use synced models as fallback for all providers (diegosouzapw#3148)

Use synced models as authoritative local catalog for all providers (+regression test). Integrated into release/v3.8.10.

* fix(qoder): bifurcate validation by token type — PAT→Cosy, regular API key→dashscope (diegosouzapw#3149)

Bifurcate Qoder validation by token type (PAT→Cosy, regular→dashscope) +regression test. Integrated into release/v3.8.10.

* fix(antigravity): dynamic model resolution via MITM alias table (diegosouzapw#3144)

Dynamic antigravity MITM model resolution in the executor (+bug fix +regression test; DB import dropped from client-reachable config). Integrated into release/v3.8.10.

* Feature/batch allow big (diegosouzapw#3128)

Podman deployment options + larger upload body-size limits (+CONTAINER_HOST docs). Integrated into release/v3.8.10.

* fix(fireworks): preserve fully-qualified router/model IDs (diegosouzapw#3133) (diegosouzapw#3160)

Fireworks router IDs (accounts/fireworks/routers/...) were double-prefixed
with accounts/fireworks/models/ → upstream 404. Add optional
acceptedModelIdPrefixes to the registry entry and skip the prepend when the
model already starts with an accepted prefix.

Co-authored-by: KooshaPari <KooshaPari@users.noreply.github.com>

* fix(llama-cpp): route to configured local baseUrl instead of OpenAI (diegosouzapw#3136) (diegosouzapw#3161)

llama-cpp was missing from the local-provider group in buildUrl(), so it
fell through to the OpenAI baseUrl and returned an OpenAI 401. Add the
case to resolve the connection's providerSpecificData.baseUrl.

Co-authored-by: tjengbudi <tjengbudi@users.noreply.github.com>

* fix(t3-chat-web): parse cookies + convexSessionId from stored credential (diegosouzapw#3007) (diegosouzapw#3162)

The executor read credentials.cookies/convexSessionId, but the pipeline
only stores the pasted string under apiKey → t3.chat always 400'd. Parse
both values from apiKey (fallback accessToken), mirroring validation.ts.

Co-authored-by: minhtran162 <minhtran162@users.noreply.github.com>

* fix(minimax): stop capping MiniMax-M3 / M2.7 max_tokens at 8192 (diegosouzapw#3141) (diegosouzapw#3163)

MiniMax-M3 had no MODEL_SPECS entry and capitalized MiniMax-M2.7 missed
its lowercase spec (case-sensitive lookup) → both fell to the 8192 default
cap. Add the M3 spec (512K output), alias the capitalized ids, and make
getModelSpec lookups case-insensitive.

Co-authored-by: totaltube <totaltube@users.noreply.github.com>

* fix(github-copilot): discover model catalog live from api.githubcopilot.com (diegosouzapw#3120, diegosouzapw#3121) (diegosouzapw#3164)

The github (Copilot) provider had a static hardcoded catalog with no
discovery source, so Import Models never refreshed (diegosouzapw#3120) and advertised
non-entitled models that 400 on use (diegosouzapw#3121). Add a live /models fetch with
fallback to the static list.

Co-authored-by: gabrielmoreira <gabrielmoreira@users.noreply.github.com>

* fix(combo): invalidate nested-combo cache on edits + log DATA_DIR (diegosouzapw#3147) (diegosouzapw#3165)

Editing a combo did not invalidate the 10s nested-combo expansion caches
(chat.ts getCombosCachedForChat + chatCore.ts getCombosCached; the exported
clearCombosCache was dead code), so a removed nested target/model could be
served as a phantom for up to 10s. Wire a shared monotonic combos-cache
version in readCache (bumped by invalidateDbCache("combos") on every combo
write); both cache layers treat a version mismatch as a miss.

Also log the resolved DATA_DIR/SQLITE_FILE absolute path at DB init so the
reporter's 'persists across restart + volume wipe' symptom (a multi-replica
Docker volume/DATA_DIR mismatch, not a routing bug) is diagnosable from logs.

Includes consolidated CHANGELOG entries for diegosouzapw#3133/diegosouzapw#3136/diegosouzapw#3007/diegosouzapw#3141/diegosouzapw#3120/diegosouzapw#3121.

Co-authored-by: ViFigueiredo <ViFigueiredo@users.noreply.github.com>

* fix(web-tools): parse bare JSON tool calls (diegosouzapw#3157)

Parse bare JSON tool calls for deepseek-web (diegosouzapw#2820) + fuzzy tool-name matching. Integrated into release/v3.8.10.

* fix(misc): minor fixes across reasoning cache, account fallback, binary manager (diegosouzapw#3177)

Misc: ProviderProfile export, DeepSeek reasoning regex, binary guard. Integrated into release/v3.8.10.

* fix(kiro): minor OAuth social exchange tweaks (diegosouzapw#3176)

Kiro social OAuth: optional targetProvider passthrough. Integrated into release/v3.8.10.

* deps: bump hono from 4.12.18 to 4.12.23 (diegosouzapw#3179)

Bump hono to 4.12.23. Integrated into release/v3.8.10.

* fix(providerRegistry): update kilocode format and executor (diegosouzapw#3166)

kilocode: openai format + default executor (matches kilo-gateway) + registry test. Integrated into release/v3.8.10.

* feat(metrics): cross-request TTFT and gap latency after tool calls (diegosouzapw#3173)

Cross-request TTFT + gap-after-tool latency metrics (+test). Integrated into release/v3.8.10.

* feat(dashboard): provider stats API endpoint and dashboard page (diegosouzapw#3175)

Provider stats dashboard + API (SQL moved to db module per Hard Rule diegosouzapw#5, +test). Integrated into release/v3.8.10.

* fix(usage): sequential+spaced OAuth quota sync, reactive force-refresh, actionable 401 (diegosouzapw#3156)

Sequential+spaced OAuth quota sync, reactive force-refresh on 401, actionable 401 in UI. Integrated into release/v3.8.10.

* fix(healthcheck): per-provider proactive-refresh skip list (rescue short-TTL OAuth) (diegosouzapw#3159)

Per-provider proactive-refresh skip list (OMNIROUTE_HEALTHCHECK_SKIP_PROVIDERS) to rescue short-TTL OAuth. Integrated into release/v3.8.10.

* feat(quota): show OAuth token expiry on provider cards (small, blue, informative) (diegosouzapw#3178)

Show OAuth token expiry on provider cards (small, blue, informative). Integrated into release/v3.8.10.

* fix(providers): empty refresh must not resurface just-cleared synced models (diegosouzapw#3181)

Empty refresh must not resurface just-cleared synced models (fixes the release-blocking provider-models-route test). Integrated into release/v3.8.10.

* chore(release): v3.8.10 — 2026-06-04 (finalize CHANGELOG)

---------

Co-authored-by: Wilson <pedbookmed@gmail.com>
Co-authored-by: Xiangzhe <32761048+xz-dev@users.noreply.github.com>
Co-authored-by: Jan Leon <Jan.gaschler@gmail.com>
Co-authored-by: M.M <mr.maatoug@gmail.com>
Co-authored-by: Hernan Javier Ardila Sanchez <hjasgr@gmail.com>
Co-authored-by: Markus Hartung <mail@hartmark.se>
Co-authored-by: KooshaPari <KooshaPari@users.noreply.github.com>
Co-authored-by: tjengbudi <tjengbudi@users.noreply.github.com>
Co-authored-by: minhtran162 <minhtran162@users.noreply.github.com>
Co-authored-by: totaltube <totaltube@users.noreply.github.com>
Co-authored-by: gabrielmoreira <gabrielmoreira@users.noreply.github.com>
Co-authored-by: ViFigueiredo <ViFigueiredo@users.noreply.github.com>
Co-authored-by: PizzaV <103120356+pizzav-xyz@users.noreply.github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Nicolas Lorin <androw95220@gmail.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants