What is a session?

Such actions can be divided into two buckets:
  • Read operations: Retrieving data (e.g., viewing wallet balances)
  • Write operations: Modifying data or performing sensitive actions (e.g., signing transactions)

How can I create a session?

Read-only sessions

In terms of end-user experience, a read-only session might make sense in low-touch applications where users are primarily reading data (think viewing wallets and their balances). As for implementation, there are a few ways a developer can achieve read-only access on behalf of a user. Note: an end-user (sub-organization) falls hierarchically under the developer (parent-organization).

Parent organization access

By default, a parent organization has read access to all of its sub-organizations’ data. This means you can set up a federated model where the client makes requests to a backend (containing the parent organization’s API key credentials), the backend populates the requested data, and returns it back to the client. From an implementation perspective, each read request (i.e. get or list) requires an organizationId parameter. Populate that field with the sub-organization’s ID in order to get its data.

Client side access

Separately, if you would like the client to have all read requests encapsulated (instead of reading data via a proxy like in the previous approach), the client can initiate a read-only session via a CreateReadOnlySession activity. This activity returns a session string that, if passed into an HTTP request via X-Session header, gives permission to perform reads. Note that because this is an activity performed by an end-user, it requires authentication (e.g. via passkey). If you’d like to do this via our SDK abstractions, you can leverage the login1 method, which creates a CreateReadOnlySession activity under the hood. It stores the resulting session string in Local Storage2, and subsequent requests to fetch data from Turnkey injects the session stored here at call time3 within @turnkey/sdk-browser.

Read-write sessions

In contrast to read-only sessions, a read-write session makes sense when a user would like to make several authenticated write requests in a window of time. There are a few ways to achieve this:

Creating a read-write session

There are several mechanisms to obtain read-write sessions: OTP, OAuth, Passkey sessions, and Session refreshing
Read-write sessions
Our SDK contains several abstractions that manage authentication. You can checkout all of our examples leveraging these examples here

Mechanisms

There are two primary mechanisms we offer that provide client side key generation and signing to support read-write sessions.

IndexedDB (web only):

For web apps that want stronger session persistence without relying on iframes or exposing credentials to your app’s JavaScript runtime, Turnkey supports using the SubtleCrypto API to generate unextractable asymmetric key pairs and store them securely in the browser’s IndexedDB. This approach enables long-lived, client-held sessions that survive page reloads, tab closures, and even browser restarts – without ever exposing the private key to your JavaScript code. Turnkey’s SDK provides helpers to:
  • Create a new session by generating a P-256 key pair via crypto.subtle.generateKey()
  • Sign requests
  • Store and retrieve the key using IndexedDB under a given session ID
  • Abstractions built on top of the IndexedDBStamper that simplify authentication flows
This is currently the most persistent session model for modern browsers that support WebCrypto. It is especially valuable in Progressive Web App (PWA) contexts or when iframe and Local Storage approaches are insufficient. To see a full working example, check out our IndexedDB SDK example. Or our Web demo application that leverages abstractions such as the IndexedDbClient for full end-to-end authentication flows.

SecureStorage (mobile only)

Secure Storage operates essentially the same as IndexedDB with respect to authentication flows for Turnkey except it is mobile native and keys are generated using @turnkey/crypto rather than WebCrypto.

LocalStorage:

Another option is to create an API key and store it directly within Local Storage. However, this is a riskier setup than IndexedDb/SecureStorage as anyone who is able to access this client-side API key has full access to a User.

Sessions FAQ