Skip to content

feat(release-service): add envelope encryption#1990

Merged
ascorbic merged 1 commit into
feat/delegated-release-servicefrom
feat/delegated-release-service-17-encryption
Jul 12, 2026
Merged

feat(release-service): add envelope encryption#1990
ascorbic merged 1 commit into
feat/delegated-release-servicefrom
feat/delegated-release-service-17-encryption

Conversation

@ascorbic

@ascorbic ascorbic commented Jul 12, 2026

Copy link
Copy Markdown
Collaborator

What does this PR do?

Implements W3.1 application-level encryption for release-service custody data. The versioned compact envelope uses AES-256-GCM with HKDF-SHA-256 purpose keys and authenticated context covering the key version, purpose, table, row ID, and owner DID where available.

Adds strict keyring and envelope validation, old-key reads, idempotent authenticated rotation, bounded inputs, stable non-leaking failures, and a required ENCRYPTION_KEYRING Worker secret. Validated configuration is passed into route handlers for the upcoming D1 custody slices.

Part of #1908.

Type of change

  • Bug fix
  • Feature (requires maintainer-approved Discussion)
  • Refactor (no behavior change)
  • Translation
  • Documentation
  • Performance improvement
  • Tests
  • Chore (dependencies, CI, tooling)

Checklist

  • I have read CONTRIBUTING.md
  • pnpm typecheck passes
  • pnpm lint passes
  • pnpm test passes (or targeted tests for my change)
  • pnpm format has been run
  • I have added/updated tests for my changes (if applicable)
  • User-visible strings in the admin UI are wrapped for translation (not applicable: no admin UI changes)
  • I have added a changeset (not applicable: only the private release-service app changed)
  • New features link to an approved Discussion: not applicable; implementation is tracked by the maintainer-owned integration PR Delegated release service #1908

AI-generated code disclosure

  • This PR includes AI-generated code — model/tool: OpenCode with GPT-5.6 Sol

Screenshots / test output

Non-visual change. Verified:

  • full pnpm build before pnpm typecheck
  • pnpm lint, pnpm lint:json, and pnpm format
  • release-service production build and generated Wrangler type check
  • 161 workerd tests
  • 38 Node encryption tests
  • fixed version 1 persisted-ciphertext compatibility vector in both runtimes
  • three focused review rounds, final pass found no remaining high, medium, or actionable low issues

Try this PR

Open a fresh playground →

A full working EmDash site, deployed from this branch. Each visit gets its own session-scoped sandbox: no login needed and no shared state. Try the admin, edit content, hit the public site.

Tracks feat/delegated-release-service-17-encryption. Updated automatically when the playground redeploys.

@changeset-bot

changeset-bot Bot commented Jul 12, 2026

Copy link
Copy Markdown

⚠️ No Changeset found

Latest commit: 6438490

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. If these changes should result in a version bump, you need to add a changeset.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Click here to learn what changesets are, and how to add one.

Click here if you're a maintainer who wants to add a changeset to this PR

@github-actions

Copy link
Copy Markdown
Contributor

Scope check

This PR changes 786 lines across 13 files. Large PRs are harder to review and more likely to be closed without review.

If this scope is intentional, no action needed. A maintainer will review it. If not, please consider splitting this into smaller PRs.

See CONTRIBUTING.md for contribution guidelines.

@cloudflare-workers-and-pages

Copy link
Copy Markdown

Deploying with  Cloudflare Workers  Cloudflare Workers

The latest updates on your project. Learn more about integrating Git with Workers.

Status Name Latest Commit Updated (UTC)
✅ Deployment successful!
View logs
emdash-playground 6438490 Jul 12 2026, 06:25 PM

@cloudflare-workers-and-pages

Copy link
Copy Markdown

Deploying with  Cloudflare Workers  Cloudflare Workers

The latest updates on your project. Learn more about integrating Git with Workers.

Status Name Latest Commit Updated (UTC)
✅ Deployment successful!
View logs
emdash-demo-do 6438490 Jul 12 2026, 06:25 PM

@cloudflare-workers-and-pages

Copy link
Copy Markdown

Deploying with  Cloudflare Workers  Cloudflare Workers

The latest updates on your project. Learn more about integrating Git with Workers.

Status Name Latest Commit Updated (UTC)
✅ Deployment successful!
View logs
emdash-demo-cache 6438490 Jul 12 2026, 06:26 PM

@github-actions

Copy link
Copy Markdown
Contributor

Overlapping PRs

This PR modifies files that are also changed by other open PRs:

This may cause merge conflicts or duplicated work. A maintainer will coordinate.

@emdashbot emdashbot Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Reviewed the release-service envelope encryption PR statically. This is a focused, well-structured security addition: AES-256-GCM with HKDF-SHA-256 purpose keys, compact versioned JSON envelope, authenticated context covering key version/purpose/table/row ID/owner DID, strict keyring and envelope parsing, old-key reads, idempotent authenticated rotation, non-leaking errors, and binding-based secret injection.

I traced the changed code end-to-end and checked it against the release-service conventions and the repo’s AGENTS.md guidance that applies here. Key observations:

  • Key derivation, AEAD parameters, and additional-data binding are correct. The HKDF salt is versioned/fixed; the IKM is a random 32-byte key, so a public salt is acceptable.
  • Envelope parsing rejects malformed JSON, extra/duplicate/missing keys, non-canonical serialization, bad lengths, padding, and unsupported versions before any crypto work.
  • Context validation correctly enforces owned/unowned/optional-owner semantics and snapshots the context synchronously before async key derivation.
  • Old keys remain available for decrypt/rotation; rotation decrypts first and is idempotent when already on the current key.
  • Configuration loading fails closed with a distinct ENCRYPTION_KEYRING_INVALID issue and no exposure of key material.
  • Tests were added for round-trips, old-key reads, rotation idempotency, context binding, oversize plaintext, invalid keyrings/envelopes, and runtime mutation of plaintext/context.
  • Changeset not needed because only the private release-service app changed. No admin UI, so Lingui/RTL conventions do not apply. No SQL/locale/API-authorization changes.

I did not find any blocking bugs, regressions, or convention violations. This looks ready to merge.

@github-actions github-actions Bot added review/approved Approved; no new commits since and removed review/needs-review No maintainer or bot review yet labels Jul 12, 2026
@ascorbic
ascorbic merged commit 5b0d760 into feat/delegated-release-service Jul 12, 2026
10 checks passed
@ascorbic
ascorbic deleted the feat/delegated-release-service-17-encryption branch July 12, 2026 19:11
@ascorbic ascorbic mentioned this pull request Jul 13, 2026
63 tasks
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant