bitwarden/server
SCIM provisioning
Active contributors: admin console team.
Purpose
SCIM 2.0 lets enterprise IdPs (Okta, Azure AD, OneLogin, JumpCloud, etc.) push users and groups into a Bitwarden organization automatically. Bitwarden's SCIM endpoint is hosted by the dedicated Scim service and lives under bitwarden_license/src/Scim/. This page focuses on the user-visible feature and how it interacts with the rest of the platform; the apps page covers the host details.
How orgs configure SCIM
- Org admin visits the Settings → SCIM page in the Web Vault.
- Enables SCIM, regenerates the API key, and is shown the SCIM endpoint URL (
https://<scim-host>/v2/<orgId>/) and bearer token. - The IdP is configured with that URL + token.
- From then on, the IdP sends standard SCIM 2.0 requests (
Users,Groups,ServiceProviderConfig,Schemas,ResourceTypes) and Bitwarden mirrors the changes.
The org-side configuration UI lives in src/Api/AdminConsole/Controllers/ScimConfigsController.cs.
Resources mirrored
- Users —
OrganizationUserrows with roleUser(the SCIM provisioning protocol does not assign roles; admins must be promoted in the Web Vault). - Groups —
Grouprows +GroupUsermemberships. - Patches — SCIM 2.0 PATCH requests are translated into the closest Admin Console mutation.
Where the code lives
| Concern | Path |
|---|---|
| Scim host | bitwarden_license/src/Scim/ |
| Per-resource commands | bitwarden_license/src/Scim/Users/{Get,Patch,Post,Put,Delete,Search}/ and bitwarden_license/src/Scim/Groups/... |
| Models | bitwarden_license/src/Scim/Models/{ScimUser, ScimGroup, ScimListResponse, ScimErrorResponse} |
| Domain | src/Core/AdminConsole/OrganizationFeatures/OrganizationUsers/, Groups/ |
| Schema | src/Sql/dbo/Tables/Group.sql, OrganizationUser.sql, Organization.sql (UseScim) |
How it works
sequenceDiagram
participant IdP
participant Scim
participant Core as Core domain
participant Db
IdP->>Scim: PUT /v2/{orgId}/Users/{id} (SCIM JSON, Bearer token)
Scim->>Scim: ScimContextMiddleware → orgId + auth
Scim->>Core: PutUserCommand → IOrganizationUserCommands.SaveAsync
Core->>Db: Update OrganizationUser, Group memberships
Scim-->>IdP: 200 OK SCIM JSONEach command is small and named after the SCIM verb (PostUserCommand, PutUserCommand, PatchUserCommand, DeleteUserCommand, GetUsersListQuery, GetUserQuery, etc.) so the routing is fully explicit.
Group membership semantics
- A SCIM
GroupPATCH that adds a user →GroupUserinsert +IPushNotificationService.PushSyncOrganizationsfor the affected user (so their client refreshes collection access). - A SCIM
GroupPATCH that removes a user →GroupUserdelete + push. - Bumping
Group.RevisionDateon access changes (PR #7467, 2026-04-04) means clients reliably see the new permissions on next sync.
Authentication
The SCIM bearer token is a long-lived ApiClient minted by the cloud control plane. The token is verified by the standard JWT pipeline; ScimContextMiddleware then ensures the URL {orgId} matches the token's claim. Mismatches return 403.
Rate limits
bitwarden_license/src/Scim/Startup.cs reuses the cloud rate-limit middleware. SCIM endpoints have a more-permissive bucket because IdPs sometimes burst hundreds of operations on a single sync.
Self-host
Self-host customers with the relevant license tier can run SCIM. The bundled stack maps /scim/* to the Scim container.
Entry points for modification
- New SCIM attribute → extend
ScimUser/ScimGroup, the JSON converters inUtilities/, and the corresponding command. - Different bulk semantics → SCIM PATCH bodies are JSON-Patch-ish; the parser lives in
bitwarden_license/src/Scim/Utilities/and is the most common place changes are needed. - Per-IdP quirks → handle with optional behaviour flags on
OrganizationConnection/SCIM config; do not branch onUser-Agent.
For the host overview see apps/scim.
Built by Factory AutoWiki from public repository content. It is a generated preview for codebase exploration, not source-maintained documentation.