# Changelog Source: https://docs.strata.io/changelog Release notes for both the Maverics Orchestrator and Maverics Console, organized by year in reverse chronological order. The Orchestrator uses calendar versioning in `vYYYY.MM.BUILD` format (e.g., v2026.02.1), where `BUILD` is the sequential build number within that month. The Console uses a similar `vYYYY.MM.DD` format, where `DD` is the day of the month the release was published. The Orchestrator transitioned from semantic versioning (v0.x.x) to CalVer starting with v2025.05.1. ## Orchestrator Releases Latest Orchestrator releases CalVer transition and v0.100+ v0.26 through v0.27 v0.23 through v0.25 ## Console Releases Latest Console releases Console UI overhaul and AI Identity Gateway Early Console releases # 2024 Source: https://docs.strata.io/changelog/console/2024 * Email form now validates email address format * Email is now treated as case insensitive * When you log out you will be redirected to the /sign-in page * Resolves an issue that may have occurred if you deployed a user flow between March 11, 2025 and March 18, 2025, and were not observing health data on the Orchestrator Telemetry page * Maverics now supports OIDC hybrid flow with an opt-in for Implicit Grant Type * The Pendo resource center has been removed and replaced with the document center * You can now define an errorPageURL in the Auth0 OIDC identity fabric configuration * Maverics now supports using a URL as a claim name for policies and OIDC/SAML claims * You can now add an attribute provider service extension to a rule when defining an access policy * New option to sign in using your email address and a one-time passcode (OTP) * Redesigned landing page with single form field * On deployment of a OIDC app type user flow, the default end session and revoke endpoints will be properly set in the config * The ARN value no longer requires the full Amazon Resource Name path * Resolved an issue preventing the orchestrator from connecting to AWS Secrets Manager # 2025 Source: https://docs.strata.io/changelog/console/2025 * Simplified Members list combining pending user invites and active members into one list * Fixed an issue where proxy outbound TLS CA file path was not being properly saved or deployed * When hosting multiple MCP Bridge apps in an AI Identity Gateway deployment, you can now assign unique namespaces to each app's tools * This prevents tool name conflicts across multiple MCP servers * Introducing Server Name Indication (SNI) TLS configuration * Configure TLS settings for individual host domains in addition to the global TLS settings * Enhanced Token Lifecycle Control for AI Agent Operations * Fine-grained control over token issuance and lifecycle for AI agent operations including: * Delegation * Refresh token lifetime * Access token lifetime * Enhancements to Rego and OpenAPI spec views and drag-n-drop * MCP Bridge Provider now supports environment variables in URLs * Bug fixes for SAML and OIDC authentication policies * Drag N Drop OpenAPI specs and Rego policy definitions when defining a MCP Bridge app * SAML Apps unauthorized page field no longer requires a full URL * When defining the tools you want to expose in your MCP, you can now directly edit OpenAPI Spec as YAML or JSON format * Note: supports v3.0 (v3.1 or higher not supported) * The AI Identity Gateway: MCP Bridge is now available * Enables teams to let AI agents interact with internal or external APIs safely, with identity, authorization, and policy enforcement * Resolved an issue where the disable hashing option was not propagated in a deployment * You can now disable the feature-specific prefix typically prepended to cache keys, enabling shared Redis cache for external data integration * Requires Orchestrator v2025.11.1 or higher * The LDAP provider and related LDAP service extensions are now generally available in the UI * You no longer need to contact support to enable it * Resolved an issue that prevented users from being able to accept account invitations * Resolved an issue that prevented new users from being able to sign up * Fixed config generation when multiple Continuity Strategies in a single deployment * Improved how TLS certificates and TLS policies (e.g., min TLS version, enabled ciphers) are configured * More flexibility and better security controls * You can sort and name search for applications, identity fabric, and user flows from the dashboard * Resolved issues in Identity Service Health Monitoring not generating correct config * The proxy user flow editor now lets you attach a user flow to a deployment * New list of deployments view * Resolved an issue where proxy user flows failed with service extensions with null metadata * New UI for the proxy application user flow editor with show view and edit slide out window * Adopted new list experience for applications including: * Search by name * Create new * View the associated user flow * Fixed PKCE toggle in OIDC Identity Fabric * When creating an OIDC based identity fabric, PKCE is enabled by default and the toggle now correctly shows enabled state * Improved warning experience when trying to delete a service extension that is in use * Added CORS configuration to OIDC applications * You can now enter multiple login and logout redirect URLs for Microsoft Entra ID OIDC and other OIDC identity fabric services * Updated look and feel of the Identity Fabric page * Deployments now support Azure Government Cloud blob storage * Requires Orchestrator version v2025.08.2 or higher * In the LDAP authentication fabric settings you can now customize login flows by uploading custom HTML pages and localizations * You can now perform a name search from the Identity Fabric list and on creation * From the Deployment Manager you can now configure TLS settings for inbound connections on the orchestrator host * Requires manual orchestrator restart * Resolved an issue where metadata value edits were not deploying * You can now add filters to suppress log messages from Observability Settings * Each filter defines a function that tests potential log output * In an OIDC app type definition you can now define a redirect URL fallback when an app's authorization request does not include a redirect\_uri parameter * Improved user flow list view with search and filtering * You can now set a file path on host to the SAML Private Key and SAML Public Key (Certificate) * Requires Orchestrator version 2025.06.4 or higher * Resolved an issue preventing users from switching accounts * Updated the system to use the latest Orchestrator Telemetry configuration * The new Deployments capability is now available in all accounts * Includes: * Deployments Workflow * Deployment Manager * Configuration Preview * Attribute Provider definition in a user flow has been expanded and renamed to Dependencies * You can now attach identity providers, service extensions, and attribute providers to a user flow * You can now define multiple Entity IDs when defining a SAML application * In an OIDC app you can now mark an app as a public client * Public clients, such as SPAs, do not require a client secret * Requires Orchestrator release v2025.05.2 or higher * View the latest Orchestrator Release Version number, date, and go directly to the release notes * Orchestrator Version Inspection to check compatibility * Added support for editing metadata values for service extension points in Proxy User Flows * You can now define an app specific unauthorized (403) URL for SAML apps * Requires Orchestrator Release v0.113.0 * Publish Preview actions are now on each app in SAML and OIDC user flows * SAML apps can define default and multiple Assertion Consumer Service (ACS) URLs * OIDC Apps now support allowedAudiences * Bug fixes for user flow metadata and SE function names * New Deployments Workflow, Deployment Manager, Configuration Preview, and Enhanced SAML App Configuration * Gradually rolling out to existing accounts * Improved text formatting and layout of the deployment manager * Resolved issues where a user could not accept an invitation to another account * When defining an OIDC app you can now require demonstrating proof of possession (DPoP) * App Centric Migrations to prepare for future UI updates * New users can sign in with a passkey as an alternative to the HYPR app * Each application is now restricted to one user flow to simplify application deployments # 2026 Source: https://docs.strata.io/changelog/console/2026 * Added a warning in the publish drawer when a configuration override is active for a deployment * Proxy app access policy editor now exposes the option to match on query parameters * OIDC Identity Fabric providers now support CIMD (Client Initiated Metadata Document) and DCR (Dynamic Client Registration) configuration * Fixed an issue where namespaces were not consistently applied to service extension claims * OIDC apps now support access token claims mapping, letting you configure which claims are included in issued access tokens * Fixed an issue in the configuration inspector where OIDC CIMD app types and token broker authentication were not handled correctly * **OIDC CIMD App Type:** Administrators can now create and configure CIMD-type OIDC applications directly in the Console. The Orchestrator fetches and validates the client's published metadata document at runtime, completing the full authorization-code + PKCE flow with no prior client registration. * Service extension claims are now available as options in the Username Mapping dropdown * Username Mapping now accepts free text input in addition to selector options * Dropdown fields can now be cleared to unselect the current value * MCP Proxy apps now support tool filtering to control which tools are accessible per app configuration * You can now configure an Authenticate SE as the username mapping source for an attribute provider resource * The Maverics Storage used for evaluation purposes has been removed. Instead, use one of the supported configuration storage providers. See [Config Publishing](/reference/console/config-publishing) for more details. * SAML Provider private and key configuration now accepts a single key; key reordering has been removed from the key management drawer. ### Improvements * OIDC provider private keys now respect configured ordering, enabling key rotation. ### New * Now that Strata Identity has joined Rubrik, there is a prompt to accept the Rubrik Terms of Service and Privacy Policy. * Claim and attribute mapping fields now accept free text input in addition to selector options * Removed "Log in with Microsoft" as a social sign-in option from the Maverics Console * Fixed an issue where Generic OAuth could not be used as an authentication provider ## Filter MCP tools by access token MCP Proxy apps can now apply an OPA connection authorization policy that decides, per upstream MCP server, whether the gateway connects to it and lists its tools — evaluated against the caller's access token. Instead of surfacing every upstream's tools to every client, you can scope which tools each session sees based on identity. See the [MCP Proxy reference](/reference/orchestrator/applications/mcp-proxy) for full configuration details. ### Proxy app type editing improvements * User flows have been completely phased out and will no longer appear in list views. * All configuration for a Proxy app — upstream, route patterns, location access policies, and global request headers — now live in the app editor. * Resources (formerly Dependencies) define the identity fabric and service extensions you reference in access policies and claims. Define your Resources first, and they'll be available in the relevant drop-downs throughout the Proxy app editor. ### Fixes * Added a warning in the configuration inspector when `http.writeTimeoutSeconds` is set for deployments using an MCP provider * Resolved an issue where SAML and OIDC claims mappings were omitted during a deployment * Added WSO2 to the supported identity provider filters for the OIDC protocol * Attribute providers can no longer be selected as authentication sources for OIDC and SAML apps * Fixed an issue where long policy metadata values were not properly truncated * Added support for multiple identity providers in authentication policies for OIDC and SAML apps * Added a scopes field to the OAuth connector in the Identity Fabric * Fixed the OIDC offline access toggle always showing as disabled in the edit form * Fixed uploaded service extension assets not being included in deployment bundles for OIDC and SAML apps * Fixed namespace handling for service extension claims in OIDC and SAML claims mapping ## Token brokering for OIDC apps OIDC apps can now broker tokens from an upstream provider. Configure token brokering directly in the OIDC app editor. Token brokering is experimental and may change in a future release. ## Generic OAuth connector A new **Generic OAuth** connector is available from the Identity Fabric. Use it to broker tokens against SaaS upstreams that expose OAuth but no OIDC discovery — for example, Databricks account-wide federation or GCP Workload Identity Federation. ## RFC 7638 key IDs for OIDC Provider JWKs The OIDC Provider JWK editor now includes a toggle for RFC 7638-compliant key ID (KID) generation. Existing keys keep their current KID; new keys use the spec-compliant algorithm. ## Fixes * Removing a Resource from a SAML or OIDC app no longer fails to save when an attribute provider still references it. Stale references now clear automatically, and the editor flags any that still need attention before you save. * Fixed SAML v2 request verification certificate handling. * Added URL validation to the Generic OAuth connector in the Identity Fabric. ### SAML app type editing improvements * User flows are being phased out and will no longer appear in list views. * All configuration for a SAML app — service provider configuration, protocol & assertion settings, access policies, and attribute mappings — now live in the app editor. * Resources (formerly Dependencies) define the identity fabric and service extensions you reference in access policies and claims. Define your Resources first, and they'll be available in the relevant drop-downs throughout the SAML app editor. ## OIDC app type editing improvements * **User flows are being phased out.** All configuration for an OIDC app — client details, access policies, claims, and OAuth 2.0 scopes — now lives in a single view. * **Resources** (formerly Dependencies) define the identity fabric and service extensions you reference in access policies and claims. Define your Resources first, and they'll be available in the relevant drop-downs throughout the OIDC app editor. ## Custom Telemetry Exporters for Metrics Ship Orchestrator metrics to any OTLP-compatible backend directly from the Observability settings page — no external collector required. The **Custom Telemetry Exporters** section lets you add one or more metrics destinations alongside Maverics Cloud Telemetry. Each exporter is configured with a name, protocol (OTLP over HTTP or gRPC), endpoint, optional auth headers, and advanced tuning for compression, temporality, histogram aggregation, and export interval/timeout. See the [metrics telemetry reference](https://docs.strata.io/reference/orchestrator/telemetry/metrics#metrics) for the full field list. **Exporter types** * **New Relic** — preset tuned for New Relic's OTLP ingest (`otlp.nr-data.net`, delta temporality, base2 exponential histograms, gzip). * **Generic OTel** — works with any OTLP receiver. Point it at your own OpenTelemetry Collector or directly at a SaaS backend that accepts OTLP, including Datadog, Grafana Cloud, Honeycomb, Splunk Observability Cloud, Dynatrace, AWS CloudWatch (via ADOT), Microsoft Azure Monitor, Google Cloud Observability, and Chronosphere. **Why it matters** Previously, fanning metrics out to a vendor meant standing up an OpenTelemetry Collector in front of the Orchestrator and managing exporter config in YAML. Now operators can wire up multi-destination metrics from the admin UI in under a minute, with per-exporter tuning of headers, interval, temporality, and histogram shape. **Notes** * Observability settings are now grouped under **Orchestrator Settings**. * Each exporter runs independently — a slow or unreachable destination won't block the others. * Maverics Cloud Telemetry remains available and is unaffected by custom exporter configuration. * Resolved an issue where SSO configuration changes were not applied * Fixed sidebar navigation active state on Identity Fabric and Service Extension detail pages * Dropdowns with 10+ items now include a search filter so you can quickly find what you need * Fixed an issue where dropdown selections couldn't be changed * Added search and filter support to dropdown selectors * Resolved issues preventing successful signup and user invitation flows * The code editor for service extensions, OPA policies, and OpenAPI code has been upgraded to Monaco Editor for an improved editing experience * Configure JSON output logging for deployments * SAML apps now support configuring NameID element qualifiers * The Console now validates Rego policy scripts for compilation errors when saving OPA policies * The OIDC Identity Fabric connector now shows a detailed error view and validates that the connected Orchestrator meets the required minimum version * Resolved an issue where account re-registration was blocked after deleting an account * **API App Type Moves to Service Extensions:** API App Types have been relocated from the Applications area to the Service Extensions area in the Maverics Console, unifying the experience for managing APIs and service extensions under a single interface. * All existing API App Types automatically appear in the Service Extensions area alongside your other extensions. * Creating a new API is straightforward — select "API" from the Service Extensions area and provide your configuration details. * API App Types can now be attached to deployments directly. * Existing deployments that already have APIs associated with them will find those APIs in a new dedicated APIs section within the deployment configuration. No migration or reconfiguration is required. * Added OIDC callback error handling configuration for the [Entra ID](/reference/orchestrator/identity-fabric/azure-ad#callback-error-handling) and [Generic OIDC](/reference/orchestrator/identity-fabric/custom-oidc) Identity Fabric connectors. Requires Orchestrator v2026.03.3 or higher. * Service extension asset uploads now support files up to 5 MB * Fixed an issue where dependencies and library settings were not deployed with API service extensions * The Console will now validate the SAML certificate and key pair when uploading to a deployment. We recommend doing this only for testing purposes; for production, always use a secrets provider. * LDAP configuration no longer shows a custom login file path option * HTTP Server TLS configuration now supports `None` as a client authentication type * Resolved issues when attaching service extensions to a deployment * Resolved issues when typing spaces or enter the Rego policy editor * Service Extensions list header is now properly titled * Fixed an issue where service extensions were not working as a Name ID source in SAML user flows * Authentication service extensions are no longer listed in the user flow dependency list * Audit Log (Beta) is now available * Resolved email case sensitivity issues when signing in and accepting user invitations * Maverics Console no longer applies an automatic namespace prefix when a Service Extension is the source for a NameID attribute value. This resolves Orchestrator runtime errors that produced "connector does not exist" and "missing claim mapping" messages, which prevented SAML authentication from completing. * **Action Needed:** SAML user flows that use a Service Extension to populate the NameID value may require a manual update to the NameID mapping field. * You can now remove members who declined a team invitation * Resolved an issue whereby screens refresh unexpectedly causing a loss of edits * Audit logs now capture login and logout events * Audit log events now include event type, category, and target metadata in the admin API * Audit logs table now shows the target type alongside the target name * Service extensions listed in user flow dependencies now show available metadata * Audit Logs navigation item is pinned to the bottom of the sidebar * Fixed sorting issues across listing views for consistent ordering * Fixed an issue where dependency metadata was not preserved when updating a user flow * Fixed the Service Extension editor shuffling metadata fields * Audit log timestamps are now formatted for readability * Session creation audit log events no longer include query parameters * Configure the maximum TLS version for deployment TLS settings (requires Orchestrator v2026.02.3 or higher) * Resolved an issue preventing login with Email OTP * Added a Target Name column to the audit logs table for easier identification of affected resources * User details are now included in membership audit log events * Configure HTTP Server timeouts and access logging in Deployments * Configure outbound authorization for MCP protocol operations (`initialize` and `tools/list`) for MCP Proxy apps (requires Orchestrator v2026.02.2 or higher) * Improved UX when deploying HTTP Server settings, including default placeholders and endpoint timeout validation * Resolved TLS configuration issues with client CA files, Windows certificate store persistence, and cipher suite persistence * Your Console account is now linked to one sign-in method (the last one you used) -- use that same method every time you log in * Sign-in options: Maverics Account passwordless (Email OTP or HYPR), social sign-in (Google or Microsoft Account), or Enterprise SSO (bring your own IdP) * GitHub sign-in has been removed as a login option * If you try a different sign-in option, you'll see a message that the email is already associated with another identity provider * Redis Cache now supports enabling TLS configuration in the Console without having to set a CA file path * A new toggle lets you enable or disable TLS for the Redis cache connection * Set the minimum TLS version (1.2 or 1.3) * Resolved an issue preventing SSO users from reliably signing into Maverics Console * Resolved a critical issue where CA (Certificate Authority) and mutual TLS configuration was not persisting in proxy applications * The system now properly saves and deploys the configuration * Fixed an issue where the proxy outbound TLS CA file path was not being properly saved or deployed * The sign up and sign in flows have been redesigned for a cleaner, more efficient user experience * The Orchestrators Main Menu has been removed -- all orchestrator settings are now accessible from the Deployment Manager * You can now configure JWT client authentication for OIDC apps * Requires Orchestrator v2026.01.3 or higher * JWT Client Authentication Configuration for the Generic OIDC Connector * Requires Orchestrator release v2026.01.3 or higher * Resolved issues preventing the attachment of service extensions to OIDC, SAML, or Proxy app type user flows * Resolved issues preventing deletion of applications or user flows that were not attached to a deployment * MCP Proxy App Type is now available * You can now create and configure MCP Proxy apps directly from the Maverics Console # 2023 Source: https://docs.strata.io/changelog/orchestrator/2023 * Fix panic when cert not found in Windows cert store * Correctly set RelayState during IDP initiated login * Add env vars for Windows Certificate Store * Improve error handling in OIDC connectors * Add support for reloadable cache * Allow SAML client to support both IDP initiated login and verified SP login Internal improvements and maintenance updates. * Add windowsclientauthenticator connector to orchestrator * Expose jose.JSONWebKeySet in v2 SE Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Add support for GetFloat and SetFloat in Service Extensions * Add support for GetTime and SetTime in Service Extensions Internal improvements and maintenance updates. * Add support for GetInt and SetInt in Service Extensions * Fix issue of cache manager not being repopulated on reload * Add support for GetBool and SetBool in Service Extensions Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Set maverics cookie in proxy apps and API SEs * OIDCProvider validate HTTP method used in token and auth endpoints Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Correct policy matching in proxy apps to be case-insensitive * Add optional nameIDFormat configuration to samlprovider app * Register SAML endpoints in case-insensitive manor * OIDC endpoints should are registered in case-insensitive manor Internal improvements and maintenance updates. * Implement TAIProvider interface for Service Extensions * Update log package to fix panic observed when running as non windows admin * Rotate refresh tokens on use per OAuth security best practices Internal improvements and maintenance updates. * Implement token revocation for JWT * Store JWT tokens in the cache Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Expose GetBytes, GetAny, and SetBytes on Service Extension session provider implementations Internal improvements and maintenance updates. * SAMLProvider validates signed authn requests received via HTTP-Redirect binding * Implement v2.Session API for Service Extensions for OIDC Provider * Add post logout redirect URL to proxy apps * Return all claims for opaque access token * Add logout to proxy apps Internal improvements and maintenance updates. * Add clock skew leeway for SAML Authn requests * Stop Maverics process on failure to bind to a port * Add support for IDP initiated login for app of type SAML * Add support for HTTP Redirect binding in the SAML auth provider * Organize LDAP Provider in preparation for SASL / GSS-SPNEGO / NTLM work * Improve attribute loading error handling in proxy apps * Add query params matching in proxy apps policies * Add handleUnauthorizedSE to proxy apps * Add upstream login extension to proxy apps * Add support for IDP initiated login for the SAML provider * Add ModifyRequest and ModifyResponse Service Extensions to proxy apps * Add LoadAttrsSE to proxy apps * Expose 'goPath' on v2 Service Extensions * Add CreateHeader service extension to proxy apps * Add IsAuthorized service extension to proxy apps * Add IsAuthenticated and Authenticate extensions to proxy apps Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Add TLS to proxy apps Internal improvements and maintenance updates. * Resolved CVE-2023-45683 * Support multiple route patterns on a proxy app * Add Orchestrator Groups cache support * Add regexp policy matching to proxyapps * Add attribute provider to proxy apps * Resolved CVE-2023-39325 Internal improvements and maintenance updates. * Support policy-level header definitions on proxy apps # 2024 Source: https://docs.strata.io/changelog/orchestrator/2024 * **TLS:** Use Go's native implementation of 'x509.SystemCertPool' on Windows Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **Dependencies:** Resolved CVE-2024-45338 Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **ldapProvider:** Correctly surface 'getHashedCredentialsSE' error Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **Secret provider:** Make CA not required for cert auth in HashiVault * **Dependencies:** Resolved CVE-2024-45337 * Fix Missing Folder for Artifactory Cleanup Workflow Internal improvements and maintenance updates. * **Connectors:** Allow multiple OIDC callback URLs to be defined Internal improvements and maintenance updates. * **Dependencies:** Resolved CVE-2024-53259 * **Service Extensions:** Implement HTTP interface of Orchestrator API. * **OIDC Connector:** Dynamically generate oauth logout callback URLs * **SAML Provider:** Fix issue where authentication requests required an ACS URL * **OIDC Provider:** Add support for 'ES256' key algorithm for client authentication * **HTTP:** Add global endpoint timeout. * **HTTP:** Add configurable HTTP server timeouts with sane defaults. * Respect env variables and CLI flags when reloading logger * **Proxy Apps:** Improve logging when required attributes are missing and not loadable * **OIDC Connector:** Dynamically generate oauth callback URLs * **OIDC Provider:** Improve logging during JWT bearer client authentication Internal improvements and maintenance updates. * Enable use of JWT for client authentication with client\_credentials grant * **Container:** Resolved CVE-2024-9143 * **SAML APP:** Support multiple ConsumerServiceURLs per SAML app Internal improvements and maintenance updates. * **SAML Connectors:** Use POST binding if available during SAML login * **Secret providers:** Support Hashicorp Vault cert auth on Windows * **Config Reload:** Make logger reloadable * **TLS:** Add support for ECDH algorithms on Windows * Add CRL revocation support to tls config * **SAML Provider:** Support compressed AuthnReq via POST binding Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **SAML & OIDC Providers:** Enable service extensions to be used in conjunction with attribute providers Internal improvements and maintenance updates. * Add OCSP revocation check * **Logger:** Add error logger to HTTP server * **OIDC Provider:** Require openid scope to access userinfo endpoint * Support Hashicorp Vault cert auth on Linux Internal improvements and maintenance updates. * **Health service:** Make health service reloadable * Update PR template to hide instructions * **Connectors:** Generic SAML health check add cookies jar * **QKSLVR-1987:** Upload additional artifacts JFrog * **OIDC Provider:** Allow "sub" and "client\_id" claims to be overwritten via service extension * Add Single Logout JSON Schema Internal improvements and maintenance updates. * Add deb build target in Makefile * **OIDC Provider:** Dynamically build userinfo response * **OIDC Provider:** Add association from token cache to userinfo cache * **OIDC Provider:** Store userinfo data only once * **Connectors:** Infer correct protocol binding from SAML metadata * Expose 'jose.ContentType' in service extensions * **Connectors:** Add support for login hint via subject in PingFed SAML Internal improvements and maintenance updates. * Update github PR template * **Connectors:** Implement login\_hint in query for Azure SAML * **SE:** Add 'postLogoutSEV2' service extension * Ensure mTLS can not be bypassed by spoofing the Host header. * **Connectors:** Restore SAML login in PingFed * **Connectors:** Add login hint to OIDC connectors * **Proxy apps:** Allow secrets loading in policy locations * **SE:** Introduce v2 service extension signature for 'evalIdleTimeoutSE' * Support retrieving AWS secrets via ARN Internal improvements and maintenance updates. * **TLS:** Add support for SNI via 'http.hosts' * **SE:** Introduce v2 session evalMaxLifetime * **Service Extensions:** Fix route registration issue * Add newline delimiter option in CCP as workaround for multi-line secrets. * Format the Hypr HTML to make it more readable * **DSO-1348:** Add Uploading Artifacts for Services Team * SAML App inherits signing cert from SAMLProvider * **HTTP:** Rework HTTP initialization logic to support SNI Internal improvements and maintenance updates. * SAMLProvider fix panic when claims mapping attribute does not use connector notation * Fix OIDCProvider panic when claims mapping attribute does not use connector notation * **Bundle Validation:** Improve error handling when loading public key * **TLS:** Rename 'clientCAs' to 'clientCAFiles' in TLS config * **Continuity:** Improve reload behavior * **Continuity:** Check for duplicated status codes * **Continuity:** Add health check to ADFS * **Connectors:** Make cert and keys paths optional for ADFS Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Support LoadAttributesSE for OIDC Apps * Enable service extensions for oidc provider authorization * Support multiple secrets for OIDC client authentication * Add load attributes service extension to SAML apps * Ensure OIDC clients are unique by client ID * Expose make commands in make help * **SAML Apps:** Support app level 'disableSignedAssertion' and 'disableSignedResponse' * Add authorization rules to OIDC apps Internal improvements and maintenance updates. * **SAML Apps:** Support app-specific signing certs * Support client defined grant types for OIDC apps * **Continuity:** Remove body matching response logging * Update mitchellh/mapstructure to go-viper/mapstructure/v2 * **Apps:** Validate 'name' uniqueness * Support ROPC flow for OIDC apps via backchannel authenticate SE * **Continuity:** Increase state parameter length in generic OIDC health check * **Continuity:** Add TLS to custom health check Internal improvements and maintenance updates. * Support IsAuthorizedSE in SAML apps * Add permissions for id-token for Jfrog Artifactory GitHub Workflow * **Continuity:** Add custom health check response body matching * Use the correct HTTP client for SAML health check * **Continuity:** Add headers to custom health check endpoint * Add QR authentication mode for Hypr connector * Add GitHub workflow for uploading artifacts to JFrog Artifactory * Update Artifactory GitHub Workflow to reference branch * **Continuity:** Add ability to define custom health check * **Continuity:** Change the default health check interval * **Continuity:** Add un/healthy threshold * Enforce authorization rules in SAML Apps * **Continuity:** Support health checks in PingFederate connector * Reimplement Cyberark Conjur Secret Provider Internal improvements and maintenance updates. * Add state to continuity enabled connectors * Remove legacy LDAP 'attrproviders' implementation * **Continuity:** Update IdP healthcheck metric prefix to include namespace * **SAML APP:** Query for nameID attributeMapping attribute if not on session * Update log level to error when referenced secret is not found * **Continuity:** Add IDP health check to Auth0 * **Continuity:** Add IdP health metrics * Expose ldap.Control * Implement SAML health check in Okta * Implement SAML health check in Azure * Add AWS Secrets manager secret provider support Internal improvements and maintenance updates. * **Continuity:** Add generic SAML health check * **Telemetry:** Update local Docker Compose telemetry environment for development * Support reload for single logout config * **Continuity:** Leverage generic OIDC health check in Okta and Azure * **Continuity:** Add meter and tracer to health check service * **Continuity:** Parse health check values as duration * Protect session store with mutex and add session service to config reloader * Implement session config reload Internal improvements and maintenance updates. * **Service Extensions:** Expose symbols for JWT encryption Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **MSI:** Fix file contention issue Internal improvements and maintenance updates. * **Continuity:** Add health check to OIDC connector Internal improvements and maintenance updates. * **OIDC & SAML Apps:** Remove legacy resilience implementation * **Proxy apps:** Remove legacy resilience implementation Internal improvements and maintenance updates. * Redirect SAML SSO error responses correctly * **Continuity:** Add health check to AD * **Continuity:** Add health check to LDAP * SAMLProvider support LogoutRequest via POST binding Internal improvements and maintenance updates. * **Connectors:** Gracefully handle failure to retrieve OIDC well-known metadata * Verify Signed SAML Logout requests via Redirect binding Internal improvements and maintenance updates. * **SAML Apps:** Store logout request in cache * Fix SAMLProvider cacheState storage when using multiple IDPs * Add support for namespace in HashiVault * **Resilience connector:** Add support for logout * Unregister SAMLProvider SLO endpoint during stop * **Connectors:** Better handle logout errors * **Resilience connector:** Implement Query Internal improvements and maintenance updates. * Append query parameters to authn request during IDP Initiated SAML * Validate bundle file in MSI installer * **SAMLProvider:** Add SingleLogoutService to metadata when sloEndpoint is defined * **SAMLProvider:** Implement SP initiated SLO * **MSI:** Fix service restart when change and add default remote configs. * **Service Extensions:** Expose symbols to enable JWT generation Internal improvements and maintenance updates. * **Connectors:** Set transport properties on health check HTTP client * **SAML Connectors:** Fix panic observed when generating unsigned logout requests * **Resilience Connector:** Add meter and tracer * **Resilience Connector:** Add attributes mapping * **Resilience Connector:** Add 'enabled' property and remove dependency on feature flag * Add instructions on setting up the dev environment for the MSI Installer * **Resilience connector:** Implement failover strategy * Improve specificity of pull request instructions * **Resilience Connector:** Add base config and validation * **Resilience Connector:** Implement base lifecycle * **SAML Apps:** Call BuildRelayState extension post-authentication * **Resilient Connector:** Scaffold connector implementation Internal improvements and maintenance updates. * **SAML Apps:** Expose NameID configuration * Include allowedProtectedPackages option for Service Extensions * Introduce cache to SAMLProvider * **SAML Apps:** Expose BuildRelayState service extension for IDP-initiated login flow * MSI - Separate HTTP address field into IP and Port. * **SAML Apps:** Allow IDP-initiated 'relayStateURL' field to be optionally defined * MSI - Add documentation hyperlink to complex properties. Internal improvements and maintenance updates. * MSI - Auto set MAVERICS\_RELOAD\_CONFIG=true * Fix log key to have correct attrProvider name * MSI - Fix double configuration source error. * MSI - Migrate system environment variables. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **SAML & OIDC Apps:** Organize authprovider pkg and improve logging * Manually validate timestamp assertions in SAML Internal improvements and maintenance updates. * Implement generic SAML in 1Kosmos and add cache * Improve MSI UX flow for Bundle Key File selection. * MSI - Find certificate should have empty selection. * **SAML Apps:** Validate SP audience is unique before creation * **Proxy Apps:** Add support for HTTP request methods in policy * **OIDC Apps:** Add 'Authorization' to list of 'Access-Control-Allow-Headers' to fix CORS issue * Resolved CVE-2024-22189 * Make Ping Fed use generic SAML package and introduce cache Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Fix remote config box gets cleared after selecting bundle public key file. * **SAML Connectors:** Only sign SAML AuthnRequest if signing certs are provided * OIDC ClaimsMapping -> LogicNodes * Implements new MSI UI flow * Minor changes to improve azure and connector behaviors * Rename LogicNode IDP to Value * Enhance SAML metadata parsing to support formatted certificates * Support api.App in IsAuthenticatedSE, AuthenticateSE and v2/BuildClaimsSE for saml apps * Support api.App in IsAuthenticatedSE, AuthenticatedSE, BuildAccessTokenClaimsSE, BuildIDTokenClaimsSE for oidc apps * Add support RP-initiated logout in OIDC provider * **NG-LDAP Provider:** Correctly handle a bind after the SASL security layer is active (Conformance) * **NG-LDAP Provider:** Various improvements to logging and user config. * Allow loading certs from Windows store in CyberArk CCP * Support api.App in loginSE and isLoggedInSE for proxy apps * Support api.App in createHeaderSE for proxy apps * Support api.App in loadAttrsSE for proxy apps * **NG-LDAP Provider:** Update Stability to Beta Internal improvements and maintenance updates. * **NG-LDAP Provider:** Fix context within SEs * **Service Extensions:** Add missing Cache WithTTL option to SE symbols Internal improvements and maintenance updates. * **NG-LDAP Provider:** Improve logging * **NG-LDAP Provider:** Handle Unbind * **NG-LDAP Provider:** Add SASL/GSS-SPNEGO/NTLM handling into the connection handler Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Update error returned when end\_session\_endpoint isn't configured Internal improvements and maintenance updates. * Okta OIDC connector resilience Internal improvements and maintenance updates. * Implement CyberArkCCP Internal improvements and maintenance updates. * **NG-LDAP Provider:** Map user config to runtime parameters Internal improvements and maintenance updates. * Ensure appropriate errors are returned instead of http.ServeMux panic * **NG-LDAP Provider:** Attach secure connection handler to server * **NG-LDAP Provider:** Add NTLM Handler (Part 2) * Azure connector resilience Internal improvements and maintenance updates. * **NG-LDAP Provider:** Add NTLM Handler (Part 1) * **NG-LDAP Provider:** Handle Extended StartTLS Internal improvements and maintenance updates. * **Security:** Resolved CWE-409 * **NG-LDAP Provider:** Handle Search * **NG-LDAP Provider:** Handle Simple Bind * Expose service extension utility to enable WebLogic integration Internal improvements and maintenance updates. * **NG-LDAP Provider:** Add Simple Bind skeleton * Pass query params from logoutURL to postLogoutRedirectURL * **NG-LDAP Provider:** Add first packet processing layer * **NG-LDAP Provider:** Fix panic on Orchestrator shutdown * **NG-LDAP Provider:** Add initial connection skeleton * Add capability to choose idp for authn with LogicNode Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **NG-LDAP Provider:** Add initial server connection logic * Add LogicNode as path to enhancing IDP logic * **NG-LDAP Provider:** Add SASL Security Layer (Security Sensitive) Internal improvements and maintenance updates. * **NG-LDAP Provider:** Add initial OIDs and message structure Internal improvements and maintenance updates. * **NG-LDAP Provider:** Add runtime params Internal improvements and maintenance updates. * **NG-LDAP Provider:** Add end-user config * Add Service Extension symbols to enable AVP use case Internal improvements and maintenance updates. * **NG-LDAP Provider:** Add initial Service Extension signatures and parsing logic Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Parse Auth request properly to generate proper state param * Move nested policy so that it can be reused across constructs Internal improvements and maintenance updates. * **NG-LDAP Provider:** Implement minimal lifecycle Internal improvements and maintenance updates. * Add LDAP provider to root of the config * Create an initial structure for the next generation of the LDAP Provider Internal improvements and maintenance updates. Internal improvements and maintenance updates. * Add configuration options to MSI installer and fix upgrade behavior * Support loading service extension assets as a file system * Add offline\_access to scopes\_supported in OIDC well-known endpoint * Implement Context interface for service extensions * Support retrieving App name from some v2 Service Extensions * Expose orchestrator cache to service extensions * Add client\_id to claims in access token * Support login options in service extensions * Resolved CVE-2023-49295 * Fixes refresh token length configuration * Closes HTTP response body in connectors * Omit the attempt to substitute env var if the line starts with '#' * Close response body when making token request * Resolved CVE-2023-48795 # 2025 Source: https://docs.strata.io/changelog/orchestrator/2025 * **MCP Proxy:** Harden implementation * **MCP Proxy:** Proxy inbound client info when initializing session with upstream server * **MCP Proxy:** Add networking configurations with reasonable defaults * **Security:** Resolved CVE-2025-64702 * **MCP Provider:** Add namespacing for tools * **MCP Proxy:** Expose streamable MCP Proxy app config * **MCP Provider:** Remove default tools * **OIDC Connector:** Use contextual logger when handling callback errors * **MCP Proxy:** Add base proxy functionality * **Service Extensions:** Fix ROPC initiated from within LDAP Provider SEs bug * **MCP Proxy:** Add inbound and outbound authorization to tool calls * **MCP Provider:** Update streamable MCP server and client to use custom Orchestrator logger * **MCP Provider:** Make the MCP Provider server name configurable * **MCP Proxy:** Add support for custom client TLS configurations * **MCP Provider:** Add support for delegated token exchange to bridge apps * **OIDC Provider:** Add support for X-Maverics-Oauth-Access-Token-Lifetime * **MCP Provider:** Add per-tool access token lifetime configuration * **Security:** Resolved CVE-2025-47914 and CVE-2025-58181 * **OIDC Provider:** Remove inherited audience in token exchange grant * **OIDC Provider:** Add support for delegated token exchange * **OIDC Provider:** Clean up logs made by session-less access token generation * **OIDC Provider:** Add evaluation of access token minting policies to implicit/hybrid grants * **OIDC Provider:** Add access token minting policies to ROPC grant * **Security:** Resolved CVE-2025-47913 * **OIDC Provider:** Populate access token minting policy fields * **LDAP Provider:** Add ability to determine the bound DN in Service Extensions * **OIDC Provider:** Add access token minting policies to authorization code grant * **Config Bundle:** Handle filesystem error and prevent panic * **OIDC Provider:** Add access policy evaluation to refresh\_token grant Internal improvements and maintenance updates. * **OIDC Provider:** Handle authorization requests when made via POST * **MCP Provider:** Add initial MCP proxy app config structure * **OIDC Provider:** Add support for custom access token minting policies * **Cache:** Add ability to disable key-prefixes on cache entries * **config:** Ensure that multiple env vars are read in separately via json * **MCP Provider:** Support inlined OpenAPI specs for MCP Bridge apps * **OIDC Provider:** Support custom scopes with ROPC grant * **OIDC Provider:** Preserve backwards-compatibility with unrecognized cu… * **OIDC Provider:** Enable custom scopes for the authorization\_code grant type * **MCP Provider:** Enable graceful shutdown of MCP clients via HTTP BaseContext * **OIDC Provider:** Add support for custom scopes with the client\_credentials grant * **OIDC Provider:** Add support for custom scopes with the refresh\_token grant * **OIDC Provider:** Add support for custom scopes with the implict and hybrid grant types * **OPA:** Update input schema for Rego policies * **MCP Provider:** Add reload capability * **Security:** Resolved CVE-2025-59530 * **OIDC Provider:** Add access policies to token exchange grant * **FIPS:** Build a FIPS compliant version of the Debian package * **MCP Bridge:** Add support for loading OPA policies from the filesystem * **OIDC Provider:** Add custom scopes to token exchange grant * **MCP Provider:** Add support for token exchange to bridge apps * **OPA:** Setup OPA to be used across multiple Orchestrator components * **MCP Provider:** Add support for loading OpenAPI files using relative paths * **FIPS:** Build FIPS version of the RPM package * **FIPS:** Build FIPS compliant version of the maverics docker image * **Config:** Merge TLS settings from environment variables with Maverics config * **MCP Provider:** Separate inbound and outbound authorization in support of token exchange * **Connectors:** Add token exchange to OIDC connector * **Config:** Merge TLS settings with Windows environment variables * **MCP Provider:** Enhance observability and context around policy decisions * **MCP Provider:** Add ability to make policy decisions based on the source IP address * **MCP Provider:** Add base MCP docs for provider and bridge apps * **MCP Broker:** Improve documentation * **MCP Provider:** Use context bound logger in bearer token middleware * **Security:** Fix mTLS security issue by starting with an empty cert pool when constructing 'ClientCAs' used in TLS configs * **OIDC Provider:** Add option to configure refresh token lifetime * **MCP Bridge:** Add basic Rego authorization policy **Resolved Issues** * Fixed an issue that prevented the Orchestrator from starting when loading configuration bundles larger than 1 MB from a GitHub repository. **New Features** * **Service Extensions:** Expose functions from the secp256k1 pkg to Service Extensions **Resolved Issues** * **OIDCProvider:** Support token revocation from `client_credentials` grant * **Config:** Allow float when setting TLS Min Version **Resolved Issues** **OIDC Provider** This release resolves an issue with the end-session endpoint not supporting POST requests. As per the [spec](https://openid.net/specs/openid-connect-rpinitiated-1_0.html), both GET and POST requests are now supported. This release also resolves an issue with how redirect URIs are matched. The matching logic has been updated to not consider query params when validating the requested redirect URI against the pre-defined set of allowed redirect URIs. **New Features** **OIDC applications** OIDC apps now support defining allowed origins and allowed credentials for CORS requests. For more information, please see the [CORS](https://developer.strata.io/orchestrator/configuration/app/oidc/#cors) documentation. **New Features** **Cloud Configuration Storage Providers** Blob Storage in Azure Gov Cloud cloud can now be defined as a configuration storage provider. For more information, [read the docs](https://developer.strata.io/orchestrator/setup/remote-config/#azure-blob-storage). **Secrets Providers** Key Vault in Azure Gov Cloud can now be defined as a secret provider. The entraIDHost query parameter as part of the MAVERICS\_SECRET\_PROVIDER environment variable connection string. For more information, please see the [Azure Key Vault docs](https://developer.strata.io/orchestrator/setup/secrets-management/#entra-id-host-option). **OIDC Provider** The OIDC provider can now optionally correlate back-channel requests with the resource owner’s session. This can help you trace backchannel token requests to the resource owner. For more information, please see OIDC Provider [Session Correlation](https://developer.strata.io/orchestrator/configuration/providers/oidcprovider/#session-correlation). **OIDC applications** OIDC apps now support the insecureSkipPKCE option. This field can be used to bypass using PKCE when using the Authorization Code grant type for public clients. **ATTENTION**: Per [OAuth 2.0 Security Best Current Practice](https://datatracker.ietf.org/doc/html/draft-ietf-oauth-security-topics#section-2.1.1), public clients MUST use PKCE when using the Authorization Code grant type. The insecureSkipPKCE option should only be used for legacy apps that are unable to use PKCE. Avoid using this configuration unless absolutely necessary. **New Features** **Connectors** The offline access [feature](https://developer.strata.io/orchestrator/configuration/connectors/oidc-connector/#offline-access) found on OIDC connectors now ensures revoked ID token claims do not remain on the user's session. This change bolsters security by guaranteeing claims removed at the IDP do not remain on a user's session after a successful refresh request. **Resolved Issues** **Connectors** SAML connectors now set the Maverics session cookie as part of SAML login flows. This fix ensures sticky session configurations that use application cookie persistence will continue to operate as expected. **OIDC Provider** The OIDC Provider now removes whitespace around redirect URLs. **New Features** **Connectors** The OIDC and Azure connectors now support silently refreshing a resource owner's ID token and access token without user interaction. For more information, please see the [docs](https://developer.strata.io/orchestrator/configuration/connectors/oidc-connector/). **OIDC Apps** This release adds basic support for the token exchange grant (RFC 8693). Future releases will include additional functionality for the handling of custom scopes and for defining advanced access policies. For more information, please see the [docs](https://developer.strata.io/orchestrator/configuration/providers/oidcprovider/). **New Features** **Applications** All application types now support aggregating authorization policy rules with different logical operators. This feature enables the creation of advances policies. For more information, please see the application [docs](https://developer.strata.io/orchestrator/configuration/app/). **Security enhancements** Patched security and performance related issues. Contact your account representative for a detailed overview. **New features** **Session Management** This release introduces revamped session management in order to improve security, enhance performance, and to enable pluggable backing data stores. For more information, read the docs: [https://developer.strata.io/orchestrator/configuration/globalsettings/sessions-user-state/](https://developer.strata.io/orchestrator/configuration/globalsettings/sessions-user-state/) **Resolved Issues** * Resolved CVE-2025-49140 and CVE-2025-49140 **New Features** **OIDC Applications** OIDC applications can now be configured to use a default redirect URL. This option can be used for applications that are unable to set the `redirect_uri` parameter on the authorization request. For more information, see the [docs](https://developer.strata.io/orchestrator/configuration/app/oidc/#default-redirect-url) ATTENTION: Per the OIDC RFC, the `redirect_uri` is a [required](https://openid.net/specs/openid-connect-core-1_0.html#AuthRequest) parameter. The `allowDefaultRedirectURI` option should only be used for apps that are unable to provide a redirect URI. Strata recommends to avoid using this configuration unless absolutely necessary. **New Features** **SAML Provider** The SAML Provider now has the ability to load the signing certificate and key from the filesystem. For more details, please see the [docs](https://developer.strata.io/orchestrator/configuration/providers/samlprovider/#signature). **Service Extensions** Service extensions can now leverage the `IsAvailable` method on the `idfabric.IdentityProvider` interface. This feature enables service extensions to determine whether a given IDP is available. For more info, please see the [docs](https://github.com/strata-io/service-extension/blob/main/idfabric/idfrabric.go#L19-L22). **Resolved Issues** **OIDC Apps** This change adds the missing `at_hash` and `c_hash` claims to ID token during hybrid and implicit flows. These claims were previously missing and are required by the RFC. **Service Extensions** When calling `Login` with a nil HTTP request or response writer a runtime panic will no longer occur. **New Features** **Support for ROPC login option in Azure and Continuity identity services** The Azure and Continuity identity services have been updated to support authentication via the Resource Owner Password Credentials (ROPC) grant. Service extensions can leverage the `WithGrantTypeROPC` login option to specify an ROPC flow for authenticating a user. This flow is typically used for legacy applications that require a username and password to authenticate the user directly. For more information, please see the [docs](https://github.com/strata-io/service-extension/blob/main/idfabric/idfrabric.go#L95-L99). **New Features** **Support for ROPC login option in OIDC identity service** Service extensions can now leverage a new login option that enables authentication via the Resource Owner Password Credentials (ROPC) grant. The `WithGrantTypeROPC` function specifies the ROPC flow for authenticating a user. This flow is typically used for legacy applications that require a username and password to authenticate the user directly. For more information, please see the [docs](https://github.com/strata-io/service-extension/blob/main/idfabric/idfrabric.go#L95-L99). NOTE: Strata does not recommend using the ROPC flow for public facing applications. The OAuth 2.1 spec suggests a more secure flow, such as Authorization Code (with PKCE). For more information, see [https://pkg.go.dev/github.com/strata-io/service-extension@v0.22.0/idfabric#WithGrantTypeROPC](https://pkg.go.dev/github.com/strata-io/service-extension@v0.22.0/idfabric#WithGrantTypeROPC) **New Features** **Support for multiple SAML entity IDs** This release introduces support for defining multiple entity IDs on a SAML app. This functionality is compatible with both SP-initiated logins and IDP-initiated logins. For more information, please see the [docs](https://developer.strata.io/orchestrator/configuration/app/saml/). **New Features** **HYPR** The HYPR connector now exposes a dynamic link and QR fallback code that can be used in custom login page templates. These fields serve as backup mechanisms for when scanning the QR code via the HYPR app fails. For more info, please see the [docs](https://developer.strata.io/orchestrator/configuration/connectors/hypr-connector/#custom-interstitial-page). **New Features** **OIDC Apps** OIDC apps now support PKCE for public clients. This functionality enables applications that cannot securely store client credentials to interact with the Orchestrator as an OIDC Provider. For more information, please reference the [documentation](https://developer.strata.io/orchestrator/configuration/app/oidc/#public). **New Features** **Config Parsing** This release introduces strict configuration validation. Any unknown fields, misspellings, or unrecognized keys will cause an immediate validation failure. These changes are intended to ensure configuration correctness and eliminate silently ignored errors that may lead to unexpected behavior. **Breaking Changes** Orchestrator v2025.05.1 removes many long-deprecated features. All removed features have a migration path to a supported substitute feature set. For more information, please reference the deprecation advisory notice issued in November 2024 **New features** **Use Authorization Service Extension and Conditional Policies for authorization** This release introduces the ability to use the IsAuthorized service extension and authorization rules together. This allows more granular control of user authorization to protected resources. This feature is supported on SAML, OIDC, and Proxy apps. Note: Both the authorization service extension and the authorization rules must be validated as true to grant a user access. If either validates as false, the user is denied access. For more details see [Authorization](https://developer.strata.io/orchestrator/configuration/app/oidc/#isauthorized-service-extension). **Custom Unauthorized Page for SAML Apps** SAML apps now support an error page for unauthorized users. Custom unauthorized pages for SAML apps will be configurable from the user interface in an upcoming release of the Maverics Console. **New features** **Support for custom query parameter in Entra ID (OIDC) and generic OIDC identity services** Orchestrator now supports routing a custom query parameter to a declared Entra ID or OIDC IDP via service extension. Orchestrator passes the query parameter which then gets captured by the browser. Service extensions should be updated per the Go documentation for idfabric: [https://pkg.go.dev/github.com/strata-io/service-extension@v0.20.0/idfabric](https://pkg.go.dev/github.com/strata-io/service-extension@v0.20.0/idfabric) **Field ordering of orchestrator logs** Readability of orchestrator logs can be improved by enabling `fieldOrdering` (optional). `fieldOrdering` organizes the fields in the log output, setting values in the following order: `ts` , `level`, `service`, `traceID`, `sessionID`, and `msg`. Please note that enabling `fieldOrdering` will impact orchestrator performance. If performance must remain optimal, Strata recommends leaving this option disabled. For more information, see [Logging](https://developer.strata.io/orchestrator/configuration/monitoring/logger/#field-ordering). **New features** **Orchestrator heartbeat** The Orchestrator now includes a heartbeat. This lightweight service logs runtime details at a configurable time interval. Enabled by default, the heartbeat service prints a log message containing the orchestrator ID, orchestrator version, orchestrator config version, as well as CPU count, usage, and total memory. By default, the heartbeat service logs at the info level. The heartbeat service is part of the Health configuration block. It will be configurable from via user interface in an upcoming release of the Maverics Console. For more information, see [Heartbeat](https://developer.strata.io/orchestrator/configuration/monitoring/health/#heartbeat). **Access logs enabled by default** HTTP access logs are now enabled by default. This change is meant to provide customers with greater insight into how requests flow through the system and can be used to confirm that all requests result in a corresponding response. By default, access logs are logged at the debug level. If desired, access logs can be disabled via the orchestrator config. Access logs will be configurable from via user interface in an upcoming release of the Maverics Console. For more information, see [Access Logs](https://developer.strata.io/orchestrator/configuration/globalsettings/http-server/#accesslog). **LDAP custom login page and localization** Orchestrator v0.111.0 introduces support for an optional custom login page when using LDAP as an IDP. By defining `customLogin` in the orchestrator configuration, the orchestrator delivers a custom HTML page stored in the filesystem. In addition, the custom login page now supports standards-based language localization (BCP 47). By default, the localization selection is driven from the `Accept-Language` header, but can be customized to meet deployment specific needs. LDAP custom login and localization will be configurable from via user interface in an upcoming release of the Maverics Console. For more information, see [Custom Login](https://developer.strata.io/orchestrator/configuration/connectors/ldap-connector/#custom-login). **New features** **Logging enhancements** * Logs in the `CreateHeader` service extension have been updated to include `traceID`, `sessionID`, and `service` attributes. * API service extensions can now leverage a newly exposed function that allows for retrieving a logger from the context of a request. The `log.WithRequest` function can be used to ensure logs include the `traceID` and `sessionID` attributes. For more information, refer to the [API examples](https://docs.strata.io/orchestrator/configuration/api/#examples). INFO Customers running API service extensions must update their service extensions to use the new function ONLY if they want to their logs to include `traceID` and `sessionID`. Strata advises customers to first test this new orchestrator release against their existing API service extensions in a lab or lower environment to ensure their service extensions continue to operate normally. For more information, refer to [Serve Service Extension](https://docs.strata.io/orchestrator/configuration/api/#serve-service-extension). **Resolved issues** This release resolves an issue in which orchestrator telemetry data was being sent to the Maverics Console even though telemetry was disabled. This issue was introduced in v0.107.0 and only impacts customers that are using Maverics Console. **New features** **Logging enhancements** Logs in the following identity services have been updated to include `traceID` and `service` attributes: * 1Kosmos * HYPR * PingFederate * SAML * Windows Client Authenticator (WCA) * WSO2 API service extension logs have been updated to include `traceID`, `service`, 'seName', 'seFuncName', and 'seChecksum' attributes. **Resolved issues** * This release resolves an issue in which re-authentications triggered by session expiry would fail when an OIDC identity provider using PKCE. * **APIs:** Enhance API SE logger with attributes by (#2879) * **Connectors:** Use contextual logger in PingFederate connector (#2873) * **Connectors:** Use contextual logger in SAML connector (#2876) * **Connectors:** Use contextual logger in 1Kosmos connector (#2872) * **Connectors:** Use contextual logger in WSO2 connector (#2877) * **Connectors:** Use contextual logger in HYPR connector (#2869) * **Connectors:** Use contextual logger in WCA connector (#2875) * **Session:** Resolved issue causing newly Set attributes to have an expiry in the past (#2878) **New Features** Orchestrator v0.108.0 adds improvements to observability, including HTTP access logs, contextual logging, tracing, and standard telemetry. These changes provide more detailed logs for better insight into transactions from all areas of the orchestrator including service extensions. **HTTP Access Logging** All HTTP requests and responses are now optionally logged. Access logs are logged at debug level by default. Currently, access logs can be enabled/disabled in the orchestrator config. Access logging can be enabled/disabled from the user interface in a forthcoming update to Maverics Console. For more info, please see the [reference docs](https://docs.strata.io/orchestrator/configuration/globalsettings/http-server/#accesslog). **Logging** The logger now includes a `traceID` attribute in log messages that can be used to trace requests through the system. Additionally, logs now include the `service` key to help clearly identify the source of logs. For service extensions, the `seName`, `seFuncName`, and `seChecksum` keys are also now included. **Security enhancements** * **Security:** Resolved CVE-2025-22872 Internal improvements and maintenance updates. * **Security:** Resolved CVE-2025-29923 * **Session v2:** Fix Cache Store Configuration * **Dependencies:** Resolved CVE-2025-22870 Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **OIDC Provider:** Expose config to disable the DPoP nonce * **Connectors:** Preserve query parameters during LDAP logout * **OIDC Provider:** Add customizable response\_mode to implicit flow Internal improvements and maintenance updates. * **Connector:** Implement LDAP connector Logout method * **OIDC Provider:** Correct 'response\_types\_supported' and 'grant\_types\_supported' attributes of well-known response * disable jfrog and e2e for testing orchestrator release process change Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **OIDC Provider:** Add implicit grant type Internal improvements and maintenance updates. * **Security:** Resolved CVE-2025-27144 Internal improvements and maintenance updates. * **OIDC Provider:** Fix introspect endpoint not handling custom nested claims * **Security:** Resolved CVE-2025-22869 * **Connectors:** Add support for error page to Auth0 connector * **Connectors:** Add support for silent authentication to Auth0 connector Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **OIDC Provider:** Ensure reload works successfully when the end session endpoint is defined Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **Secret Provider:** Add support for multiple secret paths in hashicorp vault secret provider * **Secret Provider:** Load Hashicorp Vault secrets lazily Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **OIDC Provider:** Expose DPoP-Nonce header to support CORS * **OIDC Provider:** Harden DPoP implementation Internal improvements and maintenance updates. * **OIDC Provider:** Add support for dpop nonce validation * **Observability:** Add new telemetry config format for metrics Internal improvements and maintenance updates. * **OIDC Provider:** Add support for dpop checking at userinfo endpoint * **OIDC Provider:** Add support for DPoP bound refresh tokens * **Proxy Apps:** Resolved attribute providers config not being respected Internal improvements and maintenance updates. * **OIDC Provider:** Add support opaque access tokens when using DPoP * **Security:** Resolved CVE-2024-45339 Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. * **OIDC Provider:** Update metadata endpoint to return DPoP signing algorithms * **OIDC Provider:** Add support for DPoP bound access tokens Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. Internal improvements and maintenance updates. # 2026 Source: https://docs.strata.io/changelog/orchestrator/2026 * **OAuth Connector:** Accept `expires_in` as a quoted string in token responses, fixing compatibility with identity providers that return the field as a string value rather than a number. * **OAuth Connector:** Fix scopes not being sent during dynamic client registration. * **OIDC Connector:** Add [RFC 7591 Dynamic Client Registration](/reference/orchestrator/identity-fabric/oauth#dynamic-client-registration) support. OIDC connectors can now register with identity providers dynamically, removing the need to pre-configure a static client ID and secret when the IdP supports Dynamic Client Registration. * **OIDC Connector:** Add [Client ID Metadata Document (CIMD)](/reference/orchestrator/identity-fabric/oauth#client-id-metadata-document) support. OIDC connectors can now authenticate using URL-based client IDs, with the connector fetching and validating the Client ID Metadata Document at runtime. * **OPA:** Add `jwt.parse_bearer` built-in function for Rego policies. Policies can now parse and inspect JWT bearer tokens directly without a service extension. * **MCP Provider:** Fix intermittent tool listing failures when multiple concurrent requests were in-flight simultaneously. ### Security Improvements ### Proxy apps * Authorization policy is now evaluated against the same normalized request path that is forwarded upstream, giving consistent policy matching for URLs that contain encoded characters or path parameters. * The mutual-TLS host guard now normalizes the Host header (case and port) before matching a request to its virtual host, so requests are consistently associated with the intended host configuration. ### OIDC Provider The form\_post authorization response now HTML-escapes the redirect URI when rendering the auto-submitting form, ensuring redirect URIs containing reserved characters are handled correctly. ### Feature Deprecations The following features have been removed from the Orchestrator and are no longer supported: * (Experimental) Orchestrator Clusters * LDAP Provider: Remove SASL, GSS-SPNEGO, and NTLM authentication mechanisms ### Enhancements * OIDC Provider: Add support for complex types in access token claims mapping * OIDC Provider: CIMD apps now only issue refresh tokens when explicitly requested and when administrator-enabled ### Bug Fixes * **Config:** Pre-flight config validation prevents startup loop. The Orchestrator now validates configuration before starting up, preventing a bad config from causing a crash-restart loop. Invalid configurations are rejected at startup with a clear error instead. * **MCP Proxy:** MCP tools list correctly handles unreachable upstreams. list-tools calls no longer fail when one or more upstream MCP servers are unreachable. Available tools are returned from reachable upstreams while unreachable ones are skipped gracefully. * **MCP Provider:** `WWW-Authenticate` header uses absolute URL for `resource_metadata`. The `resource_metadata` field in `WWW-Authenticate` challenge responses now correctly returns an absolute URL, fixing compatibility issues with MCP clients that use it to locate the protected resource metadata document. * **OIDC Provider:** Access token claims mapping applied to CIMD clients. `accessToken.claimsMapping` configuration is now correctly applied when issuing tokens to OIDC CIMD apps. Previously, claims mapping was accepted by the config but silently ignored for CIMD clients. * **OIDC Provider:** Add support for claims mapping for access tokens * **OAuth Connector:** Improve login callback validation and avoid unnecessary JWKS fetches during authentication * **OIDC Connector:** Fix PKCE generation to exclude special characters * **MCP Provider:** Reconcile proxied tools per session, ensuring MCP clients see a consistent and current tool list throughout a session. * **Orchestrator:** Add support for graceful process restarts, reducing downtime during config changes and enabling everything except ports to be updated without a full restart. * **OIDC Provider:** Refresh upstream access tokens during passthrough token brokering * **Licensing:** Updated terms and conditions URL in startup event log to point to the current Rubrik–Strata service agreement * **Authenticate Service Extension:** Add `idfabric.WithForceAuthentication()` support. When called from `authenticateSE`, the connector is instructed to actively re-authenticate the user with the IdP even if an existing session is present. The SAML connector is the first to implement this, sending `ForceAuthn="true"` on the AuthnRequest. See the [documentation](/reference/orchestrator/service-extensions/proxy#force-re-authentication-on-every-login) for configuration details. * **MCP Proxy:** Add OPA-based tool listing control via a new `listing` authorization block. The policy is evaluated once per tool in every `tools/list` response from the upstream server; only tools where the policy returns `allowed=true` are forwarded to the client. Policies evaluate against upstream tool names before namespace prefixing, keeping them consistent with `inbound` call-time policies. See the [documentation](/reference/orchestrator/applications/mcp-proxy#tool-filtering-opa) for configuration details. ## \[Experimental] Client ID Metadata Documents (CIMD) The Orchestrator now supports dynamic OAuth client registration via URL-based client IDs, implementing `draft-ietf-oauth-client-id-metadata-document`. AI agents and MCP clients (Claude Code, ChatGPT) can authorize without being pre-registered — the Orchestrator fetches and validates the client's metadata document at runtime. Configure using the new `oidcCimd` app type. See the [full documentation](https://docs.strata.io/reference/orchestrator/experimental/client-id-metadata-documents) for configuration reference and examples. ### Security * Resolved security issues ## Hardened encryption of Redis-cached values This release strengthens how the Orchestrator encrypts values stored in an external Redis cache. The on-disk format of cached entries has changed as a result. No action required on upgrade. The Orchestrator adopts the new format automatically. Entries written by earlier versions are ignored and expire on their own TTL if configured with a TTL. You do not need to flush or modify Redis, and no users are signed out — session stores do not use the Redis cache. **What to expect after upgrading:** * **OIDC Provider.** Refresh tokens issued before the upgrade are invalidated. Applications re-authorize on their next refresh; for users with an active session this is seamless, with no sign-in prompt. Existing JWT access tokens remain valid until they expire. The transition completes within your refresh-token lifetime (default 24 hours). Clients that authenticate without a user session, such as machine-to-machine clients, may need to re-authenticate once. Existing opaque access tokens will need to be re-issued. * **SAML Provider.** Flows in progress at the moment of upgrade may need to be retried. Established sessions are unaffected. * **Service Extensions.** Cached entries from before the upgrade are treated as misses and repopulated on next use. If an extension combines direct key access (disable-prefix) with value encryption, re-write previously stored values, as they are unreadable in the new format. * **Multi-node deployments.** Complete the rollout promptly. Mixed-version clusters may not share cached entries, causing a temporary rise in re-authentications until all nodes are upgraded. ### Fixes * **OIDC Provider:** Return HTTP 400 for login callback failures caused by client errors Internal improvements and maintenance updates. ## Filter MCP tools by access token MCP Proxy apps can now apply an OPA **connection authorization** policy that decides, per upstream MCP server, whether the gateway connects to it and lists its tools — evaluated against the caller's access token. Instead of surfacing every upstream's tools to every client, you can scope which tools each session sees based on identity. * **MCP Proxy:** Add OPA policy support for connection authorization, filtering which upstream MCP tools are exposed to a session based on the access token ## Deployments * **Google Cloud Config Storage:** Add read-only scope and workload identity support for the GCP config provider ### Fixes * **MCP Provider:** Fix HTTP deadline not being cleared when MCP is enabled, which could cause requests to time out unexpectedly * **MCP Proxy:** Clean up upstream MCP sessions when the downstream session ends * **Service Extensions:** Fix configuration bundle asset access for proxy app's `CreateHeader`, single logout's `ParsePostLogoutSE`, and session's `ParseEvalIdleTimeoutSE` and `ParseEvalMaxLifetimeSE` service extensions * **OIDC Apps:** Allow non-identity-provider namespaces to be used in token brokering exchange template interpolation * **MCP Proxy:** Fixed token audience validation so a token is accepted when any one of its listed audiences matches an expected value, instead of being rejected unless all audiences matched. * **MCP Proxy:** Fixed a signature verification issue that could block requests when multiple MCP servers are configured. * **Token Brokering (experimental):** Add [Federated Exchange](/reference/orchestrator/experimental/token-brokering) flow, where the Orchestrator mints a short-lived JWT and exchanges it with an upstream authorization server (e.g., Databricks, GCP Workload Identity Federation). Mappings also support dynamic claim values via templating interpolation. * **OIDC Connector:** Add `disableClientAuthentication` for federation flows where the upstream authenticates via the subject token alone (e.g., Databricks account-wide federation) * **OIDC Provider:** Add support for RFC 7638-compliant JWK thumbprints as the `kid`. Opt in per signing key with `useRFC7638Thumbprint: true` — coordinate with relying parties first, since the `kid` will change. * **OIDC Client:** Cache the actor token used in `client_credentials`-backed token exchange requests * **OIDC Provider:** Allow clients with only non-interactive grants to omit authentication * **Telemetry:** Add support for v1 OTel configuration * **Security:** Resolved security issues * **Config:** Fixed `MAVERICS_DEBUG_MODE=true` being silently ignored when a `logger:` block was configured. Setting the env var now correctly forces DEBUG-level logging as documented. ## What's new **MCP** Significantly expanded MCP observability so operators can run at info and still get full session traceability and audit coverage — no more flipping to debug to reconstruct what happened. * Every MCP request log now carries a hashed mcpSessionID, giving you end-to-end correlation across a client-to-Maverics session without exposing the raw Mcp-Session-Id credential. * Proxy-path logs also carry an upstreamMCPSessionID, so you can follow a single interaction from the client, through Maverics, to the upstream MCP server on the same line. * Every tool call emits a single tool call completed log at info with an outcome of success, tool\_error, or failed — consistent across bridge and proxy modes. * Every list-tools call emits a single list tools completed log at info with the outcome and tool count. * Session register/unregister and upstream session established/terminated events are now surfaced at info. * Raw session IDs never appear in logs or traces. ### Fixed **MCP Proxy** Fixed an issue where responses from upstream MCP servers using gzip compression could reach the client corrupted or unreadable. Compressed responses are now handled correctly. ### Improvements **Logging** Audit and security events now log at info level. This makes them visible in standard log pipelines without needing to lower global log thresholds, so your SIEM and observability tooling will pick them up by default. * **Logout:** Fix bug where logout redirect URLs containing pre-existing query parameters (e.g., Azure B2C custom policy endpoints with `?p=`) produced malformed URLs with duplicate `?` characters, causing downstream parameters like `id_token_hint` and `state` to be silently dropped * **MCP Proxy:** Fix path parameter handling and improve tolerance for common schema quirks in MCP bridge apps built from OpenAPI specs * **OIDC Provider:** Add [token brokering](/reference/orchestrator/experimental/token-brokering) (experimental) to the OIDC provider. Clients can exchange a Maverics access token for upstream service tokens using standard RFC 8693 token exchange. The initial release supports session passthrough mode, which returns a cached upstream token. Token brokering integrates with existing OPA token minting policies for authorization. * **Telemetry:** Add W3C `traceparent` header propagation to maintain a stable traceID across the entire request lifecycle. When a request enters the Orchestrator, the traceID is preserved and forwarded to all downstream services — including identity providers and MCP endpoints — enabling true end-to-end distributed tracing with a single, consistent identifier. This is especially valuable when the Orchestrator acts as an auth provider to an AI Identity Gateway, where a single user prompt can trigger a chain of token exchanges, policy evaluations, and tool invocations across multiple services. With a stable traceID, operators can trace an AI gateway request from initial authentication through policy evaluation, token minting, and downstream MCP tool calls, correlating every hop in a single distributed trace. * **SAML Provider:** Make NameID name qualifiers optional * **SAML Provider:** Fix WS-Fed name claim incorrectly being included in SAML assertions * **SAML Provider:** Correct XML namespacing across all SAML response types * **Telemetry:** Add stable Secure Orchestrator ID (`soid`) to all log entries and OTel telemetry (`service.instance.id`) for deployment correlation * **OIDC Connector:** Add configurable error handling for authentication callbacks * **OIDC Provider:** Fix state parameter encoding in form post response mode * **Security:** Resolved security issues * **MCP Proxy:** Gracefully re-establish session with the upstream MCP server and retry the request when the session is terminated * **Proxy Apps:** Allow service extensions to be reused across all application types by loosening namespace validation * **Connectors:** HYPR connector now reads custom HTML files from the configuration bundle * **MCP Proxy:** Gracefully re-establish sessions with upstream and retry requests when a session is terminated * **Proxy Apps:** Allow service extensions to be reused across all app types * **Connectors:** Support reading custom HTML files from the configuration bundle for Hypr integrations * **TLS:** Add max version configuration for all TLS settings * **Session:** Fixed an issue where empty sessions were persisted when the SLO endpoint terminated an unestablished session * **MCP Proxy:** Add configurable scopes and token lifetimes for all MCP protocol operations * **Security:** Resolved security issues * **Security:** Resolved CVE-2026-2405 * **MCP Proxy:** Respect outbound authorization policy when making list tools requests * **SAML Apps:** Enable claims mapping and the BuildClaims service extension to be used together * **MCP Proxy:** Explicitly handle session termination errors that are returned from the upstream * **OIDC Connector:** Add client assertion authentication mechanism (rfc 7523) * **OIDC Connector:** Add support for JWT client assertion authentication as part of the token exchange grant * **OIDC Provider:** Demonstrate JWT client authentication can be used with authcode, token-exchange grants * **OIDC Provider:** Make openid scope and scope param optional * **SAML Provider:** Ensure SAML Response elements are ordered correctly * **OIDC Provider:** Add Subject and Actor token claims to token minting policy # Connect ChatGPT to the AI Identity Gateway Source: https://docs.strata.io/guides/ai-identity/connect/chatgpt Connect ChatGPT to the AI Identity Gateway so that ChatGPT can discover and invoke MCP tools with full identity, authentication, and authorization on every call. When ChatGPT connects to the AI Identity Gateway as an MCP client, it goes through the standard OAuth discovery flow -- discovering the authorization server from the Gateway's protected resource metadata (RFC 9470), authenticating the user, and obtaining an access token. From there, ChatGPT can discover and invoke any MCP tools the Gateway exposes through [MCP Bridge](/guides/ai-identity/mcp-bridge) or [MCP Proxy](/guides/ai-identity/mcp-proxy) apps. ## How ChatGPT's Token Works ChatGPT authenticates the user and sends a standard OAuth access token where the `sub` claim is the authenticated user. The token does **not** include delegation semantics -- there is no `act` claim or separate agent identity. From the token alone, the Gateway cannot distinguish "ChatGPT acting on behalf of the user" from "the user directly." This has implications for how the Gateway evaluates and processes requests: * **Inbound authorization policies** operate on the token as received. Since ChatGPT does not perform a token exchange before calling the Gateway, inbound OPA policies see only the claims in the access token -- user identity claims (`sub`, `email`, `groups`, etc.) and the `client_id` identifying the OAuth client. The `client_id` is a required claim in JWT access tokens per [RFC 9068](https://datatracker.ietf.org/doc/html/rfc9068#name-data-structure), so admins can write policies that target ChatGPT traffic by matching on it. When using CIMD, the `client_id` is a URL (e.g., `https://chatgpt.com/oauth/{id}/client.json`) rather than a simple string -- see the policy example in [Harden Tool Access](#harden-tool-access-with-inbound-authorization-policies). * **Outbound token exchange** is where the Gateway adds delegation semantics. When the Gateway performs [RFC 8693](https://datatracker.ietf.org/doc/html/rfc8693) token exchange to call upstream APIs via MCP Bridge or MCP Proxy, it can mint delegation tokens with an `act` claim that includes the agent's client identity. This gives upstream services visibility into both the user and the agent that initiated the request. ChatGPT uses [OAuth Client ID Metadata Documents (CIMD)](https://datatracker.ietf.org/doc/draft-ietf-oauth-client-id-metadata-document/) natively, presenting a verifiable HTTPS URL as its `client_id`. This is a meaningful improvement over agents that use self-asserted client identity strings -- the Auth Provider Orchestrator fetches and validates the metadata document, giving inbound policies a cryptographically grounded client identity to match on. ## Prerequisites * **A running AI Identity Gateway** -- Follow the [AI Identity overview](/guides/ai-identity/overview) to set up the Auth Provider Orchestrator and AI Identity Gateway Orchestrator with at least one MCP Bridge or MCP Proxy app configured. * **OAuth authorization enabled on the MCP Provider** -- The Gateway's `mcpProvider.authorization.oauth` must be enabled so ChatGPT can authenticate. See the [AI Identity Gateway reference](/reference/modes/ai-identity-gateway) for configuration details. * **ChatGPT Business or Enterprise/Edu account** -- Creating and publishing workspace apps requires a Business or Enterprise/Edu workspace. Owners and Admins can publish apps; individual members install them. ## Register ChatGPT as an OAuth Client Configure the **Auth Provider Orchestrator** to accept ChatGPT using [Client ID Metadata Documents (CIMD)](/reference/orchestrator/experimental/client-id-metadata-documents). CIMD eliminates the need to pre-register a client ID, secret, redirect URLs, or scopes -- a single `oidcCimd` app with `allowedDomains: [chatgpt.com]` is all that is required. See the [CIMD reference](/reference/orchestrator/experimental/client-id-metadata-documents) for configuration steps and options. ## Connect ChatGPT to the Gateway Once the Auth Provider Orchestrator is configured, a workspace Owner or Admin creates and publishes the ChatGPT app so that workspace members can install it. ChatGPT routes all MCP traffic through OpenAI's infrastructure, so the AI Identity Gateway and Auth Provider Orchestrator must both be accessible from the public internet. ChatGPT connects to the AI Identity Gateway through OpenAI's infrastructure. The Gateway and Auth Provider Orchestrator must both be publicly accessible -- local or private network URLs (e.g., `localhost`, `127.0.0.1`, private DNS) will not work without tunneling. **Admin setup:** Go to **[chatgpt.com/admin/apps](https://chatgpt.com/admin/apps)**. You must be a workspace Owner or Admin to access this page. Click **+ Create**. The **New App** dialog opens. Enter a **Name** and optional **Description** for the app. Under **Connection**, ensure **Server URL** is selected and enter the AI Identity Gateway's MCP endpoint: ``` https://your-gateway.example.com/mcp ``` Click **Advanced OAuth settings** to open the OAuth configuration panel. Ensure **Authentication** is set to **OAuth** and that the **Registration method** shows **Client Identifier Metadata Document (CIMD)**. ChatGPT selects both automatically based on what the Auth Provider supports. Check the **I understand and want to continue** box, then click **Create**. ChatGPT saves the app as a draft. In the **Drafts** tab, click **Publish** next to your app. Review and acknowledge each security risk section, check both confirmation boxes, and click **Publish** to confirm. The app moves to the **Enabled** tab with a **CUSTOM** label and becomes visible to all workspace members. **Member setup:** Each workspace member authenticates individually to ensure ChatGPT only accesses tools the member is authorized to use: 1. In ChatGPT, click **Plugins** in the left sidebar. 2. Click the workspace tab (your organization's name) to see apps published by your admin. 3. Find the AI Identity Gateway app and click **+** to install it. 4. Complete the OAuth flow -- authenticate with your identity provider when prompted. Once connected, the Gateway's MCP tools are available in conversations. ## Verify the Connection After connecting, verify that ChatGPT can discover and invoke tools from the AI Identity Gateway. 1. **Check tool discovery** -- Ask ChatGPT to list available tools. ChatGPT should display the MCP tools exposed by your MCP Bridge and MCP Proxy apps. 2. **Invoke a tool** -- Ask ChatGPT to call one of the discovered tools. The AI Identity Gateway authenticates the request, evaluates authorization policies, performs token exchange, and returns the result. 3. **Check the Orchestrator logs** -- The AI Identity Gateway Orchestrator logs show the complete request flow: agent authentication, OPA policy evaluation, token exchange, and upstream API call. Verify that all steps completed successfully. If ChatGPT cannot discover tools or tool invocations fail, see the troubleshooting sections in the [Expose APIs to Agents](/guides/ai-identity/mcp-bridge#troubleshooting) and [Protect MCP Servers](/guides/ai-identity/mcp-proxy#troubleshooting) guides. # Connect Claude to the AI Identity Gateway Source: https://docs.strata.io/guides/ai-identity/connect/claude Connect Claude Desktop, Claude Code, or claude.ai to the AI Identity Gateway so that Claude can discover and invoke MCP tools with full identity, authentication, and authorization on every call. When Claude connects to the AI Identity Gateway as an MCP client, it goes through the standard OAuth discovery flow -- discovering the authorization server from the Gateway's protected resource metadata (RFC 9470), authenticating the user, and obtaining an access token. From there, Claude can discover and invoke any MCP tools the Gateway exposes through [MCP Bridge](/guides/ai-identity/mcp-bridge) or [MCP Proxy](/guides/ai-identity/mcp-proxy) apps. ## How Claude's Token Works Claude authenticates the user and sends a standard OAuth access token where the `sub` claim is the authenticated user. The token does **not** include delegation semantics -- there is no `act` claim or separate agent identity. From the token alone, the Gateway cannot distinguish "Claude acting on behalf of the user" from "the user directly." This has implications for how the Gateway evaluates and processes requests: * **Inbound authorization policies** operate on the token as received. Since Claude does not perform a token exchange before calling the Gateway, inbound OPA policies see only the claims in the access token -- user identity claims (`sub`, `email`, `groups`, etc.) and the `client_id` identifying the OAuth client. The `client_id` is a required claim in JWT access tokens per [RFC 9068](https://datatracker.ietf.org/doc/html/rfc9068#name-data-structure), so admins can write policies that target Claude traffic by matching on it (e.g., `input.token.client_id == "claude"`). The token does not carry delegation semantics -- there is no `act` claim distinguishing "Claude acting on behalf of the user" from "the user directly." * **Outbound token exchange** is where the Gateway adds delegation semantics. When the Gateway performs [RFC 8693](https://datatracker.ietf.org/doc/html/rfc8693) token exchange to call upstream APIs via MCP Bridge or MCP Proxy, it can mint delegation tokens with an `act` claim that includes the agent's client identity. This gives upstream services visibility into both the user and the agent that initiated the request. Today, Claude's `client_id` is a self-asserted string (e.g., `"claude"`) with no cryptographic proof of the agent's identity. Because Claude is a closed platform, customers are limited to what Claude supports out of the box -- unlike custom agents or other AI clients, which can implement proof of possession, delegation chains, workload attestation, and other advanced identity patterns directly. Several emerging standards aim to address agent identity and delegation: * [**OAuth Client ID Metadata Documents (CIMD)**](https://datatracker.ietf.org/doc/draft-ietf-oauth-client-id-metadata-document/) strengthen client identity by using an HTTPS URL as the `client_id`. The authorization server fetches and validates the metadata document, providing verified (rather than self-asserted) client identity for policy decisions. * [**WIMSE**](https://datatracker.ietf.org/wg/wimse/about/) (Workload Identity in Multi-System Environments) and [**SPIFFE**](https://spiffe.io/) (Secure Production Identity Framework For Everyone) provide cryptographically attested workload identity, enabling agents to prove who they are independently of OAuth client registration. * The [**AI Agent Authentication and Authorization**](https://datatracker.ietf.org/doc/draft-klrc-aiagent-auth/) IETF draft ties these together, proposing that agents are workloads with WIMSE/SPIFFE identifiers and that access tokens carry dual identity: `client_id` as the agent's verifiable workload identity and `sub` as the delegated user. None of these standards solve delegation in isolation, but together they define a path toward tokens that carry both verified agent identity and user identity. Realizing this requires Claude to both establish a verifiable agent identity (via CIMD, WIMSE, or SPIFFE) **and** perform a token exchange before calling the Gateway -- producing a token that carries the user as the subject and the agent as the actor. Without token exchange, the token represents only the user regardless of how the agent identifies itself during the OAuth flow. Until Claude natively supports these patterns, the Gateway's inbound policies for Claude traffic can match on `client_id` and user identity claims but cannot distinguish delegation from direct access. Customers can use [service extensions](/reference/orchestrator/service-extensions) such as `buildAccessTokenClaimsSE` to construct an `act` claim that simulates delegation semantics by embedding the client identity as the actor. The service extension should derive these values from a trusted source within the Auth Provider's request context, not from upstream identity provider attributes that could be manipulated. ## Prerequisites * **A running AI Identity Gateway** -- Follow the [AI Identity overview](/guides/ai-identity/overview) to set up the Auth Provider Orchestrator and AI Identity Gateway Orchestrator with at least one MCP Bridge or MCP Proxy app configured. The Gateway must use the **Streamable HTTP** transport -- SSE is not supported by Claude's connector infrastructure. * **OAuth authorization enabled on the MCP Provider** -- The Gateway's `mcpProvider.authorization.oauth` must be enabled so Claude can authenticate. See the [AI Identity Gateway reference](/reference/modes/ai-identity-gateway) for configuration details. * **Claude Desktop, Claude Code, or a claude.ai account** -- Any Claude client that supports remote MCP servers works with this guide. Claude requires an interactive OAuth flow where a user authenticates via the browser. The `client_credentials` grant type (machine-to-machine OAuth with no user interaction) is not supported by Claude's MCP connector infrastructure. Register Claude with the `authorization_code` and `refresh_token` grant types. See the [Anthropic Connectors Directory FAQ](https://support.claude.com/en/articles/11596036-anthropic-connectors-directory-faq) for details on Claude's connector requirements. ## Choose a Client Type When you register Claude as an OAuth client with the Auth Provider Orchestrator, you choose between a **confidential client** or a **public client**. This choice affects how Claude authenticates to the authorization server. | | Confidential Client | Public Client | | ------------------ | --------------------------------------------------- | --------------------------------------------------------------------- | | **Authentication** | Client ID + client secret | Client ID + PKCE (no secret) | | **Security** | Stronger -- the secret proves the client's identity | Weaker -- relies on PKCE alone to protect the authorization code flow | | **Best for** | Claude Code (CLI), server-side integrations | Environments where a client secret cannot be securely stored | | **Grant types** | Authorization Code, Refresh Token | Authorization Code (with PKCE), Refresh Token | Use a **confidential client** whenever possible. Confidential clients authenticate with a client secret, which proves the client's identity to the authorization server and prevents unauthorized applications from exchanging authorization codes for tokens. Public clients rely solely on PKCE, which protects against code interception but does not authenticate the client itself. [OAuth Client ID Metadata Documents (CIMD)](https://datatracker.ietf.org/doc/draft-ietf-oauth-client-id-metadata-document/) address this gap by allowing public clients to use a verifiable HTTPS URL as their `client_id`, giving the authorization server a way to verify the client's identity without a shared secret. As the MCP ecosystem adopts CIMD and authorization servers add support, public clients will be able to provide verified identity comparable to confidential clients. Until then, use a confidential client when the deployment allows it, and pair public clients with [token minting policies](#harden-token-issuance-with-token-minting-policies) to compensate. ## Register Claude as an OAuth Client Register Claude as an OIDC application on the **Auth Provider Orchestrator** -- the same orchestrator deployment that issues tokens for the AI Identity Gateway. This gives Claude the credentials it needs to authenticate and obtain access tokens. Go to **Applications** in the sidebar and click **Create**. Select **OIDC-based** from the application type list. Enter a **Name** for the application (e.g., `Claude`). Enter a **Client ID** (e.g., `claude`). Leave **Client Authentication Method** set to **Client Secret**. Click **Add Client Secret** and enter a strong secret or a [secret provider](/reference/orchestrator/configuration/secret-providers) reference (e.g., ``). Store client secrets in a [secret provider](/reference/orchestrator/configuration/secret-providers) rather than entering them directly. Use secret reference syntax so the Orchestrator resolves the value at runtime. Click **Add Redirect URL** and add the redirect URLs for the Claude clients you plan to use: * **claude.ai and Claude Desktop:** `https://claude.ai/api/mcp/auth_callback` and `https://claude.com/api/mcp/auth_callback` * **Claude Code:** `http://localhost:{PORT}/callback` where `{PORT}` is a fixed port you choose (e.g., `http://localhost:29352/callback`). Users must pass `--callback-port {PORT}` when adding the MCP server in Claude Code. See the [Connect Claude Code](#connect-claude-to-the-gateway) section for details. * **Claude Desktop via mcp-remote:** `http://localhost:{PORT}/oauth/callback` (e.g., `http://localhost:3334/oauth/callback`). Note the `/oauth/callback` path -- this differs from Claude Code's `/callback` path. Under **Grant Types**, ensure the following are checked: * **Authorization Code** (under Recommended and Modern Flows) * **Refresh Token** (under Recommended and Modern Flows) Uncheck **Client Credentials** -- it is not needed for Claude's user-facing OAuth flow. Leave **Type** set to **JWT**. Optionally set **Lifetime Seconds** (default is 1 hour). Under **Refresh Token Settings**, toggle **Allow Offline Access** on. This lets Claude refresh expired access tokens without requiring you to re-authenticate. Click **Save** to create the OIDC application. Add a new OIDC app to the Auth Provider Orchestrator's configuration. The client uses the `authorization_code` and `refresh_token` grant types with a client secret for authentication. ```yaml maverics.yaml theme={null} apps: - name: claude type: oidc clientID: claude credentials: secrets: - grantTypes: - authorization_code - refresh_token redirectURLs: # claude.ai and Claude Desktop web connectors (routed through Anthropic) - https://claude.ai/api/mcp/auth_callback - https://claude.com/api/mcp/auth_callback # Claude Code -- fixed port via --callback-port (connects directly from user's machine) - http://localhost:29352/callback # Claude Desktop via mcp-remote -- note /oauth/callback path differs from Claude Code - http://localhost:3334/oauth/callback accessToken: type: jwt lifetimeSeconds: 3600 refreshToken: allowOfflineAccess: true lifetimeSeconds: 86400 authentication: idps: - upstream-idp claimsMapping: email: upstream-idp.email name: upstream-idp.name sub: upstream-idp.sub ``` The `redirectURLs` include all Claude clients: * **claude.ai and Claude Desktop** both use `https://claude.ai/api/mcp/auth_callback`. Include the `claude.com` variant as well to future-proof the configuration. * **Claude Code** uses `http://localhost:{PORT}/callback`. By default, Claude Code picks a random port, but since redirect URLs must be pre-registered, you must choose a fixed port (e.g., `29352`) and have users specify `--callback-port 29352` when adding the MCP server. * **Claude Desktop via mcp-remote** uses `http://localhost:{PORT}/oauth/callback` (note the `/oauth/callback` path, which differs from Claude Code's `/callback`). The default port is `3334`. Store the client secret in a [secret provider](/reference/orchestrator/configuration/secret-providers). Never hardcode secrets in configuration files. Go to **Applications** in the sidebar and click **Create**. Select **OIDC-based** from the application type list. Enter a **Name** for the application (e.g., `Claude Public`). Enter a **Client ID** (e.g., `claude-public`). You do not need to add a client secret -- public clients authenticate using PKCE instead. Under **Application Security Settings**, toggle **Public Client** on. This disables client secret authentication and restricts the available grant types to Authorization Code (with PKCE), Refresh Token, and Implicit flows. Public clients cannot authenticate themselves to the authorization server. Any application that knows the client ID can initiate an authorization flow. Only use public clients when you cannot securely distribute a client secret. Click **Add Redirect URL** and add the redirect URLs for the Claude clients you plan to use: * **claude.ai and Claude Desktop:** `https://claude.ai/api/mcp/auth_callback` and `https://claude.com/api/mcp/auth_callback` * **Claude Code:** `http://localhost:{PORT}/callback` where `{PORT}` is a fixed port you choose (e.g., `http://localhost:29352/callback`). Users must pass `--callback-port {PORT}` when adding the MCP server in Claude Code. * **Claude Desktop via mcp-remote:** `http://localhost:{PORT}/oauth/callback` (e.g., `http://localhost:3334/oauth/callback`). Note the `/oauth/callback` path -- this differs from Claude Code's `/callback` path. Ensure the **Bypass Proof Key for Code Exchange (PKCE)** toggle is **off** (the default). Public clients must use PKCE to protect the authorization code flow. Under **Grant Types**, ensure the following are checked: * **Authorization Code** (under Recommended and Modern Flows) * **Refresh Token** (under Recommended and Modern Flows) Leave **Type** set to **JWT**. Optionally set **Lifetime Seconds** (default is 1 hour). Under **Refresh Token Settings**, toggle **Allow Offline Access** on. Click **Save** to create the OIDC application. Add a new OIDC app to the Auth Provider Orchestrator's configuration with `public: true`. Public clients do not use a client secret -- they rely on PKCE to protect the authorization code flow. ```yaml maverics.yaml theme={null} apps: - name: claude-public type: oidc clientID: claude-public public: true grantTypes: - authorization_code - refresh_token redirectURLs: # claude.ai and Claude Desktop web connectors (routed through Anthropic) - https://claude.ai/api/mcp/auth_callback - https://claude.com/api/mcp/auth_callback # Claude Code -- fixed port via --callback-port (connects directly from user's machine) - http://localhost:29352/callback # Claude Desktop via mcp-remote -- note /oauth/callback path differs from Claude Code - http://localhost:3334/oauth/callback accessToken: type: jwt lifetimeSeconds: 3600 refreshToken: allowOfflineAccess: true lifetimeSeconds: 86400 authentication: idps: - upstream-idp claimsMapping: email: upstream-idp.email name: upstream-idp.name sub: upstream-idp.sub ``` Public clients cannot authenticate themselves to the authorization server. Any application that knows the client ID can initiate an authorization flow. Only use public clients when you cannot securely distribute a client secret. Registration is not complete until the application is bound to an identity connector, which tells the Orchestrator which IdP authenticates users. In the Console UI, you finish this from the application's own settings; in YAML, the `authentication.idps` field you already set on the app handles it directly. If you haven't already, add your identity connector to the Auth Provider deployment's **Identity Fabric**. Navigate to **Identity Fabric** in the sidebar, click **Create**, and select your IdP's connector type (e.g., Entra ID, Okta, or Keycloak). The connector must exist before you can select it as an application's authentication source. Navigate to **Applications** in the sidebar and open your Claude application. In the application's **Resources** card, click **Edit**, then click **Add Resource** and select the identity connector you added in the previous step. Click **Save**. A connector must be added as a resource before it can be selected as an authentication source. Find the **Access Control** card and click **Edit**. From the **Select an authentication source** dropdown, choose the connector you just added, then click **Save**. Navigate to the deployment's **Settings** page and click **Publish Preview** in the footer bar. Review the configuration diff, optionally add a revision note, and click **Publish**. The Orchestrator picks up the new configuration on its next poll cycle. See [Publishing Deployment Configs](/reference/console/config-publishing) for details on the publishing lifecycle. No additional step is needed. The `authentication.idps` field in the OIDC app configuration (shown in the previous step) already binds the app to your identity connector. The Orchestrator reads this directly from the configuration file. ## Connect Claude to the Gateway Once Claude is registered as an OAuth client and associated with your identity connector, configure your Claude client to connect to the AI Identity Gateway's MCP endpoint. Claude will automatically discover the authorization server via the Gateway's protected resource metadata and prompt you to authenticate. How you connect depends on whether the AI Identity Gateway is publicly accessible or on a private network: * **Publicly accessible Gateway** -- All client tabs below work. Use a **confidential client** (client ID + secret) so the secret proves the client's identity to the authorization server. The **Organization (Team / Enterprise)** tab configures a web connector that routes through Anthropic's infrastructure -- both the Gateway and Auth Provider Orchestrator must be reachable from the public internet. * **Private / internal Gateway** -- Select the **Claude Code** or **Claude Desktop** tab below. These clients connect directly from your machine, so local and private network URLs work. Use a **public client** (client ID + PKCE, no secret) to avoid distributing and managing secrets across individual machines. Add the AI Identity Gateway as a remote MCP server using the Claude Code CLI. Claude Code connects directly from your machine, so the Gateway does not need to be publicly accessible. The Auth Provider Orchestrator requires pre-registered OAuth clients rather than Dynamic Client Registration (DCR), giving administrators full control over which applications can request tokens. You must pass the OAuth client credentials explicitly when adding the server. You also need `--callback-port` to fix the OAuth redirect URI to match the pre-registered redirect URL. If you registered Claude as a **public client** on the Auth Provider Orchestrator, pass only `--client-id`. Claude Code uses PKCE (Proof Key for Code Exchange) to protect the authorization code flow -- no client secret is needed. ```bash theme={null} claude mcp add \ --transport http \ --client-id claude-public \ --callback-port 29352 \ ai-identity-gateway https://your-gateway.example.com/mcp ``` * `--client-id claude-public` provides the OAuth client ID so Claude Code can authenticate without DCR. * `--callback-port 29352` fixes the OAuth redirect URI to `http://localhost:29352/callback`, matching the redirect URL registered in the OIDC app. Without this flag, Claude Code picks a random port that would not match. Public clients are a good fit when Claude Code connects directly to a Gateway on a local or private network, since there is no client secret to manage or protect on each user's machine. If you registered Claude as a **confidential client**, pass both `--client-id` and `--client-secret`. This is the recommended approach when the Gateway is publicly accessible, as the secret proves the client's identity to the authorization server. ```bash theme={null} claude mcp add \ --transport http \ --client-id claude \ --client-secret YOUR_CLIENT_SECRET \ --callback-port 29352 \ ai-identity-gateway https://your-gateway.example.com/mcp ``` Replace `YOUR_CLIENT_SECRET` with the client secret you configured in the OIDC app on the Auth Provider Orchestrator. * `--client-id claude` and `--client-secret` provide the OAuth credentials so Claude Code can authenticate without DCR. * `--callback-port 29352` fixes the OAuth redirect URI to `http://localhost:29352/callback`, matching the redirect URL registered in the OIDC app. Without this flag, Claude Code picks a random port that would not match. The `--client-secret` flag stores the secret in Claude Code's MCP configuration file. For shared or production environments, consider using a secret that can be rotated, and restrict file permissions on the configuration file. When you start a Claude Code session, Claude connects to the Gateway, discovers the authorization server, and opens your browser for OAuth authentication. **Managing the connection:** ```bash theme={null} # List all configured MCP servers claude mcp list # View details for the Gateway server, including OAuth config claude mcp get ai-identity-gateway # Remove the server claude mcp remove ai-identity-gateway ``` Inside a Claude Code session, use the `/mcp` slash command to check server status, authenticate, and manage connections: * **Authenticate** -- Run `/mcp` and select the AI Identity Gateway to open the browser OAuth flow. Claude Code stores tokens securely and refreshes them automatically. * **View available tools** -- After authenticating, Claude automatically discovers tools from the Gateway. Ask Claude to list available tools or use `/mcp` to check the server's connection status and tool count. * **Clear authentication** -- Run `/mcp`, select the AI Identity Gateway, and choose **Clear authentication** to revoke the stored OAuth tokens. Use this when switching users, troubleshooting token issues, or revoking access. * **Reauthenticate** -- After clearing authentication, run `/mcp` again and select the Gateway to start a fresh OAuth flow. For more details on Claude Code's MCP support, see [Connect Claude Code to tools via MCP](https://docs.anthropic.com/en/docs/claude-code/mcp). Claude Desktop routes all remote MCP traffic through Anthropic's cloud infrastructure. This means the AI Identity Gateway and Auth Provider Orchestrator must both be publicly accessible for Claude Desktop to reach them -- this applies to all remote MCP servers, not just those requiring OAuth. To connect Claude Desktop to the AI Identity Gateway, use one of the following approaches: * **Organization web connector** (Team / Enterprise plans) -- See the **Organization (Team / Enterprise)** tab. Admins configure the Gateway URL and OAuth credentials centrally. Requires a publicly accessible Gateway. * **mcp-remote proxy** -- Use the open-source [`mcp-remote`](https://github.com/geelen/mcp-remote) package as a local stdio proxy that handles the OAuth flow and MCP communication on your behalf. Because Claude Desktop treats `mcp-remote` as a local stdio server, the actual network connection to the Gateway happens directly from the user's machine -- so the Gateway does not need to be publicly accessible. ### Connect with mcp-remote [`mcp-remote`](https://github.com/geelen/mcp-remote) is a local stdio proxy that bridges Claude Desktop to remote MCP servers. It handles OAuth discovery, PKCE, token storage, and token refresh locally, then forwards MCP requests to the Gateway. Because it runs as a local process, it connects directly from the user's machine, bypassing Anthropic's cloud infrastructure. `mcp-remote` is an open-source third-party component not maintained by Strata. Strata does not attest to its security, compliance, or suitability for any purpose, and provides no warranty or guarantees regarding its use. Evaluate it against your organization's security requirements before deploying. If you are interested in a Strata-supported Claude Desktop extension that can be centrally distributed across your enterprise, [contact us](https://www.strata.io/contact). See [Building Desktop Extensions with MCPB](https://support.claude.com/en/articles/12922929-building-desktop-extensions-with-mcpb) for background on the desktop extension model. Open Claude Desktop and navigate to **Settings** > **Developer** > **Edit Config**. This opens the `claude_desktop_config.json` file. Add an entry under `mcpServers` that runs `mcp-remote` as a local stdio server. Use the `--static-oauth-client-info` flag to provide the pre-registered OAuth client credentials, since the Auth Provider Orchestrator requires pre-registered clients rather than Dynamic Client Registration (DCR). Include a port number after the Gateway URL to fix the OAuth callback port -- by default `mcp-remote` uses port `3334`, but you can choose any available port. The redirect URL registered in the OIDC app must match `http://localhost:{PORT}/oauth/callback`. Use `--transport http-only` since the AI Identity Gateway uses Streamable HTTP. Without this flag, `mcp-remote` defaults to `http-first` which attempts an SSE fallback on failure, potentially causing duplicate connections and authentication issues. If you registered Claude as a **public client** on the Auth Provider Orchestrator, provide only the `client_id`. `mcp-remote` uses PKCE (Proof Key for Code Exchange) to protect the authorization code flow -- no client secret is needed. ```json claude_desktop_config.json theme={null} { "mcpServers": { "ai-identity-gateway": { "command": "npx", "args": [ "mcp-remote", "https://your-gateway.example.com/mcp", "3334", "--transport", "http-only", "--static-oauth-client-info", "{\"client_id\":\"claude-public\"}" ] } } } ``` Public clients are a good fit when Claude Desktop connects to a Gateway on a local or private network, since there is no client secret to manage or protect on each user's machine. To avoid JSON escaping issues in `claude_desktop_config.json`, you can store the OAuth client info in a separate file and reference it with the `@` prefix: ```json oauth_client_info.json theme={null} { "client_id": "claude-public" } ``` ```json claude_desktop_config.json theme={null} "args": [ "mcp-remote", "https://your-gateway.example.com/mcp", "--static-oauth-client-info", "@/path/to/oauth_client_info.json" ] ``` If you registered Claude as a **confidential client**, provide both the `client_id` and `client_secret` in the static OAuth client info. This is the recommended approach when the Gateway is publicly accessible, as the secret proves the client's identity to the authorization server. ```json claude_desktop_config.json theme={null} { "mcpServers": { "ai-identity-gateway": { "command": "npx", "args": [ "mcp-remote", "https://your-gateway.example.com/mcp", "3334", "--transport", "http-only", "--static-oauth-client-info", "{\"client_id\":\"claude\",\"client_secret\":\"YOUR_CLIENT_SECRET\"}" ] } } } ``` Replace `YOUR_CLIENT_SECRET` with the client secret you configured in the OIDC app on the Auth Provider Orchestrator. The `client_secret` is embedded in the configuration file in plain text. Restrict file permissions on `claude_desktop_config.json` and consider using a secret that can be rotated. You can also store the credentials in a separate file and reference it with `@/path/to/oauth_client_info.json`. Close and reopen Claude Desktop to pick up the new configuration. When you start a conversation, `mcp-remote` connects to the Gateway, discovers the authorization server via protected resource metadata (RFC 9470), and opens your browser for OAuth authentication. Tokens are stored locally in `~/.mcp-auth/` and refreshed automatically. For more details on configuring MCP servers in Claude Desktop, see [Connect to local MCP servers](https://modelcontextprotocol.io/quickstart/user). On Claude Team and Enterprise plans, an organization **Owner** can add the AI Identity Gateway as a managed **web connector** that is available to all team members. This centralizes the configuration -- admins set the Gateway URL and OAuth credentials once, and individual members just click **Connect** and authenticate with their own identity. Web connectors route traffic through Anthropic's infrastructure. The AI Identity Gateway and Auth Provider Orchestrator must both be accessible from the public internet. Local or private network URLs (e.g., `localhost`, `127.0.0.1`, private DNS) will not work with web connectors. For private or internal gateways, use the **Claude Code** or **Claude Desktop** tabs instead. The **Add** dialog in Organization settings offers both **Web** and **Desktop** connector types. Choose **Web** for the AI Identity Gateway. The **Desktop** option is for uploading packaged desktop extensions (`.mcpb` files) that run locally on users' machines -- it is not used for remote MCP servers. **Admin setup:** In claude.ai, go to **Organization settings** > **Connectors**. Click **Add** and select **Custom** > **Web**. Enter the AI Identity Gateway's MCP endpoint URL: ``` https://your-gateway.example.com/mcp ``` Click **Advanced settings** and enter the **OAuth Client ID** and **OAuth Client Secret** from the OIDC app you registered on the Auth Provider Orchestrator. The Auth Provider Orchestrator requires pre-registered OAuth clients rather than Dynamic Client Registration (DCR), so Claude needs these credentials to authenticate. Click **Add**. The connector now appears in the organization's connector list, visible to all team members. **Member setup:** Each team member authenticates individually to ensure Claude only accesses tools the member is authorized to use: 1. Go to **Settings** > **Connectors** in claude.ai. 2. Find the AI Identity Gateway connector (labeled **Custom**) and click **Connect**. 3. Complete the OAuth flow -- authenticate with your identity provider when prompted. Once connected, the Gateway's MCP tools are available in conversations. Members can enable or disable the connector per conversation. For details on plan requirements and connector management, see [Get started with custom connectors using remote MCP](https://support.claude.com/en/articles/11175166-get-started-with-custom-connectors-using-remote-mcp). ## Verify the Connection After connecting, verify that Claude can discover and invoke tools from the AI Identity Gateway. 1. **Check tool discovery** -- Ask Claude to list available tools. Claude should display the MCP tools exposed by your MCP Bridge and MCP Proxy apps. Tool names include the namespace prefix (e.g., `my_api_listUsers`). 2. **Invoke a tool** -- Ask Claude to call one of the discovered tools. For example: "List all users using the my\_api\_listUsers tool." The AI Identity Gateway authenticates the request, evaluates authorization policies, performs token exchange, and returns the result. 3. **Check the Orchestrator logs** -- The AI Identity Gateway Orchestrator logs show the complete request flow: agent authentication, OPA policy evaluation, token exchange, and upstream API call. Verify that all steps completed successfully. If Claude cannot discover tools or tool invocations fail, see the troubleshooting sections in the [Expose APIs to Agents](/guides/ai-identity/mcp-bridge#troubleshooting) and [Protect MCP Servers](/guides/ai-identity/mcp-proxy#troubleshooting) guides. ## Harden Tool Access with Inbound Authorization Policies The AI Identity Gateway Orchestrator evaluates [OPA inbound authorization policies](/guides/security/policies#ai-identity-gateway-opa-authorization) on every MCP tool call before it reaches the upstream service. While token minting policies (below) govern whether a token is issued at all, inbound authorization policies govern what an agent can do with that token -- controlling which tools are accessible, under what conditions, and for which callers. This is the primary mechanism for enforcing least-privilege access at the tool level. Policies can inspect the tool name, tool arguments, HTTP headers (including the JWT), source IP, and any other field in the [MCP app input schema](/guides/security/policies#mcp-app-input-schema). ### Example: Separate Read and Write Access to Sensitive Data The following policy allows agents with `hr:read` scope to query employee data, but requires `hr:admin` scope to create or update records. This prevents AI agents from modifying sensitive HR data unless explicitly authorized with elevated permissions: ```yaml maverics.yaml theme={null} apps: - name: hr-api type: mcpBridge authorization: inbound: type: opa opa: name: hr-read-write-separation rego: | package orchestrator default result["allowed"] := false # Decode the bearer token's claims. Undefined when the header is # absent or is not a JWT, so the rules below fail and deny. jwt_payload := jwt.parse_bearer(input.request.http.headers.Authorization) # Read-only tools require hr:read scope. result["allowed"] if { input.request.mcp.tool.params.name in ["listEmployees", "getEmployee"] contains(jwt_payload.scope, "hr:read") } # Write tools require hr:admin scope. result["allowed"] if { input.request.mcp.tool.params.name in ["createEmployee", "updateEmployee"] contains(jwt_payload.scope, "hr:admin") } result["internal_message"] := sprintf("denied %s for client %s", [ input.request.mcp.tool.params.name, jwt_payload.client_id, ]) if { not result.allowed } result["external_message"] := "insufficient permissions for this operation" if { not result.allowed } ``` See the [Authorization Policies guide](/guides/security/policies#ai-identity-gateway-opa-authorization) for the full input schema, output schema, and additional examples. ## Harden Token Issuance with Token Minting Policies The Auth Provider Orchestrator supports [OPA token minting policies](/guides/security/policies#configure-opa-token-minting-policies-oidc-provider-only-optional) that evaluate every token request before issuance. These policies add a governance layer on top of OAuth client registration -- even after a user authenticates successfully, the Orchestrator can deny or constrain the token based on client identity, grant type, requested scopes, or environmental conditions. This is especially valuable when using **public clients**. Because public clients authenticate with only a client ID and PKCE (no secret), any application that knows the client ID can initiate an authorization flow. Token minting policies let you enforce additional constraints at the point of token issuance to compensate -- for example, restricting which networks can mint tokens for a given client. **Public client** is an OAuth term describing how the client authenticates (no secret, PKCE only) -- it does not mean the Gateway is publicly accessible. A public client can connect to a Gateway on a private network (e.g., Claude Code or Claude Desktop via mcp-remote connecting to an internal Gateway). Similarly, a publicly accessible Gateway can use confidential clients. The client type and deployment model are independent choices. ### Example: Restrict a Private Gateway to Corporate Networks The following policy ensures that the public client `claude-public` can only mint tokens when the request originates from the corporate network. This is useful when the Gateway is on a private network and you want to ensure tokens are only issued to users connecting from known internal ranges: ```yaml maverics.yaml theme={null} apps: - name: claude-public type: oidc clientID: claude-public public: true grantTypes: - authorization_code - refresh_token authorization: tokenMinting: accessToken: policies: - name: restrict-public-client-by-network rego: | package orchestrator default result := {"allowed": true} # Only allow the public client to mint tokens from the # corporate network. result := {"allowed": false, "internal_message": "public client not allowed from this network"} { input.request.oauth.client_id == "claude-public" not net.cidr_contains("10.0.0.0/8", input.source.ip) } redirectURLs: # claude.ai and Claude Desktop web connectors (routed through Anthropic) - https://claude.ai/api/mcp/auth_callback - https://claude.com/api/mcp/auth_callback # Claude Code -- fixed port via --callback-port (connects directly from user's machine) - http://localhost:29352/callback # Claude Desktop via mcp-remote -- note /oauth/callback path differs from Claude Code - http://localhost:3334/oauth/callback accessToken: type: jwt lifetimeSeconds: 3600 refreshToken: allowOfflineAccess: true lifetimeSeconds: 86400 authentication: idps: - upstream-idp claimsMapping: email: upstream-idp.email name: upstream-idp.name sub: upstream-idp.sub ``` This policy denies token issuance for `claude-public` unless the request originates from the `10.0.0.0/8` CIDR range. Replace the CIDR with your organization's internal network range. You can combine multiple `net.cidr_contains` checks to allow several network ranges. Source IP checks are a useful defense-in-depth measure but should not be your only security control. Client IPs can be obscured by proxies, VPNs, or NAT, and the `input.source.ip` value reflects the immediate connection to the Orchestrator, which may be a load balancer or reverse proxy rather than the end user's machine. Use IP restrictions alongside other controls -- such as user authentication, PKCE, and scoped token lifetimes -- rather than relying on them in isolation. ### Example: Restrict a Public Gateway to Anthropic's IP Ranges When the Gateway is publicly accessible and Claude connects via claude.ai or Claude Desktop web connectors, traffic arrives from [Anthropic's published outbound IP ranges](https://platform.claude.com/docs/en/api/ip-addresses). The following policy restricts token issuance to requests originating from these ranges: ``` package orchestrator default result := {"allowed": true} # Only allow token minting from Anthropic's outbound IP ranges. # See https://platform.claude.com/docs/en/api/ip-addresses # for the current ranges. result := {"allowed": false, "internal_message": "request not from Anthropic IP range"} { not anthropic_ip } anthropic_ip { # Anthropic outbound IPv4 net.cidr_contains("160.79.104.0/21", input.source.ip) } anthropic_ip { # Anthropic outbound IPv6 net.cidr_contains("2607:6bc0::/48", input.source.ip) } ``` If you also support Claude Code or Claude Desktop via mcp-remote (which connect directly from users' machines), combine the Anthropic ranges with your corporate network ranges: ``` package orchestrator anthropic_ip { # Anthropic outbound IPv4 net.cidr_contains("160.79.104.0/21", input.source.ip) } anthropic_ip { # Anthropic outbound IPv6 net.cidr_contains("2607:6bc0::/48", input.source.ip) } corporate_ip { net.cidr_contains("10.0.0.0/8", input.source.ip) } result := {"allowed": false, "internal_message": "request not from allowed network"} { not anthropic_ip not corporate_ip } ``` Token minting policies can inspect any field in the token request, including `input.request.oauth.client_id`, `input.request.oauth.scope`, `input.request.oauth.audience`, `input.request.oauth.grant_type`, and `input.source.ip`. See the [token minting policy reference](/guides/security/policies#configure-opa-token-minting-policies-oidc-provider-only-optional) for the full input schema. ### IP Allowlisting for Public Deployments When the AI Identity Gateway and Auth Provider Orchestrator are publicly accessible, you can restrict inbound traffic to known IP ranges as an additional layer of protection. Understanding the traffic flow is important for applying restrictions at the right layer: * **User's browser → Auth Provider** -- During the OAuth authorization step, the user's browser connects directly to the Auth Provider Orchestrator's authorize endpoint. This traffic comes from the user's IP, not Anthropic's. * **Anthropic's backend → Auth Provider** -- Token exchange and token refresh requests are made server-side by Anthropic's infrastructure. This traffic comes from [Anthropic's published outbound IP ranges](https://platform.claude.com/docs/en/api/ip-addresses). * **Anthropic's backend → Gateway** -- MCP tool calls are routed through Anthropic's infrastructure. This traffic also comes from Anthropic's outbound IP ranges. This means IP restrictions apply differently depending on the component: * **Gateway infrastructure-level allowlisting** -- The Gateway can be locked down to [Anthropic's outbound IP ranges](https://platform.claude.com/docs/en/api/ip-addresses) (`160.79.104.0/21` for IPv4, `2607:6bc0::/48` for IPv6) since only Anthropic's backend connects to it for web connectors. Use your cloud provider's firewall, security groups, WAF, or reverse proxy. * **Auth Provider infrastructure-level allowlisting** -- The Auth Provider cannot be restricted to Anthropic's IPs alone because the user's browser must reach the authorize endpoint during the OAuth flow. However, it does not need to be open to the entire internet -- organizations can restrict access to Anthropic's outbound IP ranges **plus** their own users' networks using VPNs, corporate IP allowlists, device management policies, or conditional access controls. The key requirement is that both Anthropic's infrastructure and the user's device can reach the Auth Provider. * **Auth Provider token minting policies** -- OPA token minting policies evaluate at the token endpoint, where requests come from Anthropic's backend (for web connectors) or the user's machine (for Claude Code / mcp-remote). Use the examples above to restrict by source IP at this layer. * **Gateway inbound authorization policies** -- Use OPA policies on the AI Identity Gateway to restrict tool invocations by source IP. This controls who can call tools even with a valid token. Anthropic publishes stable outbound IP addresses for MCP tool calls from claude.ai and Claude Desktop. See [Anthropic IP Addresses](https://platform.claude.com/docs/en/api/ip-addresses) for the current ranges. These addresses will not change without notice. For Claude Code and Claude Desktop via mcp-remote, traffic originates from the user's machine rather than Anthropic's infrastructure. Whether infrastructure-level IP allowlisting is practical for these clients depends on your network topology and trust domains -- organizations with well-defined corporate IP ranges can allowlist those ranges alongside token minting and Gateway authorization policies. ## Troubleshooting The redirect URI Claude sends does not match what is configured in the OIDC app's `redirectURLs`. **Resolution:** 1. Check the Auth Provider Orchestrator logs for the exact `redirect_uri` value Claude is sending. 2. Add that exact URI (including scheme, host, port, and path) to the OIDC app's `redirectURLs` array. 3. For **claude.ai and Claude Desktop**, ensure both `https://claude.ai/api/mcp/auth_callback` and `https://claude.com/api/mcp/auth_callback` are in the redirect URLs list. 4. For **Claude Code**, ensure you passed `--callback-port` when adding the MCP server, and that `http://localhost:{PORT}/callback` with that port is in the redirect URLs list. Without `--callback-port`, Claude Code picks a random port that will not match any pre-registered URL. 5. For **Claude Desktop via mcp-remote**, ensure `http://localhost:{PORT}/oauth/callback` is in the redirect URLs list. Note the `/oauth/callback` path -- this differs from Claude Code's `/callback` path. The default port is `3334`. If Claude connects and authenticates but sees no tools: * Verify that MCP Bridge or MCP Proxy apps are configured and running on the AI Identity Gateway Orchestrator. * Check that the agent's token has the required scopes for tool discovery. * Review the AI Identity Gateway Orchestrator logs for errors during tool registration or upstream connection failures. * Confirm that inbound OPA policies do not block tool listing. If Claude does not prompt you to authenticate when connecting to the Gateway: * Verify that `mcpProvider.authorization.oauth.enabled` is `true` on the AI Identity Gateway Orchestrator. * Check that the Gateway's `/.well-known/oauth-protected-resource` endpoint is reachable and returns valid metadata. * Ensure the Auth Provider Orchestrator's well-known endpoint is listed in the Gateway's `mcpProvider.authorization.oauth.servers` configuration. * For Claude Desktop, confirm you restarted the application after editing the configuration file. If Claude's session stops working after the access token expires: * Verify that the OIDC app's `grantTypes` includes `refresh_token`. * Check that `refreshToken.allowOfflineAccess` is `true` in the OIDC app configuration. * Confirm the refresh token has not expired (check `refreshToken.lifetimeSeconds`). * If using a confidential client, ensure the client secret has not been rotated or revoked since the session was established. When a user disconnects a connector in claude.ai or Claude Desktop, Anthropic removes the tokens from its systems but does **not** revoke them at the identity provider. Access and refresh tokens on the Auth Provider Orchestrator remain valid until they expire, and session cookies are not cleared. **Resolution:** * Set short `accessToken.lifetimeSeconds` values (e.g., 300--900 seconds) to limit the window of validity after disconnection. * Set `refreshToken.lifetimeSeconds` to bound how long a refresh token can extend a session. * If immediate revocation is required, revoke the user's session directly on the Auth Provider Orchestrator or upstream identity provider. If `mcp-remote` fails with `UNABLE_TO_VERIFY_LEAF_CERTIFICATE` or similar TLS errors, the Gateway's certificate is not trusted by Node.js. This is common with self-signed certificates, internal CAs, or VPN-intercepted connections. **Resolution (recommended):** Point `NODE_EXTRA_CA_CERTS` to your organization's CA certificate file so Node.js trusts the Gateway's certificate chain: ```json claude_desktop_config.json theme={null} { "mcpServers": { "ai-identity-gateway": { "command": "npx", "args": ["mcp-remote", "https://your-gateway.example.com/mcp"], "env": { "NODE_EXTRA_CA_CERTS": "/path/to/your-ca-bundle.pem" } } } } ``` **Resolution (development only):** For local development with self-signed certificates, you can disable TLS verification entirely. Do **not** use this in production. ```json claude_desktop_config.json theme={null} { "mcpServers": { "ai-identity-gateway": { "command": "npx", "args": ["mcp-remote", "https://your-gateway.example.com/mcp"], "env": { "NODE_TLS_REJECT_UNAUTHORIZED": "0" } } } } ``` Setting `NODE_TLS_REJECT_UNAUTHORIZED=0` disables all TLS certificate verification, making the connection vulnerable to man-in-the-middle attacks. Use `NODE_EXTRA_CA_CERTS` with your organization's CA certificate for non-development environments. ## Related Pages Set up the Auth Provider Orchestrator and understand agent identity concepts Make REST APIs available to Claude as MCP tools via MCP Bridge Add identity governance to existing MCP servers via MCP Proxy Full configuration reference for OAuth client registration ### Anthropic Documentation Critical reference covering connector architecture, traffic routing, OAuth requirements, token limits, timeouts, and privacy details Claude Code docs covering MCP transports, OAuth options, and callback port configuration How to add remote MCP servers as connectors on claude.ai, including plan requirements Developer guide for building OAuth-protected MCP servers that work with Claude How to package local MCP servers as desktop extensions (.mcpb) for enterprise distribution MCP protocol docs for configuring MCP servers in Claude Desktop # Expose APIs to Agents Source: https://docs.strata.io/guides/ai-identity/mcp-bridge Make your existing REST APIs available to AI agents as discoverable MCP tools -- with full identity verification and authorization on every call. ## How It Works MCP Bridge enables AI agents to access your existing REST APIs as MCP tools -- without modifying either the agents or the APIs. The Model Context Protocol (MCP) is an open standard that provides a structured way for AI agents to discover and invoke tools. MCP Bridge brings this capability to your existing REST APIs by translating between the two protocols automatically. The Maverics Orchestrator sits between the AI agent and your REST APIs, acting as a translator. When an agent makes an MCP tool request, the Orchestrator converts it into the corresponding REST API call. When the REST API responds, the Orchestrator translates the response back into MCP format. This means your REST APIs become discoverable, invocable tools for AI agents -- without any changes to your existing API code. But translation alone is not enough. Every tool invocation also passes through the Orchestrator's identity and authorization layer. Here is what happens when an agent requests a tool: 1. **Authenticates the agent** -- When the agent first connects, the AI Identity Gateway Orchestrator returns protected resource metadata (per RFC 9470) that tells the agent which authorization server(s) to authenticate against. The agent authenticates with the Auth Provider Orchestrator (or your external IdP) and obtains a token, then presents it to the gateway for validation. 2. **Resolves the user context** -- AI agents typically act on behalf of a human user. The Orchestrator identifies which user delegated authority to the agent, so authorization decisions reflect the user's actual permissions -- not just the agent's. 3. **Evaluates authorization policies** -- The Orchestrator checks whether the agent (acting on behalf of the user) is permitted to invoke the requested tool. Policies can restrict access based on the agent's scopes, the user's group memberships, the specific tool being invoked, or any combination of these factors. 4. **Translates and forwards** -- The Orchestrator exchanges the agent's token for a short-lived, narrowly scoped token specific to the tool being invoked, then converts the MCP tool call into the corresponding REST API request (mapping parameters, headers, and body content) and forwards it to your backend service with this fresh token. 5. **Returns the response** -- The REST API response is translated back into MCP format and returned to the agent, along with any identity context the agent needs for subsequent calls. ```mermaid theme={null} flowchart LR Agent["AI Agent"] --> Gateway["MCP Bridge
(AI Identity Gateway Orchestrator)"] Gateway --> AuthServer["Auth Provider
(Orchestrator / OIDC Provider)"] Gateway --> API1["REST API 1"] Gateway --> API2["REST API 2"] ``` **MCP Bridge vs MCP Proxy:** MCP Bridge translates REST APIs into MCP tools -- choose it when you want to expose existing REST APIs to AI agents via MCP. MCP Proxy proxies existing MCP server connections with identity injection -- choose it when you already have MCP servers running. See the [AI overview](/guides/ai-identity/overview) for a side-by-side comparison of both approaches. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed the Orchestrator yet, follow the [Quick Start guide](/guides/getting-started/quick-start) first. The Orchestrator is a small, lightweight runtime that deploys almost anywhere. * **An identity provider configured as an identity connector** -- The Orchestrator needs an [Identity Fabric](/reference/orchestrator/identity-fabric) to authenticate agents. If you have not connected an identity provider yet, the Quick Start guide covers this step. * **One or more REST APIs you want to expose as MCP tools** -- These are the backend APIs that AI agents will access. The APIs must use OAuth for authentication (MCP Bridge performs token exchange to call them on behalf of agents) and must be under your organization's control. * **An OpenAPI spec for your REST API** -- MCP Bridge uses the OpenAPI specification to generate MCP tool definitions from your API endpoints. * **An AI agent that supports the Model Context Protocol (MCP)** -- The agent connects to MCP Bridge as its MCP server, discovering and invoking tools through the standard MCP protocol. ## Configure MCP Bridge The MCP Provider is the Orchestrator's entry point for AI agent connections. It handles MCP transport (how agents connect), agent authentication (verifying agent identity via OAuth), and tool routing (directing tool calls to the correct app). Configure the MCP Provider with transport settings and OAuth-based agent authentication. The MCP Provider supports both SSE (Server-Sent Events) and Streamable HTTP transports. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. AI Identity Gateway mode selection screen in Maverics Console showing MCP Bridge option Define the MCP Provider and the OIDC connector that authenticates agents. The `mcpProvider.authorization.oauth` section configures how agent tokens are validated. ```yaml maverics.yaml theme={null} connectors: # Points to the Auth Provider Orchestrator (the separate OIDC Provider deployment) - name: auth-provider type: oidc oidcWellKnownURL: https://your-auth-server.example.com/.well-known/openid-configuration oauthClientID: ai-identity-gateway oauthClientSecret: oauthLoginRedirect: urls: - https://your-gateway.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-gateway.example.com/logout mcpProvider: enabled: true transports: sse: enabled: true path: "/mcp/sse" messagePath: "/mcp/message" keepAlive: enabled: true interval: 30s stream: enabled: true path: "/mcp" session: enabled: true headerName: "Mcp-Session-Id" allowClientTermination: true timeout: 1h authorization: oauth: enabled: true metadataPath: /.well-known/oauth-protected-resource servers: - wellKnownEndpoint: https://your-auth-server.example.com/.well-known/oauth-authorization-server refreshInterval: 24h tokenValidation: expectedAudiences: - https://your-gateway.example.com/ method: jwt jwt: clockSkew: 15s ``` The MCP Provider enables both SSE and Streamable HTTP transports so agents can connect using whichever method they support. The `authorization.oauth` section configures JWT-based token validation -- the Orchestrator fetches the Auth Provider Orchestrator's signing keys from the well-known endpoint and validates agent tokens against them. For the full set of AI Identity Gateway mode options, see the [AI Identity Gateway reference](/reference/modes/ai-identity-gateway). Register your REST API as an MCP Bridge app. The Orchestrator reads your API's OpenAPI specification and automatically generates MCP tool definitions for each endpoint. Agents discover these tools through the standard MCP protocol. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. REST API to MCP tool mapping configuration screen in Maverics Console showing endpoint and parameter fields Define an MCP Bridge app in the `apps` section. The `openapi.spec.uri` points to your API's OpenAPI specification, and `openapi.baseURL` points to the actual REST API server. ```yaml maverics.yaml theme={null} apps: - name: my-api-bridge type: mcpBridge mode: openapi toolNamespace: disabled: false name: my_api_ openapi: spec: uri: https://your-api.example.com/openapi.yaml baseURL: https://your-api.example.com/api/v1 ``` The `toolNamespace.name` prefix is added to all tool names generated from this API. For example, if your API has a `listUsers` endpoint, agents will see it as `my_api_listUsers`. This prevents naming collisions when you have multiple MCP Bridge apps exposing tools from different APIs. The `openapi.spec.uri` can be an HTTP URL or a local file path (`file:///path/to/spec.yaml`). The `openapi.baseURL` is the base URL where the Orchestrator sends the translated REST API requests. Authorization is critical for MCP apps. Every MCP app requires both **inbound** authorization (OPA policy that decides whether a tool call is allowed) and **outbound** authorization (how the Orchestrator authenticates to the upstream REST API on behalf of the agent). **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Authorization policy configuration screen in Maverics Console showing policy rules and conditions The outbound authorization is where the Orchestrator's per-tool token exchange happens. Instead of forwarding the agent's original token to your REST API, the Orchestrator mints a fresh, short-lived token for each tool invocation. Each token carries only the scopes needed for that specific tool and expires in seconds. Add the `authorization` block to your MCP Bridge app. The `inbound` section defines the OPA policy, and the `outbound` section configures token exchange for the upstream REST API. ```yaml maverics.yaml theme={null} apps: - name: my-api-bridge type: mcpBridge mode: openapi toolNamespace: disabled: false name: my_api_ openapi: spec: uri: https://your-api.example.com/openapi.yaml baseURL: https://your-api.example.com/api/v1 authorization: inbound: opa: name: my-api-bridge-inbound-authz rego: | package orchestrator default result["allowed"] := false result["allowed"] := true { input.request.mcp.tool.params.name == "listUsers" } result["allowed"] := true { input.request.mcp.tool.params.name == "getUser" } outbound: type: tokenExchange tokenExchange: type: delegation idp: auth-provider audience: https://your-api.example.com/ tools: - name: listUsers ttl: 5s scopes: - name: user:List - name: getUser ttl: 5s scopes: - name: user:Get - name: createUser ttl: 5s scopes: - name: user:Create ``` **Inbound authorization (OPA):** The Rego policy evaluates every tool invocation against the OPA input schema. The `input.request.mcp.tool.params.name` field contains the MCP tool name, and `input.request.mcp.tool.params.arguments` contains the tool arguments. You can also access `input.request.http.headers` (including the inbound access token), `input.request.http.method`, and `input.source.ip` for richer policy decisions. See the [Authorization Policies guide](/guides/security/policies#opa-authorization-ai-identity-gateway) for the full input schema and example policies. **Outbound authorization (token exchange):** The Orchestrator exchanges the agent's token for a delegation token scoped to the target REST API. Each tool can have its own `scopes` (the permissions included in the delegated token) and `ttl` (how long the delegated token is valid). The `idp` references the connector used for the token exchange. This means when an agent calls `listUsers`, the Orchestrator mints a token with only `user:List` scope that expires in 5 seconds. When the same agent calls `createUser` a moment later, a completely different token is minted with only `user:Create` scope. No single token ever carries more permissions than a single tool needs, and no token lives longer than it takes to complete the call. For unprotected upstream APIs that do not require authentication, use `type: unprotected` instead of `type: tokenExchange`. See [MCP Bridge Reference](/reference/orchestrator/applications/mcp-bridge) for all available fields. Start with a deny-by-default policy and explicitly grant access to specific tools. This is safer than starting with allow-all and trying to restrict later -- it ensures agents only access what you intentionally permit. Test the complete flow by connecting an AI agent to MCP Bridge and invoking a registered tool. This verifies that authentication, authorization, and REST API translation all work correctly end-to-end. Connect your AI agent to the Orchestrator's MCP endpoint. The agent should be able to: 1. **Discover tools** -- The agent's MCP client lists available tools and sees the REST APIs you registered 2. **Authenticate** -- The agent presents its OAuth credentials and receives a valid session 3. **Invoke a tool** -- The agent calls a tool, and the Orchestrator translates it to the REST API call 4. **Receive a response** -- The REST API response is returned to the agent in MCP format Check the Orchestrator logs to confirm that each step completed successfully. The logs show authentication events, policy evaluations, API translations, and any errors that occurred. **Success!** Your REST APIs are now accessible as MCP tools through the Orchestrator. AI agents authenticate with their credentials, authorization policies control which tools each agent can access, and every tool invocation is logged for audit and compliance. ## Troubleshooting If the agent connects to MCP Bridge but sees no tools, check the following: * Verify that REST APIs are correctly registered as MCP tools in the Bridge configuration. Each API endpoint needs a valid URL, method, and tool name. * Check that the agent has the required scopes to discover tools. Some configurations restrict tool listing based on the agent's permissions. * Look at the Orchestrator logs for errors during tool registration. If an API endpoint is unreachable during startup, the tool may not be registered. * Confirm that authorization policies do not block tool listing. A policy that denies all access will also prevent tool discovery. Agent authentication failures typically have one of these causes: * The agent's OAuth client credentials (client ID and secret) are incorrect. Double-check them against your identity provider's application registration. * The identity provider is not reachable from the Orchestrator. Test connectivity to your IdP's token endpoint. * The agent's client registration has expired or been revoked in the identity provider. * The Orchestrator's identity connector is misconfigured. Check that the connector's issuer URL and client configuration match your IdP. Check the Orchestrator logs for specific authentication error details -- the logs include the identity provider's error response, which usually identifies the exact issue. MCP Bridge translates MCP tool invocations to REST API calls and translates the responses back. When the underlying REST API returns an error, the Orchestrator passes it through as an MCP error response. To isolate the issue: * Call the REST API directly (bypassing MCP Bridge) to confirm it works on its own. This tells you whether the issue is in the translation or the API. * Check the Orchestrator logs for the full REST request and response. The logs show how MCP Bridge mapped tool parameters to API parameters. * Verify that parameter mappings are correct -- a common issue is mapping an MCP tool parameter to the wrong REST query parameter or header. * If the REST API requires authentication, ensure the outbound authorization is configured with the correct token exchange settings and scopes. ## What's Next Learn about agent identity concepts and set up the Auth Provider for token exchange Detailed configuration reference for all MCP Bridge settings and options # Protect MCP Servers Source: https://docs.strata.io/guides/ai-identity/mcp-proxy Add identity governance to your existing MCP servers -- authenticate every agent, authorize every tool call, and audit every action, without modifying your MCP servers. ## How It Works MCP Proxy is for when you already have MCP servers running but they lack identity awareness. Maybe you built MCP servers that expose tools for your AI agents, but those servers do not know who is calling them or whether the caller is authorized. MCP Proxy solves this by adding an identity-aware layer between your agents and your existing MCP servers -- without modifying either side. The Model Context Protocol (MCP) is an open standard for AI agent-to-tool communication. When you have MCP servers already deployed, they speak MCP natively -- agents connect, discover tools, and invoke them. The problem is that vanilla MCP does not include identity. Any agent that can reach your MCP server can invoke any tool. MCP Proxy fixes this gap. The Maverics Orchestrator acts as a transparent proxy between agents and your MCP servers. Agents connect to the Orchestrator (thinking it is the MCP server), and the Orchestrator forwards their requests to your actual MCP servers after applying identity and authorization. Here is the flow: 1. **Agent connects** -- The AI agent connects to the Orchestrator's MCP endpoint, treating it as a standard MCP server. 2. **Authentication** -- The AI Identity Gateway Orchestrator returns protected resource metadata (per RFC 9470) that tells the agent which authorization server(s) to authenticate against. The agent authenticates with the Auth Provider Orchestrator and obtains a token, which the gateway validates before allowing the connection to proceed. 3. **Identity injection** -- For every tool invocation, the Orchestrator injects identity context into the request before forwarding it to the upstream MCP server. This context includes the agent's identity, the delegating user's identity, and any relevant claims or attributes. 4. **Authorization** -- The Orchestrator evaluates authorization policies to determine whether this agent, acting on behalf of this user, is allowed to invoke this specific tool. 5. **Transparent forwarding** -- The Orchestrator exchanges the agent's token for a short-lived, narrowly scoped token specific to the tool being invoked, then forwards the authorized request to the upstream MCP server with this fresh token and identity context attached. The MCP server receives the request as if the agent connected directly -- but now with identity information it can use. 6. **Response passthrough** -- The MCP server's response flows back through the Orchestrator to the agent, with audit logging capturing the complete interaction. ```mermaid theme={null} flowchart LR Agent["AI Agent"] --> Gateway["MCP Proxy
(AI Identity Gateway Orchestrator)"] Gateway --> AuthServer["Auth Provider
(Orchestrator / OIDC Provider)"] Gateway --> MCP1["MCP Server 1"] Gateway --> MCP2["MCP Server 2"] ``` **MCP Proxy vs MCP Bridge:** MCP Proxy proxies existing MCP server connections with identity injection -- choose it when you already have MCP servers running. MCP Bridge translates REST APIs into MCP tools -- choose it when you have REST APIs, not MCP servers. See the [AI overview](/guides/ai-identity/overview) for a side-by-side comparison of both approaches. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed the Orchestrator yet, follow the [Quick Start guide](/guides/getting-started/quick-start) first. The Orchestrator is a small, lightweight runtime that deploys almost anywhere. * **An identity provider configured as an identity connector** -- The Orchestrator needs an [Identity Fabric](/reference/orchestrator/identity-fabric) to authenticate agents and resolve user context. * **One or more existing MCP servers** -- These are the upstream MCP servers that your AI agents will access through the proxy. They must be reachable from the Orchestrator over the network. * **An AI agent that supports the Model Context Protocol (MCP)** -- The agent connects to the Orchestrator's MCP endpoint (not directly to your MCP servers). ## Configure MCP Proxy The MCP Provider is the Orchestrator's entry point for AI agent connections -- the same component used by MCP Bridge. It handles MCP transport, agent authentication via OAuth, and routes tool calls to the correct MCP Proxy app. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. AI Identity Gateway mode selection screen in Maverics Console showing MCP Proxy option Define the MCP Provider and the OIDC connector for agent authentication. This configuration is identical to the MCP Bridge setup -- the MCP Provider serves both Bridge and Proxy apps. ```yaml maverics.yaml theme={null} connectors: # Points to the Auth Provider Orchestrator (the separate OIDC Provider deployment) - name: auth-provider type: oidc oidcWellKnownURL: https://your-auth-server.example.com/.well-known/openid-configuration oauthClientID: ai-identity-gateway oauthClientSecret: oauthLoginRedirect: urls: - https://your-gateway.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-gateway.example.com/logout mcpProvider: enabled: true transports: sse: enabled: true path: "/mcp/sse" messagePath: "/mcp/message" keepAlive: enabled: true interval: 30s stream: enabled: true path: "/mcp" session: enabled: true headerName: "Mcp-Session-Id" allowClientTermination: true timeout: 1h authorization: oauth: enabled: true metadataPath: /.well-known/oauth-protected-resource servers: - wellKnownEndpoint: https://your-auth-server.example.com/.well-known/oauth-authorization-server refreshInterval: 24h tokenValidation: expectedAudiences: - https://your-gateway.example.com/ method: jwt jwt: clockSkew: 15s ``` The MCP Provider configuration is shared across all MCP apps (both Bridge and Proxy). Agents authenticate once at the MCP Provider level (via the Auth Provider Orchestrator) and can then invoke tools from any registered MCP app. Register your upstream MCP server as an MCP Proxy app. The Orchestrator proxies MCP protocol natively -- it receives MCP requests from agents and forwards them to your upstream MCP server over the Streamable HTTP transport. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Upstream MCP server registration screen in Maverics Console showing server endpoint and transport settings Define an MCP Proxy app in the `apps` section. The `upstream` configuration points to your existing MCP server, and `toolNamespace` prefixes tool names to avoid collisions. ```yaml maverics.yaml theme={null} apps: - name: my-mcp-server-proxy type: mcpProxy toolNamespace: disabled: false name: my_server_ upstream: transport: stream stream: url: http://mcp-server.example.com:8080/mcp connection: dialTimeout: 10s keepAlive: interval: 15s pool: maxIdleConns: 100 maxIdleConnsPerHost: 100 ``` The `upstream.stream.url` points to your MCP server's Streamable HTTP endpoint. The `toolNamespace.name` prefix is added to all tools from this upstream server -- for example, `my_server_listItems`. This prevents naming collisions when you proxy multiple MCP servers. The `connection` settings control how the Orchestrator maintains its connection pool to the upstream MCP server, including dial timeouts and keep-alive intervals. If your MCP servers are behind a firewall or VPN, make sure the Orchestrator has network access to them. The Orchestrator needs to reach each upstream server to discover its tools and forward requests. Like MCP Bridge, every MCP Proxy app requires both **inbound** authorization (OPA policy) and **outbound** authorization (how the Orchestrator authenticates to the upstream MCP server on behalf of the agent). This is the same authorization pattern used across all MCP apps. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Agent authentication and authorization configuration screen in Maverics Console for MCP Proxy The outbound authorization is where the Orchestrator's per-tool token exchange happens. Instead of forwarding the agent's original token to your MCP server, the Orchestrator mints a fresh, short-lived token for each tool invocation -- scoped to exactly the permissions that tool needs, with a TTL measured in seconds. Add the `authorization` block to your MCP Proxy app. The `inbound` section defines the OPA policy, and the `outbound` section configures token exchange (or marks the upstream as unprotected). ```yaml maverics.yaml theme={null} apps: - name: my-mcp-server-proxy type: mcpProxy toolNamespace: disabled: false name: my_server_ upstream: transport: stream stream: url: http://mcp-server.example.com:8080/mcp connection: dialTimeout: 10s keepAlive: interval: 15s pool: maxIdleConns: 100 maxIdleConnsPerHost: 100 authorization: inbound: opa: name: my-mcp-server-inbound-authz rego: | package orchestrator default result["allowed"] := false result["allowed"] := true { input.request.mcp.tool.params.name == "listItems" } result["allowed"] := true { input.request.mcp.tool.params.name == "getItem" } outbound: type: tokenExchange tokenExchange: type: delegation idp: auth-provider audience: https://mcp-server.example.com/ tools: - name: listItems ttl: 5s scopes: - name: item:List - name: getItem ttl: 5s scopes: - name: item:Get - name: createItem ttl: 5s scopes: - name: item:Create - name: updateItem ttl: 5s scopes: - name: item:Update ``` **Inbound authorization (OPA):** The Rego policy controls which tool calls are allowed. The OPA input schema provides `input.request.mcp.tool.params.name` (the tool name), `input.request.mcp.tool.params.arguments` (the tool arguments), `input.request.http.headers` (including the inbound access token), and `input.source.ip` (the client IP). See the [Authorization Policies guide](/guides/security/policies#opa-authorization-ai-identity-gateway) for the full input schema and example policies. **Outbound authorization (token exchange):** Each tool gets its own scopes and TTL for the delegated token. The `type: delegation` means the exchanged token preserves both the agent's and the delegating user's identity. This means when an agent calls `listItems`, the Orchestrator mints a token with only `item:List` scope that expires in 5 seconds. When the same agent calls `createItem` next, a completely different token is minted with only `item:Create` scope. Every tool invocation gets a fresh, minimal-privilege token -- nothing is reused or over-scoped. If your upstream MCP server does not require authentication, use `type: unprotected`: ```yaml theme={null} authorization: inbound: opa: name: my-mcp-server-inbound-authz file: /etc/maverics/policies/my-mcp-server-inbound-authz.rego outbound: type: unprotected ``` See [MCP Proxy Reference](/reference/orchestrator/applications/mcp-proxy) for all available fields. If your upstream MCP servers are also accessible directly (not just through the proxy), agents could bypass the identity layer by connecting to the MCP server directly. Restrict network access so that MCP servers only accept connections from the Orchestrator. Test the complete flow by connecting an AI agent to MCP Proxy and verifying that identity context is correctly injected into upstream requests. Connect your agent to the Orchestrator's MCP endpoint and invoke a tool. Then check: 1. **Agent authentication** -- The Orchestrator logs show the agent was authenticated successfully 2. **Tool discovery** -- The agent sees tools from all registered upstream MCP servers 3. **Identity injection** -- The upstream MCP server received the request with identity context attached (check the MCP server's logs or add a debug tool that echoes received metadata) 4. **Authorization enforcement** -- Try invoking a tool the agent should not have access to and confirm the request is denied **Success!** Your existing MCP servers are now protected by the Orchestrator's identity layer. Agents authenticate before accessing tools, identity context is injected into every request, and authorization policies control which tools each agent can use. ## Troubleshooting If the Orchestrator cannot reach your upstream MCP servers, agents will see connection timeout errors. Check the following: * Verify that the upstream MCP server is running and listening on the configured endpoint. * Test network connectivity from the Orchestrator to the MCP server. If the server is behind a firewall, ensure the Orchestrator's IP is allowed. * Check the transport protocol configuration -- ensure the MCP server and the Orchestrator are using compatible transport protocols. * Look at the Orchestrator logs for specific timeout or connection error details. If your MCP server is receiving requests but without identity context, the outbound authorization configuration may be incorrect: * Verify the outbound type is set to `tokenExchange` (not `unprotected`) if you need identity context forwarded. * Check that the token exchange `idp` references a valid connector and that the `audience` matches what the upstream server expects. * If using per-tool scopes, verify the tool names in the `tools` array match the actual tool names from the upstream MCP server. * Enable debug logging in the Orchestrator to see the full token exchange flow and identify where identity context is lost. Authentication failures for MCP Proxy follow the same patterns as MCP Bridge: * Verify the agent's OAuth credentials (client ID and secret) are correct. * Confirm the identity provider is reachable from the Orchestrator. * Check that the agent's client registration has not expired or been revoked. * Review the Orchestrator logs for the identity provider's error response. See the [AI Identity overview](/guides/ai-identity/overview) for more detail on agent credential management and common authentication issues. ## What's Next Learn about agent identity concepts and set up the Auth Provider for token exchange Detailed configuration reference for all MCP Proxy settings and options # Overview Source: https://docs.strata.io/guides/ai-identity/overview Secure AI agent access to your APIs and MCP tools with identity, authentication, and authorization on every call. The Maverics Orchestrator lets you control which agents can access which tools, trace every action back to the human user who authorized it, and audit everything -- so AI agents operate with the same identity governance as your human users. The Orchestrator provides two approaches for securing AI agent access through the **Model Context Protocol (MCP)**, an open standard that lets AI agents discover and invoke tools in a structured, protocol-driven way. Each approach adds identity, authentication, and authorization to MCP connections in a different way, depending on your architecture and what you already have in place. Whether you have existing REST APIs you want to open up to AI agents or existing MCP servers that need identity awareness -- there is an approach that fits your situation. ## Choose Your Approach | Approach | When to Use | How It Works | | ------------------------- | -------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | | **Expose APIs to Agents** | You have existing REST APIs you want AI agents to access | Translates REST APIs into MCP tools automatically -- agents discover and invoke tools via MCP while the Orchestrator handles the REST translation behind the scenes | | **Protect MCP Servers** | You have existing MCP servers that need identity | Proxies MCP connections with identity injection -- the Orchestrator sits between agents and your MCP servers, adding authentication and authorization to every tool invocation | Not sure which approach to start with? If you have REST APIs today and want to expose them to AI agents, start with **MCP Bridge**. If you already have MCP servers running, start with **MCP Proxy**. ## Agent Identity Concepts AI agents are not humans -- but they still need identity. When an AI agent accesses a tool, reads data, or performs an action on behalf of a user, something needs to answer these questions: Who is this agent? Who authorized it to act? What is it allowed to do? And what did it actually do? Agent identity addresses this by adding three capabilities that traditional service accounts lack: * **Delegation chains** -- Every agent action traces back to the human user who authorized it. When Agent X accesses a tool, the system knows that Alice delegated authority to Agent X and that Alice's permissions (not just the agent's) determine what the agent can do. This is implemented through OAuth 2.0 token exchange, which supports two modes. **Delegation** (default) produces a token with an `act` claim that identifies both the user and the agent acting on their behalf, giving downstream services full visibility for auditability. **Impersonation** produces a token that fully assumes the user's identity, with no trace of agent involvement -- use this when downstream services do not support the actor claim pattern. See the [MCP Bridge](/reference/orchestrator/applications/mcp-bridge#token-exchange) and [MCP Proxy](/reference/orchestrator/applications/mcp-proxy#token-exchange) references for configuration details. * **Dynamic scopes** -- Agent permissions can change based on context. An agent might have broad scopes for one task and narrow scopes for another, depending on what the delegating user authorized. Scopes are named permissions (like `read:orders`, `write:invoices`, or `admin:users`) that your identity provider issues in the agent's token. * **Action-level audit** -- Every tool invocation is logged with the full identity context: which agent, which user, which tool, what parameters, and what result. This gives you a complete audit trail that satisfies compliance requirements and enables forensic analysis when something goes wrong. The Maverics Orchestrator works with your existing identity provider to manage agent identity. You register agents in your identity provider (just like you register applications), configure their scopes and permissions, and the Orchestrator enforces those permissions at runtime -- whether you are using [MCP Bridge](/guides/ai-identity/mcp-bridge) or [MCP Proxy](/guides/ai-identity/mcp-proxy) mode. ## How Token Security Works The AI Identity Gateway involves two orchestrator deployments working together: * **Auth Provider Orchestrator** -- A separate orchestrator deployment running as an OIDC Provider (authorization server). It handles agent authentication, token issuance, and token exchange (minting short-lived, scoped delegation tokens for each tool invocation). * **AI Identity Gateway Orchestrator** -- Runs the MCP Provider with MCP Bridge and/or MCP Proxy apps. It handles MCP transport, tool routing, inbound authorization (OPA policies), and upstream forwarding. These can be the same orchestrator instance for simpler deployments, but are typically separate deployments in production. Every tool invocation gets its own token. When an agent calls a tool, the AI Identity Gateway Orchestrator does not reuse the agent's existing token or forward it to the upstream service. Instead, it requests a token exchange from the Auth Provider Orchestrator -- trading the agent's token for a brand-new token specific to that single tool call. Each token carries only the scopes that tool needs (like `employee:List` for listing employees) and expires in seconds (typically a `ttl` of `5s`). A different tool call a moment later gets a completely different token with different scopes. ```mermaid theme={null} sequenceDiagram participant Agent as AI Agent participant Gateway as AI Identity Gateway
(Orchestrator) participant AuthServer as Auth Provider
(Orchestrator / OIDC Provider) participant API as Tool / API Agent->>Gateway: Connect to MCP endpoint Gateway-->>Agent: 401 + /.well-known/oauth-protected-resource Agent->>Gateway: GET /.well-known/oauth-protected-resource Gateway-->>Agent: Protected resource metadata (lists authorization servers) Agent->>AuthServer: OAuth authorization flow AuthServer-->>Agent: Access token Agent->>Gateway: Invoke tool (with access token) Gateway->>Gateway: Validate token + evaluate OPA policies Gateway->>AuthServer: Token exchange: mint scoped token
ttl: 5s, scopes: [employee:List] AuthServer-->>Gateway: Short-lived delegation token Gateway->>API: Forward request with delegation token API-->>Gateway: Response Gateway-->>Agent: Tool result ``` ## MCP Spec OAuth Discovery (RFC 9470) When an agent first connects to the AI Identity Gateway, it goes through a standards-based OAuth discovery flow: 1. The agent connects to the AI Identity Gateway Orchestrator's MCP endpoint. 2. The gateway returns a `401` along with a pointer to its protected resource metadata endpoint. 3. The gateway exposes `/.well-known/oauth-protected-resource` (per RFC 9470), which returns protected resource metadata including the list of authorization server(s) the agent can authenticate against. 4. The agent reads the metadata, authenticates against the Auth Provider Orchestrator (one of the listed authorization servers), and obtains a token. 5. The agent returns to the gateway with a valid token. The gateway validates the token and proceeds with tool discovery and invocation. This flow means agents do not need to be pre-configured with authorization server URLs -- they discover them dynamically from the gateway's protected resource metadata. Traditional approaches give agents broad, long-lived tokens that accumulate permissions. The Orchestrator takes the opposite approach: every tool invocation gets a fresh, minimal-privilege token that expires in seconds. No single token ever carries more permissions than a single tool needs, and no token lives longer than it takes to complete the call. ## Set Up the Auth Provider The OIDC Provider you configure here is the Orchestrator's own token minting infrastructure. It does not just validate tokens from an external provider -- it issues short-lived, narrowly scoped tokens for each tool invocation. You configure it with token exchange grant types so it can mint delegation tokens that carry both the agent's identity and the delegating user's identity. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Agent registration guidance screen in Maverics Console showing identity provider setup steps This configuration is for the **Auth Provider Orchestrator** deployment -- the separate orchestrator instance that runs the OIDC Provider. It is not the same deployment as the AI Identity Gateway Orchestrator that runs the MCP Provider. Configure the `oidcProvider` and register the AI Identity Gateway as an OIDC application with token exchange grants and custom scopes for MCP tools. ```yaml maverics.yaml theme={null} connectors: - name: upstream-idp type: oidc oidcWellKnownURL: https://your-idp.example.com/.well-known/openid-configuration oauthClientID: orchestrator-client oauthClientSecret: oauthLoginRedirect: urls: - https://your-auth-server.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-auth-server.example.com/logout disablePKCE: false scopes: openid profile email oidcProvider: correlateSession: true discovery: issuer: https://your-auth-server.example.com endpoints: wellKnown: https://your-auth-server.example.com/.well-known/oauth-authorization-server jwks: https://your-auth-server.example.com/oauth2/jwks auth: https://your-auth-server.example.com/oauth2/auth token: https://your-auth-server.example.com/oauth2/token userinfo: https://your-auth-server.example.com/oauth2/userinfo introspect: https://your-auth-server.example.com/oauth2/introspect jwks: - algorithm: RSA256 publicKey: privateKey: ``` The OIDC Provider issues tokens that the AI Identity Gateway validates when agents connect. The `jwks` section defines the signing keys used to sign tokens -- the gateway fetches the public key from the `jwks` endpoint to verify token signatures. Treat agent credentials with the same care as user passwords. Store the client secret in a [secret provider](/reference/orchestrator/configuration/secret-providers) \-- never in source code, configuration files, or environment variables that might be logged or exposed. Register the AI Identity Gateway as an OIDC application that can perform token exchange. This client uses the `urn:ietf:params:oauth:grant-type:token-exchange` grant type to exchange a user's token for a delegation token scoped to specific downstream APIs. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Agent scope and permission configuration screen in Maverics Console Define the gateway client in the `apps` section with `grantTypes` that include both `client_credentials` and `token-exchange`. Configure `customScopes` for the MCP tools the gateway will broker access to. ```yaml maverics.yaml theme={null} apps: - name: ai-identity-gateway type: oidc clientID: ai-identity-gateway credentials: secrets: - grantTypes: - client_credentials - urn:ietf:params:oauth:grant-type:token-exchange accessToken: type: jwt allowedAudiences: - https://your-api.example.com/ - https://mcp-server.example.com/ customScopes: scopes: - name: user:List - name: user:Get - name: user:Create - name: user:Update - name: item:List - name: item:Get - name: item:Create claimsMapping: email: upstream-idp.email name: upstream-idp.name sub: upstream-idp.sub ``` The `grantTypes` array enables both `client_credentials` (for machine-to-machine auth) and `urn:ietf:params:oauth:grant-type:token-exchange` (RFC 8693 token exchange for delegation). The `allowedAudiences` list restricts which downstream services the gateway can request tokens for. The `customScopes` define the per-tool permissions that can be included in exchanged tokens. Administrators can also configure token minting policies on the OIDC Provider app (`authorization.tokenMinting.accessToken.policies`) to apply OPA-based governance over which tokens get issued during exchange. This provides a second control point beyond inbound OPA policies -- inbound policies control which tool calls are allowed, while token minting policies control which tokens are issued. See the [OIDC Provider reference](/reference/modes/oidc-provider) for configuration details. ### Per-Tool Token Exchange Each tool in the `tools` array gets its own `ttl` and `scopes`, and each tool invocation triggers a separate token exchange operation. This is not a single token with all scopes -- every tool call gets its own freshly minted token. For example, when an agent calls `listEmployees`, the Orchestrator mints a token with only `employee:List` scope, valid for 5 seconds. When the same agent calls `createEmployee` a moment later, the Orchestrator performs a completely separate token exchange, minting a different token with only `employee:Create` scope, also valid for 5 seconds. The first token has already expired by the time the second call completes. This means no token ever accumulates permissions across tools, and no token outlives its purpose. The `ttl` and `scopes` fields in the YAML above are not just configuration -- they define the security boundary for each individual tool invocation. Document your scope naming convention and share it with your team. Consistent scope names (like always using the `action:resource` pattern) make policies easier to write, review, and audit. ## Guides Make your existing REST APIs available to AI agents as discoverable MCP tools with full identity and authorization Add identity governance to your existing MCP servers -- authenticate every agent and authorize every tool call ## Troubleshooting If an agent cannot authenticate with its client credentials, check the following: * Verify the client ID and client secret are correct. Client secrets are often only shown once when created -- if you have lost the secret, generate a new one in your identity provider. * Check that the agent's application registration is active and has not been disabled or deleted in the identity provider. * Confirm the grant type is set to "client\_credentials" in the agent's application registration. * Verify that the token endpoint URL in the Orchestrator's identity connector matches your identity provider's actual token endpoint. * If the agent's credentials have an expiration date, check whether they have expired. If the Orchestrator cannot resolve the delegation chain (the agent authenticates but the user context is missing): * Verify that the delegated token includes the `act` (actor) claim or whatever custom claim your identity provider uses for delegation. * Check that the token exchange was performed correctly -- the original user token must be exchanged for a delegated agent token, not simply passed through. * Verify that the gateway client's `grantTypes` includes `urn:ietf:params:oauth:grant-type:token-exchange`. * If your identity provider does not support the standard OAuth 2.0 token exchange, check the Orchestrator's identity connector documentation for provider-specific delegation configuration. * Enable debug logging in the Orchestrator to see the full token contents and identify which claims are present or missing. If the token exchange succeeds but the downstream service rejects the exchanged token: * Verify the `allowedAudiences` in the gateway client includes the audience value used in the MCP app's `outbound.tokenExchange.audience`. * Check that the downstream service's expected audience matches the `audience` value in the token exchange configuration. * Review the exchanged token's claims (using a JWT debugger) to confirm the `aud` claim contains the expected value. ## Related Pages Detailed configuration reference for all AI Identity Gateway modes and settings TLS, secrets management, authorization policies, and compliance guides SSO, OIDC, SAML federation, and identity provider migration guides # OWASP MCP Top 10 Source: https://docs.strata.io/guides/ai-identity/owasp-mcp-top-10 The [OWASP MCP Top 10](https://owasp.org/www-project-mcp-top-10/) identifies the most critical security risks in Model Context Protocol deployments. As AI agents interact with enterprise systems through MCP, new attack surfaces emerge -- from token mismanagement and privilege escalation to shadow servers and context injection. The Maverics Orchestrator in [AI Identity Gateway](/reference/modes/ai-identity-gateway) mode addresses several of these risks directly. Using a second Orchestrator as an [Auth Provider](/guides/ai-identity/overview#set-up-the-auth-provider) (OIDC Provider) with per-tool token exchange, it provides identity, authorization, and audit controls for every MCP interaction. This page maps each OWASP MCP risk to the specific capabilities that mitigate it -- and is transparent about where complementary controls are needed. **Disclaimer:** This page is provided for informational purposes only and does not constitute a guarantee of security, compliance, or complete risk mitigation. The mappings described here reflect general architectural capabilities and may not apply to every deployment topology or configuration. Security outcomes depend on proper configuration, organizational governance, and complementary controls. Customers are responsible for evaluating their own security posture, conducting independent assessments, and implementing appropriate controls for their specific environment. Strata Identity makes no warranties regarding the completeness or accuracy of these mappings. The AI Identity Gateway operates at the **identity and authorization layer** -- authentication, token management, policy enforcement, telemetry, and auditing. Some OWASP MCP risks target the **AI model layer** (prompt injection, intent manipulation, context memory). For those risks, the gateway limits the blast radius and enables detection, but prevention requires complementary controls at the model and application layers. ## Coverage Summary | OWASP Risk | Coverage | How the AI Identity Gateway Addresses It | | ------------------------------------------------------- | ---------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | [**MCP01**](#mcp01) -- Token Mismanagement | Directly addresses | Upstream services never see long-lived or over-scoped tokens. Per-tool token exchange mints short-lived, scoped tokens with customizable TTLs (e.g., 5s). The agent's original token is never forwarded to upstream services. | | [**MCP02**](#mcp02) -- Privilege Escalation | Reduces attack surface | Per-tool scopes and short-lived tokens prevent runtime scope accumulation. OPA policies and token minting policies enforce configured boundaries. Configuration-level scope creep (admins gradually broadening permissions) requires organizational governance. | | [**MCP03**](#mcp03) -- Tool Poisoning | Reduces attack surface | The gateway only serves tools from OpenAPI specs and MCP servers that your organization explicitly registers -- no public registries or auto-discovery. OPA policies can validate tool arguments before they reach upstream services. Tool namespacing mitigates shadowing. | | [**MCP04**](#mcp04) -- Supply Chain Attacks | Reduces attack surface | The Orchestrator is a single binary with no plugin marketplace or dependency resolution. Upstream servers and APIs are explicitly registered in configuration. Complementary controls needed for SBOM and dependency scanning of your own services. | | [**MCP05**](#mcp05) -- Command Injection | Directly addresses (gateway layer) | The gateway forwards structured protocol messages (MCP or REST) to upstream services, never executes commands or code. OPA policies can inspect and reject malicious tool argument values before they reach upstream services. | | [**MCP06**](#mcp06) -- Intent Flow Subversion | Limits blast radius | Even if an agent is subverted, OPA policies constrain which tools it can invoke and what arguments it can pass. Delegation tokens enforce both the agent's and the delegating user's permissions on upstream services. Auditing enables detection. Prevention requires AI model-layer controls. | | [**MCP07**](#mcp07) -- Insufficient Auth | Directly addresses | Upstream services are protected by multi-layer auth: OAuth 2.0 agent authentication, OPA policies on every tool call, per-tool token exchange with scoped delegation tokens, and token minting policies. This is the core problem the gateway was built to solve. | | [**MCP08**](#mcp08) -- Lack of Audit | Directly addresses | Every tool call to an upstream service is logged with agent identity, user identity, tool name, parameters, and outcome. Structured JSON for SIEM. Downstream analysis and tamper protection depend on SIEM configuration. | | [**MCP09**](#mcp09) -- Shadow MCP Servers | Directly addresses (gateway layer) | Agents access upstream services only through the centralized gateway. Upstream servers are explicitly registered. Network isolation prevents agents from bypassing the gateway. Discovering rogue servers in the org requires separate tooling. | | [**MCP10**](#mcp10) -- Context Injection & Over-Sharing | Reduces attack surface | Upstream services are protected from cross-context access -- each tool invocation gets its own scoped token, and sessions are isolated per agent. Model-layer context memory isolation requires complementary controls. | ## Risk Details **OWASP risk:** Tokens and credentials serve as the primary means of authentication and authorization in MCP systems. Developers frequently embed secrets improperly, creating "contextual secret leakage" where protocols themselves become unintentional credential repositories. Long-lived sessions and context persistence compound the problem. Attackers retrieve tokens through prompt injection, log scraping, or context poisoning -- leading to complete infrastructure compromise, lateral movement across integrated services, and data exfiltration. **Coverage: Directly addresses** The Orchestrator's [per-tool token exchange](/guides/ai-identity/overview#how-token-security-works) protects upstream services by ensuring they never receive long-lived or over-scoped tokens: * **Per-tool token exchange** -- Every tool invocation triggers a fresh token exchange. The gateway mints a new delegation token with only the scopes that tool needs and a customizable TTL (e.g., `5s`). A different tool call a moment later gets a completely different token with different scopes. * **No token forwarding** -- The gateway never passes the agent's original token to upstream services. Every upstream call uses a freshly minted, minimally scoped delegation token. The agent's primary token never reaches the backend. * **Inbound delegation support** -- Agents can optionally perform a token exchange before connecting to the gateway, producing a token with the user as the subject and the agent as the actor (`act` claim). Regardless of whether this inbound exchange happens, the gateway always performs its own outbound token exchange for each tool call. The protection profile varies depending on your deployment topology. When the upstream service is another AI agent, short TTLs and scoped tokens are especially critical -- a compromised downstream agent with a long-lived, broadly scoped token could leverage that access far more aggressively than a traditional API consumer would. When the upstream is a REST API, the same token constraints protect against token reuse and lateral movement, but the attack vectors differ. The gateway's per-tool token exchange addresses both scenarios by ensuring that no upstream service -- agent or API -- ever receives more access than a single tool invocation requires. **OWASP risk:** Scope creep occurs when narrowly scoped permissions granted to an MCP agent expand over time -- intentionally for convenience or accidentally through configuration drift -- until the agent holds broad or administrative privileges. This enables unauthorized code modifications, unreviewed deployments, full environment control through service account impersonation, and regulatory violations. The risk is amplified by autonomous agent execution paths that compound incremental permission increases. **Coverage: Reduces attack surface** The Orchestrator prevents runtime scope accumulation, but configuration-level scope creep -- where admins gradually broaden permissions over time -- is an organizational governance problem the gateway cannot solve on its own. What the gateway does is make scope boundaries explicit, auditable, and enforceable at runtime: 1. **Per-tool scopes** -- Each tool has an explicit, declarative scopes list. Scopes are defined in configuration, not accumulated at runtime. A `listUsers` tool gets `user:List`; a `createUser` tool gets `user:Create`. Adding a new scope requires a deliberate configuration change, which flows through your change management process. 2. **Automatic token expiry** -- Every minted token has a TTL measured in seconds. Permissions cannot accumulate over time because each token is destroyed before the next one is issued. There is no long-lived session where scopes could grow. 3. **OPA inbound policies** -- Rego policies evaluate every tool invocation with a [deny-by-default stance](/guides/ai-identity/mcp-bridge#configure-authorization) before the request reaches any upstream service. Policy authors have access to tool name, argument names and values, HTTP headers (including the inbound access token, which can be parsed for identity claims), and source IP. The identity claims available in the token depend on the inbound flow -- an agent that performed token exchange presents a token with the user as subject and agent as actor, while an autonomous agent presents its own identity token. Policy authors can write arbitrarily granular validation logic against any of this context. For example, a policy can allow `createUser` only when the `role` argument is not `admin`, or restrict `deleteItem` to specific token subjects. For elevated operations, OPA policies will soon support human-in-the-loop approval, requiring explicit human authorization before the action proceeds. An agent cannot invoke a tool that the policy does not explicitly permit. 4. **Token minting policies** -- The Auth Provider Orchestrator can apply [OPA-based governance](/guides/ai-identity/overview#set-up-the-auth-provider) over which tokens are issued during exchange. This is a second, independent control point -- even if an inbound policy allows a tool call, the Auth Provider can refuse to mint the token if the requested scopes violate minting policy. **OWASP attack scenarios and how the gateway responds:** * **Accidental escalation** (temporary `repo:write` expands to permanent broad access): Scopes are defined declaratively and require a deliberate configuration change to modify, not an ad-hoc runtime grant. * **Credential harvesting + escalation** (long-lived token found in logs, used to grant additional scopes): Delegation tokens minted for upstream calls expire in seconds and cannot be used to request additional scopes. The agent's own access token should also be configured with an appropriately short TTL on the Auth Provider. The token exchange flow is one-directional -- delegation tokens are minted by the Auth Provider for specific tools, not requested or influenced by the agent. * **Automated policy bypass** (attacker updates agent manifest to add admin privileges): The Auth Provider defines the universe of allowed scopes. A tool cannot request a scope that is not registered in the Auth Provider. **Complementary controls needed:** The gateway enforces whatever scopes and policies are configured, but does not prevent those configurations from becoming overly permissive over time. OWASP recommends automated scope expiry, periodic entitlement reviews, and separation of duties for configuration changes. These are organizational governance practices that complement the gateway's runtime enforcement. See the [MCP Bridge authorization](/guides/ai-identity/mcp-bridge#configure-authorization) and [MCP Proxy authorization](/guides/ai-identity/mcp-proxy#configure-authorization) guides for full configuration details. **OWASP risk:** Tool poisoning occurs when an adversary compromises the tools, plugins, or their schemas that an AI model depends on. Techniques include rug pulls (malicious updates to trusted tools), schema poisoning (corrupting interface definitions so legitimate agents execute unintended destructive operations), and tool shadowing (introducing fake or duplicate tools). Impact includes data compromise, privilege escalation, policy circumvention, and audit trail corruption -- because logs show valid actions per contract despite the contract being malicious. **Coverage: Reduces attack surface** The Orchestrator prevents tool poisoning through architectural controls that keep tool definitions under organizational control: * **Explicitly registered upstream services** -- Both app types require explicit registration of upstream services. [MCP Bridge](/guides/ai-identity/mcp-bridge#define-the-mcp-bridge-app) dynamically generates tools from OpenAPI specifications you provide. [MCP Proxy](/guides/ai-identity/mcp-proxy#define-the-mcp-proxy-app) proxies tool calls to upstream MCP servers registered by URL. In both cases, tools come from sources your organization controls -- there is no auto-discovery from public registries, third-party marketplaces, or community repositories. Rogue tools cannot enter the catalog because the system only serves tools from explicitly registered upstreams. * **Tool namespacing** -- Tool names are prefixed with a configurable namespace (e.g., `my_api_listUsers`). This mitigates tool shadowing by making the source of each tool identifiable -- if two tools share a name, the namespace disambiguates them. Agents see which registered upstream each tool comes from. * **OPA argument-level validation** -- Inbound OPA policies inspect tool arguments before any request reaches an upstream service. Policy authors can validate argument names, check argument values against expected patterns, reject unexpected parameters, and enforce business rules -- catching anomalous behavior that might indicate a poisoned tool definition before it affects upstream resources. **Complementary controls needed:** The Orchestrator does not implement cryptographic schema signing (JWS/COSE/PKI), content-addressable hash verification of tool definitions, or provenance metadata tracking (author, timestamp, approver) on schemas -- all recommended by OWASP for this risk. If your threat model includes sophisticated supply chain attackers who could compromise your internal OpenAPI specs or MCP server configurations, implement schema signing and integrity verification in your CI/CD pipeline as a complementary control. **OWASP risk:** MCP ecosystems depend on open-source packages, connectors, and model-side plug-ins that may contain malicious or vulnerable components. Attackers target MCP server libraries, third-party plugins, dependency updates, and build pipelines. Compromised dependencies can call unsafe APIs, exfiltrate context data, insert rogue schemas, tamper with tool execution, or silently escalate privileges. These components often appear legitimate and can operate undetected for extended periods. **Coverage: Reduces attack surface** The Orchestrator's deployment model eliminates several attack vectors that make MCP supply chain attacks possible: * **No runtime plugin ecosystem** -- Unlike MCP frameworks that rely on user-installed plugins, connectors, or community extensions, the Orchestrator does not have a runtime extension mechanism where customers pull packages from public registries. This eliminates the dependency confusion, typosquatting, and registry compromise vectors that OWASP highlights for the gateway layer specifically. * **Explicit upstream registration** -- All upstream services are explicitly registered. MCP Proxy connects to upstream MCP servers you configure. MCP Bridge reads OpenAPI specifications from URIs you provide. In neither case does the system auto-discover or auto-install tools from public repositories. * **Deliberate configuration changes** -- Tool definitions, authorization policies, and server registrations are defined declaratively. Changes are auditable through your existing change management process. **Complementary controls needed:** The gateway adds one component to the deployment (the Orchestrator binary itself), but does not reduce supply chain risk for upstream MCP servers, REST APIs, or the AI agents connecting to it. Each of those systems has its own dependencies, build pipelines, and attack surface. It is the customer's responsibility to ensure that upstream services, agents, and the Orchestrator deployment all follow standard supply chain security practices -- SBOM management, dependency scanning, version pinning, signed builds, and vendor security assessments. **OWASP risk:** AI agents construct and execute system commands, shell scripts, API calls, or code snippets using untrusted input without proper validation or sanitization. The attack surface is unique because the agent interprets natural language instructions and translates them into executable operations. Techniques include prompt-driven execution, dynamic command construction through string concatenation, tool-mediated execution via MCP tools wrapping system calls, and chained execution using shell operators. **Coverage: Directly addresses (gateway layer)** The gateway protects upstream services from command injection by validating and constraining every tool invocation before it is forwarded: * **Protocol-level gateway, not a command executor** -- The Orchestrator forwards structured protocol messages to upstream services in both app types. MCP Proxy forwards MCP protocol messages to upstream MCP servers. MCP Bridge translates MCP tool calls into structured REST API requests (HTTP method, URL, headers, body) mapped through the OpenAPI spec. In neither case does the Orchestrator execute shell commands, scripts, or arbitrary code. There is no string concatenation or template injection in the forwarding path. * **OPA argument-level validation** -- Inbound OPA policies inspect every tool invocation before it reaches an upstream service. Policy authors have access to tool argument names and values, the tool name, HTTP headers, and source IP. Policies can reject arguments containing shell metacharacters, SQL injection patterns, path traversal sequences, or any other suspicious content. Because Rego is a full policy language, policy authors can write validation logic as granular as their upstream services require -- allowlisting specific argument values, enforcing type constraints, or matching against regex patterns. * **Per-tool token scoping** -- Even if a malicious argument passes OPA validation and reaches an upstream service, the delegation token limits the blast radius to the scopes configured for that specific tool. The upstream service cannot be used to access resources beyond the tool's configured scope. **Upstream service security is outside gateway scope.** The Orchestrator validates and constrains at the gateway layer, but cannot prevent an upstream MCP server or REST API from being vulnerable to injection in its own implementation. If your upstream tools wrap shell commands, SQL queries, or code execution, those tools must implement their own input sanitization, parameterized execution, and sandboxing as recommended by OWASP. **OWASP risk:** Intent flow subversion occurs when malicious instructions embedded within retrieved context cause an MCP-enabled agent to deviate from the user's original goal. Unlike direct prompt injection, this happens "in-flow" -- the agent retrieves resources containing hidden directives that override intended objectives. Impact includes goal hijacking (the agent pursues an entirely different objective), unauthorized autonomous actions (deleting repositories, modifying cloud configurations), and stealthy persistence (meta-instructions in long-lived contexts alter behavior across multiple sessions). **Coverage: Limits blast radius** Intent flow subversion is fundamentally an **AI model-layer problem** -- the attack targets how the model interprets context, not how identity or authorization is enforced. The AI Identity Gateway cannot prevent a model from being manipulated by malicious context. However, it protects upstream services by ensuring that even a subverted agent cannot exceed its authorized boundaries: * **OPA policies as a containment boundary** -- Even if an agent's intent is hijacked, every tool invocation must pass OPA policy evaluation before reaching any upstream service. Policy authors can constrain not just which tools are allowed, but what argument values are permitted. If the OWASP attack scenario describes an agent being tricked into calling `delete_branch` on a production repository, the OPA policy can deny that tool entirely, restrict it to specific branches, or block it based on the argument values. For high-impact operations, OPA policies will soon support human-in-the-loop approval, requiring explicit human authorization before the request proceeds to the upstream service. The policy enforces the boundary regardless of what the agent's manipulated intent says. * **Delegation tokens enforce both agent and user permissions** -- For user-delegated agents, the delegation token carries the user as the subject and the agent as the actor (`act` claim). Upstream services receive tokens that reflect both sets of permissions -- the user's actual entitlements and the agent's configured scopes. An agent acting on behalf of a read-only user cannot perform write operations on upstream services even if its intent is subverted. For autonomous agents operating without a delegating user, the token carries only the agent's own registered scopes, and OPA policies enforce boundaries based on agent identity alone. In both cases, an agent without the required scopes is blocked regardless of its intent. * **Short-lived, per-invocation tokens** -- Delegation tokens are minted by the gateway and sent directly to upstream services -- the agent never sees or handles them. Each token is scoped to a single tool with a customizable TTL (e.g., 5s). Even if a delegation token is intercepted in transit, it expires almost immediately and cannot be used for a different tool or service. * **Auditing enables detection** -- Action-level logging captures every tool invocation with full identity context. Unusual patterns -- unexpected tools being called, anomalous invocation frequency, suspicious parameters -- are visible in the audit trail for security teams to detect and respond to. **Complementary controls needed:** The gateway provides damage limitation, not prevention. To address intent flow subversion at its source, implement AI model-layer controls: intent alignment validation, guardrail models that review agent plans independently of potentially poisoned context, context sanitization that treats all retrieved MCP resources as untrusted data (not instructions), and drift detection that pauses sessions when agent behavior deviates from the original objective. See [OWASP MCP06](https://owasp.org/www-project-mcp-top-10/2025/MCP06-2025%E2%80%93Intent-Flow-Subversion) for detailed model-layer mitigation guidance. **OWASP risk:** MCP servers, tools, or agents fail to properly verify identities or enforce access controls during interactions. Manifestations include missing API validation, hardcoded secrets, static credentials, insecure token issuance without expiry or scoping, client-side-only authorization, and unverified caller metadata. Since MCP ecosystems involve multiple agents, users, and services exchanging data and executing actions, weak identity validation exposes critical attack paths: unauthorized access to sensitive operations, privilege escalation through token reuse, agent impersonation, and complete service compromise through chained malicious actions. **Coverage: Directly addresses -- this is the core problem the gateway was built to solve** The Orchestrator protects upstream services through multiple independent layers of authentication and authorization, addressing every vulnerability indicator OWASP lists: 1. **Agent authentication (OAuth 2.0 inbound)** -- Every agent must authenticate before accessing any upstream tools or services. The gateway validates agent tokens using JWT verification or token introspection against the [Auth Provider Orchestrator](/guides/ai-identity/overview#set-up-the-auth-provider). Unauthenticated agents receive a `401` and are directed to the authorization server via [RFC 9470 protected resource metadata](/guides/ai-identity/overview#mcp-spec-oauth-discovery-rfc-9470). There is no anonymous or guest access to upstream resources. 2. **Inbound authorization (OPA policies)** -- After authentication, every tool invocation is evaluated against Rego policies with a deny-by-default stance before reaching any upstream service. Policy authors can write granular rules based on tool name, tool argument names and values, HTTP headers (including the inbound token's identity claims), and client IP. Authorization is enforced server-side on the gateway -- never client-side. 3. **Outbound authorization (per-tool token exchange)** -- The Orchestrator performs [per-tool token exchange](/guides/ai-identity/overview#how-token-security-works) with the Auth Provider, minting a scoped delegation token for each upstream call. Each token is bound to a specific tool, carries only the scopes that tool needs, expires in seconds, and includes both agent and user identity. Tokens are not reusable across agents, tools, or sessions. 4. **Token minting policies** -- The Auth Provider Orchestrator can apply OPA-based governance during token exchange. This is an independent control point -- even if an inbound policy allows a tool call, the Auth Provider can refuse to mint the token. 5. **Centralized identity management** -- The Auth Provider Orchestrator integrates with your organizational IdP (Microsoft Entra ID, Okta, Auth0, or any OIDC provider) via [Identity Fabric connectors](/reference/orchestrator/identity-fabric). Agent identities are managed through your existing IAM infrastructure, not through separate, disconnected credential stores. 6. **Per-agent identity** -- Each agent authenticates with its own credentials. Credentials are not shared across agents. The Auth Provider defines the permitted scopes per agent registration. **OWASP attack scenarios and how the gateway responds:** * **Token replay** (intercepted token reused for admin operations): Delegation tokens expire quickly (with configurable TTLs, typically seconds), are scoped to a single tool, and are bound to a specific audience. A replayed token is expired, wrong-scoped, and wrong-audience. * **Cross-environment escalation** (test and production share auth scopes): The Auth Provider can restrict which downstream services each gateway client can request tokens for. Test and production gateways use separate client registrations with separate audience restrictions. * **Spoofed agent registration** (malicious service registers as legitimate agent): Agent registration happens in the Auth Provider's OIDC Provider configuration or upstream IdP, both under administrative control. There is no self-service or unprotected enrollment endpoint. * **Inherited privileged credentials** (agents inherit credentials through shared context): The gateway never forwards the inbound agent's token to upstream services. Each upstream call receives a freshly minted delegation token with only the scopes configured for that specific tool. If the upstream service is another agent, it receives a scoped token -- not the calling agent's credentials. Agent-to-agent credential sharing that happens outside the gateway (through shared context or direct communication) is outside gateway scope. **OWASP risk:** MCP systems orchestrate complex, autonomous workflows with minimal human intervention. When auditing mechanisms fail, organizations cannot track agent actions, access patterns, or decision logic. Consequences include inability to perform root-cause analysis, regulatory violations (GDPR, PCI DSS, ISO 27001), extended breach dwell time, behavioral drift going undetected, and inability to demonstrate proper data governance. **Coverage: Directly addresses** The Orchestrator generates comprehensive, structured audit data for every interaction with upstream services: * **Full identity context per event** -- The Orchestrator can log all MCP requests and responses, capturing agent identity, delegating user identity, tool name, tool parameters, response content, and session ID. This creates a complete audit trail that traces every action back to both the agent and the human who authorized it. Policy authors can also add custom log messages via OPA policies for additional context. * **Structured JSON logging** -- Logs are output in structured JSON format for direct SIEM ingestion. Session IDs correlate events across a user's session for complete interaction reconstruction. * **Authorization decision logging** -- Every OPA policy evaluation is logged: which policies were evaluated, what input data they received, and whether access was allowed or denied. Failed authorization attempts are captured alongside successful ones. * **Token exchange logging** -- Token exchange events are logged: which tokens were minted, for which tools, with which scopes, and with what TTL. This provides visibility into the delegation chain for every upstream call. * **Access logging** -- HTTP-level access logging records every inbound request with method, path, status code, and timing. **OWASP attack scenarios and how the gateway responds:** * **Silent exfiltration** (agent exports data through legitimate tool calls without detection): Every tool call is logged with full parameters. Unusual data access patterns (large result sets, unexpected tools, high frequency) are visible in the audit trail for SIEM-based alerting. * **Insider manipulation** (developer disables telemetry during testing): The Orchestrator's logging is configured at the infrastructure level, not controlled by individual agents or users. An agent cannot disable logging for its own sessions. * **Prompt injection data theft** (malicious instruction causes credential retrieval): The audit trail shows the exact tool invocations, parameters, and outcomes -- enabling forensic reconstruction of what data was accessed and where it was sent. See the [Compliance and Audit guide](/guides/security/compliance) for SIEM integration setup and the [Telemetry reference](/reference/orchestrator/telemetry) for all logging configuration. **Downstream responsibilities:** The Orchestrator generates the audit data. Tamper-evident storage (append-only, HMAC integrity), retention policy enforcement, PII redaction, ML-based anomaly detection, and real-time alerting are responsibilities of your SIEM/XDR platform (Splunk, ELK, Sentinel, Datadog, etc.). **OWASP risk:** Shadow MCP servers are unapproved or unsupervised MCP deployments that operate outside formal security governance. Like Shadow IT, these rogue nodes are spun up for experimentation or convenience, using default credentials, permissive configurations, or unsecured APIs. They create unmonitored attack surface, expose sensitive data processing capabilities, introduce compliance violations, and complicate incident response because untracked servers are invisible during containment and forensics. **Coverage: Directly addresses (gateway layer)** The Orchestrator's gateway architecture ensures agents only reach approved, governed upstream services: * **Single entry point** -- Agents connect to the AI Identity Gateway Orchestrator, not directly to MCP servers. The gateway is the only MCP endpoint configured in agent configurations. All tool discovery and invocation flows through the gateway's authentication and authorization layers. An agent configured to use the gateway cannot reach an unregistered MCP server through the gateway. * **Explicit server registration** -- Upstream MCP servers must be explicitly registered in the gateway. The gateway does not auto-discover, auto-register, or dynamically connect to MCP servers. Shadow servers cannot inject themselves into the tool catalog. * **Network isolation** -- The [recommended deployment pattern](/guides/ai-identity/mcp-proxy#configure-authorization) restricts network access so that MCP servers only accept connections from the Orchestrator. Agents that attempt to bypass the gateway and connect to MCP servers directly are blocked at the network level. This turns the gateway into a mandatory checkpoint. * **Centralized governance** -- All authentication, authorization, and audit policies are configured on the Orchestrator. Shadow servers that bypass the gateway operate without any identity governance, making them detectable through their absence from audit logs -- and through network monitoring for MCP traffic patterns outside the gateway's known endpoints. **Complementary controls needed:** The gateway prevents managed agents from accessing shadow servers, but does not discover shadow servers in your network. OWASP recommends network discovery scanning (Nmap, CSPM, EASM), passive network sensors for MCP traffic patterns, mandatory registration governance before deployment, CI/CD pipeline gates blocking unregistered instances, and developer education on shadow MCP risks. These are organizational governance controls outside the scope of the gateway. **OWASP risk:** In MCP-based systems, context acts as the working memory for agents -- storing prompts, retrieved documents, intermediate reasoning, and interaction history. When this shared context lacks proper isolation or governance, sensitive information from one task, user, or agent may be exposed to another. The risk combines context injection (malicious content embedded in shared memory) with over-sharing (reusing context across systems that should be isolated). Impact includes cross-agent and cross-user information disclosure, regulatory violations, exposure of trade secrets, and persistent behavioral contamination. **Coverage: Reduces attack surface** The Orchestrator protects upstream services from cross-context access through token-level and session-level isolation: * **Per-tool token scoping** -- The gateway mints a separate delegation token for each tool invocation and sends it directly to the upstream service -- the agent never sees or handles these tokens. Each token carries only the scopes that specific tool needs. An upstream service receiving a `user:List` token cannot use it to access a different service expecting `order:List`. This prevents cross-tool data access at the authorization layer. * **Short TTLs limit exposure** -- Delegation tokens expire in seconds. Even if a token is intercepted between the gateway and an upstream service, it cannot be reused in a different context or against a different service because it has already expired and is scoped to a single tool. * **Delegation vs impersonation controls** -- The Orchestrator supports [two token exchange modes](/reference/modes/ai-identity-gateway#delegation-vs-impersonation). Delegation (default) produces tokens with an `act` claim that preserves full identity context -- downstream services see both agent and user identity. Impersonation produces tokens that assume the user's identity without exposing the agent's identity. Organizations choose the mode that matches their data-sharing requirements. * **Session isolation** -- At the MCP transport layer, sessions are isolated per agent connection. One agent's session context -- including discovered tools, session state, and MCP session ID -- is not shared with other agents connecting to the same gateway. This is transport-level isolation; model-level context isolation (the core OWASP concern) is addressed in the complementary controls below. **Complementary controls needed:** The gateway prevents **token-based** cross-context access but does not control the **AI model's context memory**. OWASP recommends ephemeral contexts with automatic deletion post-task, per-user/per-agent namespace isolation in vector stores, data classification tagging (Public/Internal/Confidential/Restricted), TTL enforcement on context memory with automated purging, PII redaction before context storage, and injection filtering that detects instruction-like persistence attempts. These are AI model-layer and data pipeline controls outside the scope of the identity gateway. ## Related Pages Set up the Auth Provider and AI Identity Gateway with per-tool token exchange Configure audit logging, TLS, secret management, and SIEM integration Define OPA-based access control policies for fine-grained authorization Complete configuration reference for MCP Provider settings, transports, and OAuth # Scale the AI Identity Gateway for Production Source: https://docs.strata.io/guides/ai-identity/scale-for-production By the end of this guide, you will have a production-scaled AI Identity Gateway deployment with horizontally scaled Auth Provider and Gateway Orchestrators, load-balanced MCP traffic, optimized token exchange, and observability tuned for AI agent workloads. The AI Identity Gateway has a [two-deployment architecture](/reference/modes/ai-identity-gateway#two-deployment-architecture): an **Auth Provider Orchestrator** (OIDC Provider) that issues and exchanges tokens, and an **AI Identity Gateway Orchestrator** (MCP Provider) that handles agent connections and tool routing. Scaling for production means scaling both deployments independently, because they have different load profiles and different infrastructure requirements. Both the Auth Provider and AI Identity Gateway are the same Orchestrator software with different configurations. You do not need to install or manage separate products -- just deploy the same Orchestrator image with the appropriate configuration for each tier. AI agent traffic patterns differ from human user traffic. Agents make rapid, bursty tool invocations -- a single agent session can trigger dozens of token exchanges in seconds. This guide addresses the scaling challenges specific to these patterns. ## Prerequisites * **A working AI Identity Gateway deployment** -- You should have the Auth Provider Orchestrator and AI Identity Gateway Orchestrator configured and working in development. See the [AI Identity overview](/guides/ai-identity/overview) for setup. * **Familiarity with production deployment basics** -- This guide builds on the [Deploy to Production](/guides/operations/deploy) and [Scale for Production](/guides/operations/scale) guides. Read those first if you have not deployed the Orchestrator to production before. * **A load balancer with cookie and header-based session affinity** -- The Auth Provider requires cookie-based affinity (on the `maverics_session` cookie). The AI Identity Gateway requires header-based affinity (on the `Mcp-Session-Id` header). See [Configure load balancing for MCP traffic](#configure-load-balancing-for-mcp-traffic) for examples. * **A Redis instance** -- Required for the Auth Provider Orchestrator (OIDC Provider) in multi-node deployments. * **An observability stack** -- Prometheus, Grafana, or equivalent for metrics and dashboards. See the [Monitor guide](/guides/operations/monitor) for setup. ## Scale the AI Identity Gateway The Auth Provider Orchestrator is a standard Maverics Orchestrator configured with an `oidcProvider` block. It runs as an OIDC Provider and handles agent authentication, token issuance, and per-tool token exchange. In an AI Identity Gateway deployment, every tool invocation triggers a token exchange request to this service. Scale the Auth Provider horizontally with Redis caching and sticky sessions, following the same pattern as any [OIDC Provider scaling](/guides/operations/scale): * **Redis cache is required** for multi-node OIDC Provider deployments. Authorization codes, token state, and provider data must be accessible from any instance. * **Sticky sessions** ensure each agent's OAuth flow completes on the same instance. Go to **Deployments** in the sidebar and select the deployment that runs your Auth Provider Orchestrator. Under **Orchestrator Settings**, scroll to **Redis Caches** and click **Add**. Fill in the Redis connection, TLS, and encryption settings, then click **Add**. Under **OIDC Provider**, click **Edit OIDC Provider**. Select the Redis cache you created from the **Redis Cache** dropdown and click **Save**. Under **Session and Cookie**, click **Edit Session and Cookie**. Adjust the cache size, lifetime, and idle timeout for your expected agent volume, then click **Save**. Configure the Auth Provider Orchestrator with Redis caching and production session settings: ```yaml maverics.yaml theme={null} # Auth Provider Orchestrator configuration http: address: "{{ env.MAVERICS_HTTP_ADDRESS }}" tls: default tls: default: certFile: "{{ env.TLS_CERT_PATH }}" keyFile: "{{ env.TLS_KEY_PATH }}" minVersion: 1.2 caches: - name: auth-redis type: redis redis: addresses: - "{{ env.REDIS_ADDRESS }}" password: tls: default encryption: keys: current: hashing: keys: disabled: false session: cookie: name: maverics_session domain: .example.com lifetime: maxTimeout: 12h idleTimeout: 30m store: type: local local: capacity: 100000 oidcProvider: cache: auth-redis correlateSession: true discovery: issuer: https://auth.example.com endpoints: wellKnown: https://auth.example.com/.well-known/oauth-authorization-server jwks: https://auth.example.com/oauth2/jwks auth: https://auth.example.com/oauth2/auth token: https://auth.example.com/oauth2/token userinfo: https://auth.example.com/oauth2/userinfo introspect: https://auth.example.com/oauth2/introspect jwks: - algorithm: RSA256 publicKey: privateKey: ``` The `capacity: 100000` on the local session store accommodates the higher session volume from AI agents. Adjust this based on your expected concurrent user count. See [Redis Cache Reference](/reference/orchestrator/caches/redis) for Redis clustering and encryption options. The Auth Provider is the token-minting bottleneck. If agents experience slow tool invocations, check Auth Provider latency first -- every tool call requires a round-trip token exchange to this service. The AI Identity Gateway Orchestrator is the same Maverics Orchestrator software, configured with an `mcpProvider` block instead of an `oidcProvider` block. It runs the MCP Provider with your MCP Bridge and MCP Proxy apps, handling inbound agent connections, tool discovery, OPA policy evaluation, and upstream forwarding. Unlike the Auth Provider, the Gateway Orchestrator does not use an external state store. Go to **Deployments** in the sidebar and select the deployment that runs your AI Identity Gateway Orchestrator. Under **Orchestrator Settings**, scroll to **MCP Provider** and click **Edit MCP Provider**. Enable the provider, configure the **Stream Endpoint**, **Session** settings (header name, timeout), and **OAuth 2.0 Authorization Settings**, then click **Save**. Configure the AI Identity Gateway Orchestrator for production: ```yaml maverics.yaml theme={null} # AI Identity Gateway Orchestrator configuration http: address: "{{ env.MAVERICS_HTTP_ADDRESS }}" tls: default tls: default: certFile: "{{ env.TLS_CERT_PATH }}" keyFile: "{{ env.TLS_KEY_PATH }}" minVersion: 1.2 mcpProvider: enabled: true transports: stream: enabled: true path: /mcp session: enabled: true headerName: Mcp-Session-Id timeout: 1h authorization: oauth: enabled: true metadataPath: /.well-known/oauth-protected-resource servers: - wellKnownEndpoint: https://auth.example.com/.well-known/oauth-authorization-server refreshInterval: 5m tokenValidation: expectedAudiences: - https://gateway.example.com/ method: jwt ``` Key scaling considerations for the Gateway Orchestrator: * **No Redis needed** -- The AI Identity Gateway uses token-based state tied to the upstream OAuth authorization server. Each request is independently validated. * **MCP session affinity** -- While the Gateway is stateless for authorization, MCP sessions (tracked via the `Mcp-Session-Id` header) maintain tool discovery state in the process memory of the instance that minted them. Configure your load balancer to pin each session to the instance that minted it; otherwise follow-up requests may land on an instance that does not recognize the session ID. See [Configure load balancing for MCP traffic](#configure-load-balancing-for-mcp-traffic) for tested LB configurations. * **OAuth metadata refresh** -- The `refreshInterval: "5m"` ensures the Gateway periodically refreshes the Auth Provider's JWKS and metadata. In high-availability deployments, this prevents stale signing key issues during key rotation. * **Scaling ratio** -- The Auth Provider and Gateway have different load profiles. The Auth Provider handles CPU-intensive cryptographic operations (JWT signing) per request, while the Gateway handles all inbound MCP traffic (tool discovery, OPA evaluation, upstream forwarding). Monitor both and scale each independently based on observed load. MCP traffic uses Streamable HTTP, which is HTTP-based but has specific load balancer requirements. You need separate load balancers (or separate listener rules) for the Auth Provider and the Gateway, since they serve different roles and may scale independently. **Auth Provider load balancer:** * Cookie-based sticky sessions on the Orchestrator's session cookie which has a default name of `maverics_session` (same as any OIDC Provider -- see [Scale for Production](/guides/operations/scale#configure-load-balancing)) * Health check on `/status` **AI Identity Gateway load balancer:** * Session affinity on the `Mcp-Session-Id` header for Streamable HTTP connections * Extended timeouts for long-lived MCP sessions (at least 1 hour to match the default `session.timeout`) * Health check on `/status` ```nginx theme={null} # Auth Provider upstream upstream auth_provider { server 10.0.1.10:9443; server 10.0.1.11:9443; sticky cookie maverics_session; } # AI Identity Gateway upstream upstream ai_gateway { server 10.0.2.10:9443; server 10.0.2.11:9443; server 10.0.2.12:9443; # Route based on the Mcp-Session-Id header for session affinity sticky route $http_mcp_session_id; } server { listen 443 ssl; server_name auth.example.com; location / { proxy_pass https://auth_provider; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; } } server { listen 443 ssl; server_name gateway.example.com; # Extended timeouts for long-lived MCP sessions proxy_read_timeout 3600s; proxy_send_timeout 3600s; location / { proxy_pass https://ai_gateway; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; } location /status { proxy_pass https://ai_gateway/status; } } ``` This example uses [Envoy Gateway](https://gateway.envoyproxy.io), an open source Kubernetes Gateway API implementation. The Auth Provider uses cookie-based session affinity (standard `BackendTrafficPolicy`). The AI Identity Gateway needs Envoy's [envelope-mode stateful session filter](https://www.envoyproxy.io/docs/envoy/latest/api-v3/extensions/http/stateful_session/envelope/v3/envelope.proto), which Envoy Gateway does not yet expose through `BackendTrafficPolicy.SessionPersistence` -- it must be enabled via [`EnvoyPatchPolicy`](https://gateway.envoyproxy.io/docs/tasks/extensibility/envoy-patch-policy/). The envelope stateful session extension was added in **Envoy v1.35.0** ([envoyproxy/envoy#39004](https://github.com/envoyproxy/envoy/pull/39004)) and shipped with the default Envoy data-plane image in **Envoy Gateway v1.5.0+**. Earlier versions silently reject the patch. See the [Envoy Gateway compatibility matrix](https://gateway.envoyproxy.io/news/releases/matrix/). `EnvoyPatchPolicy` is also disabled by default and must be turned on in the EnvoyGateway config. With the official [Helm chart](https://gateway.envoyproxy.io/docs/install/install-helm/) set `config.envoyGateway.extensionApis.enableEnvoyPatchPolicy=true` at install or upgrade time. ```yaml theme={null} # Auth Provider -- cookie-based affinity on maverics_session apiVersion: gateway.networking.k8s.io/v1 kind: HTTPRoute metadata: name: auth-provider namespace: maverics spec: parentRefs: - name: maverics hostnames: - auth.example.com rules: - backendRefs: - name: auth-provider port: 9443 --- apiVersion: gateway.envoyproxy.io/v1alpha1 kind: BackendTrafficPolicy metadata: name: auth-provider-affinity namespace: maverics spec: targetRefs: - group: gateway.networking.k8s.io kind: HTTPRoute name: auth-provider loadBalancer: type: ConsistentHash consistentHash: type: Cookie cookie: name: maverics_session --- # AI Identity Gateway -- HTTPRoute (LB affinity is set up via EnvoyPatchPolicy below) apiVersion: gateway.networking.k8s.io/v1 kind: HTTPRoute metadata: name: ai-gateway namespace: maverics spec: parentRefs: - name: maverics hostnames: - gateway.example.com rules: - backendRefs: - name: ai-gateway port: 9443 --- # AI Identity Gateway -- session affinity via envelope-mode stateful_session. # # Envoy rewrites the Mcp-Session-Id response header to embed the chosen # upstream instance's address alongside the original session ID. On subsequent # requests, Envoy decodes the address back out and routes to that instance, # restoring the original session ID before forwarding upstream. Transparent # to MCP clients (the session ID is treated as opaque per the MCP spec) # and to the AI Identity Gateway (it never sees the encoded form). apiVersion: gateway.envoyproxy.io/v1alpha1 kind: EnvoyPatchPolicy metadata: name: ai-gateway-envelope-session namespace: maverics spec: targetRef: group: gateway.networking.k8s.io kind: Gateway name: maverics type: JSONPatch jsonPatches: - type: type.googleapis.com/envoy.config.listener.v3.Listener # Envoy Gateway names listeners //. # Update this to match your Gateway. The listener name is also visible # in the data-plane Envoy's /listeners admin endpoint. name: maverics/maverics/https operation: op: add path: /default_filter_chain/filters/0/typed_config/http_filters/0 value: name: envoy.filters.http.stateful_session typed_config: "@type": type.googleapis.com/envoy.extensions.filters.http.stateful_session.v3.StatefulSession session_state: name: envoy.http.stateful_session.envelope typed_config: "@type": type.googleapis.com/envoy.extensions.http.stateful_session.envelope.v3.EnvelopeSessionState header: name: Mcp-Session-Id ``` **Why not just `BackendTrafficPolicy.SessionPersistence`?** Envoy Gateway exposes `Cookie` and `Header` modes there, but neither fits the MCP protocol: * **Cookie mode** writes a `Set-Cookie` that the LB reads on subsequent requests. MCP clients typically do not use cookies, so the cookie is dropped and affinity is lost. * **Header mode** writes the chosen upstream's address into a configured response header. If you point it at `Mcp-Session-Id`, the value collides with the session ID the AI Identity Gateway already wrote; if you point it at a sibling header, MCP clients do not know to roundtrip it. The envelope mode rewrites the existing `Mcp-Session-Id` *value* to embed both the upstream address and the original session ID, which is the only approach that is transparent to MCP clients while preserving the protocol semantics. This example uses the [HAProxy Kubernetes Ingress Controller](https://www.haproxy.com/documentation/kubernetes-ingress/), the official open source Ingress Controller from HAProxy Technologies. The Auth Provider uses cookie-based session affinity (the standard [`haproxy.org/cookie-persistence`](https://www.haproxy.com/documentation/kubernetes-ingress/community/configuration-reference/ingress/#cookie-persistence) annotation). The AI Identity Gateway uses HAProxy's [stick-table](https://www.haproxy.com/documentation/haproxy-configuration-tutorials/load-balancing/sticky-sessions/) mechanism, which learns the `` mapping from the upstream's `Mcp-Session-Id` response header and routes subsequent requests with the same header back to the recorded instance. The Ingress Controller does not expose stick-table-on-header as a first-class annotation, so we inject the directives via the controller's escape hatch: [`haproxy.org/backend-config-snippet`](https://www.haproxy.com/documentation/kubernetes-ingress/community/configuration-reference/ingress/#backend-config-snippet). Install the controller via the official [Helm chart](https://github.com/haproxytech/helm-charts/tree/main/kubernetes-ingress): ```bash theme={null} helm repo add haproxytech https://haproxytech.github.io/helm-charts helm install haproxy-kic haproxytech/kubernetes-ingress \ -n haproxy-controller --create-namespace ``` The `backend-config-snippet` annotation passes raw HAProxy directives directly into the rendered backend section, so syntax is validated by HAProxy at reload time -- not by the controller. Malformed snippets cause HAProxy to fail to reload; check the controller pod logs after applying. ```yaml theme={null} # Auth Provider -- cookie-based affinity on maverics_session apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: auth-provider namespace: maverics annotations: haproxy.org/cookie-persistence: maverics_session spec: ingressClassName: haproxy rules: - host: auth.example.com http: paths: - path: / pathType: Prefix backend: service: name: auth-provider port: number: 9443 --- # AI Identity Gateway -- session affinity via stick-table on Mcp-Session-Id. # # HAProxy maintains an in-memory stick-table keyed by the Mcp-Session-Id # value. The `stick store-response` directive records -> # when an upstream responds with the header (i.e. on `initialize`). # The `stick on` directive looks up that mapping on subsequent requests # and routes to the recorded instance -- transparent to MCP clients (they # roundtrip the protocol-mandated Mcp-Session-Id header by spec). apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: ai-gateway namespace: maverics annotations: haproxy.org/load-balance: roundrobin haproxy.org/backend-config-snippet: | stick-table type string len 128 size 100k expire 1h stick on req.hdr(Mcp-Session-Id) stick store-response res.hdr(Mcp-Session-Id) # Extended timeouts for long-lived MCP sessions haproxy.org/timeout-client: 1h haproxy.org/timeout-server: 1h spec: ingressClassName: haproxy rules: - host: gateway.example.com http: paths: - path: / pathType: Prefix backend: service: name: ai-gateway port: number: 9443 ``` **Why not `haproxy.org/cookie-persistence` for the AI Identity Gateway too?** The annotation works perfectly for the Auth Provider's browser-based OAuth flow, but cookie-based affinity does not work for typical MCP clients. MCP clients only roundtrip the protocol-mandated `Mcp-Session-Id` header, so the LB has to key affinity off that header rather than off a cookie it sets itself. The stick-table state lives in HAProxy's process memory. For multi-replica HAProxy deployments, configure HAProxy [`peers`](https://docs.haproxy.org/dev/configuration.html#3.5) to replicate stick-tables across replicas; otherwise each replica builds its own table independently and traffic must remain pinned to a specific HAProxy replica (typically via L4 source-IP affinity at the upstream LB). Per-tool token exchange is one of the core security mechanism of the AI Identity Gateway -- every tool invocation triggers a token exchange round-trip to the Auth Provider. At scale, this becomes the primary latency and throughput bottleneck. Optimize token exchange performance: 1. **Minimize network latency between Gateway and Auth Provider** -- Deploy them in the same region and availability zones. Each tool invocation adds one round-trip to the Auth Provider, so every millisecond of network latency is multiplied by the number of tool calls. 2. **Scale the Auth Provider ahead of demand** -- The Auth Provider handles cryptographic operations (JWT signing) for every token exchange. Monitor CPU utilization on Auth Provider instances and scale horizontally before saturation. When deploying on platforms like Kubernetes, autoscaling rules can be configured based on the CPU utilization (see the Orchestrator [Helm Chart](https://github.com/strata-io/helm-charts/blob/main/charts/orchestrator/values.yaml#L93C3-L93C33) for an example). 3. **Set appropriate token TTLs** -- Short TTLs (e.g., `5s`) are the default and provide the strongest security. If your tool invocations involve slow upstream APIs, increase the TTL to avoid tokens expiring mid-request. Balance security requirements against your upstream response times. Go to **Applications** in the sidebar and select your MCP Bridge or MCP Proxy application. Under **Application Identity**, click **Edit**. In the **Outbound Request Authorization** section, set **Authorization Type** to **Token Exchange**, choose the **Exchange Type** and **OIDC Identity Provider**, and set the **Audience**. Under **Tool Configurations**, click **Add Tool Configuration**. Enter the **Tool Name** (exact match or regex pattern), set a **Token Lifetime (TTL)**, and add any required **OAuth Scopes**. Repeat for each tool or tool pattern. Configure per-tool token exchange with appropriate TTLs in your MCP Bridge or MCP Proxy app: ```yaml maverics.yaml theme={null} # On the AI Identity Gateway Orchestrator apps: - name: employee-api type: mcpBridge mode: openapi openapi: spec: uri: https://api.example.com/openapi.json baseURL: https://api.example.com authorization: outbound: type: tokenExchange tokenExchange: type: delegation # Connector pointing to the Auth Provider's OIDC well-known idp: auth-provider audience: https://api.example.com/ tools: - name: listEmployees ttl: 10s scopes: - name: employee:List - name: getEmployee ttl: 10s scopes: - name: employee:Get - name: createEmployee ttl: 30s scopes: - name: employee:Create ``` Write operations (`createEmployee`) use a longer TTL because the upstream API may take longer to process mutations. Read operations use shorter TTLs because they complete quickly and benefit from tighter token lifetimes. AI agent traffic generates different load patterns than human user traffic. Agents make rapid, bursty requests -- a single agent session can trigger dozens of tool invocations in seconds. Monitor both the Auth Provider and Gateway deployments to detect bottlenecks early. Key host-level metrics to monitor on both deployments: | Metric | Why It Matters | | ----------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | | CPU utilization | Token exchange (Auth Provider) and policy evaluation (Gateway) are CPU-intensive. Scale horizontally when utilization exceeds 70%. | | Memory usage | High memory on the Auth Provider may indicate Redis connection pooling issues. High memory on the Gateway may indicate excessive concurrent MCP sessions. | | Network throughput | Every tool invocation generates a round-trip between Gateway and Auth Provider. Monitor for saturation, especially if they are in different availability zones. | | Request rate and error rate | Use your load balancer's metrics to track inbound request volume and 5xx error rates for each deployment independently. | | Load balancer health check failures | Indicates an Orchestrator instance is unhealthy or unreachable. Configure alerts so failed instances are investigated promptly. | | Open file descriptors | The Gateway maintains concurrent connections: inbound from agents, outbound to the Auth Provider for token exchange, and outbound to upstream APIs. While connections are reused across requests, each concurrent agent session consumes file descriptors across all three. Ensure the OS `ulimit -n` is set high enough and monitor usage to avoid connection failures. | See the [Monitor guide](/guides/operations/monitor) for setting up OpenTelemetry metrics and traces, and [Telemetry Reference](/reference/orchestrator/telemetry) for all configuration options. AI Identity Gateway-specific metrics -- including token exchange latency, MCP session counts, and tool invocation rates -- are planned for a future Orchestrator release. Today, use host-level and load balancer metrics to monitor your deployment. With both deployments scaled, load balancers configured, and observability in place, verify that the entire system works end-to-end under load. ```bash theme={null} # Verify Auth Provider instances are healthy curl -s https://auth.example.com/status | jq . # Verify AI Identity Gateway instances are healthy curl -s https://gateway.example.com/status | jq . # Verify OAuth discovery works through the load balancer curl -s https://gateway.example.com/.well-known/oauth-protected-resource | jq . ``` Test the full agent flow: 1. **Connect an agent to the Gateway** through the load balancer -- verify OAuth discovery returns the Auth Provider's metadata 2. **Authenticate the agent** against the Auth Provider -- verify token issuance succeeds 3. **Discover tools** -- verify the agent receives the full tool catalog 4. **Invoke a tool** -- verify the tool call succeeds end-to-end (agent → Gateway → token exchange → Auth Provider → upstream API) 5. **Check audit logs** -- verify the tool invocation is logged with both agent and user identity 6. **Simulate a Gateway instance failure** -- stop one Gateway instance and verify the agent's next request is routed to a healthy instance 7. **Simulate an Auth Provider instance failure** -- stop one Auth Provider instance and verify token exchange still succeeds via remaining instances **Success!** Your AI Identity Gateway is scaled for production. The Auth Provider handles token exchange with Redis-backed state, the Gateway handles MCP traffic seamlessly, load balancers route traffic with appropriate session affinity, and observability captures AI-specific metrics for monitoring and alerting. Remember, both tiers are running the same Orchestrator software -- upgrades and patches apply uniformly to both deployments. ## Architecture Overview The following diagram shows the scaled two-deployment architecture with load balancers, multiple instances, and the flow of MCP traffic: ```mermaid theme={null} flowchart LR subgraph Users["User-Delegated Agents"] U1[Agent 1] U2[Agent N] end subgraph Autonomous["Autonomous Agents"] A1[Agent 1] A2[Agent N] end subgraph ALB["Auth Provider Load Balancer"] ALB1[Cookie-based
sticky sessions] end subgraph Auth["Auth Provider
(OIDC Provider)"] AP1[Auth 1] AP2[Auth 2] AP3[Auth N] end subgraph GLB["Gateway Load Balancer"] GLB1[MCP session affinity
Extended timeouts] end subgraph Gateway["AI Identity Gateway
(MCP Provider)"] G1[Gateway 1] G2[Gateway 2] G3[Gateway N] end Redis[(Redis)] APIs[Upstream APIs /
MCP Servers] U1 & U2 -->|Authentication| ALB1 A1 & A2 -->|Authentication| ALB1 ALB1 --> AP1 & AP2 & AP3 AP1 & AP2 & AP3 --> Redis U1 & U2 -->|MCP Tool Calls| GLB1 A1 & A2 -->|MCP Tool Calls| GLB1 GLB1 --> G1 & G2 & G3 G1 & G2 & G3 -->|Token Exchange| ALB1 G1 & G2 & G3 -->|Tool Invocation| APIs ``` ## Troubleshooting High token exchange latency usually means the Auth Provider is the bottleneck: * **Check Auth Provider CPU** -- Token exchange involves JWT signing, which is CPU-intensive. If CPU utilization is above 70%, add more Auth Provider instances. * **Check Redis latency** -- The Auth Provider reads/writes token state in Redis. High Redis latency propagates to every token exchange. Monitor Redis response times and consider upgrading to a larger Redis instance or a Redis cluster. * **Check network latency** -- If the Gateway and Auth Provider are in different availability zones or regions, every tool invocation pays the cross-zone round-trip cost. Co-locate them in the same zone. Premature session disconnections are usually caused by load balancer timeouts: * **Check load balancer idle timeout** -- MCP sessions can be idle between tool invocations. If the load balancer's idle timeout is shorter than the MCP session timeout, the connection drops. Set the load balancer idle timeout to at least match `mcpProvider.transports.stream.session.timeout` (default 1 hour). * **Check proxy timeouts** -- NGINX `proxy_read_timeout` and `proxy_send_timeout` must accommodate long-lived MCP sessions. Set both to at least 3600 seconds. If agents lose their tool catalog after a Gateway scaling event (new instances added or removed): * **Check session affinity** -- If the load balancer is not pinning each MCP session to the instance that minted it, agents may be routed to a Gateway instance that does not have their session context. See [Configure load balancing for MCP traffic](#configure-load-balancing-for-mcp-traffic) for tested LB configurations; in particular, generic consistent-hashing on the `Mcp-Session-Id` header does not deliver affinity (the instance that minted the session and the instance the hash selects are uncorrelated), and cookie-based affinity does not work for MCP clients that do not use cookies. * **Check connection draining** -- When a Gateway instance is removed, in-progress MCP sessions should drain gracefully. Configure connection draining (deregistration delay) on your load balancer to allow active sessions to complete. * **Agent reconnection** -- Well-behaved MCP agents should reconnect and re-discover tools when a session is lost. If your agents do not handle reconnection, consider increasing the connection draining timeout. Slow OPA policy evaluation adds latency to every tool invocation: * **Review policy complexity** -- Complex Rego policies with external data lookups or deep object traversals take longer to evaluate. Simplify policies where possible. * **Check policy data size** -- Large policy data sets (loaded via `data` imports) increase evaluation time. Keep policy data minimal and load only what each policy needs. * **Monitor Gateway CPU** -- OPA evaluation is CPU-bound. If Gateway CPU is high and most of the time is in policy evaluation, scale the Gateway horizontally. ## Related Pages Set up the AI Identity Gateway from scratch with Auth Provider and Gateway configuration Full configuration reference for MCP Provider settings, transports, and OAuth authorization General Orchestrator scaling guide with load balancer examples for all modes Set up OpenTelemetry observability with metrics, traces, and structured logging # Choosing an Orchestrator Mode Source: https://docs.strata.io/guides/authentication/choosing-a-mode The Maverics Orchestrator operates in five modes, each designed for a different protocol and deployment pattern. Choosing the right mode depends on what protocol your application speaks, whether you can modify the application, and what identity operations you need. Most deployments use one or two modes; some use three or more simultaneously. This guide helps you compare all five modes side-by-side so you can pick the right one without reading each mode page individually. If you already know which mode you need, jump to the mode-specific guides linked at the bottom of this page. All five modes share the same Orchestrator binary, configuration framework, and Service Extension SDK. The difference is in how identity is delivered to your applications -- tokens, assertions, HTTP headers, LDAP entries, or OAuth-scoped MCP context. ## Decision Matrix The following table compares all five modes across the criteria that matter most when choosing a deployment pattern. | Criteria | OIDC Provider | SAML Provider | HTTP Proxy | LDAP Provider | AI Identity Gateway | | ----------------------------- | ------------------------------------------------------------------- | ------------------------------------------------------------------- | ---------------------------------------------------------------------------- | ----------------------------------------------------------------------- | ---------------------------------------------------------------- | | **Protocol** | OpenID Connect | SAML 2.0 | HTTP | LDAP | MCP (Model Context Protocol) | | **Best for** | Modern apps that consume OIDC tokens natively | Enterprise SAML apps with rigid federation requirements | Legacy apps where you cannot modify authentication code | LDAP-dependent apps that need a virtual directory | AI agents that invoke tools on behalf of users | | **App modification required** | Yes -- app must be an OIDC client (relying party) | Yes -- app must be configured as a SAML SP | No -- the Orchestrator proxies traffic transparently | No -- the app connects to the Orchestrator as if it were an LDAP server | Yes -- the AI agent must be an MCP/OAuth client | | **Identity delivery** | JWT or opaque tokens (ID token, access token, refresh token) | Signed SAML assertions with mapped attributes | HTTP headers injected into upstream requests (e.g., `SM_USER`) | LDAP entries returned via bind and search operations | OAuth access tokens with MCP tool-scoped context | | **Authorization model** | Per-app declarative rules or OPA policies | Per-app declarative rules | Location-based policies (different rules per URL path) | Service Extension-driven (custom Go logic) | OPA policies evaluated per-tool invocation | | **Session management** | Cookie-based sessions with configurable lifetime | Cookie-based sessions with configurable lifetime | Cookie-based sessions with configurable lifetime | Per-connection LDAP bind state | Token-based (OAuth token lifetime) | | **Service Extensions** | Optional hooks for custom claims, authentication, and authorization | Optional hooks for custom claims, authentication, and authorization | Optional hooks for request/response modification, headers, and authorization | Required for all core operations (bind, search, credential lookup) | Optional (OPA policies are the primary authorization mechanism) | | **Can combine with** | SAML Provider, HTTP Proxy | OIDC Provider, HTTP Proxy | OIDC Provider, SAML Provider, LDAP Provider | HTTP Proxy | Standalone (runs alongside other modes on the same Orchestrator) | ## Decision Flowchart Use this decision tree to identify the right mode for your application. Start at question 1 and follow the path that matches your situation. 1. **Does your application support OpenID Connect natively?** If yes, use [OIDC Provider](/reference/modes/oidc-provider). OIDC is the modern standard for authentication -- if your app supports it, this is the most straightforward mode. (Your IdP does not need to support OIDC -- the Orchestrator can translate from any upstream protocol.) 2. **Does your application only support SAML 2.0?** If yes, use [SAML Provider](/reference/modes/saml-provider). Many enterprise apps (Salesforce, ServiceNow, Workday) require SAML assertions for federated SSO. 3. **Can you NOT modify the application's authentication code at all?** If yes, use [HTTP Proxy](/reference/modes/http-proxy). The Orchestrator sits in front of the app as a reverse proxy, handling authentication and injecting identity headers without any changes to the application. 4. **Does your application require LDAP directory lookups for authentication or user data?** If yes, use [LDAP Provider](/reference/modes/ldap-provider). The Orchestrator presents a virtual LDAP directory backed by modern cloud identity providers. This mode is often paired with HTTP Proxy for comprehensive legacy stack modernization. 5. **Are you securing AI agent-to-tool communication via MCP?** If yes, use [AI Identity Gateway](/reference/modes/ai-identity-gateway). This mode adds identity, authorization, and audit to Model Context Protocol connections between AI agents and enterprise tools. ## Protocol Translation The Orchestrator's mode determines what protocol your **application** speaks. The Identity Fabric connector determines what protocol your **identity provider** speaks. These are completely independent. This means you do not need to match your IdP's protocol to your application's protocol. For example: * An application that only speaks SAML can authenticate against an OIDC-only IdP (using SAML Provider mode with an OIDC connector) * An application that only speaks OIDC can authenticate against a SAML-only IdP (using OIDC Provider mode with a SAML connector) * An application behind HTTP Proxy can authenticate against an LDAP directory or any OIDC/SAML provider The Orchestrator handles all protocol translation transparently. When choosing a mode, focus on what protocol your **application** requires -- the IdP side is handled by the connector, which can speak any supported protocol. ## Connector Compatibility Every Orchestrator mode works with every Identity Fabric connector -- the Orchestrator handles protocol translation between your identity provider and your application. However, some connectors are more commonly used with certain modes. The table below shows the typical pairings and notes for each combination. | Connector | OIDC Provider | SAML Provider | HTTP Proxy | LDAP Provider | AI Identity Gateway | | ---------------------------------------------------------------------------- | :-----------: | :-----------: | :--------: | :---------------------: | :-----------------: | | [Microsoft Entra ID](/reference/orchestrator/identity-fabric/azure-ad) | Common | Common | Common | Common | Common | | [Okta](/reference/orchestrator/identity-fabric/okta) | Common | Common | Common | Common | Common | | [PingFederate](/reference/orchestrator/identity-fabric/pingone) | Common | Common | Common | Possible | Possible | | [Auth0](/reference/orchestrator/identity-fabric/auth0) | Common | Common | Common | Possible | Common | | [ADFS](/reference/orchestrator/identity-fabric/adfs) | Common | Common | Common | Possible | Possible | | [Amazon Cognito](/reference/orchestrator/identity-fabric/cognito) | Common | Possible | Possible | Possible | Common | | [Generic OIDC](/reference/orchestrator/identity-fabric/custom-oidc) | Common | Common | Common | Possible | Common | | [Google Workspace](/reference/orchestrator/identity-fabric/google-workspace) | Common | Common | Common | Possible | Common | | [Generic SAML](/reference/orchestrator/identity-fabric/custom-saml) | Common | Common | Common | Rare | Rare | | [LDAP](/reference/orchestrator/identity-fabric/ldap) | Possible | Possible | Common | Common (as attr source) | Rare | | [Active Directory](/reference/orchestrator/identity-fabric/activedirectory) | Possible | Possible | Common | Common (as attr source) | Rare | | [Continuity](/reference/orchestrator/identity-fabric/continuity) | Common | Common | Common | Possible | Possible | **Common** = frequently used pairing. **Possible** = works but less typical. **Rare** = technically possible but uncommon. All connectors work with all modes -- the Orchestrator handles protocol translation. Continuity connectors aggregate multiple IdPs for failover and are mode-agnostic. For a complete walkthrough on setting up Identity Continuity with automatic failover, see the [Identity Continuity guide](/guides/identity-continuity/overview). ## Common Combinations Modes can run simultaneously on the same Orchestrator instance. Here are the most common combinations and when to use them. ### OIDC Provider + HTTP Proxy Use this combination when your organization has both modern and legacy applications. Modern apps consume OIDC tokens directly from the Orchestrator's OIDC Provider. Legacy apps that cannot be modified receive identity through HTTP headers injected by the proxy. Both share the same upstream identity providers and session infrastructure. ### HTTP Proxy + LDAP Provider Use this combination for full legacy stack modernization. Many legacy applications depend on both header-based authentication (for the web tier) and LDAP directory lookups (for user data and group membership). Running both modes on the same Orchestrator provides a complete identity bridge -- the proxy handles HTTP traffic while the virtual directory handles LDAP queries, both sourcing identity from modern cloud providers. ### OIDC Provider + SAML Provider Use this combination to bridge modern and enterprise authentication protocols. The Orchestrator acts as both an OIDC authorization server and a SAML identity provider simultaneously. This enables protocol translation -- upstream OIDC identity providers can feed downstream SAML service providers, or vice versa -- making IdP migration possible without changing application configurations on either side. ## Deployment Topologies The Common Combinations section above describes modes running together on a single Orchestrator instance. In production, organizations typically deploy multiple separate Orchestrator instances, each named and configured for a specific role. The Console manages all deployments from a single pane of glass. The patterns below are common starting points -- many permutations are possible depending on your organization's needs. ### Auth Provider A centralized deployment running OIDC Provider and SAML Provider modes together. This deployment acts as the organization's identity broker -- modern apps connect via OIDC, enterprise apps connect via SAML, and both share the same upstream identity providers and session infrastructure. This is the most common starting point for organizations adopting the Orchestrator. ### AI Identity Gateway A standalone deployment running only AI Identity Gateway mode. It secures MCP connections between AI agents and enterprise tools, enforcing identity, authorization, and audit on every tool invocation. Typically deployed alongside (but separate from) the Auth Provider so that AI identity workflows are isolated from traditional authentication traffic. ### HTTP Proxy HTTP Proxy deployments follow two common patterns depending on the environment. **Centralized proxy** -- A single HTTP Proxy deployment fronting multiple legacy applications. This is simpler to manage and works well when applications share similar authentication patterns and header requirements. **Per-application proxy** -- A dedicated HTTP Proxy deployment for each legacy application. This provides isolation -- each app gets its own configuration, policies, and scaling. Use this pattern when applications have different authentication requirements or when teams manage their own infrastructure. ### LDAP Provider LDAP Provider deployments also follow two common patterns. **Centralized** -- A single LDAP Provider deployment serving multiple LDAP-consuming applications across the network. This minimizes the number of deployments to manage and works well when applications share similar directory schemas. **Co-located** -- An LDAP Provider deployed on the same server (or in the same pod) as the LDAP-consuming application. This keeps LDAP traffic local -- the application connects to localhost rather than sending LDAP queries across the network. Use this pattern in security-sensitive environments or for applications with high LDAP query volume. ## Mode-Specific Guides Configure the Orchestrator as an OIDC Provider for modern single sign-on Federate enterprise SAML applications through the Orchestrator Protect legacy applications with reverse proxy authentication and header injection Migrate between identity providers with zero downtime Set up automatic IdP failover with health monitoring and simulation testing ## Mode Reference Pages Complete OIDC Provider configuration reference Complete SAML Provider configuration reference Complete HTTP Proxy configuration reference Complete LDAP Provider configuration reference Complete AI Identity Gateway configuration reference Shared app fields, authorization rules, and all 5 app types # How Authentication Works Source: https://docs.strata.io/guides/authentication/how-auth-works The Maverics Orchestrator handles authentication across five modes, each serving a different protocol: OIDC, SAML, HTTP, LDAP, and MCP. Although each mode speaks a different wire protocol, the three core modes -- OIDC Provider, SAML Provider, and HTTP Proxy -- follow a common authentication pipeline: intercept the request, authenticate the user against an upstream identity provider, enrich the user's attributes, establish a cookie-based session, and deliver identity to the application in the format it expects. LDAP Provider and AI Identity Gateway follow a similar pattern but handle authentication state differently: LDAP Provider uses per-connection bind state rather than cookie-based sessions, and AI Identity Gateway uses OAuth token-based state management. This page explains how that pipeline works so you can understand the system holistically before diving into mode-specific configuration. By the end, you will know which steps are shared across the core modes, where LDAP Provider and AI Identity Gateway diverge, and how sessions and Service Extensions fit into the authentication lifecycle. Understanding the shared pipeline also makes it easier to run multiple modes simultaneously. Many deployments combine HTTP Proxy with LDAP Provider for legacy stacks, or run OIDC Provider alongside SAML Provider for mixed application portfolios. Because OIDC Provider, SAML Provider, and HTTP Proxy share the same session and attribute enrichment infrastructure, users authenticated in one of these modes carry their identity context across the system. LDAP Provider uses per-connection bind state and does not participate in the shared session infrastructure. AI Identity Gateway uses token-based state management tied to the upstream OAuth authorization server. ## The Authentication Pipeline OIDC Provider, SAML Provider, and HTTP Proxy follow the same six-step pipeline, with steps 2 through 4 shared across these three modes. LDAP Provider and AI Identity Gateway follow a similar pattern but differ in how they handle authentication (step 2) and session state (step 4). Steps 1 and 5 differ by mode across all five modes. 1. **Request arrives** -- A protocol-specific trigger starts the flow. For OIDC, this is an authorization request to the `/oauth2/auth` endpoint. For SAML, it is an `AuthnRequest` from a service provider. For HTTP Proxy, it is any HTTP request matching a route pattern. For LDAP, it is a bind operation on the LDAP port. For AI Identity Gateway, it is an MCP connection with an OAuth token. 2. **Upstream IdP authentication** -- The Orchestrator routes the user to a configured upstream identity provider (Microsoft Entra ID, Okta, PingFederate, or any OIDC/SAML/LDAP connector) for authentication. If multiple IdPs are configured, the Orchestrator tries them in order -- if the primary IdP is unavailable, authentication falls back to the next provider seamlessly. The [Continuity connector](/guides/identity-continuity/overview) enables health-check-driven failover without application changes. 3. **Attribute enrichment** -- After authentication succeeds, attribute providers load additional claims about the user from directories, databases, and APIs. This enrichment step aggregates identity data from multiple sources into a single profile, regardless of which IdP authenticated the user. 4. **Session establishment** -- For OIDC Provider, SAML Provider, and HTTP Proxy, the Orchestrator creates a server-side session containing the authentication state, tokens, and enriched attributes. An opaque session cookie is returned to the client. All sensitive data stays server-side -- the cookie is just an identifier. LDAP Provider maintains per-connection bind state instead of creating a cookie-based session. AI Identity Gateway relies on the upstream OAuth token lifecycle rather than Orchestrator-managed sessions. See the [Sessions documentation](/reference/orchestrator/sessions) for configuration details. 5. **Identity delivery** -- The Orchestrator delivers the authenticated identity in the format the application expects. For OIDC, this means issuing ID tokens, access tokens, and optional refresh tokens. For SAML, it means generating a signed assertion. For HTTP Proxy, it means injecting identity headers into the upstream request. For LDAP, it means returning translated directory entries. For AI Identity Gateway, it means propagating identity context through tool invocations. 6. **Ongoing operations** -- After the initial authentication, the Orchestrator manages the ongoing lifecycle: token refresh for OIDC, session expiry and re-authentication for cookie-based modes, and audit logging of identity events. Steps 2 through 4 -- upstream authentication, attribute enrichment, and session establishment -- are shared across OIDC Provider, SAML Provider, and HTTP Proxy. If you configure a connector or attribute provider once, these modes can use it. LDAP Provider uses Service Extensions for authentication (step 2) and per-connection bind state instead of cookie-based sessions (step 4). AI Identity Gateway validates OAuth tokens (step 2) and uses token-based state (step 4). Step 3 (attribute enrichment) is available across all modes. ## Per-Mode Authentication Flows Each mode implements the shared pipeline with protocol-specific behavior at the entry and delivery points. The following sections summarize how authentication works in each mode without duplicating the full reference documentation. ### OIDC Provider The OIDC Provider mode configures the Orchestrator as an OpenID Connect authorization server, issuing standards-compliant tokens to applications that support OIDC natively. 1. The application redirects the user to the Orchestrator's authorization endpoint (`/oauth2/auth`) with standard OIDC parameters (client ID, redirect URI, scopes). 2. The Orchestrator authenticates the user against the configured upstream IdP. The upstream IdP can use any protocol -- the Orchestrator handles protocol translation between OIDC, SAML, and LDAP. 3. After authentication and attribute enrichment, the Orchestrator generates OIDC tokens -- an ID token, an access token, and optionally a refresh token -- with claims mapped from the authenticated identity. 4. The application receives the tokens at its redirect URI and uses them for session establishment and authorization decisions. 5. The Orchestrator serves the JWKS endpoint for token verification, handles token introspection and revocation, and manages refresh token flows. The OIDC Provider supports both JWT and opaque access tokens, DPoP sender-bound tokens for proof-of-possession, and seamless key rotation via the JWKS array. Like all modes, the OIDC Provider can authenticate against upstream IdPs using any supported connector protocol -- OIDC, SAML, or LDAP. See the [OIDC Provider reference](/reference/modes/oidc-provider) for full configuration. ### SAML Provider The SAML Provider mode configures the Orchestrator as a SAML 2.0 identity provider, generating signed assertions for enterprise applications that require SAML federation. 1. A SAML service provider sends an `AuthnRequest` to the Orchestrator's SSO endpoint (SP-initiated flow), or a user navigates to an IdP-initiated login URL. 2. The Orchestrator authenticates the user against the upstream IdP. The upstream IdP can use any protocol -- the Orchestrator handles protocol translation between OIDC, SAML, and LDAP. 3. After attribute enrichment, the Orchestrator generates a signed SAML assertion containing the NameID and mapped attributes. 4. The SAML response is POSTed to the service provider's assertion consumer service URL. The SP validates the signature and establishes a session. The SAML Provider translates between protocols -- an upstream OIDC identity provider can feed a downstream SAML service provider, making IdP migration possible without changing SP configurations. See the [SAML Provider reference](/reference/modes/saml-provider) for full configuration. ### HTTP Proxy The HTTP Proxy mode deploys the Orchestrator as an identity-aware reverse proxy, injecting authentication headers into upstream requests without requiring any changes to the application. 1. The Orchestrator intercepts HTTP requests matching configured route patterns (hostname/path combinations) before they reach the upstream application. 2. If the user does not have a valid session, the Orchestrator redirects them to the configured IdP for authentication. After authentication, a session cookie is established. 3. The Orchestrator evaluates location-based authorization rules against the user's attributes. 4. For authorized requests, the Orchestrator injects identity headers (e.g., `SM_USER`, `X-Remote-User`) into the upstream request using template syntax that maps claims from connectors. 5. The request is forwarded to the upstream backend with the injected headers. The application uses these headers for its own identity decisions. HTTP Proxy supports location-based policies -- different URL paths within the same application can have different authentication and authorization requirements. See the [HTTP Proxy reference](/reference/modes/http-proxy) for full configuration. ### LDAP Provider The LDAP Provider mode configures the Orchestrator as a virtual LDAP directory, presenting a standard LDAP interface to applications while sourcing identity data from modern cloud identity providers. 1. An LDAP-dependent application connects to the Orchestrator's LDAP endpoint (`ldap://` or `ldaps://`) and sends a bind request with a DN and password. 2. A Service Extension validates the credentials against a cloud identity provider -- typically by translating the LDAP bind into an authentication request against the upstream IdP. 3. After successful authentication, the application sends LDAP search requests. A search Service Extension translates these into queries against upstream identity sources and returns matching entries in LDAP format. 4. The Service Extension maps cloud IdP attributes (e.g., Microsoft Entra ID user properties) into the LDAP attribute names the application expects (e.g., `cn`, `sAMAccountName`, `memberOf`). Every LDAP Provider integration requires Service Extensions for its core operations. The `authenticateSE` handles bind operations, and the `searchSE` handles search queries. Unlike other modes that can use declarative configuration alone, the LDAP Provider relies on Go-based Service Extension code. See the [LDAP Provider reference](/reference/modes/ldap-provider) for full configuration. ### AI Identity Gateway The AI Identity Gateway mode extends the Orchestrator into AI agent-to-tool communication, adding identity, authorization, and audit to Model Context Protocol (MCP) connections. 1. An AI agent connects to the Orchestrator's MCP endpoint via SSE or Streamable HTTP transport and presents an OAuth access token. 2. The Orchestrator validates the agent's token against the configured OAuth authorization server. The token identifies both the agent and the delegating user. 3. The agent discovers available tools -- generated from OpenAPI specs (MCP Bridge) or discovered from upstream MCP servers (MCP Proxy). 4. When the agent invokes a tool, the Orchestrator evaluates OPA policies on the inbound request, performs token exchange to obtain a scoped delegation token, and forwards the request to the upstream service. The AI Identity Gateway propagates both agent identity and delegated user identity through the entire tool chain, enabling least-privilege access per tool and full audit trails. See the [AI Identity Gateway reference](/reference/modes/ai-identity-gateway) for full configuration. ## Sessions and Authentication After authentication succeeds in OIDC Provider, SAML Provider, or HTTP Proxy mode, the Orchestrator creates a server-side session that persists the user's authentication state. This session is the bridge between the initial authentication event and subsequent requests -- it eliminates the need for re-authentication on every request. LDAP Provider and AI Identity Gateway manage authentication state differently: LDAP Provider maintains per-connection bind state (see the [LDAP Provider reference](/reference/modes/ldap-provider)), and AI Identity Gateway relies on the OAuth token lifecycle (see the [AI Identity Gateway reference](/reference/modes/ai-identity-gateway)). The session stores authentication state, tokens from upstream identity providers, and enriched attributes from attribute providers. All of this data stays server-side. The client receives only an opaque session cookie (the `maverics_session` cookie by default) that identifies the session. Because the cookie carries no sensitive data, session hijacking risks are limited to cookie theft, which is mitigated by the Orchestrator's secure cookie defaults (`HttpOnly`, `Secure`, `SameSite`). On subsequent requests, the Orchestrator checks whether the session cookie maps to a valid, unexpired session. If it does, the user is considered authenticated and the request proceeds without re-authentication. If the session has expired or the cookie is missing, the user is redirected through the full authentication flow. Session lifetime is controlled by two settings: a maximum lifetime (total time since authentication, default 12 hours) and an optional idle timeout (time since last activity, disabled by default). Both can be evaluated dynamically using Service Extensions, enabling context-aware timeout policies -- for example, shorter timeouts for contractors and longer timeouts for employees. For multi-node deployments, each Orchestrator instance maintains its own local session store. To ensure users consistently reach the instance that holds their session, configure cookie-based sticky sessions (session affinity) on your load balancer using the `maverics_session` cookie. For complete session configuration including cookie settings, lifetime controls, and store options, see the [Sessions reference](/reference/orchestrator/sessions). ## Service Extensions in the Auth Lifecycle Service Extensions are Go-based hook functions that customize the Orchestrator's behavior at key points in the authentication and authorization lifecycle. The following hooks are most relevant to authentication: * **`isAuthenticatedSE`** -- Runs a custom check to determine whether the user is already authenticated. Available on OIDC, SAML, and HTTP Proxy apps. Must be paired with `authenticateSE`. * **`authenticateSE`** -- Implements custom authentication logic when standard IdP connector authentication is insufficient. Required for LDAP Provider mode. Must be paired with `isAuthenticatedSE` on OIDC, SAML, and HTTP Proxy apps. * **`isAuthorizedSE`** -- Runs custom authorization logic after authentication succeeds. Available on all app types that support authorization rules. * **`buildClaimsSE`** -- Constructs custom claims for SAML assertions, replacing the declarative `claimsMapping` when more complex logic is needed. * **`buildIDTokenClaimsSE` / `buildAccessTokenClaimsSE`** -- Customize the claims included in OIDC ID tokens and access tokens, respectively. * **`loadAttrsSE`** -- Loads custom attributes from external sources after authentication, supplementing or replacing the declarative `attrProviders` configuration. These hooks provide escape hatches when standard configuration is insufficient. For the full list of 22 hook points and their function signatures, see the [Service Extensions reference](/reference/orchestrator/service-extensions). ## Related Pages Configure the Orchestrator as an OpenID Connect authorization server Configure the Orchestrator as a SAML 2.0 identity provider for federation Protect applications with reverse proxy mode and header injection Virtualize LDAP directories for legacy applications Secure AI agent-to-tool communication with identity and authorization Session stores, cookie configuration, and lifetime controls Custom Go hooks for authentication, authorization, and claims building Authorization rules, OPA policies, and access control patterns # Add SSO to Web Apps Source: https://docs.strata.io/guides/authentication/http-proxy-auth By the end of this guide, you will have a Maverics Orchestrator deployed as an identity-aware reverse proxy -- authenticating users through your identity provider and injecting identity headers into requests to your backend application, with no application code changes required. ## What Is HTTP Proxy Mode? HTTP Proxy authentication places the Maverics Orchestrator between your users and your backend application as a reverse proxy. The Orchestrator intercepts every request, checks whether the user is authenticated, redirects unauthenticated users to your identity provider, and then injects identity information as HTTP headers into the upstream request. Your backend application reads these headers to identify the user -- no changes to the application code or configuration are required. This pattern is especially useful for legacy applications, COTS (commercial off-the-shelf) products, and any application that supports header-based authentication (e.g., SiteMinder-style `SM_USER` headers, `REMOTE_USER`, or custom identity headers). ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed the Orchestrator yet, follow the [Quick Start guide](/guides/getting-started/quick-start) or see the [installation reference](/reference/orchestrator/installation). * **An identity provider account** -- You need credentials for an identity provider that supports OIDC, such as [Microsoft Entra ID](/reference/orchestrator/identity-fabric/azure-ad), [Okta](/reference/orchestrator/identity-fabric/okta), or [Auth0](/reference/orchestrator/identity-fabric/auth0). See the full list of [Identity Fabric](/reference/orchestrator/identity-fabric). * **A target web application** -- A web application accessible via HTTP/HTTPS that you want to protect with modern authentication. The application should accept identity information via HTTP headers. ## Configure HTTP Proxy Mode In the Maverics Console, all configuration lives within a **Deployment** -- a managed Orchestrator instance with its own configuration, storage provider, and signing keys. Before you can create identity connectors and applications, you need a Deployment to hold them. 1. Log in to the [Maverics Console](https://maverics.strata.io). 2. Navigate to **Deployments** in the sidebar and click **Create**. 3. Enter a name for your deployment (e.g., `HTTP Proxy Auth`). 4. Select a deployment provider. The Console supports several options: * **AWS S3**, **Azure Blob Storage**, or **Google Cloud Storage** -- customer-managed cloud storage for production. * **GitHub** or **GitLab** -- deploy bundles to a Git repository. * **Download Only** -- manual bundle download for air-gapped environments. See [Publishing Deployment Configs overview](/reference/console/config-publishing#deployment-providers) for provider setup details. 5. Click **Create**. Your new deployment opens automatically. You can now configure identity connectors and applications within it. When using direct configuration, no deployment setup is needed -- configuration is defined directly in the `maverics.yaml` file and delivered to the Orchestrator via the `-config` flag or `MAVERICS_CONFIG` environment variable. See [Installation](/reference/orchestrator/installation) for details on configuration delivery options. An identity provider (IdP) is the service that manages your user accounts and handles login -- think Microsoft Entra ID (now Microsoft Entra ID), Okta, or Google Workspace. Connecting the Orchestrator to your IdP tells it where to send users when they need to authenticate. The Orchestrator uses [Identity Fabric](/reference/orchestrator/identity-fabric) connectors to communicate with your IdP. This guide demonstrates an OIDC connector, but the connector protocol is independent of the Orchestrator's mode -- even though the Orchestrator is running in HTTP Proxy mode, the IdP connector can use OIDC, SAML, or LDAP. The Orchestrator handles the protocol translation between your IdP and your application. You will need your IdP's client ID, client secret, and discovery URL (the well-known endpoint). These credentials allow the Orchestrator to establish a trust relationship with your provider. 1. Navigate to **Identity Fabric** in the sidebar and click **Create**. 2. Select your identity provider from the list. Choose a provider-specific option (such as **Okta (OIDC)**, **Microsoft Entra ID (OIDC)**, or **Auth0 (OIDC)**) or select **Generic OIDC Configuration** for any OIDC-compliant provider. SAML and LDAP connector options are also available -- this guide demonstrates the OIDC connector path, but any connector type is valid here. 3. Fill in the connector form: | Field | Required | Description | | ---------------------------- | -------- | --------------------------------------------------------------------------------------------------------------------------------- | | Name | Yes | A friendly name for your identity provider (e.g., `my-idp`). | | OIDC Well Known URL | Yes | Your IdP's OIDC discovery endpoint (e.g., `https://your-idp.example.com/.well-known/openid-configuration`). | | OAuth Client ID | Yes | The client ID from the application you registered in your IdP for Maverics. | | Client Authentication Method | Yes | Select **OAuth Client Secret** (default) or **OAuth JWT Client Authentication**. | | OAuth Client Secret | Yes | The client secret from your IdP. For production, use a [secret provider](/reference/orchestrator/configuration/secret-providers). | | Redirect URLs | Yes | The callback URL where your IdP redirects after authentication (e.g., `https://your-orchestrator.example.com/oidc-callback`). | | Scopes | No | Space-separated OIDC scopes (e.g., `openid profile email`). | The **PKCE** toggle is enabled by default. Disable it only if your IdP does not support Proof Key for Code Exchange. 4. Click **Save**. Define an OIDC connector in the `connectors` section of your `maverics.yaml` file. This example uses Microsoft Entra ID, but any OIDC-compatible IdP works the same way. ```yaml maverics.yaml theme={null} connectors: - name: azure type: azure oidcWellKnownURL: https://login.microsoftonline.com/{tenant-id}/v2.0/.well-known/openid-configuration oauthClientID: your-client-id oauthClientSecret: scopes: openid profile email ``` Replace `{tenant-id}` with your Microsoft Entra ID tenant ID. The `oauthClientSecret` uses the `` secret reference syntax -- the Orchestrator retrieves this value at runtime from your [secret provider](/reference/orchestrator/configuration/secret-providers) rather than reading a plaintext value from the config file. Not sure which connector to use? The [Identity Fabric overview](/reference/orchestrator/identity-fabric) includes a comparison table mapping each connector to its supported protocols and use cases. **Protocol translation:** This guide shows an OIDC connector, but the Orchestrator can connect to your IdP using any supported protocol -- OIDC, SAML, or LDAP. The Orchestrator's mode (HTTP Proxy) determines how your *application* receives identity (via headers). The connector determines what protocol your *IdP* speaks. These are independent -- you can connect a SAML-only or LDAP-only IdP and the Orchestrator will translate identity attributes into HTTP headers for your application. See the [Identity Fabric overview](/reference/orchestrator/identity-fabric) for all connector types. Next, create a proxy application entry that tells the Orchestrator which hostname to listen on and where to forward requests. 1. Navigate to **Applications** in the sidebar and click **Create**. 2. Select **Proxy-based**. 3. Fill in the application form: | Field | Required | Description | | -------------- | -------- | ---------------------------------------------------------------------------------------------- | | Name | Yes | A friendly name for your application (e.g., `my-legacy-app`). | | Upstream URL | Yes | The backend URL the Orchestrator forwards requests to (e.g., `https://backend.internal:8080`). | | Route Patterns | Yes | Hostname/path patterns the Orchestrator intercepts (e.g., `myapp.example.com`). | Advanced fields such as TLS profile and **Preserve Host** (which forwards the original `Host` header to the upstream) are available but not required for basic setup. 4. Click **Save**. Define a proxy application in the `apps` section. The `upstream` URL is where the Orchestrator forwards authenticated requests. The `routePatterns` define which hostnames and paths the Orchestrator intercepts. ```yaml maverics.yaml theme={null} apps: - name: my-legacy-app type: proxy upstream: https://backend.internal:8080 routePatterns: - "myapp.example.com" ``` The `upstream` must be reachable from the Orchestrator's network. The `routePatterns` entry tells the Orchestrator to intercept all HTTP requests for `myapp.example.com` and proxy them to `https://backend.internal:8080`. Now bind the identity connector to the proxy application by adding an authentication policy. The policy defines which paths require authentication and which IdP handles it. In the Console, authentication policies are configured on the proxy application itself, within its access control policies. 1. Open your proxy application. In the **Resources** card, click **Edit**, click **Add Resource**, select the connector you created in Step 2, and click **Save**. A connector must be added as a resource before it can be used as an authentication source. 2. Find the **Access Control** card and click **Edit**, then click **Policy** to add an access control policy and set its **Location** to the path you want to protect (e.g., `/`). 3. From the **Select an authentication source** dropdown, select your identity provider -- the connector you added. 4. For **Authorization method**, choose **Allow all access** to permit any authenticated user (you can add rules later). 5. Click **Save**. In the Console, an application's authentication, headers, and policies are configured together on the application. In YAML, these are separate sections within the application configuration block. Add a `policies` section to your proxy application. The `location` defines the URL path to protect, `authentication.idps` references the connector name from Step 2, and `authorization.allowAll` permits all authenticated users. ```yaml maverics.yaml theme={null} apps: - name: my-legacy-app type: proxy upstream: https://backend.internal:8080 routePatterns: - "myapp.example.com" policies: - location: "/" authentication: idps: ["azure"] authorization: allowAll: true ``` The `idps` array references the connector `name` from Step 2 (`azure`). Setting `location: "/"` protects all paths under the root. Setting `allowAll: true` authorizes every authenticated user -- you can add fine-grained authorization rules later. This is where the Orchestrator translates identity into something your application understands. Add headers to inject user attributes from the identity provider into HTTP requests sent to your backend. Header injection is configured within the proxy application's access control policy. 1. Open the application you configured in the previous step, find the **Access Control** card, and click **Edit**. 2. In your policy, find the **Headers** section. 3. Add header mappings: | Field | Description | | ----------------- | -------------------------------------------------------------------------------- | | Header Name | The HTTP header name sent to the upstream (e.g., `SM_USER`, `REMOTE_USER`). | | Identity Source | Select the identity provider connector to pull the attribute from. | | Attribute Mapping | The attribute from the IdP to use as the header value (e.g., `email`, `groups`). | 4. Click **Header** to add additional rows for each header your application expects. 5. Click **Save**. Add a `headers` section to your proxy application. Each entry specifies a header name and a value using the `{{ connector.attribute }}` template syntax. ```yaml maverics.yaml theme={null} apps: - name: my-legacy-app type: proxy upstream: https://backend.internal:8080 routePatterns: - "myapp.example.com" headers: - name: SM_USER value: "{{ azure.email }}" - name: X-Remote-Groups value: "{{ azure.groups }}" policies: - location: "/" authentication: idps: ["azure"] authorization: allowAll: true ``` The template syntax `{{ azure.email }}` pulls the `email` claim from the `azure` connector. The prefix before the dot must match the connector `name` from Step 2. Common header patterns include: | Header Name | Purpose | Example Value | | ----------------- | -------------------------------- | -------------------------------- | | `SM_USER` | SiteMinder-style user identifier | `{{ azure.email }}` | | `REMOTE_USER` | Standard remote user header | `{{ azure.preferred_username }}` | | `X-Remote-User` | Custom user identifier | `{{ azure.email }}` | | `X-Remote-Groups` | Group memberships | `{{ azure.groups }}` | | `X-Remote-Name` | Display name | `{{ azure.name }}` | After configuring your deployment, identity connector, application, and headers in the Console, you need to publish the configuration so the Orchestrator receives it and applies your changes. 1. At the bottom of the deployment Settings page, click **Publish Preview** in the sticky footer bar. 2. In the Deployment Manager dialog, review the configuration diff to verify your changes. 3. Optionally add a revision note describing what changed (e.g., "Initial HTTP Proxy auth setup"). 4. Click **Publish** to deploy the configuration bundle to your storage provider. 5. The Orchestrator detects the new bundle on its next poll cycle and applies the configuration automatically. See [Publishing Deployment Configs overview](/reference/console/config-publishing) for details on the publishing lifecycle, revision history, and bundle verification. When using direct configuration, configuration is delivered directly to the Orchestrator via the `-config` flag or `MAVERICS_CONFIG` environment variable. No publishing step is needed -- restart the Orchestrator to apply configuration changes. With the identity provider connected, proxy application defined, authentication policy applied, and headers configured, you are ready to test the complete authentication flow. Start (or restart) the Orchestrator to pick up your configuration and verify it is healthy: ```bash theme={null} maverics -config /etc/maverics/config.yaml curl -s https://localhost:9443/status | jq . ``` A healthy response confirms the Orchestrator is running: ```json theme={null} { "status": "up" } ``` Now walk through the authentication flow: 1. **Visit the proxy URL** -- Open `https://myapp.example.com` in a browser. You should be redirected to your identity provider's login page. 2. **Authenticate** -- Log in with valid credentials at the IdP. 3. **Verify redirect** -- After authentication, you should land on your backend application with full access. 4. **Verify headers** -- Check that your backend application receives the injected identity headers. If your application has a debug or profile page that displays HTTP headers, verify `SM_USER` and `X-Remote-Groups` contain the expected values. 5. **Check logs** -- Review the Orchestrator logs for authentication events confirming the flow completed successfully. **Success!** Your Maverics Orchestrator is acting as an identity-aware reverse proxy -- authenticating users through your identity provider and injecting identity headers into requests to your backend application. Users experience seamless authentication without any changes to your application code. ## Adding Authorization Rules Once authentication is working, you can add path-specific authorization to restrict access based on user attributes like group membership. ```yaml theme={null} policies: - location: "/admin" authentication: idps: ["azure"] authorization: rules: - and: - contains: ["{{ azure.groups }}", "app-admins"] - location: "/" authentication: idps: ["azure"] authorization: allowAll: true ``` In this example, the `/admin` path requires the user to be a member of the `app-admins` group, while all other paths are accessible to any authenticated user. Policies are evaluated in order -- more specific paths should be listed first. For the full set of authorization operators and rule composition, see the [Security and Policies guide](/guides/security/policies) and the [Authorization reference](/reference/orchestrator/authorization). ## Troubleshooting This usually means the Orchestrator authenticated the user successfully but cannot reach the upstream application. Verify that the `upstream` URL is correct and that the backend is running and accessible from the Orchestrator's network. Check for firewall rules, DNS resolution, or TLS certificate issues between the Orchestrator and the backend. Verify that the `headers` section is defined at the application level (not inside a policy). Check that the connector name in the template syntax matches the `name` field of your connector exactly (e.g., `{{ azure.email }}` requires a connector named `azure`). Review the Orchestrator logs for template evaluation errors. Ensure the `policies` section has a `location` that matches the request path. If `location` is set to a specific path like `/app`, requests to `/` will not trigger authentication. Use `location: "/"` to protect all paths. Also verify that `routePatterns` matches the hostname the user is accessing. ## Related Pages Complete configuration reference for HTTP Proxy mode -- route patterns, upstreams, headers, and policies Authorization rules, operators, and policy composition for fine-grained access control All supported identity providers and connector configuration Session storage options and cookie configuration for proxy authentication # Migrate Between Identity Providers Source: https://docs.strata.io/guides/authentication/idp-migration By the end of this guide, you will have a Maverics deployment that seamlessly routes authentication between your old and new identity providers -- migrating users with zero downtime and no application changes. ## Why Migrate Identity Providers? Identity provider migration is one of the most common -- and most stressful -- projects in enterprise IAM. Organizations outgrow their current IdP, acquire companies running different providers, consolidate after mergers, or switch to a provider with better pricing or features. Whatever the reason, the migration usually affects every user and every application in the organization. The traditional approach is painful: reconfigure every application to trust the new IdP, migrate all user accounts, coordinate a cutover date, and hope nothing breaks. With the Maverics Orchestrator, migration becomes gradual and reversible. The Orchestrator sits between your applications and both identity providers, routing authentication to whichever IdP is appropriate for each user -- so you can migrate users in batches, roll back instantly if something goes wrong, and keep every application running throughout the process. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed the Orchestrator yet, follow the [Quick Start guide](/guides/getting-started/quick-start) or see the [installation reference](/reference/orchestrator/installation). * **Source identity provider connector configured** -- Your Orchestrator should already be connected to your current (source) IdP. The [SSO with OIDC guide](/guides/authentication/sso-with-oidc) covers connector setup. * **Target identity provider account** -- You need credentials and access to the new IdP you are migrating to (for example, moving from [ADFS](/reference/orchestrator/identity-fabric/adfs) to [Microsoft Entra ID](/reference/orchestrator/identity-fabric/azure-ad), or from [Okta](/reference/orchestrator/identity-fabric/okta) to [Auth0](/reference/orchestrator/identity-fabric/auth0)). ## Configure the Migration The first step is connecting the Orchestrator to both your source (current) and target (new) identity providers. Each provider gets its own [Identity Fabric](/reference/orchestrator/identity-fabric) with independent credentials and configuration. If you already have a connector configured for your source IdP (from your existing Maverics deployment), you only need to add the new target connector. The Orchestrator can maintain active connections to both providers simultaneously -- users authenticating against either provider will have a seamless experience. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Maverics Console showing two identity provider connectors configured side by side -- source and target Define both connectors in the `connectors` section of your `maverics.yaml` file. Each connector has its own credentials and discovery endpoint. ```yaml maverics.yaml theme={null} connectors: - name: source-idp type: oidc oidcWellKnownURL: https://source-idp.example.com/.well-known/openid-configuration oauthClientID: orchestrator-source-client oauthClientSecret: oauthLoginRedirect: urls: - https://your-orchestrator.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-orchestrator.example.com/logout scopes: openid profile email - name: target-idp type: oidc oidcWellKnownURL: https://target-idp.example.com/.well-known/openid-configuration oauthClientID: orchestrator-target-client oauthClientSecret: oauthLoginRedirect: urls: - https://your-orchestrator.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-orchestrator.example.com/logout scopes: openid profile email ``` Both connectors can use the same redirect URLs -- the Orchestrator routes callbacks to the correct connector based on the session state. Name your connectors clearly (e.g., `source-idp` and `target-idp`) to avoid confusion during migration. Name your connectors clearly to distinguish between source and target -- for example, `okta-source` and `azure-ad-target`. Clear naming prevents configuration mistakes during migration when you are referencing connectors in policies. The [Continuity connector](/reference/orchestrator/identity-fabric/continuity) is what makes zero-downtime migration possible. It acts as a smart router between your two identity providers -- directing each authentication request to the right IdP based on your migration policies. The Continuity connector wraps both of your IdP connectors and adds failover logic. If a user has already been migrated to the new IdP, their authentication is routed there. If they have not been migrated yet, authentication goes to the source IdP. If either provider is temporarily unavailable, the Continuity connector can fail over to the other -- keeping authentication working even during provider outages. Think of it as a load balancer for identity -- but instead of distributing traffic for performance, it routes authentication based on migration state and availability. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Continuity connector configuration screen in Maverics Console showing source and target IdP routing Add a Continuity connector that references both IdP connectors. The `failover.idps` array lists connectors in priority order -- the first entry is tried first, and subsequent entries serve as fallbacks. ```yaml maverics.yaml theme={null} connectors: - name: source-idp type: oidc oidcWellKnownURL: https://source-idp.example.com/.well-known/openid-configuration oauthClientID: orchestrator-source-client oauthClientSecret: oauthLoginRedirect: urls: - https://your-orchestrator.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-orchestrator.example.com/logout scopes: openid profile email - name: target-idp type: oidc oidcWellKnownURL: https://target-idp.example.com/.well-known/openid-configuration oauthClientID: orchestrator-target-client oauthClientSecret: oauthLoginRedirect: urls: - https://your-orchestrator.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-orchestrator.example.com/logout scopes: openid profile email - name: migration-connector type: continuity strategy: failover failover: idps: - target-idp - source-idp attributes: - name: email mapping: target-idp: email source-idp: email - name: name mapping: target-idp: name source-idp: name ``` The Continuity connector lists `target-idp` first so the Orchestrator tries the new provider first. If the target IdP is unavailable or the user has not been migrated, it falls back to `source-idp`. The `attributes` section normalizes attribute names across providers. Even if both IdPs use the same attribute names, explicitly mapping them ensures consistent behavior regardless of which IdP handles the authentication. See [Continuity Connector Reference](/reference/orchestrator/identity-fabric/continuity) for all available fields. Update your application configurations to use the Continuity connector instead of pointing directly at a single IdP. This is the key change that enables failover -- your applications reference the Continuity connector, and the connector handles routing to the appropriate IdP. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Application configuration screen in Maverics Console showing Continuity connector selection Update the `authentication.idps` array in your application definitions to reference the Continuity connector name instead of a specific IdP connector. ```yaml maverics.yaml theme={null} apps: - name: my-web-app type: oidc clientID: my-web-app credentials: secrets: - redirectURLs: - https://your-app.example.com/callback authentication: idps: - migration-connector accessToken: type: jwt claimsMapping: email: migration-connector.email name: migration-connector.name ``` The `authentication.idps` now references `migration-connector` (the Continuity connector) instead of a specific IdP. The `claimsMapping` also references the Continuity connector's normalized attribute names -- not the individual IdP connectors. This ensures your application receives consistent claims regardless of which IdP authenticated the user. Always start with a small group or low percentage and monitor before expanding. IdP migrations affect every user's ability to log in -- a cautious rollout lets you catch configuration issues before they impact the entire organization. With both connectors active and the Continuity connector routing authentication, the Orchestrator begins routing authentication according to your failover configuration. Monitor the migration to ensure users are authenticating successfully against the target IdP. Key things to watch during migration: * **Authentication success rates** -- Compare success rates between source and target IdPs. A drop in the target IdP's success rate may indicate configuration issues. * **User complaints** -- Users who experience login problems are likely hitting the target IdP with misconfigured attributes or missing accounts. * **Session behavior** -- Verify that sessions created by the target IdP work correctly with all your applications. As confidence grows, you can adjust the Continuity connector's failover order. When all users are successfully authenticating against the new provider, remove the source connector from the `failover.idps` list. Eventually, you can remove the Continuity connector entirely and point applications directly at the target IdP. ```bash theme={null} # Check Orchestrator health and connector status during migration curl -s https://localhost:9443/status | jq . ``` **Success!** Your Maverics Orchestrator is seamlessly routing authentication between both identity providers. Users are being migrated gradually with zero downtime -- and your applications required no changes at all. When the migration is complete, remove the Continuity connector and source IdP configuration to clean up. ## Troubleshooting Check your Continuity connector's `failover.idps` order to verify the routing logic is correct. The first connector in the list is always tried first. If a user who should be on the new IdP is still authenticating against the source, the target IdP may be rejecting the user (causing failover to the source). Use the Orchestrator logs to trace which connector handled a specific authentication request -- the logs show the connector name and the failover path that was followed. Also verify that the user's account exists in the target IdP with the correct attributes. If a user has an active session from the source IdP and then gets routed to the target IdP on their next login, they may see unexpected behavior -- such as being asked to re-authenticate or losing session data. This happens when session identifiers differ between the two providers. Configure the Orchestrator to invalidate existing sessions when a user's IdP routing changes, or set session timeouts short enough that users naturally cycle through during the migration window. See the [Sessions reference](/reference/orchestrator/sessions) for session management options. The Orchestrator supports instant rollback -- update your Continuity connector's `failover.idps` order to list the source IdP first. Because the Orchestrator re-reads configuration changes, the updated failover order takes effect on the next authentication request. After rolling back, investigate the issue, fix the target IdP configuration, and resume the gradual rollout by restoring the target IdP to first position. ## Related Pages Return to the Authentication guides hub for SSO, SAML, and other authentication workflows Supported identity providers and connector configuration for Microsoft Entra ID, Okta, Auth0, and more Complete configuration reference for the Continuity connector -- failover, routing, and migration settings # Modernize LDAP Authentication Source: https://docs.strata.io/guides/authentication/ldap-provider By the end of this guide, you will have a Maverics Orchestrator configured as a virtual LDAP directory -- authenticating LDAP bind requests against a modern cloud identity provider and returning directory data to LDAP-dependent applications, without changing the application's LDAP configuration. ## What Is LDAP Provider Mode? Many enterprise applications -- especially legacy and commercial off-the-shelf (COTS) products -- depend on LDAP for authentication and directory lookups. These applications perform LDAP bind operations to validate user credentials and LDAP search operations to retrieve user attributes like group memberships, email addresses, and display names. The Maverics Orchestrator's LDAP Provider mode creates a virtual LDAP directory that presents a standard LDAP interface to these applications while sourcing identity data from modern cloud identity providers such as Microsoft Entra ID, Okta, or PingFederate. Applications continue using their existing LDAP configuration -- the Orchestrator handles the translation between LDAP protocol operations and cloud IdP APIs. The most common deployment pattern pairs LDAP Provider with [HTTP Proxy](/guides/authentication/http-proxy-auth) mode in a **facade** architecture, where the Orchestrator handles both the browser-facing authentication (via HTTP Proxy) and the application's backend LDAP operations (via LDAP Provider). See Step 6 for details on this pattern. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed the Orchestrator yet, follow the [Quick Start guide](/guides/getting-started/quick-start) or see the [installation reference](/reference/orchestrator/installation). * **An identity provider account** -- You need credentials for an identity provider such as [Microsoft Entra ID](/reference/orchestrator/identity-fabric/azure-ad), [Okta](/reference/orchestrator/identity-fabric/okta), or [PingFederate](/reference/orchestrator/identity-fabric/pingone). This IdP will serve as the upstream source of identity data that the Orchestrator translates into LDAP responses. * **A target LDAP-dependent application** -- An application that authenticates users via LDAP bind operations or retrieves user attributes via LDAP search queries. * **Service Extension development capability (Go)** -- Unlike other Orchestrator modes, the LDAP Provider **requires** Go-based Service Extensions for its core operations. There is no declarative-only configuration path. You will need to write Service Extensions that handle LDAP bind authentication and search queries. See [Service Extensions reference](/reference/orchestrator/service-extensions). * **Knowledge of your application's LDAP expectations** -- You must know the bind DN format your application uses, the search base DN, and the LDAP attributes it expects in search results (e.g., `cn`, `sAMAccountName`, `memberOf`). **Service Extensions are required.** Every LDAP Provider integration requires Go-based Service Extensions to handle LDAP operations (bind authentication, search queries, credential lookups). The LDAP Provider cannot function without them. Plan for Service Extension development as part of your integration timeline. ## Configure LDAP Provider Mode In the Maverics Console, all configuration lives within a **Deployment** -- a managed Orchestrator instance with its own configuration, storage provider, and signing keys. Before you can configure the LDAP Provider, you need a Deployment to hold the configuration. 1. Log in to the [Maverics Console](https://maverics.strata.io). 2. Navigate to **Deployments** in the sidebar and click **Create**. 3. Enter a name for your deployment (e.g., `LDAP Provider`). 4. Select a deployment provider. The Console supports several options: * **AWS S3**, **Azure Blob Storage**, or **Google Cloud Storage** -- customer-managed cloud storage for production. * **GitHub** or **GitLab** -- deploy bundles to a Git repository. * **Download Only** -- manual bundle download for air-gapped environments. See [Publishing Deployment Configs overview](/reference/console/config-publishing#deployment-providers) for provider setup details. 5. Click **Create**. Your new deployment opens automatically. You can now configure the LDAP Provider, identity connectors, and Service Extensions within it. When using direct configuration, no deployment setup is needed -- configuration is defined directly in the `maverics.yaml` file and delivered to the Orchestrator via the `-config` flag or `MAVERICS_CONFIG` environment variable. See [Installation](/reference/orchestrator/installation) for details on configuration delivery options. The LDAP Provider must be enabled and configured at the deployment level. This sets up the virtual LDAP directory server that LDAP-dependent applications will connect to. 1. Open your deployment and click the **gear icon** in the sidebar to open **Deployment Settings**. 2. Find the **LDAP Provider** section. 3. Toggle **Enable** to on. 4. Select the **Protocol**: `ldap://` (unencrypted) or `ldaps://` (TLS-encrypted). Use `ldaps://` for production deployments. 5. Set the **URI** -- the address and port the LDAP Provider listens on (e.g., `ldaps://0.0.0.0:636` for TLS on the standard LDAPS port, or `ldap://0.0.0.0:389` for unencrypted). 6. If using `ldaps://`, provide the **TLS Certificate** file path and **TLS Key File** path. 7. Click **Save**. The LDAP Provider Deployment Settings fields are documented in detail in the [LDAP Provider reference](/reference/modes/ldap-provider#setup). Use the Console UI tab there for field-by-field descriptions. Enable the LDAP Provider in your `maverics.yaml` file. The `ldapProvider` top-level key configures the virtual directory server. ```yaml maverics.yaml theme={null} tls: ldap-server-tls: certFile: /etc/maverics/certs/ldap-server.pem keyFile: /etc/maverics/certs/ldap-server-key.pem ldapProvider: enabled: true uri: ldaps://0.0.0.0:636 tls: ldap-server-tls readDeadline: 5m writeDeadline: 5m rootDSE: attributes: namingContexts: - dc=example,dc=com ``` The `uri` sets the listen address. Use `ldaps://` with a named TLS profile for production. The `rootDSE.attributes.namingContexts` should match the base DN that your LDAP-dependent application expects when it discovers the directory's capabilities. See [LDAP Provider Reference](/reference/modes/ldap-provider) for all available fields, including advanced Root DSE configuration. An identity provider (IdP) is the service that manages your user accounts -- Microsoft Entra ID, Okta, Google Workspace, or an on-premises directory. Connecting the Orchestrator to your IdP tells it where to source identity data for LDAP responses. The Orchestrator uses [Identity Fabric](/reference/orchestrator/identity-fabric) connectors to communicate with your IdP. The connector provides the upstream identity data that your Service Extensions (configured in the next steps) will translate into LDAP responses. You will need your IdP's client ID, client secret, and discovery URL. These credentials allow the Orchestrator to query the IdP for user authentication and attribute data. 1. Navigate to **Identity Fabric** in the sidebar and click **Create**. 2. Select your identity provider from the list. Choose a provider-specific option (such as **Okta (OIDC)**, **Microsoft Entra ID (OIDC)**, or **Auth0 (OIDC)**) or select **Generic OIDC Configuration** for any OIDC-compliant provider. SAML and LDAP connector options are also available. 3. Fill in the connector form: | Field | Required | Description | | ---------------------------- | -------- | --------------------------------------------------------------------------------------------------------------------------------- | | Name | Yes | A friendly name for your identity provider (e.g., `upstream-idp`). | | OIDC Well Known URL | Yes | Your IdP's OIDC discovery endpoint (e.g., `https://your-idp.example.com/.well-known/openid-configuration`). | | OAuth Client ID | Yes | The client ID from the application you registered in your IdP for Maverics. | | Client Authentication Method | Yes | Select **OAuth Client Secret** (default) or **OAuth JWT Client Authentication**. | | OAuth Client Secret | Yes | The client secret from your IdP. For production, use a [secret provider](/reference/orchestrator/configuration/secret-providers). | | Redirect URLs | Yes | The callback URL where your IdP redirects after authentication. | | Scopes | No | Space-separated OIDC scopes (e.g., `openid profile email`). | 4. Click **Save**. Define a connector in the `connectors` section of your `maverics.yaml` file. The connector specifies how the Orchestrator communicates with your identity provider to retrieve user data. ```yaml maverics.yaml theme={null} connectors: - name: upstream-idp type: oidc oidcWellKnownURL: https://your-idp.example.com/.well-known/openid-configuration oauthClientID: ldap-bridge oauthClientSecret: ``` Replace `your-idp.example.com` with your identity provider's domain. The `oauthClientSecret` uses the `` secret reference syntax -- the Orchestrator retrieves this value at runtime from your [secret provider](/reference/orchestrator/configuration/secret-providers). Not sure which connector to use? The [Identity Fabric overview](/reference/orchestrator/identity-fabric) includes a comparison table mapping each connector to its supported protocols and use cases. **Protocol translation:** The Orchestrator's mode (LDAP Provider) determines what protocol your *application* speaks. The connector determines what protocol your *IdP* speaks. These are independent -- you can connect an OIDC-only or SAML-only IdP and the Orchestrator (through your Service Extensions) will translate identity data into LDAP responses for your application. See the [Identity Fabric overview](/reference/orchestrator/identity-fabric) for all connector types. The authentication Service Extension handles LDAP bind operations. When an LDAP-dependent application sends a bind request (DN + password), this Service Extension validates the credentials against your upstream identity provider and returns success or failure. This step is **unique to the LDAP Provider** -- other Orchestrator modes handle authentication declaratively. The LDAP Provider requires a Go Service Extension because LDAP bind semantics vary widely across applications, and the translation from LDAP bind to cloud IdP authentication (typically via OIDC Resource Owner Password Credentials grant or a direct API call) requires custom logic. Your authentication Service Extension should: 1. Receive the bind DN and password from the LDAP client 2. Parse the bind DN to extract the username or identifier 3. Translate the credentials into an authentication request against the upstream IdP (e.g., ROPC grant, SCIM API, or direct API call) 4. Return success or failure to the LDAP client See the [Service Extensions reference](/reference/orchestrator/service-extensions) for the function signature, available context objects, and build instructions. **Illustrative example only.** The following Service Extension is a simplified test example with hardcoded credentials. A production implementation would validate credentials against your upstream identity provider (e.g., via ROPC grant or direct API call) and retrieve user data from `api.Session()` or `api.Cache()`. See the [Service Extensions reference](/reference/orchestrator/service-extensions) for production patterns. ```go simple.go theme={null} import ( "strings" "github.com/strata-io/service-extension/orchestrator" ) // This is an example Simple Authentication Service Extension that shows a quick way // to test a Bind request using the Simple Authentication method between the // application and the Orchestrator. In this example, only a user with the username // of `bob` and the password of `th3Bu!ld3R` to be authenticated. // // A production version of this Service Extension would typically retrieve the // password hash of the user from either `api.Cache` or `api.Session` and would // compute the hash of the password received and compare it with the one stored. The // user is typically a short-lived / one-time user created by an Orchestrator serving // as the identity-aware proxy, after the end-user has been authenticated by // the configured IdP. func Authenticate(api orchestrator.Orchestrator, username string, password string) (bool, error) { api.Logger().Debug( "service", "LDAP Provider", "extension", "Authenticate", "msg", "authenticating user", "username", username, ) if strings.EqualFold(username, "bob") && password == "th3Bu!ld3R" { api.Logger().Debug( "service", "LDAP Provider", "extension", "Authenticate", "msg", "user authenticated", "username", username, ) return true, nil } api.Logger().Debug( "service", "LDAP Provider", "extension", "Authenticate", "msg", "user not authenticated", "username", username, ) return false, nil } ``` 1. Open your deployment and click the **gear icon** to open **Deployment Settings**. 2. In the **LDAP Provider** section, find the **Authentication** area. 3. Toggle **Enable Simple Auth** to on. 4. Under **Authentication Service Extension**, select your compiled Service Extension from the dropdown. 5. Click **Save**. Configure the authentication Service Extension in the `ldapProvider.authentication` section. ```yaml maverics.yaml theme={null} ldapProvider: enabled: true uri: ldaps://0.0.0.0:636 tls: ldap-server-tls authentication: allowAnonymous: false methods: simple: enabled: true authenticateSE: file: /etc/maverics/extensions/authenticate.go funcName: Authenticate ``` The `authenticateSE.file` points to the Go source file containing your authentication logic. The `authenticateSE.funcName` specifies the entry point function that the Orchestrator calls when it receives a bind request. The search Service Extension handles LDAP search operations. When an LDAP-dependent application sends a search request (base DN, scope, filter, requested attributes), this Service Extension translates the query into lookups against your upstream identity sources and returns matching entries in LDAP format. Your search Service Extension should: 1. Receive the search parameters (base DN, scope, filter, requested attributes) from the LDAP client 2. Parse the LDAP filter to determine what the application is looking for 3. Query the upstream identity source (cloud IdP API, database, etc.) for matching users or groups 4. Map the upstream attributes into the LDAP attribute names the application expects (e.g., `cn`, `sAMAccountName`, `memberOf`, `mail`) 5. Return the matching entries in LDAP format See the [Service Extensions reference](/reference/orchestrator/service-extensions) for the function signature, available context objects, and build instructions. **Illustrative example only.** The following Service Extension returns hardcoded attributes for a test user. A production implementation would query your upstream identity provider or attribute source for real user data, typically via `api.Session()`, `api.Cache()`, or `api.AttributeProvider()`. See the [Service Extensions reference](/reference/orchestrator/service-extensions) for production patterns. ```go search.go theme={null} import ( "strings" "github.com/strata-io/service-extension/ldap" "github.com/strata-io/service-extension/orchestrator" ) // This is an example of an Search Service Extension and shows a simple way to verify // the LDAP connection between the application and the Orchestrator. It is configured // to return hard-coded attributes for a test user, regardless of the Search request // received. // // A production version will be dependant on the application and environment; however, // typically, attributes originate from the end-users Session and would NOT be // hardcoded. For example, if the policy requires a user to be authenticated // using Entra ID, then the attributes would likely come from Entra ID, and stored // on the cache via the Orchestrator servicing as the proxy for the application. func Search(api orchestrator.Orchestrator, dn string, filter string, reqAttrs []string) (map[string]map[string]interface{}, error) { api.Logger().Debug( "service", "LDAP Provider", "extension", "Search", "msg", "processing request", "user", ldap.BindDN(api.Context()), "dn", dn, "filter", filter, "attributes", strings.Join(reqAttrs, ","), ) result := make(map[string]map[string]interface{}) // User attributes would typically originate from the users Session and would NOT // be hardcoded. For example, if the policy requires a user to be authenticated // using Entra ID, then the attributes would likely come from Entra ID. userAttrs := make(map[string]interface{}) userAttrs["Name"] = "Test User" userAttrs["mail"] = "test.user@acme.org" userAttrs["givenName"] = "Test" userAttrs["sn"] = "User" result["CN=Test,CN=Domain Users,CN=Users,DC=acme,DC=local"] = userAttrs api.Logger().Debug( "service", "LDAP Provider", "extension", "Search", "msg", "request processed", "dn", dn, "filter", filter, "attributes", strings.Join(reqAttrs, ","), ) return result, nil } ``` 1. Open your deployment and click the **gear icon** to open **Deployment Settings**. 2. In the **LDAP Provider** section, find the **Search** area. 3. Under **Search Service Extension**, select your compiled Service Extension from the dropdown. 4. Click **Save**. Configure the search Service Extension in the `ldapProvider.search` section. ```yaml maverics.yaml theme={null} ldapProvider: enabled: true uri: ldaps://0.0.0.0:636 tls: ldap-server-tls search: searchSE: file: /etc/maverics/extensions/search.go funcName: Search ``` The `searchSE.file` points to the Go source file containing your search logic. The `searchSE.funcName` specifies the entry point function that the Orchestrator calls when it receives a search request. The most common LDAP Provider deployment pairs it with [HTTP Proxy](/reference/modes/http-proxy) mode in a **facade** (or "sandwich") pattern. In this architecture, the application sits between two Orchestrator roles: * **HTTP Proxy** handles browser-facing authentication -- intercepting HTTP requests, redirecting users to a cloud IdP for modern authentication (MFA, conditional access), and injecting identity headers or stuffing login forms * **LDAP Provider** handles the application's backend LDAP operations -- authenticating bind requests and serving search results from the same cloud IdP This pattern lets you modernize the full authentication stack for LDAP-dependent applications without changing any application code. **To set up the facade pattern:** 1. **Configure an HTTP Proxy application** for the web tier -- follow the [HTTP Proxy Auth guide](/guides/authentication/http-proxy-auth) to set up reverse proxy authentication with header injection or form-stuffing. 2. **Configure the LDAP Provider** (this guide) for the backend tier -- the same Orchestrator instance or a separate one handles the application's LDAP bind and search requests. 3. **Add a shared cache** if running separate Orchestrator instances -- when the HTTP Proxy and LDAP Provider run as separate Orchestrator instances (the most common facade deployment), they need a [shared cache](/reference/orchestrator/caches) so that one-time credentials generated by the proxy Orchestrator can be validated by the LDAP Provider Orchestrator. The facade can be deployed as a single Orchestrator running both HTTP Proxy and LDAP Provider modes, two separate Orchestrator instances, or groups of Orchestrators for high-availability deployments. When both modes run on a single Orchestrator instance, the local in-memory cache is sufficient. See the [LDAP Provider reference -- Pairing with HTTP Proxy](/reference/modes/ldap-provider#pairing-with-http-proxy) for the complete architecture diagram, credential delivery methods, and shared cache requirements. With the LDAP Provider enabled, identity connector configured, and Service Extensions in place, you are ready to publish and test the virtual LDAP directory. 1. At the bottom of the deployment Settings page, click **Publish Preview** in the sticky footer bar. 2. In the Deployment Manager dialog, review the configuration diff to verify your changes. 3. Optionally add a revision note describing what changed (e.g., "Initial LDAP Provider setup"). 4. Click **Publish** to deploy the configuration bundle to your storage provider. 5. The Orchestrator detects the new bundle on its next poll cycle and applies the configuration automatically. See [Publishing Deployment Configs overview](/reference/console/config-publishing) for details on the publishing lifecycle, revision history, and bundle verification. When using direct configuration, start (or restart) the Orchestrator to apply your changes: ```bash theme={null} maverics -config /etc/maverics/config.yaml ``` **Test the LDAP connection:** Point your LDAP client application at the Orchestrator's LDAP endpoint and verify the full flow: 1. **Test connectivity** -- Use an LDAP client tool (such as `ldapsearch` or Apache Directory Studio) to connect to the Orchestrator's LDAP URI and verify the connection is accepted. ```bash theme={null} ldapsearch -H ldaps://your-orchestrator.example.com:636 -x -b "dc=example,dc=com" -s base "(objectClass=*)" ``` 2. **Test bind authentication** -- Attempt a bind operation with valid credentials to verify the authentication Service Extension is working. ```bash theme={null} ldapsearch -H ldaps://your-orchestrator.example.com:636 -x -D "cn=user@example.com,dc=example,dc=com" -W -b "dc=example,dc=com" "(cn=user@example.com)" ``` 3. **Test search** -- After a successful bind, perform a search to verify the search Service Extension returns the expected attributes. 4. **Test with your application** -- Point your LDAP-dependent application at the Orchestrator's LDAP endpoint and walk through a full authentication and data retrieval flow. **Success!** Your Maverics Orchestrator is acting as a virtual LDAP directory -- authenticating LDAP bind requests against your cloud identity provider and serving directory data to your LDAP-dependent application. The application continues using its existing LDAP configuration while the actual identity data comes from your modern cloud IdP. ## What's Next Complete configuration reference for LDAP Provider mode -- authentication methods, search handling, and Root DSE Deploy the Orchestrator as a reverse proxy -- pair with LDAP Provider for the facade pattern Write Go-based Service Extensions for custom authentication, search, and credential handling logic Connect upstream identity providers to the Orchestrator -- Microsoft Entra ID, Okta, PingFederate, and more # Overview Source: https://docs.strata.io/guides/authentication/overview The Authentication guides walk you through configuring single sign-on and federation with the Maverics Orchestrator. Start with [How Authentication Works](/guides/authentication/how-auth-works) for a conceptual overview of the authentication pipeline, then use [Choosing a Mode](/guides/authentication/choosing-a-mode) to pick the right Orchestrator mode for your applications. The step-by-step guides below walk you through configuration for each protocol. ## Understand Authentication Understand the shared authentication pipeline across all 5 Orchestrator modes -- from request interception through session establishment Compare OIDC Provider, SAML Provider, HTTP Proxy, LDAP Provider, and AI Identity Gateway side-by-side to pick the right mode ## Step-by-Step Guides Configure the Orchestrator as an OIDC Provider -- connect your identity provider, define an OIDC app, map claims, and issue tokens to your application Federate enterprise SAML applications through the Orchestrator as a SAML Provider -- configure connectors, register relying parties, and map assertion attributes Deploy the Orchestrator as an identity-aware reverse proxy -- protect legacy applications with header-based authentication, no code changes required Configure the Orchestrator as a virtual LDAP directory -- authenticate LDAP-dependent applications against modern cloud identity providers Configure Single Logout to log out of all authenticated identity providers and terminate the Maverics session in one action Migrate between identity providers with zero downtime -- configure dual connectors with Continuity-based failover and attribute normalization ## Related Pages Complete configuration reference for the Orchestrator's OIDC Provider mode -- claims, scopes, and token settings Supported identity providers and connector configuration for Microsoft Entra ID, Okta, Auth0, and more Rule-based access control with enforcement behavior, per-mode differences, and real-world patterns Session management, lifetime configuration, and how sessions integrate with authentication Secure AI agent access to APIs and MCP tools with identity, authorization, and audit Set up automatic IdP failover with health monitoring, Schema Abstraction Layer, and simulation testing # Federate SAML Apps Source: https://docs.strata.io/guides/authentication/saml-federation By the end of this guide, you will have a Maverics Orchestrator acting as a SAML Provider -- federating authentication between your identity provider and SAML-based enterprise applications. ## What Is SAML? SAML (Security Assertion Markup Language) is an XML-based authentication protocol that has been the standard for enterprise single sign-on for over two decades. Many enterprise applications -- especially older ones built before OIDC existed -- only support SAML for federated authentication. SAML works by exchanging signed XML documents (called assertions) between an identity provider (IdP) and a service provider (SP) to prove a user's identity. The Maverics Orchestrator can act as a SAML Provider, receiving assertions from your identity provider and translating them into authenticated sessions for your applications. This means your applications do not need to implement SAML directly -- the Orchestrator handles the protocol complexity for them. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed the Orchestrator yet, follow the [Quick Start guide](/guides/getting-started/quick-start) or see the [installation reference](/reference/orchestrator/installation). * **An identity provider account** -- While this guide demonstrates a SAML connector, the Orchestrator can connect to your IdP over OIDC, SAML, or LDAP. Your IdP does not need to support SAML specifically. Common IdPs include [Microsoft Entra ID](/reference/orchestrator/identity-fabric/azure-ad), [Okta](/reference/orchestrator/identity-fabric/okta), and [PingFederate](/reference/orchestrator/identity-fabric/pingone). * **A target SAML application** -- An enterprise application that authenticates users via SAML assertions. Common examples include legacy portals, HR systems, and internal tools that were built for SAML-based SSO. ## Configure SAML Federation In the Maverics Console, all configuration lives within a **Deployment** -- a managed Orchestrator instance with its own configuration, storage provider, and signing keys. Before you can create identity connectors and applications, you need a Deployment to hold them. 1. Log in to the [Maverics Console](https://maverics.strata.io). 2. Navigate to **Deployments** in the sidebar and click **Create**. 3. Enter a name for your deployment (e.g., `SAML Federation`). 4. Select a deployment provider. The Console supports several options: * **AWS S3**, **Azure Blob Storage**, or **Google Cloud Storage** -- customer-managed cloud storage for production. * **GitHub** or **GitLab** -- deploy bundles to a Git repository. * **Download Only** -- manual bundle download for air-gapped environments. See [Publishing Deployment Configs overview](/reference/console/config-publishing#deployment-providers) for provider setup details. 5. Click **Create**. Your new deployment opens automatically. You can now configure identity connectors and applications within it. When using direct configuration, no deployment setup is needed -- configuration is defined directly in the `maverics.yaml` file and delivered to the Orchestrator via the `-config` flag or `MAVERICS_CONFIG` environment variable. See [Installation](/reference/orchestrator/installation) for details on configuration delivery options. The SAML Provider must be enabled and configured at the deployment level before creating connectors or applications. This configures the Orchestrator to act as a SAML identity provider to your downstream applications -- issuing signed SAML assertions after authenticating users through your upstream IdP connector. The SAML Provider requires signing credentials (a certificate and private key) that the Orchestrator uses to sign assertions. Your downstream applications validate these signatures to ensure assertions came from a trusted source. In the Maverics Console, SAML Provider settings are configured through the **Deployment Settings** dialog. 1. Click the **gear icon** in the sidebar to open **Deployment Settings**. 2. Find the **SAML Provider** section and configure the provider-level settings. The SAML Provider Deployment Settings fields (Issuer, endpoints, signing options, certificates, and Redis cache) are documented in the [SAML Provider reference](/reference/modes/saml-provider#setup). Use the Console UI tab there for field-by-field details. The key settings to configure are the **Issuer** (your Orchestrator's Entity ID) and the **Signing Option** (which parts of the SAML response to sign). Click **Generate** after entering the Issuer to auto-populate the Metadata, Single Sign-on, and Single Logout endpoint URLs. If signing credentials (certificate and private key) are left blank, the Orchestrator auto-generates a self-signed certificate at startup. This certificate is **ephemeral** -- it is regenerated on every restart, which means all previously issued assertions become unverifiable by service providers. For production, always configure explicit signing credentials. Use the `` [secret provider](/guides/security/secrets-management) syntax to store certificates and private keys securely rather than in plaintext configuration. Define the `samlProvider` section in your `maverics.yaml` file. This configures the Orchestrator's SAML issuer identity and signing credentials. ```yaml maverics.yaml theme={null} samlProvider: issuer: https://your-orchestrator.example.com endpoints: metadata: https://your-orchestrator.example.com/saml/metadata singleSignOnService: https://your-orchestrator.example.com/saml/sso singleLogoutService: https://your-orchestrator.example.com/saml/slo signature: certificate: privateKey: ``` The `signature.certificate` and `signature.privateKey` use secret references -- the Orchestrator retrieves these from your [secret provider](/reference/orchestrator/configuration/secret-providers) at runtime. The certificate is included in the SAML metadata so downstream applications can validate assertion signatures. See [SAML Provider Reference](/reference/modes/saml-provider) for all available fields. Next, connect the Orchestrator to your identity provider as a SAML identity source. This tells the Orchestrator where to send users for authentication and how to validate the signed assertions it receives back. SAML supports two authentication flows, and it helps to understand the difference: * **SP-initiated** -- The user visits your application first. The Orchestrator (acting as the Service Provider) redirects the user to the identity provider for authentication, and the IdP sends the user back with a SAML assertion. This is the most common flow. * **IdP-initiated** -- The user logs into the identity provider first (through a portal or dashboard) and then navigates to the application. The IdP sends a SAML assertion directly to the Orchestrator without a prior authentication request. The Orchestrator supports both flows. You will need your IdP's SAML metadata URL (or metadata XML file), which contains the IdP's signing certificate, SSO endpoint URLs, and entity ID. 1. Navigate to **Identity Fabric** in the sidebar and click **Create**. 2. Select your identity provider from the list. Choose a provider-specific SAML option (such as **Okta (SAML)** or **Microsoft Entra ID (SAML)**) or select **Generic SAML** for any SAML-compliant provider. OIDC and LDAP connector options are also available -- this guide demonstrates the SAML connector path, but any connector type is valid here. 3. Fill in the connector form: | Field | Required | Description | | -------------------------- | -------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | Name | Yes | A friendly name for your identity provider (e.g., `my-saml-idp`). | | Metadata URL | Yes | Your IdP's SAML metadata URL (e.g., `https://your-idp.example.com/saml/metadata`). The Orchestrator fetches signing certificates and endpoints from this URL automatically. | | Consumer Service (ACS) URL | Yes | The Assertion Consumer Service URL where your IdP sends SAML responses after authentication (e.g., `https://your-orchestrator.example.com/saml/acs`). | | Entity ID | Yes | The unique identifier for the Service Provider (e.g., `https://your-orchestrator.example.com`). | | Logout Callback URL | No | The URL for Single Logout (SLO) callback. | | SP Certificate Path | No | Path to the Service Provider certificate for request signing. | | SP Private Key Path | No | Path to the Service Provider private key for request signing. | | NameID Format | No | The NameID format to use in SAML assertions (e.g., `emailAddress`, `persistent`). | The **Enable IdP Initiated Login** toggle allows authentication flows started by the identity provider. Enable this if your users will access the application from an IdP portal. 4. Click **Save**. Define a SAML connector in the `connectors` section of your `maverics.yaml` file. The connector communicates with your identity provider over SAML 2.0. ```yaml maverics.yaml theme={null} connectors: - name: my-saml-idp type: saml samlMetadataURL: https://your-idp.example.com/saml/metadata samlConsumerServiceURL: https://your-orchestrator.example.com/saml/acs samlEntityID: https://your-orchestrator.example.com ``` The `samlMetadataURL` points to your identity provider's SAML metadata endpoint. The Orchestrator fetches this automatically to retrieve the IdP's signing certificate, SSO endpoint, and entity ID. If your IdP does not publish a metadata URL, you can provide the metadata as a local file using `samlMetadataFile` instead. Most identity providers publish a SAML metadata URL that the Orchestrator can fetch automatically. This is easier than manually entering certificates and endpoints -- the metadata contains everything the Orchestrator needs to establish the trust relationship. **Protocol translation:** This guide shows a SAML connector, but the Orchestrator can connect to your IdP using any supported protocol -- OIDC, SAML, or LDAP. The Orchestrator's mode (SAML Provider) determines what protocol your *application* speaks. The connector determines what protocol your *IdP* speaks. These are independent -- you can connect an OIDC-only IdP and the Orchestrator will translate to SAML for your application. See the [Identity Fabric overview](/reference/orchestrator/identity-fabric) for all connector types. Register your application as a SAML relying party (service provider) in the `apps` section. This tells the Orchestrator which application to issue SAML assertions for, where to send the assertions, and which identity connector to use for authentication. In the Console, you create the SAML application and connect it to your identity provider in a single flow. The connector you select becomes the application's authentication source. 1. Navigate to **Applications** in the sidebar and click **Create**. 2. Select **SAML-based**. 3. Fill in the application form: | Field | Required | Description | | --------------------------------------- | -------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------- | | Name | Yes | A friendly name for your application (e.g., `my-saml-app`). | | Upload Icon | No | Upload an image for your application (JPEG, PNG, or SVG, up to 2MB). | | Default Entity ID | Yes | The entity ID identifying the service provider. Click the **Entity ID** button to add additional entity IDs. | | Default URL (ACS) | Yes | The default Assertion Consumer Service URL. Click the **URL** button to add additional ACS URLs. | | Logout URL | No | The URL where SAML logout responses are sent. | | Unauthorized Page | No | Redirect URL for unauthorized users. | | Duration | No | The duration in seconds for which responses are valid. Defaults to 300 seconds. | | Name ID Format | No | The NameID format for the SAML assertion. The specific NameID attribute mapping is configured on the application's **Protocol & Assertion Settings** card. | | Signing Options | No | Select **Use deployment settings** (default), **Sign Response Only**, **Sign Response & Assertion**, or **Sign Assertion Only**. | | Certificate File (Request Verification) | No | Upload a PEM certificate to verify signed incoming requests from the SP. | | Login URL (IDP Initiated Login) | No | Endpoint for IdP-initiated login flow. | | Relay State URL (IDP Initiated Login) | No | Landing page URL after IdP-initiated authentication. | 4. Click **Save**. 5. On the application settings page, find the **Resources** card and click **Edit**. Click **Add Resource**, select the SAML connector you created earlier, and click **Save**. A connector must be added as a resource before it can be selected as an authentication source. 6. Find the **Access Control** card and click **Edit**. 7. From the **Select an authentication source** dropdown, select your identity provider. To add more than one source, click **Add identity provider**. 8. Click **Save**. For any fields that accept certificates or private keys (such as SP Certificate for request verification), use [secret provider](/guides/security/secrets-management) references to avoid storing sensitive material in plaintext. Define a SAML application in the `apps` section. The `entityIDs` and `consumerServiceURLs` identify your application in the SAML trust, and `authentication.idps` binds the connector from the first step. ```yaml maverics.yaml theme={null} apps: - name: my-saml-app type: saml entityIDs: - identifier: https://your-app.example.com default: true consumerServiceURLs: - url: https://your-app.example.com/saml/acs default: true logoutServiceURL: https://your-app.example.com/saml/logout duration: 300 requestVerification: skipVerification: true authentication: idps: - my-saml-idp ``` The `entityIDs` array identifies your application in the SAML trust relationship. The `consumerServiceURLs` specify where the Orchestrator sends the SAML assertion after authentication. The `duration` sets the assertion validity period in seconds. Set `requestVerification.skipVerification` to `true` if your application does not sign its SAML authentication requests. For applications that do sign requests, provide the application's certificate instead: ```yaml theme={null} requestVerification: certificate: ``` Configure the `nameID` and `claimsMapping` to control which identity attributes appear in the SAML assertions your application receives. The `nameID` is the primary user identifier in the assertion, and `claimsMapping` adds additional attributes. 1. Open the application you created in the previous step. 2. Find the **Attribute Mappings** card and click **Edit**. 3. Add a claim mapping for each attribute your application needs: | Field | Description | | ------------- | --------------------------------------------------------------------------------------- | | Claim Name | The attribute name that will appear in the SAML assertion (e.g., `email`, `firstName`). | | Claim Source | Select the identity provider connector to pull the attribute from. | | Value Mapping | The attribute name from the identity provider (e.g., `email`, `given_name`). | 4. Click the **Claim** button to add additional rows for each claim you need to map. For example, to pass the user's email, first name, and last name, add three claim rows: * `email` from your IdP's `email` * `firstName` from your IdP's `given_name` * `lastName` from your IdP's `family_name` 5. Click **Save**. **Configure the NameID:** The NameID is configured separately, on the **Protocol & Assertion Settings** card. 6. Find the **Protocol & Assertion Settings** card and click **Edit**. 7. Under **NameID**, set the **Dynamic NameID Source** to the identity provider connector that provides the NameID value, and set the **Dynamic NameID Attribute** to the attribute to use as the primary subject identifier (e.g., `email`). 8. Click **Save**. Add `nameID` and `claimsMapping` to your SAML application definition. The `nameID.attrMapping` references an attribute from your IdP connector using the format `connectorName.attributeName`. ```yaml maverics.yaml theme={null} apps: - name: my-saml-app type: saml entityIDs: - identifier: https://your-app.example.com default: true consumerServiceURLs: - url: https://your-app.example.com/saml/acs default: true logoutServiceURL: https://your-app.example.com/saml/logout duration: 300 requestVerification: skipVerification: true nameID: format: urn:oasis:names:tc:SAML:1.1:nameid-format:emailAddress attrMapping: my-saml-idp.email authentication: idps: - my-saml-idp claimsMapping: email: my-saml-idp.email firstName: my-saml-idp.given_name lastName: my-saml-idp.family_name ``` The `nameID.format` specifies the NameID format the application expects. Common formats include `emailAddress`, `persistent`, and `unspecified`. The `attrMapping` value references the connector attribute to use as the NameID value. The `claimsMapping` keys (`email`, `firstName`, `lastName`) become attribute names in the SAML assertion. The values reference attributes from your IdP connector. See [SAML Provider Reference](/reference/modes/saml-provider) for all available fields, including IdP-initiated login, per-app signature settings, and advanced assertion configuration. See the [SAML Provider reference](/reference/modes/saml-provider) for the complete list of configurable attributes, name formats, and assertion settings. After configuring your deployment, identity connector, application, and assertion attributes in the Console, you need to publish the configuration so the Orchestrator receives it and applies your changes. 1. At the bottom of the deployment Settings page, click **Publish Preview** in the sticky footer bar. 2. In the Deployment Manager dialog, review the configuration diff to verify your changes. 3. Optionally add a revision note describing what changed (e.g., "Initial SAML federation setup"). 4. Click **Publish** to deploy the configuration bundle to your storage provider. 5. The Orchestrator detects the new bundle on its next poll cycle and applies the configuration automatically. See [Publishing Deployment Configs overview](/reference/console/config-publishing) for details on the publishing lifecycle, revision history, and bundle verification. When using direct configuration, configuration is delivered directly to the Orchestrator via the `-config` flag or `MAVERICS_CONFIG` environment variable. No publishing step is needed -- restart the Orchestrator to apply configuration changes. With your SAML identity source configured, your application registered as a relying party, and attribute mapping in place, you are ready to test the federated authentication flow. Start (or restart) the Orchestrator and verify it is healthy: ```bash theme={null} maverics -config /etc/maverics/config.yaml curl -s https://localhost:9443/status | jq . ``` Now test the SAML flow by visiting your application's URL: 1. **Visit the application URL** -- The Orchestrator redirects you to your identity provider's login page (SP-initiated flow) 2. **Authenticate** -- Log in with valid credentials at your IdP 3. **Verify redirect** -- After authentication, you should land on your application with a valid session 4. **Check attributes** -- If your application has a profile or debug page, verify that the SAML attributes match your mapping configuration To test the IdP-initiated flow, log into your identity provider's portal and click the application tile. You should be redirected to your application with a valid session -- no separate login required. **Success!** Your Maverics Orchestrator is federating SAML authentication between your identity provider and your enterprise application. Users authenticate through your IdP, the Orchestrator translates the SAML assertion, and your application receives the attributes it expects -- all without modifying the application. ## Troubleshooting SAML assertions are cryptographically signed, and the Orchestrator validates these signatures using the certificate from your IdP's metadata. If the certificate has been rotated (updated) on the IdP side but the Orchestrator still has the old certificate, validation fails. Re-fetch the IdP's metadata or manually update the signing certificate in your Orchestrator configuration. If you are using a metadata URL, the Orchestrator can pick up certificate changes automatically on the next metadata refresh. Your identity provider rejects the SAML request because the ACS URL (Assertion Consumer Service URL) does not match what is registered. This is the URL where the IdP sends the SAML response after authentication. Verify that the ACS URL configured in the Orchestrator exactly matches the one registered in your IdP -- including protocol, domain, port, and path. This is similar to the redirect URI mismatch issue in OIDC. SAML assertions include timestamps that the Orchestrator validates to prevent replay attacks. If the clocks on your IdP server and the Orchestrator's host are not synchronized, the Orchestrator may reject valid assertions because they appear to be from the future or already expired. Ensure both systems use NTP (Network Time Protocol) to keep their clocks synchronized. Most SAML implementations allow a small clock skew tolerance (typically 1-2 minutes) -- check your Orchestrator configuration for a skew tolerance setting. ## What's Next Move users from one identity provider to another with zero downtime and no application changes Explore the complete SAML Provider configuration -- assertions, attributes, signing, and advanced settings # Single Logout (SLO) Source: https://docs.strata.io/guides/authentication/single-logout By the end of this guide, you will have Single Logout configured on your Maverics Orchestrator -- enabling users to log out of all identity providers they authenticated with and terminate their Maverics session in a single action. ## What Is Single Logout? When a user authenticates through the Maverics Orchestrator, they may authenticate with multiple Identity Fabric connectors during a single session. The Orchestrator's session tracks which identity providers the user has authenticated with. Without Single Logout, ending a session with one identity provider leaves the others active. The Maverics session and other IdP sessions remain, which means the user is still effectively logged in and can access applications without re-authenticating. Single Logout solves this by propagating the logout signal across all authenticated identity providers via **front-channel logout**. When a user visits the SLO endpoint, the Orchestrator: 1. Checks the session for each Identity Fabric connector the user authenticated with 2. For each authenticated connector, calls that connector's logout method, which redirects the user to the IdP for front-channel logout 3. Each IdP logout redirects back to the SLO handler, allowing the Orchestrator to iterate through remaining authenticated connectors 4. After all IdP logouts complete, terminates the Maverics session (preventing session replay attacks) 5. Runs the `postLogoutSE` Service Extension if configured 6. Redirects the user to the `postLogout.redirectURL`, or displays a default "You have been logged out." message if no redirect URL is configured Single Logout is separate from any protocol-level logout endpoints you may configure on an Orchestrator running as a SAML or OIDC provider. Provider endpoints (such as `singleLogoutService` for SAML or `endSession` for OIDC) handle protocol-specific logout requests from individual service providers or relying parties. The global SLO handler, by contrast, handles the user-facing logout flow across all authenticated Identity Fabric connectors. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed the Orchestrator yet, follow the [Quick Start guide](/guides/getting-started/quick-start) or see the [installation reference](/reference/orchestrator/installation). * **At least one configured application** -- An OIDC, SAML, or proxy application registered with the Orchestrator. See the [SSO with OIDC](/guides/authentication/sso-with-oidc), [Federate SAML Apps](/guides/authentication/saml-federation), or [Add SSO to Web Apps](/guides/authentication/http-proxy-auth) guides. * **An identity provider connector** -- A configured upstream IdP. See the [Identity Fabric reference](/reference/orchestrator/identity-fabric) for supported connectors. ## Configure Single Logout Add the `singleLogout` block at the top level of your Orchestrator configuration. This defines the post-logout redirect destination and optional Service Extension hook. Single Logout can be configured in the Maverics Console within a Deployment. 1. Open the **Maverics Console** and navigate to the Deployment you want to configure. 2. Scroll to the **Single Logout** section. 3. Click **Edit** to open the SLO settings. 4. Set the **Logout URL** -- this is the URL that will be registered on the Orchestrator deployment and called by user interaction on an app to initiate the SLO process (e.g., `https://auth.example.com/single-logout`). 5. Under **Post Logout**, set the **Redirect URL** to where users should be sent after logout completes (e.g., `https://enterprise.com/index.html`). 6. Optionally, configure a **Post Logout Service Extension** by specifying the function name and file path for custom post-logout logic. 7. Click **Save** to apply the changes. Add the `singleLogout` block to your `maverics.yaml` file. This block is a **top-level key** -- it is not nested under `session` or any application. ```yaml maverics.yaml theme={null} singleLogout: logoutURL: https://auth.example.com/single-logout postLogout: redirectURL: https://enterprise.com/index.html ``` | Key | Type | Required | Description | | -------------------------------------- | ------ | -------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | | `singleLogout.logoutURL` | string | No | The URL registered on the Orchestrator deployment that is called by user interaction on an app to initiate the SLO process. | | `singleLogout.postLogout.redirectURL` | string | No | Where to redirect the user after logout completes (e.g., a landing page or login screen). If not set, the Orchestrator displays a default "You have been logged out." page. | | `singleLogout.postLogout.postLogoutSE` | object | No | A [Service Extension](/reference/orchestrator/service-extensions) hook that runs after the logout flow completes but before the redirect. Use for audit logging, cleanup, or custom logic. | Single Logout works by iterating through the Identity Fabric connectors that the user has authenticated with during their session. Each connector's logout method is called via front-channel redirect, so the connectors must support logout. Verify that your Identity Fabric connectors are configured correctly. The Orchestrator automatically tracks which connectors the user authenticated with via the session -- no additional per-connector SLO configuration is required beyond the standard connector setup. If an Identity Fabric connector points to another Orchestrator deployment running as a SAML or OIDC provider, that provider deployment's logout endpoints must be configured for the front-channel logout to propagate correctly. For example, if you have an auth provider deployment and a separate proxy app deployment, and the proxy app's Identity Fabric connector points to the auth provider, ensure the auth provider has its SAML `singleLogoutService` or OIDC `endSession` endpoint configured. See the [SAML Provider](/reference/modes/saml-provider) and [OIDC Provider](/reference/modes/oidc-provider) references for details. See the [Identity Fabric reference](/reference/orchestrator/identity-fabric) for supported connectors and their logout capabilities. With Single Logout configured, test the end-to-end flow: 1. **Authenticate** -- Log in to one of your applications through the Orchestrator. If possible, authenticate with multiple Identity Fabric connectors to test the full front-channel logout loop. 2. **Trigger SLO** -- Navigate to the Orchestrator's Single Logout endpoint. 3. **Observe front-channel logout** -- The Orchestrator redirects through each authenticated IdP's logout endpoint in sequence. Each IdP redirects back to the SLO handler so the next IdP can be logged out. 4. **Verify redirect** -- After all IdP logouts complete, you should be redirected to the `postLogout.redirectURL` (or see a default "You have been logged out." page if no redirect URL is configured). 5. **Confirm session termination** -- Try accessing your applications. You should be prompted to re-authenticate, confirming that the Maverics session and all IdP sessions were cleared. Enable debug-level [logging](/reference/orchestrator/telemetry/logging) to trace the SLO flow. The Orchestrator logs each IdP logout as it iterates through authenticated connectors, making it easy to verify that all IdPs are being logged out in sequence. ## Dynamic Session Expiration with SLO You can combine Single Logout with [Service Extensions](/reference/orchestrator/service-extensions) to dynamically expire sessions and redirect users to the SLO endpoint. This is useful for enforcing role-based session policies -- for example, giving contractors shorter sessions than full-time employees. Configure dynamic session expiration using the `evalMaxLifetimeSE` and `evalIdleTimeoutSE` hooks in the `session.lifetime` block: ```yaml maverics.yaml theme={null} session: lifetime: evalMaxLifetimeSE: funcName: EvalMaxLifetime file: /etc/maverics/extensions/session.go evalIdleTimeoutSE: funcName: EvalIdleTimeout file: /etc/maverics/extensions/session.go store: type: local local: capacity: 50000 singleLogout: logoutURL: https://idp.enterprise.com/single-logout postLogout: redirectURL: https://enterprise.com/index.html ``` The Service Extension evaluates session lifetime on each request. When the session exceeds the allowed duration, the SE redirects the user to the SLO endpoint, triggering a full logout across all applications: ```go session.go theme={null} package main import ( "net/http" "time" "github.com/strata-io/service-extension/orchestrator" ) const sloEndpoint = "https://auth.example.com/single-logout" func EvalMaxLifetime( api orchestrator.Orchestrator, rw http.ResponseWriter, req *http.Request, createdAt time.Time, ) bool { maxLifetime := 12 * time.Hour employeeType, err := api.Session().GetString("idp.employeeType") if err == nil && employeeType == "contractor" { maxLifetime = 1 * time.Hour } if time.Now().After(createdAt.Add(maxLifetime)) { api.Logger().Info("se", "session expired, redirecting to SLO") http.Redirect(rw, req, sloEndpoint, http.StatusFound) return false } return false } ``` The `sloEndpoint` constant in the Go code should point to the Orchestrator's Single Logout endpoint. See [Local Sessions -- Dynamic Session Expiration](/reference/orchestrator/sessions/local#dynamic-session-expiration) for the complete example including idle timeout evaluation. ## Post-Logout Service Extension The `postLogoutSE` hook runs custom logic after the SLO flow completes -- after all Identity Fabric connector logouts and the Maverics session termination, but before the user is redirected to `postLogout.redirectURL`. Common use cases include audit logging, analytics, and cleanup of external resources. ```yaml maverics.yaml theme={null} singleLogout: logoutURL: https://idp.enterprise.com/single-logout postLogout: redirectURL: https://enterprise.com/index.html postLogoutSE: funcName: PostLogout file: /etc/maverics/extensions/postLogout.go ``` ```go logout.go theme={null} package main import ( "net/http" "github.com/strata-io/service-extension/orchestrator" ) func PostLogout( api orchestrator.Orchestrator, rw http.ResponseWriter, req *http.Request, ) { api.Logger().Info("se", "user completed single logout", "remoteAddr", req.RemoteAddr, ) } ``` See [Service Extensions](/reference/orchestrator/service-extensions) for the full list of available hooks. ## Local Development When developing and testing SLO locally, keep these considerations in mind: * **TLS requirements** -- Session cookies default to `Secure` (HTTPS only). For local HTTP testing, set `session.cookie.disableSecure: true` in your Orchestrator configuration. Do not use this setting in production. * **Cookie domain** -- If your local applications run on different ports of `localhost`, set `session.cookie.domain` to `localhost` so the session cookie is shared across ports. * **IdP logout** -- Some IdPs may not support logout redirects to `localhost`. During local development, you can test the Maverics session termination without full IdP front-channel logout propagation. Example local development configuration: ```yaml maverics.yaml theme={null} http: address: 0.0.0.0:8443 tls: server tls: server: certFile: /etc/maverics/certs/localhost.pem keyFile: /etc/maverics/certs/localhost-key.pem session: cookie: domain: localhost disableSecure: false store: type: local local: capacity: 1000 singleLogout: logoutURL: https://localhost:8443/single-logout postLogout: redirectURL: https://localhost:8443/ ``` Use tools like [mkcert](https://github.com/FiloSottile/mkcert) to generate locally-trusted TLS certificates. This avoids browser security warnings and keeps your local environment closer to production by keeping the `Secure` cookie flag enabled. ## Troubleshooting **Symptoms:** After triggering Single Logout, the user is immediately logged back in when accessing an application. **Causes:** * An Identity Fabric connector's logout did not fully clear the IdP session. The upstream IdP recognizes the user's existing session and silently re-authenticates without prompting for credentials. * The connector does not support logout, so the SLO flow skipped it. **Resolution:** 1. Verify that your Identity Fabric connectors support logout and are configured correctly. See the [Identity Fabric reference](/reference/orchestrator/identity-fabric) for connector-specific logout support. 2. Enable debug-level logging to confirm the Orchestrator is iterating through all authenticated connectors during the SLO flow. 3. Verify that each IdP's logout endpoint redirects back to the Orchestrator so the front-channel logout loop can continue to the next connector. **Symptoms:** Navigating to the Single Logout endpoint returns a 404 error. **Causes:** * The `singleLogout` block is missing from the Orchestrator configuration. * The Orchestrator has not been restarted after adding the `singleLogout` block. **Resolution:** 1. Verify that the `singleLogout` block exists at the top level of your configuration (not nested under `session` or any app). 2. Restart the Orchestrator after making configuration changes. **Symptoms:** The SLO flow starts but gets stuck or only logs out of one IdP. **Causes:** * An IdP's logout endpoint does not redirect back to the Orchestrator's SLO handler. * A network or TLS issue prevents the redirect from reaching the Orchestrator. **Resolution:** 1. Check that each IdP is configured to redirect back to the Orchestrator after logout. The SLO handler relies on these redirects to iterate through all authenticated connectors. 2. Enable debug-level logging to see which connector the flow stopped at. 3. Verify TLS and network connectivity between the Orchestrator and each IdP. **Symptoms:** After SLO completes, the user sees "You have been logged out." instead of being redirected. **Causes:** * The `postLogout.redirectURL` is not set. The Orchestrator defaults to displaying a plain text message when no redirect URL is configured. * A `postLogoutSE` is configured and writes its own response, overriding the redirect behavior. **Resolution:** 1. Set `singleLogout.postLogout.redirectURL` to a valid URL. 2. If using a `postLogoutSE`, ensure the SE does not write its own HTTP response or redirect -- doing so overrides the default redirect behavior. ## What's Next Complete reference for all logout types including Single Logout configuration Session store configuration, dynamic session expiration, and session management Custom Go hooks including postLogoutSE for post-logout logic Session types, lifecycle, and production deployment guidance # SSO with OIDC Source: https://docs.strata.io/guides/authentication/sso-with-oidc By the end of this guide, you will have a running Maverics Orchestrator configured as an OIDC Provider -- authenticating users through your identity provider and issuing tokens to your application. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed the Orchestrator yet, follow the [Quick Start guide](/guides/getting-started/quick-start) or see the [installation reference](/reference/orchestrator/installation). * **An identity provider account** -- You need credentials for an identity provider such as [Microsoft Entra ID](/reference/orchestrator/identity-fabric/azure-ad), [Okta](/reference/orchestrator/identity-fabric/okta), or [Auth0](/reference/orchestrator/identity-fabric/auth0). While this guide demonstrates an OIDC connector, the Orchestrator supports OIDC, SAML, and LDAP connectors, so your IdP does not need to support OIDC specifically. * **A target application** -- Any web application that accepts OIDC tokens or that you want to protect with OIDC-based single sign-on. ## Configure SSO In the Maverics Console, all configuration lives within a **Deployment** -- a managed Orchestrator instance with its own configuration, storage provider, and signing keys. Before you can create identity connectors and applications, you need a Deployment to hold them. 1. Log in to the [Maverics Console](https://maverics.strata.io). 2. Navigate to **Deployments** in the sidebar and click **Create**. 3. Enter a name for your deployment (e.g., `OIDC SSO`). 4. Select a deployment provider. The Console supports several options: * **AWS S3**, **Azure Blob Storage**, or **Google Cloud Storage** -- customer-managed cloud storage for production. * **GitHub** or **GitLab** -- deploy bundles to a Git repository. * **Download Only** -- manual bundle download for air-gapped environments. See [Publishing Deployment Configs overview](/reference/console/config-publishing#deployment-providers) for provider setup details. 5. Click **Create**. Your new deployment opens automatically. You can now configure identity connectors and applications within it. When using direct configuration, no deployment setup is needed -- configuration is defined directly in the `maverics.yaml` file and delivered to the Orchestrator via the `-config` flag or `MAVERICS_CONFIG` environment variable. See [Installation](/reference/orchestrator/installation) for details on configuration delivery options. The OIDC Provider must be enabled and configured at the deployment level before creating applications. This sets up the issuer identity, endpoints, and signing keys that all OIDC applications in the deployment share. 1. Open your deployment and click the **gear icon** in the sidebar to open **Deployment Settings**. 2. Find the **OIDC Provider** section. 3. Enter the **Issuer** URL (e.g., `https://your-orchestrator.example.com`). This becomes the `iss` claim in all issued tokens. 4. Click **Generate** to auto-populate the Well-Known, Authorization, Token, Introspect, Revocation, End Session, UserInfo, and JWKS endpoint URLs from the Issuer. 5. Under **JSON Web Keys**, click **Edit JSON Web Keys** to configure the signing key pair used for token signing. 6. Click **Save**. If JSON Web Keys are left blank, the Orchestrator auto-generates a signing key pair at startup. This key pair is **ephemeral** -- a new one is created every time the Orchestrator restarts, which means all previously issued tokens become unverifiable. Only rely on auto-generated keys for local development and testing. For production, always configure explicit signing keys managed by a [secret provider](/guides/security/secrets-management). The OIDC Provider Deployment Settings fields are documented in detail in the [OIDC Provider reference](/reference/modes/oidc-provider#setup). Use the Console UI tab there for field-by-field descriptions. In YAML, the OIDC Provider is configured via the `oidcProvider` top-level key. This is shown in the next step alongside the application configuration. If the `jwks` array is omitted from `oidcProvider`, the Orchestrator auto-generates a signing key pair at startup. This key pair is **ephemeral** -- it is regenerated on every restart, invalidating all previously issued tokens. For production deployments, always provide explicit keys using [secret provider](/guides/security/secrets-management) references (e.g., ``). An identity provider (IdP) is the service that manages your user accounts and handles login -- think Microsoft Entra ID (now Microsoft Entra ID), Okta, or Google Workspace. Connecting the Orchestrator to your IdP tells it where to send users when they need to authenticate. The Orchestrator uses [Identity Fabric](/reference/orchestrator/identity-fabric) connectors to communicate with your IdP. This guide demonstrates an OIDC connector, but the connector protocol is independent of the Orchestrator's mode -- even though the Orchestrator is serving OIDC to your application, the IdP connector can use OIDC, SAML, or LDAP. The Orchestrator handles the protocol translation between your IdP and your application. You will need your IdP's client ID, client secret, and discovery URL (sometimes called the issuer URL or well-known endpoint). These credentials allow the Orchestrator to establish a trust relationship with your provider. 1. Navigate to **Identity Fabric** in the sidebar and click **Create**. 2. Select your identity provider from the list. Choose a provider-specific option (such as **Okta (OIDC)**, **Microsoft Entra ID (OIDC)**, or **Auth0 (OIDC)**) or select **Generic OIDC Configuration** for any OIDC-compliant provider. SAML and LDAP connector options are also available -- this guide demonstrates the OIDC connector path, but any connector type is valid here. 3. Fill in the connector form: | Field | Required | Description | | ---------------------------- | -------- | --------------------------------------------------------------------------------------------------------------------------------- | | Name | Yes | A friendly name for your identity provider (e.g., `my-idp`). | | OIDC Well Known URL | Yes | Your IdP's OIDC discovery endpoint (e.g., `https://your-idp.example.com/.well-known/openid-configuration`). | | OAuth Client ID | Yes | The client ID from the application you registered in your IdP for Maverics. | | Client Authentication Method | Yes | Select **OAuth Client Secret** (default) or **OAuth JWT Client Authentication**. | | OAuth Client Secret | Yes | The client secret from your IdP. For production, use a [secret provider](/reference/orchestrator/configuration/secret-providers). | | Redirect URLs | Yes | The callback URL where your IdP redirects after authentication (e.g., `https://your-orchestrator.example.com/oidc-callback`). | | Scopes | No | Space-separated OIDC scopes (e.g., `openid profile email`). | The **PKCE** toggle is enabled by default. Disable it only if your IdP does not support Proof Key for Code Exchange. 4. Click **Save**. Define an OIDC connector in the `connectors` section of your `maverics.yaml` file. The connector specifies how the Orchestrator communicates with your identity provider. ```yaml maverics.yaml theme={null} connectors: - name: my-idp type: oidc oidcWellKnownURL: https://your-idp.example.com/.well-known/openid-configuration oauthClientID: your-orchestrator-client-id oauthClientSecret: oauthLoginRedirect: urls: - https://your-orchestrator.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-orchestrator.example.com/logout disablePKCE: false scopes: openid profile email ``` Replace `your-idp.example.com` with your identity provider's domain. The `oidcWellKnownURL` points to the OIDC discovery endpoint, which provides the Orchestrator with all of the IdP's endpoints and signing keys automatically. The `oauthClientSecret` uses the `` secret reference syntax -- the Orchestrator retrieves this value at runtime from your [secret provider](/reference/orchestrator/configuration/secret-providers) rather than reading a plaintext value from the config file. Not sure which connector to use? The [Identity Fabric overview](/reference/orchestrator/identity-fabric) includes a comparison table mapping each connector to its supported protocols and use cases. **Protocol translation:** This guide shows an OIDC connector, but the Orchestrator can connect to your IdP using any supported protocol -- OIDC, SAML, or LDAP. The Orchestrator's mode (OIDC Provider) determines what protocol your *application* speaks. The connector determines what protocol your *IdP* speaks. These are independent -- you can connect a SAML-only IdP and the Orchestrator will translate to OIDC for your application. See the [Identity Fabric overview](/reference/orchestrator/identity-fabric) for all connector types. Next, register your application with the Orchestrator's [OIDC Provider](/reference/modes/oidc-provider). This tells the Orchestrator which application will receive OIDC tokens and how to handle the authentication flow. You configure a client ID and secret for your application (separate from the IdP credentials above), the redirect URLs your application accepts after authentication, and which identity connector to use for authenticating users. In the Console, you create the OIDC application and connect it to your identity provider in a single flow. The connector you select becomes the application's authentication source. 1. Navigate to **Applications** in the sidebar and click **Create**. 2. Select **OIDC-based**. 3. Fill in the application form: | Field | Required | Description | | ------------- | -------- | ---------------------------------------------------------------------------------------------------------------------------------------------------- | | Name | Yes | A friendly name for your application (e.g., `my-web-app`). | | Client ID | Yes | The client identifier your application will use to authenticate with the Orchestrator. | | Client Secret | Yes | Click **Add Client Secret** and enter a secret. Your application will use this to authenticate token requests. | | Redirect URL | Yes | Click **Add Redirect URL** and enter the callback URL your application accepts after authentication (e.g., `https://your-app.example.com/callback`). | The default grant types (**Authorization Code**, **Refresh Token**, and **Client Credentials**) work for most applications. Under **Access Token Settings**, the token type defaults to **JWT**. 4. Click **Save**. 5. On the application settings page, find the **Resources** card and click **Edit**. Click **Add Resource**, select the connector you created in the previous step, and click **Save**. A connector must be added as a resource before it can be selected as an authentication source. 6. Find the **Access Control** card and click **Edit**. 7. From the **Select an authentication source** dropdown, select your identity provider. To add more than one source, click **Add identity provider**. 8. Click **Save**. Store application client secrets using the `` secret reference syntax rather than plaintext values. See [Secrets Management](/guides/security/secrets-management) for setup instructions. Define the OIDC Provider and register your application in the `apps` section. The `authentication.idps` array binds the connector from the previous step to this application. ```yaml maverics.yaml theme={null} oidcProvider: discovery: issuer: https://your-orchestrator.example.com endpoints: wellKnown: https://your-orchestrator.example.com/.well-known/openid-configuration jwks: https://your-orchestrator.example.com/oauth2/jwks auth: https://your-orchestrator.example.com/oauth2/auth token: https://your-orchestrator.example.com/oauth2/token userinfo: https://your-orchestrator.example.com/oauth2/userinfo introspect: https://your-orchestrator.example.com/oauth2/introspect jwks: - algorithm: RSA256 publicKey: privateKey: apps: - name: my-web-app type: oidc clientID: my-web-app credentials: secrets: - redirectURLs: - https://your-app.example.com/callback authentication: idps: - my-idp accessToken: type: jwt ``` The `authentication.idps` array references the connector name from the previous step (`my-idp`). When a user accesses your application, the Orchestrator redirects them to that IdP for authentication. The `credentials.secrets` array uses secret references so your application's client secret is never stored in plaintext. The `accessToken.type` can be `jwt` (self-contained tokens) or `opaque` (reference tokens that require introspection). Claims are pieces of identity information about the user -- their email address, display name, group memberships, roles, and any custom attributes your IdP provides. When the Orchestrator acts as an [OIDC Provider](/reference/modes/oidc-provider), it issues tokens to your application that contain these claims. Claim mapping lets you control which identity attributes from your IdP end up in the tokens your application receives. You can rename claims (so your app sees `email` instead of `preferred_username`), filter out unnecessary data, or combine claims from multiple sources. This is where the Orchestrator's protocol translation becomes powerful -- your IdP might use one claim format, but your application expects another. The Orchestrator handles the translation so neither side needs to change. 1. Open the application you created in the previous step. 2. Find the **Claims and OAuth 2.0 Scopes** card and click **Edit**. 3. Under **Attribute to Standard OIDC Claim Mapping**, add a claim mapping for each attribute your application needs: | Field | Description | | ------------- | ------------------------------------------------------------------------------------------ | | Claim Name | The claim name that will appear in the issued token (e.g., `email`, `name`, `given_name`). | | Claim Source | Select the identity provider connector to pull the attribute from. | | Value Mapping | The attribute name from the identity provider (e.g., `preferred_username`, `name`). | 4. Click the **Claim** button to add additional rows for each claim you need to map. For example, to pass the user's email, name, and family name, add three claim rows: * `email` from your IdP's `preferred_username` * `name` from your IdP's `name` * `family_name` from your IdP's `family_name` 5. Click **Save**. Add a `claimsMapping` section to your application definition. Each entry maps a claim name in the issued token (left side) to an attribute from your IdP connector (right side), using the format `connectorName.attributeName`. ```yaml maverics.yaml theme={null} apps: - name: my-web-app type: oidc clientID: my-web-app credentials: secrets: - redirectURLs: - https://your-app.example.com/callback authentication: idps: - my-idp accessToken: type: jwt claimsMapping: email: my-idp.preferred_username name: my-idp.name family_name: my-idp.family_name given_name: my-idp.given_name ``` The `claimsMapping` keys (`email`, `name`, `family_name`, `given_name`) are the claim names that appear in the tokens your application receives. The values (`my-idp.preferred_username`, `my-idp.name`, etc.) reference attributes from the identity connector. The prefix before the dot must match the connector `name` from the previous step. See [OIDC Provider Reference](/reference/modes/oidc-provider) for all available fields, including scopes, token lifetimes, and advanced claim configuration. See the [OIDC Provider reference](/reference/modes/oidc-provider) for the complete list of configurable claims, scopes, and token settings. After configuring your deployment, identity connector, application, and claim mapping in the Console, you need to publish the configuration so the Orchestrator receives it and applies your changes. 1. At the bottom of the deployment Settings page, click **Publish Preview** in the sticky footer bar. 2. In the Deployment Manager dialog, review the configuration diff to verify your changes. 3. Optionally add a revision note describing what changed (e.g., "Initial OIDC SSO setup"). 4. Click **Publish** to deploy the configuration bundle to your storage provider. 5. The Orchestrator detects the new bundle on its next poll cycle and applies the configuration automatically. See [Publishing Deployment Configs overview](/reference/console/config-publishing) for details on the publishing lifecycle, revision history, and bundle verification. When using direct configuration, configuration is delivered directly to the Orchestrator via the `-config` flag or `MAVERICS_CONFIG` environment variable. No publishing step is needed -- restart the Orchestrator to apply configuration changes. With your identity provider connected, your application defined, and claim mapping configured, you are ready to test the complete SSO flow. Start (or restart) the Orchestrator to pick up your configuration and verify it is healthy: ```bash theme={null} maverics -config /etc/maverics/config.yaml curl -s https://localhost:9443/status | jq . ``` A healthy response confirms the Orchestrator is running: ```json theme={null} { "status": "up" } ``` Now open your application's public URL in a browser and walk through the SSO flow: 1. **Visit your application URL** -- You should be redirected to your identity provider's login page 2. **Authenticate** -- Log in with valid credentials 3. **Verify redirect** -- After authentication, you should land on your application with full access 4. **Inspect tokens** -- If your application exposes token details, verify the claims match your mapping configuration **Success!** Your Maverics Orchestrator is acting as an OIDC Provider -- authenticating users through your identity provider and issuing tokens with the claims your application expects. Users experience seamless single sign-on without your application needing to integrate directly with your IdP. ## Troubleshooting This is the most common OIDC configuration issue. Your identity provider rejects the authentication request because the redirect URI (callback URL) the Orchestrator sends does not exactly match what is registered in your IdP. Check both sides -- the URI configured in the Orchestrator and the URI registered in your IdP's application settings must be character-for-character identical, including the protocol (`https://`), domain, port, and path. Trailing slashes matter. If your application receives a token but cannot validate it, verify that the audience (`aud`) claim in the token matches what your application expects. The audience is set during claim mapping -- make sure it points to your application's client ID or expected identifier. If claims are missing from the token, check that the scopes requested during authentication include the data you need (for example, `email` scope for email claims, `profile` scope for name claims). See the [OIDC Provider reference](/reference/modes/oidc-provider) for scope-to-claim mappings. This usually indicates the Orchestrator successfully authenticated the user but cannot reach the upstream application. Verify that the upstream URL in your application route is correct and that the application is running and accessible from the Orchestrator's network. Check the Orchestrator logs for connection errors or timeouts. ## What's Next Set up SAML 2.0 federation for legacy enterprise applications that do not support OIDC Explore the complete OIDC Provider configuration -- scopes, claims, token lifetimes, and advanced settings # Protect Your First Application Source: https://docs.strata.io/guides/getting-started/first-application This guide picks up where the Quick Start left off. You already have a running Orchestrator with SSO protecting a basic route. Now you will add session management, identity header injection, and production-ready configuration. ## Prerequisites * **Completed the [Quick Start guide](/guides/getting-started/quick-start)** -- You should have a running Orchestrator with an identity provider connected and a working application route protected by SSO. * **A configured identity provider connector** -- Your Orchestrator should already be connected to an identity provider (Microsoft Entra ID, Okta, or another supported IdP) from the Quick Start. ## Configure Your Application You should already have a working application route from the Quick Start guide. The steps below add session management and header injection to that existing configuration. Session management controls how the Orchestrator tracks authenticated users between requests. Without session management, users would need to re-authenticate on every page load -- which is not a practical experience. The Orchestrator creates a session after a user successfully authenticates. This session stores the user's identity information (who they are, what claims they have) so that subsequent requests can be authorized without a full round-trip to the identity provider. Sessions can be stored in-memory for development or configured with [cookie-based sticky sessions](/reference/orchestrator/sessions/local) for production multi-node deployments (the load balancer uses the `maverics_session` cookie for affinity). Session management is configured in the Deployment settings, not on an individual application. 1. Navigate to **Deployments** in the sidebar and select your deployment. 2. Under **Orchestrator Settings**, find the **Session and Cookie** section. 3. Click **Edit Session and Cookie** to open the settings dialog. 4. Configure session lifetime settings: | Field | Default | Description | | -------------------- | ---------------- | ------------------------------------------------------------------------------------------------------------------------------ | | Max Lifetime Seconds | 86400 (24 hours) | The maximum number of seconds that can elapse post-authentication before a session's authentication state becomes invalidated. | | Idle Timeout | 0 (disabled) | The number of seconds a session may remain idle before timing out. Set to `0` to disable idle timeout. | | Cache Size | 50,000 | Limits the number of sessions maintained in memory. | 5. Optionally configure the **Cookie** settings: | Field | Description | | ------------------------------- | ---------------------------------------------------------------------------------------------------- | | Domain | Specifies the hosts to which the session cookie will be sent (e.g., `example.com`). | | Name | The name of your Maverics session cookie. | | Disable HttpOnly Attribute | If enabled, the session cookie can be accessed via client-side scripts. Leave disabled for security. | | Disable Secure Cookie Attribute | If enabled, the cookie can be sent over unencrypted HTTP. Leave disabled for security. | 6. Click **Save**. The dialog also offers optional **Service Extension** dropdowns for evaluating session maximum lifetime and idle timeout programmatically. See the [Sessions reference](/reference/orchestrator/sessions) for details. ```yaml theme={null} session: cookie: name: "maverics_session" domain: "example.com" lifetime: maxTimeout: "12h" idleTimeout: "30m" store: type: "local" local: capacity: 50000 ``` The `cookie.domain` scopes the session cookie to your domain. The `lifetime` settings control how long sessions remain valid. The `store.type: "local"` uses in-memory storage suitable for both development and production. See the [Sessions Reference](/reference/orchestrator/sessions) for all session configuration options. Header injection (also called identity propagation) is how the Orchestrator passes user identity information to your upstream application. After the Orchestrator authenticates a user, it adds HTTP headers to the proxied request -- telling your application who the user is without your application needing to handle authentication directly. Common headers include the user's email address, display name, group memberships, and any custom claims from the identity provider. Your upstream application reads these headers to identify the user and make authorization decisions. For example, the Orchestrator might inject: * `X-Forwarded-User` -- The authenticated user's unique identifier * `X-Forwarded-Email` -- The user's email address from the identity provider * `X-Forwarded-Groups` -- A comma-separated list of the user's group memberships Header injection is configured per-location within the application's access control policy. 1. Open your application's settings. 2. In the **Resources** card, click **Edit**, click **Add Resource**, and add your identity provider connector. A connector must be added as a resource before it can be used as an authentication source. 3. Find the **Access Control** card and click **Edit**, then click **Policy** to add a policy (or edit an existing one) in the **Edit Access Control** drawer. 4. Set the **Location** for the route you want to protect (e.g., `/`). 5. From the **Select an authentication source** dropdown, select the identity provider connector that will authenticate users for this location. 6. For **Authorization method**, choose **Allow all access**. 7. Under **Headers**, add the identity headers your application needs: | Header Name | Identity Source | Attribute Mapping | | -------------------- | ------------------ | ----------------- | | `X-Forwarded-User` | Your IdP connector | `sub` | | `X-Forwarded-Email` | Your IdP connector | `email` | | `X-Forwarded-Groups` | Your IdP connector | `groups` | Click **Header** to add each additional header. 8. Click **Save**. You can also use the **Global Request Headers & Service Extensions** card on the application to add headers to all locations without repeating them in each access control policy. Add the `headers` array to your existing app entry from the Quick Start: ```yaml theme={null} # Add to your existing app entry from Quick Start headers: - name: "X-Forwarded-User" value: "{{ azure.sub }}" - name: "X-Forwarded-Email" value: "{{ azure.email }}" - name: "X-Forwarded-Groups" value: "{{ azure.groups }}" ``` Headers are defined as an array of `{name, value}` objects. Values use the `{{ connector.claim }}` template syntax, where the connector name (e.g., `azure`) is the namespace and the claim name (e.g., `email`, `sub`, `groups`) comes from the identity provider. Your complete app entry with headers should look like this: ```yaml theme={null} apps: - name: my-application type: proxy upstream: "https://internal-app.example.com" routePatterns: - "app.example.com" headers: - name: "X-Forwarded-User" value: "{{ azure.sub }}" - name: "X-Forwarded-Email" value: "{{ azure.email }}" - name: "X-Forwarded-Groups" value: "{{ azure.groups }}" policies: - location: "/" authentication: idps: ["azure"] authorization: allowAll: true ``` Make sure your upstream application only trusts these headers when they come from the Orchestrator. If users can reach your application directly (bypassing the Orchestrator), they could forge these headers. Configure your application to only accept traffic from the Orchestrator's IP address or network, or use [mTLS](/guides/security/tls) between the Orchestrator and your upstream so both sides verify each other's identity cryptographically. With session management and header injection configured, restart the Orchestrator to pick up your updated configuration. Now open your application's public URL in a browser and walk through the complete flow: 1. **Visit your application URL** -- You should be redirected to your identity provider's login page 2. **Authenticate** -- Log in with valid credentials 3. **Verify redirect** -- After authentication, you should land on your application with full access 4. **Verify session persistence** -- Close and reopen your browser, then revisit the application URL. Your session should persist without requiring re-authentication (within the configured timeout) 5. **Check headers** -- If your application has a debug or profile page, verify that the injected identity headers (`X-Forwarded-User`, `X-Forwarded-Email`, `X-Forwarded-Groups`) are present and contain the correct values **Success!** Your application is fully protected by the Maverics Orchestrator. Users authenticate through your identity provider, sessions are managed automatically, and your application receives user identity through HTTP headers -- all without modifying your application code. ## Troubleshooting A 403 error after successful authentication usually means an authorization policy is blocking the user. Check whether you have configured any access policies that restrict which users can access the application. Also verify that the user's claims from the identity provider include the required attributes (such as group membership) that your policies expect. Verify that header injection is configured for the correct application entry. If your upstream application is behind a load balancer or reverse proxy, that intermediate layer may be stripping non-standard headers. Check each hop in the request path. You can use a tool like `curl -v` to inspect the headers the Orchestrator sends to your upstream. Session behavior is controlled by the session store configuration. Check the session timeout value -- it may be set too low for your use case. If sessions are not expiring, verify that the session store is correctly configured and that the Orchestrator is reading from the same store it writes to (important in multi-instance deployments). See the [Sessions reference](/reference/orchestrator/sessions) for all timeout and expiration options. ## What's Next Explore SSO with OIDC, SAML federation, and identity provider migration Learn how to deploy the Orchestrator for production workloads with high availability # Overview Source: https://docs.strata.io/guides/getting-started/overview The Getting Started guides walk you through your first experience with the Maverics Orchestrator -- from installing it on your infrastructure to protecting a real application with single sign-on. Whether you are an IAM administrator setting up identity routing for the first time or a developer integrating authentication into your stack, these guides give you a hands-on path to a working deployment. Before you begin, make sure you have [Console access and an organization set up](/introduction/getting-started). Start with the Quick Start if you want to get up and running fast. Move to Protect Your First Application when you are ready to see a complete, production-style configuration with session management and identity propagation. ## Guides Install the Orchestrator, connect an identity provider, and protect your first route in minutes Build a complete deployment with SSO, session management, and header-based identity propagation ## Related Pages Get access to the Console and set up your organization Dive deeper into SSO, OIDC, SAML federation, and identity provider migration # Quick Start Source: https://docs.strata.io/guides/getting-started/quick-start By the end of this guide, you will have a running Maverics Orchestrator connected to your identity provider with your first application route protected by single sign-on. ## Prerequisites * **A supported operating system** -- The Orchestrator runs on Linux, macOS, Windows, and in containers. See the [installation reference](/reference/orchestrator/installation) for full system requirements. * **An identity provider account** -- You need an account with an identity provider such as [Microsoft Entra ID](/reference/orchestrator/identity-fabric/azure-ad) or [Okta](/reference/orchestrator/identity-fabric/okta). This is the system your users log into today. * **A target application** -- Any web application running on a URL you can reach from the machine where the Orchestrator will run. ## Install and Configure The Maverics Orchestrator is a small, lightweight runtime that deploys almost anywhere -- on a virtual machine, in a container, or on bare metal. Installation takes just a few minutes. The Orchestrator sits between your users and your applications, handling authentication and identity routing so your apps do not have to. Think of it as an identity abstraction layer -- it authenticates users against your identity provider and then forwards authenticated requests to your upstream applications. 1. Log in to the [Maverics Console](https://maverics.strata.io) 2. Navigate to **Deployments** and create a new Deployment 3. Select a configuration storage provider (e.g., **No Cloud Storage Service Configured** for a quick start, or an S3/Azure/GCS bucket for production) 4. Open the **Download Orchestrator Software** modal 5. Download the installer for your platform and follow the platform-specific installation steps Download the Orchestrator binary from the [Maverics Console](https://maverics.strata.io). The Console provides platform-specific installers through the **Download Orchestrator Software** modal inside any Deployment. After downloading and extracting the binary for your platform: ```bash theme={null} # Verify the installation maverics -version ``` For a quick look at the available installation methods -- including Docker, Kubernetes, and direct install -- see the [Installation reference](/reference/orchestrator/installation). An identity provider (IdP) is the system that manages your user accounts and handles login -- services like Microsoft Entra ID (now called Microsoft Entra ID), Okta, or Google Workspace. Connecting the Orchestrator to your IdP tells it where to send users when they need to authenticate. The Orchestrator uses [Identity Fabric](/reference/orchestrator/identity-fabric) connectors to communicate with your IdP. Each connector handles the protocol details -- OIDC, SAML, or LDAP -- so you just need to provide your provider's credentials and endpoint information. 1. Navigate to **Identity Fabric** in the sidebar. 2. Click **Create**. 3. In the **Create Identity Fabric** dialog, search for and select your identity provider (e.g., **Microsoft Entra ID (OIDC)**). 4. Fill in the connector fields: | Field | Description | | ----------------------- | -------------------------------------------------------------------------------------- | | **Name** | A friendly name for this connector (e.g., `azure`). | | **OIDC Well Known URL** | Your provider's OpenID Connect discovery endpoint. | | **OAuth Client ID** | The client ID of the application registered in your identity provider. | | **OAuth Client Secret** | The corresponding client secret. | | **Redirect URLs** | The callback URL the Orchestrator will use (e.g., `https://app.example.com/callback`). | 5. Leave **PKCE** enabled (recommended) and configure optional fields like **Scopes** or **Logout Callback URLs** if needed. 6. Click **Save**. The dialog supports a wide range of providers including Okta, Auth0, Ping, LDAP, Active Directory, and more. Pick the connector that matches your identity provider's protocol. ```yaml theme={null} connectors: - name: azure type: azure oauthClientID: "{{ env.AZURE_CLIENT_ID }}" oauthClientSecret: oidcWellKnownURL: "https://login.microsoftonline.com/{{ env.AZURE_TENANT_ID }}/v2.0/.well-known/openid-configuration" oauthRedirectURL: "https://app.example.com/callback" ``` Replace the environment variable values with your Microsoft Entra ID tenant details. The `{{ env.VAR }}` syntax reads from environment variables. The `` syntax reads from your configured [secret provider](/reference/orchestrator/configuration/secret-providers). Not sure which connector to use? The [Identity Fabric overview](/reference/orchestrator/identity-fabric) has a comparison table that maps each connector to its supported protocols and use cases. An application route tells the Orchestrator which upstream application to protect and how to route traffic. When a user requests your application URL, the Orchestrator intercepts the request, authenticates the user against your IdP, and then forwards the authenticated request to your upstream service. This step connects the identity connector you just configured to a specific application -- creating the link between "who the user is" and "what they can access." 1. Navigate to **Applications** in the sidebar. 2. Click **Create**. 3. In the **Create a new Application** dialog, select **Proxied App**. 4. Fill in the application fields: | Field | Description | | ---------------- | ------------------------------------------------------------------------------------------------------------- | | **Name** | A friendly name for your application. | | **Upstream URL** | The URL of the application the Orchestrator will proxy traffic to (e.g., `https://internal-app.example.com`). | 5. Click **Save**. 6. In the application's settings, open the **Resources** card, click **Edit**, then click **Add Resource** and add your identity provider connector. A connector must be added as a resource before it can be used as an authentication source. 7. Find the **Access Control** card and click **Edit**. Add a policy with **Location** `/`, select your connector from the **Select an authentication source** dropdown, and choose **Allow all access** for the **Authorization method**. 8. Click **Save**, then publish your configuration. Route patterns, identity provider assignment, and authorization policies are configured on the application. The [Protect Your First Application](/guides/getting-started/first-application) guide covers this in more detail. ```yaml theme={null} apps: - name: my-application type: proxy upstream: "https://internal-app.example.com" routePatterns: - "app.example.com" policies: - location: "/" authentication: idps: ["azure"] authorization: allowAll: true ``` The `policies[].authentication.idps` array specifies which connectors handle authentication for this route. The `authorization.allowAll: true` allows any authenticated user. With the Orchestrator installed, your identity provider connected, and your application route defined, you are ready to start the Orchestrator and confirm everything works. Start the Orchestrator and check its health endpoint to verify it is running: ```bash theme={null} maverics -config /etc/maverics/maverics.yaml curl -s https://localhost:9443/status ``` The health endpoint returns a JSON response showing the status of the Orchestrator: ```json theme={null} { "status": "up" } ``` Next, open your application URL in a browser. You should be redirected to your identity provider's login page. After authenticating, you will be redirected back to your application -- now with a valid session managed by the Orchestrator. **Success!** Your Orchestrator is running and your first application route is protected with single sign-on. Users authenticate through your identity provider, and the Orchestrator manages the session lifecycle. To add session management and identity header injection to this route, continue to the [Protect Your First Application](/guides/getting-started/first-application) guide. ## Troubleshooting Check that the configuration file path is correct and that the file is valid YAML. The Orchestrator logs the specific parsing error on startup -- look for a line starting with `error` in the output. Common causes include indentation issues, missing required fields, or referencing a connector name that does not match the name in your connectors block. Verify that your IdP credentials (client ID, client secret, tenant ID) are correct and that the Orchestrator can reach your IdP's endpoints over the network. If you are using environment variables for secrets, confirm they are set in the shell where the Orchestrator is running. See the [secret providers reference](/reference/orchestrator/configuration/secret-providers) for alternative secret management options. A redirect loop usually means the callback URL configured in your identity provider does not match the Orchestrator's expected redirect URI. Double-check both sides. A 502 error means the Orchestrator cannot reach your upstream application -- verify the upstream URL is correct and the application is running. ## What's Next Add session management and header injection to your route Dive deeper into OpenID Connect single sign-on configuration and claim mapping # Overview Source: https://docs.strata.io/guides/identity-continuity/overview Identity Continuity ensures uninterrupted authentication by automatically routing users to a healthy identity provider when the primary becomes unavailable. Whether your cloud IdP has a regional failure, a network partition isolates your on-premises directory, or a provider pushes a breaking change, the Maverics Orchestrator detects the problem and switches traffic transparently -- no user action required. These guides cover configuring Identity Continuity from initial setup through advanced multi-tier high availability architectures. ## Guides Configure automatic IdP failover with health monitoring, Schema Abstraction Layer, and simulation testing Layer Identity Continuity configurations across deployment tiers to eliminate IdP single points of failure *** By the end of this guide, you will have a Maverics deployment that automatically fails over between identity providers when one becomes unavailable -- keeping your users authenticated without any service interruption. **Console terminology:** In the Maverics Console, Continuity is configured as a **Continuity Strategy** under **Identity Fabric**. In YAML, this maps to a connector with `type: continuity`. ## Why Identity Continuity? Unplanned identity provider outages can lock out every user in the organization. Whether your cloud IdP has a regional failure, a network partition isolates your on-premises directory, or a provider pushes a breaking change -- the result is the same: nobody can log in. Identity Continuity is a **high availability prevention system**, not a backup or recovery tool. It does not restore service after an outage -- it reduces the risk of an outage affecting users. The Orchestrator continuously monitors each identity provider's health and reroutes traffic to a healthy alternative before users ever see a login failure. Two primary use cases drive most Continuity deployments: * **Cloud IdP fails over to on-premises directory** -- Your primary cloud IdP (e.g., Okta, Entra ID) becomes unavailable, and the Orchestrator routes authentication to an on-premises LDAP or AD connector. * **Cloud IdP fails over to another cloud IdP** -- Your primary cloud IdP becomes unavailable, and the Orchestrator routes to a secondary cloud provider. Identity Continuity keeps authentication working when a provider goes down. If you need to **permanently migrate users** from one identity provider to another, see the [IdP Migration guide](/guides/authentication/idp-migration) instead. Architecture diagram showing Maverics Orchestrator routing authentication between multiple identity providers with health checks ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed the Orchestrator yet, follow the [Quick Start guide](/guides/getting-started/quick-start) or see the [installation reference](/reference/orchestrator/installation). * **At least two identity provider connectors configured** -- You need a primary and one or more backup identity providers. See the [Identity Fabric reference](/reference/orchestrator/identity-fabric) for supported providers and connector setup. * **User identities synced across identity providers** -- Your identity providers must already have the same user accounts provisioned. Failover to a backup IdP will fail if that IdP does not have the user's account. Typically this is handled by an Identity Governance and Administration (IGA) product or directory synchronization tool that keeps your identity stores in sync. * **A deployment configured** -- Your Orchestrator needs an active deployment with a configured storage provider. See the [Publishing Deployment Configs overview](/reference/console/config-publishing) for setup details. ## Configure Identity Continuity You need at least two identity services -- a primary that handles authentication under normal conditions and one or more backups that take over when the primary is unavailable. Each provider gets its own [Identity Fabric](/reference/orchestrator/identity-fabric) connector with independent credentials and configuration. 1. Navigate to **Identity Fabric** in the sidebar and click **Create**. 2. Select your primary provider type from the list (e.g., **Okta (OIDC)**, **Microsoft Entra ID (OIDC)**, or **Generic OIDC Configuration**). 3. Fill in the connector form with your primary IdP's credentials -- client ID, client secret, and discovery URL. 4. Click **Save**. 5. Repeat steps 1-4 for each backup identity provider. Name your connectors clearly (e.g., `primary-okta` and `backup-entra-id`) to make the failover order obvious when configuring the Continuity Strategy. Define both connectors in the `connectors` section. Each connector has its own credentials and discovery endpoint. ```yaml maverics.yaml theme={null} connectors: - name: primary-idp type: oidc oidcWellKnownURL: https://primary-idp.example.com/.well-known/openid-configuration oauthClientID: orchestrator-client oauthClientSecret: oauthLoginRedirect: urls: - https://your-orchestrator.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-orchestrator.example.com/logout scopes: openid profile email - name: backup-idp type: oidc oidcWellKnownURL: https://backup-idp.example.com/.well-known/openid-configuration oauthClientID: orchestrator-backup-client oauthClientSecret: oauthLoginRedirect: urls: - https://your-orchestrator.example.com/oidc-callback oauthLogoutRedirect: urls: - https://your-orchestrator.example.com/logout scopes: openid profile email ``` Name your connectors descriptively (e.g., `primary-okta` and `backup-entra-id`) so the failover order is clear when configuring the Continuity connector. The Orchestrator can maintain active connections to both providers simultaneously. Users authenticating against either provider will have a seamless experience. Health monitoring must be enabled on each **individual IdP connector**, not on the Continuity connector itself. The Orchestrator polls each IdP's health endpoint at a configurable interval and uses the results to decide when to trigger failover. 1. Open each identity service you configured in the previous step. 2. Scroll to **Identity Service Health Monitoring** and enable it. 3. Configure the health check settings: | Setting | Recommended (Testing) | Recommended (Production) | Description | | ------------------ | --------------------- | ------------------------ | ------------------------------------------------------------------------ | | Polling frequency | 10s | 30s-60s | How often the Orchestrator checks the IdP's health | | Timeout | 10s | 10s | How long to wait for a health check response before marking it as failed | | Failover threshold | 3 | 3 | Number of consecutive failures before triggering failover | | Fallback threshold | 3 | 3 | Number of consecutive successes before routing traffic back | 4. Optionally enable **Custom Health Check** for more granular control over what constitutes a healthy response. 5. Click **Save**. 6. Repeat for each identity service in your Continuity configuration. Add a `healthCheck` block to each connector that participates in the Continuity Strategy. ```yaml maverics.yaml theme={null} connectors: - name: primary-idp type: oidc oidcWellKnownURL: https://primary-idp.example.com/.well-known/openid-configuration oauthClientID: orchestrator-client oauthClientSecret: healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 3 ``` Repeat the `healthCheck` configuration for each connector in the failover list. For OIDC-based identity services, health checks automatically call the well-known endpoint and authorization server. For LDAP/AD services, health checks attempt a connection and bind. The Continuity Strategy is the component that orchestrates failover between your identity providers. It wraps your IdP connectors and adds routing logic based on health status. 1. Navigate to **Identity Fabric** in the sidebar and click **Create**. 2. Select **Continuity Strategy** from the list. 3. Enter a name for the strategy (e.g., `ha-failover`). 4. In the **Fallback Strategy** section, add your identity providers in priority order -- primary first, then backups. The dropdown lists only identity services you have already configured. Maverics Console showing the Continuity Strategy creation dialog with Name, Fallback Strategy, and Schema Abstraction Layer sections Add a connector with `type: continuity` that references your IdP connectors in the `failover.idps` array. The first entry is the primary; subsequent entries are fallbacks tried in order. ```yaml maverics.yaml theme={null} connectors: - name: ha-failover type: continuity strategy: failover failover: idps: - primary-idp - backup-idp ``` See the [Continuity connector reference](/reference/orchestrator/identity-fabric/continuity) for all available configuration fields. The Schema Abstraction Layer maps attributes from different IdPs to consistent names. When failover occurs, your applications receive the same attribute names regardless of which IdP authenticated the user. For example, one IdP might call the email attribute `preferred_username` while another calls it `mail`. The Schema Abstraction Layer normalizes both to a single attribute name (e.g., `email`) that your applications can rely on. Diagram showing how Maverics normalizes attribute names across Okta and Microsoft Entra ID to consistent values 1. In the Continuity Strategy configuration, scroll to the **Schema Abstraction Layer** section. 2. For each attribute your applications need (e.g., email, name, role), click to add a row. 3. Enter the normalized attribute **Name** (what your applications will see). 4. Map it to the corresponding claim name from each identity service. 5. Optionally set a **Default** value for cases where the attribute is unavailable from any IdP. 6. Click **Save**. Schema Abstraction Layer configuration showing attribute mapping across identity providers Add an `attributes` section to the Continuity connector. Each entry maps a normalized name to the corresponding attribute name from each IdP. ```yaml maverics.yaml theme={null} connectors: - name: ha-failover type: continuity strategy: failover failover: idps: - primary-idp - backup-idp attributes: - name: email mapping: primary-idp: preferred_username backup-idp: mail - name: displayName mapping: primary-idp: name backup-idp: displayName ``` Update your application configuration to use the Continuity Strategy as its authentication provider instead of a specific IdP connector. This is the same binding pattern used in other authentication guides -- the only difference is that you reference the Continuity Strategy instead of an individual IdP. 1. Open your application's settings. 2. In the **Resources** card, click **Edit**, click **Add Resource**, and add your Continuity Strategy. A resource must be added before it can be selected as an authentication source. 3. In the **Access Control** card, select the Continuity Strategy from the **Select an authentication source** dropdown. 4. For headers or claims, update the source to the Continuity Strategy and select attributes from the Schema Abstraction Layer. 5. Click **Publish Preview** to review changes, then click **Publish** to deploy. For all application types, the Continuity Strategy is selected from the **Select an authentication source** dropdown on the **Access Control** card. For proxy applications, add it within an access control policy. Update the `authentication.idps` array in your application definition to reference the Continuity connector. Use the Schema Abstraction Layer attribute names in `claimsMapping`. ```yaml maverics.yaml theme={null} apps: - name: my-app type: oidc clientID: my-app authentication: idps: - ha-failover claimsMapping: email: ha-failover.email name: ha-failover.displayName ``` The `claimsMapping` references the Continuity connector's normalized attribute names -- not the individual IdP connectors. This ensures your application receives consistent claims regardless of which IdP authenticated the user. The Orchestrator handles **protocol translation** automatically. Your application does not need to support the same protocol as your identity providers. For example, an OIDC application can authenticate users through a SAML or LDAP identity provider -- the Orchestrator translates between protocols transparently. The Maverics Console includes a simulation feature that lets you test failover behavior without waiting for a real outage. When publishing changes, you can enable simulation to cycle through test phases automatically. 1. When publishing your configuration, toggle **Simulate Continuity Strategy**. 2. Set a time interval for the simulation cycle (e.g., 60 seconds per phase). 3. Click **Publish** to deploy with simulation enabled. The simulation cycles through test phases automatically. During each phase, open an **incognito/private browser window**, navigate to your application URL, and verify the correct IdP login page appears. Simulation mode is only available through the Console UI publish flow. When using direct configuration, you can test failover manually by stopping the primary IdP's service or blocking its health check endpoint, then verifying that authentication routes to the backup IdP. Timeline showing Continuity simulation test phases: primary, failover to secondary, tertiary, fallback The simulation runs through these phases: 1. **Test primary** -- Authenticate using your primary IdP credentials. Verify login works normally. 2. **Test failover to secondary** -- The primary appears unavailable. Open an incognito window, go to your app URL, and verify the login redirects to your secondary (backup) IdP. 3. **Test tertiary** (if configured) -- The secondary also appears unavailable. Verify failover to the third IdP. 4. **Test fallback** -- The secondary comes back online. Verify traffic routes back to the secondary. 5. **Test fallback to primary** -- The primary comes back online. Verify traffic routes back to the primary. For each phase, use a fresh incognito window to avoid cached sessions interfering with the test. Your Maverics Orchestrator is automatically routing authentication between your identity providers based on health status. ## Troubleshooting Check the Orchestrator's debug logs for health check messages. Look for log entries like: ``` level=debug msg="idp health check failed: well-known metadata unavailable" ``` Common causes: * The well-known endpoint or LDAP server is not reachable from the Orchestrator's network. * The `unhealthyThreshold` has not been reached yet -- the Orchestrator requires the configured number of consecutive failures before triggering failover. * Health monitoring is not enabled on the individual IdP connectors (health checks are configured on each connector, not on the Continuity connector itself). Verify the Schema Abstraction Layer mappings cover all attributes your application needs. Each IdP may use different claim names for the same data (e.g., `email` vs `mail` vs `preferred_username`). Check that `attributes[].mapping` entries exist for **every** IdP listed in the `failover.idps` array. If a mapping is missing for an IdP, the attribute will be empty when that IdP handles authentication. Simulation mode is only available through the Console UI publish flow. Verify that you: 1. Toggled the **Simulate Continuity Strategy** switch before publishing. 2. Set a time interval for the simulation cycle. 3. Published the configuration after enabling simulation. Check the Orchestrator logs for simulation-related messages. If you are using direct configuration (YAML), simulation mode is not available -- test failover manually by making the primary IdP's health check endpoint unreachable. Verify that `healthyThreshold` is configured on the individual IdP connectors. The Orchestrator requires the configured number of consecutive healthy checks before routing traffic back to a recovered IdP. Also check: * The health check `interval` -- enough time must pass for the required number of healthy checks to accumulate. * The recovered IdP's health check endpoint is actually responding successfully. * The Orchestrator logs show health check success messages for the recovered IdP. ## Related Pages Complete configuration reference for the Continuity connector -- failover, routing, and attribute normalization settings Migrate between identity providers with zero downtime using the same Continuity connector Supported identity providers and connector configuration for Microsoft Entra ID, Okta, Auth0, and more Session management, invalidation, and storage options for the Orchestrator # Reducing Single Points of Failure Source: https://docs.strata.io/guides/identity-continuity/reducing-spofs The most common question reliability architects ask about the Orchestrator is: **"Isn't it a single point of failure?"** The short answer is no -- the Orchestrator scales horizontally behind a load balancer (see the [Scale for Production guide](/guides/operations/scale)). If one instance goes down, the others continue serving traffic and users are transparently re-authenticated. But scaling the Orchestrator itself only solves half the problem. Your **identity providers** can still be single points of failure. If your sole IdP goes down, it does not matter how many Orchestrator instances you have -- nobody can authenticate. [Identity Continuity](/reference/orchestrator/identity-fabric/continuity) is how you address that: the Orchestrator monitors IdP health and automatically fails over to a backup when an outage is detected. This guide presents a tiered approach to Identity Continuity. Each tier adds resilience against progressively more severe failure scenarios. Choose the tier that matches your risk tolerance. ## Understanding Failure Modes Before choosing a tier, understand what can go wrong: | Failure mode | Example | Impact | | ------------------------------ | ------------------------------------------------------ | ------------------------------------------------------------------------- | | **Single IdP outage** | Unplanned incident, scheduled maintenance window | Users who authenticate through that IdP cannot log in | | **Vendor-wide outage** | An entire IdP vendor's service is unavailable | Every application relying on that vendor is affected | | **Regional network partition** | Orchestrator in US-East cannot reach IdPs in EU-West | Users at affected sites cannot authenticate, even if the IdPs are healthy | | **Multi-provider outage** | Two or more IdP vendors are unavailable simultaneously | Rare but catastrophic -- all failover targets are unavailable | ## Tier 1: Basic Continuity **Protects against:** Single IdP outage The simplest configuration: one [Continuity connector](/reference/orchestrator/identity-fabric/continuity) with a primary IdP and one backup. If the primary goes down, the Orchestrator automatically routes authentication to the backup. ```yaml maverics.yaml theme={null} connectors: - name: primary-idp type: oidc oidcWellKnownURL: https://primary.example.com/.well-known/openid-configuration oauthClientID: orchestrator-client oauthClientSecret: oauthRedirectURL: https://orch.example.com/oidc/callback scopes: openid profile email healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 2 - name: backup-idp type: oidc oidcWellKnownURL: https://backup.example.com/.well-known/openid-configuration oauthClientID: orchestrator-backup-client oauthClientSecret: oauthRedirectURL: https://orch.example.com/oidc/callback scopes: openid profile email healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 2 - name: ha-failover type: continuity strategy: failover failover: idps: - primary-idp - backup-idp ``` **Limitation:** If both IdPs are from the same vendor or hosted in the same region, a vendor-wide or regional outage takes both down simultaneously. Tier 2 addresses this. For a full walkthrough of setting up Continuity with health monitoring and the Schema Abstraction Layer, see the [Identity Continuity setup guide](/guides/identity-continuity/overview). ## Tier 2: Diversified Continuity **Protects against:** Vendor-specific outage, regional outage Tier 2 applies a single principle: **diversity**. Add three or more IdPs from different vendors, deployed in different regions, using different protocols. A vendor-wide outage or regional network partition only takes out one link in the chain. ```yaml maverics.yaml theme={null} connectors: # Cloud IdP - Vendor A (US region) - name: okta-idp type: oidc oidcWellKnownURL: https://corp.okta.com/.well-known/openid-configuration oauthClientID: orchestrator-client oauthClientSecret: oauthRedirectURL: https://orch.example.com/oidc/callback scopes: openid profile email healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 2 # Cloud IdP - Vendor B (EU region) - name: entra-idp type: saml samlMetadataURL: https://login.microsoftonline.com/TENANT/federationmetadata/2007-06/federationmetadata.xml samlConsumerServiceURL: https://orch.example.com/saml/callback samlEntityID: https://orch.example.com healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 2 # On-premises IdP - different network path entirely - name: onprem-ldap type: ldap url: ldaps://dc.corp.example.com:636 baseDN: dc=corp,dc=example,dc=com bindDN: cn=svc-maverics,ou=service-accounts,dc=corp,dc=example,dc=com bindPassword: healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 2 - name: diversified-failover type: continuity strategy: failover failover: idps: - okta-idp - entra-idp - onprem-ldap # The Schema Abstraction Layer normalizes attributes across # providers so downstream apps see consistent claim names # regardless of which IdP authenticated the user. attributes: - name: email mapping: okta-idp: email entra-idp: preferred_username onprem-ldap: mail - name: displayName mapping: okta-idp: name entra-idp: displayName onprem-ldap: cn - name: role mapping: okta-idp: role entra-idp: group default: "user" ``` The key decisions in this tier: * **Different vendors** -- Okta and Entra ID are independent services. A vendor-specific incident only affects one. * **Different regions** -- Cloud IdPs in US and EU, plus an on-premises LDAP server. A regional network partition cannot take all three offline. * **Different protocols** -- OIDC, SAML, and LDAP. A protocol-specific bug or misconfiguration is contained to one connector. * **Schema Abstraction Layer** -- The `attributes` block normalizes claim names so your applications see `email`, `displayName`, and `role` regardless of which IdP responded. Without this, failover would break applications that depend on specific claim names. Health monitoring is configured on each **individual IdP connector**, not on the Continuity connector. The Continuity connector reads health status from its member connectors to make routing decisions. See the [Identity Continuity reference](/reference/orchestrator/identity-fabric/continuity) for the full health check configuration. ## Tier 3: Cascading Continuity **Protects against:** Regional isolation, near-total IdP infrastructure failure Tier 3 introduces **Orchestrator-to-Orchestrator federation**. Instead of every Orchestrator instance connecting directly to every IdP, you create a two-layer architecture: * **Root Orchestrators** in primary data centers connect directly to the actual IdPs via Continuity. They run as [OIDC Providers](/reference/modes/oidc-provider) or [SAML Providers](/reference/modes/saml-provider), acting as a stable identity endpoint. * **Edge Orchestrators** in secondary regions or branch offices use [Generic OIDC](/reference/orchestrator/identity-fabric/custom-oidc) or [Generic SAML](/reference/orchestrator/identity-fabric/custom-saml) connectors pointed at the root Orchestrators. They use Continuity to fail over between multiple root Orchestrators. ```mermaid theme={null} %%{init: {'theme': 'neutral', 'themeVariables': {'edgeWidth': 4}}}%% flowchart TB subgraph IdPs["Identity Providers"] Okta["Okta (Vendor A)"] Entra["Entra ID (Vendor B)"] end subgraph Roots["Root Orchestrators — Continuity failover across IdPs"] RootDC1["Root Orch (DC1)
OIDC Provider"] RootDC2["Root Orch (DC2)
OIDC Provider"] RootN["Root Orch (N...)
OIDC Provider"] end subgraph Edge["Edge Orchestrators — Continuity failover across roots"] EdgeA["Edge Orch (Branch A)"] EdgeB["Edge Orch (Branch B)"] EdgeC["Edge Orch (Branch C)"] end Okta --> RootDC1 Okta --> RootDC2 Okta --> RootN Entra --> RootDC1 Entra --> RootDC2 Entra --> RootN RootDC1 --> EdgeA RootDC1 --> EdgeB RootDC1 --> EdgeC RootDC2 --> EdgeA RootDC2 --> EdgeB RootDC2 --> EdgeC RootN --> EdgeA RootN --> EdgeB RootN --> EdgeC classDef orch stroke:#6A3EC8,stroke-width:6px class RootDC1,RootDC2,RootN,EdgeA,EdgeB,EdgeC orch ``` Only root Orchestrators need direct IdP credentials and configurations. Edge sites treat the root Orchestrators as their identity providers. If an edge site loses connectivity to one root, it fails over to another. If all roots are unreachable (full regional isolation), only that edge site is affected -- other edge sites continue operating through whichever root they can reach. ### Root Orchestrator Configuration Root Orchestrators connect directly to your IdPs via Continuity and expose an OIDC Provider endpoint that edge Orchestrators authenticate against. ```yaml root-orch.yaml theme={null} connectors: - name: okta-idp type: oidc oidcWellKnownURL: https://corp.okta.com/.well-known/openid-configuration oauthClientID: orchestrator-client oauthClientSecret: oauthRedirectURL: https://root-dc1.example.com/oidc/callback scopes: openid profile email healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 2 - name: entra-idp type: saml samlMetadataURL: https://login.microsoftonline.com/TENANT/federationmetadata/2007-06/federationmetadata.xml samlConsumerServiceURL: https://root-dc1.example.com/saml/callback samlEntityID: https://root-dc1.example.com healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 2 - name: root-failover type: continuity strategy: failover failover: idps: - okta-idp - entra-idp attributes: - name: email mapping: okta-idp: email entra-idp: preferred_username - name: displayName mapping: okta-idp: name entra-idp: displayName # Expose this Orchestrator as an OIDC Provider so edge # Orchestrators can authenticate against it. oidcProvider: discovery: issuer: https://root-dc1.example.com jwks: - name: signing-key type: rsa file: /etc/maverics/keys/signing.key apps: - name: edge-app type: oidc clientID: edge-orchestrator clientSecret: authentication: idps: - root-failover claimsMapping: email: root-failover.email name: root-failover.displayName ``` ### Edge Orchestrator Configuration Edge Orchestrators treat root Orchestrators as IdPs using Generic OIDC connectors, with Continuity providing failover between roots. ```yaml edge-orch.yaml theme={null} connectors: # Root Orchestrator in DC1, treated as an OIDC IdP - name: root-dc1 type: oidc oidcWellKnownURL: https://root-dc1.example.com/.well-known/openid-configuration oauthClientID: edge-orchestrator oauthClientSecret: oauthRedirectURL: https://edge-branch-a.example.com/oidc/callback scopes: openid profile email healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 2 # Root Orchestrator in DC2, treated as an OIDC IdP - name: root-dc2 type: oidc oidcWellKnownURL: https://root-dc2.example.com/.well-known/openid-configuration oauthClientID: edge-orchestrator oauthClientSecret: oauthRedirectURL: https://edge-branch-a.example.com/oidc/callback scopes: openid profile email healthCheck: enabled: true interval: 30s timeout: 10s unhealthyThreshold: 3 healthyThreshold: 2 - name: edge-failover type: continuity strategy: failover failover: idps: - root-dc1 - root-dc2 # Edge Orchestrator serves local applications. # Configure apps here using the edge-failover connector. apps: - name: branch-app type: oidc clientID: branch-app authentication: idps: - edge-failover claimsMapping: email: edge-failover.email name: edge-failover.name ``` Since root Orchestrators already normalize attributes via their Schema Abstraction Layer, edge Orchestrators receive consistent claims regardless of which root (or underlying IdP) handled authentication. You only need Schema Abstraction Layer mappings at the edge if the two root Orchestrators emit different claim names. ## Tier 4: Tactical Edge Continuity **Protects against:** Total connectivity loss (DDIL -- Denied, Degraded, Intermittent, or Limited) Tiers 1-3 assume that at least one upstream IdP is reachable at all times. Tactical and field deployments break that assumption. In DDIL environments -- forward-deployed operations, remote industrial sites, shipboard networks, or disaster-response staging areas -- connectivity to cloud identity providers can be intermittent or severed entirely. Tier 4 addresses this with a **co-located on-premises IdP** (such as Keycloak) deployed alongside the tactical Orchestrator on the same local network segment. When cloud connectivity is available, the Orchestrator routes authentication to the cloud IdP normally. When connectivity is lost, the Orchestrator detects the failure and falls back to the local IdP autonomously -- no operator intervention required. ```mermaid theme={null} %%{init: {'theme': 'neutral', 'themeVariables': {'edgeWidth': 4}}}%% flowchart TB subgraph Cloud["Cloud Identity Providers"] Okta["Okta"] Entra["Entra ID"] end subgraph Tactical["Tactical Deployment (Local Network)"] TactOrch["Tactical Orchestrator"] LocalIdP["Keycloak"] end Okta -. "intermittent connectivity" .-> TactOrch Entra -. "intermittent connectivity" .-> TactOrch LocalIdP -- "always available" --> TactOrch classDef orch stroke:#6A3EC8,stroke-width:6px classDef local stroke:#2E7D32,stroke-width:4px class TactOrch orch class LocalIdP local ``` ```yaml tactical-orch.yaml theme={null} connectors: # Cloud IdP -- preferred when connectivity is available - name: cloud-idp type: oidc oidcWellKnownURL: https://corp.okta.com/.well-known/openid-configuration oauthClientID: tactical-client oauthClientSecret: oauthRedirectURL: https://tactical-orch.local/oidc/callback scopes: openid profile email healthCheck: enabled: true interval: 10s timeout: 5s unhealthyThreshold: 2 healthyThreshold: 3 # Co-located Keycloak -- always reachable on the local network - name: local-keycloak type: oidc oidcWellKnownURL: https://keycloak.local/realms/tactical/.well-known/openid-configuration oauthClientID: tactical-client oauthClientSecret: oauthRedirectURL: https://tactical-orch.local/oidc/callback scopes: openid profile email healthCheck: enabled: true interval: 10s timeout: 5s unhealthyThreshold: 2 healthyThreshold: 2 - name: tactical-failover type: continuity strategy: failover failover: idps: - cloud-idp - local-keycloak # Schema Abstraction Layer ensures apps see consistent attributes whether the user # authenticated against the cloud IdP or local Keycloak. attributes: - name: email mapping: cloud-idp: email local-keycloak: email - name: displayName mapping: cloud-idp: name local-keycloak: preferred_username - name: role mapping: cloud-idp: role local-keycloak: realm_access.roles default: "user" ``` Key design decisions for tactical deployments: * **Aggressive health check intervals** -- The `interval: 10s` and `unhealthyThreshold: 2` configuration detects connectivity loss in as little as 20 seconds. Standard deployments use 30-second intervals and a threshold of 3 (90 seconds to detect). In DDIL environments, fast detection is critical because users cannot wait minutes for the system to recognize that the cloud is unreachable. * **Co-located on the same network segment** -- The local IdP or directory must be reachable without traversing any WAN link. If the local IdP depends on the same network path as the cloud, it will fail at the same time. * **Schema Abstraction Layer bridges the gap** -- Cloud IdPs and on-premises IdPs rarely use the same attribute names. The Schema Abstraction Layer ensures applications see `email`, `displayName`, and `role` regardless of whether Okta or local Keycloak responded. * **Automatic recovery** -- When cloud connectivity restores, the Orchestrator's health checks detect the cloud IdP as healthy again and automatically route traffic back. No manual switchover is required. ## Choosing the Right Tier | | Tier 1: Basic | Tier 2: Diversified | Tier 3: Cascading | Tier 4: Tactical Edge | | ----------------------------- | --------------------------------- | --------------------------------------- | ----------------------------------------------- | --------------------------------------------- | | **Protects against** | Single IdP outage | Vendor or regional outage | Regional isolation, near-total failure | Total connectivity loss (DDIL) | | **Number of IdPs** | 2 | 3+ | 3+ (at root), 2+ roots (at edge) | 1+ cloud, 1+ local | | **Vendor diversity** | Optional | Required | Required at root layer | Required (cloud + on-prem) | | **IdP credentials needed at** | Every Orchestrator | Every Orchestrator | Root Orchestrators only | Tactical Orchestrator (both cloud and local) | | **Configuration complexity** | Low | Medium | High | Medium-High | | **Best for** | Most organizations, internal apps | Regulated workloads, SLA-bound services | Global deployments, zero-tolerance environments | Tactical/field deployments, DDIL environments | **Start simple.** Most organizations begin at Tier 1 -- a primary IdP with a single backup handles the vast majority of outage scenarios. Move to Tier 2 when you need protection against vendor-wide incidents or have compliance requirements for vendor diversity. Tier 3 is for global deployments where regional isolation is a realistic threat and downtime tolerance is near zero. Tier 4 is purpose-built for tactical and field deployments where cloud connectivity cannot be guaranteed -- DDIL environments, disconnected operations, and forward-deployed sites. ## Custom Health Checks and Manual Failover The default health check polls each IdP automatically, but you are not limited to automatic detection. [Custom health check endpoints](/reference/orchestrator/identity-fabric/continuity#custom-health-check-fields) let you point the Orchestrator at any URL and define what a healthy response looks like -- specific status codes, expected response body values, or custom headers. This opens up scenarios beyond automatic IdP monitoring: * **Manual failover** -- Stand up a simple internal endpoint (e.g., `/idp-status`) that your operations team controls. Flipping that endpoint to return a non-healthy status forces the Orchestrator to fail over immediately, without waiting for the IdP to actually go down. Useful for planned maintenance windows or preemptive action. * **External monitoring signals** -- Wire the custom endpoint to your existing monitoring infrastructure (SIEM, network monitoring, threat detection). If your SOC detects that an IdP has been compromised or a network path is degraded, the monitoring system can flip the health endpoint and trigger failover before users are impacted. * **Composite health** -- Build a health endpoint that aggregates multiple signals -- network latency, certificate expiry, IdP vendor status pages -- into a single healthy/unhealthy decision. The Orchestrator doesn't need to understand each signal; it just needs a status code. ```yaml maverics.yaml theme={null} connectors: - name: primary-idp type: oidc oidcWellKnownURL: https://corp.okta.com/.well-known/openid-configuration oauthClientID: orchestrator-client oauthClientSecret: healthCheck: enabled: true interval: 10s timeout: 5s unhealthyThreshold: 2 healthyThreshold: 3 customEndpoint: type: http endpoint: https://internal-monitoring.example.com/idp-status/okta responseMatcher: expectedStatuses: [200] body: contains: "healthy" ``` With this configuration, the Orchestrator checks `https://internal-monitoring.example.com/idp-status/okta` instead of the IdP's well-known endpoint. If that endpoint returns anything other than a `200` with `"healthy"` in the body, failover begins. ## Supporting Infrastructure Identity Continuity handles the authentication layer, but a production HA deployment also depends on infrastructure outside the Orchestrator: * **Global load balancers or GeoDNS** -- Route users to the nearest healthy Orchestrator instances. Required for Tier 3 to direct edge traffic to the closest root. * **Health check integration** -- Your load balancer should poll each Orchestrator's `/status` endpoint and remove unhealthy instances from the pool. See the [Scale for Production guide](/guides/operations/scale) for load balancer configuration examples. * **Network path diversity** -- If all your IdP connections traverse the same network link, a single link failure defeats the purpose of multiple IdPs. Ensure root Orchestrators have diverse network paths to their upstream IdPs. * **Monitoring and alerting** -- Configure alerts on Continuity failover events so your team knows when a backup IdP is actively handling traffic. See the [Monitor and Observe guide](/guides/operations/monitor) for telemetry configuration. ## Related Pages Step-by-step guide to configuring your first Continuity connector with health monitoring Full configuration reference for the Continuity connector, health checks, and Schema Abstraction Layer Scale horizontally with sticky sessions, local session storage, and load balancer configuration Deploy with CLI flags, Docker or systemd, secret provider configuration, and health probes # Deploy to Production Source: https://docs.strata.io/guides/operations/deploy By the end of this guide, you will have a production-ready Maverics Orchestrator deployment with environment-specific configuration, health monitoring, and automated restarts. This guide focuses on production deployment -- not installation. If you have not yet installed the Orchestrator, start with the [installation reference](/reference/orchestrator/installation) for system requirements and platform options. This guide picks up where installation leaves off, covering the production-specific concerns that matter when real users depend on your deployment. **Console terminology:** In the Maverics Console, Orchestrator instances and configuration delivery are managed through **Deployments**. When working directly with YAML, configuration is managed as files delivered via the `-config` flag or `MAVERICS_CONFIG` environment variable. ## Prerequisites * **The Orchestrator installed** -- See the [installation reference](/reference/orchestrator/installation) for system requirements and installation methods. * **A working configuration file** -- You should have a YAML configuration that works in development. See the [configuration reference](/reference/orchestrator/configuration) for config file structure. * **A target environment** -- Docker, Kubernetes, a Linux/macOS host, or a Windows server where the Orchestrator will run. ## Deploy to Production Production configuration differs from development in a few important ways. In development, you might hardcode secrets and use default ports. In production, you want secrets managed externally, environment-specific values injected at runtime, and explicit resource boundaries. The Orchestrator supports environment variable substitution in YAML configuration -- so you can keep a single config file and vary behavior per environment. For secrets like IdP client credentials and TLS certificates, use an external [secret provider](/reference/orchestrator/configuration/secret-providers) instead of putting values directly in your config file. Key production configuration concerns: * **Secrets** -- Use a [secret provider](/reference/orchestrator/configuration/secret-providers) (HashiCorp Vault, AWS Secrets Manager, Azure Key Vault) instead of plaintext values * **External config sources** -- Pull configuration from a [config source](/reference/orchestrator/configuration/config-sources) for centralized management across multiple Orchestrator instances * **TLS** -- Enable TLS termination at the Orchestrator or ensure your load balancer handles it. See the [Transport Layer Security (TLS) Reference](/reference/orchestrator/tls-security) * **Logging** -- Set log level to `info` or `warn` for production (not `debug`). See the [Monitor guide](/guides/operations/monitor) for full observability setup **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Production configuration panel in Maverics Console showing environment variables and secret provider settings A minimal production `maverics.yaml` uses environment variable substitution for environment-specific values and secret references for sensitive data: ```yaml maverics.yaml theme={null} version: "1" http: address: "{{ env.MAVERICS_HTTP_ADDRESS }}" tls: "default" tls: "default": certFile: "{{ env.TLS_CERT_PATH }}" keyFile: "{{ env.TLS_KEY_PATH }}" minVersion: "1.2" logger: level: "info" jsonOutput: true health: location: "/status" heartbeat: interval: "60s" connectors: - name: my-idp type: oidc oauthClientID: "{{ env.OIDC_CLIENT_ID }}" oauthClientSecret: oidcWellKnownURL: "{{ env.OIDC_WELL_KNOWN_URL }}" apps: - name: my-app type: proxy upstream: "{{ env.APP_UPSTREAM_URL }}" routePatterns: - "{{ env.APP_ROUTE_PATTERN }}" policies: - location: "/" authentication: idps: ["my-idp"] ``` Use `{{ env.VAR }}` for values that change between environments (addresses, URLs, non-sensitive IDs). Use `` for secrets that should be retrieved from a secret provider at runtime. See [Configuration Reference](/reference/orchestrator/configuration) for complete config file structure. Keep your production configuration in version control -- but use environment variable references for anything sensitive. This way your config file is auditable without exposing secrets. Secret providers are configured via the `MAVERICS_SECRET_PROVIDER` environment variable or the `-secretProvider` CLI flag -- not in YAML. Only one secret provider may be active at a time. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Secret provider configuration in Maverics Console Secret providers are configured via environment variable or CLI flag, not in YAML configuration. The examples below show shell commands for setting up each provider type. ```bash theme={null} # HashiCorp Vault export MAVERICS_SECRET_PROVIDER="hashivault://vault.example.com:8200/secret/data/maverics?token=" # AWS Secrets Manager export MAVERICS_SECRET_PROVIDER="awssecretsmanager://us-east-1" # Azure Key Vault export MAVERICS_SECRET_PROVIDER="azurekeyvault://my-vault.vault.azure.net" # Secret File (development only) export MAVERICS_SECRET_PROVIDER="secretfile:////etc/maverics/secrets.json" ``` Once configured, reference secrets in YAML using angle bracket syntax: ```yaml theme={null} oauthClientSecret: ``` See [Secret Providers Reference](/reference/orchestrator/configuration/secret-providers) for all 7 provider types and their URL schemes. The Orchestrator is small and lightweight -- it deploys almost anywhere. Choose the deployment model that matches your infrastructure. **Docker deployment** is the simplest path to production. Mount your configuration file and any TLS certificates, expose the Orchestrator's listening port, and set environment variables for secrets. **Kubernetes deployment** is ideal for teams already running workloads on Kubernetes. The Orchestrator runs as a Deployment with a Service, and you configure it through ConfigMaps (for YAML configuration) and Secrets (for credentials). Kubernetes also gives you built-in health check integration, rolling updates, and automatic restarts. Strata provides an [official Helm chart](https://github.com/strata-io/helm-charts) for streamlined Kubernetes installation. **Windows deployment** is supported via the MSI installer, which registers the Orchestrator as a Windows service with automatic startup. The installer provides a guided setup for configuration source, TLS certificates, and environment variables. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Deployment wizard in Maverics Console showing Docker and Kubernetes deployment options **CLI invocation** -- The Orchestrator accepts the following flags: ```bash theme={null} maverics \ -config /etc/maverics/maverics.yaml \ -secretProvider "hashivault://vault.example.com:8200/secret/data/maverics?token=" ``` Available CLI flags: | Flag | Description | | ----------------- | ----------------------------------------------------------------------- | | `-config` | Path to YAML configuration file (required) | | `-secretProvider` | Secret provider URL (alternative to `MAVERICS_SECRET_PROVIDER` env var) | | `-version` | Print version and exit | | `-verbose` | Enable debug-level logging | **Docker deployment:** ```bash theme={null} docker run -d \ --name maverics \ -p 9443:9443 \ -v /etc/maverics/maverics.yaml:/etc/maverics/maverics.yaml:ro \ -v /etc/maverics/certs:/etc/maverics/certs:ro \ -e MAVERICS_SECRET_PROVIDER="hashivault://vault.example.com:8200/secret/data/maverics?token=" \ -e MAVERICS_HTTP_ADDRESS="0.0.0.0:9443" \ maverics-orchestrator \ -config /etc/maverics/maverics.yaml ``` **systemd deployment:** ```ini theme={null} # /etc/systemd/system/maverics.service [Unit] Description=Maverics Orchestrator After=network-online.target Wants=network-online.target [Service] Type=simple ExecStart=/usr/local/bin/maverics -config /etc/maverics/maverics.yaml EnvironmentFile=/etc/maverics/env Restart=always RestartSec=5 [Install] WantedBy=multi-user.target ``` ```bash theme={null} # /etc/maverics/env MAVERICS_SECRET_PROVIDER=hashivault://vault.example.com:8200/secret/data/maverics?token= MAVERICS_HTTP_ADDRESS=0.0.0.0:9443 TLS_CERT_PATH=/etc/maverics/certs/server.pem TLS_KEY_PATH=/etc/maverics/certs/server-key.pem ``` Whichever deployment model you choose, the Orchestrator behaves the same way. The only differences are how you deliver the configuration file and how you manage the process lifecycle (restarts, scaling, health checks). The Orchestrator exposes a health endpoint that reports its operational status -- whether it has started successfully and is ready to handle traffic. In production, you should configure your infrastructure to poll this endpoint and take action when the Orchestrator is unhealthy. The status endpoint returns a JSON response indicating the Orchestrator's operational state. Your load balancer, container orchestrator, or process manager can use this endpoint to: * **Route traffic only to healthy instances** -- Remove unhealthy instances from the load balancer pool * **Restart failed instances** -- Kubernetes liveness probes and Docker restart policies use health checks to detect and recover from failures automatically * **Block traffic during startup** -- Readiness probes prevent traffic from reaching an instance before it has finished initializing ```bash theme={null} # Check the status endpoint curl -s https://localhost:9443/status | jq . ``` ```json theme={null} { "status": "up" } ``` **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Health check settings in Maverics Console showing endpoint configuration and probe intervals Configure the health endpoint path and heartbeat monitoring: ```yaml maverics.yaml theme={null} health: location: "/status" heartbeat: disabled: false logLevel: "info" interval: "60s" ``` **Kubernetes probes** using the health endpoint: ```yaml theme={null} # Kubernetes deployment snippet livenessProbe: httpGet: path: /status port: 9443 scheme: HTTPS initialDelaySeconds: 10 periodSeconds: 15 readinessProbe: httpGet: path: /status port: 9443 scheme: HTTPS initialDelaySeconds: 5 periodSeconds: 10 ``` **Docker health check:** ```bash theme={null} docker run -d \ --health-cmd="curl -kf https://localhost:9443/status || exit 1" \ --health-interval=15s \ --health-timeout=5s \ --health-retries=3 \ # ... rest of docker run command ``` With the Orchestrator deployed and health checks configured, verify that everything is working end-to-end. Start by confirming the health endpoint returns a healthy status, then test the full authentication flow. ```bash theme={null} # Verify status curl -s https://your-orchestrator-host:9443/status | jq . # Check that the Orchestrator is serving traffic curl -I https://your-orchestrator-host:9443/ ``` Walk through the full user flow to confirm end-to-end functionality: 1. **Visit a protected URL** -- You should be redirected to your identity provider 2. **Authenticate** -- Log in with valid credentials 3. **Verify redirect** -- After authentication, you should land on your protected application 4. **Check logs** -- Confirm the Orchestrator logged the authentication event **Success!** Your Orchestrator is deployed in production with environment-specific configuration, health monitoring, and automated restarts. The health endpoint reports a healthy status, and the full authentication flow works end-to-end. ## Troubleshooting Check the Orchestrator's startup logs for the specific error. The most common causes are: * **Invalid YAML** -- Indentation errors, missing colons, or unclosed quotes. Run your config through a YAML validator. * **Missing required fields** -- The Orchestrator validates its configuration on startup and logs which fields are missing. * **Port conflict** -- Another process is already using the configured listening port. Check with `lsof -i :8080` or change the port in your configuration. * **Permission denied** -- The Orchestrator process does not have permission to read the config file, TLS certificates, or bind to the configured port. If you are using an external [config source](/reference/orchestrator/configuration/config-sources), verify that: * The config source credentials are correct and the Orchestrator can reach the external service over the network * The config source path or key matches what the Orchestrator expects * Environment variables referenced in the configuration are set in the Orchestrator's runtime environment (not just your local shell) Enable `debug` logging temporarily to see the exact config source requests and responses. An unhealthy status usually means one or more connectors failed to initialize. Check the Orchestrator's logs for startup errors. If the health endpoint times out entirely, the Orchestrator may not be listening on the expected port. Verify the port configuration and check that no firewall rules are blocking access to the health endpoint. ## Related Pages Back to the Operations guides hub Full reference for configuration file structure, environment variables, and runtime settings Scale your deployment horizontally with sticky sessions and Redis caching # Monitor and Observe Source: https://docs.strata.io/guides/operations/monitor By the end of this guide, you will have a fully instrumented Maverics Orchestrator with OpenTelemetry-based metrics and traces, structured log output, and health check monitoring for key operational events. Good observability means you know what your Orchestrator is doing before users tell you something is wrong. The Orchestrator exports metrics and traces via OpenTelemetry (OTLP), emits structured logs, and provides health endpoints -- giving you the raw data you need to build dashboards, set up alerts, and debug issues when they arise. **Console terminology:** In the Maverics Console, Orchestrator instances and configuration delivery are managed through **Deployments**. When working directly with YAML, configuration is managed as files delivered via the `-config` flag or `MAVERICS_CONFIG` environment variable. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not deployed yet, follow the [Deploy to Production guide](/guides/operations/deploy) first. * **An OpenTelemetry collector** -- The Orchestrator exports telemetry via OTLP. You need an OpenTelemetry Collector (or compatible endpoint like Grafana Alloy, Datadog Agent, or New Relic) to receive metrics and traces. * **A log aggregation system** (recommended) -- Elasticsearch, Loki, Splunk, or any system that can ingest structured JSON logs. ## Set Up Observability The Orchestrator uses OpenTelemetry to export metrics and traces via the OTLP protocol. Metrics are collected through periodic readers that push to your OTLP endpoint at a configured interval. Traces are exported through simple processors. The Orchestrator can export telemetry data including: * **Request metrics** -- Total requests, response status codes, and request duration histograms * **Authentication metrics** -- Authentication event data (availability varies by Orchestrator version) * **Runtime metrics** -- Process-level metrics such as memory and concurrency data * **Distributed traces** -- End-to-end request tracing through authentication and authorization flows The specific metrics and trace data available depend on your Orchestrator version and configuration. Consult your Orchestrator's actual OTLP output to confirm which metrics are exported in your deployment. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Telemetry endpoint configuration in Maverics Console showing OTLP endpoint and interval settings Configure OTLP exporters for both metrics and traces: ```yaml maverics.yaml theme={null} telemetry: metrics: readers: - periodic: exporter: otlp: protocol: "http/protobuf" endpoint: "http://otelcol.example.com:4318/v1/metrics" insecure: true timeout: 5000 interval: 5000 traces: processors: - simple: exporter: otlp: protocol: "http/protobuf" endpoint: "http://otelcol.example.com:4318/v1/traces" ``` | Field | Description | | --------------------------------------------------- | -------------------------------------------------- | | `metrics.readers[].periodic.exporter.otlp.protocol` | OTLP transport -- use `"http/protobuf"` | | `metrics.readers[].periodic.exporter.otlp.endpoint` | Your OTLP collector's metrics endpoint | | `metrics.readers[].periodic.exporter.otlp.insecure` | Skip TLS verification for the collector connection | | `metrics.readers[].periodic.exporter.otlp.timeout` | Export timeout in milliseconds | | `metrics.readers[].periodic.interval` | Collection interval in milliseconds | | `traces.processors[].simple.exporter.otlp.protocol` | OTLP transport for traces | | `traces.processors[].simple.exporter.otlp.endpoint` | Your OTLP collector's traces endpoint | The OTLP exporter supports additional production options including TLS certificates, gzip compression, custom headers, and aggregation temporality preferences. For traces, a batch processor is available for high-volume environments. See [Telemetry Reference](/reference/orchestrator/telemetry) for the complete field reference. See [Telemetry Reference](/reference/orchestrator/telemetry) for all telemetry fields. If you manage Orchestrator configuration through the Maverics Console, advanced telemetry settings like batch processing, TLS, compression, and custom headers require the [**config override**](/reference/console/config-publishing#override-config) feature. Config override requires enablement for your organization -- contact your Strata account team or [Strata support](https://strataidentity.my.site.com/support/s/) to enable it. The Orchestrator exports all telemetry via OTLP. If you use Prometheus, configure your OpenTelemetry Collector to receive OTLP and export to Prometheus using the `prometheusremotewrite` exporter. The Orchestrator emits structured logs in JSON format -- making them easy to parse, search, and aggregate in any log management system. Structured logs include consistent fields like timestamp, log level, request ID, and component name, so you can filter and correlate events across your deployment. Production logging best practices: * **Log level** -- Use `info` for normal production operation. Switch to `debug` only when actively troubleshooting -- debug logging is verbose and can impact performance. * **Output format** -- JSON format (`jsonOutput: true`) is recommended for production. It integrates cleanly with log aggregation systems like Elasticsearch, Loki, and Splunk. * **Output destination** -- Stdout is the standard approach for containerized deployments (Docker and Kubernetes capture stdout automatically). For bare-metal deployments, you can configure file-based output with rotation. * **Request ID correlation** -- Each request gets a unique ID that appears in every log entry for that request. Use this to trace a single user's authentication flow across log entries. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Structured logging settings in Maverics Console showing log level, format, and output options Configure the logger for production: ```yaml maverics.yaml theme={null} logger: level: "info" jsonOutput: true timeFormat: "RFC3339Nano" logSessionID: false fieldOrdering: enabled: true ``` | Field | Default | Description | | ------------------------------ | --------------- | ------------------------------------------------------- | | `logger.level` | `"info"` | Log verbosity: `"debug"`, `"info"`, `"warn"`, `"error"` | | `logger.jsonOutput` | `false` | Output logs in JSON format for structured logging | | `logger.timeFormat` | `"RFC3339Nano"` | Time format string for log timestamps | | `logger.logSessionID` | `false` | Include the session ID in log entries for correlation | | `logger.fieldOrdering.enabled` | `false` | Order log fields consistently across entries | The `-verbose` CLI flag or `MAVERICS_DEBUG_MODE=true` environment variable overrides `logger.level` to `"debug"` at startup. You can also configure HTTP access logging separately: ```yaml maverics.yaml theme={null} http: accessLog: disabled: false level: "info" ``` The Orchestrator exposes a configurable health endpoint that load balancers and orchestration platforms use to verify operational status. The health endpoint returns a JSON response, and a periodic heartbeat logs system metrics. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Health check settings in Maverics Console showing endpoint path and heartbeat interval Configure the health endpoint and heartbeat: ```yaml maverics.yaml theme={null} health: location: "/status" heartbeat: disabled: false logLevel: "info" interval: "60s" ``` | Field | Default | Description | | --------------------------- | ----------- | --------------------------------------- | | `health.location` | `"/status"` | HTTP path for the health check endpoint | | `health.heartbeat.disabled` | `false` | Disable periodic heartbeat logging | | `health.heartbeat.logLevel` | `"info"` | Heartbeat log level | | `health.heartbeat.interval` | `"60s"` | Heartbeat interval (duration string) | Verify the health endpoint: ```bash theme={null} curl -s https://localhost:9443/status | jq . ``` ```json theme={null} { "status": "up" } ``` The periodic heartbeat log entry includes: `orchestrator_version`, `config_version`, `cpu_count`, `cpu_usage`, `total_memory`, `memory_usage`, and `active_goroutines`. Every log entry (including heartbeat entries) includes a [`soid`](/introduction/glossary#soid-secure-orchestrator-id) field for identifying and correlating logs by Orchestrator instance. See [Logging — Deployment Correlation](/reference/orchestrator/telemetry/logging#deployment-correlation) for details. Metrics and logs are useful for investigation, but alerts are what tell you something needs attention right now. Configure alerts for the conditions that indicate real problems -- not just noise. Recommended alerts for a production Orchestrator deployment: * **High error rate** -- Alert when the 5xx error rate exceeds a threshold (for example, more than 1% of requests returning 500-series errors over a 5-minute window). This catches upstream failures, misconfigurations, and application errors. * **Authentication failure spike** -- Alert when authentication failures increase significantly above the baseline. A sudden spike could indicate an IdP outage, expired credentials, or a misconfigured connector. * **Health check failure** -- Alert when the health endpoint reports an unhealthy status for more than 2 consecutive checks. This catches connector failures and startup issues. * **High latency** -- Alert when the p95 request latency exceeds your SLA threshold. High latency often indicates network issues, slow upstream services, or resource contention. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Alerting rules configuration in Maverics Console showing threshold settings and notification channels Alerting is configured in your monitoring platform (Prometheus, Grafana, Datadog, etc.), not in the Orchestrator YAML. The Orchestrator exports the metrics that your alerting rules evaluate. **Example Prometheus alert rules** for an Orchestrator deployment: ```yaml theme={null} # prometheus-alerts.yaml groups: - name: maverics rules: - alert: MavericsHealthCheckFailed expr: up{job="maverics"} == 0 for: 2m labels: severity: critical annotations: summary: "Orchestrator instance is down" - alert: MavericsHighErrorRate expr: rate(http_server_requests_total{status=~"5.."}[5m]) > 0.01 for: 5m labels: severity: warning annotations: summary: "Orchestrator error rate above 1%" ``` **Prometheus scrape configuration** for the Orchestrator's OTLP metrics (after your OpenTelemetry Collector translates to Prometheus format): ```yaml theme={null} # prometheus.yaml scrape config scrape_configs: - job_name: "maverics" scrape_interval: 15s static_configs: - targets: ["otelcol.example.com:8889"] ``` Start with a small number of high-signal alerts and add more as you learn your deployment's baseline behavior. Too many alerts leads to alert fatigue -- where important signals get lost in the noise. With telemetry, logging, and alerting configured, verify that data is flowing correctly through your entire observability pipeline. ```bash theme={null} # Verify status endpoint curl -s https://your-orchestrator-host:9443/status | jq . ``` Walk through a complete verification: 1. **Check your OTLP collector** -- Confirm the collector is receiving metrics and traces from the Orchestrator 2. **Check dashboards** -- If you have Grafana dashboards, verify that charts are rendering with real data 3. **Check logs** -- Trigger a few requests and confirm the structured log entries appear in your log aggregation system with the correct JSON format and fields 4. **Test an alert** -- If possible, trigger one of your alert conditions (for example, temporarily set a very low threshold) and confirm the alert fires and notifications are delivered **Success!** Your Orchestrator deployment is fully instrumented. Metrics and traces are being exported via OTLP, structured logs are flowing to your aggregation system, and alerts are configured for key operational events. ## Troubleshooting Verify that the OTLP endpoint URL in your `telemetry` configuration is correct and reachable from the Orchestrator. Check that the collector is running and listening on the expected port. If the collector uses TLS, set `insecure: false` and ensure the Orchestrator can verify the collector's certificate. Check firewall rules and network policies between the Orchestrator and collector. If your log aggregation system is not parsing the Orchestrator's logs correctly, check that you are using a JSON parser (not a regex-based parser for plain text logs). The Orchestrator outputs JSON-formatted logs when `jsonOutput: true` is set. If you see raw JSON strings instead of parsed fields, your log shipper (Filebeat, Fluentd, Vector) may need a JSON parsing filter configured. Check the log shipper's documentation for JSON input configuration. If alerts are not firing when expected, check these common causes: * **Threshold too high** -- Your alert threshold may be higher than the actual metric values. Check the raw metric values in your monitoring platform to set realistic thresholds. * **Wrong metric name** -- Verify the exact metric name matches what your alert rule references. Metric names are case-sensitive. * **Evaluation interval** -- Alert rules only evaluate at configured intervals. If your evaluation interval is 5 minutes, the alert will not fire until the next evaluation window after the condition is met. * **Notification channel** -- The alert rule may be firing but the notification is not reaching you. Check your alerting tool's notification configuration (email, Slack, PagerDuty). ## Related Pages Back to the Operations guides hub Complete configuration reference for logger, telemetry, access logs, and health check settings Set up your production deployment before configuring monitoring # Overview Source: https://docs.strata.io/guides/operations/overview The Operations guides cover the full lifecycle of running the Maverics Orchestrator in production. The Orchestrator is small and lightweight -- it deploys almost anywhere, whether that is a Docker container, a Kubernetes cluster, or a bare-metal server. Once running, it provides a health endpoint, OpenTelemetry-based metrics and traces, and structured JSON logging so you always know what is happening. These guides take you from a working development setup to a production deployment -- covering how to deploy safely, monitor effectively, scale horizontally, and troubleshoot when things do not go as expected. Each guide stands on its own, so you can jump directly to the topic you need. ## Guides Deploy with CLI flags, Docker or systemd, secret provider configuration, health probes, and environment-specific YAML Configure OpenTelemetry metrics and traces via OTLP export, structured JSON logging, and Prometheus alerting rules Scale horizontally with sticky sessions, local session storage, and mode-appropriate Redis caching Diagnose and resolve common startup failures, authentication errors, configuration problems, and connectivity issues ## Related Pages Full reference for installation methods, system requirements, and platform support Complete configuration reference for metrics, logging, and health check settings TLS configuration, certificate management, and security hardening for production deployments New to Maverics? Start here for installation, first configuration, and your first protected application Set up automatic IdP failover and cascading high availability to eliminate identity provider single points of failure # Scale for Production Source: https://docs.strata.io/guides/operations/scale By the end of this guide, you will have a horizontally scaled Maverics deployment with multiple Orchestrator instances, sticky sessions, local session storage, and mode-appropriate Redis caching. A single Orchestrator instance can handle a significant amount of traffic -- the Orchestrator is small, lightweight, and efficient. But production workloads often require multiple instances for high availability (if one instance goes down, the others continue serving traffic) and for handling peak loads that exceed a single instance's capacity. Scaling the Orchestrator horizontally requires sticky sessions (cookie-based session affinity) on your load balancer so that each user's requests consistently reach the same Orchestrator instance, plus Redis caching when your mode requires cross-instance data sharing. **Console terminology:** In the Maverics Console, Orchestrator instances and configuration delivery are managed through **Deployments**. When working directly with YAML, configuration is managed as files delivered via the `-config` flag or `MAVERICS_CONFIG` environment variable. ## Prerequisites * **A running Orchestrator deployment** -- If you have not deployed to production yet, follow the [Deploy to Production guide](/guides/operations/deploy) first. * **A load balancer that supports cookie-based session affinity (sticky sessions)** -- Any HTTP load balancer that supports health check-based routing and cookie-based affinity (NGINX Plus, HAProxy, AWS ALB, F5 BIG-IP, GCP Load Balancer, etc.). * **A Redis instance** -- Required for OIDC Provider mode; recommended for SAML Provider mode; not needed for other modes. See the [Redis Cache reference](/reference/orchestrator/caches/redis) for setup. ## Scale Your Deployment Sessions are stored locally on each Orchestrator instance. Sticky sessions (session affinity) ensure that each user's requests consistently reach the same instance, so the Orchestrator can find the user's session on every request. Configure your load balancer to use **cookie-based affinity** targeting the `maverics_session` cookie (or your custom `session.cookie.name` value). Cookie-based affinity is more reliable than IP-based affinity because it works correctly when multiple users share the same IP address (e.g., behind a corporate NAT) or when a user's IP changes mid-session (e.g., switching networks on a mobile device). **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Session storage settings in Maverics Console showing local session store configuration Configure local session storage on each Orchestrator instance. The load balancer handles routing -- the Orchestrator configuration is the same as a single-node deployment: ```yaml maverics.yaml theme={null} session: cookie: name: "maverics_session" domain: ".example.com" lifetime: maxTimeout: "12h" idleTimeout: "30m" store: type: "local" local: capacity: 50000 ``` See [Sessions Reference](/reference/orchestrator/sessions) for all session configuration fields. If an Orchestrator node goes down, sessions on that node are lost. Users are transparently re-authenticated via their upstream IdP session -- they experience a brief redirect but are not prompted to log in again. Redis is a **cache** for connector tokens and provider data -- not a session store. In multi-node deployments, Redis ensures that provider-specific data (authorization codes, SAML request data, connector tokens) is accessible from any Orchestrator instance, even though each user's requests are routed to the same instance via sticky sessions. The need for Redis depends on which Orchestrator mode you are using: * **OIDC Provider:** Redis cache is **required** for multi-node deployments. The OIDC Provider stores authorization codes, token state, and provider data in the cache. Without Redis, an authorization code issued by one instance cannot be redeemed by another -- and even with sticky sessions, the token endpoint request may arrive from the application server rather than the user's browser, bypassing session affinity. * **SAML Provider:** Redis cache is **recommended**. The SAML Provider caches SAML request data (AuthnRequest and LogoutRequest form parameters) so that after a user authenticates upstream, any Orchestrator instance can restore the original request context and generate the SAML response. Without Redis, if the authentication callback arrives at a different instance than the one that received the original AuthnRequest, the SAML response flow will fail because the request data is only in local memory. * **HTTP Proxy:** Redis cache is **not needed**. Each instance manages its own connector tokens independently. * **LDAP Provider:** A shared cache is **not typically needed** for standalone LDAP Provider deployments -- the LDAP Provider uses per-connection bind state. However, in **facade (sandwich) deployments** where HTTP Proxy and LDAP Provider run as separate Orchestrator instances, a shared cache **is required** so that one-time credentials generated by the proxy can be validated by the LDAP Provider. When both modes run on a single Orchestrator, the local cache is sufficient. See [LDAP Provider -- Pairing with HTTP Proxy](/reference/modes/ldap-provider#pairing-with-http-proxy) and the [Caches reference](/reference/orchestrator/caches). * **AI Identity Gateway:** A cache is **not typically needed**. AI Identity Gateway uses token-based state tied to the upstream OAuth authorization server. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Redis cache settings in Maverics Console showing cache and provider configuration Define a Redis cache and reference it from your provider configuration: ```yaml maverics.yaml theme={null} caches: - name: "my-redis" type: "redis" redis: addresses: - "redis.example.com:6379" password: tls: "redis-tls" # Reference the cache from your provider: oidcProvider: cache: "my-redis" # ... other oidcProvider config samlProvider: cache: "my-redis" # ... other samlProvider config ``` See [Redis Cache Reference](/reference/orchestrator/caches/redis) for all Redis cache fields including encryption and hashing options. A load balancer distributes incoming requests across your Orchestrator instances. Configure it to use health check-based routing so that traffic only goes to healthy instances, and cookie-based sticky sessions so that each user's requests reach the same instance. Key load balancer configuration: * **Health check endpoint** -- Point the load balancer's health check at the Orchestrator's `/status` endpoint. Remove instances from the pool when they return an unhealthy status. * **Sticky sessions** -- Configure cookie-based session affinity using the `maverics_session` cookie (or your custom `session.cookie.name` value). This ensures each user's requests consistently reach the same Orchestrator instance. * **Connection draining** -- When an instance is removed from the pool (during a rolling update or failure), allow existing connections to complete before terminating the instance. This prevents request failures during deployments. * **TLS termination** -- Decide whether TLS terminates at the load balancer or at the Orchestrator. Terminating at the load balancer is simpler to manage when running multiple instances. Load balancers are external to the Orchestrator -- they are configured in your infrastructure layer, not in `maverics.yaml`. Select your load balancer below for configuration examples: ```nginx theme={null} upstream maverics { server 10.0.1.10:9443; server 10.0.1.11:9443; server 10.0.1.12:9443; # Use the Orchestrator's session cookie for affinity. # If you customized session.cookie.name, use that value instead. sticky cookie maverics_session; } server { listen 443 ssl; server_name app.example.com; location / { proxy_pass https://maverics; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; } location /status { proxy_pass https://maverics/status; } } ``` ```haproxy theme={null} frontend maverics_fe bind *:443 ssl crt /etc/haproxy/certs/app.pem default_backend maverics_be backend maverics_be cookie maverics_session insert indirect nocache server orch1 10.0.1.10:9443 ssl check cookie orch1 server orch2 10.0.1.11:9443 ssl check cookie orch2 server orch3 10.0.1.12:9443 ssl check cookie orch3 option httpchk GET /status ``` HAProxy's `cookie` directive in the backend inserts a cookie to track which server handles each session. The `insert indirect nocache` options tell HAProxy to manage the affinity cookie transparently. Enable application cookie-based stickiness on the ALB target group: ```bash theme={null} aws elbv2 modify-target-group-attributes \ --target-group-arn arn:aws:elasticloadbalancing:REGION:ACCOUNT:targetgroup/maverics/XXXXX \ --attributes \ Key=stickiness.enabled,Value=true \ Key=stickiness.type,Value=app_cookie \ Key=stickiness.app_cookie.cookie_name,Value=maverics_session \ Key=stickiness.app_cookie.duration_seconds,Value=86400 ``` In the AWS Console: navigate to **EC2 > Target Groups > your target group > Attributes > Stickiness**, enable stickiness, select **Application-based cookie**, and set the cookie name to `maverics_session`. Use an iRule or a persistence profile with cookie-based persistence targeting the `maverics_session` cookie. Consult your load balancer's documentation for cookie-based affinity configuration. Enable cookie-based affinity on the backend settings. Azure Application Gateway uses its own affinity cookie by default, but can be configured for application-managed affinity. Consult the Azure documentation for cookie-based affinity configuration. Use a backend service with `GENERATED_COOKIE` or `HTTP_COOKIE` session affinity and specify the `maverics_session` cookie name. Consult the GCP documentation for cookie-based affinity configuration. Use the sticky sessions configuration in the load balancer service definition with a cookie name of `maverics_session`. Consult the Traefik documentation for sticky session configuration. Always use **cookie-based affinity** rather than IP-based affinity. Cookie-based affinity works correctly when users share IPs (corporate NAT) or change networks mid-session (mobile devices). Each user's requests will consistently reach the same Orchestrator instance based on their session cookie. With multiple instances behind a load balancer and sticky sessions configured, verify that your deployment is truly highly available by testing failover. ```bash theme={null} # Verify all instances are healthy via the load balancer curl -s https://your-load-balancer:9443/status | jq . # Authenticate through the load balancer and verify your session works # Make several requests to confirm sticky sessions are routing correctly ``` Test a failover scenario: 1. **Authenticate through the load balancer** -- Establish a session 2. **Stop one Orchestrator instance** -- Simulate a failure 3. **Make another request** -- If the stopped instance was handling your session, the load balancer routes you to a healthy instance. The Orchestrator redirects you to your upstream IdP, which recognizes your existing IdP session and completes authentication silently -- you experience a brief redirect but are not prompted to log in again. 4. **Restart the stopped instance** -- It should rejoin the pool automatically once the health check passes **Success!** Your Orchestrator deployment is horizontally scaled with high availability. Each instance stores sessions locally, the load balancer uses cookie-based sticky sessions to route users consistently, and failover triggers transparent re-authentication via the upstream IdP. ## Troubleshooting If users are being asked to re-authenticate unexpectedly, sticky sessions may be misconfigured: * Verify the load balancer has cookie-based session affinity configured on the session cookie (`maverics_session` by default, or your custom `session.cookie.name` value). * Verify all instances use `store.type: "local"`. * Check load balancer logs to confirm requests from the same user consistently reach the same instance. * If using IP-based affinity instead of cookie-based, switch to cookie-based affinity. IP-based affinity breaks when multiple users share the same IP (corporate NAT) or when a user's IP changes mid-session. If a new or restarted Orchestrator instance is not receiving traffic, check that: * The instance's health endpoint is returning a healthy status * The load balancer's health check is configured to poll the correct port and path * The health check interval and threshold are set appropriately -- some load balancers require multiple consecutive healthy responses before adding an instance to the pool * Network rules allow the load balancer to reach the instance on both the application port and the health check port ## Related Pages Back to the Operations guides hub Scale the two-tier AI Identity Gateway architecture with MCP-specific load balancing and token exchange tuning Set up your production deployment before scaling horizontally Session store types and session configuration Redis cache configuration for connector tokens and provider data # Troubleshoot Common Issues Source: https://docs.strata.io/guides/operations/troubleshoot By the end of this guide, you will have a systematic approach to diagnosing Maverics Orchestrator issues -- with clear steps for identifying root causes and resolving the most common problems. Troubleshooting is easier when you have a systematic approach. This guide organizes the most common Orchestrator issues by category -- startup, authentication, configuration, and connectivity -- so you can quickly find the problem that matches your symptoms and follow the resolution steps. Each section covers the likely causes, diagnostic commands, and fixes. **Console terminology:** In the Maverics Console, Orchestrator instances and configuration delivery are managed through **Deployments**. When working directly with YAML, configuration is managed as files delivered via the `-config` flag or `MAVERICS_CONFIG` environment variable. Before diving into a specific issue, check the Orchestrator's logs first. The Orchestrator emits structured JSON logs that include error details, request IDs, and component names. Most issues are diagnosable from the log output alone. See the [Monitor and Observe guide](/guides/operations/monitor) for log configuration. ## Startup Issues These issues prevent the Orchestrator from starting or completing its initialization. The Orchestrator validates its configuration on startup and exits with an error if anything is invalid. Check the error output for the specific cause. **Common causes:** * **Invalid YAML syntax** -- Indentation errors, missing colons, unclosed quotes, or tabs instead of spaces. Run your config file through a YAML validator to catch syntax errors. * **Missing required fields** -- The Orchestrator logs which required fields are missing. Check the [configuration reference](/reference/orchestrator/configuration) for the minimum required configuration. * **Permission denied** -- The Orchestrator process does not have permission to read the config file, bind to the configured port, or access TLS certificates. Check file permissions and ensure the process runs with appropriate privileges. **Diagnostic steps:** ```bash theme={null} # Check the Orchestrator's error output maverics -config /etc/maverics/config.yaml 2>&1 | head -20 # Validate YAML syntax python3 -c "import yaml; yaml.safe_load(open('/etc/maverics/config.yaml'))" # Check file permissions ls -la /etc/maverics/config.yaml ``` The Orchestrator cannot locate the configuration file at the specified path. **Common causes:** * **Wrong path** -- The `-config` flag points to a path that does not exist. Double-check the path, including case sensitivity on Linux. * **Mount not available** -- In Docker or Kubernetes, the volume mount may not be configured correctly. Verify the mount path inside the container matches the config flag. * **Environment variable not set** -- If you use an environment variable for the config path, confirm it is set in the Orchestrator's runtime environment. **Diagnostic steps:** ```bash theme={null} # Check if the file exists at the expected path ls -la /etc/maverics/config.yaml # In Docker, check the mount docker inspect | jq '.[0].Mounts' # In Kubernetes, check the ConfigMap mount kubectl exec -- ls -la /etc/maverics/ ``` The Orchestrator cannot bind to its configured listening port because another process is already using it. **Common causes:** * **Previous instance still running** -- A previous Orchestrator process did not shut down cleanly. Find and stop it before starting a new one. * **Another service** -- A different application is using the same port. * **Port below 1024** -- Ports below 1024 require root privileges on most systems. **Diagnostic steps:** ```bash theme={null} # Find what is using the port (Linux/macOS) lsof -i :8080 # Kill the previous process if needed kill # Or change the port in your configuration ``` ## Authentication Issues These issues affect user login flows, token validation, and SSO behavior. When users visit a protected URL, they should be redirected to the identity provider's login page. If the redirect is not happening, the issue is usually in the application route or connector configuration. **Common causes:** * **Route not matched** -- The request URL does not match any configured application route. Check that the route's URL pattern matches the URL the user is visiting. * **Connector not assigned** -- The application route does not have an identity connector assigned, so the Orchestrator does not know where to redirect for authentication. * **Connector misconfigured** -- The identity connector's authorization endpoint URL is wrong or unreachable. **Diagnostic steps:** * Check the Orchestrator's logs for the incoming request -- the log entry shows which route (if any) matched and whether a connector was invoked * Verify the redirect URL in the browser's developer tools (Network tab) to see if the Orchestrator is issuing a redirect at all * Test the IdP's authorization endpoint directly with `curl` to confirm it is reachable The user authenticates successfully, but the upstream application rejects the request or shows an unauthorized error. **Common causes:** * **Missing headers** -- The Orchestrator is not injecting the identity headers that the upstream application expects. Check your header injection configuration. * **Wrong header format** -- The upstream application expects headers in a specific format (for example, a Bearer token in the Authorization header) but the Orchestrator is sending a different format. * **Clock skew** -- Token validation failures can occur when the Orchestrator's clock and the upstream application's clock are out of sync. Ensure both systems use NTP. **Diagnostic steps:** * Use `curl -v` to inspect the exact headers the Orchestrator sends to the upstream * Check the upstream application's logs for the specific rejection reason * Compare the expected header format with what the Orchestrator sends The user gets stuck in an infinite loop between the Orchestrator and the identity provider -- redirecting back and forth without ever landing on the application. **Common causes:** * **Callback URL mismatch** -- The callback URL registered in the identity provider does not match the Orchestrator's expected redirect URI. Both sides must match exactly (including protocol, host, port, and path). * **Session not persisting** -- The session cookie is not being set or read correctly. Check cookie domain and path settings, and ensure the browser is not blocking third-party cookies. * **Application behind the Orchestrator redirecting again** -- The upstream application has its own authentication that triggers another redirect. Disable the upstream app's authentication since the Orchestrator handles it. **Diagnostic steps:** * Open the browser's developer tools and watch the Network tab to see the exact redirect sequence * Check that the callback URL in your IdP configuration matches the Orchestrator's redirect URI exactly * Look for `Set-Cookie` headers in the Orchestrator's responses to confirm the session cookie is being set ## Configuration Issues These issues affect how the Orchestrator reads and applies its configuration. You updated the configuration file but the Orchestrator's behavior has not changed. **Common causes:** * **Orchestrator not restarted** -- The Orchestrator reads its configuration at startup. Changes to the config file require a restart to take effect. * **Wrong config file** -- You may have edited a different config file than the one the Orchestrator is using. Check the `-config` flag or environment variable to confirm the path. * **Listen address change** -- Changes to `http.address` (or LDAP listen address) are not applied by a config reload. A change to the listening address requires a full process restart (not just a reload), because the listening socket is inherited from process startup and cannot be re-bound in place. * **Cached config** -- If using an external [config source](/reference/orchestrator/configuration/config-sources), the config may be cached. Check the config source's cache TTL and refresh settings. **Diagnostic steps:** ```bash theme={null} # Check which config file the Orchestrator is using ps aux | grep maverics # Restart the Orchestrator to pick up changes systemctl restart maverics # or in Docker docker restart ``` You used an environment variable reference in your configuration file but the Orchestrator is using the literal string instead of the variable's value. **Common causes:** * **Variable not set** -- The environment variable is not set in the Orchestrator's runtime environment. Variables set in your local shell are not automatically available to services started by systemd, Docker, or Kubernetes. * **Wrong syntax** -- The Orchestrator uses `{{ env.VAR_NAME }}` syntax (double curly braces with spaces) for environment variable references in YAML. See the [configuration reference](/reference/orchestrator/configuration) for details. * **Variable set after startup** -- Environment variables are read at process startup. If you set a variable after the Orchestrator started, restart it. **Diagnostic steps:** ```bash theme={null} # Check if the variable is set in the Orchestrator's environment # For systemd systemctl show maverics -p Environment # For Docker docker inspect | jq '.[0].Config.Env' # For Kubernetes kubectl exec -- env | grep YOUR_VAR ``` A secret referenced in the configuration is not loading from the external [secret provider](/reference/orchestrator/configuration/secret-providers). **Common causes:** * **Authentication failure** -- The Orchestrator cannot authenticate to the secret provider. Check the secret provider's credentials and IAM permissions. * **Wrong secret path** -- The secret path or key does not match what exists in the secret provider. Paths are case-sensitive and must match exactly. In YAML, secrets are referenced with `` syntax (angle brackets). * **Network access** -- The Orchestrator cannot reach the secret provider's endpoint. Check network policies, firewall rules, and DNS resolution. **Diagnostic steps:** * Enable `debug` logging to see the exact secret provider requests and responses * Test the secret provider connection independently using its CLI tool (for example, `vault read secret/data/maverics` for HashiCorp Vault) * Verify IAM roles and policies grant read access to the specific secret path The Orchestrator performs a config reload when `MAVERICS_RELOAD_CONFIG=true` is set and the config changes. If reloads appear to have no effect, the likely cause is one of three missing requirements -- each with a distinct symptom and log signal. **Common causes:** | Requirement | Symptom | Log signal | | --------------------------------------------- | ------------------------------------------------------------------------- | ------------------------------------- | | `MAVERICS_RELOAD_CONFIG=true` env var not set | Config changes silently ignored; pod restart required to apply | *(no log -- reload never starts)* | | Writable temp directory not mounted | Reload is a silent no-op; old config keeps serving | `failed to create handoff listener` | | Stable `/etc/machine-id` not projected | Reload applies new config, but in-flight state (sessions, caches) is lost | `failed to connect to handoff socket` | **Diagnostic steps:** ```bash theme={null} # Kubernetes: check logs for the two error strings kubectl logs | grep -E "failed to create handoff listener|failed to connect to handoff socket" # Docker: same check docker logs 2>&1 | grep -E "failed to create handoff listener|failed to connect to handoff socket" # Confirm the env var is set kubectl exec -- env | grep MAVERICS_RELOAD ``` If `failed to create handoff listener` appears: add a writable `emptyDir` mount and set `TMPDIR` to point to it. If `failed to connect to handoff socket` appears: project a stable `/etc/machine-id` via the Downward API. **Fix:** See the [Kubernetes](/reference/orchestrator/installation/kubernetes#in-place-config-reload) and [Docker](/reference/orchestrator/installation/docker#in-place-config-reload) installation pages for the complete configuration. On macOS, `os.TempDir()` returns a long path under `/var/folders/.../T/` (typically 50-70 characters). The handoff socket path (`/maverics-handoff-.sock`) can exceed macOS's 104-byte Unix socket path limit, causing socket creation to fail. **Symptom:** Config reload is enabled but changes are not applied. The logs contain `failed to create handoff listener`. **Diagnostic:** ```bash theme={null} # Check the current TMPDIR length echo -n "$TMPDIR/maverics-handoff-12345.sock" | wc -c # If this exceeds 104, the socket will fail to create ``` **Fix:** Set `TMPDIR=/tmp` to use a shorter path: ```bash theme={null} TMPDIR=/tmp ./maverics -config /path/to/config.yaml ``` For persistent background operation via launchd, set `TMPDIR=/tmp` in the `EnvironmentVariables` key of your launch daemon plist. ## Connectivity Issues These issues affect the Orchestrator's ability to communicate with external services. The Orchestrator returns a 502 Bad Gateway error because it cannot connect to the upstream application. **Common causes:** * **Upstream not running** -- The upstream application is down or not listening on the expected port. * **Wrong upstream URL** -- The upstream URL in the route configuration is incorrect (wrong host, port, or protocol). * **Network isolation** -- Firewall rules, security groups, or Kubernetes NetworkPolicies are blocking traffic from the Orchestrator to the upstream. * **DNS resolution** -- The Orchestrator cannot resolve the upstream hostname. **Diagnostic steps:** ```bash theme={null} # Test connectivity from the Orchestrator's host curl -v http://upstream-host:8080/ # Check DNS resolution nslookup upstream-host # In Kubernetes, check network policies kubectl get networkpolicies -n ``` The Orchestrator times out when trying to reach the identity provider during authentication flows. **Common causes:** * **IdP endpoint unreachable** -- The identity provider's endpoints are not reachable from the Orchestrator's network. This is common in air-gapped environments or when network egress is restricted. * **DNS issues** -- The Orchestrator cannot resolve the IdP's hostname. * **TLS handshake failure** -- The Orchestrator cannot complete a TLS handshake with the IdP, often because of a missing CA certificate or certificate verification failure. * **Proxy required** -- Your network requires an HTTP proxy for outbound connections, and the Orchestrator is not configured to use it. **Diagnostic steps:** * Test the IdP's OIDC discovery endpoint directly from the Orchestrator's host: `curl -v https://your-idp.example.com/.well-known/openid-configuration` * Check for proxy requirements and set `HTTP_PROXY` / `HTTPS_PROXY` environment variables if needed * Verify the IdP's TLS certificate chain is trusted by the Orchestrator's CA bundle The health endpoint (`/status`) returns `{"status": "up"}` when the Orchestrator is operational. If your load balancer intermittently removes and re-adds the instance, the Orchestrator may be unresponsive during those periods. **Common causes:** * **Resource pressure** -- The Orchestrator is running low on memory or CPU, causing slow health check responses that the load balancer interprets as timeouts. * **Network instability** -- Intermittent network issues between the load balancer and the Orchestrator instance. * **Process restarts** -- The Orchestrator is restarting due to configuration reloads or OOM kills, causing brief unavailability windows. **Diagnostic steps:** ```bash theme={null} # Verify the health endpoint responds curl -s https://localhost:9443/status # Expected response: {"status": "up"} ``` * Monitor the Orchestrator's resource usage (CPU, memory) during failure periods * Check system logs (`journalctl -u maverics` or `docker logs`) for restarts * Increase the load balancer's health check timeout and failure threshold to tolerate brief interruptions without removing the instance from the pool ## Getting Help If you have worked through the troubleshooting steps above and are still stuck, here is how to get additional help. **Collect diagnostic information** before reaching out to support. This makes it much faster to identify and resolve your issue: * **Orchestrator version** -- Run the Orchestrator with a `-version` flag or check the startup logs * **Deployment identifier** -- Every log entry includes a [`soid`](/introduction/glossary#soid-secure-orchestrator-id) field that identifies the Orchestrator instance. Include this value so support can correlate your logs to the specific instance * **Configuration file** -- A sanitized copy of your config file (remove secrets and credentials) * **Logs** -- The relevant log entries around the time the issue occurred. Include the full error message and any stack traces. Enable `debug` logging temporarily for more detail * **Environment details** -- Operating system, container runtime version, Kubernetes version, cloud provider, and any relevant network configuration **Support channels:** * **Strata Identity support** -- Contact the Strata support team for production issues. Include the diagnostic information above. * **Documentation** -- The [Orchestrator Configuration Reference](/reference/orchestrator/configuration) pages often have the specific detail you need for configuration questions. ## Related Pages Back to the Operations guides hub Full reference for configuration file structure, environment variables, and runtime settings Complete configuration reference for telemetry, logging, and health check settings Configuration for HashiCorp Vault, AWS, Azure, and other secret providers # Compliance and Audit Source: https://docs.strata.io/guides/security/compliance By the end of this guide, you will have a Maverics Orchestrator with comprehensive audit logging -- capturing authentication events, authorization decisions, configuration changes, and administrative actions for compliance reporting. **Console terminology:** In the Maverics Console, Orchestrator instances and configuration delivery are managed through **Deployments**. When working directly with YAML, configuration is managed as files delivered via the `-config` flag or `MAVERICS_CONFIG` environment variable. Compliance configurations use features documented across multiple reference pages. Each section below links to the detailed guide and reference for the specific feature being configured. ## What Is Compliance and Audit Logging? Compliance means demonstrating that your identity system operates according to your organization's policies and applicable regulations. Audit logging is how you produce the evidence. Every time a user authenticates, every time a policy allows or denies access, and every time an administrator changes the configuration -- these events form an audit trail that tells the story of who did what, when, and whether the system allowed it. The Maverics Orchestrator generates detailed audit events for every significant action it processes. A SIEM (Security Information and Event Management) system -- such as Splunk, Datadog, or Elastic -- collects and analyzes these events, giving your security team a centralized view of identity activity across your infrastructure. Compliance frameworks like SOC2 (Service Organization Control 2, a standard for service providers), HIPAA (Health Insurance Portability and Accountability Act, for healthcare data), and GDPR (General Data Protection Regulation, for EU personal data) each require specific types of audit evidence, and the Orchestrator's logging covers the identity-related requirements for all of them. ## FIPS 140-3 Compliance FIPS 140-3 builds are an experimental feature. See [FIPS 140-3 Builds](/reference/orchestrator/experimental/fips) for who needs FIPS, current validation status, feature parity details, and contact information. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed it yet, follow the [Quick Start guide](/guides/getting-started/quick-start) first. * **A log aggregation system** -- You need somewhere to send audit logs for analysis and long-term retention. This can be a SIEM like Splunk, Datadog, or Elastic, a cloud logging service like AWS CloudWatch or Azure Monitor, or even a file-based log management system for smaller deployments. ## Configure Security Features for Compliance TLS encryption is a baseline requirement for all compliance frameworks. It ensures that authentication tokens, user credentials, and personal data are encrypted in transit. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. TLS configuration overview in Maverics Console showing certificate status Define a TLS profile and bind it to the HTTP listener: ```yaml maverics.yaml theme={null} tls: "default": certFile: "/etc/maverics/certs/server.pem" keyFile: "/etc/maverics/certs/server-key.pem" minVersion: "1.2" http: address: "0.0.0.0:9443" tls: "default" ``` For compliance, set `minVersion: "1.2"` to disable older, vulnerable TLS versions. For the highest security, use `"1.3"`. See the [Configure TLS guide](/guides/security/tls) for complete setup instructions and the [Transport Layer Security (TLS) Reference](/reference/orchestrator/tls-security) for all profile fields. Compliance frameworks require that secrets (API keys, credentials, certificates) are stored securely with access controls and audit trails. External secret providers satisfy these requirements by centralizing secret storage with rotation, access logging, and fine-grained policies. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Secret provider connection status in Maverics Console Configure a secret provider via environment variable (not YAML): ```bash theme={null} export MAVERICS_SECRET_PROVIDER="hashivault://vault.example.com:8200/secret/data/maverics?token=" ``` Then reference secrets in YAML using angle bracket syntax: ```yaml maverics.yaml theme={null} connectors: - name: my-idp type: oidc oauthClientSecret: ``` This ensures no plaintext secrets appear in configuration files -- a common audit finding and compliance requirement. See the [Manage Secrets guide](/guides/security/secrets-management) for setup instructions and the [Secret Providers Reference](/reference/orchestrator/configuration/secret-providers) for all 7 provider types. Authorization policies provide the access control evidence that compliance auditors look for. Every policy evaluation is logged, creating an audit trail of who was allowed or denied access to each resource. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Policy enforcement dashboard in Maverics Console showing allow/deny statistics Define authorization policies on your apps: ```yaml maverics.yaml theme={null} apps: - name: my-app type: proxy upstream: https://backend.example.com routePatterns: - "app.example.com" policies: - location: "/" authentication: idps: ["my-idp"] authorization: rules: - and: - contains: ["{{ my-idp.groups }}", "authorized-users"] ``` Each policy evaluation generates a log entry recording the user, resource, decision (allow/deny), and the policy rule that was evaluated. These entries form the authorization audit trail required by SOC2, HIPAA, and GDPR. See the [Authorization Policies guide](/guides/security/policies) for access control configuration -- RBAC, ABAC, PBAC, and external PDP integration, and the [Applications Reference](/reference/orchestrator/applications) for rule syntax. The Orchestrator captures authentication and authorization events through its structured logging system. Configure the logger for production audit logging and export logs to your SIEM for centralized analysis and long-term retention. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Audit logging configuration screen in Maverics Console showing event categories and logging levels Configure structured logging with session correlation for audit trails: ```yaml maverics.yaml theme={null} logger: level: "info" jsonOutput: true logSessionID: true http: accessLog: disabled: false level: "info" ``` Key settings for compliance logging: * `jsonOutput: true` -- Structured JSON logs for SIEM ingestion * `logSessionID: true` -- Correlate events across a user's session for complete audit trails * `accessLog.disabled: false` -- Record every HTTP request for access auditing The Orchestrator's structured logs capture authentication events (login, logout, failures), authorization decisions (policy allow/deny), and request metadata. Events are viewable in the Maverics Console and can be exported to external SIEM systems via your log shipper. See the [Monitor and Observe guide](/guides/operations/monitor) for complete observability setup and the [Telemetry Reference](/reference/orchestrator/telemetry) for all logging fields. Start by enabling all event categories. You can always reduce the logging level later if the volume is too high, but it is much harder to retroactively generate events that were not captured. For compliance, it is better to log too much than too little. Session security settings control cookie protection and session lifetimes. Compliance frameworks require that sessions are protected against hijacking and have appropriate timeout policies. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Session security configuration in Maverics Console Configure session cookies and lifetimes for compliance: ```yaml maverics.yaml theme={null} session: cookie: name: "maverics_session" domain: ".example.com" disableHTTPOnly: false disableSecure: false lifetime: maxTimeout: "8h" idleTimeout: "30m" ``` Key security settings: * `disableHTTPOnly: false` -- Keeps HTTPOnly flag enabled, preventing client-side script access to the session cookie * `disableSecure: false` -- Keeps Secure flag enabled, ensuring cookies are only sent over HTTPS * `maxTimeout` -- Maximum session duration before forced re-authentication * `idleTimeout` -- Inactivity timeout before session expires See the [Sessions Reference](/reference/orchestrator/sessions) for all session configuration fields. With TLS, secret management, authorization policies, audit logging, and session security configured, map the Orchestrator's security features to your compliance framework requirements. **SOC2** -- Requires evidence of access controls, change management, and system monitoring. The Orchestrator provides: authentication/authorization policy enforcement (access controls), structured audit logs (system monitoring), and configuration-as-code with secret management (change management). **HIPAA** -- Requires audit trails for access to systems handling protected health information (PHI). The Orchestrator provides: per-request authentication and authorization logging, session ID correlation across events, and policy enforcement logs showing access decisions for PHI-containing applications. **GDPR** -- Requires records of data processing activities and access to personal data. The Orchestrator provides: authentication event logs (tracking access to personal data), session management with appropriate timeouts, and TLS encryption for data in transit. **Success!** Your Orchestrator is configured with comprehensive security features for compliance. TLS encrypts all connections, secrets are managed externally, authorization policies control access, structured audit logs capture every significant event, and session security prevents hijacking. ## Troubleshooting If expected events are not appearing in the Orchestrator's logs, verify that the log level is set to `"info"` or lower. Events at the `"info"` level include authentication and authorization decisions. If you need more detail, temporarily set the level to `"debug"` to see all internal events. Also confirm that `jsonOutput: true` is set so your SIEM can parse the structured log format. If audit logs are generated locally but not appearing in your SIEM, check the log shipper configuration between the Orchestrator and your SIEM. Common issues include incorrect endpoint URLs, authentication failures with the SIEM's ingestion API, network connectivity issues (firewalls blocking the export traffic), and format mismatches (the SIEM expects JSON but receives plain text). Test the log path independently to isolate the issue. If your compliance reports show gaps -- periods where no events were recorded -- investigate whether the Orchestrator was running during those periods and whether the log export was functioning. Gaps can also occur if the SIEM dropped events due to ingestion rate limits or storage capacity. For critical compliance requirements, configure redundant log export destinations so that a single export failure does not create gaps in your audit trail. ## Related Pages Return to the Security guides hub for TLS, secrets, policies, and compliance Complete configuration reference for logging, monitoring, and observability Define the access control policies whose enforcement is captured in audit logs Monitor and operate the Orchestrator in production -- including log management # Overview Source: https://docs.strata.io/guides/security/overview The Maverics Orchestrator sits at the center of your identity infrastructure -- handling authentication tokens, user attributes, client secrets, and session data on every request. That makes it a critical piece of your security posture. These guides walk you through the four pillars of securing your Maverics deployment so that sensitive data stays protected in transit, at rest, and under audit. The four pillars are: **TLS** for encrypting connections between clients, the Orchestrator, and your upstream applications; **secrets management** for keeping credentials out of config files by integrating with external vaults; **authorization policies** for controlling who can access what through multiple access control models -- roles, attributes, policies, and external policy decision points; and **compliance** for audit logging and regulatory reporting. Work through them in any order -- each guide stands on its own. ## Guides Define named TLS profiles, bind them to the HTTP listener with http.tls, and configure backend TLS for upstream connections Configure secret providers via environment variables and CLI flags -- HashiCorp Vault, AWS Secrets Manager, Azure Key Vault, and more with namespace.key references Define authentication policies with idps, nested and/or authorization rules, and OPA policies for flexible access control across RBAC, ABAC, PBAC, and external PDP models Configure security features for SOC2, HIPAA, and GDPR compliance -- TLS, secrets, policies, logging, and session management checklist ## Related Pages Complete configuration reference for TLS certificates, HTTPS listeners, and security settings Detailed configuration for each supported secret provider -- Vault, AWS, Azure, Delinea, and environment variables Deploy, monitor, and scale the Orchestrator in production environments Configure SSO, SAML federation, and identity provider migration # Configure Authorization Policies Source: https://docs.strata.io/guides/security/policies By the end of this guide, you will have a Maverics Orchestrator enforcing authorization policies on every request -- evaluating user attributes, roles, and context to determine whether access is allowed. ## Authentication vs. Authorization Before diving in, it helps to understand the distinction between these two concepts because they are often confused. **Authentication** answers the question "Who is this user?" -- it verifies identity through credentials like passwords, OIDC tokens, or SAML assertions. **Authorization** answers the question "What is this user allowed to do?" -- it checks whether an authenticated user has permission to access a specific resource or perform a specific action. The Maverics Orchestrator handles both. Your [authentication configuration](/guides/authentication/overview) verifies user identity. The authorization policies in this guide control what those authenticated users can access. Authentication always happens first -- you cannot authorize a user you have not identified. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed it yet, follow the [Quick Start guide](/guides/getting-started/quick-start) first. * **An identity provider connected** -- Your Orchestrator should be authenticating users against an identity provider. The Quick Start or [SSO guides](/guides/authentication/overview) cover this. * **Users authenticating successfully** -- Before adding authorization, confirm that users can log in and access your applications without policy restrictions. ## Configure Policies ### Choose your authorization approach The Orchestrator provides different authorization mechanisms depending on the mode you are running. Choose the approach that matches your deployment: * **HTTP Proxy** -- Uses location-based policies with declarative `and`/`or` rules per URL path. Each policy binds to a route and evaluates user attributes against conditions you define. See [HTTP Proxy authorization](#http-proxy) below. * **OIDC Provider and SAML Provider** -- Uses app-level authorization with declarative rules. OIDC Provider also supports OPA token minting policies. Authorization is configured on the app itself rather than per-location. See [OIDC and SAML Provider authorization](#oidc-and-saml-provider) below. * **MCP Bridge and MCP Proxy** (AI Identity Gateway) -- Uses OPA-based inbound authorization exclusively. Policies written in Rego evaluate per-tool invocations with access to MCP-specific context. See [OPA Authorization (AI Identity Gateway)](#opa-authorization-ai-identity-gateway) below. * **LDAP Provider** -- Handles authorization entirely through Service Extensions. There are no declarative authorization rules. See the [Service Extensions reference](/reference/orchestrator/service-extensions) for the `authenticateSE` and `searchSE` hooks. Not sure which mode applies? See [Choosing a Mode](/guides/authentication/choosing-a-mode). ### HTTP Proxy In HTTP Proxy mode, authorization is configured per-location within the `policies` array on each app. Each policy specifies a URL path, the identity providers that handle authentication, and optionally the authorization rules that control access after authentication. Before configuring authorization rules, you need a policy that binds your identity provider connectors to application routes. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Policy model overview screen in Maverics Console showing access control configuration options Define policies on your app with authentication connector bindings: ```yaml maverics.yaml theme={null} apps: - name: my-app type: proxy upstream: https://backend.example.com routePatterns: - "app.example.com" policies: - location: "/" authentication: idps: ["azure", "ldap"] ``` | Field | Description | | ------------------------------------------------ | ---------------------------------------------------------------------------- | | `policies[].location` | URL path this policy applies to (must be unique per app) | | `policies[].authentication.idps` | Connector names for authentication -- must match `connectors[].name` entries | | `policies[].authentication.allowUnauthenticated` | Allow unauthenticated access to this location (default: `false`) | | `policies[].decision.lifetime` | Authorization decision cache TTL (duration string, e.g., `"5m"`) | The `idps` array references connectors by name. The Orchestrator will redirect unauthenticated users to the first listed identity provider for login. Authorization rules determine whether an authenticated user is allowed to access a resource. Rules support nested `and`/`or` conditions with four comparison operators: `equals`, `notEquals`, `contains`, and `notContains`. The Orchestrator supports multiple access control models, and you can combine them: **RBAC (Role-Based Access Control)** assigns permissions based on roles. A user has one or more roles (like "admin," "editor," or "viewer"), and each role grants access to specific resources. RBAC is straightforward and works well when your access patterns align with job functions. **ABAC (Attribute-Based Access Control)** makes decisions based on attributes -- properties of the user, the resource, or the request context. Attributes can include things like department, location, or any claim from the identity provider. **PBAC (Policy-Based Access Control)** makes decisions based on centralized policies evaluated against request context, user attributes, and environmental conditions. PBAC generalizes RBAC and ABAC by expressing access rules as policies that can incorporate any combination of roles, attributes, and contextual factors. **External PDP (Policy Decision Point)** integration delegates authorization decisions to an external policy engine -- such as OPA, Cedar, or a custom PDP -- for organizations that maintain centralized policy engines across multiple systems. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Policy definition screen in Maverics Console showing role and attribute condition builders **Allow all authenticated users** (simplest authorization): ```yaml maverics.yaml theme={null} policies: - location: "/" authentication: idps: ["azure"] authorization: allowAll: true ``` **Simple role-based rule:** ```yaml maverics.yaml theme={null} policies: - location: "/admin" authentication: idps: ["azure"] authorization: rules: - and: - contains: ["{{ azure.groups }}", "admin-group"] ``` **Nested and/or rules** for complex access control: ```yaml maverics.yaml theme={null} policies: - location: "/" authentication: idps: ["azure", "ldap"] authorization: rules: - and: - equals: ["{{ ldap.role }}", "admin"] - contains: ["{{ ldap.memberOf }}", "cn=managers"] - or: - equals: ["{{ http.request.method }}", "GET"] - notContains: ["{{ ldap.department }}", "restricted"] rulesAggregationMethod: "and" ``` In this example: the first rule requires the user to be an admin AND a member of the managers group. The second rule allows GET requests OR users not in the restricted department. Both rules must pass (`rulesAggregationMethod: "and"`). **Operators:** | Operator | Description | Operands | | ------------- | ----------------------------- | ---------- | | `equals` | Exact string match | 2 operands | | `notEquals` | Inverse exact match | 2 operands | | `contains` | Substring or membership check | 2 operands | | `notContains` | Inverse substring/membership | 2 operands | **Operand formats:** * `{{ connector.attribute }}` -- claim from a named connector (e.g., `{{ azure.groups }}`) * `{{ http.request.method }}` -- HTTP request method * `"literal"` -- static comparison value See [Authorization Reference](/reference/orchestrator/authorization) for the complete rule syntax and per-mode comparison. Start with broad policies and refine as needed. A common pattern is to require authentication on all routes first, then add access control restrictions to specific paths. You can always tighten access later without disrupting users who already have the right permissions. For authorization logic that goes beyond declarative rules, HTTP Proxy mode supports two Service Extension hooks: * **`isAuthorizedSE`** runs after declarative rule evaluation and can override or supplement the result. This lets you implement dynamic authorization checks -- for example, querying an external system, checking time-of-day restrictions, or applying business logic that cannot be expressed as `and`/`or` rules. Configure at `policies[].authorization.isAuthorizedSE`. See [Service Extensions](/reference/orchestrator/service-extensions). * **`handleUnauthorizedSE`** customizes the response when authorization is denied. Instead of the default 403 Forbidden page, you can render a custom error page, redirect to a request-access workflow, or log additional context. Configure at `apps[].handleUnauthorizedSE`. This hook is mutually exclusive with the `unauthorizedPage` setting. See [Service Extensions](/reference/orchestrator/service-extensions). ### OIDC and SAML Provider In OIDC Provider and SAML Provider modes, authorization is configured at the app level (`apps[].authorization`) rather than per-location. The same declarative rule syntax is available -- `allowAll`, `rules`, and `rulesAggregationMethod` -- but the configuration lives directly on the app instead of inside a `policies[]` block. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. **Allow all authenticated users:** ```yaml maverics.yaml theme={null} apps: - name: my-oidc-app type: oidc authorization: allowAll: true ``` **Role-based rule at the app level:** ```yaml maverics.yaml theme={null} apps: - name: my-oidc-app type: oidc authorization: rules: - and: - contains: ["{{ azure.groups }}", "app-users"] rulesAggregationMethod: "and" ``` The rule syntax (`and`, `or`, operators, operand formats) is the same as HTTP Proxy. The only difference is the config location: `apps[].authorization` instead of `apps[].policies[].authorization`. OIDC Provider mode supports OPA policies for token minting authorization. This provides a governance layer over which tokens the Orchestrator issues -- you can enforce policies on token exchange based on user attributes, client identity, or environmental conditions. This does not apply to SAML Provider mode, which issues assertions rather than tokens. ```yaml maverics.yaml theme={null} apps: - name: my-oidc-app type: oidc authorization: tokenMinting: accessToken: policies: - name: token-governance rego: | package orchestrator default result := {"allowed": true} # Deny tokens requested with the client_credentials grant type result := {"allowed": false, "internal_message": "client_credentials not permitted"} { input.request.oauth.grant_type == "client_credentials" } ``` OPA token minting policies must define a `result` object containing an `allowed` field. The Orchestrator denies token issuance if `allowed` is `false`. You can optionally include `internal_message` (logged server-side) and `external_message` (returned to the client) fields. See [OPA Policy Output Schema](#opa-policy-output-schema) for the full output format. #### OIDC app input schema The following JSON shows the complete data available under `input` when evaluating an OIDC token minting policy. Values are demonstrative. ```json theme={null} { "source": { "ip": "192.168.1.100" }, "request": { "http": { "host": "idp.example.com", "method": "POST", "path": "/token", "headers": { "Content-Type": "application/x-www-form-urlencoded", "User-Agent": "Go-http-client/1.1" } }, "oauth": { "client_id": "325859cf-5bbe-492f-b9e7-929f2bed1230", "scope": "read:users write:settings", "grant_type": "urn:ietf:params:oauth:grant-type:token-exchange", "subject_token": { "claims": { "scope": "api:read api:write" } }, "actor_token": { "claims": { "scope": "openid" } }, "response": { "access_token": { "claims": { "scope": "read:users write:settings", "aud": "https://api.example.com", "client_id": "325859cf-5bbe-492f-b9e7-929f2bed1230" } }, "scope": "read:users write:settings", "expires_in": 3600 } } } } ``` #### OIDC app example: enforce scope reduction on token exchange The following policy ensures that scopes are only reduced during token exchange flows. The requested scopes in the token exchange request must be a subset of the scopes in the `subject_token`. All other grant types are allowed without restriction. ```rego policy.rego theme={null} package orchestrator default result["allowed"] := false # Allow all non-token-exchange grant types. result["allowed"] if { input.request.oauth.grant_type != "urn:ietf:params:oauth:grant-type:token-exchange" } # Parse scopes from space-separated strings into sets. requested_scopes := {s | some s in split(input.request.oauth.scope, " "); s != ""} subject_scopes := {s | some s in split(input.request.oauth.subject_token.claims.scope, " "); s != ""} # For token exchange grants, allow if requested scopes are a subset of subject token scopes. result["allowed"] if { input.request.oauth.grant_type == "urn:ietf:params:oauth:grant-type:token-exchange" print("requested_scopes:", requested_scopes) print("subject_scopes:", subject_scopes) count(requested_scopes - subject_scopes) == 0 } result["internal_message"] := "requested scopes exceed subject_token scopes" if { not result.allowed } result["external_message"] := "invalid_scope" if { not result.allowed } ``` The `isAuthorizedSE` Service Extension hook is also available in OIDC Provider and SAML Provider modes. Configure at `apps[].authorization.isAuthorizedSE`. See [Service Extensions](/reference/orchestrator/service-extensions). ### AI Identity Gateway (OPA Authorization) In MCP Bridge and MCP Proxy modes (AI Identity Gateway), OPA is the only authorization mechanism. There are no declarative `and`/`or` rules. All authorization is handled through Rego policies that evaluate per-tool invocations with access to MCP-specific context such as tool name and arguments. Configure OPA via `authorization.inbound.opa` with a policy `name` and either `file` (path to a `.rego` file) or inline `rego`. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. OPA policy configuration screen in Maverics Console **Inline OPA policy:** ```yaml maverics.yaml theme={null} authorization: inbound: type: opa opa: name: my-auth-policy rego: | package orchestrator default result := {"allowed": false} # Allow the listUsers tool result := {"allowed": true} { input.request.mcp.type == "tool" input.request.mcp.tool.params.name == "listUsers" } # Allow the getUser tool result := {"allowed": true} { input.request.mcp.type == "tool" input.request.mcp.tool.params.name == "getUser" } ``` **File-based OPA policy:** ```yaml maverics.yaml theme={null} authorization: inbound: type: opa opa: name: my-auth-policy file: /etc/maverics/policies/auth.rego ``` For tool filtering configuration -- controlling which tools are exposed to MCP clients during `tools/list` -- see the [MCP Proxy App reference](/reference/orchestrator/applications/mcp-proxy#tool-filtering-opa). For the complete per-mode authorization comparison, see the [Authorization Reference](/reference/orchestrator/authorization#per-mode-authorization-differences). OPA policies must define a `result` object containing an `allowed` field. The Orchestrator denies the request if `allowed` is `false`. You can optionally include `internal_message` (logged server-side) and `external_message` (returned to the client) fields. See [OPA Policy Output Schema](#opa-policy-output-schema) for the full output format. #### MCP app input schema The input schema varies by policy type. Connection policies receive only the HTTP request context; inbound and listing policies additionally receive `input.request.mcp` with the request type in `mcp.type`. **Connection admission** — evaluated by the `connection` policy when the proxy establishes a new upstream session. No `mcp` context is present because no tool has been invoked yet: ```json theme={null} { "source": { "ip": "192.168.1.100" }, "request": { "http": { "host": "mcp.example.com", "method": "POST", "path": "/mcp", "headers": { "Authorization": "Bearer eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9...", "Content-Type": "application/json", "User-Agent": "MCP-Client/1.0" } } } } ``` **Tool call** (`mcp.type: "tool"`) — evaluated by the `inbound` policy on every tool invocation: ```json theme={null} { "source": { "ip": "192.168.1.100" }, "request": { "http": { "host": "mcp.example.com", "method": "POST", "path": "/mcp", "headers": { "Authorization": "Bearer eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9...", "Content-Type": "application/json", "User-Agent": "MCP-Client/1.0" } }, "mcp": { "type": "tool", "tool": { "params": { "name": "listUsers", "arguments": { "exampleBodyKeyAlpha": 10, "exampleBodyKeyBeta": true } } } } } } ``` **Tool listing** (`mcp.type: "tools_list"`) — evaluated by the `listing` policy once per tool during a `tools/list` request. The policy runs for each tool individually; tools the policy denies are removed before the response reaches the MCP client: ```json theme={null} { "source": { "ip": "192.168.1.100" }, "request": { "http": { "host": "mcp.example.com", "method": "POST", "path": "/mcp", "headers": { "Authorization": "Bearer eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9...", "Content-Type": "application/json", "User-Agent": "MCP-Client/1.0" } }, "mcp": { "type": "tools_list", "response": { "tools_list": { "name": "listUsers" } } } } } ``` #### MCP app example: JWT-based tool authorization The following policy grants access to the `get_ticket_price` tool only if the `Authorization` header contains a JWT with the `tickets:read` scope. All other tools and requests are denied by default. ```rego policy.rego theme={null} package orchestrator # Default deny policy - all requests are denied unless explicitly allowed default result["allowed"] := false # Decode the bearer token's claims. jwt.parse_bearer strips the "Bearer " # prefix and returns the payload, or undefined if the header is absent or # does not carry a JWT -- in which case every rule below fails and the # default deny applies. jwt_payload := jwt.parse_bearer(input.request.http.headers.Authorization) # Allows access to the get_ticket_price tool if the token contains # the tickets:read scope. Logs the tool name, client ID, and subject # for audit purposes. result["allowed"] if { print("request made to tool: ", input.request.mcp.tool.params.name) input.request.mcp.tool.params.name == "get_ticket_price" print("request made with client of: ", jwt_payload.client_id) contains(jwt_payload.scope, "tickets:read") print("access granted to subject:", jwt_payload.sub) } result["internal_message"] := "access is only permitted to the 'get_ticket_price' tool with tickets:read scope" if { not result.allowed } result["external_message"] := "unauthorized, contact support@example.com" if { not result.allowed } ``` #### Connection admission example: check permitted MCP servers claim The following policy gates upstream session establishment to bearers whose JWT contains a custom `permitted_mcp_servers` claim that includes the target server name. An IdP stamps this claim with the list of MCP servers the agent is authorized to reach; the policy checks membership before the session is opened. Because the admission decision is sticky for the lifetime of the session, this check runs once at connect time rather than on every tool call. ```rego connection.rego theme={null} package orchestrator default result["allowed"] := false jwt_payload := jwt.parse_bearer(input.request.http.headers.Authorization) result["allowed"] if { "mission-control" in jwt_payload.permitted_mcp_servers } result["internal_message"] := "bearer token does not permit access to this MCP server" if { not result["allowed"] } result["external_message"] := "unauthorized: MCP server access not granted" if { not result["allowed"] } ``` #### Tool Filtering example: allowlist tools exposed to the MCP client The following policy exposes only the tools in the permitted set. The MCP client receives only these tools in its `tools/list` response -- everything else is hidden, reducing the capabilities available to the AI agent. ```rego listing.rego theme={null} package orchestrator default result["allowed"] := false # Tools visible to downstream MCP clients allowed_tools := {"listUsers", "getUser", "searchUsers"} result["allowed"] if { input.request.mcp.type == "tools_list" input.request.mcp.response.tools_list.name in allowed_tools } result["internal_message"] := "tool is not in the allowed set" if { not result["allowed"] } ``` #### Tool Filtering example: scope-based tool exposure The following policy exposes a different set of tools depending on the agent's JWT scopes. `ticketService:write` is a superset of `ticketService:read`: agents with only `ticketService:read` see read-only tools; agents with `ticketService:write` see both read and write tools. This narrows each agent's attack surface to exactly what it needs. ```rego listing.rego theme={null} package orchestrator default result["allowed"] := false jwt_payload := jwt.parse_bearer(input.request.http.headers.Authorization) # Read-only tools available to agents with ticketService:read or ticketService:write read_tools := {"listTickets", "getTicket", "searchTickets"} # Write tools restricted to agents with the ticketService:write scope write_tools := {"createTicket", "updateTicket", "closeTicket"} result["allowed"] if { input.request.mcp.type == "tools_list" input.request.mcp.response.tools_list.name in read_tools some s in ["ticketService:read", "ticketService:write"] contains(jwt_payload.scope, s) } result["allowed"] if { input.request.mcp.type == "tools_list" input.request.mcp.response.tools_list.name in write_tools contains(jwt_payload.scope, "ticketService:write") } result["internal_message"] := "tool not permitted for this agent's scope" if { not result["allowed"] } ``` ### Rego Built-in Functions In addition to the standard [OPA built-in functions](https://www.openpolicyagent.org/docs/policy-reference#built-in-functions), the Orchestrator registers its own built-ins. These are available in every OPA policy the Orchestrator evaluates -- OIDC token minting, MCP connection, MCP inbound, and MCP tool filtering. #### `jwt.parse_bearer` Decodes the claims from a bearer token in a single call, replacing the `startswith` / `substring` / `io.jwt.decode` sequence that policies would otherwise need to extract a JWT from an `Authorization` header. ```rego theme={null} jwt.parse_bearer(header_value) ``` | Parameter | Type | Description | | -------------- | ------ | ------------------------------------------------------------------------------------------------------------------------------ | | `header_value` | String | The full `Authorization` header value, including the `Bearer ` scheme -- typically `input.request.http.headers.Authorization`. | Returns an object containing the token's payload claims. The auth-scheme is matched case-insensitively, per [RFC 6750 section 2.1](https://datatracker.ietf.org/doc/html/rfc6750#section-2.1), so `Bearer`, `bearer`, and `BEARER` are all accepted. The credentials that follow are decoded exactly as sent. **Usage:** ```rego policy.rego theme={null} package orchestrator default result["allowed"] := false claims := jwt.parse_bearer(input.request.http.headers.Authorization) result["allowed"] if { contains(claims.scope, "tickets:read") } ``` **Undefined results** The function returns undefined -- rather than an error -- when it cannot produce claims. This happens when: * The `Authorization` header is missing or empty. * The header does not use the `Bearer` auth-scheme (for example, `Basic`). * The value after the scheme is not a well-formed signed JWT. * The JWT payload is not a JSON object. Because an undefined value makes any rule referencing it fail, a policy with a `default result["allowed"] := false` rule denies the request in all of these cases. This is the recommended pattern -- write the default deny and let undefined claims fall through to it. `jwt.parse_bearer` decodes the token payload **without verifying its signature**, its expiry, or any other claim. It is a parsing helper, not a validation step -- a policy that trusts its output alone will accept a forged token. Token trust is established elsewhere. Configure `mcpProvider.authorization.oauth` with `servers[].tokenValidation` so the Orchestrator validates the bearer token before the request reaches your policy. That OAuth block is optional -- if it is absent, no token validation happens and a policy reading these claims is trusting unverified input. If you need to verify a signature inside the policy itself, use OPA's `io.jwt.decode_verify` instead. ### OPA Policy Output Schema All OPA policies -- whether for OIDC token minting or MCP inbound authorization -- must return a `result` object with the following structure: ```json theme={null} { "result": { "allowed": true, "internal_message": "user does not have necessary group membership: missing admin membership", "external_message": "unauthorized" } } ``` | Field | Required | Description | | ------------------------- | -------- | ----------------------------------------------------------------------------------- | | `result.allowed` | Yes | Whether access should be granted (`true`) or denied (`false`) | | `result.internal_message` | No | Details about the decision for server-side logs only. Not returned to clients. | | `result.external_message` | No | Details returned to the client and also logged. Use for user-facing error messages. | Use `print()` statements in your Rego policies to emit debug output to Orchestrator logs. This is useful for tracing which rules matched and inspecting input values during policy development. ### Test policy enforcement With policies defined and applied, test that they work as expected by making requests as users with different roles and attributes. Testing both the "allowed" and "denied" paths confirms that your policies are enforced correctly. Start (or restart) the Orchestrator to load your policy configuration: ```bash theme={null} maverics -config /etc/maverics/maverics.yaml ``` Test with a user who should have access: 1. **Log in** as a user whose roles or attributes satisfy the policy conditions 2. **Navigate** to the protected resource -- you should see the application content 3. **Verify** the request reached your upstream application (check application logs) Test with a user who should be denied: 1. **Log in** as a user who does not meet the policy conditions 2. **Navigate** to the same resource -- you should receive a 403 Forbidden response 3. **Verify** the request did not reach your upstream application **Success!** Your Orchestrator is enforcing authorization policies. Requests from authorized users proceed to your applications, and unauthorized requests are blocked before they ever reach your upstream services. ## Troubleshooting If a policy does not seem to take effect, verify that it is attached to the correct application route. A defined but unattached policy is inert -- it exists in the configuration but does not affect any traffic. Also check that the route path pattern matches the URLs you are testing. The Orchestrator logs which policies are evaluated on each request when debug logging is enabled. If a user is denied access when you expect them to be allowed, check the user's claims from the identity provider. The most common cause is a mismatch between the role or attribute name in your policy and the actual claim value from the IdP. For example, your policy may check for a role called "admin" but the IdP sends "Admin" (case matters). Enable debug logging to see the exact claims the Orchestrator receives and the policy evaluation result. If a policy references an attribute that the identity provider does not include in its token or assertion, the policy evaluation fails because the attribute is missing. Verify that your identity provider is configured to include the needed claims (roles, groups, department, or custom attributes) in the token it sends to the Orchestrator. Check the [Identity Fabric reference](/reference/orchestrator/identity-fabric) for details on claim mapping for your specific provider. ## Related Pages Return to the Security guides hub for TLS, secrets, policies, and compliance Per-mode authorization differences, enforcement behavior, and OPA policy patterns Complete configuration reference for authorization rules, operators, and policy syntax Configure SSO, SAML federation, and identity provider connections that policies build on Custom authorization logic via isAuthorizedSE, handleUnauthorizedSE, and other SE hooks Log policy decisions and authorization events for compliance reporting # Manage Secrets Source: https://docs.strata.io/guides/security/secrets-management By the end of this guide, you will have a Maverics Orchestrator that retrieves all sensitive configuration values -- API keys, client secrets, certificates -- from your organization's secret management system rather than from files or environment variables. **Console terminology:** In the Maverics Console, Orchestrator instances and configuration delivery are managed through **Deployments**. When working directly with YAML, configuration is managed as files delivered via the `-config` flag or `MAVERICS_CONFIG` environment variable. ## Why External Secret Providers? Secrets are sensitive values that your Orchestrator needs to function -- things like identity provider client secrets, API keys for upstream services, TLS private keys, and database passwords. Storing these directly in configuration files or environment variables creates risk: anyone with access to the file system or process environment can read them, and they are easy to accidentally commit to version control. External secret providers solve this problem by storing secrets in a dedicated, access-controlled system. The Orchestrator fetches secrets at runtime using authenticated API calls, which means the actual secret values never appear in your config files. Providers like HashiCorp Vault, AWS Secrets Manager, and Azure Key Vault also offer features like automatic rotation, audit logging, and fine-grained access policies -- giving you centralized control over who and what can access each secret. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed it yet, follow the [Quick Start guide](/guides/getting-started/quick-start) first. * **Access to a secret provider** -- You need an account and appropriate permissions on one of the supported providers: [HashiCorp Vault](/reference/orchestrator/configuration/secret-providers/hashicorp-vault), [AWS Secrets Manager](/reference/orchestrator/configuration/secret-providers/aws-secrets-manager), [Azure Key Vault](/reference/orchestrator/configuration/secret-providers/azure-key-vault), [Delinea Secret Server](/reference/orchestrator/configuration/secret-providers/delinea), [CyberArk Conjur](/reference/orchestrator/configuration/secret-providers/conjur), [CyberArk CCP](/reference/orchestrator/configuration/secret-providers/cyberark-ccp), or a [Secret File](/reference/orchestrator/configuration/secret-providers/environment) for development. ## Integrate a Secret Provider The Maverics Orchestrator supports 7 secret provider types, each suited to different environments and organizational requirements. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Secret provider selection screen in Maverics Console showing supported providers Secret providers are not configured in YAML. They are configured via the `MAVERICS_SECRET_PROVIDER` environment variable or the `-secretProvider` CLI flag. The table below lists all supported providers. | Provider | URL Scheme | Best For | | ------------------------------------------------------------------------------------------------- | ----------------------------------- | ------------------------------------------------------------------- | | [HashiCorp Vault](/reference/orchestrator/configuration/secret-providers/hashicorp-vault) | `hashivault://` or `hashivaults://` | Multi-cloud, on-premises -- dynamic secrets, automatic rotation | | [AWS Secrets Manager](/reference/orchestrator/configuration/secret-providers/aws-secrets-manager) | `awssecretsmanager://` | AWS-native deployments -- IAM integration, cross-region replication | | [Azure Key Vault](/reference/orchestrator/configuration/secret-providers/azure-key-vault) | `azurekeyvault://` | Azure-native deployments -- managed identity, HSM backing | | [Delinea Secret Server](/reference/orchestrator/configuration/secret-providers/delinea) | `delinea://` | Enterprise PAM -- session recording, approval workflows | | [CyberArk Conjur](/reference/orchestrator/configuration/secret-providers/conjur) | `conjur://` | DevOps-oriented secrets for CI/CD and containers | | [CyberArk CCP](/reference/orchestrator/configuration/secret-providers/cyberark-ccp) | `cyberarkccp://` | CyberArk Central Credential Provider | | [Secret File](/reference/orchestrator/configuration/secret-providers/environment) | `secretfile://` | Development and testing -- local file-based secrets | For most production deployments, choose the provider that matches your cloud platform or existing secret management infrastructure. See [Secret Providers Reference](/reference/orchestrator/configuration/secret-providers) for detailed configuration documentation for each provider. Secret providers are configured via the `MAVERICS_SECRET_PROVIDER` environment variable or the `-secretProvider` CLI flag -- not in YAML configuration. Only one secret provider may be active at a time. The Orchestrator authenticates to the secret provider at startup and maintains the connection for the lifetime of the process. If the connection drops, the Orchestrator retries automatically. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Secret provider connection configuration screen showing authentication fields Secret providers are configured via environment variable or CLI flag, not in YAML. The examples below show shell commands for the three most common providers. **HashiCorp Vault:** ```bash theme={null} export MAVERICS_SECRET_PROVIDER="hashivault://vault.example.com:8200/secret/data/maverics?token=" ``` **AWS Secrets Manager:** ```bash theme={null} export MAVERICS_SECRET_PROVIDER="awssecretsmanager://us-east-1" ``` **Azure Key Vault:** ```bash theme={null} export MAVERICS_SECRET_PROVIDER="azurekeyvault://my-vault.vault.azure.net" ``` You can also pass the provider via the CLI flag instead of an environment variable: ```bash theme={null} maverics \ -config /etc/maverics/maverics.yaml \ -secretProvider "hashivault://vault.example.com:8200/secret/data/maverics?token=" ``` See [Secret Providers Reference](/reference/orchestrator/configuration/secret-providers) for provider-specific URL parameters and authentication options. The credentials used to connect to the secret provider itself (like a Vault token or Azure service principal) should have the minimum permissions needed -- typically read-only access to the specific secrets the Orchestrator uses. Follow the principle of least privilege. Once the secret provider is configured, replace hardcoded secret values in your Orchestrator configuration with secret references. A secret reference uses angle bracket syntax: ``. The Orchestrator resolves these references at startup by fetching the value from the configured provider. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Secret reference configuration screen showing how to reference secrets in connector settings Use `` syntax to reference secrets anywhere a sensitive value is needed: ```yaml maverics.yaml theme={null} connectors: - name: my-idp type: oidc oauthClientID: "my-client-id" oauthClientSecret: oidcWellKnownURL: "https://idp.example.com/.well-known/openid-configuration" caches: - name: "shared-redis" type: "redis" redis: addresses: - "redis.example.com:6379" password: tls: "default": certFile: "/etc/maverics/certs/server.pem" keyFile: "/etc/maverics/certs/server-key.pem" ``` In this example: * `` -- The `maverics` namespace and `oidc-client-secret` key map to the secret path in your provider * `` -- Same namespace, different key for the Redis password The Orchestrator resolves all `` references during startup. The rest of the system works exactly the same -- the only difference is where the value comes from. Secret references work in any string field in the YAML configuration. Use them for client secrets, passwords, API keys, encryption keys, and any other sensitive value. After configuring secret references, restart the Orchestrator and verify that it successfully retrieves all secrets from the provider. The Orchestrator resolves secret references during startup, so any issues will appear in the startup logs. Start (or restart) the Orchestrator: ```bash theme={null} maverics -config /etc/maverics/maverics.yaml ``` Check the logs for successful secret resolution. The Orchestrator logs when it connects to the secret provider and when it resolves each secret reference. Look for confirmation that all secrets were retrieved without errors. Verify the health endpoint to confirm the Orchestrator started successfully with resolved secrets: ```bash theme={null} curl -s https://localhost:9443/status | jq . ``` If the health endpoint returns `{"status": "up"}`, your secrets are resolving correctly -- the Orchestrator was able to use the retrieved credentials to connect to your identity providers and other services. **Success!** Your Orchestrator is retrieving secrets from your external provider at runtime. No sensitive values are stored in configuration files, and your secrets benefit from the provider's rotation, access control, and audit logging features. ## Troubleshooting The Orchestrator logs an error if it cannot find a secret at the referenced path in the provider. Verify that the secret path in your configuration exactly matches the path in your provider -- paths are case-sensitive and must include the full hierarchy (for Vault, this includes the mount path and secret path). Also check that the secret has been created in the provider before the Orchestrator tries to read it. If the Orchestrator cannot authenticate to your secret provider, check that the connection credentials are correct and have not expired. For Vault, verify the token has not been revoked. For AWS, verify the IAM role or access keys have the correct permissions. For Azure, verify the service principal credentials and that the Key Vault access policy grants the necessary permissions. The Orchestrator logs the specific authentication error during startup. By default, the Orchestrator resolves secrets at startup. If your provider rotates a secret while the Orchestrator is running, the Orchestrator continues using the previously fetched value until it is restarted. For production deployments that require seamless rotation, check whether your secret provider supports a notification mechanism or configure the Orchestrator's secret refresh interval to periodically re-fetch values. ## Related Pages Return to the Security guides hub for TLS, secrets, policies, and compliance Detailed configuration for each supported provider -- Vault, AWS, Azure, Delinea, CyberArk Conjur, CyberArk CCP, and Secret File Store TLS certificates and private keys as secrets for secure certificate management Deploy and monitor the Orchestrator in production -- including secret management best practices # Configure TLS Source: https://docs.strata.io/guides/security/tls By the end of this guide, you will have a Maverics Orchestrator with TLS encryption on all connections -- HTTPS for client-facing traffic and optionally TLS for backend connections to upstream applications. **Console terminology:** In the Maverics Console, Orchestrator instances and configuration delivery are managed through **Deployments**. When working directly with YAML, configuration is managed as files delivered via the `-config` flag or `MAVERICS_CONFIG` environment variable. ## What Is TLS? TLS (Transport Layer Security) is the protocol that encrypts data as it travels between two systems over a network. When you see "HTTPS" in a browser URL, that is HTTP running over TLS -- meaning the connection between the browser and the server is encrypted so that no one in between can read or tamper with the data. For the Maverics Orchestrator, TLS matters in two places. First, the connection between your users' browsers and the Orchestrator -- this is called **TLS termination** because the Orchestrator accepts the encrypted HTTPS connection and decrypts it. Second, the connection between the Orchestrator and your upstream applications -- this is called **backend TLS** and is optional but recommended in production environments where the Orchestrator and your apps are on different networks. ## Prerequisites * **A running Maverics Orchestrator** -- If you have not installed it yet, follow the [Quick Start guide](/guides/getting-started/quick-start) first. * **A TLS certificate and private key** -- You can use a certificate from a certificate authority (CA) like Let's Encrypt, your organization's internal CA, or a self-signed certificate for testing. The certificate should be in PEM format. ## Configure TLS The Orchestrator uses **named TLS profiles** to manage certificates and encryption settings in one place. Each profile is a named entry under the `tls` top-level key. Once defined, a profile can be referenced by the HTTP listener, identity connectors, and [external cache](/reference/orchestrator/caches) connections -- so you configure your certificate paths and TLS constraints once and reuse them wherever encrypted connections are needed. A TLS certificate is a file that proves your server's identity to clients. It comes in a pair: a **certificate file** (the public part, often ending in `.crt` or `.pem`) and a **private key file** (the secret part, often ending in `.key`). The certificate authority that issued your certificate vouches that it belongs to your domain. For production deployments, use a certificate from a trusted certificate authority. [Let's Encrypt](https://letsencrypt.org/) provides free certificates that are trusted by all major browsers. Your organization may also have an internal CA that issues certificates for internal services. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. TLS certificate upload screen in Maverics Console showing certificate and key file fields Define one or more named TLS profiles under the `tls` top-level key: ```yaml maverics.yaml theme={null} tls: "default": certFile: "/etc/maverics/certs/server.pem" keyFile: "/etc/maverics/certs/server-key.pem" minVersion: "1.2" "upstream-idp": caFile: "/etc/maverics/certs/idp-ca.pem" insecureSkipVerify: false ``` The key fields are `certFile` and `keyFile` for the certificate pair, `minVersion` to set the minimum TLS version (defaults to `"1.2"`), and `caFile` when connecting to upstream servers with custom CA certificates. You can also set `maxVersion` to cap the TLS version -- for example, setting both `minVersion` and `maxVersion` to `"1.2"` restricts the profile to TLS 1.2 only. See the [TLS Reference](/reference/orchestrator/tls-security#profile-fields) for the complete list of profile fields including mTLS, OCSP, CRL, and cipher suite options. Store your private key securely. If you are managing multiple secrets, consider using a [secret provider](/guides/security/secrets-management) to keep the private key out of the filesystem and retrieve it at runtime from HashiCorp Vault, AWS Secrets Manager, or another provider. With your TLS profile defined, bind it to the Orchestrator's HTTP listener. This is where **TLS termination** happens -- the Orchestrator accepts encrypted connections from clients and decrypts them internally. Set `http.tls` to the name of the TLS profile you defined in the previous step. This is the critical wiring step that connects your certificate to the HTTP server. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. HTTPS listener configuration screen in Maverics Console showing port, certificate path, and key path Reference the named TLS profile from the `http` configuration: ```yaml maverics.yaml theme={null} http: address: "0.0.0.0:9443" tls: "default" tls: "default": certFile: "/etc/maverics/certs/server.pem" keyFile: "/etc/maverics/certs/server-key.pem" minVersion: "1.2" ``` The `http.tls` field takes the name of a profile defined under the `tls` key -- in this case, `"default"`. The Orchestrator uses this profile for all incoming HTTPS connections. If you need to serve multiple domains with different certificates, use `http.hosts` instead of `http.tls` for SNI-based certificate selection: ```yaml maverics.yaml theme={null} http: address: "0.0.0.0:443" hosts: - serverName: "app.example.com" tls: "app-cert" - serverName: "api.example.com" tls: "api-cert" ``` `http.tls` and `http.hosts` are mutually exclusive. Use `http.tls` for a single TLS profile on all connections, or `http.hosts` for SNI-based virtual hosting with different TLS profiles per server name. See the [TLS Reference](/reference/orchestrator/tls-security) for the complete set of TLS configuration options -- including cipher suite selection, minimum TLS version, and client certificate authentication. Backend TLS secures the connection between the Orchestrator and your upstream applications. This step is optional -- if the Orchestrator and your apps run on the same host or in a trusted private network, you may not need it. But if traffic crosses network boundaries or your compliance requirements mandate encryption everywhere, backend TLS ensures data stays encrypted for the entire journey. When you enable backend TLS, the Orchestrator connects to your upstream application over HTTPS instead of HTTP. If your upstream uses a self-signed certificate or an internal CA, you will need to provide the CA certificate so the Orchestrator can verify the connection. **Console UI documentation is coming soon.** This section will walk you through configuring this component using the Maverics Console's visual interface, including step-by-step screenshots and field descriptions. Backend TLS configuration screen in Maverics Console showing upstream certificate verification settings Create a TLS profile for upstream connections and reference it in your app configuration: ```yaml maverics.yaml theme={null} tls: "default": certFile: "/etc/maverics/certs/server.pem" keyFile: "/etc/maverics/certs/server-key.pem" minVersion: "1.2" "upstream": caFile: "/etc/maverics/certs/upstream-ca.pem" insecureSkipVerify: false http: address: "0.0.0.0:9443" tls: "default" apps: - name: my-app type: proxy upstream: https://backend.example.com tls: "upstream" routePatterns: - "app.example.com" ``` The proxy app's `tls` field references a named TLS profile used for the connection to the upstream backend. The `caFile` in the profile lets the Orchestrator verify the upstream server's certificate. For mutual TLS (mTLS) with the upstream, include `certFile` and `keyFile` in the upstream profile to present a client certificate. Never set `insecureSkipVerify: true` in production. This disables certificate verification, making the connection vulnerable to man-in-the-middle attacks. Use it only for local development with self-signed certificates. Some compliance frameworks and legacy integrations require specific TLS version constraints. The `minVersion` and `maxVersion` fields let you control exactly which TLS versions the Orchestrator accepts. Three common patterns: **Production default (TLS 1.2+)** -- Accept TLS 1.2 and above. This is the default when only `minVersion` is set: ```yaml maverics.yaml theme={null} tls: "default": certFile: "/etc/maverics/certs/server.pem" keyFile: "/etc/maverics/certs/server-key.pem" minVersion: "1.2" ``` **TLS 1.3 only** -- Require the latest protocol version. Clients that do not support TLS 1.3 will be rejected: ```yaml maverics.yaml theme={null} tls: "tls13-only": certFile: "/etc/maverics/certs/server.pem" keyFile: "/etc/maverics/certs/server-key.pem" minVersion: "1.3" ``` **TLS 1.2 only** -- Pin to TLS 1.2 for systems that require it. Setting both `minVersion` and `maxVersion` to `"1.2"` prevents TLS 1.3 negotiation: ```yaml maverics.yaml theme={null} tls: "tls12-only": certFile: "/etc/maverics/certs/server.pem" keyFile: "/etc/maverics/certs/server-key.pem" minVersion: "1.2" maxVersion: "1.2" ``` `maxVersion` requires Orchestrator v2026.02.3 or later. Earlier versions only support `minVersion`. With TLS configured, restart the Orchestrator and verify that HTTPS connections are working correctly. A simple test confirms that the certificate is being served and the connection is encrypted. Start (or restart) the Orchestrator to pick up your TLS configuration: ```bash theme={null} maverics -config /etc/maverics/maverics.yaml ``` Test the HTTPS endpoint with curl: ```bash theme={null} curl -v https://your-orchestrator-domain:9443/status ``` The `-v` (verbose) flag shows the TLS handshake details. Look for lines showing the certificate subject, issuer, and that the handshake completed successfully. If you are using a self-signed certificate for testing, add the `-k` flag to skip certificate verification: ```bash theme={null} curl -vk https://localhost:9443/status ``` To verify the negotiated TLS version specifically, use `openssl`: ```bash theme={null} openssl s_client -connect localhost:9443 < /dev/null 2>/dev/null | grep "Protocol" ``` This outputs the protocol version (e.g., `TLSv1.2` or `TLSv1.3`), confirming your version constraints are in effect. You can also verify the full certificate details: ```bash theme={null} openssl s_client -connect localhost:9443 -showcerts < /dev/null ``` **Success!** Your Orchestrator is serving traffic over HTTPS with TLS encryption. Client connections are encrypted, and if you configured backend TLS, the connection to your upstream applications is encrypted too. ## Troubleshooting The Orchestrator logs an error at startup if it cannot find the certificate or key file at the configured path. Verify that the file paths in your configuration are absolute paths (not relative) and that the files are readable by the user running the Orchestrator. Common causes include typos in the file path, incorrect file permissions, or the certificate being stored in a different directory than expected. A TLS handshake failure means the client and server could not agree on how to encrypt the connection. This can happen when the certificate does not match the domain the client is connecting to (a hostname mismatch), when the certificate has expired, or when the client and server do not support any common TLS versions or cipher suites. Check the Orchestrator logs for the specific handshake error and verify that your certificate's Common Name (CN) or Subject Alternative Name (SAN) matches the domain you are connecting to. Browsers and clients need the full certificate chain -- your certificate plus any intermediate certificates from the CA -- to verify trust. If clients see a "certificate not trusted" error even though your certificate is valid, you may be missing intermediate certificates. Concatenate your certificate and the intermediate certificate(s) into a single PEM file, with your certificate first and the intermediates following in order. If clients receive "protocol version" or "no protocols available" errors, the client and server do not share a supported TLS version. Check your profile's `minVersion` and `maxVersion` settings against what the client supports. For example, if `minVersion` is `"1.3"` but the client only supports TLS 1.2, the handshake will fail. Use `openssl s_client -connect host:port` to see which protocol version is negotiated, or test with a specific version using `openssl s_client -tls1_2` or `-tls1_3`. If the Orchestrator and client cannot agree on a cipher suite, the connection fails with a "no cipher suites in common" error. This typically happens when `enabledCiphers` is set to a restrictive list that does not overlap with the client's supported ciphers. Verify your cipher list against the client's capabilities. Remember that `enabledCiphers` only affects TLS 1.2 -- TLS 1.3 cipher suites are fixed by the protocol and cannot be restricted. ## Related Pages Return to the Security guides hub for TLS, secrets, policies, and compliance Complete configuration reference for TLS profiles, cipher suites, mTLS, OCSP, and CRL settings Production deployment guide including TLS best practices and high availability Store TLS private keys and other credentials in an external secret provider # Architecture Source: https://docs.strata.io/introduction/architecture Maverics has two core components -- the **Orchestrator**, a lightweight, self-hosted runtime that handles identity workflows, and the **Console**, a cloud SaaS platform for configuration and deployment management. The Orchestrator operates in five modes, each addressing a different identity protocol or deployment pattern. ```mermaid theme={null} flowchart TB Console["Maverics Console (Cloud SaaS)"] Console -->|"Publishes signed config bundles"| Orch Orch["Orchestrator (Self-hosted)"] Orch --> OIDC["OIDC Provider"] Orch --> SAML["SAML Provider"] Orch --> Proxy["HTTP Proxy"] Orch --> LDAP["LDAP Provider"] Orch --> AI["AI Identity Gateway"] ``` ## The Orchestrator The Orchestrator is a lightweight, self-hosted runtime deployed alongside your applications. It coordinates identity workflows -- authentication, authorization, and protocol translation -- without requiring changes to application code. The Orchestrator is stateless by design. It pulls its configuration from the Console (as signed bundles) or from local YAML files, making it easy to scale horizontally and deploy in any environment. A single Orchestrator instance can operate in one or more of five modes simultaneously -- OIDC Provider, SAML Provider, HTTP Proxy, LDAP Provider, and AI Identity Gateway. Each mode addresses a specific identity protocol or deployment pattern. ## The Console The Console is Strata Identity's cloud SaaS management platform, available at [maverics.strata.io](https://maverics.strata.io). It provides a visual interface for configuring Orchestrators, managing deployments, and monitoring identity workflows. The Console is multi-tenant and multi-region. It publishes signed configuration bundles to Orchestrators -- ensuring that runtime configuration is cryptographically verified and tamper-resistant. Key capabilities include visual point-and-click configuration, deployment management across environments, and audit logging for compliance and troubleshooting. ## Deployment Modes The Orchestrator runs in one or more modes simultaneously on a single instance. Each mode is purpose-built for a specific identity protocol or pattern: * **OIDC Provider** -- Modern web and mobile SSO with OpenID Connect, including claim enrichment and IdP failover * **SAML Provider** -- Legacy enterprise federation with SAML 2.0 protocol translation * **HTTP Proxy** -- Protect applications without code modification by intercepting HTTP traffic * **LDAP Provider** -- Virtual directory for LDAP-dependent applications migrating to modern identity * **AI Identity Gateway** -- AI agent identity via MCP Bridge and MCP Proxy ## How They Work Together The Console publishes configuration, and the Orchestrator consumes it at runtime. This separation of control plane (Console) and data plane (Orchestrator) means your identity traffic never leaves your infrastructure -- only configuration flows through the cloud. You can configure the Orchestrator through the Console UI or YAML files. Both interfaces manage the same underlying Orchestrator, so you can choose the workflow that fits your team. The Orchestrator runs wherever your applications run -- cloud, on-premises, or hybrid environments. ## What's Next Explore core concepts in detail -- modes, interfaces, and deployment models. Detailed Orchestrator installation, configuration, and operational reference. # Concepts Source: https://docs.strata.io/introduction/concepts This page covers the foundational concepts behind Maverics -- modes, interfaces, and deployment models. Each concept links to detailed reference documentation for deeper exploration. ## Modes The Orchestrator operates in five modes, each addressing a different identity protocol or deployment pattern. | Mode | Protocol | Use Case | | ----------------------- | -------------- | ---------------------------------------------------------------- | | **OIDC Provider** | OpenID Connect | Modern web and mobile SSO with claim enrichment and IdP failover | | **SAML Provider** | SAML 2.0 | Legacy enterprise federation with protocol translation | | **HTTP Proxy** | HTTP | Protect applications without code modification | | **LDAP Provider** | LDAP | Virtual directory for LDAP-dependent applications | | **AI Identity Gateway** | MCP | AI agent identity via MCP Bridge and MCP Proxy | Modes can run simultaneously on a single Orchestrator instance -- deploy one binary that handles OIDC, SAML, and LDAP at the same time. ## Interfaces Two interfaces configure the same Orchestrator -- choose the one that fits your workflow. | Interface | Best For | Description | | ------------------------ | ------------------------- | --------------------------------------------------------------------------------------------------------- | | **Console UI** | Visual configuration | Web-based management at maverics.strata.io -- point-and-click setup, deployment management, audit logging | | **Configuration (YAML)** | Declarative configuration | Local configuration files checked into version control -- ideal for GitOps workflows | Both interfaces configure the same underlying Orchestrator -- changes made in one are reflected in the other. ## Deployment Models The Orchestrator is designed to run wherever your applications run. Three deployment models cover the most common environments: * **Cloud** -- Orchestrator runs in cloud infrastructure (AWS, Azure, GCP) alongside cloud-native applications. Ideal for teams with fully cloud-based identity stacks. * **On-premises** -- Orchestrator runs in data centers alongside legacy applications. Critical for enterprises with mainframe, LDAP, or on-prem web applications that cannot migrate to the cloud. * **Hybrid** -- A mix of cloud and on-premises Orchestrators managed from a single Console. This is the most common model for enterprises modernizing incrementally. The Console is always cloud-hosted (SaaS) regardless of where Orchestrators are deployed. ## What's Next Deploy your first Orchestrator and route an authentication request in minutes. Detailed reference documentation for each Orchestrator mode. # FAQ Source: https://docs.strata.io/introduction/faq Common questions about the Maverics platform organized by topic. Can't find your answer? [Contact support](https://strataidentity.my.site.com/support/s/). ## General Maverics is an identity orchestration platform from Strata Identity. It consists of two components: the Orchestrator (a lightweight identity abstraction layer deployed in your infrastructure) and the Console (a cloud-hosted management interface). Together they let you route, translate, and manage authentication across any combination of identity providers, protocols, and applications. The Orchestrator supports OIDC, SAML 2.0, LDAP, HTTP header-based authentication, and the Model Context Protocol (MCP) for AI identity. It can translate between these protocols, so a SAML application can authenticate against an OIDC provider (or vice versa) without application changes. The Identity Fabric is an architectural pattern where a lightweight abstraction layer (the Orchestrator) sits between applications and identity providers. It decouples applications from specific identity vendors, enabling incremental migration, protocol translation, and policy-based routing without modifying application code. No. Maverics is a commercial product. Contact [Strata Identity sales](https://strataidentity.my.site.com/support/s/) for licensing information. ## Getting Started The Orchestrator is distributed as a single binary and can run on Linux, in Docker containers, or on Kubernetes. Download it from the Console, deploy it to your environment, and point it at your configuration. See the [Quick Start guide](/guides/getting-started/quick-start) for step-by-step instructions. The Console is the recommended way to use Maverics. It provides visual configuration, centralized deployment management, audit logging, and config bundle publishing with cryptographic signing. While the Orchestrator can technically run standalone with local YAML files, the Console streamlines operations significantly and is how most customers manage their deployments. The Orchestrator is lightweight and runs on Linux (x86\_64 and ARM64), in Docker containers, or on Kubernetes. Specific resource requirements depend on traffic volume and the number of configured applications. ## Architecture The Orchestrator runs in your infrastructure -- on-premises, in the cloud (AWS, Azure, GCP), or both. It deploys as a lightweight binary alongside your applications. The Console is always cloud-hosted (SaaS). Yes. You can deploy multiple Orchestrator instances for high availability, geographic distribution, or workload isolation. All instances are managed from a single Console. Configuration is managed through the Console UI (visual, point-and-click) or YAML files (declarative, version-controlled). Both interfaces configure the same Orchestrator, so changes made in one are reflected in the other. A Config Bundle is a cryptographically signed package of configuration that the Console publishes to Orchestrators. Bundles are signed with ECDSA P-256 and verified by the Orchestrator before deployment, ensuring configuration integrity. ## Security Maverics integrates with external secret providers (HashiCorp Vault, AWS Secrets Manager, Azure Key Vault, CyberArk, Conjur, and Delinea). Secrets are never stored in configuration files -- the Orchestrator fetches them at runtime from your chosen provider. Yes. All communication between the Console and Orchestrators uses TLS. Config Bundles are additionally signed (ECDSA P-256) so the Orchestrator can verify they have not been tampered with. Visit the [Strata Trust Center](https://trust.strata.io) for current certifications, security practices, and compliance documentation. ## Licensing Contact [Strata Identity](https://strataidentity.my.site.com/support/s/) for licensing details. Licensing terms depend on deployment scale and use case. Contact [Strata Identity sales](https://strataidentity.my.site.com/support/s/) to discuss trial options. # Getting Started Source: https://docs.strata.io/introduction/getting-started New to Maverics? Start here. This page walks you through getting access to the Console and setting up your organization -- the foundation for everything else you'll do with Maverics. ## Step 1: Get Access to the Console The [Maverics Console](https://maverics.strata.io) is the management hub for your Maverics deployments. To get started: 1. **Request access** -- Contact your Strata account team or visit [Strata support](https://strataidentity.my.site.com/support/s/) to request a Console account for your organization 2. **Accept your invitation** -- You'll receive an email invitation to join your organization 3. **Log in** -- Sign in to the Console at [maverics.strata.io](https://maverics.strata.io) ## Step 2: Set Up Your Organization Once you're logged in, orient yourself with the Console: * **Organization settings** -- Review your organization name and member list under **Settings** * **Invite team members** -- Add colleagues who will help manage deployments and configurations * **Review audit logging** -- Every action in the Console is captured in the [audit log](/reference/console/audit-logs) for compliance and troubleshooting ## Step 3: Explore the Console With your organization set up, take a moment to explore the Console: * **Deployments** -- View and manage your Orchestrator deployments, each pairing a configuration with one or more running nodes * **Configuration** -- Browse the visual configuration editor where you define apps, routes, connectors, and policies * **Audit logs** -- Review a complete record of every action taken in your organization for compliance and troubleshooting ## Next Steps Your Console organization is set up and ready to go. Follow the hands-on guides to install the Orchestrator and configure your first identity workflow: Install the Orchestrator, connect an identity provider, and protect your first route Build a complete deployment with SSO, session management, and header-based identity propagation Understand how the Orchestrator, Console, and identity connectors work together Learn the key concepts -- modes, connectors, apps, routes, and policies # Glossary Source: https://docs.strata.io/introduction/glossary Key terms used throughout the Maverics documentation. Terms are listed alphabetically. ### App A configuration unit in the Orchestrator that represents a workload. Apps have a type that determines their behavior: HTTP Proxy, OIDC, SAML, MCP Bridge, or MCP Proxy. Some app types (such as HTTP Proxy) define Routes for path-based request handling, while others (such as OIDC or MCP Bridge) operate at the app level without routes. *** ### Audit Log A record of actions and events captured by the Console and Orchestrator. Console audit logs track API-level administrative actions (configuration changes, deployments, user management) while the Orchestrator emits structured logs for runtime authentication and authorization events as part of its telemetry output. See [Console Audit Logs](/reference/console/audit-logs) and [Orchestrator Telemetry](/reference/orchestrator/telemetry). *** ### Break-Glass Emergency procedures for making Orchestrator configuration changes outside the normal Console workflow when Console access is unavailable. Break-glass trades some security guarantees for operational continuity. See [Break-Glass procedures](/reference/console/break-glass). *** ### Cache A storage backend used by the Orchestrator for temporary data such as session state, tokens, and IdP metadata. Supported cache backends include Redis. See [Caches reference](/reference/orchestrator/caches). *** ### Claim A user identity attribute -- such as email, name, roles, or group membership -- passed from identity providers to applications inside tokens or assertions. The Orchestrator can enrich claims by pulling additional attributes from LDAP directories, databases, or APIs, and map them into the format each application expects. *** ### Config Bundle A compiled package of Orchestrator configuration published from the Console. Config bundles are cryptographically signed (ECDSA P-256) before deployment, and the Orchestrator verifies the signature as part of its validation before applying the new configuration. See [Config Publishing](/reference/console/config-publishing). *** ### Config Source The location from which the Orchestrator loads its configuration. Supported sources include local files, environment variables, the Console, S3, Azure Blob Storage, GCS, GitHub, and GitLab. See [Config Sources reference](/reference/orchestrator/configuration/config-sources). *** ### Connector An integration that connects the Orchestrator to an external identity provider (IdP). Connectors abstract the protocol details (OIDC, SAML, LDAP) so the Orchestrator can work with any provider through a uniform interface. See [Identity Fabric reference](/reference/orchestrator/identity-fabric). *** ### Console The cloud-hosted (SaaS) management interface for Maverics. Provides visual configuration, deployment management, and audit logging at [maverics.strata.io](https://maverics.strata.io). See [Console reference](/reference/console/overview). *** ### Custom API An HTTP endpoint defined directly in the Orchestrator configuration using service extensions. Custom APIs receive the full Orchestrator interface -- sessions, caches, secrets, and connectors -- for building health endpoints, webhooks, or custom integration logic. Custom APIs are configured as part of the Orchestrator's service extensions. *** ### Deployment A managed Orchestrator instance in the Console that pairs configuration with one or more running Orchestrator nodes. Deployments are typically named by purpose (e.g., "Auth Provider", "AI Identity Gateway", "xyz-app-proxy"). An environment may contain multiple deployments, and Console organizations can be used to separate environments. *** ### Failover Automatic fallback from a primary identity provider to one or more backup providers when the primary becomes unavailable. The Orchestrator tries connectors in configured order, routing authentication to the next available provider without requiring application changes. See [Concepts](/introduction/concepts). *** ### Feature Flag A configuration toggle that enables experimental or gated features in the Orchestrator. Feature flags prevent accidental use of alpha or beta capabilities in production. Feature flags are set under the `features` key in the Orchestrator configuration. *** ### Identity Fabric The collection of identity providers, directories, and authentication systems an organization uses to manage access -- Entra ID, Active Directory, Okta, LDAP directories, and others. The Maverics Orchestrator connects to this fabric through connectors, abstracting protocol differences and enabling protocol translation, incremental migration, and policy-based routing without modifying applications. See [Identity Fabric reference](/reference/orchestrator/identity-fabric). *** ### MCP (Model Context Protocol) An open standard protocol for AI agent-to-tool communication. MCP enables AI agents to discover and invoke tools through a structured interface. The Orchestrator supports MCP through its AI Identity Gateway mode. See [AI Identity Gateway](/reference/modes/ai-identity-gateway). *** ### MCP Bridge An AI Identity Gateway capability that translates REST APIs into MCP tools. The Orchestrator reads OpenAPI specifications and automatically generates MCP tool definitions, allowing AI agents to discover and call REST APIs through the MCP protocol without any API changes. See [MCP Bridge reference](/reference/orchestrator/applications/mcp-bridge). *** ### MCP Proxy An AI Identity Gateway capability that proxies connections to existing MCP servers while injecting identity context and enforcing authorization on every tool invocation. Used when MCP servers already exist but need identity awareness. See [MCP Proxy reference](/reference/orchestrator/applications/mcp-proxy). *** ### MRN (Maverics Record Number) A unique identifier assigned to every resource managed by the Maverics platform. MRNs follow a colon-delimited format that encodes region, organization, resource type, and resource ID: `maverics::::`. For example: `maverics:us-east:05951629-da9a-41e6-8364-5b0dc4b95884:deployments:2a476eb8-03b5-43d2-afc8-8c44c5a8a304`. *** ### Mode The operating mode of the Orchestrator, which determines what identity protocol it handles. Available modes: OIDC Provider, SAML Provider, HTTP Proxy, LDAP Provider, and AI Identity Gateway. A single Orchestrator can run multiple modes simultaneously. See [Concepts](/introduction/concepts). *** ### OPA (Open Policy Agent) A policy engine that evaluates authorization decisions using the Rego policy language. Used by the Orchestrator for fine-grained access control on API endpoints, MCP tool invocations, and advanced authorization scenarios. See [Authorization Policies guide](/guides/security/policies). *** ### Orchestrator The core runtime component of Maverics. A lightweight binary deployed in your infrastructure (on-premises, cloud, or hybrid) that intercepts, routes, and translates authentication requests between applications and identity providers. See [Orchestrator reference](/reference/orchestrator/overview). *** ### Policy A rule that determines whether an authenticated user or agent can access a specific resource. Policies evaluate user attributes, roles, and request context to make authorization decisions. The Orchestrator supports rule-based policies (role checks, attribute matching) and code-based policies (OPA/Rego). See [Authorization Policies guide](/guides/security/policies). *** ### Protocol Translation The Orchestrator's ability to convert between identity protocols -- OIDC, SAML, LDAP, and HTTP headers -- transparently. For example, a SAML-only application can authenticate users from an OIDC identity provider, or an LDAP-dependent application can authenticate against a cloud IdP, without modifying either side. *** ### Provider An Orchestrator operating mode where it acts as an identity provider. In OIDC Provider mode, the Orchestrator issues OpenID Connect tokens. In SAML Provider mode, it issues SAML assertions. Applications connect to the Orchestrator as their IdP, and the Orchestrator handles upstream authentication, protocol translation, and claim enrichment behind the scenes. *** ### Route A path-based rule within an App that determines how the Orchestrator handles requests matching a specific URL pattern. Routes define authentication requirements, upstream targets, and policy enforcement. *** ### Secret Provider An external secrets management service that the Orchestrator integrates with to retrieve sensitive values (API keys, certificates, passwords) at runtime. Supported providers include HashiCorp Vault, AWS Secrets Manager, Azure Key Vault, CyberArk, Conjur, and Delinea. See [Secret Providers reference](/reference/orchestrator/configuration/secret-providers). *** ### Service Extension Custom logic that extends the Orchestrator's behavior at specific points in the request processing pipeline. Service Extensions allow developers to add custom authentication, authorization, or transformation logic. *** ### Session Server-side state maintained by the Orchestrator for authenticated users. Sessions track authentication status, tokens, and user attributes across requests. See [Sessions reference](/reference/orchestrator/sessions). *** ### SOID (Secure Orchestrator ID) A stable identifier that uniquely identifies each Orchestrator instance in a deployment. The SOID is automatically derived at startup -- no manual setup is required. It remains stable across restarts on the same machine as long as the Orchestrator points to the same deployment in the Console (or the same local config file path when not using the Console). A 10-character prefix of the SOID appears as the `soid` field in every log entry, enabling log correlation across restarts and instance filtering in multi-node deployments. Available starting in **v2026.03.3**. See [Logging — Deployment Correlation](/reference/orchestrator/telemetry/logging#deployment-correlation). *** ### TLS Profile A named TLS configuration in the Orchestrator that specifies certificates, cipher suites, and minimum protocol versions for encrypted connections. See [TLS reference](/guides/security/tls). *** ### Token Exchange The process of exchanging one security token for another, following RFC 8693. Used for delegation (preserving both agent and user identity) or impersonation (acting on behalf of a user) scenarios. Common in AI Identity Gateway mode where agent tokens are exchanged for service-specific scoped tokens. # Welcome to Maverics Source: https://docs.strata.io/introduction/overview Maverics is Strata Identity's orchestration platform for modern, legacy, and AI identity. The **Orchestrator** -- a lightweight identity abstraction layer -- routes authentication and authorization between your applications and any identity provider, while the **Maverics Console** provides a visual interface for managing connectors, policies, and configurations.