Authentication & SSO
How users sign in to nivq — social login, generic OIDC (Keycloak/Okta/Azure AD), per-workspace SSO, a local bootstrap admin, and mapping IdP groups to workspaces and roles.
nivq is its own OAuth2 Authorization Server. Whatever identity provider a user authenticates with, nivq mints its own JWT afterwards — so the API, multi-tenant isolation, and workspace claims behave identically across every login method. The IdP's token is never passed through.
The login page is adaptive: it only renders the methods the deployment actually has
configured (fetched from GET /v1/auth/providers). If that endpoint is unreachable it
falls back to showing the social buttons so login is never a dead end.
Login methods at a glance
| Method | Appears when | Configured in |
|---|---|---|
| Bootstrap admin (local password) | NIVQ_BOOTSTRAP_ADMIN_USERNAME + _PASSWORD set | env |
| Google / Microsoft / GitHub | the matching *_CLIENT_ID / *_CLIENT_SECRET set | env |
| Generic OIDC (Keycloak, Okta, Auth0, Azure AD, …) | OIDC_ISSUER_URI + OIDC_CLIENT_ID + OIDC_CLIENT_SECRET set | env |
| Corporate SSO (email → per-workspace IdP) | at least one enabled workspace SSO config exists | app UI |
All env keys are listed in Configuration → Identity. This guide explains how each method works and how users land in the right workspace with the right role.
Bootstrap admin (local login)
For on-prem demo / trial deployments that can't stand up an IdP, nivq can expose a single local username/password account:
NIVQ_BOOTSTRAP_ADMIN_USERNAME=admin@example.com # must be an email
NIVQ_BOOTSTRAP_ADMIN_PASSWORD=a-long-passphraseWhen both are set, the login page shows an email/password form. On submit the credentials
are posted to the Authorization Server (POST /login/password), which establishes a
session and mints the same JWT the OIDC flow does. The password is BCrypt-hashed in
memory only and never written to the database (the user record has no password column).
A password without a username aborts startup; a password shorter than 12 characters
doesn't block, but logs a warning at boot — use a long passphrase.
Use it as a break-glass account
Treat the bootstrap admin as a first-run / break-glass login: bring nivq up, sign in, configure your real IdP, then clear the two variables (or keep them sealed for IdP outages). Leave them unset in normal production.
Social providers
Set the credentials for any of Google, Microsoft, or GitHub and that button appears.
Microsoft additionally takes MICROSOFT_TENANT. Unconfigured providers (left at the
placeholder) are filtered out and never shown.
Generic OIDC (Keycloak, Okta, Auth0, Azure AD …)
For a single corporate IdP across the whole deployment, point nivq at the issuer:
OIDC_ISSUER_URI=https://keycloak.company.com/realms/company
OIDC_CLIENT_ID=nivq
OIDC_CLIENT_SECRET=...
OIDC_DISPLAY_NAME=Company SSOEndpoints (authorization, token, JWKS) are discovered automatically from
{issuer}/.well-known/openid-configuration. In your IdP, register the redirect URI:
{BACKEND_URL}/login/oauth2/code/oidcAny OIDC-compliant provider works with no code changes.
Per-workspace SSO (email domain → IdP)
nivq also supports per-workspace SSO keyed by email domain — useful when different tenants bring their own IdP. A workspace owner configures it in Workspace Settings → SSO:
emailDomain— e.g.acme.comissuerUri— the tenant's OIDC issuer (discovery-based)clientId/clientSecret— encrypted at rest (AES-256-GCM)
On the login page, a user enters their corporate email; if its domain has an enabled config, they're routed to that tenant's IdP. The same domain can be attached to a workspace so its members all land there (see role mapping below).
Requires the Enterprise SSO feature
Per-workspace SSO and group mappings are gated behind the ENTERPRISE_SSO
plan feature. The generic OIDC button and social login are not.
Roles & auto-join
nivq roles are per workspace: OWNER > ADMIN > MEMBER. A federated user can be a
member of several workspaces, each with a different role, and switches between them in the
app. Two mechanisms place users automatically.
IdP group → role (domain auto-join)
When a user's email domain matches an enabled workspace SSO config, they auto-join that workspace with a role derived from their IdP group claim:
NIVQ_OIDC_GROUPS_CLAIM=groups # claim holding the group names
NIVQ_OIDC_DEFAULT_ROLE=MEMBER # role when no group matches
NIVQ_OIDC_OWNER_GROUPS=nivq-owners
NIVQ_OIDC_ADMIN_GROUPS=nivq-admins
NIVQ_OIDC_MEMBER_GROUPS=nivq-usersPrecedence is OWNER > ADMIN > MEMBER. The role is re-synced on every login, so IdP
group changes propagate. The workspace owner's own membership is never changed by mapping.
Matching is case-insensitive and tolerant of Keycloak path-style groups (/nivq-admins
matches nivq-admins).
IdP group → workspace (UI-managed)
To route users from a single IdP into different — and multiple — workspaces by group, each workspace owner defines rules in Workspace Settings → SSO group mappings:
| IdP group | Role in this workspace |
|---|---|
nivq-sales-admin | ADMIN |
nivq-eng | MEMBER |
At login, a user joins every workspace whose mapping matches one of their groups, with the mapped role. A user in two mapped groups joins two workspaces. When several rules hit one workspace, the highest role wins. Mappings target existing workspaces (they are never auto-created), and are stored per workspace (one tenant's rules can't affect another's).
LDAP / Active Directory
nivq does not connect to LDAP/AD directly — by design, no directory credentials ever reach the platform. The standard pattern is to bridge through an IdP:
NivQ ──(OIDC)──> Keycloak ──(LDAP/AD federation)──> Active Directory / OpenLDAPKeycloak (or AD FS / Entra ID) federates the directory and exposes OIDC; nivq connects via the generic OIDC slot above. Directory groups then drive the role/workspace mappings.
Recommended on-prem setup
- Boot nivq and sign in with the bootstrap admin.
- Configure your IdP — the generic OIDC slot for one corporate IdP, or per-workspace SSO for multi-tenant.
- Create the workspaces your teams need.
- Add group → role (env) and/or group → workspace (UI) mappings.
- Users sign in via the IdP and land in the right workspace(s) with the right role.
- Optionally clear the bootstrap admin variables once SSO is verified.
Result
One IdP login, directory-driven membership: each user automatically sees exactly the workspaces their groups grant, at the role their groups grant — no manual invitations.