| Purpose | Stored in | Secret name | Value |
|---|---|---|---|
| Runtime mailbox-domain management | Cloudflare kaisoumail-api Worker secret |
CLOUDFLARE_RUNTIME_API_TOKEN |
runtime token |
| Deploy workflow | GitHub repository secret | CLOUDFLARE_DEPLOY_API_TOKEN |
deploy token |
This repository already supports split tokens. No code change is required.
Direct binding from /domains also requires the GitHub repository secret CLOUDFLARE_ACCOUNT_ID. The deploy workflow injects that value into the API Worker runtime variables; it is not a token permission, but without it /api/meta reports cloudflareDomainBindingEnabled=false.
If you only need the fastest single-operator setup for evaluation or a low-risk environment, you can keep one shared token:
kaisoumail-api Worker secret: CLOUDFLARE_API_TOKENCLOUDFLARE_API_TOKENThat shared token must cover both runtime and deploy permissions.
| Surface | Preferred secret | Fallback secret |
|---|---|---|
| API Worker runtime | CLOUDFLARE_RUNTIME_API_TOKEN |
CLOUDFLARE_API_TOKEN |
| Deploy workflow | CLOUDFLARE_DEPLOY_API_TOKEN |
CLOUDFLARE_API_TOKEN |
If split-token secrets and a shared token both exist, the split-token secrets win.
Runtime code calls:
GET /zonesPOST /zonesGET /zones/:zone_idDELETE /zones/:zone_idPOST /zones/:zone_id/email/routing/enablePOST /zones/:zone_id/email/routing/dnsPOST /zones/:zone_id/email/routing/rulesDELETE /zones/:zone_id/email/routing/rules/:rule_idGET /zones/:zone_id/email/routing/rules/catch_allPUT /zones/:zone_id/email/routing/rules/catch_allRequired permissions:
| Permission | Purpose |
|---|---|
Zone: Zone: Edit |
list, validate, create, and delete project-bound zones |
Zone: Email Routing Rules: Edit |
create and delete mailbox routing rules |
Zone: Zone Settings: Edit |
enable Email Routing |
The runtime token scope must cover every zone that KaisouMail should manage.
In Cloudflare's custom token builder, Zone: Zone: Edit already covers the read/list capability needed on the /zones path, so you do not need to add a separate Zone: Zone: Read row.
CLOUDFLARE_RUNTIME_API_TOKEN, with CLOUDFLARE_API_TOKEN as the
shared-token fallback.GET /zones/:zone_id/email/routing/rules/catch_all accepts
Email Routing Rules Read or Email Routing Rules WritePUT /zones/:zone_id/email/routing/rules/catch_all requires
Email Routing Rules WriteZone: Email Routing Rules: Edit, so the
minimum runtime permission set does not grow when catch-all management is
enabled.The deploy flow performs:
wrangler deploywrangler pages deployRequired permissions:
| Permission | Purpose |
|---|---|
Account: D1: Edit |
remote D1 migrations |
Account: Workers Scripts: Edit |
Worker deploy |
Account: Workers R2 Storage: Edit |
validate and bind the R2 bucket |
Account: Cloudflare Pages: Edit |
Pages deploy |
Zone: Workers Routes: Edit |
Worker custom-domain routes |
If you use the shared quickstart token, it must include all of the following:
Zone: Zone: EditZone: Email Routing Rules: EditZone: Zone Settings: EditAccount: D1: EditAccount: Workers Scripts: EditAccount: Workers R2 Storage: EditAccount: Cloudflare Pages: EditZone: Workers Routes: EditAuthentication errorCheck these first:
Zone: Zone Settings: Edit.This usually means the token can read the zone but cannot write the required Email Routing settings for that zone.