OpenE2EE

Backend identity contracts

Keep existing authentication while issuing Relay-specific assertions.

Reviewed: 2026-10-22.

Your application can retain its existing authentication. Its backend verifies the session or intended API token, checks current member eligibility, and issues the Relay-specific ES256 assertion. A provider token does not grant Relay account-management authority.

Evidence levels

The Better Auth recipe has a local real-provider test path and an explicit actual-Relay verifier path. Their recorded results must accompany acceptance. They do not prove a hosted provider deployment.

The other rows below describe backend contracts from primary provider documentation. They are not tested vendor adapters or native Relay profiles. Hosted acceptance remains unverified for every row.

Existing loginBackend verificationStable mapping and standingEvidence
Better AuthActual server auth.api.getSession with the cookie cache disabled.Stateful session revocation plus current application membership in a server-selected tenant.Local recipe tests; hosted unverified.
WorkOS AuthKitSupported sealed-session helper and its authentication result.Map the verified user in the intended Organization. Check current application membership; cached role claims alone are insufficient.Documented contract; hosted unverified.
Auth0Current server Auth0Client.getSession; validate intended API tokens when that is the application's contract.Qualify the immutable provider subject by issuer/tenant, then check current application membership.Documented contract; hosted unverified.
Supabase AuthSupported server verification; use getUser when current user data is needed. Do not authorize from embedded getSession user data.Map the verified user to the application tenant. Check current standing separately. getUser alone does not guarantee immediate session revocation.Documented contract; hosted unverified.
Amazon CognitoSupported verifier checks issuer, expiry, token_use, and the applicable access client_id or ID-token aud.Qualify the user by pool/issuer. Check current application membership and disablement policy.Documented contract; hosted unverified.
Microsoft Entra IDValidate the exact API audience, intended tenant, and actor.A tenant-qualified user mapping must distinguish users from service principals. tid or oid possession alone grants no membership.Documented contract; hosted unverified.
OktaSupported backend verifier with the intended issuer and API audience.Qualify the subject by issuer. Check current application eligibility.Documented contract; hosted unverified.
KeycloakSupported backend verification or confidential-client introspection under the application's policy.Qualify the subject by realm/issuer and intended audience. Check current application eligibility.Documented contract; hosted unverified.

Do not forward an ordinary ID token, API access token, or arbitrary JWKS URL as a Relay assertion. The configured custom-token profile accepts its exact issuer, audience, algorithm, subject claim, and public keys.

Own the member mapping

Assign an opaque, immutable, non-reassigned local member ID. The Better Auth broker signs JSON.stringify([tenantId, memberId]) under its configured issuer. This encoding qualifies the subject by tenant and preserves delimiter boundaries. Preserve the tuple and encoding for existing accounts. Never use a matching email as proof that two provider accounts belong to one member.

Link multiple providers only after authenticating both accounts and checking application authorization. Preserve the application member ID when a phone number, username, display name, or login provider changes. Refuse tenant substitutions. Deny guest issuance unless an explicit supported member policy covers those guests.

A verified session identifies the caller. Your current membership store decides eligibility. Select the tenant from trusted application routing or server configuration. Do not let a body field choose a different tenant, signing profile, or member.

Own assurance and keys

Each provider path must identify the actual authentication event that supports recent or step-up assurance. A refreshed token, session extension, or cached claim cannot supply missing authentication evidence. If the backend lacks that evidence, refuse the requested assurance.

Keep the Relay assertion signing key separate from provider credentials, device authentication keys, and Signal identity keys. Retain verification-key overlap for outstanding assertions and clock tolerance. Test key removal before rollout. Key removal does not revoke existing Relay device proofs.

Loss of membership and provider events

Refuse new assertions when the authoritative session or application membership is no longer valid. Existing devices require a supported privileged lifecycle operation to stop identified access. Recovery replaces encryption identity and is not a disable operation. A sender identity cannot cancel anonymous capabilities that do not contain it.

The customer lifecycle procedure awaits the supported backend and CLI surface. This issuance recipe does not expose private controls or service credentials. Customer suspension/resume acceptance remains open.

This recipe includes no provider event adapter. Before adding one, specify signature verification, issuer/tenant binding, event ordering, deduplication, exact member mapping, retries, and reconciliation. Do not infer current standing from delivery order or an event's absence. Preserve the exact unresolved lifecycle attempt across a lost response.

Application acceptance

  1. Verify two different members receive distinct Relay bindings.
  2. Verify repeat authentication preserves one member's binding.
  3. Refuse missing, expired, revoked, disabled, and foreign-tenant sessions.
  4. Verify a retained session-cache cookie cannot bypass revocation.
  5. Refuse recovery assurance without actual authentication evidence.
  6. Verify phone and username changes preserve the member mapping.
  7. Test encrypted exchange between real devices before rollout.
  8. Complete customer lifecycle acceptance when its supported surface exists.

The SDK package does not include these provider adapters or their dependencies. Use supported provider libraries on your backend. The application remains responsible for its membership, authentication evidence, signing keys, and deprovisioning policy.

On this page