Open in ClaudeOpen in ChatGPT

OpenID Connect

To configure the Valsight application to use the OpenID Connect SSO, edit conf/config.yml and restart the server after making changes.

To enable OpenID Connect login configure the following value:

Configuration Key (loginMethodConfigurations → openIdConnect →)DescriptionExample ValueDefault Value
enabledWhether OpenID Connect authentication should be used or nottruefalse

To configure an OpenID Connect client enter the following configuration keys:

spring:
    security:
        oauth2:
            client:
                registration:
                    openIdConnect:
                        .....

Then configure the OpenID Connection client values as follows:

Configuration keyDescriptionExampleDefault
client-idOAuth 2.0 client identifier, valid at the authorization serverjmxDcfi1gEffVMktJn/a
client-authentication-methodThe type of client authentication to perform with the authorization server. See Client authentication methods.client_secret_basicclient_secret_basic
client-secretClient secret token, provided by the authorization server. Since 6.3.0 this is no longer mandatory unless client_secret_basic is the client authentication mode.aZWAuRZUSxT-Sh8-xDLdHIn/a
scopeComma-separated list of scopes to request, when additional claims are neededopenid, email, profilen/a
providerThe name of the OpenID Connect provider to use. Required unless a provider with the registration id openIdConnect exists.openIdConnectn/a
valsightOpenIdConnectProperties → userProfileMapping → usernameThe claim used to uniquely identify a user. Must always be present in the provider’s response, and unique per user. See Claim names are case sensitive.preferred_usernamesub
valsightOpenIdConnectProperties → userProfileMapping → emailThe claim that contains the user’s e-mail address. Optional.emailn/a
valsightOpenIdConnectProperties → userProfileMapping → fullNameThe claim that contains the user’s full name. Optional.namen/a
valsightOpenIdConnectProperties → loginSuccessfulUrlThe absolute URL, starting with http or https, of the application’s main page. The user is redirected there after a successful login.https://valsight.example.com/n/a
valsightOpenIdConnectProperties → forceGroupsOverageForces the application to always use the https://graph.microsoft.com/v1.0 API to fetch the user’s groups. No effect unless groupsClaim is enabled. Optional.truefalse
valsightOpenIdConnectProperties → acr_valuesPasses additional authentication-related information to the user service. Optional.myvalue1:myvalue2:myvalue3:myvalue4n/a
valsightOpenIdConnectProperties → mandatoryClaimsCustomizes which claims must be present, and with which values, beyond those requested by the OpenID Connect specification. See Mandatory claims. Optional.See Mandatory claimsn/a
valsightOpenIdConnectProperties → groupsClaimThe claim holding the groups the user belongs to. See Group synchronization. Optional.groupsInOpenIDConnectResponsen/a
valsightOpenIdConnectProperties → requiredGroupNamePrefixRemoved in 6.0.0. See Removed: requiredGroupNamePrefix.AcceptedGroup_n/a
valsightOpenIdConnectProperties → userInfoEndpointScopesScopes that are accessible only from the user info endpoint, not from the token. See User info endpoint scopes.See User info endpoint scopesprofile, email, address, phone

Three further settings under valsightOpenIdConnectProperties control what the login page offers and which scopes each login option requests: buttonText (see Login button label), additionalScopes (see Additional scopes), and the alternativeLogin group (see Alternative login flow).

Client authentication methods

The supported forms of authentication are client_secret_basic and private_key_jwt.

With client_secret_basic a client-secret must be provided; with private_key_jwt a privateRSAKeyPath must be provided instead. For more on private_key_jwt, see OAuth 2.0 with private key JWT client authentication.

Claim names are case sensitive

Ensure the configured string matches the IdP claim name exactly. This applies to every userProfileMapping entry, to groupsClaim, and to the claim values under mandatoryClaims.

Mandatory claims

Every claim configured here must be present in the provider’s response and carry the specified value. Where a claim has multiple values in the response — a list of the user’s groups, for example — one of those values must match the configured value exactly.

MIGRATETOKEN1ENDTOKEN

Group synchronization

Setting groupsClaim turns on group synchronization. If the claim is absent or empty, groups must be managed inside the application instead. The value should be a claim name that contains the groups the provider supplies.

