diff --git a/docs/installation/production/manual/configuration/advanced/social_auth.rst b/docs/installation/production/manual/configuration/advanced/social_auth.rst index 48642430f..480d2d65c 100644 --- a/docs/installation/production/manual/configuration/advanced/social_auth.rst +++ b/docs/installation/production/manual/configuration/advanced/social_auth.rst @@ -704,7 +704,7 @@ OneLogin .. code-block:: bash - tethys settings --set OAUTH_CONFIG.SOCIAL_AUTH_ONELOGIN_OIDC_KEY --set OAUTH_CONFIG.SOCIAL_AUTH_ONELOGIN_OIDC_SECRET --set OAUTH_CONFIG.SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN + tethys settings --set OAUTH_CONFIG.SOCIAL_AUTH_ONELOGIN_OIDC_KEY --set OAUTH_CONFIG.SOCIAL_AUTH_ONELOGIN_OIDC_SECRET --set OAUTH_CONFIG.SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN OAUTH_CONFIG.SOCIAL_AUTH_ONELOGIN_OIDC_TOKEN_ENDPOINT_AUTH_METHOD "POST" References ++++++++++ @@ -772,10 +772,12 @@ Configuring multi-tenant SSO backends is similar to configuring other SSO backen SOCIAL_AUTH_ONELOGIN_OIDC_KEY: SOCIAL_AUTH_ONELOGIN_OIDC_SECRET: SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN: + SOCIAL_AUTH_ONELOGIN_OIDC_TOKEN_ENDPOINT_AUTH_METHOD: "POST" tenant2: SOCIAL_AUTH_ONELOGIN_OIDC_KEY: SOCIAL_AUTH_ONELOGIN_OIDC_SECRET: SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN: + SOCIAL_AUTH_ONELOGIN_OIDC_TOKEN_ENDPOINT_AUTH_METHOD: "POST" Tenant Keys +++++++++++ @@ -1019,10 +1021,12 @@ OneLogin Multi Tenant SOCIAL_AUTH_ONELOGIN_OIDC_KEY: SOCIAL_AUTH_ONELOGIN_OIDC_SECRET: SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN: + SOCIAL_AUTH_ONELOGIN_OIDC_TOKEN_ENDPOINT_AUTH_METHOD: "POST" : SOCIAL_AUTH_ONELOGIN_OIDC_KEY: SOCIAL_AUTH_ONELOGIN_OIDC_SECRET: SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN: + SOCIAL_AUTH_ONELOGIN_OIDC_TOKEN_ENDPOINT_AUTH_METHOD: "POST" .. _social_auth_settings: @@ -1106,6 +1110,7 @@ The following settings in the :file:`portal_config.yml` are used to configure so SOCIAL_AUTH_ONELOGIN_OIDC_KEY: '' SOCIAL_AUTH_ONELOGIN_OIDC_SECRET: '' SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN: '' + SOCIAL_AUTH_ONELOGIN_OIDC_TOKEN_ENDPOINT_AUTH_METHOD: "POST" You can use the ``tethys settings`` command to easily set the settings in the :file:`portal_config.yml`. For example: diff --git a/docs/tethys_portal/configuration.rst b/docs/tethys_portal/configuration.rst index 5fb788a74..db2685521 100644 --- a/docs/tethys_portal/configuration.rst +++ b/docs/tethys_portal/configuration.rst @@ -229,52 +229,53 @@ OAUTH_CONFIG # pip pip install hs_restclient -================================================== ================================================================================ -Setting Description -================================================== ================================================================================ -SSO_TENANT_REGEX A regular expression defining the characters allowed in the Tenant field on the /accounts/tenant/ page. This page is only needed when using Multi-Tenant SSO features. Defaults to "^[\w\s_-]+$". -SOCIAL_AUTH_AZUREAD_OAUTH2_KEY Key for authenticating with Azure Active Directory using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. -SOCIAL_AUTH_AZUREAD_OAUTH2_SECRET Secret for authenticating with Azure Active Directory using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. -SOCIAL_AUTH_AZUREAD_TENANT_OAUTH2_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_azuread_multi` Setup. -SOCIAL_AUTH_AZUREAD_TENANT_OAUTH2_KEY Key for authenticating with Azure Active Directory against a single Tenant/Active Directory using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. -SOCIAL_AUTH_AZUREAD_TENANT_OAUTH2_SECRET Secret for authenticating with Azure Active Directory against a single Tenant/Active Directory using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. -SOCIAL_AUTH_AZUREAD_TENANT_OAUTH2_TENANT_ID The ID of the Tenant/Active Directory to authenticate against. See :ref:`social_auth_azuread` SSO Setup. -SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_azuread_multi` Setup. -SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_KEY Key for authenticating with Azure Active Directory B2C using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. -SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_SECRET Secret for authenticating with Azure Active Directory B2C using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. -SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_TENANT_ID The ID of the Tenant/Active Directory to authenticate against in Azure Active Directory B2C. See :ref:`social_auth_azuread` SSO Setup. -SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_POLICY The user flow policy to use. Use `'b2c_'` unless you have created a custom user flow that you would like to use. See :ref:`social_auth_azuread` SSO Setup. -SOCIAL_AUTH_ADFS_OIDC_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_adfs_multi` Setup. -SOCIAL_AUTH_ADFS_OIDC_KEY Client ID for authenticating with an AD FS services using its Open ID Connect interface. See :ref:`social_adfs` SSO Setup. -SOCIAL_AUTH_ADFS_OIDC_SECRET Secret for authenticating with an AD FS service using its Open ID Connect interface. See :ref:`social_adfs` SSO Setup. -SOCIAL_AUTH_ADFS_OIDC_DOMAIN Domain of the AD FS server. See :ref:`social_adfs` SSO Setup. -SOCIAL_AUTH_FACEBOOK_KEY Key for authenticating with Facebook using their OAuth2 service. See :ref:`social_auth_facebook` SSO Setup. -SOCIAL_AUTH_FACEBOOK_SECRET Secret for authenticating with Facebook using their OAuth2 service. See :ref:`social_auth_facebook` SSO Setup. -SOCIAL_AUTH_FACEBOOK_SCOPE List of scopes for authenticating with Facebook using their OAuth2 service. See :ref:`social_auth_facebook` SSO Setup. -SOCIAL_AUTH_GOOGLE_OAUTH2_KEY Key for authenticating with Google using their OAuth2 service. See :ref:`social_auth_google` SSO Setup. -SOCIAL_AUTH_GOOGLE_OAUTH2_SECRET Secret for authenticating with Google using their OAuth2 service. See :ref:`social_auth_google` SSO Setup. -SOCIAL_AUTH_HYDROSHARE_KEY Key for authenticating with HydroShare using their OAuth2 service. See :ref:`social_auth_hydroshare` SSO Setup. -SOCIAL_AUTH_HYDROSHARE_SECRET Secret for authentication with HydroShare using their OAuth2 service. See :ref:`social_auth_hydroshare` SSO Setup. -SOCIAL_AUTH_ARCGIS_KEY Key for authenticating with ArcGIS Online using their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. -SOCIAL_AUTH_ARCGIS_SECRET Secret for authentication with ArcGIS Online using their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. -SOCIAL_AUTH_ARCGIS_PORTAL_KEY Key for authenticating with an ArcGIS Enterprise Portal using their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. -SOCIAL_AUTH_ARCGIS_PORTAL_SECRET Secret for authentication with an ArcGIS Enterprise Portal using their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. -SOCIAL_AUTH_ARCGIS_PORTAL_URL Root URL of the ArcGIS Enterprise Portal that will provide their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. -SOCIAL_AUTH_LINKEDIN_OAUTH2_KEY Key for authenticating with LinkedIn using their OAuth2 service. See :ref:`social_auth_linkedin` SSO Setup. -SOCIAL_AUTH_LINKEDIN_OAUTH2_SECRET Secret for authenticating with LinkedIn using their OAuth2 service. See :ref:`social_auth_linkedin` SSO Setup. -SOCIAL_AUTH_OKTA_OAUTH2_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_okta_multi` Setup. -SOCIAL_AUTH_OKTA_OAUTH2_KEY Client ID for authenticating with Okta using their OAuth 2 interface. See :ref:`social_auth_okta` SSO Setup. -SOCIAL_AUTH_OKTA_OAUTH2_SECRET Secret for authenticating with Okta using their OAuth 2 interface. See :ref:`social_auth_okta` SSO Setup. -SOCIAL_AUTH_OKTA_OAUTH2_API_URL Your Okta Organization URL. See :ref:`social_auth_okta` SSO Setup. -SOCIAL_AUTH_OKTA_OPENIDCONNECT_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_okta_multi` Setup. -SOCIAL_AUTH_OKTA_OPENIDCONNECT_KEY Client ID for authenticating with Okta using their Open ID Connect interface. See :ref:`social_auth_okta` SSO Setup. -SOCIAL_AUTH_OKTA_OPENIDCONNECT_SECRET Secret for authenticating with Okta using their Open ID Connect interface. See :ref:`social_auth_okta` SSO Setup. -SOCIAL_AUTH_OKTA_OPENIDCONNECT_API_URL Your Okta Organization URL. See :ref:`social_auth_okta` SSO Setup. -SOCIAL_AUTH_ONELOGIN_OIDC_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_onelogin_multi` Setup. -SOCIAL_AUTH_ONELOGIN_OIDC_KEY Client ID for authenticating with OneLogin using their Open ID Connect interface. See :ref:`social_auth_onelogin` SSO Setup. -SOCIAL_AUTH_ONELOGIN_OIDC_SECRET Secret for authenticating with OneLogin using their Open ID Connect interface. See :ref:`social_auth_onelogin` SSO Setup. -SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN Your OneLogin Subdomain. See :ref:`social_auth_onelogin` SSO Setup. -================================================== ================================================================================ +====================================================== ================================================================================ +Setting Description +====================================================== ================================================================================ +SSO_TENANT_REGEX A regular expression defining the characters allowed in the Tenant field on the /accounts/tenant/ page. This page is only needed when using Multi-Tenant SSO features. Defaults to "^[\w\s_-]+$". +SOCIAL_AUTH_AZUREAD_OAUTH2_KEY Key for authenticating with Azure Active Directory using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. +SOCIAL_AUTH_AZUREAD_OAUTH2_SECRET Secret for authenticating with Azure Active Directory using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. +SOCIAL_AUTH_AZUREAD_TENANT_OAUTH2_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_azuread_multi` Setup. +SOCIAL_AUTH_AZUREAD_TENANT_OAUTH2_KEY Key for authenticating with Azure Active Directory against a single Tenant/Active Directory using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. +SOCIAL_AUTH_AZUREAD_TENANT_OAUTH2_SECRET Secret for authenticating with Azure Active Directory against a single Tenant/Active Directory using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. +SOCIAL_AUTH_AZUREAD_TENANT_OAUTH2_TENANT_ID The ID of the Tenant/Active Directory to authenticate against. See :ref:`social_auth_azuread` SSO Setup. +SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_azuread_multi` Setup. +SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_KEY Key for authenticating with Azure Active Directory B2C using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. +SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_SECRET Secret for authenticating with Azure Active Directory B2C using their OAuth2 service. See :ref:`social_auth_azuread` SSO Setup. +SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_TENANT_ID The ID of the Tenant/Active Directory to authenticate against in Azure Active Directory B2C. See :ref:`social_auth_azuread` SSO Setup. +SOCIAL_AUTH_AZUREAD_B2C_OAUTH2_POLICY The user flow policy to use. Use `'b2c_'` unless you have created a custom user flow that you would like to use. See :ref:`social_auth_azuread` SSO Setup. +SOCIAL_AUTH_ADFS_OIDC_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_adfs_multi` Setup. +SOCIAL_AUTH_ADFS_OIDC_KEY Client ID for authenticating with an AD FS services using its Open ID Connect interface. See :ref:`social_adfs` SSO Setup. +SOCIAL_AUTH_ADFS_OIDC_SECRET Secret for authenticating with an AD FS service using its Open ID Connect interface. See :ref:`social_adfs` SSO Setup. +SOCIAL_AUTH_ADFS_OIDC_DOMAIN Domain of the AD FS server. See :ref:`social_adfs` SSO Setup. +SOCIAL_AUTH_FACEBOOK_KEY Key for authenticating with Facebook using their OAuth2 service. See :ref:`social_auth_facebook` SSO Setup. +SOCIAL_AUTH_FACEBOOK_SECRET Secret for authenticating with Facebook using their OAuth2 service. See :ref:`social_auth_facebook` SSO Setup. +SOCIAL_AUTH_FACEBOOK_SCOPE List of scopes for authenticating with Facebook using their OAuth2 service. See :ref:`social_auth_facebook` SSO Setup. +SOCIAL_AUTH_GOOGLE_OAUTH2_KEY Key for authenticating with Google using their OAuth2 service. See :ref:`social_auth_google` SSO Setup. +SOCIAL_AUTH_GOOGLE_OAUTH2_SECRET Secret for authenticating with Google using their OAuth2 service. See :ref:`social_auth_google` SSO Setup. +SOCIAL_AUTH_HYDROSHARE_KEY Key for authenticating with HydroShare using their OAuth2 service. See :ref:`social_auth_hydroshare` SSO Setup. +SOCIAL_AUTH_HYDROSHARE_SECRET Secret for authentication with HydroShare using their OAuth2 service. See :ref:`social_auth_hydroshare` SSO Setup. +SOCIAL_AUTH_ARCGIS_KEY Key for authenticating with ArcGIS Online using their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. +SOCIAL_AUTH_ARCGIS_SECRET Secret for authentication with ArcGIS Online using their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. +SOCIAL_AUTH_ARCGIS_PORTAL_KEY Key for authenticating with an ArcGIS Enterprise Portal using their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. +SOCIAL_AUTH_ARCGIS_PORTAL_SECRET Secret for authentication with an ArcGIS Enterprise Portal using their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. +SOCIAL_AUTH_ARCGIS_PORTAL_URL Root URL of the ArcGIS Enterprise Portal that will provide their OAuth2 service. See :ref:`social_auth_arcgis` SSO Setup. +SOCIAL_AUTH_LINKEDIN_OAUTH2_KEY Key for authenticating with LinkedIn using their OAuth2 service. See :ref:`social_auth_linkedin` SSO Setup. +SOCIAL_AUTH_LINKEDIN_OAUTH2_SECRET Secret for authenticating with LinkedIn using their OAuth2 service. See :ref:`social_auth_linkedin` SSO Setup. +SOCIAL_AUTH_OKTA_OAUTH2_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_okta_multi` Setup. +SOCIAL_AUTH_OKTA_OAUTH2_KEY Client ID for authenticating with Okta using their OAuth 2 interface. See :ref:`social_auth_okta` SSO Setup. +SOCIAL_AUTH_OKTA_OAUTH2_SECRET Secret for authenticating with Okta using their OAuth 2 interface. See :ref:`social_auth_okta` SSO Setup. +SOCIAL_AUTH_OKTA_OAUTH2_API_URL Your Okta Organization URL. See :ref:`social_auth_okta` SSO Setup. +SOCIAL_AUTH_OKTA_OPENIDCONNECT_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_okta_multi` Setup. +SOCIAL_AUTH_OKTA_OPENIDCONNECT_KEY Client ID for authenticating with Okta using their Open ID Connect interface. See :ref:`social_auth_okta` SSO Setup. +SOCIAL_AUTH_OKTA_OPENIDCONNECT_SECRET Secret for authenticating with Okta using their Open ID Connect interface. See :ref:`social_auth_okta` SSO Setup. +SOCIAL_AUTH_OKTA_OPENIDCONNECT_API_URL Your Okta Organization URL. See :ref:`social_auth_okta` SSO Setup. +SOCIAL_AUTH_ONELOGIN_OIDC_MULTI_TENANT Define one or more sets of settings for multiple tenants, each indexed by a Tenant Key. See: :ref:`social_auth_onelogin_multi` Setup. +SOCIAL_AUTH_ONELOGIN_OIDC_KEY Client ID for authenticating with OneLogin using their Open ID Connect interface. See :ref:`social_auth_onelogin` SSO Setup. +SOCIAL_AUTH_ONELOGIN_OIDC_SECRET Secret for authenticating with OneLogin using their Open ID Connect interface. See :ref:`social_auth_onelogin` SSO Setup. +SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN Your OneLogin Subdomain. See :ref:`social_auth_onelogin` SSO Setup. +SOCIAL_AUTH_ONELOGIN_OIDC_TOKEN_ENDPOINT_AUTH_METHOD The authentication method to use when requesting tokens from the token endpoint. See :ref:`social_auth_onelogin` SSO Setup. +====================================================== ================================================================================ MFA_CONFIG ++++++++++ diff --git a/scripts/generate_portal_config_tables.py b/scripts/generate_portal_config_tables.py index e7056d40d..ddab9f54e 100644 --- a/scripts/generate_portal_config_tables.py +++ b/scripts/generate_portal_config_tables.py @@ -108,6 +108,7 @@ "SOCIAL_AUTH_ONELOGIN_OIDC_KEY": "Client ID for authenticating with OneLogin using their Open ID Connect interface. See :ref:`social_auth_onelogin` SSO Setup.", "SOCIAL_AUTH_ONELOGIN_OIDC_SECRET": "Secret for authenticating with OneLogin using their Open ID Connect interface. See :ref:`social_auth_onelogin` SSO Setup.", "SOCIAL_AUTH_ONELOGIN_OIDC_SUBDOMAIN": "Your OneLogin Subdomain. See :ref:`social_auth_onelogin` SSO Setup.", + "SOCIAL_AUTH_ONELOGIN_OIDC_TOKEN_ENDPOINT_AUTH_METHOD": "The authentication method to use when requesting tokens from the token endpoint. See :ref:`social_auth_onelogin` SSO Setup.", }, "MFA_CONFIG": { "ADMIN_MFA_REQUIRED": "Are admin (staff) users required to set up MFA when MFA_REQUIRED is ``True``. Defaults to ``True``.", diff --git a/tests/unit_tests/test_tethys_services/test_backends/test_onelogin.py b/tests/unit_tests/test_tethys_services/test_backends/test_onelogin.py index 121969296..31c395229 100644 --- a/tests/unit_tests/test_tethys_services/test_backends/test_onelogin.py +++ b/tests/unit_tests/test_tethys_services/test_backends/test_onelogin.py @@ -162,84 +162,6 @@ def test_oidc_endpoint__subdomain_no_end_slash(self): ret = inst.OIDC_ENDPOINT self.assertEqual("https://my-org.onelogin.mok/oidc/2", ret) - def test_find_valid_key(self): - access_token = self.generate_access_token() - id_token = self.generate_id_token(access_token) - inst = OneLoginOIDC() - inst.get_jwks_keys = mock.MagicMock(return_value=[self.pub_key]) - ret = inst.find_valid_key(id_token) - self.assertEqual(self.pub_key, ret) - - def test_validate_and_return_id_token(self): - access_token = self.generate_access_token() - id_token = self.generate_id_token(access_token) - inst = OneLoginOIDC() - inst.find_valid_key = mock.MagicMock(return_value=self.pub_key) - inst.id_token_issuer = mock.MagicMock(return_value=self.issuer) - inst.validate_claims = mock.MagicMock() - inst.validate_and_return_id_token(id_token, access_token) - - def test_validate_and_return_id_token__no_valid_key(self): - access_token = self.generate_access_token() - id_token = self.generate_id_token(access_token) - inst = OneLoginOIDC() - inst.find_valid_key = mock.MagicMock(return_value=None) - - with self.assertRaises(AuthTokenError) as cm: - inst.validate_and_return_id_token(id_token, access_token) - - self.assertEqual( - str(cm.exception), "Token error: Signature verification failed" - ) - - def test_validate_and_return_id_token__expired_signature(self): - # Backdate iat and exp parameters 1 day to make them expired - self.iat = dt.datetime.utcnow() - dt.timedelta(days=1) - self.id_exp = self.iat + dt.timedelta(hours=3) - self.access_exp = self.iat + dt.timedelta(hours=1) - - access_token = self.generate_access_token() - id_token = self.generate_id_token(access_token) - - inst = OneLoginOIDC() - inst.find_valid_key = mock.MagicMock(return_value=self.pub_key) - inst.id_token_issuer = mock.MagicMock(return_value=self.issuer) - - with self.assertRaises(AuthTokenError) as cm: - inst.validate_and_return_id_token(id_token, access_token) - - self.assertEqual(str(cm.exception), "Token error: Signature has expired") - - def test_validate_and_return_id_token__claims_error(self): - # Generate id_token with an invalid access token hash - access_token = self.generate_access_token() - id_token = self.generate_id_token(access_token, at_hash="iNvAlIdAtHaSh") - - inst = OneLoginOIDC() - inst.find_valid_key = mock.MagicMock(return_value=self.pub_key) - inst.id_token_issuer = mock.MagicMock(return_value=self.issuer) - - with self.assertRaises(AuthTokenError) as cm: - inst.validate_and_return_id_token(id_token, access_token) - - self.assertEqual( - str(cm.exception), "Token error: at_hash claim does not match access_token." - ) - - @mock.patch("tethys_services.backends.onelogin.jwt.decode") - def test_validate_and_return_id_token__jwt_error(self, mock_decode): - access_token = self.generate_access_token() - id_token = self.generate_id_token(access_token) - inst = OneLoginOIDC() - inst.find_valid_key = mock.MagicMock(return_value=self.pub_key) - inst.id_token_issuer = mock.MagicMock(return_value=self.issuer) - mock_decode.side_effect = JWTError - - with self.assertRaises(AuthTokenError) as cm: - inst.validate_and_return_id_token(id_token, access_token) - - self.assertEqual(str(cm.exception), "Token error: Invalid signature") - class OneLoginOIDCMultiTenantBackendTest(test.SimpleTestCase): def setUp(self): diff --git a/tethys_services/backends/onelogin.py b/tethys_services/backends/onelogin.py index 6082edd23..3beb7657c 100644 --- a/tethys_services/backends/onelogin.py +++ b/tethys_services/backends/onelogin.py @@ -27,47 +27,6 @@ def OIDC_ENDPOINT(self): return subdomain + "/oidc/2" - def find_valid_key(self, id_token): - for key in self.get_jwks_keys(): - rsakey = jwk.construct(key, algorithm=ALGORITHMS.RS256) - message, encoded_sig = id_token.rsplit(".", 1) - decoded_sig = base64url_decode(encoded_sig.encode("utf-8")) - if rsakey.verify(message.encode("utf-8"), decoded_sig): - return key - - def validate_and_return_id_token(self, id_token, access_token): - """ - Validates the id_token according to the steps at - http://openid.net/specs/openid-connect-core-1_0.html#IDTokenValidation. - """ - client_id, client_secret = self.get_key_and_secret() - - key = self.find_valid_key(id_token) - - if not key: - raise AuthTokenError(self, "Signature verification failed") - - rsakey = jwk.construct(key, algorithm=ALGORITHMS.RS256) - - try: - claims = jwt.decode( - id_token, - rsakey.to_pem().decode("utf-8"), - algorithms=[ALGORITHMS.HS256, ALGORITHMS.RS256, ALGORITHMS.ES256], - audience=client_id, - issuer=self.id_token_issuer(), - access_token=access_token, - options=self.JWT_DECODE_OPTIONS, - ) - except ExpiredSignatureError: - raise AuthTokenError(self, "Signature has expired") - except JWTClaimsError as error: - raise AuthTokenError(self, str(error)) - except JWTError: - raise AuthTokenError(self, "Invalid signature") - - self.validate_claims(claims) - class OneLoginOIDCMultiTenant(MultiTenantMixin, OneLoginOIDC): pass