diff options
Diffstat (limited to 'server')
11 files changed, 203 insertions, 20 deletions
diff --git a/server/sonar-auth-saml/src/main/java/org/sonar/auth/saml/SamlSettings.java b/server/sonar-auth-saml/src/main/java/org/sonar/auth/saml/SamlSettings.java index edca87b14f6..d1f795b5ad4 100644 --- a/server/sonar-auth-saml/src/main/java/org/sonar/auth/saml/SamlSettings.java +++ b/server/sonar-auth-saml/src/main/java/org/sonar/auth/saml/SamlSettings.java @@ -32,7 +32,6 @@ import static org.sonar.api.PropertyType.PASSWORD; @ServerSide public class SamlSettings { - public static final String ENABLED = "sonar.auth.saml.enabled"; public static final String PROVIDER_ID = "sonar.auth.saml.providerId"; public static final String PROVIDER_NAME = "sonar.auth.saml.providerName"; @@ -117,7 +116,7 @@ public class SamlSettings { configuration.get(USER_NAME_ATTRIBUTE).isPresent(); } - static List<PropertyDefinition> definitions() { + public static List<PropertyDefinition> definitions() { return Arrays.asList( PropertyDefinition.builder(ENABLED) .name("Enabled") diff --git a/server/sonar-auth-saml/src/test/java/org/sonar/auth/saml/SamlIdentityProviderTest.java b/server/sonar-auth-saml/src/test/java/org/sonar/auth/saml/SamlIdentityProviderTest.java index 1e7eba451ee..b474f0596cb 100644 --- a/server/sonar-auth-saml/src/test/java/org/sonar/auth/saml/SamlIdentityProviderTest.java +++ b/server/sonar-auth-saml/src/test/java/org/sonar/auth/saml/SamlIdentityProviderTest.java @@ -38,8 +38,6 @@ import org.sonar.api.server.authentication.OAuth2IdentityProvider; import org.sonar.api.server.authentication.UnauthorizedException; import org.sonar.api.server.authentication.UserIdentity; import org.sonar.api.utils.System2; -import org.sonar.api.utils.log.LogAndArguments; -import org.sonar.api.utils.log.LogTester; import org.sonar.db.DbTester; import static org.assertj.core.api.Assertions.assertThat; @@ -49,7 +47,6 @@ import static org.mockito.ArgumentMatchers.argThat; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; -import static org.sonar.api.utils.log.LoggerLevel.ERROR; public class SamlIdentityProviderTest { private static final String SQ_CALLBACK_URL = "http://localhost:9000/oauth2/callback/saml"; @@ -65,8 +62,6 @@ public class SamlIdentityProviderTest { @Rule public DbTester db = DbTester.create(); - @Rule - public LogTester log = new LogTester(); private final MapSettings settings = new MapSettings(new PropertyDefinitions(System2.INSTANCE, SamlSettings.definitions())); private final SamlIdentityProvider underTest = new SamlIdentityProvider(new SamlSettings(settings.asConfig()), new SamlMessageIdChecker(db.getDbClient())); @@ -230,11 +225,11 @@ public class SamlIdentityProviderTest { settings.setProperty("sonar.auth.saml.sp.privateKey.secured", WRONG_FORMAT_PRIVATE_KEY); DumbCallbackContext callbackContext = new DumbCallbackContext(request, response, "encoded_minimal_response.txt", SQ_CALLBACK_URL); - underTest.callback(callbackContext); - - assertThat(log.getLogs(ERROR)) - .extracting(LogAndArguments::getFormattedMsg) - .contains("Error in parsing service provider private key, please make sure that it is in PKCS 8 format."); + try { + underTest.callback(callbackContext); + } catch (IllegalStateException ise) { + assertThat(ise.getMessage()).contains("Error in parsing service provider private key, please make sure that it is in PKCS 8 format."); + } } @Test @@ -396,7 +391,7 @@ public class SamlIdentityProviderTest { private String loadResponse(String file) { try (InputStream json = getClass().getResourceAsStream("SamlIdentityProviderTest/" + file)) { - return IOUtils.toString(json, StandardCharsets.UTF_8.name()); + return IOUtils.toString(json, StandardCharsets.UTF_8); } catch (IOException e) { throw new IllegalStateException(e); } diff --git a/server/sonar-webserver-auth/src/main/java/org/sonar/server/authentication/OAuth2ContextFactory.java b/server/sonar-webserver-auth/src/main/java/org/sonar/server/authentication/OAuth2ContextFactory.java index b2750c95ece..66f2797b226 100644 --- a/server/sonar-webserver-auth/src/main/java/org/sonar/server/authentication/OAuth2ContextFactory.java +++ b/server/sonar-webserver-auth/src/main/java/org/sonar/server/authentication/OAuth2ContextFactory.java @@ -25,6 +25,7 @@ import java.util.Set; import javax.annotation.Nullable; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; +import org.jetbrains.annotations.NotNull; import org.sonar.api.platform.Server; import org.sonar.api.server.ServerSide; import org.sonar.api.server.authentication.OAuth2IdentityProvider; @@ -67,6 +68,11 @@ public class OAuth2ContextFactory { return new OAuthContextImpl(request, response, identityProvider); } + @NotNull + public String generateCallbackUrl(String identityProviderKey) { + return server.getPublicRootUrl() + CALLBACK_PATH + identityProviderKey; + } + public class OAuthContextImpl implements OAuth2IdentityProvider.InitContext, OAuth2CallbackContext { private final HttpServletRequest request; @@ -81,7 +87,7 @@ public class OAuth2ContextFactory { @Override public String getCallbackUrl() { - return server.getPublicRootUrl() + CALLBACK_PATH + identityProvider.getKey(); + return generateCallbackUrl(identityProvider.getKey()); } @Override diff --git a/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlAction.java b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlAction.java new file mode 100644 index 00000000000..c4cc182e507 --- /dev/null +++ b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlAction.java @@ -0,0 +1,26 @@ +/* + * SonarQube + * Copyright (C) 2009-2022 SonarSource SA + * mailto:info AT sonarsource DOT com + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ +package org.sonar.server.saml.ws; + +import org.sonar.api.server.ws.Definable; +import org.sonar.api.server.ws.WebService; + +public interface SamlAction extends Definable<WebService.NewController> { +} diff --git a/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationInitAction.java b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationInitAction.java index b569075a38b..4b5397f26ae 100644 --- a/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationInitAction.java +++ b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationInitAction.java @@ -37,6 +37,7 @@ public class SamlValidationInitAction extends ServletFilter implements SamlActio public static final String VALIDATION_RELAY_STATE = "validation-query"; private final SamlAuthenticator samlAuthenticator; + private final OAuth2ContextFactory oAuth2ContextFactory; public SamlValidationInitAction(SamlAuthenticator samlAuthenticator, OAuth2ContextFactory oAuth2ContextFactory) { diff --git a/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationModule.java b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationModule.java new file mode 100644 index 00000000000..2baff89a489 --- /dev/null +++ b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationModule.java @@ -0,0 +1,32 @@ +/* + * SonarQube + * Copyright (C) 2009-2022 SonarSource SA + * mailto:info AT sonarsource DOT com + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ +package org.sonar.server.saml.ws; + +import org.sonar.core.platform.Module; + +public class SamlValidationModule extends Module { + @Override + protected void configureModule() { + add( + SamlValidationWs.class, + SamlValidationInitAction.class + ); + } +} diff --git a/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationWs.java b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationWs.java new file mode 100644 index 00000000000..52529579be9 --- /dev/null +++ b/server/sonar-webserver-webapi/src/main/java/org/sonar/server/saml/ws/SamlValidationWs.java @@ -0,0 +1,41 @@ +/* + * SonarQube + * Copyright (C) 2009-2022 SonarSource SA + * mailto:info AT sonarsource DOT com + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ +package org.sonar.server.saml.ws; + +import java.util.List; +import org.sonar.api.server.ws.WebService; + +public class SamlValidationWs implements WebService { + + public static final String SAML_VALIDATION_CONTROLLER = "api/saml"; + private final List<SamlAction> actions; + + public SamlValidationWs(List<SamlAction> actions) { + this.actions = actions; + } + + @Override + public void define(WebService.Context context) { + WebService.NewController controller = context.createController(SAML_VALIDATION_CONTROLLER); + controller.setDescription("Handle SAML validation."); + actions.forEach(action -> action.define(controller)); + controller.done(); + } +} diff --git a/server/sonar-webserver-webapi/src/test/java/org/sonar/server/qualityprofile/QProfileBackuperImplTest.java b/server/sonar-webserver-webapi/src/test/java/org/sonar/server/qualityprofile/QProfileBackuperImplTest.java index 704fe8f7571..d0bc2bd9e8a 100644 --- a/server/sonar-webserver-webapi/src/test/java/org/sonar/server/qualityprofile/QProfileBackuperImplTest.java +++ b/server/sonar-webserver-webapi/src/test/java/org/sonar/server/qualityprofile/QProfileBackuperImplTest.java @@ -87,7 +87,7 @@ public class QProfileBackuperImplTest { StringWriter writer = new StringWriter(); underTest.backup(db.getSession(), profile, writer); - assertThat(writer).hasToString("<?xml version=\"1.0\" encoding=\"UTF-8\"?>" + + assertThat(writer).hasToString("<?xml version='1.0' encoding='UTF-8'?>" + "<profile><name>" + profile.getName() + "</name>" + "<language>" + profile.getLanguage() + "</language>" + "<rules>" + @@ -96,7 +96,7 @@ public class QProfileBackuperImplTest { "<key>" + rule.getRuleKey() + "</key>" + "<type>" + RuleType.valueOf(rule.getType()).name() + "</type>" + "<priority>" + activeRule.getSeverityString() + "</priority>" + - "<parameters></parameters>" + + "<parameters/>" + "</rule>" + "</rules>" + "</profile>"); @@ -133,10 +133,10 @@ public class QProfileBackuperImplTest { StringWriter writer = new StringWriter(); underTest.backup(db.getSession(), profile, writer); - assertThat(writer).hasToString("<?xml version=\"1.0\" encoding=\"UTF-8\"?>" + + assertThat(writer).hasToString("<?xml version='1.0' encoding='UTF-8'?>" + "<profile><name>" + profile.getName() + "</name>" + "<language>" + profile.getLanguage() + "</language>" + - "<rules></rules>" + + "<rules/>" + "</profile>"); } @@ -156,7 +156,7 @@ public class QProfileBackuperImplTest { StringWriter writer = new StringWriter(); underTest.backup(db.getSession(), profile, writer); - assertThat(writer).hasToString("<?xml version=\"1.0\" encoding=\"UTF-8\"?>" + + assertThat(writer).hasToString("<?xml version='1.0' encoding='UTF-8'?>" + "<profile>" + "<name>" + profile.getName() + "</name>" + "<language>" + profile.getLanguage() + "</language>" + @@ -186,7 +186,7 @@ public class QProfileBackuperImplTest { StringWriter writer = new StringWriter(); underTest.backup(db.getSession(), profile, writer); - assertThat(writer).hasToString("<?xml version=\"1.0\" encoding=\"UTF-8\"?>" + + assertThat(writer).hasToString("<?xml version='1.0' encoding='UTF-8'?>" + "<profile>" + "<name>" + profile.getName() + "</name>" + "<language>" + profile.getLanguage() + "</language>" + diff --git a/server/sonar-webserver-webapi/src/test/java/org/sonar/server/saml/ws/SamlValidationModuleTest.java b/server/sonar-webserver-webapi/src/test/java/org/sonar/server/saml/ws/SamlValidationModuleTest.java new file mode 100644 index 00000000000..dd5f0456131 --- /dev/null +++ b/server/sonar-webserver-webapi/src/test/java/org/sonar/server/saml/ws/SamlValidationModuleTest.java @@ -0,0 +1,35 @@ +/* + * SonarQube + * Copyright (C) 2009-2022 SonarSource SA + * mailto:info AT sonarsource DOT com + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ +package org.sonar.server.saml.ws; + +import org.junit.Test; +import org.sonar.core.platform.ListContainer; + +import static org.assertj.core.api.Assertions.assertThat; + +public class SamlValidationModuleTest { + + @Test + public void load_configure_module() { + ListContainer container = new ListContainer(); + new SamlValidationModule().configure(container); + assertThat(container.getAddedObjects()).isNotEmpty(); + } +} diff --git a/server/sonar-webserver-webapi/src/test/java/org/sonar/server/saml/ws/SamlValidationWsTest.java b/server/sonar-webserver-webapi/src/test/java/org/sonar/server/saml/ws/SamlValidationWsTest.java new file mode 100644 index 00000000000..c2de7550c7c --- /dev/null +++ b/server/sonar-webserver-webapi/src/test/java/org/sonar/server/saml/ws/SamlValidationWsTest.java @@ -0,0 +1,46 @@ +/* + * SonarQube + * Copyright (C) 2009-2022 SonarSource SA + * mailto:info AT sonarsource DOT com + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ +package org.sonar.server.saml.ws; + +import java.util.Collections; +import org.junit.Test; +import org.sonar.api.server.ws.WebService; + +import static org.mockito.ArgumentMatchers.anyString; +import static org.mockito.Mockito.mock; +import static org.mockito.Mockito.verify; +import static org.mockito.Mockito.when; + +public class SamlValidationWsTest { + + private final SamlValidationWs underTest = new SamlValidationWs(Collections.emptyList()); + + @Test + public void define() { + WebService.Context context = mock(WebService.Context.class); + WebService.NewController newController = mock(WebService.NewController.class); + when(context.createController(anyString())).thenReturn(newController); + + underTest.define(context); + + verify(newController).setDescription(anyString()); + verify(newController).done(); + } +} diff --git a/server/sonar-webserver/src/main/java/org/sonar/server/platform/platformlevel/PlatformLevel4.java b/server/sonar-webserver/src/main/java/org/sonar/server/platform/platformlevel/PlatformLevel4.java index cb000db07cb..3e689002d2a 100644 --- a/server/sonar-webserver/src/main/java/org/sonar/server/platform/platformlevel/PlatformLevel4.java +++ b/server/sonar-webserver/src/main/java/org/sonar/server/platform/platformlevel/PlatformLevel4.java @@ -221,6 +221,7 @@ import org.sonar.server.rule.ws.RuleQueryFactory; import org.sonar.server.rule.ws.RuleWsSupport; import org.sonar.server.rule.ws.RulesWs; import org.sonar.server.rule.ws.TagsAction; +import org.sonar.server.saml.ws.SamlValidationModule; import org.sonar.server.scannercache.ScannerCache; import org.sonar.server.scannercache.ws.AnalysisCacheWsModule; import org.sonar.server.setting.ProjectConfigurationLoaderImpl; @@ -381,6 +382,7 @@ public class PlatformLevel4 extends PlatformLevel { new GitLabModule(), new LdapModule(), new SamlModule(), + new SamlValidationModule(), DefaultAdminCredentialsVerifierImpl.class, DefaultAdminCredentialsVerifierNotificationTemplate.class, DefaultAdminCredentialsVerifierNotificationHandler.class, |