Skip to main content
This guide builds a browser app that signs users in with Ave and receives an AES-256 key for encrypting their data on the client. It takes a registered app, one scope, and two SDK calls.

Register your app

1

Create the app

Go to devs.aveid.net and create an app. You get a client ID, which is safe to ship in browser code, and a client secret, which only belongs on a server. Browser and mobile apps use PKCE and never need the secret.
2

Register your callback URL

Add the exact URL Ave should return users to, such as https://yourapp.com/callback. It must match character for character, including any trailing slash.Turn on development mode to allow localhost, loopback, and Expo Go callbacks on any port while you build. Production callbacks must still be listed explicitly.
3

Choose the encryption mode

Encryption is requested per sign-in with a scope, so there is nothing else to configure in the portal:This guide uses e2ee:symmetric. See End-to-end encryption for the asymmetric mode.

Install the SDK

Sign in and receive the key

Start sign-in from a button. startPkceLogin generates the PKCE verifier, state, and nonce, stores them in sessionStorage, and redirects to Ave.
On the callback page, completeOAuthCallback checks state, exchanges the code, verifies the returned JWTs, reads the key from the URL fragment, removes it from the address bar, and saves everything in an AveSession.
On later page loads, call await session.hydrate() before reading tokens or the key.
The key is delivered in the callback URL fragment (#app_key=...). Browsers never send fragments to servers, so the key does not pass through Ave’s token endpoint or your backend.
createLocalStorageAdapter() keeps tokens and the key in localStorage, where any script on your origin can read them. It is the simplest option; Ave Session covers memory-only and custom storage.

Encrypt data on the client

Import the key into Web Crypto and use AES-GCM with a fresh 12-byte IV for every message.
Store the IV next to the ciphertext. Your backend only ever sees these two values. The same user receives the same key every time they sign in to your app, on any device where their Ave account is unlocked. A different identity receives a different key.

Authenticate API requests

Send the id_token to your backend and verify it there. Its audience is your client ID, and sub is the stable identity ID to key rows by.
getValidIdToken() refreshes tokens before they expire when you requested offline_access, and saves the rotated refresh token.

Errors

The client ID or client secret does not match a registered app.
The authorization code or refresh token is invalid, expired, or already used. Codes are single-use and short-lived, so exchange them as soon as the callback loads.
A required field is missing, most often the PKCE verifier.
A standard scope is not in your app’s allowlist, or the request asked for more than one encryption mode.

Next steps

End-to-end encryption

Asymmetric keys, encrypting for other users, and key rotation.

Encryption model

How keys are wrapped, unlocked, and delivered.

Ave Session

Storage choices, refresh, and framework adapters.

OAuth details

Token payloads, manual PKCE, and validation steps.
Last modified on September 28, 2026