Mint a fresh set of recovery codes
Recovery codes are the fallback that gets you back in when your passkey is unavailable. You can mint a fresh set yourself, and there are two things to understand before you do, because both are irreversible in the moment.
Regenerating destroys the old set, and shows the new one once
Minting a fresh set invalidates every previous code for your address immediately. There is no overlap period and no way to keep the old set working alongside the new one.
The new codes are returned once, for one-time display. They are not stored in a form that can be shown again and there is no route that will return them a second time. If you close that view without capturing them, the outcome is not “look them up later”: it is that you have invalidated your old codes and hold none.
So capture them before you dismiss the view, and put them where you keep your other break-glass material rather than where you keep your passwords.
You can only regenerate your own
The route identifies you the same way every other authenticated route does, then scopes the regeneration to your own verified email address. There is no parameter for whose codes to mint, so an owner cannot regenerate a colleague’s set on their behalf, and nobody can regenerate yours.
If a colleague has lost both their passkey and their codes, this route is not the answer for them; that is an account-recovery conversation, not a regeneration.
A break-glass token cannot regenerate a set
Signing in with the bare break-glass token and asking for fresh recovery codes is refused, and the reason is worth stating because the refusal looks arbitrary.
Recovery codes are a per-user credential, scoped to an email address. The break-glass token is not a per-email identity: it has no address to scope a set to. Beyond that, the token is the credential you are meant to be disposing of in a recovery, not one that holds recovery codes of its own.
The refusal says so in the response: recovery codes are per-user, so sign in as a user, by passkey or through Cloudflare Access, to regenerate.
Every way the request is refused
Not signed in. A 401. Nothing about your codes changed.
Signed in with no user identity. A 403 with the per-user explanation above. This is the break-glass token case.
A fresh identity check is needed. Regenerating is a sensitive action, so it asks for step-up re-authentication first. Approve the prompt and it proceeds. See step-up re-authentication.
The request did not come from the console. A 403 on the origin check. Regeneration is a mutating request that can be carried by a session cookie, so it is origin-gated like every other mutating route.
Too many attempts. The authentication rate limit applies here as it does to signing in, so a burst of attempts is throttled rather than served.
In each case no codes are minted and none are invalidated. A refused regeneration leaves your existing set working, which is the safe direction: the failure mode to avoid is one that destroys the old set without delivering a new one.
Where this fits
- Session management covers the sessions a passkey sign-in creates.
- Step-up re-authentication covers the fresh-proof requirement this route sits behind.
- Offboarding and exit covers what to do with a departing user’s credentials, which is a different question from regenerating your own.
- The key ceremony and recovery kit covers the break-glass material these codes sit alongside.
Last updated .