Skip to content

Tighten Hosted's deploy check, both Relays' asset caching, and two rule wordings - #1345

Merged
nedtwigg merged 2 commits into
mainfrom
deploy-preflight-and-rule-wording
Oct 21, 2026
Merged

nedtwigg merged 2 commits into
mainfrom
deploy-preflight-and-rule-wording

Conversation

@nedtwigg

@nedtwigg nedtwigg commented Oct 21, 2026 •

Copy link
Copy Markdown
Member

Deploy-check, caching, and spec-wording fixes for Hosted, the self-host Relay, and the workflow audit.

Deploy check (hosted/scripts/production.mjs)

productionConfigs and preflight now require every Worker to bind exactly one Hyperdrive, and fail (<name> must bind exactly one Hyperdrive) before preflight reads anything. Previously a Worker whose config listed no Hyperdrive passed both, and preflight never checked that Worker's caching, migration host/port/database, or role. The "three different Hyperdrives" check now counts the IDs actually bound rather than the three environment variables, so preflight also catches two Workers sharing one when handed configs directly. The Hyperdrive variable is now required for every Worker, not only one whose config lists a binding.

Asset caching (hosted/server/headers.ts, relay/src/app.ts)

immutable caching now applies only to names carrying Vite's content hash ([name]-[hash].[ext], 8 base64url characters, checked against the current Pocket, one-time, and account builds). On Hosted that covers /assets/ (account and Pocket) and /connect/assets/ (one-time page); on the self-host Relay, Pocket's /assets/. Any other file there takes its path's normal policy: no-cache on Pocket's paths, no-store on the account and the one-time page. Both Relays use one check, isContentHashedName in remote-lib-common/src/remote/relay-common.ts. docs/specs/pocket-app.md -> "Serving the built bundle", which owns Pocket's cache classes for both Relays, now says so; relay.md already points there. Hosted test fixtures now use realistic 8-character hashes.

RelayRoom sweep (hosted/server/relay-room.ts)

The next sweep is now scheduled RELAY_ROOM_SWEEP_MS after the current alarm started rather than after the sweep finished, so a slow row read (up to RELAY_ROW_READ_TIMEOUT_MS) no longer delays it. This is a one-line change (the alarm already captured its start time), so it was simpler to fix the code than to reword the rule around the delay. The rule in security-hosted.md (S115) now says what the code guarantees: each sweep schedules the next no later than the interval after its own start.

Spec wording

  • docs/specs/security-hosted.md: S122 names each Worker's single Hyperdrive; S115 as above. The word budget is raised to 3150.
  • docs/specs/security-ci.md: S48 now states plainly that an admin's push or branch_creation whose tip is lost is skipped, and the commit's next activity row decides. Any other row with a lost tip is still reported as unexplained. The classifier is unchanged.

No files under .github/ change; S48 only describes .github/workflows/workflow-audit.yaml.

Tests

  • hosted/scripts/production.test.mjs: a Worker with no, missing, or two Hyperdrive bindings fails productionConfigs and preflight before any read. Two Workers bound to one ID fail preflight.
  • relay/test/static.test.mjs: on the self-host Relay, /assets/plain.js and a 7-character hash are no-cache; real hashed names, including a multi-dash one, stay immutable. remote-lib-common/test/relay-common.test.mjs pins the shared check on its own.
  • hosted/server/tests/boundary.test.ts: names without a hash (/assets/plain.js, a 7-character hash, /connect/assets/plain.js) are not immutable on either Worker. A real multi-dash hashed name is.
  • hosted/server/tests/relay-room.test.ts: a sweep stalled on its row read still schedules the next sweep within the interval from its start.

Each new assertion fails with its fix reverted. Ran: hosted vitest run (Docker, 204 pass), pnpm typecheck, node --test hosted/scripts/*.test.mjs, node --test scripts/workflow-audit.test.mjs, remote-lib-common and relay pnpm test, pnpm test:checks.

🤖 Generated with Claude Code

- The production preflight requires each Worker to bind exactly one
  Hyperdrive before it reads any, so no Worker's caching, origin, or role
  check is skipped, and the distinct-Hyperdrive check counts the bindings
  themselves.
- Only a file whose name carries Vite's content hash is cached as
  immutable under `/assets/` and `/connect/assets/`; any other file there
  takes its path's normal policy.
- The RelayRoom schedules its next sweep from the current one's start, so
  a slow row read no longer delays it, and the rule says so.
- The workflow audit rule states plainly that an admin's push or branch
  creation with a lost tip is skipped rather than reported.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@cloudflare-workers-and-pages

cloudflare-workers-and-pages Bot commented Oct 21, 2026 •

Copy link
Copy Markdown

Deploying mouseterm with  Cloudflare Pages  Cloudflare Pages

Latest commit: 84788fc
Status: ✅  Deploy successful!
Preview URL: https://b76fe9ca.mouseterm.pages.dev
Branch Preview URL: https://deploy-preflight-and-rule-wo.mouseterm.pages.dev

View logs

… Relay

The self-host Relay marked every file under `/assets/` immutable. It now
applies Hosted's rule: only a name carrying Vite's content hash is
immutable, and any other file there is revalidated like the rest of
Pocket. The hash-name check moves to `isContentHashedName` in
remote-lib-common, which both Relays already import.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@nedtwigg nedtwigg changed the title Tighten Hosted's deploy check, asset caching, and two rule wordings Tighten Hosted's deploy check, both Relays' asset caching, and two rule wordings Oct 21, 2026
@nedtwigg
nedtwigg merged commit b451924 into main Oct 21, 2026
14 checks passed
@nedtwigg
nedtwigg deleted the deploy-preflight-and-rule-wording branch October 21, 2026 20:28
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants