From b7af076ab524c018992a05b031cd8e3533ab59d4 Mon Sep 17 00:00:00 2001 From: Mathieu Velten Date: Fri, 22 Mar 2024 11:35:11 +0100 Subject: [PATCH] Add OIDC config to add extra parameters to the authorize URL (#16971) --- changelog.d/16971.feature | 1 + .../configuration/config_documentation.md | 5 +++++ synapse/config/oidc.py | 6 ++++++ synapse/handlers/oidc.py | 20 +++++++++++++------ 4 files changed, 26 insertions(+), 6 deletions(-) create mode 100644 changelog.d/16971.feature diff --git a/changelog.d/16971.feature b/changelog.d/16971.feature new file mode 100644 index 000000000..9fdc88a32 --- /dev/null +++ b/changelog.d/16971.feature @@ -0,0 +1 @@ +Add an OIDC config to specify extra parameters for the authorization grant URL. IT can be useful to pass an ACR value for example. diff --git a/docs/usage/configuration/config_documentation.md b/docs/usage/configuration/config_documentation.md index 638a459ed..985f90c8a 100644 --- a/docs/usage/configuration/config_documentation.md +++ b/docs/usage/configuration/config_documentation.md @@ -3349,6 +3349,9 @@ Options for each entry include: not included in `scopes`. Set to `userinfo_endpoint` to always use the userinfo endpoint. +* `additional_authorization_parameters`: String to string dictionary that will be passed as + additional parameters to the authorization grant URL. + * `allow_existing_users`: set to true to allow a user logging in via OIDC to match a pre-existing account instead of failing. This could be used if switching from password logins to OIDC. Defaults to false. @@ -3473,6 +3476,8 @@ oidc_providers: token_endpoint: "https://accounts.example.com/oauth2/token" userinfo_endpoint: "https://accounts.example.com/userinfo" jwks_uri: "https://accounts.example.com/.well-known/jwks.json" + additional_authorization_parameters: + acr_values: 2fa skip_verification: true enable_registration: true user_mapping_provider: diff --git a/synapse/config/oidc.py b/synapse/config/oidc.py index 102dba021..d0a03baf5 100644 --- a/synapse/config/oidc.py +++ b/synapse/config/oidc.py @@ -342,6 +342,9 @@ def _parse_oidc_config_dict( user_mapping_provider_config=user_mapping_provider_config, attribute_requirements=attribute_requirements, enable_registration=oidc_config.get("enable_registration", True), + additional_authorization_parameters=oidc_config.get( + "additional_authorization_parameters", {} + ), ) @@ -444,3 +447,6 @@ class OidcProviderConfig: # Whether automatic registrations are enabled in the ODIC flow. Defaults to True enable_registration: bool + + # Additional parameters that will be passed to the authorization grant URL + additional_authorization_parameters: Mapping[str, str] diff --git a/synapse/handlers/oidc.py b/synapse/handlers/oidc.py index ab28dc800..22b59829f 100644 --- a/synapse/handlers/oidc.py +++ b/synapse/handlers/oidc.py @@ -453,6 +453,10 @@ class OidcProvider: # optional brand identifier for this auth provider self.idp_brand = provider.idp_brand + self.additional_authorization_parameters = ( + provider.additional_authorization_parameters + ) + self._sso_handler = hs.get_sso_handler() self._device_handler = hs.get_device_handler() @@ -1006,17 +1010,21 @@ class OidcProvider: metadata = await self.load_metadata() + additional_authorization_parameters = dict( + self.additional_authorization_parameters + ) # Automatically enable PKCE if it is supported. - extra_grant_values = {} if metadata.get("code_challenge_methods_supported"): code_verifier = generate_token(48) # Note that we verified the server supports S256 earlier (in # OidcProvider._validate_metadata). - extra_grant_values = { - "code_challenge_method": "S256", - "code_challenge": create_s256_code_challenge(code_verifier), - } + additional_authorization_parameters.update( + { + "code_challenge_method": "S256", + "code_challenge": create_s256_code_challenge(code_verifier), + } + ) cookie = self._macaroon_generaton.generate_oidc_session_token( state=state, @@ -1055,7 +1063,7 @@ class OidcProvider: scope=self._scopes, state=state, nonce=nonce, - **extra_grant_values, + **additional_authorization_parameters, ) async def handle_oidc_callback(