audit PK: id 8 required 3 unique

Description

Tracks active authentication sessions for users, including JWT tokens issued by Supabase Auth after login via email/password, BankID, or Vipps. Sessions include auth provider metadata, expiry timestamps, and are referenced during biometric re-authentication.

18
Attributes
7
Indexes
8
Validation Rules
20
CRUD Operations

Data Structure

Name Type Description Constraints
id uuid Primary key — unique session identifier, generated on session creation by Supabase Auth
PKrequiredunique
user_id uuid Foreign key referencing users.id — the authenticated user this session belongs to
required
token text JWT access token issued by Supabase Auth. Contains sub (user_id), role, org_id claims. Stored encrypted at rest. Never logged or exposed in API responses.
requiredunique
refresh_token text Opaque refresh token used to obtain a new JWT without re-authentication. Rotated on every use. Stored in Flutter Secure Storage on device, reference hash kept server-side.
unique
auth_provider enum The authentication method used to create this session
required
created_at datetime UTC timestamp when the session was created. Used for audit trails and session age calculations.
required
expires_at datetime UTC timestamp when the JWT access token expires. Default: created_at + 1 hour (Supabase default). Extended sessions for biometric flows may use longer TTL.
required
is_active boolean Whether this session is currently valid and usable. Set to false on logout, token revocation, password change, or admin revocation. Does not auto-update on expiry — use expires_at for expiry checks.
required
device_id string Stable device identifier (e.g., Flutter device_info platform ID). Used to correlate sessions per device and limit concurrent active sessions per device.
-
device_name string Human-readable device label (e.g., 'iPhone 15 Pro'). Displayed in active session management UI for user transparency.
-
ip_address string IP address of the client at session creation time. Used for anomaly detection and audit logging. IPv4 or IPv6.
-
user_agent text HTTP User-Agent string from the initial authentication request. Useful for audit and fraud detection.
-
revoked_at datetime UTC timestamp when the session was explicitly revoked (logout, admin action, password reset). Null if session expired naturally or is still active.
-
revocation_reason enum Reason the session was revoked, for audit purposes
-
last_used_at datetime UTC timestamp of the most recent authenticated request using this session token. Updated on each API call. Used to detect and clean up idle sessions.
-
is_biometric_session boolean True if this session was initiated or re-authenticated via biometric (Face ID / fingerprint) without a full BankID/Vipps re-flow. Used to determine whether sensitive operations require step-up authentication.
required
bankid_token_claims json Parsed BankID ID token claims (e.g., sub, pid, acr) stored at session creation for audit and compliance. Only populated when auth_provider = 'bankid'. PII — restricted access via RLS.
-
vipps_token_claims json Parsed Vipps ID token claims (e.g., sub, phone_number, nnin) stored at session creation. Only populated when auth_provider = 'vipps'. PII — restricted access via RLS.
-

Database Indexes

idx_auth_sessions_user_id
btree

Columns: user_id

idx_auth_sessions_user_active
btree

Columns: user_id, is_active

idx_auth_sessions_token
btree unique

Columns: token

idx_auth_sessions_refresh_token
btree unique

Columns: refresh_token

idx_auth_sessions_expires_at
btree

Columns: expires_at

idx_auth_sessions_provider
btree

Columns: auth_provider

idx_auth_sessions_device_id
btree

Columns: user_id, device_id

Validation Rules

token_format_valid error

Validation failed

expires_at_future_on_create error

Validation failed

user_id_references_existing_user error

Validation failed

auth_provider_claim_consistency error

Validation failed

revocation_fields_consistent error

Validation failed

device_id_format warning

Validation failed

last_used_at_not_in_future error

Validation failed

rls_self_read_only error

Validation failed

Business Rules

single_active_session_per_device
on_create

A user may not have more than one active session per device_id. On new login from the same device, the existing session for that device must be revoked (revoked_at set, is_active = false) before the new session is created.

biometric_session_requires_prior_full_auth
on_create

A session with is_biometric_session = true can only be created if the user has a prior non-biometric session (auth_provider in ['email_password', 'bankid', 'vipps']) that was created on the same device_id within the biometric enrollment window. Prevents biometric sessions from being bootstrapped without a full auth flow.

session_revoked_on_password_reset
on_update

All active sessions for a user must be revoked when a password reset is completed. Prevents stolen session tokens from remaining valid after a security event.

step_up_required_for_sensitive_operations
always

Sessions where is_biometric_session = true are not permitted to perform sensitive operations (e.g., viewing BankID/Vipps claims, initiating encrypted assignment decryption, modifying payment details) without a step-up re-authentication via BankID or Vipps. The consuming component must check this flag before proceeding.

bankid_vipps_claims_immutable
on_update

bankid_token_claims and vipps_token_claims are write-once fields set at session creation and must never be updated. These are audit records of what the identity provider attested at login time.

max_concurrent_active_sessions
on_create

A user may not have more than 5 concurrent active sessions across all devices. If this limit is reached, the oldest active session (by created_at) is automatically revoked before the new one is created.

admin_session_revocation
on_update

Administrators may revoke any user's session via Admin Portal. Revocation sets is_active = false, revoked_at = now(), revocation_reason = 'admin_revocation'. The affected user's next request will receive a 401 and must re-authenticate.

refresh_token_rotation
on_update

Refresh tokens are single-use. When a refresh token is exchanged for a new JWT, the old refresh_token value is immediately invalidated (set to null or replaced) and a new token is stored. Reuse of a revoked refresh token triggers immediate full session revocation (security event).

Storage Configuration

Storage Type
primary_table
Location
main_db
Partitioning
by_date
Retention
archive_after_1year

Entity Relationships

users
incoming one_to_many

A user may have multiple active sessions across different devices and auth providers

optional cascade delete