[ Switch to styled version → ]


← Docs index

Identity & SSO

Early access. Identity integration is available in assisted enterprise deployments. Confirm the validation and admission path for your provider before rollout.

This document describes integration with external identity providers (IDPs), JWT validation, JWKS caching, external IDs, and directory sync.

Overview

The documented native validation path covers OIDC/JWT. SAML, Entra ID, LDAP, and other systems connect through OIDC, an external identity bridge, or a custom webhook. Network admission still follows the configured join rule and Pilot identity checks.

Identity integration is registry-global. A single IDP configuration applies across the registry. Setting a new configuration replaces the previous one.

Supported providers

Configuration

Configure an identity provider with the `set_idp_config` protocol command.

{
  "type": "set_idp_config",
  "idp_type": "oidc",
  "url": "https://accounts.example.com/.well-known/openid-configuration",
  "client_id": "pilot-network-prod",
  "admin_token": "your-admin-token"
}

The IDP configuration is stored in the registry and persists across restarts. It can also be set through a blueprint using the `identity_provider` field.

To query the current configuration:

{
  "type": "get_idp_config",
  "admin_token": "your-admin-token"
}

An `idp.configured` audit event is emitted when the IDP is set or changed.

JWT validation

The registry includes built-in JWT validation supporting two algorithms:

Validate a token with the `validate_token` protocol command:

{
  "type": "validate_token",
  "token": "eyJhbGciOiJSUzI1NiIs...",
  "admin_token": "your-admin-token"
}

The command returns `verified` (boolean), `subject`, `issuer`, and an `error` string on failure.

The validator checks the following claims:

JWKS caching

For RS256 tokens, the registry fetches the provider’s JSON Web Key Set (JWKS) to obtain public keys for signature verification. JWKS responses are cached.

If the JWKS endpoint is unreachable and the cache has expired, validation fails. The registry does not fall back to accepting unverified tokens.

Security

The validator prevents algorithm confusion attacks by cross-checking the JWT's `alg` header against the matched JWKS key's type. An HS256 token cannot be verified against an RSA signing key. RS256 and HS256 are the only supported algorithms.

A 60-second clock skew tolerance is applied to time-based claims (`exp` and `nbf`) to accommodate minor clock differences between the IDP and the registry.

Webhook identity

For systems that do not support OIDC or SAML, a webhook identity provider can be configured. The registry sends an agent's credentials to an HTTP endpoint, which returns an approval or rejection.

{
  "type": "set_idp_config",
  "idp_type": "webhook",
  "url": "https://auth.example.com/verify-agent",
  "admin_token": "your-admin-token"
}

The endpoint receives a POST with the agent’s identity information and must return a JSON response indicating authorization status.

Separately, the registry can push identity events to an outbound webhook. Set the URL with the `set_identity_webhook` command or via the `identity_url` field in a blueprint's `webhooks` object.

{
  "type": "set_identity_webhook",
  "url": "https://ops.example.com/pilot-identity",
  "admin_token": "your-admin-token"
}

This command returns a status of `enabled` or `disabled`. The URL is validated for SSRF safety before being stored.

External IDs

Agents can be mapped to external identity systems using external IDs.

{
  "type": "set_external_id",
  "node_id": 5,
  "external_id": "[email protected]",
  "admin_token": "your-admin-token"
}

{
  "type": "get_identity",
  "node_id": 5,
  "admin_token": "your-admin-token"
}

External IDs are free-form strings, such as email addresses or UPNs. They are stored in the registry and included in audit events. An `identity.external_id_set` audit event is emitted on change.

Key metadata

Query a node's key lifecycle metadata with the `get_key_info` command.

{
  "type": "get_key_info",
  "node_id": 5
}

The command returns `node_id`, `created_at`, `rotate_count`, `rotated_at` (if set), `expires_at` (if set), and a derived `key_age_days`.

Directory sync

Directory sync pushes entries from an external directory to the registry. It updates roles for existing members, removes members no longer in the directory, and stores role pre-assignments for identities that have not yet joined. It does not add new members.

The sync operation is performed with the `directory_sync` command.

{
  "type": "directory_sync",
  "network_id": 1,
  "entries": [
    {
      "external_id": "[email protected]",
      "display_name": "Alice",
      "role": "admin"
    },
    {
      "external_id": "[email protected]",
      "display_name": "Bob",
      "role": "member"
    }
  ],
  "remove_unlisted": true,
  "admin_token": "your-admin-token"
}

The sync operation performs the following actions:

Directory sync supports role pre-assignment. An identity not yet in the network has its assigned role stored. When the matching node later joins, it receives that role instead of the default.

Query the sync status with the `directory_status` command.

{
  "type": "directory_status",
  "network_id": 1,
  "admin_token": "your-admin-token"
}

This command returns `network_id`, `total`, `mapped`, `unmapped`, `pre_assignments`, `enterprise`, and `last_sync`. A `directory.synced` audit event is emitted after each sync.

Related