You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Commit b993b99
Browse filesBrowse the repository at this point in the historyBrowse files
Self-hosted Cloudflare installation and native custom-domain deployment
exposed failures in authentication forms, recovery, candidate readiness,
and shared inbound email. This change fixes those paths and adds guarded
acceptance fixtures and regressions.
- Verify actual native Worker versions and custom-domain readiness,
preserve existing bindings/triggers, and publish pinned secrets before
initial readiness. Apps remain Workers Free compatible unless they opt
into a paid feature.
- Fix installation TLS validation and unnamed Access identity providers;
preserve a configured dashboard origin, reconcile interrupted cutovers,
and bound durable email bootstrap retries.
- Make setup, administrator, and account-link forms submit with the
correct origin while retaining exact-origin checks; handle dashboard
discovery and OAuth failures safely.
- Provision literal shared-email recipients with durable ownership
gates, verify plus addressing, preserve unrelated rules, and fence
deletion/slug reuse until teardown is verified. Migration 0056 preserves
upstream 0054/0055 and declares only its exact tested canonical
predecessor as rollback safe.
- Add guarded runtime acceptance fixtures and move temporary test apps
outside workspace package scans. Install Chromium in the CI jobs that
execute native browser forms, and verify the intentional canonical
schema conversion without relaxing other preserved data checks.
- Emit each inferred Durable Object binding and migration tag once,
preserve authored migration chronology and external bindings, and reject
incompatible Sandbox namespace storage before any provisioning or
entitlement request.
Validation at head ee32f5b:
- Local CI=true vp run test:all passed: formatting, lint, builds, all 28
package checks, 653 test files and 12,150 tests; 25 skipped. Three
optional Deno cases skip an explicit unsupported user npm configuration;
Node/Bun and Chromium cases execute.
- The Durable Object/Sandbox batch passed 700 focused unit tests and 14
real plugin/deployment build regressions. Combined and repeated builds
preserve external bindings and authored migration order; Free apps emit
no paid bindings.
- Canonical migrations 0054/0055/0056 passed against disposable
PostgreSQL seeded from the immutable previous release b4a4749. Its
projects/secrets API suites passed 137/137 against the upgraded
database; 27 fixture/baseline regressions passed.
- Live isolated installation and native custom-domain dashboard
deployment succeeded. Eleven public health/access checks, ten additional
anonymous GET checks and 50 anonymous feature authorization checks
passed. Genuine Cloudflare OIDC reached the first-administrator review.
- Exact-head GitHub Actions CI, Platform CI (including schema
compatibility), Security Analysis and both npm/pnpm Prepublish Test jobs
passed. The main-only live-e2e job was skipped; its status does not
establish live acceptance. Independent native runtime acceptance is
still in progress.
- The separate external Workers Builds check for void-cloud failed
(build ad6c6447-cb4d-40a2-8fda-324a8a9941d9). Its production-account
logs are unavailable in the logged-in test account, and no failure cause
or production deployment success is claimed.
Managed live acceptance remains incomplete: the built-in browser blocks
the approved /auth/bootstrap/confirm submission with
net::ERR_BLOCKED_BY_CLIENT before a server response. Current readback
has zero users and an expired unconsumed bootstrap. Genuine user
signup/deployments, admin/user management, teams, real email receipt,
managed Zero Trust, user queue consumption and Sandbox execution have
not passed live acceptance. Prepared runners are not executed tests. The
isolated live installation retains its earlier fork migration history;
this canonical runtime has not been applied to that fork.
Credentials, private recovery files and workstation acceptance logs are
excluded.
Copy file name to clipboardExpand all lines: docs/guide/email.md
+2-2Lines changed: 2 additions & 2 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -77,7 +77,7 @@ void email domain add acme.com
77
77
78
78
`add` opens a Cloudflare API-token template. Restrict the token to the selected account and mail zone before creating it; Workers Scripts permission applies across that account. The CLI accepts a masked paste or a newly copied token and asks you to confirm those restrictions. The platform encrypts the credential for the zone connection, so projects sharing that zone do not need separate ingress Workers.
79
79
80
-
When an apex already receives mail, the CLI proposes `mail.<domain>`. Use `--subdomain <label|host>` to choose another mail subdomain. Void refuses to replace a foreign enabled catch-all. A domain belongs to one project; multiple exact domains can share a zone, and a project can register more than one domain.
80
+
Platform-managed custom inbound email requires the apex of a Cloudflare zone. Cloudflare’s catch-all only covers that apex, so a subdomain of the selected zone cannot receive arbitrary addresses. Choose an apex without another mail provider, or use the platform’s shared mail address. Void preserves foreign MX records and enabled catch-alls. Each custom apex belongs to one project; a project can register more than one apex.
81
81
82
82
Setup returns an operation ID. If your connection drops, the platform keeps the recorded operation and the CLI checks that operation's status. An uncertain Cloudflare write stops conflicting changes until its outcome can be established.
83
83
@@ -395,7 +395,7 @@ remain available through that domain's sending capability.
395
395
### Configuring inbound delivery
396
396
397
397
On an email-enabled platform, `<slug>+anything@<mail domain>` reaches your
398
-
deployed `email/` handlers without per-project DNS setup. A
398
+
deployed `email/` handlers without per-project DNS setup once the platform has verified your recipient rule and enabled plus addressing. Deployment reports a routing conflict or capacity limit if setup cannot complete. A
399
399
[registered custom domain](#your-own-domain-on-the-platform) reaches those
400
400
handlers once its inbound readiness is `ready`. Use `void email domain status`
401
401
to check current provider routing and any remaining setup steps.
Copy file name to clipboardExpand all lines: docs/guide/platform/administration/email.md
+9-7Lines changed: 9 additions & 7 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -6,7 +6,9 @@ outline: deep
6
6
7
7
## Managing Email
8
8
9
-
These commands apply to a platform that enables email. Every project can send from and receive at `<slug>+tag@<mail domain>` on the platform's shared mail domain; the [email guide](/guide/email) describes what applications do with that.
9
+
These commands apply to a platform that enables email. Every project can send from `<slug>+tag@<mail domain>` on the platform’s shared mail domain and receive there once its recipient rule is ready; the [email guide](/guide/email) describes what applications do with that.
10
+
11
+
Shared inbound mail uses one exact routing rule per project and enables Cloudflare’s per-zone plus addressing. Existing rules and the apex catch-all remain in place. Cloudflare normally allows [200 routing rules per domain](https://developers.cloudflare.com/email-service/platform/limits/); remove unused rules or request a higher limit if the shared domain reaches capacity. An unrelated rule for a project’s base address or a plus address blocks its setup until that conflict is removed.
Then register a domain for a project. The zone must be in the platform's Cloudflare account; the platform's own credential does the setup, and no Cloudflare credential is stored per domain:
Name the exact mail domain: a subdomain such as `mail.example.com` when the apex already receives mail, otherwise the apex itself. `domain-status` reports inbound, outbound, and management readiness separately. Follow any required DNS or Cloudflare dashboard step, then use `domain-sync` to reconcile. Use `domain-rotate-secret` when you need to replace the zone ingress credential explicitly. Email Sending onboarding needs Workers Paid; after upgrading, `domain-sync` re-attempts it. For a zone in another Cloudflare account, pipe an API token for that account on standard input:
86
+
Use the apex of the selected Cloudflare zone. Platform-managed custom inbound email uses its catch-all, which does not cover subdomains; choose an apex without another mail provider or use the platform’s shared mail address. `domain-status` reports inbound, outbound, and management readiness separately. Follow any required DNS or Cloudflare dashboard step, then use `domain-sync` to reconcile. Use `domain-rotate-secret` when you need to replace the zone ingress credential explicitly. Email Sending onboarding needs Workers Paid; after upgrading, `domain-sync` re-attempts it. For a zone in another Cloudflare account, pipe an API token for that account on standard input:
Project owners see administrator-registered domains in `void email domain list` and `status`; `status` names the `void platform email` command for any step they cannot take themselves, and `sync` and `remove` point them at `domain-sync` and `domain-remove`. A domain an owner registered before you switched to `admin` stays theirs to renew, sync and remove. The runtime token needs the email permissions listed in the [self-hosting guide](/guide/platform/installation/credentials#runtime-token-permissions) for this to work.
@@ -97,7 +99,7 @@ to finish the retained cleanup. If its token has expired or been revoked, provid
97
99
a replacement scoped to the same account and zone:
Set the same two variables before `void platform install` to enable email during a new installation. Void records the pair for later upgrades; an ordinary upgrade cannot replace it.
59
59
60
+
Before installing, enable [Cloudflare Email Routing](https://developers.cloudflare.com/email-service/get-started/route-emails/) for the exact shared sender domain and confirm that its MX records point to Cloudflare. For a subdomain, add that name under the zone's **Email Routing → Settings → Subdomains**. Cloudflare adds the required MX and SPF records. The installer's shared-mail bootstrap verifies those records; it does not add them. Keep existing mail-provider records on other domain names in place.
61
+
60
62
Enabling email lets administrators [register email domains for projects](/guide/platform/administration/email#registering-email-domains-for-projects) and lets projects register destination addresses through the runtime token. That needs **Email Routing Addresses: Edit** and **Email Sending: Edit** on the account, plus **Zone: Read**, **Zone Settings: Edit** and **Email Routing Rules: Edit** on the zones that will carry mail. The runtime-token link preselects them when email is enabled. Email Sending onboarding for arbitrary recipients needs Workers Paid.
61
63
62
-
The installer deploys the email gateway, prepares the shared mail route, and verifies inbound readiness before opening platform traffic. If setup fails, correct the reported permission, mail-zone configuration, or routing conflict, then rerun the same install or upgrade command. A fresh install resumes with `void platform install --resume --name <installation-id>`.
64
+
The installer deploys the email gateway, prepares the shared mail route, and verifies inbound readiness before opening platform traffic. If setup fails, correct the reported permission, exact-domain MX records, or routing conflict, then rerun the same install or upgrade command. A fresh install resumes with `void platform install --resume --name <installation-id>`; it continues the recorded email operation after the configuration is corrected.
Copy file name to clipboardExpand all lines: docs/guide/platform/installation/domains.md
+28Lines changed: 28 additions & 0 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -19,6 +19,8 @@ If nameservers, certificates, or project Zero Trust protection are pending, foll
19
19
20
20
Use `--installation <id>` to select an installation explicitly, `--zone example.com` for an app domain such as `apps.example.com`, or `--dedicated-zone` for catch-all routing on a dedicated zone. Nested domains still need the wildcard certificate described below. This command adds the first domain; replacing an existing application domain is not currently supported. It uses the installed runtime and does not require `--runtime` or an app redeploy.
21
21
22
+
Choose an application domain whose wildcard leaves existing Worker Custom Domains reachable. Existing more-specific routes covering all requests can preserve those hostnames. If Void reports a conflict, choose another application domain; for a new installation, you can start with `void platform install --workers-dev` and add a suitable domain later.
23
+
22
24
Browser login sessions are specific to each origin. Apps using their own OAuth providers may need to register their new callback URLs. Void's built-in auth uses the request origin automatically unless the app overrides that configuration.
23
25
24
26
### What Changes in Testing Mode?
@@ -49,6 +51,32 @@ The management token needs **SSL and Certificates: Read** (or Edit) on that zone
49
51
50
52
:::
51
53
54
+
## Optional Dashboard
55
+
56
+
The API's `/admin/` pages are included in the core installation. You can deploy
57
+
the optional user dashboard separately and configure its HTTPS origin during
58
+
installation with `--dashboard-url https://dash.example.com`.
59
+
60
+
For an existing installation, preview and apply the configuration with:
The origin must contain no credentials, path, query, or fragment. Void saves it
68
+
for login callbacks and keeps it across upgrades and repairs. The command does
69
+
not create a dashboard Worker or DNS records; deploy that app separately. Omit
70
+
the option to keep the saved origin. The dashboard provides sign-in, linked
71
+
login methods, and sign-out; use the CLI for user project and team management.
72
+
73
+
If Access protects the platform, its application must cover this dashboard
74
+
origin too. Configure the origin when installing protection. To change it on an
75
+
already protected platform, deliberately remove protection through authentication
76
+
configuration, apply the origin, then enable protection again. Choose a separate
77
+
admission rule first if signup depends on the Access gate. Maintenance stops if
78
+
the configured origin is outside the active coverage.
79
+
52
80
## Cloudflare footprint
53
81
54
82
New platform resources use deterministic `void-<installation-name>-<role>` names where Cloudflare allows them, such as `void-team-api`. Choose an unused installation name in the account; Void stops on an unowned name conflict instead of replacing that resource. Existing installations keep their recorded names, including older names with suffixes.
0 commit comments