`POST /auth/webauthn/start` — begin a passkey / security-key sign-in (`rh-kk6vbu`). Anonymous; the server runs Cognito's `USER_AUTH` flow with `PREFERRED_CHALLENGE=WEB_AUTHN` on the org's app client.
/auth/webauthn/startEvery "no challenge" outcome — no key registered, unknown user, unknown org —
is one 400 with one sentence, so this is no better an account oracle than
the pool's preventUserExistenceErrors already allows.
Json only, like /auth/session and for the same login-CSRF reason: a form
post is a 415 before the handler runs.
Request Body
application/json
TypeScript Definitions
Use the request body type in TypeScript.
POST /auth/webauthn/start's body.
Response Body
application/json
curl -X POST "https://example.com/auth/webauthn/start" \ -H "Content-Type: application/json" \ -d '{ "email": "string", "slug": "string" }'{ "credential_request_options": "string", "session": "string"}`POST /auth/webauthn/finish` — answer the challenge with the browser's assertion and, on success, issue the session exactly as `/auth/session` does ([`establish_session`]) minus the MFA gate: a user-verified WebAuthn sign-in is the strong factor. POST
All four of `/auth/session`'s login-CSRF controls apply unchanged — `Json` only, no CORS layer, the `Sec-Fetch-Site` CSRF layer and `__Host-` cookies — and the tokens are minted server-side, so a caller cannot choose them.
`POST /billing/setup-intent` — start adding a card. **Owner-only** (financial root-of-trust). Provisions the org's Stripe customer on first use, then returns a SetupIntent `client_secret` the browser confirms with Stripe Elements (the card is vaulted + attached client-side; raw card never touches us). POST
Next Page