Server SDK Quickstart
The Server SDK handles the server-side steps of the Relay flow. It abstracts away Privacy Pass cryptography and handles retries automatically.
Installation
npm
yarn
Setup
Relay methods are available on the persona.relays namespace.
Creating a Relay session
Call persona.relays.create() before rendering the widget. This returns a session access token to pass to your frontend, along with a relayToken and relaySecret that you must store securely on your server — never expose these to the client.
Recommended: Encrypt your claim payload
We recommend generating an asymmetric key pair so that the claim payload is encrypted and only decryptable by your server.
Once your frontend has the access token, initialize the widget and wait for onComplete before proceeding. See Widget usage.
Issuing a Privacy Pass
A Privacy Pass is the billing unit for Relay — it is billed on creation and is what gets redeemed to fetch the claim result. Since issuance uses your API key, Persona knows your platform identity at this point for billing purposes. Redemption remains fully anonymous — Persona does not know who redeems the claim. Each Privacy Pass can only be redeemed once, so we recommend storing the privacyPassToken on your end and mapping it to the corresponding relay.
persona.relays.issuePrivacyPass requires a relay to exist — the challenge is obtained through the relay’s endpoint — but can be called at any point after relay creation and before redemption. Issuing immediately after creating the relay, before the widget completes, is recommended: it makes it harder for Persona to correlate your platform identity to a relay via timing. One Privacy Pass must exist before you can redeem any relay.
This step requires your Persona API key — you can find it in the Persona Dashboard under API Keys.
Redeeming the claim
onComplete should trigger a call to your server to run the following steps. The SDK handles the full blind RSA protocol internally.
The Privacy Pass is redeemed only on a successful claim. Since each pass can only be redeemed once, retrying a successful request with the same already-spent token — for example, after a network drop where your server never received the response — would normally result in a double-spend error. Idempotency is handled automatically by the SDK.
Parsing the claim payload
If you opted out of encryption (encryptionKeyPem: null), parse claimPayload directly:
If you provided an encryptionKeyPem, decrypt the payload with your private key first:
See the claim payload schema for the full type definition.

