diff --git a/services/src/main/java/org/keycloak/protocol/saml/SamlService.java b/services/src/main/java/org/keycloak/protocol/saml/SamlService.java index 76d15ab7da..06d949a0db 100755 --- a/services/src/main/java/org/keycloak/protocol/saml/SamlService.java +++ b/services/src/main/java/org/keycloak/protocol/saml/SamlService.java @@ -307,7 +307,7 @@ public class SamlService extends AuthorizationEndpointBase { } else { redirect = client.getAttribute(SamlProtocol.SAML_ASSERTION_CONSUMER_URL_REDIRECT_ATTRIBUTE); } - if (redirect == null) { + if (redirect == null || redirect.trim().isEmpty()) { redirect = client.getManagementUrl(); } diff --git a/services/src/main/java/org/keycloak/protocol/saml/installation/SamlSPDescriptorClientInstallation.java b/services/src/main/java/org/keycloak/protocol/saml/installation/SamlSPDescriptorClientInstallation.java index 3646581e5a..8d89c9d2a2 100755 --- a/services/src/main/java/org/keycloak/protocol/saml/installation/SamlSPDescriptorClientInstallation.java +++ b/services/src/main/java/org/keycloak/protocol/saml/installation/SamlSPDescriptorClientInstallation.java @@ -56,10 +56,10 @@ public class SamlSPDescriptorClientInstallation implements ClientInstallationPro logoutUrl = client.getAttribute(SamlProtocol.SAML_SINGLE_LOGOUT_SERVICE_URL_REDIRECT_ATTRIBUTE); binding = JBossSAMLURIConstants.SAML_HTTP_REDIRECT_BINDING.get(); } - if (assertionUrl == null || assertionUrl.isEmpty()) assertionUrl = client.getManagementUrl(); - if (assertionUrl == null || assertionUrl.isEmpty()) assertionUrl = FALLBACK_ERROR_URL_STRING; - if (logoutUrl == null || assertionUrl.isEmpty()) logoutUrl = client.getManagementUrl(); - if (logoutUrl == null || assertionUrl.isEmpty()) logoutUrl = FALLBACK_ERROR_URL_STRING; + if (assertionUrl == null || assertionUrl.trim().isEmpty()) assertionUrl = client.getManagementUrl(); + if (assertionUrl == null || assertionUrl.trim().isEmpty()) assertionUrl = FALLBACK_ERROR_URL_STRING; + if (logoutUrl == null || logoutUrl.trim().isEmpty()) logoutUrl = client.getManagementUrl(); + if (logoutUrl == null || logoutUrl.trim().isEmpty()) logoutUrl = FALLBACK_ERROR_URL_STRING; String nameIdFormat = samlClient.getNameIDFormat(); if (nameIdFormat == null) nameIdFormat = SamlProtocol.SAML_DEFAULT_NAMEID_FORMAT; String spCertificate = SPMetadataDescriptor.xmlKeyInfo(" ", null, samlClient.getClientSigningCertificate(), KeyTypes.SIGNING.value(), true); diff --git a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/servlet/SAMLServletAdapterTest.java b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/servlet/SAMLServletAdapterTest.java index 364f976437..d717e776a9 100644 --- a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/servlet/SAMLServletAdapterTest.java +++ b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/adapter/servlet/SAMLServletAdapterTest.java @@ -816,6 +816,29 @@ public class SAMLServletAdapterTest extends AbstractSAMLServletAdapterTest { testSuccessfulAndUnauthorizedLogin(salesPostServletPage, testRealmSAMLPostLoginPage); } + /** + * KEYCLOAK-13005: setting the Consumer Service POST Binding URL in the admin console and then deleting it (i.e. erase + * the field contents) leads to failure to properly redirect back to the app after a successful login. It happens because + * the admin console sets the value of a field that was previously configured to an empty string instead of null, so the + * code must verify if the configured URL is not null and non-empty. + * + * This test verifies the fix for the issue works by mimicking the behavior of the admin console - i.e. setting an empty + * string in the {@code saml_assertion_consumer_url_post} attribute. It is expected that in this situation the master + * URL is picked and redirection to the app works after a successful login. + * + * @throws Exception if an error occurs while running the test. + */ + @Test + public void salesPostEmptyConsumerPostURL() throws Exception { + try (Closeable client = ClientAttributeUpdater.forClient(adminClient, testRealmPage.getAuthRealm(), SalesPostServlet.CLIENT_NAME) + .setAttribute(SamlProtocol.SAML_ASSERTION_CONSUMER_URL_POST_ATTRIBUTE, "") + .update()) { + testSuccessfulAndUnauthorizedLogin(salesPostServletPage, testRealmSAMLPostLoginPage); + } finally { + salesPostEncServletPage.logout(); + } + } + @Test public void salesPostEncTest() { testSuccessfulAndUnauthorizedLogin(salesPostEncServletPage, testRealmSAMLPostLoginPage);