This feature allows users to enroll passkeys after they have successfully logged into the application using traditional authentication methods.

Overview

The enrollment process consists of two main components:
  1. Step 1: Obtain your Private Key
  2. Step 2: Build an endpoint for JWT token generation
  3. Step 3: Passkey enrollment via OwnID SDK

Step 1 - Obtaining the Private Key

To generate the required RSA private key for JWT signing, follow these steps in the OwnID Console:
1

Navigate to Security Settings

In your OwnID Console, go to Integration > Security section for your application.
2

Generate Signing Key

Under the Signing Key section, click the “Generate a new key” button.
Generating a new RSA key pair will immediately invalidate any existing key. All requests currently using the old key will begin to return errors.
3

Confirm Key Generation

A confirmation dialog will appear warning about key invalidation. Click “Continue” to proceed with generating the new key pair.
4

Copy Private Key

Once generated, a modal will display your new RSA private key. Copy the entire private key including the -----BEGIN RSA PRIVATE KEY----- and -----END RSA PRIVATE KEY----- markers.
This is the only time you’ll be able to view the private key. Store it securely!

Step 2 - Backend Implementation

Implement a backend endpoint to generate a signed JWT enrollment token that authorizes the passkey enrollment session.
const createPasskeyEnrollmentToken = (userEmail, issuer) => {
  const now = Date.now();
  const iat = Math.floor(now / 1000);
  const exp = iat + 900; // 15 minutes
  const sessionExp = iat + 300; // 5 minutes for authorization_details

  const payload = {
    jti: require('crypto').randomUUID(),
    iat: iat,
    exp: exp,
    iss: `https://${issuer}`,
    aud: `https://${issuer}`,
    sub: `Email:${userEmail}`,
    authorization_details: [
      {
        type: "sessionCreation",
        iat: iat,
        exp: sessionExp
      }
    ]
  };

  const enrollmentToken = jwt.sign(payload, ownidSecretRSA, {
    algorithm: 'RS256',
    keyid: issuer
  });
  return { enrollmentToken };
}
JWT Payload Structure
jti
string
required
Unique token identifier
iat
number
required
Token issued at timestamp (Unix timestamp)
exp
number
required
Token expiration timestamp (15 minutes from iat)
iss
string
required
Issuer (website URL)
aud
string
required
Audience (same as issuer)
sub
string
required
Subject (user email with “Email:” prefix)
authorization_details
array
required
Session creation authorization details

Step 3 - Frontend Implementation

  • Ensure OwnID SDK is properly initialized with your application’s configuration before calling the enrollment function.
  • We recommend you to trigger the Passkeys enrollment UI on the next page load after login.
The frontend initiates passkey enrollment after obtaining the enrollment token:
const req = await this.authService.getPasskeyEnrollmentToken();
window.ownid('enrollCredential', req.enrollmentToken);
The UI is automatically managed by OwnID, both on mobile and desktop devices.

Next Steps

Ready to deploy?