Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
494 commits
Select commit Hold shift + click to select a range
456fbc2
Merge branch 'release/v3.8.53' into fix/embedding-combo-pinned-dimens…
diegosouzapw Nov 3, 2026
d436adb
Merge branch 'release/v3.8.53' into fix-echo-client-requested-model
diegosouzapw Nov 3, 2026
3b1799c
Merge branch 'release/v3.8.53' into fix/call-log-artifact-zombie-cleanup
diegosouzapw Nov 3, 2026
5ab943f
Merge branch 'release/v3.8.53' into fix/18517-cc-alias-provider-key
diegosouzapw Nov 3, 2026
b59b724
Merge branch 'release/v3.8.53' into fix/18541-expiry-first-direct-model
diegosouzapw Nov 3, 2026
25b047c
Merge branch 'release/v3.8.53' into fix/combo-set-retry-cancellation
diegosouzapw Nov 3, 2026
ff2308f
Merge branch 'release/v3.8.53' into fix/require-api-key-consistent-parse
diegosouzapw Nov 3, 2026
f834388
Merge branch 'release/v3.8.53' into fix/combo-service-tier-upstream
diegosouzapw Nov 3, 2026
623a3cb
Merge branch 'release/v3.8.53' into fix/17997-agentrouter-responses
diegosouzapw Nov 3, 2026
b8e16c1
Merge branch 'release/v3.8.53' into fix/codex-paid-credits-last
diegosouzapw Nov 3, 2026
30b1f1e
Merge branch 'release/v3.8.53' into fix/quota-kimi-provider-label
diegosouzapw Nov 3, 2026
a97e77c
Merge branch 'release/v3.8.53' into fix/qoder-per-model-quota-scope
diegosouzapw Nov 3, 2026
2bc954c
Merge branch 'release/v3.8.53' into fix/request-rejected-streak-scope
diegosouzapw Nov 3, 2026
43bae5b
Merge branch 'release/v3.8.53' into fix/windows-autostart-stale-cli-path
diegosouzapw Nov 3, 2026
ddd769a
Merge branch 'release/v3.8.53' into fix/18607-exact-thinking-replay
diegosouzapw Nov 3, 2026
e9b1a54
Merge branch 'release/v3.8.53' into fix/gemini-stream-recovery-termin…
diegosouzapw Nov 3, 2026
417ac3a
Merge branch 'release/v3.8.53' into fix/cursor-sync-locality-public-2…
diegosouzapw Nov 3, 2026
d32fda5
Merge branch 'release/v3.8.53' into fix/antigravity-usage-only-chunk
diegosouzapw Nov 3, 2026
177ab50
Merge branch 'release/v3.8.53' into fix/18598-pricing-bucket
diegosouzapw Nov 3, 2026
0b2d264
Merge branch 'release/v3.8.53' into fix/boundary-engine-usagedb
diegosouzapw Nov 3, 2026
2738d42
Merge branch 'release/v3.8.53' into fix/provider-403-quota-exhausted-…
diegosouzapw Nov 3, 2026
c683d1d
Merge branch 'release/v3.8.53' into fix/antigravity-verify-link-not-s…
diegosouzapw Nov 3, 2026
b2e315d
Merge branch 'release/v3.8.53' into fix/antigravity-route-by-account-…
diegosouzapw Nov 3, 2026
c8c7e0c
Merge branch 'release/v3.8.53' into fix/claude-thinking-duplicate-too…
diegosouzapw Nov 3, 2026
85bdf6c
Merge branch 'release/v3.8.53' into fix/provider-request-capture-error
diegosouzapw Nov 3, 2026
b544fd2
Merge branch 'release/v3.8.53' into fix/responses-gemini-developer
diegosouzapw Nov 3, 2026
83649ae
Merge branch 'release/v3.8.53' into fix/antigravity-preheaders-budget
diegosouzapw Nov 3, 2026
ac274bd
Merge branch 'release/v3.8.53' into fix/displaced-tool-results-3.8.53
diegosouzapw Nov 3, 2026
76d143a
Merge branch 'release/v3.8.53' into fix/vision-bridge-blocked-providers
diegosouzapw Nov 3, 2026
2fe5fc9
Merge branch 'release/v3.8.53' into fix/codex-exhaustion-boundary-202…
diegosouzapw Nov 3, 2026
656f951
Merge branch 'release/v3.8.53' into perf/quota-availability-read-view…
diegosouzapw Nov 3, 2026
b836af5
Merge branch 'release/v3.8.53' into fix/main-cooldown-wait-test
diegosouzapw Nov 3, 2026
18f520a
Merge branch 'release/v3.8.53' into fix/credit-balance-exhausted
diegosouzapw Nov 3, 2026
8e14369
Merge branch 'release/v3.8.53' into fix/turn-guard-self-retry
diegosouzapw Nov 3, 2026
967c5ae
Merge branch 'release/v3.8.53' into fix/18746-codex-claude-effort
diegosouzapw Nov 3, 2026
d06a5ed
Merge branch 'release/v3.8.53' into fix/retry-delay-select-width
diegosouzapw Nov 3, 2026
1b300cc
Merge remote-tracking branch 'origin/release/v3.8.53' into HEAD
diegosouzapw Nov 3, 2026
5cbec92
Merge release/v3.8.53 into fix/port-pr-5037-claude-cache-tail-ttl
diegosouzapw Nov 3, 2026
aebf256
Merge remote-tracking branch 'origin/release/v3.8.53' into HEAD
diegosouzapw Nov 3, 2026
6e15bb7
test(stryker): list hedge-cancel-streaming-leg in tap.testFiles
jjxyxsjr Nov 3, 2026
54199c8
Merge branch 'release/v3.8.53' into fix/codex-quota-signal-normalization
diegosouzapw Nov 3, 2026
9b4461c
Merge branch 'release/v3.8.53' into fix/direct-headers-volume-tier
diegosouzapw Nov 3, 2026
a688ec7
Merge branch 'release/v3.8.53' into fix/18414-docker-node-verification
diegosouzapw Nov 3, 2026
83ccd78
Merge branch 'release/v3.8.53' into fix/windows-regression-portabilit…
diegosouzapw Nov 3, 2026
e83d3e1
Merge remote-tracking branch 'origin/release/v3.8.53' into HEAD
diegosouzapw Nov 3, 2026
b075d03
Merge remote-tracking branch 'upstream/release/v3.8.53' into fix/1841…
HouMinXi Nov 3, 2026
76d8c57
Merge branch 'release/v3.8.53' into fix/18296-claude-model-scoped-429
diegosouzapw Nov 3, 2026
ff46d6b
Merge branch 'release/v3.8.53' into fix/cancel-received-storm
diegosouzapw Nov 3, 2026
c8767bf
Merge branch 'release/v3.8.53' into codex/fix-deepseek-rate-limit-hint
diegosouzapw Nov 3, 2026
cd585d4
Merge branch 'release/v3.8.53' into fix/18718-fix-providers-kiro-tool…
diegosouzapw Nov 3, 2026
57bad9d
Merge branch 'release/v3.8.53' into fix/18679-responses-chat-tool-sch…
diegosouzapw Nov 3, 2026
277b095
Merge branch 'release/v3.8.53' into fix/upstream-cf-health-20261028
diegosouzapw Nov 3, 2026
0cc4240
Merge origin/release/v3.8.53 into fix/18664-model-lockout-not-quota-e…
diegosouzapw Nov 3, 2026
04cbc1b
Merge release/v3.8.53 into fix/18556-mcp-stdio-path-guard
diegosouzapw Nov 3, 2026
4e2b913
fix(discovery): resolve Mistral context window, capabilities, and out…
RayJW Oct 28, 2026
5e648ce
fix(catalog): export tool_calling in synced model capabilities
RayJW Oct 28, 2026
bee8ad3
docs(changelog): add news fragment for Mistral discovery fixes
RayJW Oct 29, 2026
00ea818
fix(providers): keep only Mistral ids and windows its docs confirm
diegosouzapw Nov 2, 2026
a8a0816
fix(providers): leave the Ministral vision verdict to the synced row
diegosouzapw Nov 2, 2026
52919ea
fix(discovery): stop publishing tool_calling from synced rows
diegosouzapw Nov 2, 2026
1174c1b
test(discovery): follow the tip's readable synced-row names in the bo…
RayJW Nov 3, 2026
4016c38
test(mistral): pin the devstral-latest retirement from #18792
RayJW Nov 3, 2026
e66d0cb
Merge remote-tracking branch 'upstream/release/v3.8.53' into fix/mist…
RayJW Nov 3, 2026
c59bb7d
Merge release/v3.8.53 into fix/18632-sanitizer-flag-overrides
Nov 3, 2026
09fd23e
Merge origin/release/v3.8.53 into fix/18664-model-lockout-not-quota-e…
diegosouzapw Nov 3, 2026
394d8d2
Merge origin/release/v3.8.53 into fix/unified-chat-body-limit
diegosouzapw Nov 3, 2026
1a69f54
Merge origin/release/v3.8.53 into fix/unified-chat-body-limit
diegosouzapw Nov 3, 2026
71c1710
Merge origin/release/v3.8.53 into fix/console-retained-history
diegosouzapw Nov 3, 2026
3c4dfb2
Merge remote-tracking branch 'origin/release/v3.8.53' into HEAD
diegosouzapw Nov 3, 2026
9febd22
fix(dashboard): localize the system metrics cards, document the endpo…
rafacpti23 Nov 3, 2026
1913ffd
Merge origin/release/v3.8.53 into work/audit-20261022b
diegosouzapw Nov 3, 2026
f2a5599
Merge origin/release/v3.8.53 into PR #18650
diegosouzapw Nov 3, 2026
1ece018
fix(db): renumber token-ledger index migration 224 to 225 after tip c…
diegosouzapw Nov 3, 2026
299c87d
refactor(dashboard): split the system metrics cards and keep the topo…
rafacpti23 Nov 3, 2026
5ab8292
Merge origin/release/v3.8.53 into PR #18784
diegosouzapw Nov 3, 2026
c56d537
docs(changelog): add the fragment for the system metrics cards
rafacpti23 Nov 3, 2026
b448064
Merge remote-tracking branch 'origin/release/v3.8.53' into HEAD
diegosouzapw Nov 3, 2026
797da63
docs(windows): say what the production launcher actually runs
rafacpti23 Nov 3, 2026
26fccb0
Merge branch 'release/v3.8.53' into fix/18675-kiro-client-tool-named-…
diegosouzapw Nov 3, 2026
0403e5c
refactor(runtime): split the hot-reload start into poll and file-watc…
rafacpti23 Nov 3, 2026
378c304
refactor(translator): split tool-output image collection out of the i…
diegosouzapw Nov 3, 2026
43696dd
Merge origin/release/v3.8.53 into PR #18805
diegosouzapw Nov 3, 2026
8cef486
fix(kiro): ignore history-synthesized tool_call when detecting client…
gaurav0107 Nov 3, 2026
6615281
refactor(dashboard): split console log history and viewer to keep new…
shevar0 Nov 3, 2026
e1b4a8d
test(quality): list the misalignment refusal test in stryker tap.test…
diegosouzapw Nov 3, 2026
71ea1e9
Merge branch 'release/v3.8.53' into fix/browser-version-lookups
diegosouzapw Nov 3, 2026
f977421
Merge branch 'release/v3.8.53' into fix/version-lookup-retry-window
diegosouzapw Nov 3, 2026
b19cbd5
Merge branch 'release/v3.8.53' into fix/opencode-plugin-v2-stale-serv…
diegosouzapw Nov 3, 2026
a06b08f
Merge branch 'release/v3.8.53' into fix/combo-transient-cooldown-retry
diegosouzapw Nov 3, 2026
451e787
Merge branch 'release/v3.8.53' into fix/18268-vision-400-lockout
diegosouzapw Nov 3, 2026
b6a1bea
Merge branch 'release/v3.8.53' into fix/claude-code-stop-reason-override
diegosouzapw Nov 3, 2026
13092ba
Merge branch 'release/v3.8.53' into fix/port-pr-5037-claude-cache-tai…
diegosouzapw Nov 3, 2026
ae1a632
Merge branch 'release/v3.8.53' into fix/18296-claude-model-scoped-429
diegosouzapw Nov 3, 2026
abbadc4
Merge branch 'release/v3.8.53' into fix/codex-request-wire-contract
diegosouzapw Nov 3, 2026
748f5bf
Merge branch 'release/v3.8.53' into fix/codex-web-search-history-actions
diegosouzapw Nov 3, 2026
02946d8
Merge branch 'release/v3.8.53' into fix/codex-quota-signal-normalization
diegosouzapw Nov 3, 2026
9e44cdb
Merge branch 'release/v3.8.53' into fix/issues-18331-openapi-1027
diegosouzapw Nov 3, 2026
4b679e3
Merge branch 'release/v3.8.53' into feat/claude-desktop-context-20261027
diegosouzapw Nov 3, 2026
7b0a81a
Merge branch 'release/v3.8.53' into fix/json-body-behind-event-stream
diegosouzapw Nov 3, 2026
0ba0d64
Merge branch 'release/v3.8.53' into fix/18385-preset-item-session
diegosouzapw Nov 3, 2026
ca2aac3
Merge branch 'release/v3.8.53' into feat/perf-resource-optimization
diegosouzapw Nov 3, 2026
4414593
Merge branch 'release/v3.8.53' into fix/direct-headers-volume-tier
diegosouzapw Nov 3, 2026
f583b7b
Merge branch 'release/v3.8.53' into fix/18421-web-fetch-claude-format
diegosouzapw Nov 3, 2026
0a86fc9
Merge branch 'release/v3.8.53' into fix/log-image-ref-metadata
diegosouzapw Nov 3, 2026
c0d120b
Merge branch 'release/v3.8.53' into fix/18418-nvidia-gpt-oss-deprecated
diegosouzapw Nov 3, 2026
3c89e91
Merge branch 'release/v3.8.53' into fix/upstream-cf-health-20261028
diegosouzapw Nov 3, 2026
cf856af
Merge branch 'release/v3.8.53' into fix-18445-sse-stream-cleanup
diegosouzapw Nov 3, 2026
4ac041d
Merge branch 'release/v3.8.53' into fix/embedding-combo-pinned-dimens…
diegosouzapw Nov 3, 2026
b7ebca0
Merge branch 'release/v3.8.53' into fix-echo-client-requested-model
diegosouzapw Nov 3, 2026
2a0f026
Merge branch 'release/v3.8.53' into fix/browser-version-lookups
diegosouzapw Nov 3, 2026
e9ce7d3
Merge branch 'release/v3.8.53' into fix/version-lookup-retry-window
diegosouzapw Nov 3, 2026
72583b4
Merge branch 'release/v3.8.53' into fix/mistral-discovery-metadata
diegosouzapw Nov 3, 2026
bb4122b
Merge branch 'release/v3.8.53' into fix/call-log-artifact-zombie-cleanup
diegosouzapw Nov 3, 2026
cb43595
Merge branch 'release/v3.8.53' into fix/18517-cc-alias-provider-key
diegosouzapw Nov 3, 2026
2e21f06
Merge branch 'release/v3.8.53' into fix/cancel-received-storm
diegosouzapw Nov 3, 2026
0e40a00
Merge branch 'release/v3.8.53' into codex/fix-deepseek-rate-limit-hint
diegosouzapw Nov 3, 2026
119fd0a
Merge branch 'release/v3.8.53' into fix/18541-expiry-first-direct-model
diegosouzapw Nov 3, 2026
efaa384
Merge branch 'release/v3.8.53' into fix/combo-set-retry-cancellation
diegosouzapw Nov 3, 2026
9729e67
Merge branch 'release/v3.8.53' into fix/require-api-key-consistent-parse
diegosouzapw Nov 3, 2026
13f1724
Merge branch 'release/v3.8.53' into fix/combo-service-tier-upstream
diegosouzapw Nov 3, 2026
41edf0e
Merge branch 'release/v3.8.53' into fix/hedge-cancel-attempt-classifi…
diegosouzapw Nov 3, 2026
fda59ad
Merge branch 'release/v3.8.53' into fix/17997-agentrouter-responses
diegosouzapw Nov 3, 2026
bafff01
Merge branch 'release/v3.8.53' into fix/codex-paid-credits-last
diegosouzapw Nov 3, 2026
953a512
Merge branch 'release/v3.8.53' into fix/quota-kimi-provider-label
diegosouzapw Nov 3, 2026
ec70441
Merge branch 'release/v3.8.53' into fix/qoder-per-model-quota-scope
diegosouzapw Nov 3, 2026
4617d75
Merge branch 'release/v3.8.53' into fix/request-rejected-streak-scope
diegosouzapw Nov 3, 2026
c9682d2
Merge branch 'release/v3.8.53' into fix/18414-docker-node-verification
diegosouzapw Nov 3, 2026
909d41e
Merge branch 'release/v3.8.53' into fix/windows-autostart-stale-cli-path
diegosouzapw Nov 3, 2026
b8a1ed6
Merge branch 'release/v3.8.53' into fix/docs-fumadocs-theme-storage-key
diegosouzapw Nov 3, 2026
1c0bf66
Merge branch 'release/v3.8.53' into fix/18607-exact-thinking-replay
diegosouzapw Nov 3, 2026
4c73c50
Merge branch 'release/v3.8.53' into fix/gemini-stream-recovery-termin…
diegosouzapw Nov 3, 2026
d22f93e
Merge branch 'release/v3.8.53' into fix/cursor-sync-locality-public-2…
diegosouzapw Nov 3, 2026
7c540e6
Merge branch 'release/v3.8.53' into fix/18556-mcp-stdio-path-guard
diegosouzapw Nov 3, 2026
d887450
Merge branch 'release/v3.8.53' into fix/18632-sanitizer-flag-overrides
diegosouzapw Nov 3, 2026
85e9313
Merge branch 'release/v3.8.53' into fix/antigravity-usage-only-chunk
diegosouzapw Nov 3, 2026
0cc528f
Merge branch 'release/v3.8.53' into fix/18598-pricing-bucket
diegosouzapw Nov 3, 2026
39ae7a9
Merge branch 'release/v3.8.53' into fix/boundary-engine-usagedb
diegosouzapw Nov 3, 2026
7870473
Merge branch 'release/v3.8.53' into fix/18637-compression-engines-dis…
diegosouzapw Nov 3, 2026
5602752
Merge branch 'release/v3.8.53' into fix/provider-403-quota-exhausted-…
diegosouzapw Nov 3, 2026
c71c903
Merge branch 'release/v3.8.53' into fix/windows-regression-portabilit…
diegosouzapw Nov 3, 2026
75685f7
Merge branch 'release/v3.8.53' into fix/antigravity-verify-link-not-s…
diegosouzapw Nov 3, 2026
18e2baa
Merge branch 'release/v3.8.53' into fix/antigravity-route-by-account-…
diegosouzapw Nov 3, 2026
de60196
Merge branch 'release/v3.8.53' into fix/claude-thinking-duplicate-too…
diegosouzapw Nov 3, 2026
690a01b
Merge branch 'release/v3.8.53' into fix/provider-request-capture-error
diegosouzapw Nov 3, 2026
69de44b
Merge branch 'release/v3.8.53' into fix/responses-gemini-developer
diegosouzapw Nov 3, 2026
15eddcd
Merge branch 'release/v3.8.53' into fix/antigravity-preheaders-budget
diegosouzapw Nov 3, 2026
1baaf5f
Merge branch 'release/v3.8.53' into fix/displaced-tool-results-3.8.53
diegosouzapw Nov 3, 2026
b11e567
Merge branch 'release/v3.8.53' into fix/vision-bridge-blocked-providers
diegosouzapw Nov 3, 2026
dd56240
Merge branch 'release/v3.8.53' into fix/codex-exhaustion-boundary-202…
diegosouzapw Nov 3, 2026
a8129bd
Merge branch 'release/v3.8.53' into perf/quota-availability-read-view…
diegosouzapw Nov 3, 2026
3617f48
Merge branch 'release/v3.8.53' into fix/copilot-gpt6-responses-routing
diegosouzapw Nov 3, 2026
31a926b
Merge branch 'release/v3.8.53' into fix/main-cooldown-wait-test
diegosouzapw Nov 3, 2026
29b9a4f
Merge branch 'release/v3.8.53' into fix/credit-balance-exhausted
diegosouzapw Nov 3, 2026
4e8f543
Merge branch 'release/v3.8.53' into fix/turn-guard-self-retry
diegosouzapw Nov 3, 2026
bb0e396
Merge branch 'release/v3.8.53' into fix/18718-fix-providers-kiro-tool…
diegosouzapw Nov 3, 2026
f93fc9f
Merge branch 'release/v3.8.53' into fix/18684-tool-output-image-cap
diegosouzapw Nov 3, 2026
058e18a
Merge branch 'release/v3.8.53' into fix/18746-codex-claude-effort
diegosouzapw Nov 3, 2026
3998df2
Merge branch 'release/v3.8.53' into fix/provider-refusal-root-causes-…
diegosouzapw Nov 3, 2026
47a52e1
Merge branch 'release/v3.8.53' into fix/18679-responses-chat-tool-sch…
diegosouzapw Nov 3, 2026
e508edd
Merge branch 'release/v3.8.53' into fix/18664-model-lockout-not-quota…
diegosouzapw Nov 3, 2026
b58edc6
Merge branch 'release/v3.8.53' into fix/safe-tool-output-preservation
diegosouzapw Nov 3, 2026
8165e45
Merge branch 'release/v3.8.53' into fix/18675-kiro-client-tool-named-…
diegosouzapw Nov 3, 2026
442402b
Merge branch 'release/v3.8.53' into fix/retry-delay-select-width
diegosouzapw Nov 3, 2026
72df0a9
Merge branch 'release/v3.8.53' into fix/combo-live-account
diegosouzapw Nov 3, 2026
9e447e9
Merge branch 'release/v3.8.53' into feat/dashboard-system-metrics-cards
diegosouzapw Nov 3, 2026
a0ee1bb
Merge branch 'release/v3.8.53' into fix/unified-chat-body-limit
diegosouzapw Nov 3, 2026
99fd77d
Merge branch 'release/v3.8.53' into fix/console-retained-history
diegosouzapw Nov 4, 2026
6d23274
Merge remote-tracking branch 'origin/release/v3.8.53' into HEAD
diegosouzapw Nov 4, 2026
cdee1d7
Merge branch 'cheaper-inference:release/v3.8.53' into fix/mistral-dis…
RayJW Nov 4, 2026
fb41904
train: merge #17908
diegosouzapw Nov 4, 2026
ce5576f
train: merge #18235
diegosouzapw Nov 4, 2026
832dfb7
train: merge #18258
diegosouzapw Nov 4, 2026
4bb5d44
train: merge #18271
diegosouzapw Nov 4, 2026
3bc78b5
train: merge #18280
diegosouzapw Nov 4, 2026
f1ef684
train: merge #18286
diegosouzapw Nov 4, 2026
d06cbf7
train: merge #18301
diegosouzapw Nov 4, 2026
792c248
train: merge #18329
diegosouzapw Nov 4, 2026
1b3cb6b
train: merge #18333
diegosouzapw Nov 4, 2026
47a9755
train: merge #18334
diegosouzapw Nov 4, 2026
6d1d2ef
train: merge #18349
diegosouzapw Nov 4, 2026
4938ed8
train: merge #18361
diegosouzapw Nov 4, 2026
c2fe2c5
train: merge #18374
diegosouzapw Nov 4, 2026
9ea0253
train: merge #18377
diegosouzapw Nov 4, 2026
2b4a72d
train: merge #18386
diegosouzapw Nov 4, 2026
748f878
train: merge #18393
diegosouzapw Nov 4, 2026
1320a3a
train: merge #18396
diegosouzapw Nov 4, 2026
648472c
train: merge #18404
diegosouzapw Nov 4, 2026
ab5e1fc
train: merge #18427
diegosouzapw Nov 4, 2026
46d8d21
train: merge #18438
diegosouzapw Nov 4, 2026
c1a7adf
train: merge #18443
diegosouzapw Nov 4, 2026
0e53d3e
train: merge #18447
diegosouzapw Nov 4, 2026
7583fc7
train: merge #18465
diegosouzapw Nov 4, 2026
7738658
train: merge #18484
diegosouzapw Nov 4, 2026
d134f83
train: merge #18495
diegosouzapw Nov 4, 2026
7fd298d
train: merge #18503
diegosouzapw Nov 4, 2026
2c4fdf3
train: merge #18507
diegosouzapw Nov 4, 2026
918de74
train: merge #18510
diegosouzapw Nov 4, 2026
b462a6b
train: merge #18511
diegosouzapw Nov 4, 2026
4b2d16f
train: merge #18522
diegosouzapw Nov 4, 2026
1f6e309
train: merge #18526
diegosouzapw Nov 4, 2026
6e56227
train: merge #18527
diegosouzapw Nov 4, 2026
9bcaf15
train: merge #18528
diegosouzapw Nov 4, 2026
3650ead
train: merge #18534
diegosouzapw Nov 4, 2026
ae20e36
train: merge #18548
diegosouzapw Nov 4, 2026
1d5bfc0
train: merge #18549
diegosouzapw Nov 4, 2026
30cc6a9
train: merge #18550
diegosouzapw Nov 4, 2026
1a33b0b
train: merge #18553
diegosouzapw Nov 4, 2026
8555f52
train: merge #18559
diegosouzapw Nov 4, 2026
24dd329
train: merge #18560
diegosouzapw Nov 4, 2026
0977110
train: merge #18561
diegosouzapw Nov 4, 2026
282eee6
train: merge #18571
diegosouzapw Nov 4, 2026
9578b24
train: merge #18572
diegosouzapw Nov 4, 2026
f6f4adc
train: merge #18574
diegosouzapw Nov 4, 2026
dc829ca
train: merge #18585
diegosouzapw Nov 4, 2026
a3ac370
train: merge #18605
diegosouzapw Nov 4, 2026
83a4b40
train: merge #18612
diegosouzapw Nov 4, 2026
c40232a
train: merge #18616
diegosouzapw Nov 4, 2026
73d15f6
train: merge #18624
diegosouzapw Nov 4, 2026
0e15a0a
train: merge #18629
diegosouzapw Nov 4, 2026
f21e2f7
train: merge #18634
diegosouzapw Nov 4, 2026
5715e42
train: merge #18635
diegosouzapw Nov 4, 2026
c624d25
train: merge #18643
diegosouzapw Nov 4, 2026
511a8f1
train: merge #18644
diegosouzapw Nov 4, 2026
78d96df
train: merge #18648
diegosouzapw Nov 4, 2026
55b8ea1
train: merge #18650
diegosouzapw Nov 4, 2026
b75761a
train: merge #18652
diegosouzapw Nov 4, 2026
6287844
train: merge #18660
diegosouzapw Nov 4, 2026
594923e
train: merge #18661
diegosouzapw Nov 4, 2026
0042159
train: merge #18665
diegosouzapw Nov 4, 2026
12ee0c4
train: merge #18688
diegosouzapw Nov 4, 2026
957d8c3
train: merge #18703
diegosouzapw Nov 4, 2026
9ffa007
train: merge #18704
diegosouzapw Nov 4, 2026
3dd3a6d
train: merge #18705
diegosouzapw Nov 4, 2026
ac49c34
train: merge #18709
diegosouzapw Nov 4, 2026
0307556
train: merge #18730
diegosouzapw Nov 4, 2026
a2c1550
train: merge #18735
diegosouzapw Nov 4, 2026
e257b3b
train: merge #18741
diegosouzapw Nov 4, 2026
8b26b15
train: merge #18743
diegosouzapw Nov 4, 2026
4527ffe
train: merge #18751
diegosouzapw Nov 4, 2026
495b70e
train: merge #18770
diegosouzapw Nov 4, 2026
00731ea
train: merge #18778
diegosouzapw Nov 4, 2026
ba0247e
train: merge #18780
diegosouzapw Nov 4, 2026
d58530a
train: merge #18784
diegosouzapw Nov 4, 2026
6b6d646
train: merge #18788
diegosouzapw Nov 4, 2026
c31b9e3
train: merge #18805
diegosouzapw Nov 4, 2026
d84dc0f
train: merge #18806
diegosouzapw Nov 4, 2026
386c839
train: merge #18814
diegosouzapw Nov 4, 2026
7b1d4ea
train: merge #18818
diegosouzapw Nov 4, 2026
3b09942
train: merge #18823
diegosouzapw Nov 4, 2026
d96d34d
train: merge #18830
diegosouzapw Nov 4, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
25 changes: 21 additions & 4 deletions .env.example
Original file line number Diff line number Diff line change
Expand Up @@ -485,6 +485,7 @@ AUTH_COOKIE_SECURE=false
# Require an API key for all /v1/* proxy endpoints.
# Used by: API middleware — rejects unauthenticated requests to the proxy API.
# Default: false | Set true for multi-user/public deployments.
# On: true, 1 or yes (case and surrounding spaces ignored). Any other value is off.
# Leaving this false is only safe when the app is reachable on loopback only
# (see APP_BIND_HOST above) or sits behind a reverse proxy doing its own auth.
REQUIRE_API_KEY=false
Expand Down Expand Up @@ -522,7 +523,8 @@ ALLOW_API_KEY_REVEAL=false
# Used by: src/shared/utils/apiKeyPolicy.ts — checkRateLimit() fallback.
# DEFAULT_RATE_LIMIT_PER_DAY=1000

