Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .prettierignore
Original file line number Diff line number Diff line change
Expand Up @@ -17,3 +17,4 @@ vendor
code-examples/sdk/typescript/src/**/*.hbs
**/.dart_tool
**/*.jsonc
.claude/
35 changes: 35 additions & 0 deletions docs/kratos/passwordless/08_deviceauthn.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ title: Device binding
sidebar_label: Device binding
---

import Mermaid from "@site/src/theme/Mermaid"

Device Authentication (also known as 'DeviceAuthn', or device binding) is a way for a user to authenticate with a hardware
resident private key.

Expand Down Expand Up @@ -797,6 +799,22 @@ And the Flutter code gets this result back: `iOS 26.2.1` (for example).

At this point the key is enrolled for the identity.

<Mermaid
chart={`
sequenceDiagram
participant C as Client (mobile app)
participant H as Device hardware (TEE/TPM)
participant S as Kratos server
C->>S: POST /self-service/settings/api (xSessionToken)
S-->>C: 200 settings flow {nonce, existing_keys}
C->>H: generateKey(nonce)
H-->>C: {client_key_id, cert_chain}
C->>S: PUT /self-service/settings?flow=... {method: deviceauthn, add: {device_name, client_key_id, cert_chain or attestation_ios}}
Note over S: Verify cert chain vs Apple/Google root CAs<br/>Check CRLs<br/>Match challenge to stored nonce<br/>Reject software/emulated keys<br/>Store pubkey, erase challenge
S-->>C: 200 updated settings flow
`}
/>

### Proof of device enrollment

1. When the user creates the login flow with the DeviceAuthn strategy, the client receives a server challenge.
Expand All @@ -809,6 +827,23 @@ At this point the key is enrolled for the identity.
1. Erases the challenge value in the database to prevent re-use.
1. Replies with 200 with a fresh session token and a higher AAL e.g. AAL2 or AAL3

<Mermaid
chart={`
sequenceDiagram
participant C as Client (mobile app)
participant H as Device hardware (TEE/TPM)
participant S as Kratos server
C->>S: POST /self-service/login/api {aal: aal2, refresh: false}
S-->>C: 200 login flow {nonce}
C->>H: sign(nonce, client_key_id)
Note right of H: biometric/PIN prompt<br/>private key never leaves hardware
H-->>C: ECDSA signature
C->>S: PUT /self-service/login?flow=... {method: deviceauthn,<br/>client_key_id, signature}
Note over S: Verify signature with stored pubkey<br/>Check no CA in chain is revoked<br/>Erase challenge
S-->>C: 200 {session_token, aal: aal2}
`}
/>

### Key Revocation

- The user can revoke a key themselves (e.g. because the device is stolen, lost, broken, etc) using the settings flow. This action
Expand Down
Loading