Skip to main content

RFC-065: SCIM Provisioning and Namespace Directory Bindings

Summary

This RFC defines how SCIM provisioning and directory synchronization integrate with Prism without allowing external provisioning systems to mutate authorization state unsafely.

The central rule is:

SCIM providers provision provider-scoped directory objects first; namespace authorization bindings are managed as explicit Prism relationships on top of that directory state.

This separation prevents one provider or namespace from accidentally rewriting another provider's identities or global authorization model.

Motivation

Enterprise deployment requires automated lifecycle management for:

  • users
  • groups
  • deprovisioning
  • membership updates

The original RFC-063 draft mapped SCIM operations directly onto Topaz authorization state. That is too blunt. Provisioning and authorization are related, but they are not the same thing.

Prism needs:

  • provider-scoped identity ingestion
  • idempotent sync semantics
  • conflict handling
  • safe namespace bindings
  • auditable rollback behavior

Goals

  1. Define provider-scoped SCIM ingestion.
  2. Separate identity sync from namespace authorization grants.
  3. Define deprovisioning semantics that avoid cross-tenant blast radius.
  4. Define idempotent reconciliation behavior.
  5. Provide a safe model for mapping SCIM groups into Topaz relationships.

Non-Goals

  • Replacing Topaz
  • Automatically granting namespace access to every provisioned group
  • Cross-provider identity linking
  • Designing Prism as a full HR or IAM system

Decision

1. SCIM Writes Into a Provider-Scoped Directory Layer

Every SCIM provider is assigned a provider identity such as:

  • scim:okta-enterprise
  • scim:azuread-corp

Provisioned users and groups are stored as provider-scoped objects, for example:

  • user:scim:okta-enterprise:2819c223-7f76-453a-919d-413861904646
  • group:scim:okta-enterprise:platform-engineering

SCIM MUST NOT directly create namespace grants merely by creating a user or group.

SCIM object identity is based on the provider-scoped SCIM resource identifier, not on a derived login subject.

If Prism also maintains a canonical login subject from RFC-064, that relationship MUST be represented as an explicit binding between the provider-scoped SCIM object and the canonical Prism subject.

2. Namespace Bindings Are Separate Objects

Namespace access is expressed through explicit Prism relationships such as:

  • group:scim:okta-enterprise:platform-engineering -> writer -> namespace:digital-twin-prod
  • group:scim:azuread-corp:platform-admins -> admin -> namespace:shared-control

This allows:

  • multiple providers to coexist
  • groups with the same display name from different providers
  • namespace authorization to be audited independently from provisioning events

3. Deprovisioning Disables Identity, Then Reconciles Bindings

When a user is deprovisioned:

  1. the provider-scoped identity is marked inactive
  2. direct subject bindings are removed or suspended
  3. derived access from group membership is removed through reconciliation
  4. the event is fully audit logged

Deletion MUST be handled as a lifecycle transition, not an unsafe immediate hard-delete of shared authorization state.

Architecture

SCIM Separation Model

SCIM Provider

│ Users / Groups / Memberships

Provider-Scoped Directory Layer

├─ identities
├─ groups
└─ memberships

Namespace Binding Layer

└─ explicit Topaz relationships to namespaces

Authorization Decisions

Resource Model

Provider-Scoped Identities

Required fields:

  • provider id
  • stable external SCIM resource id
  • active status
  • display attributes
  • last synchronized timestamp
  • optional canonical-subject binding reference

Provider-Scoped Groups

Required fields:

  • provider id
  • external group id
  • display name
  • active status
  • last synchronized timestamp

Namespace Bindings

Required fields:

  • bound subject or group
  • namespace
  • relation: read, write, admin, or future approved relation
  • source: manual, policy, or approved sync mapping
  • audit metadata

Sync Semantics

Idempotency

SCIM operations MUST be idempotent at the provider-object level. Repeating the same event must not create duplicate identities, groups, or namespace bindings.

Conflict Resolution

Conflicts are resolved by object scope:

  • provider-scoped identity conflicts are resolved within the provider only
  • namespace binding conflicts are resolved within the namespace policy layer

Prism MUST NOT merge two users or groups from different providers merely because user-facing attributes match.

Prism MUST also avoid assuming that a SCIM resource id and a login-provider subject are the same identifier unless an explicit binding has been established.

Supported Mapping Modes

Prism SHOULD support:

  1. manual-binding
  2. approved-group-mapping
  3. dry-run

In approved-group-mapping, a namespace admin explicitly approves a rule such as:

namespace: digital-twin-prod

bindings:
- source_group: group:scim:okta-enterprise:twin-operators
relation: write

That is different from allowing SCIM to grant arbitrary namespace access on its own.

Security Considerations

Blast Radius

Provisioning systems can disable large sets of users quickly. Changes MUST be reversible through audit trails and reconciliation logs.

Provider Isolation

Provider-scoped object IDs prevent collisions when two providers use the same group names.

Unauthorized Grants

SCIM ingestion without approved binding rules would be an authorization bypass. Namespace grants must remain explicit.

Implementation Plan

Phase 1

  1. Define provider-scoped identity and group schemas.
  2. Add SCIM ingestion endpoints and persistence model.
  3. Add reconciliation engine for memberships.

Phase 2

  1. Add namespace binding APIs and approval workflows.
  2. Add dry-run and audit-first sync modes.
  3. Add deprovisioning rollback and replay support.

Phase 3

  1. Add provider-specific guides for Okta and Azure AD.
  2. Add conformance tests for idempotency and conflict handling.
  3. Add operational runbooks for large-scale provisioning incidents.

Revision History

  • 2026-04-13: Initial draft split from RFC-063 foundation work