Group matching then happens as follows:

  1. Read the groups from the OpenID Connect response.
  2. Create groups that are missing in the application.
  3. Add the user to all groups from the response.
  4. Remove the user from all groups not in the response.

This functionality never automatically deletes groups in the application.

Removed: requiredGroupNamePrefix

Available since 5.9.1, removed in 6.0.0 and replaced by loginMethodConfigurations → commonSSOOptions → requiredGroupNamePrefixes. See Common SSO Options.

Before 6.0.0 this determined whether group names had to carry a given prefix to be recognised by the application: any group name in the OpenID Connect response not starting with the value was treated as absent. When mandatoryGroupName was also set, the mandatory group name had to carry the required prefix.

User info endpoint scopes

To stop the user info endpoint being invoked at all, populate this list with none of the scopes listed under scope. Setting it to an empty list means the user info endpoint is always invoked.

Available since 6.0.26.

MIGRATETOKEN2ENDTOKEN

Login button label

Available since 7.2.5 and 7.3.0.

Configuration keyDescriptionExampleDefault
valsightOpenIdConnectProperties → buttonTextLabel of the OpenID Connect button on the login page. Optional.Log in with Acme IDOpenID Connect

This key sets a default, it does not override: whatever an administrator has saved under Login Page Settings wins whenever it is set. See Login Page Customization for that setting.

Use buttonText to ship a label together with the configuration file, so a newly installed instance already shows the right wording before anyone opens the settings page. If neither is set, the button reads OpenID Connect.

Additional scopes

Available since 7.2.5 and 7.3.0.

Configuration keyDescriptionExampleDefault
valsightOpenIdConnectProperties → additionalScopesScopes the login button requests in addition to those listed under scope. Optional.urn:zitadel:iam:org:id:123456789456132n/a

Write the value either as a YAML list or as a single string with the scopes separated by commas, whitespace, or both. The scopes are added to scope; nothing is removed.

The typical use is an identity provider that accepts an organization scope. Sending it pins the login to one organization, so the user reaches their own identity provider directly instead of first having to enter an email address for domain discovery.

That same scope excludes everyone who is not a member of that organization. Those users need the alternative login flow.

Alternative login flow

Available since 7.2.5 and 7.3.0.

A second login option that requests a different set of scopes from the same OpenID Connect client. It exists for the users an organization scope in additionalScopes would otherwise lock out, for example staff who authenticate against a different organization’s identity provider.

Configuration key (valsightOpenIdConnectProperties → alternativeLogin →)DescriptionExampleDefault
additionalScopesScopes this flow requests instead of additionalScopes. May be left empty. See An empty scope list is a valid configuration. Optional.urn:zitadel:iam:org:id:987654321098765n/a
buttonTextLabel of the link on the login page. Without it the flow stays reachable by its URL but is not listed. Optional.Log in with a different organizationn/a
enabledSwitches the flow on or off explicitly. See When the enabled key is needed. Optional.falseOn when additionalScopes or buttonText is set
requiredHeaderLists the link only for clients whose request carries this header. See Listing the link for some clients only. Optional.x-internal-clientUnset, so the link is listed for every client

The flow is requested with a query parameter on the authorization URL:

<server_url>/<contextPath>/oauth2/authorization/openIdConnect?loginFlow=alternative

That parameter only selects between scope sets already configured on the server. An absent, unknown, or unconfigured value falls back to the primary scopes, so no caller can request scopes of their own.

On the login page the option is rendered as a link below the OpenID Connect button rather than as a second button, because it is a variant of the same provider and not a login method of its own.

When the enabled key is needed

Configuring either additionalScopes or buttonText under alternativeLogin already enables the flow, so most instances need no enabled key at all. Set it explicitly in two cases:

  • enabled: true for a flow that has neither scopes nor a label of its own, which is otherwise indistinguishable from an unconfigured one.
  • enabled: false to switch a configured flow off without deleting its keys.

An empty scope list is a valid configuration

Leaving alternativeLogin → additionalScopes empty is a meaningful configuration rather than a pointless one. The flow then sends only the scopes listed under scope, and so no organization scope at all, which is what makes the identity provider fall back to its own account chooser.

For that reason the alternative flow never falls back to the primary additionalScopes. Once the flow is enabled, requesting it always replaces the primary scopes, even when it defines none.