# Maximum request body size in bytes (rejects larger payloads).
# Maximum request body size in bytes (rejects larger payloads). A saved maxBodySizeMb wins.
# Chat Completions and Responses keep a 50 MB default until a limit is saved.
# Used by: src/shared/middleware/bodySizeGuard.ts — prevents oversized uploads.
# Default: 10485760 (10 MB)
# MAX_BODY_SIZE_BYTES=10485760
Expand All @@ -537,6 +539,7 @@ ALLOW_API_KEY_REVEAL=false
# as structure-heavy. Default 262144 (256 KB).
# OMNIROUTE_CHAT_LARGE_BODY_BYTES=262144
# Actual-byte hard cap enforced during bounded ingestion. Default 52428800 (50 MB).
# A saved maxBodySizeMb replaces the default; when set here, this also caps that saved value.
# OMNIROUTE_CHAT_HARD_MAX_BODY_BYTES=52428800
# Legacy request-COUNT cap (#503-fanout). Now binds only when explicitly set here —
# left unset, heavyweight admission is gated by OMNIROUTE_CHAT_MAX_INFLIGHT_BYTES below
Expand Down Expand Up @@ -864,6 +867,15 @@ ALLOW_API_KEY_REVEAL=false
# own cap. Positive integers only; unset or invalid values keep 128.
# OMNIROUTE_MAX_TOOLS_LIMIT=128

