Architecture reference
Authentication & Authorization
Your app never handles passwords. Users prove who they are on secureFlows; your app only ever holds a short-lived session token.
This page explains how identity and access work end to end — hosted login, the session token, encrypted per-user storage, API calls, and logout — so you can evaluate the model with confidence before you integrate. For step-by-step HTTP details see the integration walkthrough and hosted login contract.
Why this model is safe
Most breaches in client apps start with credentials or tokens living in the wrong place: a password form you
built yourself, a token in localStorage, or identity taken from a request body the client can forge.
secureFlows is designed so those paths are not part of a correct integration.
End users sign in on secureFlows hosted login. Your product never sees email/password or provider secrets —
only a sessionToken after a successful redirect.
Workspace, user, and app binding are taken from the verified session JWT on the server. Clients must not send “who I am” in JSON bodies for Session API calls.
Token lifetime and data lifetime are separate. The default is durable user data; a
410 on an expired token means “sign in again,” not “your data was deleted.”
Session payloads are encrypted before storage. Workspaces are hard isolation boundaries — another tenant cannot read your ciphertext even with raw database access.
Authentication vs authorization
| Concept | What it answers | In secureFlows |
|---|---|---|
| Authentication | Who is this person? | Firebase Auth on the hosted login page proves identity. secureFlows then mints a session token bound to that user, workspace, and application. |
| Authorization | What may they do now? |
Every Session API request presents Authorization: Bearer <sessionToken>. The API
loads the session from that token and allows only that user’s encrypted record — no cross-user
access by construction.
|
| Admin / console | Who may manage the workspace? | Separate from end-user sessions: owners and admins use Management API user JWTs after console sign-in. End-user apps stay on the Session API path. |
Hosted login & redirect
Hosted login is the browser page on secureFlows where your user authenticates. Your app sends
them there with query parameters that name the workspace, application, and an allowlisted return URL. After
success, secureFlows redirects back to your app with a sessionToken (and optional
state for CSRF binding).
Required query parameters
| Parameter | Purpose |
|---|---|
workspace_name |
Which tenant this login belongs to. |
app_id |
Which registered application is logging the user in (scopes redirect allowlist and session). |
redirect_uri |
Exact callback URL on your origin (typically https://<your-host>/callback). Must match
the application allowlist.
|
state |
Opaque value you generate; returned unchanged so you can bind the round-trip (CSRF defense). |
/app/sessions/login for session apps
/app/login is for console sign-in and a legacy Firebase-token path — not the session-token
integration contract. Session products should always use hosted session login.
Login
On the hosted page the user signs in with Firebase (email/password or configured providers). secureFlows never silently auto-completes a redirect just because another tab was signed in: if a prior identity is restored for this application’s Firebase instance, the user must confirm with an explicit “Continue as …?” step (or choose a different account).
Session token & storage
The sessionToken is a signed JWT that authorizes Session API access for one user in one workspace
for one application. Treat it like a browser session credential:
-
Store it in
sessionStorage, keyed by workspace and app id (for examplesf.token.v2.<workspace>.<appId>) — not inlocalStorage. - Send it only as
Authorization: Bearer <sessionToken>. - Do not decode the JWT on the client for identity; call
GET /api/v1/sessions/identityinstead. - Default token lifetime is on the order of days (commonly 7); when it expires, renew via hosted login — the encrypted user record remains.
localStorage, while the vaulted
user data continues to live on the server.
Session data operations
With a valid bearer token, your app reads and writes the user’s encrypted JSON record through the Session API. Typical operations:
GET /api/v1/sessions— load the payloadPOST /api/v1/sessions/set/{key}/GET …/get/{key}/DELETE …/delete/{key}— per-key updatesGET /api/v1/sessions/identity— display email next to Sign out
Logout
Signing out is a first-party redirect through secureFlows so the session token is invalidated in a controlled
way (and hosted-login cookies can be cleared). Browser apps should use the hosted logout redirect — not only
delete a key from sessionStorage.
The entire flow
Putting it together: provision an application once in the console, then every end-user trip is hosted login →
token in sessionStorage → Session API → optional logout. Your code never becomes a password
store or an identity authority.
Do not collect passwords in your UI, store session tokens in localStorage, trust a user id from
the client body, decode the JWT for “who am I,” or treat HTTP 410 as data loss.
Those patterns undo the safety guarantees above.
Related reading: End-to-end user management, Security infrastructure, System components, Session API.
Your app ships features. secureFlows holds identity and the vault.