Name a request header in requiredHeader and the link is listed only for clients whose request carries it; leave the key unset and the link is listed for everyone. Use it where a login page carries one customer’s branding and the alternative option is meant for a different group of users — staff, say — who can be told apart by something the infrastructure in front of Valsight already knows.

Which clients get the header is decided in that infrastructure and not in Valsight. The application never interprets the value, only whether the header is there with a non-blank value, so the header can mean whatever the deployment needs it to mean.

Two requirements on whichever component injects it:

  • It has to set the header on every request, so that a copy sent by the client is always overwritten. If a client could supply the header itself, the setting would gate on nothing.
  • It has to be a component the request cannot bypass. Valsight reads the configured header alone, with no fallback to X-Forwarded-For or X-Real-IP, because a client writes those freely. See Reverse Proxy.

Hiding the link decides what the login page offers; it is not an access rule. The flow’s URL keeps working without the header, and opening the login page with ?alternativeLogin=1 lists the link for any client:

<server_url>/<contextPath>/app/index.html#/login?alternativeLogin=1

Give that URL to the users the flow is for who reach the login page without the header. Where nothing injects the header, no client ever carries it and the link is only reached this way — so leave requiredHeader unset until the header is actually in place.

While requiredHeader is set, the login page’s data response carries a Vary header naming it, so a cache between Valsight and the browser cannot serve one client’s login page to another.

Example configuration

spring:
    security:
        oauth2:
            client:
                registration:
                    openIdConnect:
                        scope: openid, email, profile
                        valsightOpenIdConnectProperties:
                            buttonText: Log in with Acme ID
                            additionalScopes: urn:zitadel:iam:org:id:123456789456132
                            alternativeLogin:
                                # deliberately empty: send no organization scope at all
                                additionalScopes:
                                buttonText: Log in with a different organization
                                requiredHeader: x-internal-client

With this configuration the login page shows one Log in with Acme ID button that pins the login to the Acme organization. Clients whose request carries x-internal-client additionally get a Log in with a different organization link below it, which sends no organization scope. Drop the requiredHeader line to offer that link to everyone.

To configure an OpenID Connect provider enter the following configuration keys:

spring:
    security:
        oauth2:
            client:
                provider:
                  openIdConnect:
                        .....

Then configure the OpenID Connection provider values as follows:

Configuration Key (….provider.openIdConnect →)DescriptionExample ValueDefault Value
issuer-uriIdentifier for the Issuer of the authorization response.https://my-oidc.com/n/a
authorization-uriThe Authorization endpoint of the OpenID Connect flowhttps://my-oidc.com/authorizen/a
token-uriThe Token endpoint of the OpenID Connect flowhttps://my-oidc.com/oauth/tokenn/a
jwk-set-uriThe endpoint that contains certificates to verify the tokenhttps://my-oidc.com/oauth2/certsn/a

Full example YAML configuration

Below is an example of all the available configuration keys for OpenID connect, with no values supplied except where stated:

spring:
    security:
        oauth2:
            client:
                registration:
                        openIdConnect:
                             client-id:
                             client-secret:
                             scope:
                             valsightOpenIdConnectProperties:
                                userProfileMapping:
                                  username:
                                  email:
                                  fullName:
                                forceGroupOverage:
                                loginSuccessfulUrl:
                                mandatoryClaims:
                                  #example value
                                  group: groupName
                                acr_values:
                                groupsClaim:
                                requiredGroupNamePrefix:
                                userInfoEndpointScopes:
                provider:
                         openIdConnect:
                             issuer-uri:
                             authorization-uri:
                             token-uri:
                             jwk-set-uri:

Logging

For logging purpose, add in the log level view (Configuration UI), the following package:

  • org.springframework.security
  • org.springframework.security.oauth2
  • com.valsight.authentication.oauth
  • com.valsight.services.authentication.SSOService
  • com.valsight.authentication
  • org.springframework.web.client

Set the log level to DEBUG

Redirect/callback URL

When configuring the IdP the redirect/callback URL for the application is:

<server_url>//login/oauth2/code/openIdConnect

Reverse proxy configuration

If the application is running behind a reverse proxy it will be required to configure the reverse proxy such that the OpenID connect authentication flow can be performed A guide to doing this can be found here: Reverse Proxy

Was this page helpful?