# Responses -> Chat translation re-sends tool-output images (function_call_output,
# custom_tool_call_output, role "tool") as user image parts. Only the newest images within
# both budgets are kept; each older one becomes a text placeholder with its tool_call_id,
# and the cap logs one warning per request.
# Used by: open-sse/translator/request/openai-responses.ts (selectDroppedToolOutputImages).
# Positive integers only; unset or invalid values keep the defaults.
# OMNIROUTE_TOOL_OUTPUT_IMAGE_MAX_COUNT=16
# OMNIROUTE_TOOL_OUTPUT_IMAGE_MAX_BYTES=20971520

# SYNTX.ai prompt-emulated tool calling. Unset = on: SYNTX chat injects the local
# tool catalog into the prompt and parses <tool_call> blocks back into OpenAI
# tool_calls. Set to 0/false/off to skip the local-tool catalog injection.
Expand Down Expand Up @@ -1369,8 +1381,9 @@ PROVIDER_LIMITS_SYNC_SPACING_MS=1500
# before the dashboard polls. Default: 5000
#PROVIDER_LIMITS_POST_USAGE_REFRESH_DELAY_MS=5000

# Disable all background services (sync, pricing, model refresh).
# Used by: src/instrumentation-node.ts, src/lib/initCloudSync.ts
# Disable all background services (sync, pricing, model refresh, connection recovery,
# credential health, retention cleanup, scheduled VACUUM, settings hot-reload poll).
# Used by: src/lib/env/backgroundServices.ts, src/lib/initCloudSync.ts
# Useful for: CI builds, test environments, or resource-constrained containers.
# OMNIROUTE_DISABLE_BACKGROUND_SERVICES=false

