API Reference
Registration
API endpoints for registering a WebAuthn passkey credential.
The registration flow allows an authenticated user to associate a new passkey with their account. It consists of two endpoints.
Both registration endpoints require authentication. Include an
Authorization: Bearer <token> header in every request.Get registration options
Generate a WebAuthn challenge and credential creation options for the client.
POST /api/passkeys/register/options
Headers
| Header | Value |
|---|---|
Authorization | Bearer <token> |
Content-Type | application/json |
Request body
| Field | Type | Required | Description |
|---|---|---|---|
app_name | string | Yes | Display name of your application (shown in the authenticator UI) |
app_url | string | Yes | Full URL of your application (used to extract the rpId) |
Request
{
"app_name": "My Application",
"app_url": "https://example.com"
}
Response — WebAuthn PublicKeyCredentialCreationOptions
Response
{
"challenge": "base64url-encoded-random-challenge",
"rp": {
"name": "My Application",
"id": "example.com"
},
"user": {
"id": "base64-encoded-user-id",
"name": "user@example.com",
"displayName": "John Doe"
},
"pubKeyCredParams": [
{ "type": "public-key", "alg": -7 },
{ "type": "public-key", "alg": -257 }
],
"timeout": 60000,
"attestation": "none",
"authenticatorSelection": {
"residentKey": "preferred",
"userVerification": "preferred"
}
}
The alg values correspond to:
-7— ES256 (ECDSA with SHA-256, Elliptic Curve P-256)-257— RS256 (RSASSA-PKCS1-v1_5 with SHA-256)
Register a passkey
Submit the credential created by the browser to store the passkey in the database.
POST /api/passkeys/register
Headers
| Header | Value |
|---|---|
Authorization | Bearer <token> |
Content-Type | application/json |
Request body
| Field | Type | Required | Description |
|---|---|---|---|
label | string | No | Human-readable name for this passkey (e.g. "MacBook Touch ID") |
id | string | Yes | Base64url-encoded credential ID from PublicKeyCredential.id |
rawId | string | Yes | Base64-encoded raw credential ID from PublicKeyCredential.rawId |
type | string | Yes | Must be "public-key" |
response.clientDataJSON | string | Yes | Base64-encoded client data JSON |
response.attestationObject | string | Yes | Base64-encoded attestation object |
Request
{
"label": "MacBook Touch ID",
"id": "credential-id-base64url",
"rawId": "credential-id-base64",
"type": "public-key",
"response": {
"clientDataJSON": "base64-encoded-client-data-json",
"attestationObject": "base64-encoded-attestation-object"
}
}
Response — 200 OK with the created passkey resource
Response
{
"passkey": {
"id": 1,
"label": "MacBook Touch ID",
"credential_id": "base64-encoded-credential-id",
"created_at": "2024-01-15T10:30:00.000000Z"
}
}
The
challenge and public_key fields are stored in the database but not returned in the response for security reasons.