Skip to content

fix(docker): bump Bun image to 1.4.0 with Turbopack and port the node image's build memory guards - #11719

Merged
diegosouzapw merged 19 commits into
cheaper-inference:mainfrom
rqzbeh:fix/docker-bun-build-oom
Aug 30, 2026
Merged

diegosouzapw merged 19 commits into
cheaper-inference:mainfrom
rqzbeh:fix/docker-bun-build-oom

Conversation

@rqzbeh

@rqzbeh rqzbeh commented Aug 26, 2026

Copy link
Copy Markdown
Contributor

fix(docker): bump Bun image to 1.4.0 with Turbopack and port the node image's build memory guards

Summary

Fixes #11709 — "Publish to Docker Hub" has been red on every push to main since the -bun image targets landed (#11039/#11168): the Bun builder stage (bun run build in Dockerfile.bun) dies with ResourceExhausted: ... cannot allocate memory on the 16 GB GitHub-hosted runners (a Next.js build worker is SIGKILLed mid-compile) on both linux/amd64 and linux/arm64. Because the multi-arch manifest step is never reached, no release image can be published — latest is still v3.8.49.

Root cause

Two compounding problems, both unique to the Bun image path:

  1. Pinned obsolete Bun release. Dockerfile.bun bases on oven/bun:1.3.14-slim (2026-05-13). Beside missing the Node-compat work that landed in Bun 1.4.0 (2026-08-20), that release cannot run Turbopack, so the -bun build is stuck on the webpack production pass — the memory-hungry path — while the node image builds with Turbopack by default. (Bun 1.4.0 also fixes a dependency-resolution bug: under 1.3.14, bun install --include=optional failed to resolve playwright@1.62.1 / postcss@^8.5.18 with bogus "No version matching" errors; 1.4.0 installs the full 2151-package tree cleanly.)
  2. Missing build memory guards. scripts/build/build-next-isolated.mjs force-forces --webpack for any process.versions.bun run (historical V8-worker-binding workaround), and Dockerfile.bun sets none of the knobs the node Dockerfile carries (fix: use Node 22 LTS + raise build heap to 6144 MB -- Node 24 crashes… [defer to 3.8.51] #10060/fix(docker): size the Next build worker pool for a 16 GB runner #11419): no OMNIROUTE_BUILD_WORKERS/CIRCLE_NODE_TOTAL (Next falls back to os.cpus()-1 = 3 page-data workers on the 4-vCPU runners) and no OMNIROUTE_BUILD_MEMORY_MB/NODE_OPTIONS (the build script applies its 8 GB per-process heap default). 4+ V8 processes at multi-GB each exceed the 16 GB runner; the cgroup OOM killer SIGKILLs a worker and buildkit surfaces cannot allocate memory.

Fix

  • Bump the Bun release: oven/bun:1.3.14-slim → oven/bun:1.4.0-slim (the release with Turbopack + Node 16.3 support and the dependency-resolution fixes).
  • Enable Turbopack on Bun (port of upstream build(bun): allow Turbopack bundler flag on Bun 1.4+ with configurable Webpack fallback #11471): resolveNextBuildBundlerFlag is now env-only (OMNIROUTE_USE_TURBOPACK=0 → --webpack, else --turbopack) instead of sniffing the runtime, and Dockerfile.bun replaces the hardcoded ENV OMNIROUTE_USE_TURBOPACK=0 with ARG OMNIROUTE_USE_TURBOPACK=1 / ENV wiring — webpack stays as the explicit --build-arg escape hatch for Bun < 1.4.
  • Port the node image's memory guards into Dockerfile.bun: ARG OMNIROUTE_BUILD_MEMORY_MB=6144 → ENV NODE_OPTIONS="--max-old-space-size=${OMNIROUTE_BUILD_MEMORY_MB}" and ARG OMNIROUTE_BUILD_WORKERS=3 → ENV CIRCLE_NODE_TOTAL=${OMNIROUTE_BUILD_WORKERS}. These bound the page-data workers on the default Turbopack path and keep the webpack fallback inside the 16 GB budget too. Worst case per the maintained model: 6144 + 2 × 2560 = 11264 MB ≤ 12288 MB (75 % of 16 GB).
  • Regression guards: tests/unit/docker-build-memory-budget.test.ts now validates both images (Dockerfile and Dockerfile.bun — wiring regexes + budget arithmetic + vCPU oversubscription), and tests/unit/build/resolve-next-build-bundler-flag.test.mjs (ported from build(bun): allow Turbopack bundler flag on Bun 1.4+ with configurable Webpack fallback #11471) pins the env-only flag contract.

Verification

  • node --experimental-strip-types --test tests/unit/docker-build-memory-budget.test.ts tests/unit/build/resolve-next-build-bundler-flag.test.mjs → 9/9 pass (run on the fleet worker).
  • Full reproduction of the failing builder stage on the 16-core fleet worker with the fixed stack (oven/bun 1.4.0 equivalent + Turbopack + the caps above): bun install --include=optional --quiet (2151 packages, no resolution errors) → better-sqlite3 node-gyp rebuild → bun run --quiet build → exit 0, ▲ Next.js 16.3.1 (Turbopack) banner, 2.2 GB standalone bundle produced, zero OOM-kills in dmesg. The same step OOM-kills before this change.
  • Note: docker-publish.yml triggers only on pushes to main / release/v* / tags / releases, so PR CI does not exercise the Docker build itself; the fix is backed by the regression tests and the real builder-stage run above.

Closes #11709.

@rqzbeh
rqzbeh requested a review from diegosouzapw as a code owner August 26, 2026 23:23
@rqzbeh
rqzbeh force-pushed the fix/docker-bun-build-oom branch 2 times, most recently from df2ee1e to f8d7503 Compare August 26, 2026 23:37
@harkaranbrar7

Copy link
Copy Markdown
Contributor

This looks right and matches the fix we were preparing on our side — the guards port into Dockerfile.bun plus the budget test covering both images is the correct approach.

One suggestion before merge: OMNIROUTE_BUILD_WORKERS=3 (→ 2 page-data workers) is likely still too much. #11647 is dropping the Node image to 1 worker because the 2-worker budget still OOMs the arm64 runner, and #11663 measured ~4.5 GB per process — 2 workers plus the parent exceeds the 16 GB budget (6144 + 2×4500 = 15,144 MB > 12,288 MB). Defaulting to OMNIROUTE_BUILD_WORKERS=2 (→ 1 worker), like #11663 does for the Node image, would avoid the Bun image hitting the same wall.

The Bun 1.4.0 + Turbopack bump is a good addition — just worth keeping in mind it makes this the first real Turbopack-on-Bun build, so if the OOM persists, a OMNIROUTE_USE_TURBOPACK=0 control run would isolate whether it's Turbopack's native memory.

@rqzbeh
rqzbeh force-pushed the fix/docker-bun-build-oom branch from f8d7503 to e55b6b6 Compare August 27, 2026 10:11
@rqzbeh

rqzbeh commented Aug 27, 2026

Copy link
Copy Markdown
Contributor Author

Thanks — adopted. Both images now default OMNIROUTE_BUILD_WORKERS=2 (1 page-data worker) against the measured ~4.5 GB per-process RSS from #7518/#11663: 2 processes × 4.5 GB ≈ 9 GB fits the 12,288 MB (75%) budget, where =3 (2 workers, 3 processes ≈ 13.5 GB) does not. The budget test now uses the measured figure for both Dockerfile and Dockerfile.bun and pins the =2 default (proven red at =3), so a future bump must re-do the arithmetic. #11663 landed on release/v3.8.51 after this PR was cut; the node Dockerfile here is aligned to =2 as well to keep the shared test honest on main. Good call on the control run: OMNIROUTE_USE_TURBOPACK=0 is now a --build-arg escape hatch on the Bun image, so an isolation run is one flag away if the OOM persists.

@rqzbeh
rqzbeh force-pushed the fix/docker-bun-build-oom branch 2 times, most recently from 57c0f8d to b8a4ddf Compare August 28, 2026 12:48
… image's build memory guards

- Bump Bun builder and runtime base images to oven/bun:1.4.0-slim
- Support Turbopack build path with environment-driven bundler flag resolution
- Port build worker and memory guards to Dockerfile.bun to prevent build OOM
- Update alibaba free-tier allowlist validUntil date and protocol clients E2E assertions
@rqzbeh
rqzbeh force-pushed the fix/docker-bun-build-oom branch from b8a4ddf to c5495e7 Compare August 28, 2026 13:15
diegosouzapw and others added 18 commits August 28, 2026 10:26
…heaper-inference#11877)

* fix(ci): publish npm from a hosted runner so provenance is accepted

The v3.8.50 staged publish failed at the upload:

  npm error code E422
  npm error 422 Unprocessable Entity - POST https://registry.npmjs.org/-/stage/package/omniroute
  Error verifying sigstore provenance bundle: Unsupported GitHub Actions runner
  environment: "self-hosted". Only "github-hosted" runners are supported when
  publishing with provenance.

3.8.49 published fine on 2026-07-30 because it predates USE_VPS_RUNNER being
turned on (2026-08-02). 3.8.50 is the first release since, so the incompatibility
had been latent for four weeks with nothing to surface it.

Neither obvious fix works on its own:

  - dropping --provenance would regress supply-chain posture; 3.8.49 carries a
    SLSA attestation and 3.8.50 must not ship without one;
  - moving the whole job to a hosted runner reintroduces the failure that made it
    self-hosted in the first place — 16 GB is not enough for build:cli's
    next-build fallback (documented on the job's runs-on).

So the work is split by what each runner is actually needed for. The self-hosted
job keeps every heavy gate — build, artifact validation, boot-smoke, the
clean-install/upgrade proof — and then packs the tarball it just proved and hands
it over. A new `stage-npm` job on ubuntu-latest downloads those exact bytes and
performs the upload, which needs no memory at all.

`npm pack --ignore-scripts` on the producing side and `--ignore-scripts` on the
publishing side both matter: prepublishOnly is `build:cli-api && build:cli &&
check:pack-artifact`, and the job already runs all three as explicit steps (the
dist/ prune is logged twice today — once at Build CLI bundle, once redundantly
inside npm stage publish). Re-running them on the small hosted runner would
rebuild bytes that were already built, validated and boot-smoked.

The DIRECT emergency fallback moved too — it published with --provenance and
would have hit the identical 422.

* chore(quality): re-baseline zizmor for the new hosted publish job

The `stage-npm` job adds 2 zizmor findings (192 -> 194), both of the same
deliberate @vn convention every workflow in this repo already follows:
unpinned-uses on actions/download-artifact@v8 and actions/setup-node@v7, plus
the cache-poisoning that setup-node@v7 already raises on the two other jobs in
this very file. SHA-pinning only the new job would break the convention.

No new class: zero template-injection, artipacked, dangerous-triggers or
excessive-permissions. The job declares contents:read + id-token:write, which is
the minimum npm provenance needs.
…alog (cheaper-inference#11867)

`Unit Tests (1/8)` went red on 2026-08-28 across every PR and on main, with
nothing changed — the clock had moved past the shipped catalog's expiry:

  config/alibaba-free-tier-allowlist.json → "validUntil": "2026-08-27"

isAlibabaFreeTierAllowlistPackValid() compares that against Date.now(), so from
28/08 loadAlibabaFreeTierAllowlistPack() returns null and the old
assert.ok(pack) could never pass again. Refreshing the date would only reschedule
the same break.

Production was never affected: resolveActiveAllowlistPack() falls back to the
embedded list when a pack expires, which is the intended design. The defect was
the test asserting the shipped catalog is currently fresh — a data property, not
a behavioral contract.

The test now writes its own packs to a temp dir with dates it controls, and
pins both halves of the contract:

  - inside the validity window, the pack REPLACES the embedded list (anchored on
    a model that exists nowhere else, so loading alone cannot satisfy it);
  - once expired, the pack is ignored and the embedded list serves.

That second path is what production has been running since 27/08 and had no
coverage at all, which is why the expiry surfaced as a red test rather than as
understood behavior. A third case pins the comparison against an injected
instant, including the no-expiry pack that never goes stale.

Whether the curated free-tier catalog still matches reality — and so deserves a
freshly dated pack — is a data question left to the operator in cheaper-inference#11866.

Closes cheaper-inference#11866
…per-inference#11891)

config/alibaba-free-tier-allowlist.json carried "validUntil": "2026-08-27".
On the 28th the loader started rejecting it — correctly, that is the design —
and a test that asserted "the shipped pack loads" turned every PR and main red
with no commit involved (cheaper-inference#11866). A time bomb: the one class of defect a diff
review can never catch, because there is no diff.

scripts/check/lib/configExpiry.mjs walks config/**/*.json for validUntil /
validTo / expiresAt / expiry / expires (and snake_case forms), parses the dates,
and classifies each as expired / expiring (< 7 days) / ok / unparseable.

The repo-wide test fails on expired or expiring packs unless the file is in a
small allowlist keyed to the issue that owns the renewal — and fails the OTHER
way when an allowlisted pack is no longer expiring, so entries cannot go stale.
A positive anchor requires at least one dated pack to be found, so a renamed
key cannot silently turn the suite into a no-op.

The Alibaba pack is allowlisted against cheaper-inference#11866: whether the curated free-tier
list still matches reality is an operator data decision, not a test fix.
Removing that entry makes the suite fail as intended (verified).
…ise (cheaper-inference#11893)

* chore(ops): make the runner janitor act on what it can prove, not advise

The .113 janitor already knew the rules and had been shouting them into a log
nobody reads: on 2026-08-28 12:00Z it reported "10 listeners > ceiling 8" and
"disk 85%" — for hours — while 6.7 GB of dead-run leftovers sat on the 12 GB
tmpfs (RAM) because its patterns matched neither e2e-build.tar.gz nor
next-build/, its 24 h fuse is a day too long for memory, and its _work/_temp
base (/home/*/actions-runner*) does not exist on this box (runners live under
/opt). Measured while draining the v3.8.50 npm publish (postmortem, Parte III).

What changes:

- idle is PROVEN before removal, with ONE lsof snapshot filtered to the swept
  bases (lsof +D per path walked whole trees and took minutes; 460 candidates
  grepping a re-printed 83k-line string was the other half). 20 s on the box.
  Without lsof the janitor removes nothing and says why (exit 1).
- tmpfs leftovers go after 3 h, disk _work/_temp after 24 h; both overridable.
  Patterns gain next-build* and e2e-build.tar.gz; /opt/actions-runner* is swept.
- zombie builds: a next-build older than 75 min has no job (a real Build step is
  ~26 min). On 2026-08-27 one ran 70 min after GitHub had declared its job lost,
  holding 3.6 GB. KillMode=mixed on the units covers systemctl stop/restart;
  this covers the lost-connection path.
- prunes 48 h-old checkouts under _work of runners whose unit is STOPPED — an
  active runner is never touched.
- alerts on memory PSI (full/avg60) and reports the listener ceiling with an
  omniroute/other breakdown (the box also hosts OmniHeuris and OmniMind).
  Enforcing the ceiling stays an operator decision (label split), not cron's.
- --dry-run prints exactly what it would do and touches nothing; unknown
  arguments are rejected.

Dry-run on the real box: 460 stale omniroute-* test fixtures (930 MB of RAM) it
would reclaim, 0 busy, 0 false "removed" lines, 20 s. The unit suite drives the
script against a fixture tree with every base redirected; the sweep branch runs
where lsof exists (hosted CI images) and the without-lsof contract everywhere.

docs/ops/RUNNER_BOX.md reconciled to the measured box: 31 GB (it said 16), ten
listeners, the 14 GB next-build ceiling, the KillMode drop-in, and the rule that
nothing is cleaned by hand while a runner is busy.

* docs(ops): restore the frontmatter fumadocs requires on RUNNER_BOX.md

Rewriting the page whole dropped its `title:` frontmatter, and docs/ is
compiled into the Next build by fumadocs-mdx — so Build, Fast Production Build
and dast-smoke all died with "[MDX] invalid frontmatter in
docs/ops/RUNNER_BOX.md". Same block as before, verbatim.
…d runner (cheaper-inference#11895)

npm rejects provenance-signed uploads from self-hosted runners:

  422 Unprocessable Entity - Error verifying sigstore provenance bundle:
  Unsupported GitHub Actions runner environment: "self-hosted".
  Only "github-hosted" runners are supported when publishing with provenance.

v3.8.50 learned that at minute 76 of its 10th publish attempt, after the tag,
the GitHub Release and the Docker images were already out. USE_VPS_RUNNER had
routed the job to the .113 pool on 2026-08-02; no release ran between 07-30 and
08-28, so the pairing sat latent for four weeks.

It is pure text — a job whose runs-on resolves to self-hosted and a step whose
run contains --provenance — so the workflow lint now checks it as a hard rule:
reported in plain mode, blocking under --strict and --ratchet (the CI mode),
emitted as provenanceRunnerFindings=<n> next to the other counters.

Against origin/main the rule finds the two real offenders (the staged upload
AND the DIRECT emergency fallback in npm-publish.yml); against the cheaper-inference#11877 split
it finds none. --provenance-file is deliberately not matched (different flag,
pre-built bundle) and an opaque runs-on expression with no literal self-hosted
is classified unknown and skipped — the check never guesses.

The unit suite's last case walks the real .github/workflows and asserts zero
findings, so it is red on main until cheaper-inference#11877 lands and green after; that is the
regression guard working, not a flake.
…per-inference#11901)

The .113 box has 31 GB and a single next-build peaks at 14–16 GB RSS: one
build fits with room, two sit at the edge, three take the box down. On
2026-08-28 13:50Z the kernel OOM-killed main's next-build (15.7 GB) while a PR
build ran beside it — five Build jobs had been queued by a burst of PRs — and
the publish lost its artefact, which sends it into the 40-minute rebuild that
OOMs on its own (attempt 5 of this release).

Job-level concurrency on `build`, two lanes:

  heavy-build-main   pushes to main — never contended, never behind PR traffic
  heavy-build-pr     pull requests — serialize among themselves

cancel-in-progress stays false: a running build is never killed by a newer
one. GitHub's own rule for a group is one running + one pending, older pendings
cancelled — so under a burst the third PR build shows "cancelled" and needs a
re-run. That is the trade-off, stated: a cancelled PR check is re-runnable; a
dead main build costs a release.

The proper fix remains a label split (omni-build on two runners, omni-light on
the rest) so the queue lives on the runner side without cancellations — an
operator decision recorded in docs/ops/RUNNER_BOX.md.
…pfs (cheaper-inference#11896)

* fix(ci): keep the next-build artefact on disk, not on the runner's tmpfs

On the .113 pool /tmp is a 12 GB tmpfs — it is RAM. The 1.3 GB next-build
artefact was parked there four times over: the Build job tar'd it to
/tmp/e2e-build.tar.gz (6 min), three E2E jobs downloaded it to /tmp/ and
extracted from there, and npm-publish.yml pulled it with gh run download into
/tmp/next-build. Measured on the v3.8.50 publish runs: that download step took
27 min (9th attempt) and 32 min (10th) — 42% of a 76-minute job — while the
very same bytes upload from disk in 2 min and the box pulls from GitHub at
7.3 MB/s (1.3 GB ≈ 3 min). Network was never the bottleneck; a tmpfs at 75%
under memory pressure was.

Every site now uses $RUNNER_TEMP / ${{ runner.temp }}: per-runner, on disk
(_work/_temp under the runner dir on the pool, /home/runner/work/_temp on
hosted images), and cleaned by the runner between jobs.

It also removes a latent race: e2e-build.tar.gz is a FIXED name under a /tmp
shared by every runner on the box, so two E2E shards on different runners could
overwrite each other's download mid-extraction. RUNNER_TEMP is per runner.

The supply-chain guard in tests/unit/npm-publish-artifact-provenance.test.ts
pins the candidate-run selection and the --name, not the directory; it stays
green. check:workflows --ratchet: zizmor unchanged at the baseline.

* fix(ci): download the next-build artefact to a workspace-relative dir (pwsh has no $RUNNER_TEMP)

The Electron Package Smoke matrix runs on windows-latest, whose default shell
is pwsh: $RUNNER_TEMP is empty there (pwsh spells it $env:RUNNER_TEMP), so the
first cut's tar -xzf "$RUNNER_TEMP/e2e-build.tar.gz" tried to open
'/e2e-build.tar.gz' and failed. A path relative to the workspace works in bash
and pwsh alike, and hosted workspaces are ephemeral. The producer (Build, Linux,
bash) and npm-publish keep $RUNNER_TEMP.
…heaper-inference#11932)

The .113 box (31 GB) holds one next-build (14–16 GB RSS) comfortably and two
at the edge; on 2026-08-28 the kernel killed main's build twice while PR
builds ran beside it. Labels are the runner-side cap: only omniroute-113-5
and omniroute-113-6 carry omni-build (added through the runners API, no
re-registration), and every job that runs a next build — ci.yml build,
npm-publish.yml publish, both nightly-release-green validations — now asks
for that label. A third heavy job queues on GitHub instead of racing for
memory. The six other runners keep omni-release and no longer take builds.
Pairs with the heavy-build-* concurrency lanes (cheaper-inference#11901); documented in
docs/ops/RUNNER_BOX.md.
…cheaper-inference#11931)

* feat(ci): publish to npm through Trusted Publishing (OIDC) by default

npm rejects provenance from self-hosted runners and is retiring tokens that
bypass 2FA; v3.8.49 answered with staged publishing (WS1.3) so a leaked token
could never publish alone — at the price of a manual `npm stage approve` per
release. Trusted Publishing gives the same guarantee with no token at all: the
github-hosted stage-npm job exchanges GitHub's id-token for a credential scoped
to that run, provenance included, and the flow is automatic again as it was up
to v3.8.48.

publish_mode gains `auto` (the default, also the path for the release event);
`staged` now runs only when asked for; `direct` stays as the emergency token
fallback. Until the owner registers the Trusted Publisher on npmjs.com
(diegosouzapw/OmniRoute, workflow npm-publish.yml) the automatic step fails
with ENEEDAUTH and either other mode can be dispatched — documented in
docs/ops/RELEASE_CHECKLIST.md.

* docs(release): date the checklist for the Trusted Publishing change and drop the env-var claim

check-deprecated-versions flags a touched doc whose header still says
2026-06-28 / v3.8.40; the fabricated-docs gate read the backticked NPM_TOKEN as
an environment variable the code never reads (it is a repository secret).
…ote-only replace (cheaper-inference#11942)

CodeQL js/incomplete-sanitization (alert cheaper-inference#888 on cheaper-inference#11929): the hand-rolled replace
only escaped double quotes, so a backslash in the fixture would have produced a
malformed YAML scalar. JSON.stringify covers every escape the double-quoted YAML
scalar needs. Test-only change (7/7 pass).
…ead to the npm leg (cheaper-inference#11973)

v3.8.50 shipped with zero desktop assets. The tag push did trigger electron-release.yml
(run 33005490476) but GitHub refused the run at startup:

  Error calling workflow 'npm-publish.yml@5458026'. The nested job 'publish' is
  requesting 'actions: read', but is only allowed 'actions: none'.

npm-publish.yml's `publish` job gained `actions: read` (it downloads the next-build
artefact) and the caller job here never widened its grant — a reusable workflow may not
request more than its caller allows, and the refusal is a startup failure of the WHOLE
run, so the `release` job that attaches the installers, the source archives and the
SBOM never ran either. Nothing about it is visible through the API (no jobs, no
check-runs); only the run page shows the annotation.

- publish-npm: `actions: read` added, with the rule written down (keep the block a
  superset of every job in npm-publish.yml).
- workflow_dispatch: new boolean input `publish_npm` (default true) and the npm leg
  is gated on it, so re-attaching assets to a release whose package already shipped
  does not try to publish the same version twice.
- web-build / build / release checkouts pin `ref: needs.validate.outputs.version`:
  a dispatch builds the tag it names, not the dispatching branch (a tag push resolves
  to the same commit, so nothing changes on the normal path).

actionlint clean; electron-release-desktop-channel-8949, electron-release-efficiency,
build-next-isolated-windows-home-2402, electron-release-latest-yml.repro and
check-workflows suites pass. Next step: dispatch on main with version=v3.8.50 and
publish_npm=false to attach the missing assets.
…ob and the main run (main twin of cheaper-inference#11972) (cheaper-inference#11978)

Same change as cheaper-inference#11972 on release/v3.8.51: the Coverage job had timeout-minutes: 20,
the c8 merge across 8 shards takes ~10 min and the informational Codecov upload hung
for the rest of the budget on two consecutive main runs (33207760653, 33215115341),
ending the job cancelled and turning the run's conclusion cancelled with every
blocking job green. Codecov step: 5-minute ceiling + continue-on-error; job: 30 min.
…rom a repaired ref (cheaper-inference#11982)

* fix(release): resync the electron lockfile and let a dispatch build from a repaired ref

The v3.8.50 desktop re-dispatch (run 33238093090) lost its Linux leg at
`npm ci` in electron/: "Missing: electron-builder-squirrel-windows@26.15.3 from
lock file" plus its 12 transitive entries — the optional Windows-installer subtree of
electron-builder had been dropped when the lock was last regenerated, and no CI ran
the desktop legs between then and the tag (v3.8.49 never ran them; v3.8.50 died at
startup, cheaper-inference#11973). `npm install --package-lock-only` restores the 13 entries; a clean
`npm ci --ignore-scripts` on the result adds 284 packages with no complaint.

The tag itself carries the broken lock, and the workflow now checks out the tag on
dispatch (cheaper-inference#11973), so a dispatch input `build_ref` (default: the version tag) lets the
operator name the repaired line — the v3.8.50 assets will be rebuilt from main, which
is 3.8.50 plus its post-release fixes. Push-triggered runs are unaffected.

actionlint clean; electron-release-desktop-channel-8949, electron-release-efficiency,
electron-release-latest-yml.repro and check-workflows suites pass.

* fix(release): do not regenerate release notes on a re-attach dispatch

`generate_release_notes: true` on an existing release APPENDS GitHub's auto-generated
"What's Changed" block to the curated body — the v3.8.50 re-dispatch (run 33238093090)
added 1,416 chars to the 121 KB notes. Only the tag push should generate notes.
…shes too (cheaper-inference#12020)

The step was gated on github.event_name == 'release'. v3.8.50's package shipped
through a workflow_dispatch (the staged publish, 11 attempts) and the step was
skipped, so the GitHub Release carried no SBOM — it was attached by hand from the
run's sbom-npm artifact (5.0 MB, 1,886 components). Now it attaches on release or
workflow_dispatch whenever a release for the published tag exists, and says so
when it does not (the workflow artifact remains the durable copy either way).

actionlint and prettier clean; npm-publish-artifact-provenance and
check-workflows-provenance-runner suites pass.
… is dispatched on (cheaper-inference#12032)

Twin of cheaper-inference#12022 on main: CodeQL flagged the same input-controlled checkout + npm cache pattern (cache-poisoning/poisonable-step) on main since it's the default branch. Checkouts go back to github.ref; dispatch still works via --ref (documented in the workflow's own on: contract).

Also fixes the packaged-app smoke: it now waits on /api/monitoring/health (which touches the DB) instead of /login (which doesn't), so the smoke can actually distinguish "native driver selected" from "database never opened." electron-smoke-script.test.ts 9/9 (2 new cases).
…lose base-red issues, guard Scorecard on the default branch (main twin) (cheaper-inference#12086)

* fix(ci): accept CVE-2025-68121 in the prebuilt tls-client .so, auto-close base-red issues, guard Scorecard on the default branch

- .trivyignore: CVE-2025-68121 (Go stdlib crypto/tls inside bogdanfinn/tls-client
  v1.15.1, built with go 1.24.1) with justification, expiry and tracker cheaper-inference#12084.
  No upstream rebuild exists; the blocking Trivy gate now also names the ignore
  file explicitly.
- nightly-release-green: close the "not green" issue when the validation passes
  again (the workflow only ever opened/commented it, so stale issues outlived
  the fix and stamped new PRs as base-red inherited).
- scorecard: the action only accepts the DEFAULT branch (the active release
  branch, not main) - guard the job on it so pushes to main stop failing.

Refs cheaper-inference#12084

(cherry picked from commit 8adf34b)

* fix(release): never let the tag-push Create Release append auto notes to the curated body

Twin of the release/v3.8.51 commit (see cheaper-inference#12085).

Refs cheaper-inference#12084
@diegosouzapw
diegosouzapw merged commit b342c1a into cheaper-inference:main Aug 30, 2026
4 of 7 checks passed
muhamadgalihsaputra pushed a commit to niyatna/NiyatnaRoute that referenced this pull request Sep 27, 2026
…leware redirect (cheaper-inference#13140)

* fix(release): let the Electron workflow start again — grant actions:read to the npm leg (cheaper-inference#11973)

v3.8.50 shipped with zero desktop assets. The tag push did trigger electron-release.yml
(run 33005490476) but GitHub refused the run at startup:

  Error calling workflow 'npm-publish.yml@2b80128'. The nested job 'publish' is
  requesting 'actions: read', but is only allowed 'actions: none'.

npm-publish.yml's `publish` job gained `actions: read` (it downloads the next-build
artefact) and the caller job here never widened its grant — a reusable workflow may not
request more than its caller allows, and the refusal is a startup failure of the WHOLE
run, so the `release` job that attaches the installers, the source archives and the
SBOM never ran either. Nothing about it is visible through the API (no jobs, no
check-runs); only the run page shows the annotation.

- publish-npm: `actions: read` added, with the rule written down (keep the block a
  superset of every job in npm-publish.yml).
- workflow_dispatch: new boolean input `publish_npm` (default true) and the npm leg
  is gated on it, so re-attaching assets to a release whose package already shipped
  does not try to publish the same version twice.
- web-build / build / release checkouts pin `ref: needs.validate.outputs.version`:
  a dispatch builds the tag it names, not the dispatching branch (a tag push resolves
  to the same commit, so nothing changes on the normal path).

actionlint clean; electron-release-desktop-channel-8949, electron-release-efficiency,
build-next-isolated-windows-home-2402, electron-release-latest-yml.repro and
check-workflows suites pass. Next step: dispatch on main with version=v3.8.50 and
publish_npm=false to attach the missing assets.

* fix(ci): stop a stalled Codecov upload from cancelling the Coverage job and the main run (main twin of cheaper-inference#11972) (cheaper-inference#11978)

Same change as cheaper-inference#11972 on release/v3.8.51: the Coverage job had timeout-minutes: 20,
the c8 merge across 8 shards takes ~10 min and the informational Codecov upload hung
for the rest of the budget on two consecutive main runs (33207760653, 33215115341),
ending the job cancelled and turning the run's conclusion cancelled with every
blocking job green. Codecov step: 5-minute ceiling + continue-on-error; job: 30 min.

* fix(release): resync the electron lockfile and let a dispatch build from a repaired ref (cheaper-inference#11982)

* fix(release): resync the electron lockfile and let a dispatch build from a repaired ref

The v3.8.50 desktop re-dispatch (run 33238093090) lost its Linux leg at
`npm ci` in electron/: "Missing: electron-builder-squirrel-windows@26.15.3 from
lock file" plus its 12 transitive entries — the optional Windows-installer subtree of
electron-builder had been dropped when the lock was last regenerated, and no CI ran
the desktop legs between then and the tag (v3.8.49 never ran them; v3.8.50 died at
startup, cheaper-inference#11973). `npm install --package-lock-only` restores the 13 entries; a clean
`npm ci --ignore-scripts` on the result adds 284 packages with no complaint.

The tag itself carries the broken lock, and the workflow now checks out the tag on
dispatch (cheaper-inference#11973), so a dispatch input `build_ref` (default: the version tag) lets the
operator name the repaired line — the v3.8.50 assets will be rebuilt from main, which
is 3.8.50 plus its post-release fixes. Push-triggered runs are unaffected.

actionlint clean; electron-release-desktop-channel-8949, electron-release-efficiency,
electron-release-latest-yml.repro and check-workflows suites pass.

* fix(release): do not regenerate release notes on a re-attach dispatch

`generate_release_notes: true` on an existing release APPENDS GitHub's auto-generated
"What's Changed" block to the curated body — the v3.8.50 re-dispatch (run 33238093090)
added 1,416 chars to the 121 KB notes. Only the tag push should generate notes.

* fix(release): attach the SBOM to the GitHub Release on dispatch publishes too (cheaper-inference#12020)

The step was gated on github.event_name == 'release'. v3.8.50's package shipped
through a workflow_dispatch (the staged publish, 11 attempts) and the step was
skipped, so the GitHub Release carried no SBOM — it was attached by hand from the
run's sbom-npm artifact (5.0 MB, 1,886 components). Now it attaches on release or
workflow_dispatch whenever a release for the published tag exists, and says so
when it does not (the workflow artifact remains the durable copy either way).

actionlint and prettier clean; npm-publish-artifact-provenance and
check-workflows-provenance-runner suites pass.

* fix(release): drop the build_ref input — a dispatch builds the ref it is dispatched on (cheaper-inference#12032)

Twin of cheaper-inference#12022 on main: CodeQL flagged the same input-controlled checkout + npm cache pattern (cache-poisoning/poisonable-step) on main since it's the default branch. Checkouts go back to github.ref; dispatch still works via --ref (documented in the workflow's own on: contract).

Also fixes the packaged-app smoke: it now waits on /api/monitoring/health (which touches the DB) instead of /login (which doesn't), so the smoke can actually distinguish "native driver selected" from "database never opened." electron-smoke-script.test.ts 9/9 (2 new cases).

* fix(ci): accept CVE-2025-68121 in the prebuilt tls-client .so, auto-close base-red issues, guard Scorecard on the default branch (main twin) (cheaper-inference#12086)

* fix(ci): accept CVE-2025-68121 in the prebuilt tls-client .so, auto-close base-red issues, guard Scorecard on the default branch

- .trivyignore: CVE-2025-68121 (Go stdlib crypto/tls inside bogdanfinn/tls-client
  v1.15.1, built with go 1.24.1) with justification, expiry and tracker cheaper-inference#12084.
  No upstream rebuild exists; the blocking Trivy gate now also names the ignore
  file explicitly.
- nightly-release-green: close the "not green" issue when the validation passes
  again (the workflow only ever opened/commented it, so stale issues outlived
  the fix and stamped new PRs as base-red inherited).
- scorecard: the action only accepts the DEFAULT branch (the active release
  branch, not main) - guard the job on it so pushes to main stop failing.

Refs cheaper-inference#12084

(cherry picked from commit d7097b02eeb3ec413a54c4e43a6538bf7ae40090)

* fix(release): never let the tag-push Create Release append auto notes to the curated body

Twin of the release/v3.8.51 commit (see cheaper-inference#12085).

Refs cheaper-inference#12084

* fix(docker): bump Bun image to 1.4.0 with Turbopack and port the node image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.

* test(infra): retry recursive temp-dir removal on main (main twin of cheaper-inference#11968) (cheaper-inference#12246)

* test(infra): retry recursive temp-dir removal on main (main twin of cheaper-inference#11968)

`main` has been red since 530d9be779 on the vitest and integration gates:

  ✖ tests/unit/autoCombo/provider-family-combos.test.ts > auto/<family>
  ✖ chat pipeline applies Codex OAuth fingerprint and priority tier inside combos

Both call resetStorage() from beforeEach, which does an fs.rmSync(TEST_DATA_DIR,
{recursive: true, force: true}) with no retry, and intermittently loses the race
with a not-yet-released SQLite handle (ENOTEMPTY).

release/v3.8.51 fixed this in cheaper-inference#11968 with a mechanical codemod adding
maxRetries/retryDelay to every recursive rm/rmSync/rmdirSync under tests/, but
that PR landed only on the release branch. Because main only receives work at
the release squash, it stayed broken for the whole cycle — and repo-wide gates
then turn every open PR into main red on checks unrelated to their diff.

This is the --base main twin: re-runs the same codemod that already shipped on
the release branch (scripts/ad-hoc/codemod-rm-maxretries.mjs), so the two
branches converge on identical test-teardown semantics. Test-only; no product
logic is touched.

The remaining three failures reported on cheaper-inference#12133 (unit full suite exceeding its
4800s ceiling, package-artifact exceeding 1200s, and the boot-smoke that is
skipped as a consequence) are runner-contention timeouts, not code defects —
validate-release-green.mjs runs those heavy gates concurrently on one shared
hosted runner. There is no fix to port for those.

* chore(scripts): carry the rm-maxretries codemod onto main alongside its output

The codemod that generated the previous commit lives in the repo on
release/v3.8.51 (added by cheaper-inference#11968) but was never on main. Bringing it over keeps
the tool next to the change it produced, so the transformation stays
reproducible and auditable from either branch.

* fix(ci): port the release-green ESLint gate fix to main (base-red cheaper-inference#12363) (cheaper-inference#12618)

Porta para `main` o fix do gate de ESLint que só havia entrado na branch de release — o padrão de PR-companheiro que `_shared/merge-gates.md` §8 prescreve.

As 12 falhas de CI foram discriminadas como o **outro** base-red do main, não deste diff. Todas descendem de um único ponto: `Package Artifact` falha e os 9 shards de E2E mais os 2 Electron Package Smoke consomem esse artefato. A própria issue cheaper-inference#12363 lista os dois separadamente:

- `❌ ESLint: could not parse eslint json` — que é justamente o que este PR conserta;
- `❌ Package artifact (npm pack policy): gate exceeded its 1200s ceiling` — a raiz da cascata.

O PR toca apenas `scripts/quality/validate-release-green.mjs` e seu teste, então não tem caminho para afetar o build do pacote. Teste portado primeiro e falhando no script atual do main (TDD).

* fix(authz): preserve zed-hosted native-app callback through root middleware redirect

The root middleware intercepts `pathname === "/"` and redirects to
`/dashboard` using `new URL(basePath+"/dashboard", url)`, which drops
the query string entirely.

Zed's native-app sign-in always redirects the browser to the loopback
root — `http://127.0.0.1:<port>/?user_id=...&access_token=...` — ignoring
any path. When the dashboard's own loopback port is reused as
`native_app_port` (see `src/lib/oauth/providers/zed-hosted.ts`'s
`resolveDashboardLoopbackPort`), that redirect lands on `/` of the running
OmniRoute instance. The root page (`src/app/page.tsx`) was already written
to forward `user_id`+`access_token` to `/callback`, but this middleware
runs first and silently discards the payload — making page.tsx's forward
dead code and breaking the entire zed-hosted sign-in flow.

Fix: detect `user_id` + `access_token` in `searchParams` and, when
present, redirect to `/callback${search}` (preserving the query string)
instead of `/dashboard`. Regular root visits (no native callback params)
continue to redirect to `/dashboard` unchanged.

This approach mirrors what `src/app/page.tsx` already does and is
provider-agnostic: any future provider whose native loopback callback lands
on `/` with `user_id`+`access_token` params benefits automatically.

* test(authz): cover zed-hosted native-app callback root redirect (cheaper-inference#13140)

Adds automated coverage for the new pathname === "/" branch: with
user_id+access_token both present the redirect now forwards to
/callback preserving the query string; with only one of the two
present, behavior is unchanged (redirect to /dashboard).

Co-authored-by: diegosouzapw <8016841+diegosouzapw@users.noreply.github.com>

---------

Co-authored-by: Diego Rodrigues de Sa e Souza <diegosouza.pw@gmail.com>
Co-authored-by: Rouzbeh† <78313022+rqzbeh@users.noreply.github.com>
Co-authored-by: diegosouzapw <8016841+diegosouzapw@users.noreply.github.com>
diegosouzapw added a commit to adivekar-utexas/OmniRoute that referenced this pull request Sep 29, 2026
…lockstep comments

The five changelog.d fragments for cheaper-inference#11719/cheaper-inference#11973/cheaper-inference#11978/cheaper-inference#11982/cheaper-inference#12020 were already folded into
CHANGELOG.md and deleted on the release branch; re-adding them would duplicate those entries.
Compacting the buildUrlForBody doc comments brings open-sse/executors/base.ts's ceiling down
from 1772 to 1760.
diegosouzapw pushed a commit that referenced this pull request Sep 29, 2026
… the rewritten body model (#12826)

Validated on the 2026-09-28 release-drain board. Maintainer rework on top of your commits: merged the current release/v3.8.51 tip, resolving the openai-to-gemini.ts conflict so the tip's output-cap-aware default budget and your explicit-thinkingLevel rule combine (an explicit level still omits the numeric budget); dropped five changelog.d fragments the branch had re-added for already-released PRs (#11719/#11973/#11978/#11982/#12020, which would have duplicated CHANGELOG entries); compacted the buildUrlForBody comments so the base.ts ceiling drops from 1772 to 1760. The 3 new test files fail on the old code -> 12/12 with the fix, plus the tip's gemini thinking-budget suites and the executor-* sample green; typecheck:core, check:open-sse-typecheck, eslint and changelog-integrity clean. Thank you @adivekar-utexas!
diegosouzapw added a commit that referenced this pull request Sep 29, 2026
Brings the 12 main-only commits into the frozen release branch so the release
PR (#11442) is no longer CONFLICTING. Most are main twins of fixes the release
branch already carries in a newer shape; resolved by proving the release side
contains them:
- #12246 temp-dir retry: release uses cleanupTempDataDir / maxRetries (kept ours).
- #11719 Bun image: release is already on oven/bun 1.4.2 (kept ours).
- #12086 CVE-2025-68121 .trivyignore: dropped on release by #12429 (wreq-js).
- #13865 npm 11 / electron overrides: release pins are newer (kept ours);
  the optional transformers webpack-ignore change merged cleanly.
- streamTiming clock injection: release moved to a monotonic clock (kept ours).
Real main-only fix ported: #13072 hoistLeadingTextSystemMessages, added to the
release's claudeSystemRole.ts (the call site in chatCore.ts merged cleanly).
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Sep 29, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Sep 30, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Sep 30, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 2, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 3, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 7, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 7, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 8, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 9, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 12, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 16, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 19, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 26, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
phonex34 pushed a commit to phonex34/OmniRoute that referenced this pull request Oct 28, 2026
… image's build memory guards (cheaper-inference#11719)

Validated in an isolated worktree against main: typecheck:core clean, 15/15 focused tests pass (docker-build-memory-budget, bun-support, resolve-next-build-bundler-flag). Root cause confirmed against the current workflow config (docker-publish.yml triggers on push to both main and release/v*, so this genuinely needed to target main). One out-of-scope change dropped before merging: config/alibaba-free-tier-allowlist.json's validUntil bump (2026-08-27 -> 2027-12-31) was unrelated to the Docker/Bun fix — reverted to the current value, keeping only the Docker/Bun/memory-guard changes this PR is actually about. Thanks for the thorough root-cause writeup and the worker-pool math.
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.

3 participants