Expand Down Expand Up @@ -1421,7 +1434,7 @@ PROVIDER_LIMITS_SYNC_SPACING_MS=1500
#OMNIROUTE_LOG_EXPORT_CHILD_MAX_OLD_SPACE_MB=1024

# Emergency budget-exhaustion fallback (set false or 0 to disable the reroute to
# nvidia/openai/gpt-oss-120b when a request fails with a 402 budget error).
# nvidia/nvidia/nemotron-3.5-super-vl-120b-a12b when a request fails with a 402 budget error).
# Used by: open-sse/services/emergencyFallback.ts. Default: enabled.
#OMNIROUTE_EMERGENCY_FALLBACK=true

Expand Down Expand Up @@ -2010,6 +2023,10 @@ CURSOR_USER_AGENT="Cursor/3.4"
# # Used when the direct upstream URL is private/LAN
# # so native Ollama cold-start TTFB can exceed 30s.
# # Default: 300000 = 5 min. See docs/guides/LOCAL_OLLAMA_DOCKER.md
# OMNIROUTE_DIRECT_HEADERS_VOLUME_ADAPTIVE=1 # Raise the direct response-start window by
# # payload tier (>512KB ×2, >2MB ×3, capped at 180s,
# # never lowering a higher floor). Set 0/false/off
# # to pin the flat window. Default: 1.
# OMNIROUTE_DIRECT_RESPONSE_RETRY_TIMEOUT_MS=600000 # Ceiling (ms) for the fresh-socket
# # RETRY attempt above (#13703). Only applies when
# # the caller already attached its own deadline
Expand Down
16 changes: 16 additions & 0 deletions .github/workflows/docker-publish.yml
Original file line number Diff line number Diff line change
Expand Up @@ -340,6 +340,22 @@ jobs:
env:
DOCKER_BUILDKIT_INLINE_CACHE: 1

