fix(api): restrict bootstrap shared caching#4499
Merged
Merged
Conversation
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
Contributor
This was referenced Jul 12, 2026
koala73
added a commit
that referenced
this pull request
Jul 12, 2026
* perf(bootstrap): restore CDN cache shield for tier reads (#5249) PR #4499 set Cache-Control: no-store on every successful /api/bootstrap response except the anonymous single-key weatherAlerts probe. Because the browser runtime fetches tiers with default same-origin credentials and every visitor carries an anonymous wm-session cookie, hasBootstrapCredentialCookie() disqualified ~100% of dashboard boots from the public path. The CDN shield that used to absorb bootstrap traffic was gone, so every boot/refresh pipelined the full seed registry (~5-10 MB) straight out of Upstash — driving Redis read egress ~30x (from ~17 GB/day to 300-520 GB/day). The tier payload is the shared production seed bundle, identical for every caller (per #4499's own non-goals: only static transforms like wildfire compaction and enrichmentMeta strip apply, never per-user variance). So a credential-less tier read is safe to serve from the shared CDN. Server (api/bootstrap.js): - Add isPublicTierBootstrapRequest(): a GET/HEAD ?tier=fast|slow with no other params. Scoped to the two fixed tier shapes (not arbitrary ?keys=) so the CDN key space stays tiny and hit rate high. - Treat credential-less tier reads as a new 'public-tier' auth kind and emit the CDN-Cache-Control shield for them (fast s-maxage=600, slow s-maxage=7200). - Credentialed / API-key / arbitrary-key reads and all failures keep no-store, preserving #4495/#4499 intent. Client (src/services/bootstrap.ts): - Send tier fetches with credentials: 'omit' so the anonymous wm-session cookie is dropped and the request qualifies for the public CDN-cacheable path. Adds bootstrap-auth coverage for the public-tier path (cacheable anonymous fast/slow reads; no-store retained for cookie/enterprise/extra-param/unknown-tier). Co-Authored-By: Claude Opus 4.8 <[email protected]> Claude-Session: https://claude.ai/code/session_01FncwEiWddJ9My2HhQmrbYL * perf(bootstrap): serve public bootstrap paths with ACAO:* and drop HEAD (#5249 review) Addresses code-review findings on the public-tier cache path: - CDN cache fragmentation / ACAO pinning: the public (weather + tier) responses reused getCorsHeaders() (echoed ACAO + Vary: Origin + credentials), so the shared CDN stored one entry per Origin and a preview/embed origin could pin an echoed ACAO onto a cached response. Switch both public paths (success and the Redis-error fallback) to getPublicCorsHeaders() (ACAO:*, no Vary, no credentials) — one cache entry per URL, no pinning. Safe because isDisallowedOrigin() already rejected unauthorized origins at handler entry; the public paths are always credential-less. - HEAD unshielded read: isPublicTierBootstrapRequest accepted HEAD, so a HEAD ?tier=fast would run the full registry Redis pipeline to build a body it must not return. Restrict the public-tier path to GET; HEAD falls through to no-store (it has no client). - Document the load-bearing invariant: the CDN caches by URL only and does not vary on Cookie, so classifying tier reads as public is safe ONLY while the payload is byte-identical for every caller. Future per-user tier variance must stop classifying these as public. Tests: assert ACAO:* / no Vary / no credentials on the public-tier response, and that a HEAD tier read returns no-store without touching Redis. Co-Authored-By: Claude Opus 4.8 <[email protected]> Claude-Session: https://claude.ai/code/session_01FncwEiWddJ9My2HhQmrbYL * fix(bootstrap): isolate public tier cache reads --------- Co-authored-by: Claude <[email protected]>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
/api/bootstrapshared caching toauth.kind === "public-weather"only.GET /api/bootstrap?keys=weatherAlertscacheable while making session/user/enterprise bootstrap successesno-store.Intent
Fixes #4495.
The remaining cache boundary after the bootstrap auth hardening was that non-key success kinds could still inherit public/CDN cache headers. This PR makes the shared-cache exception explicit and narrow: anonymous weather bootstrap only.
Non-goals:
Validation Matrix
node --test api/bootstrap-auth.test.mjs api/bootstrap-cors.test.mjs api/_api-key.test.mjsTMPDIR=/tmp node --import tsx --test tests/embed-public-data-auth.test.mtsnpm run typecheck:apinpm run test:sidecargit diff --checkgit push -u origin HEADpre-push hookReview Gates
Documentation
Not applicable. This is an internal API response-header policy fix with regression coverage.
Screenshots / UI Evidence
Not applicable. No user-visible UI changed.
Residual Findings
None.