# Check the binaries in both final Node images on each native architecture,
# before their digests can reach the multi-arch manifest/promotion job.
- name: Verify published Node runtimes
env:
DIGEST_BASE: ${{ steps.build.outputs.digest }}
DIGEST_WEB: ${{ steps.build-web.outputs.digest }}
PLATFORM: ${{ matrix.platform }}
run: |
set -euo pipefail
for digest in "$DIGEST_BASE" "$DIGEST_WEB"; do
image="${GHCR_IMAGE_NAME}@${digest}"
echo "Verifying Node runtime in ${image} (${PLATFORM})"
docker run --rm --pull always --platform "$PLATFORM" --entrypoint node -i \
"$image" --input-type=module < scripts/ci/check-docker-node-runtime.mjs
done

- name: Build and push BUN base platform image by digest
id: build-bun-base
# Bun is a best-effort compatibility target, not a supported runtime
Expand Down
2 changes: 1 addition & 1 deletion @omniroute/opencode-plugin-v2/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ server reads it, not only in the shell that runs `opencode models`.
| `managementReadToken` | option, then `OMNIROUTE_MANAGEMENT_API_KEY`, then `apiKey` | Management key for `/api/*` (combos, providers, enrichment) — usually **not** the same key |
| `displayName` | `"OmniRoute"` | Provider display name |
| `timeoutMs` | `10000` | Per-endpoint fetch timeout |
| `modelCacheTtlMs` | `300000` | Catalog cache TTL; disk snapshot warms cold starts |
| `modelCacheTtlMs` | `300000` | Catalog cache TTL and background refresh period (minimum 60000 ms): the served catalog follows the gateway within this window, with no service restart; disk snapshot warms cold starts |
| `timeouts` | per-endpoint override | `{ models, combos, enrichment }` in ms; falls back to `timeoutMs` (`autoCombos` still parses but is ignored — the virtual-entries route is no longer requested) |
| `enrichment` | `true` | Fetch names + pricing (`/api/pricing*`, `/api/free-tier/summary`) |
| `providerTag` | `true` | Prefix a display name with the upstream provider it routes to |
Expand Down
7 changes: 7 additions & 0 deletions @omniroute/opencode-plugin-v2/src/cache.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,13 @@ import { isHttpUrl } from "./shared/index.js";

export const DEFAULT_MODEL_CACHE_TTL_MS = 300_000 as const;

/**
* Lower bound on the background refresh period. Keeps the loop from spinning
* on configurations that set a tiny TTL (the existing tests use 1 ms) and
* matches the v1 minimum.
*/
export const MIN_REFRESH_INTERVAL_MS = 60_000 as const;

/**
* Breather after a refresh whose models fetch came back empty (gateway down
* or refusing). Transforms inside the window serve last-known-good without
Expand Down
83 changes: 75 additions & 8 deletions @omniroute/opencode-plugin-v2/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,12 +17,14 @@ import { buildProviderPayload, collectCatalog } from "./catalog.js";
import { usesModelsComboSource } from "./combos-source.js";
import {
UNREACHABLE_COOLDOWN_MS,
MIN_REFRESH_INTERVAL_MS,
memoryCacheKey,
readDiskSnapshot,
snapshotIdentityFingerprint,
writeDiskSnapshot,
type CatalogSnapshot,
} from "./cache.js";
import { startRefreshLoop } from "./refresh-loop.js";
import { assertContext } from "./compat.js";
import { type ApiKeyOrigin, resolveApiKey, warnIfMissing } from "./credentials.js";
import { createSourceErrorReporter } from "./enrichment-report.js";
Expand Down Expand Up @@ -136,6 +138,11 @@ export default Plugin.define({
unreachableUntil: 0,
};

// Per-installation stopped flag for the background refresh loop. Declared
// up front so the closures below can reference it without a temporal
// dead zone, and so a tick that lands after teardown publishes nothing.
let stopped = false;

// The credential the host holds wins over one written in config, so a
// user who connected the integration from the UI never has to paste a
// key into `opencode.json`. Reading it is async and the transforms must
Expand Down Expand Up @@ -164,9 +171,16 @@ export default Plugin.define({
if (credentialChecked && apiKeyOrigin !== "missing") return;
const next = await resolveApiKey(ctx, X, parsed.apiKey, log);
const moved = next.key !== resolved.apiKey;
const previousCacheKey = cacheKey;
resolved.apiKey = next.key;
apiKeyOrigin = next.origin;
if (moved) ({ cacheKey, identityFingerprint } = credentialsOf());
if (moved) {
({ cacheKey, identityFingerprint } = credentialsOf());
// Drop the stale entry so the memory cache does not grow across a
// credential change.
state.entries.delete(previousCacheKey);
state.inFlight.delete(previousCacheKey);
}
if (!credentialChecked) warnIfMissing(next, X, log);
else if (moved) log.info(`[omniroute-v2] API key picked up from the ${next.origin} source`);
credentialChecked = true;
Expand Down Expand Up @@ -304,7 +318,7 @@ export default Plugin.define({
enrichment: previous?.enrichment ?? new Map(),
fetchedAt: Date.now(),
};
if (models.length > 0) {
if (!stopped && models.length > 0) {
state.entries.set(cacheKey, snapshot);
await writeDiskSnapshot(X, snapshot, identityFingerprint, log);
}
Expand Down Expand Up @@ -334,6 +348,7 @@ export default Plugin.define({
SourceResult<OmniRouteEnrichmentMap>,
]
): Promise<void> {
if (stopped) return;
if (state.entries.get(cacheKey) !== base) return;
// Per source: a success replaces (even with an empty answer — that is
// the gateway's answer), a failure keeps what we had.
Expand Down Expand Up @@ -362,7 +377,7 @@ export default Plugin.define({
);
const optionalChanged = state.optionalFingerprint !== optionalFingerprint;
state.optionalFingerprint = optionalFingerprint;
if (optionalChanged) {
if (optionalChanged && !stopped) {
try {
await ctx.provider.reload();
} catch (err) {
Expand All @@ -373,10 +388,11 @@ export default Plugin.define({
}
}

function loadSnapshot(): Promise<CatalogSnapshot> {
function loadSnapshot(force = false): Promise<CatalogSnapshot> {
const now = Date.now();
const hit = state.entries.get(cacheKey);
if (hit && hit.fetchedAt + resolved.modelCacheTtlMs > now) return Promise.resolve(hit);
if (!force && hit && hit.fetchedAt + resolved.modelCacheTtlMs > now)
return Promise.resolve(hit);
// Cooldown after a total models failure: skip the network until it
// lapses. Serves last-known-good when one exists; otherwise the refresh
// below still runs (nothing to serve, no point pretending).
Expand Down Expand Up @@ -427,10 +443,13 @@ export default Plugin.define({
// setup publishes first, then the host replays the callback (during
// registration and on every reload) and reads the published snapshot.
let latest: { info: unknown; models: unknown[] } | undefined;
const refreshAndPublish = async (): Promise<void> => {
const refreshAndPublish = async (options?: { force?: boolean }): Promise<void> => {
if (stopped) return;
await ensureCredential();
if (stopped) return;
await ensureWarmSnapshot();
const snapshot = await loadSnapshot();
const snapshot = await loadSnapshot(options?.force === true);
if (stopped) return;
let effective = snapshot;
if (snapshot.models.length === 0) {
const stale = state.entries.get(cacheKey);
Expand Down Expand Up @@ -468,7 +487,7 @@ export default Plugin.define({
const fingerprint = catalogContentFingerprint(effective.models, effective.combos);
const changed = state.fingerprint !== undefined && state.fingerprint !== fingerprint;
state.fingerprint = fingerprint;
if (changed) {
if (changed && !stopped) {
await Promise.resolve();
try {
await ctx.provider.reload();
Expand Down Expand Up @@ -621,5 +640,53 @@ export default Plugin.define({
);
}
}

// Background refresh loop: keep the served catalog aligned with the
// gateway. The first publish above already populated `latest`; the loop
// only re-runs refreshAndPublish on the configured TTL.
// Registry of live loops, keyed by providerId, scoped to globalThis so it
// survives module re-evaluation (the host loads the plugin up to ~20
// times per process). Defense in depth behind the Cleanup returned below.
const registryKey = Symbol.for("omniroute.opencode-plugin-v2.refresh-loops");
const g = globalThis as unknown as Record<
symbol,
Map<string, { stop: () => void; state: RefreshState }>
>;
if (!g[registryKey]) g[registryKey] = new Map();
const registry = g[registryKey];
// Stop any loop already registered for this providerId.
const existing = registry.get(X);
if (existing) {
try {
existing.stop();
} catch {
// ignore
}
registry.delete(X);
}

const stopLoop = startRefreshLoop({
intervalMs: Math.max(MIN_REFRESH_INTERVAL_MS, resolved.modelCacheTtlMs),
refresh: () => refreshAndPublish({ force: true }),
logger: log,
});

// Cleanup returned to the host: flag the installation as stopped (a tick
// already in flight then publishes nothing), clear the timer and drop the
// registry entry. The entry carries `state` only so tests can inspect the
// memory cache.
const stop = () => {
stopped = true;
try {
stopLoop();
} catch {
// ignore
}
registry.delete(X);
};

registry.set(X, { stop, state });

return stop;
},
});
43 changes: 43 additions & 0 deletions @omniroute/opencode-plugin-v2/src/refresh-loop.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
export interface RefreshLoopOptions {
intervalMs: number;
refresh: () => Promise<void>;
logger: { warn: (message: string) => void; debug?: (message: string) => void };
}

/**
* Run `refresh` on a fixed interval without overlapping invocations.
*
* Returns a `stop` function that sets the stopped flag and clears the
* interval. `unref()` is guarded so the timer never keeps the process
* alive and works on both Node 22 and Node 24.
*/
export function startRefreshLoop(options: RefreshLoopOptions): () => void {
const { intervalMs, refresh, logger } = options;
let stopped = false;
let inFlight = false;

const tick = async (): Promise<void> => {
if (stopped) return;
if (inFlight) return;
inFlight = true;
try {
await refresh();
} catch (err) {
logger.warn(
`[omniroute-v2] background refresh failed: ${err instanceof Error ? err.message : String(err)}`
);
} finally {
inFlight = false;
}
};

const timer = setInterval(() => {
void tick();
}, intervalMs);
if (typeof timer.unref === "function") timer.unref();

return () => {
stopped = true;
clearInterval(timer);
};
}
Loading
Loading