@@ -102,6 +102,7 @@ import org.sonar.server.permission.PermissionTemplateService; | |||
import org.sonar.server.permission.PermissionUpdater; | |||
import org.sonar.server.permission.UserPermissionChanger; | |||
import org.sonar.server.permission.index.PermissionIndexer; | |||
import org.sonar.server.permission.ws.template.DefaultTemplatesResolverImpl; | |||
import org.sonar.server.platform.DatabaseServerCompatibility; | |||
import org.sonar.server.platform.DefaultServerUpgradeStatus; | |||
import org.sonar.server.platform.ServerFileSystemImpl; | |||
@@ -327,6 +328,7 @@ public class ComputeEngineContainerImpl implements ComputeEngineContainer { | |||
UserIndex.class, | |||
// permissions | |||
DefaultTemplatesResolverImpl.class, | |||
PermissionTemplateService.class, | |||
PermissionUpdater.class, | |||
UserPermissionChanger.class, |
@@ -88,7 +88,7 @@ public class ComputeEngineContainerImplTest { | |||
assertThat(picoContainer.getComponentAdapters()) | |||
.hasSize( | |||
CONTAINER_ITSELF | |||
+ 77 // level 4 | |||
+ 78 // level 4 | |||
+ 4 // content of CeConfigurationModule | |||
+ 3 // content of CeHttpModule | |||
+ 5 // content of CeQueueModule |
@@ -122,7 +122,8 @@ public class ComponentUpdater { | |||
private void handlePermissionTemplate(DbSession dbSession, ComponentDto componentDto, String organizationUuid, @Nullable Long userId) { | |||
permissionTemplateService.applyDefault(dbSession, organizationUuid, componentDto, userId); | |||
if (componentDto.qualifier().equals(PROJECT) && permissionTemplateService.hasDefaultTemplateWithPermissionOnProjectCreator(dbSession, organizationUuid, componentDto)) { | |||
if (componentDto.qualifier().equals(PROJECT) | |||
&& permissionTemplateService.hasDefaultTemplateWithPermissionOnProjectCreator(dbSession, organizationUuid, componentDto)) { | |||
favoriteUpdater.add(dbSession, componentDto, userId); | |||
} | |||
} |
@@ -1,36 +0,0 @@ | |||
/* | |||
* SonarQube | |||
* Copyright (C) 2009-2016 SonarSource SA | |||
* mailto:contact 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.permission; | |||
import static java.lang.String.format; | |||
public class DefaultPermissionTemplates { | |||
public static final String DEFAULT_TEMPLATE_PROPERTY = "sonar.permission.template.default"; | |||
public static final String DEFAULT_TEMPLATE_KEY = "default_template"; | |||
private static final String DEFAULT_ROOT_QUALIFIER_TEMPLATE_PATTERN = "sonar.permission.template.%s.default"; | |||
private DefaultPermissionTemplates() { | |||
// utility class | |||
} | |||
public static String defaultRootQualifierTemplateProperty(String qualifier) { | |||
return format(DEFAULT_ROOT_QUALIFIER_TEMPLATE_PATTERN, qualifier); | |||
} | |||
} |
@@ -28,7 +28,6 @@ import java.util.Set; | |||
import javax.annotation.CheckForNull; | |||
import javax.annotation.Nullable; | |||
import org.apache.commons.lang.StringUtils; | |||
import org.sonar.api.config.Settings; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.server.ServerSide; | |||
import org.sonar.core.component.ComponentKeys; | |||
@@ -38,6 +37,7 @@ import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.component.ComponentDto; | |||
import org.sonar.db.component.ResourceDto; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import org.sonar.db.permission.GroupPermissionDto; | |||
import org.sonar.db.permission.UserPermissionDto; | |||
import org.sonar.db.permission.template.PermissionTemplateCharacteristicDto; | |||
@@ -45,9 +45,12 @@ import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.db.permission.template.PermissionTemplateGroupDto; | |||
import org.sonar.db.permission.template.PermissionTemplateUserDto; | |||
import org.sonar.server.permission.index.PermissionIndexer; | |||
import org.sonar.server.permission.ws.template.DefaultTemplatesResolver; | |||
import org.sonar.server.permission.ws.template.DefaultTemplatesResolverImpl; | |||
import org.sonar.server.user.UserSession; | |||
import static com.google.common.base.Preconditions.checkArgument; | |||
import static java.lang.String.format; | |||
import static java.util.Arrays.asList; | |||
import static java.util.Collections.singletonList; | |||
import static org.sonar.api.security.DefaultGroups.isAnyone; | |||
@@ -58,15 +61,16 @@ import static org.sonar.server.ws.WsUtils.checkFoundWithOptional; | |||
public class PermissionTemplateService { | |||
private final DbClient dbClient; | |||
private final Settings settings; | |||
private final PermissionIndexer permissionIndexer; | |||
private final UserSession userSession; | |||
private final DefaultTemplatesResolver defaultTemplatesResolver; | |||
public PermissionTemplateService(DbClient dbClient, Settings settings, PermissionIndexer permissionIndexer, UserSession userSession) { | |||
public PermissionTemplateService(DbClient dbClient, PermissionIndexer permissionIndexer, UserSession userSession, | |||
DefaultTemplatesResolver defaultTemplatesResolver) { | |||
this.dbClient = dbClient; | |||
this.settings = settings; | |||
this.permissionIndexer = permissionIndexer; | |||
this.userSession = userSession; | |||
this.defaultTemplatesResolver = defaultTemplatesResolver; | |||
} | |||
/** | |||
@@ -206,16 +210,22 @@ public class PermissionTemplateService { | |||
if (matchingTemplates.size() == 1) { | |||
return matchingTemplates.get(0); | |||
} | |||
String qualifierTemplateKey = settings.getString("sonar.permission.template." + component.qualifier() + ".default"); | |||
if (!StringUtils.isBlank(qualifierTemplateKey)) { | |||
return dbClient.permissionTemplateDao().selectByUuid(dbSession, qualifierTemplateKey); | |||
} | |||
String defaultTemplateKey = settings.getString("sonar.permission.template.default"); | |||
if (StringUtils.isBlank(defaultTemplateKey)) { | |||
throw new IllegalStateException("At least one default permission template should be defined"); | |||
DefaultTemplates defaultTemplates = dbClient.organizationDao().getDefaultTemplates(dbSession, organizationUuid) | |||
.orElseThrow(() -> new IllegalStateException( | |||
format("No Default templates defined for organization with uuid '%s'", organizationUuid))); | |||
String qualifier = component.qualifier(); | |||
DefaultTemplatesResolverImpl.ResolvedDefaultTemplates resolvedDefaultTemplates = defaultTemplatesResolver.resolve(defaultTemplates); | |||
if (Qualifiers.PROJECT.equals(qualifier)) { | |||
return dbClient.permissionTemplateDao().selectByUuid(dbSession, resolvedDefaultTemplates.getProject()); | |||
} else if (Qualifiers.VIEW.equals(qualifier)) { | |||
String viewDefaultTemplateUuid = resolvedDefaultTemplates.getView().orElseThrow( | |||
() -> new IllegalStateException("Attempt to create a view when Governance plugin is not installed")); | |||
return dbClient.permissionTemplateDao().selectByUuid(dbSession, viewDefaultTemplateUuid); | |||
} else { | |||
throw new IllegalArgumentException(format("Qualifier '%s' is not supported", qualifier)); | |||
} | |||
return dbClient.permissionTemplateDao().selectByUuid(dbSession, defaultTemplateKey); | |||
} | |||
private static void checkAtMostOneMatchForComponentKey(String componentKey, List<PermissionTemplateDto> matchingTemplates) { |
@@ -26,7 +26,6 @@ import org.sonar.server.permission.ws.template.AddUserToTemplateAction; | |||
import org.sonar.server.permission.ws.template.ApplyTemplateAction; | |||
import org.sonar.server.permission.ws.template.BulkApplyTemplateAction; | |||
import org.sonar.server.permission.ws.template.CreateTemplateAction; | |||
import org.sonar.server.permission.ws.template.DefaultPermissionTemplateFinder; | |||
import org.sonar.server.permission.ws.template.DeleteTemplateAction; | |||
import org.sonar.server.permission.ws.template.RemoveGroupFromTemplateAction; | |||
import org.sonar.server.permission.ws.template.RemoveProjectCreatorFromTemplateAction; | |||
@@ -70,7 +69,6 @@ public class PermissionsWsModule extends Module { | |||
// utility classes | |||
SearchProjectPermissionsDataLoader.class, | |||
SearchTemplatesDataLoader.class, | |||
PermissionWsSupport.class, | |||
DefaultPermissionTemplateFinder.class); | |||
PermissionWsSupport.class); | |||
} | |||
} |
@@ -1,119 +0,0 @@ | |||
/* | |||
* SonarQube | |||
* Copyright (C) 2009-2016 SonarSource SA | |||
* mailto:contact 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.permission.ws.template; | |||
import com.google.common.base.Function; | |||
import java.util.List; | |||
import java.util.Set; | |||
import javax.annotation.Nonnull; | |||
import org.sonar.api.config.Settings; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.resources.ResourceType; | |||
import org.sonar.api.resources.ResourceTypes; | |||
import static com.google.common.collect.FluentIterable.from; | |||
import static com.google.common.collect.Ordering.natural; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.DEFAULT_TEMPLATE_PROPERTY; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.defaultRootQualifierTemplateProperty; | |||
public class DefaultPermissionTemplateFinder { | |||
private final Settings settings; | |||
private final ResourceTypes resourceTypes; | |||
public DefaultPermissionTemplateFinder(Settings settings, ResourceTypes resourceTypes) { | |||
this.settings = settings; | |||
this.resourceTypes = resourceTypes; | |||
} | |||
public Set<String> getDefaultTemplateUuids() { | |||
return from(resourceTypes.getRoots()) | |||
.transform(ResourceType::getQualifier) | |||
.transform(new QualifierToDefaultTemplate(settings)) | |||
.toSortedSet(natural()); | |||
} | |||
public List<TemplateUuidQualifier> getDefaultTemplatesByQualifier() { | |||
return from(resourceTypes.getRoots()) | |||
.transform(ResourceType::getQualifier) | |||
.transform(new QualifierToTemplateUuidQualifier(settings)) | |||
.toList(); | |||
} | |||
public static class TemplateUuidQualifier { | |||
private final String templateUuid; | |||
private final String qualifier; | |||
TemplateUuidQualifier(String templateUuid, String qualifier) { | |||
this.templateUuid = templateUuid; | |||
this.qualifier = qualifier; | |||
} | |||
public String getTemplateUuid() { | |||
return templateUuid; | |||
} | |||
public String getQualifier() { | |||
return qualifier; | |||
} | |||
} | |||
private static class QualifierToDefaultTemplate implements Function<String, String> { | |||
private final Settings settings; | |||
QualifierToDefaultTemplate(Settings settings) { | |||
this.settings = settings; | |||
} | |||
@Override | |||
public String apply(@Nonnull String qualifier) { | |||
return effectiveTemplateUuid(settings, qualifier); | |||
} | |||
} | |||
private static class QualifierToTemplateUuidQualifier implements Function<String, TemplateUuidQualifier> { | |||
private final Settings settings; | |||
QualifierToTemplateUuidQualifier(Settings settings) { | |||
this.settings = settings; | |||
} | |||
@Override | |||
public TemplateUuidQualifier apply(@Nonnull String qualifier) { | |||
String effectiveTemplateUuid = effectiveTemplateUuid(settings, qualifier); | |||
return new TemplateUuidQualifier(effectiveTemplateUuid, qualifier); | |||
} | |||
} | |||
private static String effectiveTemplateUuid(Settings settings, String qualifier) { | |||
String qualifierTemplateUuid = settings.getString(defaultRootQualifierTemplateProperty(qualifier)); | |||
String projectTemplateUuid = settings.getString(defaultRootQualifierTemplateProperty(Qualifiers.PROJECT)); | |||
String defaultTemplateUuid = settings.getString(DEFAULT_TEMPLATE_PROPERTY); | |||
if (qualifierTemplateUuid != null) { | |||
return qualifierTemplateUuid; | |||
} else if (projectTemplateUuid != null) { | |||
return projectTemplateUuid; | |||
} else { | |||
return defaultTemplateUuid; | |||
} | |||
} | |||
} |
@@ -0,0 +1,60 @@ | |||
/* | |||
* SonarQube | |||
* Copyright (C) 2009-2016 SonarSource SA | |||
* mailto:contact 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.permission.ws.template; | |||
import java.util.Optional; | |||
import javax.annotation.Nullable; | |||
import javax.annotation.concurrent.Immutable; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import static java.util.Objects.requireNonNull; | |||
import static java.util.Optional.ofNullable; | |||
public interface DefaultTemplatesResolver { | |||
/** | |||
* Resolve the effective default templates uuid for the specified {@link DefaultTemplates}. | |||
* <ul> | |||
* <li>{@link ResolvedDefaultTemplates#project} is always the same as {@link DefaultTemplates#projectUuid}</li> | |||
* <li>when Governance is not installed, {@link ResolvedDefaultTemplates#view} is always {@code null}</li> | |||
* <li>when Governance is not installed, {@link ResolvedDefaultTemplates#view} is {@link DefaultTemplates#viewUuid} | |||
* when it is non {@code null}, otherwise it is {@link DefaultTemplates#projectUuid}</li> | |||
* </ul> | |||
*/ | |||
ResolvedDefaultTemplates resolve(DefaultTemplates defaultTemplates); | |||
@Immutable | |||
final class ResolvedDefaultTemplates { | |||
private final String project; | |||
private final String view; | |||
ResolvedDefaultTemplates(String project, @Nullable String view) { | |||
this.project = requireNonNull(project, "project can't be null"); | |||
this.view = view; | |||
} | |||
public String getProject() { | |||
return project; | |||
} | |||
public Optional<String> getView() { | |||
return ofNullable(view); | |||
} | |||
} | |||
} |
@@ -0,0 +1,52 @@ | |||
/* | |||
* SonarQube | |||
* Copyright (C) 2009-2016 SonarSource SA | |||
* mailto:contact 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.permission.ws.template; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.resources.ResourceType; | |||
import org.sonar.api.resources.ResourceTypes; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import static java.util.Optional.ofNullable; | |||
public class DefaultTemplatesResolverImpl implements DefaultTemplatesResolver { | |||
private final ResourceTypes resourceTypes; | |||
public DefaultTemplatesResolverImpl(ResourceTypes resourceTypes) { | |||
this.resourceTypes = resourceTypes; | |||
} | |||
@Override | |||
public ResolvedDefaultTemplates resolve(DefaultTemplates defaultTemplates) { | |||
String projectDefaultTemplate = defaultTemplates.getProjectUuid(); | |||
return new ResolvedDefaultTemplates( | |||
projectDefaultTemplate, | |||
isViewsEnabled(resourceTypes) ? ofNullable(defaultTemplates.getViewUuid()).orElse(projectDefaultTemplate) : null); | |||
} | |||
private static boolean isViewsEnabled(ResourceTypes resourceTypes) { | |||
return resourceTypes.getRoots() | |||
.stream() | |||
.map(ResourceType::getQualifier) | |||
.anyMatch(Qualifiers.VIEW::equals); | |||
} | |||
} |
@@ -19,12 +19,12 @@ | |||
*/ | |||
package org.sonar.server.permission.ws.template; | |||
import java.util.Set; | |||
import org.sonar.api.server.ws.Request; | |||
import org.sonar.api.server.ws.Response; | |||
import org.sonar.api.server.ws.WebService; | |||
import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.server.permission.ws.PermissionWsSupport; | |||
import org.sonar.server.permission.ws.PermissionsWsAction; | |||
@@ -34,6 +34,7 @@ import org.sonarqube.ws.client.permission.DeleteTemplateWsRequest; | |||
import static org.sonar.server.permission.PermissionPrivilegeChecker.checkGlobalAdmin; | |||
import static org.sonar.server.permission.ws.PermissionsWsParametersBuilder.createTemplateParameters; | |||
import static org.sonar.server.permission.ws.template.WsTemplateRef.newTemplateRef; | |||
import static org.sonar.server.ws.WsUtils.checkFoundWithOptional; | |||
import static org.sonar.server.ws.WsUtils.checkRequest; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_ORGANIZATION_KEY; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_TEMPLATE_ID; | |||
@@ -43,13 +44,13 @@ public class DeleteTemplateAction implements PermissionsWsAction { | |||
private final DbClient dbClient; | |||
private final UserSession userSession; | |||
private final PermissionWsSupport finder; | |||
private final DefaultPermissionTemplateFinder defaultPermissionTemplateFinder; | |||
private final DefaultTemplatesResolver defaultTemplatesResolver; | |||
public DeleteTemplateAction(DbClient dbClient, UserSession userSession, PermissionWsSupport support, DefaultPermissionTemplateFinder defaultPermissionTemplateFinder) { | |||
public DeleteTemplateAction(DbClient dbClient, UserSession userSession, PermissionWsSupport support, DefaultTemplatesResolver defaultTemplatesResolver) { | |||
this.dbClient = dbClient; | |||
this.userSession = userSession; | |||
this.finder = support; | |||
this.defaultPermissionTemplateFinder = defaultPermissionTemplateFinder; | |||
this.defaultTemplatesResolver = defaultTemplatesResolver; | |||
} | |||
@Override | |||
@@ -66,6 +67,7 @@ public class DeleteTemplateAction implements PermissionsWsAction { | |||
@Override | |||
public void handle(Request request, Response response) throws Exception { | |||
userSession.checkLoggedIn(); | |||
doHandle(toDeleteTemplateWsRequest(request)); | |||
response.noContent(); | |||
} | |||
@@ -76,12 +78,45 @@ public class DeleteTemplateAction implements PermissionsWsAction { | |||
request.getTemplateId(), request.getOrganization(), request.getTemplateName())); | |||
checkGlobalAdmin(userSession, template.getOrganizationUuid()); | |||
checkTemplateUuidIsNotDefault(template.getUuid()); | |||
DefaultTemplates defaultTemplates = retrieveDefaultTemplates(dbSession, template); | |||
checkTemplateUuidIsNotDefault(template, defaultTemplates); | |||
dbClient.permissionTemplateDao().deleteById(dbSession, template.getId()); | |||
updateViewDefaultTemplateWhenGovernanceIsNotInstalled(dbSession, template, defaultTemplates); | |||
dbSession.commit(); | |||
} | |||
} | |||
/** | |||
* The default template for view can be removed when Governance is not installed. To avoid keeping a reference | |||
* to a non existing template, we update the default templates. | |||
*/ | |||
private void updateViewDefaultTemplateWhenGovernanceIsNotInstalled(DbSession dbSession, PermissionTemplateDto template, DefaultTemplates defaultTemplates) { | |||
String viewDefaultTemplateUuid = defaultTemplates.getViewUuid(); | |||
if (viewDefaultTemplateUuid != null && viewDefaultTemplateUuid.equals(template.getUuid())) { | |||
defaultTemplates.setViewUuid(null); | |||
dbClient.organizationDao().setDefaultTemplates(dbSession, template.getOrganizationUuid(), defaultTemplates); | |||
} | |||
} | |||
private DefaultTemplates retrieveDefaultTemplates(DbSession dbSession, PermissionTemplateDto template) { | |||
return checkFoundWithOptional( | |||
dbClient.organizationDao().getDefaultTemplates(dbSession, template.getOrganizationUuid()), | |||
"Can't find default templates of Organization with uuid '%s' to which template with uuid '%s' belongs", | |||
template.getOrganizationUuid(), template.getUuid()); | |||
} | |||
private void checkTemplateUuidIsNotDefault(PermissionTemplateDto template, DefaultTemplates defaultTemplates) { | |||
DefaultTemplatesResolverImpl.ResolvedDefaultTemplates resolvedDefaultTemplates = defaultTemplatesResolver.resolve(defaultTemplates); | |||
checkRequest(!resolvedDefaultTemplates.getProject().equals(template.getUuid()), | |||
"It is not possible to delete the default permission template for projects"); | |||
resolvedDefaultTemplates.getView() | |||
.ifPresent(viewDefaultTemplateUuid -> checkRequest( | |||
!viewDefaultTemplateUuid.equals(template.getUuid()), | |||
"It is not possible to delete the default permission template for views")); | |||
} | |||
private static DeleteTemplateWsRequest toDeleteTemplateWsRequest(Request request) { | |||
return new DeleteTemplateWsRequest() | |||
.setTemplateId(request.param(PARAM_TEMPLATE_ID)) | |||
@@ -89,8 +124,4 @@ public class DeleteTemplateAction implements PermissionsWsAction { | |||
.setTemplateName(request.param(PARAM_TEMPLATE_NAME)); | |||
} | |||
private void checkTemplateUuidIsNotDefault(String key) { | |||
Set<String> defaultTemplateUuids = defaultPermissionTemplateFinder.getDefaultTemplateUuids(); | |||
checkRequest(!defaultTemplateUuids.contains(key), "It is not possible to delete a default template"); | |||
} | |||
} |
@@ -21,6 +21,7 @@ package org.sonar.server.permission.ws.template; | |||
import java.util.Locale; | |||
import org.sonar.api.i18n.I18n; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.server.ws.Request; | |||
import org.sonar.api.server.ws.Response; | |||
import org.sonar.api.server.ws.WebService; | |||
@@ -107,12 +108,18 @@ public class SearchTemplatesAction implements PermissionsWsAction { | |||
private static void buildDefaultTemplatesResponse(SearchTemplatesWsResponse.Builder response, SearchTemplatesData data) { | |||
TemplateIdQualifier.Builder templateUuidQualifierBuilder = TemplateIdQualifier.newBuilder(); | |||
for (DefaultPermissionTemplateFinder.TemplateUuidQualifier templateUuidQualifier : data.defaultTemplates()) { | |||
response.addDefaultTemplates(templateUuidQualifierBuilder | |||
.clear() | |||
.setQualifier(templateUuidQualifier.getQualifier()) | |||
.setTemplateId(templateUuidQualifier.getTemplateUuid())); | |||
} | |||
DefaultTemplatesResolverImpl.ResolvedDefaultTemplates resolvedDefaultTemplates = data.defaultTemplates(); | |||
response.addDefaultTemplates(templateUuidQualifierBuilder | |||
.setQualifier(Qualifiers.PROJECT) | |||
.setTemplateId(resolvedDefaultTemplates.getProject())); | |||
resolvedDefaultTemplates.getView() | |||
.ifPresent(viewDefaultTemplate -> response.addDefaultTemplates( | |||
templateUuidQualifierBuilder | |||
.clear() | |||
.setQualifier(Qualifiers.VIEW) | |||
.setTemplateId(viewDefaultTemplate))); | |||
} | |||
private static void buildTemplatesResponse(WsPermissions.SearchTemplatesWsResponse.Builder response, SearchTemplatesData data) { |
@@ -22,7 +22,7 @@ package org.sonar.server.permission.ws.template; | |||
import com.google.common.collect.Table; | |||
import java.util.List; | |||
import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.server.permission.ws.template.DefaultPermissionTemplateFinder.TemplateUuidQualifier; | |||
import org.sonar.server.permission.ws.template.DefaultTemplatesResolver.ResolvedDefaultTemplates; | |||
import static com.google.common.base.MoreObjects.firstNonNull; | |||
import static com.google.common.base.Preconditions.checkState; | |||
@@ -31,14 +31,14 @@ import static com.google.common.collect.ImmutableTable.copyOf; | |||
class SearchTemplatesData { | |||
private final List<PermissionTemplateDto> templates; | |||
private final List<TemplateUuidQualifier> defaultTemplates; | |||
private final ResolvedDefaultTemplates defaultTemplates; | |||
private final Table<Long, String, Integer> userCountByTemplateIdAndPermission; | |||
private final Table<Long, String, Integer> groupCountByTemplateIdAndPermission; | |||
private final Table<Long, String, Boolean> withProjectCreatorByTemplateIdAndPermission; | |||
private SearchTemplatesData(Builder builder) { | |||
this.templates = copyOf(builder.templates); | |||
this.defaultTemplates = copyOf(builder.defaultTemplates); | |||
this.defaultTemplates = builder.defaultTemplates; | |||
this.userCountByTemplateIdAndPermission = copyOf(builder.userCountByTemplateIdAndPermission); | |||
this.groupCountByTemplateIdAndPermission = copyOf(builder.groupCountByTemplateIdAndPermission); | |||
this.withProjectCreatorByTemplateIdAndPermission = copyOf(builder.withProjectCreatorByTemplateIdAndPermission); | |||
@@ -52,7 +52,7 @@ class SearchTemplatesData { | |||
return templates; | |||
} | |||
public List<TemplateUuidQualifier> defaultTemplates() { | |||
public ResolvedDefaultTemplates defaultTemplates() { | |||
return defaultTemplates; | |||
} | |||
@@ -70,7 +70,7 @@ class SearchTemplatesData { | |||
public static class Builder { | |||
private List<PermissionTemplateDto> templates; | |||
private List<TemplateUuidQualifier> defaultTemplates; | |||
private ResolvedDefaultTemplates defaultTemplates; | |||
private Table<Long, String, Integer> userCountByTemplateIdAndPermission; | |||
private Table<Long, String, Integer> groupCountByTemplateIdAndPermission; | |||
private Table<Long, String, Boolean> withProjectCreatorByTemplateIdAndPermission; | |||
@@ -94,7 +94,7 @@ class SearchTemplatesData { | |||
return this; | |||
} | |||
public Builder defaultTemplates(List<TemplateUuidQualifier> defaultTemplates) { | |||
public Builder defaultTemplates(ResolvedDefaultTemplates defaultTemplates) { | |||
this.defaultTemplates = defaultTemplates; | |||
return this; | |||
} |
@@ -25,31 +25,37 @@ import com.google.common.collect.TreeBasedTable; | |||
import java.util.List; | |||
import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import org.sonar.db.permission.template.CountByTemplateAndPermissionDto; | |||
import org.sonar.db.permission.template.PermissionTemplateCharacteristicDto; | |||
import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.server.permission.ws.template.DefaultPermissionTemplateFinder.TemplateUuidQualifier; | |||
import org.sonar.server.permission.ws.template.DefaultTemplatesResolver.ResolvedDefaultTemplates; | |||
import org.sonarqube.ws.client.permission.SearchTemplatesWsRequest; | |||
import static org.sonar.server.permission.ws.template.SearchTemplatesData.builder; | |||
import static org.sonar.server.ws.WsUtils.checkFoundWithOptional; | |||
public class SearchTemplatesDataLoader { | |||
private final DbClient dbClient; | |||
private final DefaultPermissionTemplateFinder defaultPermissionTemplateFinder; | |||
private final DefaultTemplatesResolver defaultTemplatesResolver; | |||
public SearchTemplatesDataLoader(DbClient dbClient, DefaultPermissionTemplateFinder defaultPermissionTemplateFinder) { | |||
public SearchTemplatesDataLoader(DbClient dbClient, DefaultTemplatesResolver defaultTemplatesResolver) { | |||
this.dbClient = dbClient; | |||
this.defaultPermissionTemplateFinder = defaultPermissionTemplateFinder; | |||
this.defaultTemplatesResolver = defaultTemplatesResolver; | |||
} | |||
public SearchTemplatesData load(DbSession dbSession, SearchTemplatesWsRequest request) { | |||
SearchTemplatesData.Builder data = builder(); | |||
List<PermissionTemplateDto> templates = searchTemplates(dbSession, request); | |||
List<Long> templateIds = Lists.transform(templates, PermissionTemplateDto::getId); | |||
List<TemplateUuidQualifier> defaultTemplates = defaultPermissionTemplateFinder.getDefaultTemplatesByQualifier(); | |||
DefaultTemplates defaultTemplates = checkFoundWithOptional( | |||
dbClient.organizationDao().getDefaultTemplates(dbSession, request.getOrganizationUuid()), | |||
"No Default templates for organization with uuid '%s'", request.getOrganizationUuid()); | |||
ResolvedDefaultTemplates resolvedDefaultTemplates = defaultTemplatesResolver.resolve(defaultTemplates); | |||
data.templates(templates) | |||
.defaultTemplates(defaultTemplates) | |||
.defaultTemplates(resolvedDefaultTemplates) | |||
.userCountByTemplateIdAndPermission(userCountByTemplateIdAndPermission(dbSession, templateIds)) | |||
.groupCountByTemplateIdAndPermission(groupCountByTemplateIdAndPermission(dbSession, templateIds)) | |||
.withProjectCreatorByTemplateIdAndPermission(withProjectCreatorsByTemplateIdAndPermission(dbSession, templateIds)); |
@@ -27,20 +27,21 @@ import org.sonar.api.server.ws.Response; | |||
import org.sonar.api.server.ws.WebService; | |||
import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import org.sonar.db.organization.OrganizationDao; | |||
import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.server.permission.ws.PermissionWsSupport; | |||
import org.sonar.server.permission.ws.PermissionsWsAction; | |||
import org.sonar.server.platform.PersistentSettings; | |||
import org.sonar.server.user.UserSession; | |||
import org.sonarqube.ws.client.permission.SetDefaultTemplateWsRequest; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.defaultRootQualifierTemplateProperty; | |||
import static org.sonar.server.permission.PermissionPrivilegeChecker.checkGlobalAdmin; | |||
import static org.sonar.server.permission.ws.PermissionRequestValidator.validateQualifier; | |||
import static org.sonar.server.permission.ws.PermissionsWsParametersBuilder.createTemplateParameters; | |||
import static org.sonar.server.permission.ws.template.WsTemplateRef.newTemplateRef; | |||
import static org.sonar.server.ws.WsParameterBuilder.QualifierParameterContext.newQualifierParameterContext; | |||
import static org.sonar.server.ws.WsParameterBuilder.createRootQualifierParameter; | |||
import static org.sonar.server.ws.WsParameterBuilder.QualifierParameterContext.newQualifierParameterContext; | |||
import static org.sonar.server.ws.WsUtils.checkFoundWithOptional; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_ORGANIZATION_KEY; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_QUALIFIER; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_TEMPLATE_ID; | |||
@@ -50,16 +51,14 @@ public class SetDefaultTemplateAction implements PermissionsWsAction { | |||
private final DbClient dbClient; | |||
private final PermissionWsSupport wsSupport; | |||
private final ResourceTypes resourceTypes; | |||
private final PersistentSettings settings; | |||
private final UserSession userSession; | |||
private final I18n i18n; | |||
public SetDefaultTemplateAction(DbClient dbClient, PermissionWsSupport wsSupport, ResourceTypes resourceTypes, PersistentSettings settings, UserSession userSession, | |||
I18n i18n) { | |||
public SetDefaultTemplateAction(DbClient dbClient, PermissionWsSupport wsSupport, ResourceTypes resourceTypes, | |||
UserSession userSession, I18n i18n) { | |||
this.dbClient = dbClient; | |||
this.wsSupport = wsSupport; | |||
this.resourceTypes = resourceTypes; | |||
this.settings = settings; | |||
this.userSession = userSession; | |||
this.i18n = i18n; | |||
} | |||
@@ -90,7 +89,7 @@ public class SetDefaultTemplateAction implements PermissionsWsAction { | |||
PermissionTemplateDto template = findTemplate(dbSession, request); | |||
checkGlobalAdmin(userSession, template.getOrganizationUuid()); | |||
validateQualifier(qualifier, resourceTypes); | |||
setDefaultTemplateUuid(dbSession, template.getUuid(), qualifier); | |||
setDefaultTemplateUuid(dbSession, template, qualifier); | |||
dbSession.commit(); | |||
} | |||
} | |||
@@ -108,7 +107,18 @@ public class SetDefaultTemplateAction implements PermissionsWsAction { | |||
request.getOrganization(), request.getTemplateName())); | |||
} | |||
private void setDefaultTemplateUuid(DbSession dbSession, String templateUuid, String qualifier) { | |||
settings.saveProperty(dbSession, defaultRootQualifierTemplateProperty(qualifier), templateUuid); | |||
private void setDefaultTemplateUuid(DbSession dbSession, PermissionTemplateDto permissionTemplateDto, String qualifier) { | |||
String organizationUuid = permissionTemplateDto.getOrganizationUuid(); | |||
OrganizationDao organizationDao = dbClient.organizationDao(); | |||
DefaultTemplates defaultTemplates = checkFoundWithOptional( | |||
organizationDao.getDefaultTemplates(dbSession, organizationUuid), | |||
"No Default templates for organization with uuid '%s'", organizationUuid); | |||
if (Qualifiers.PROJECT.equals(qualifier)) { | |||
defaultTemplates.setProjectUuid(permissionTemplateDto.getUuid()); | |||
} else if (Qualifiers.VIEW.equals(qualifier)) { | |||
defaultTemplates.setViewUuid(permissionTemplateDto.getUuid()); | |||
} | |||
organizationDao.setDefaultTemplates(dbSession, organizationUuid, defaultTemplates); | |||
} | |||
} |
@@ -93,6 +93,7 @@ import org.sonar.server.permission.PermissionUpdater; | |||
import org.sonar.server.permission.UserPermissionChanger; | |||
import org.sonar.server.permission.index.PermissionIndexer; | |||
import org.sonar.server.permission.ws.PermissionsWsModule; | |||
import org.sonar.server.permission.ws.template.DefaultTemplatesResolverImpl; | |||
import org.sonar.server.platform.BackendCleanup; | |||
import org.sonar.server.platform.PersistentSettings; | |||
import org.sonar.server.platform.ServerLogging; | |||
@@ -349,6 +350,7 @@ public class PlatformLevel4 extends PlatformLevel { | |||
UserGroupsModule.class, | |||
// permissions | |||
DefaultTemplatesResolverImpl.class, | |||
PermissionsWsModule.class, | |||
PermissionTemplateService.class, | |||
PermissionUpdater.class, |
@@ -22,7 +22,6 @@ package org.sonar.server.startup; | |||
import java.util.Date; | |||
import java.util.Optional; | |||
import javax.annotation.Nullable; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.security.DefaultGroups; | |||
import org.sonar.api.utils.log.Logger; | |||
import org.sonar.api.utils.log.Loggers; | |||
@@ -30,76 +29,58 @@ import org.sonar.api.utils.log.Profiler; | |||
import org.sonar.api.web.UserRole; | |||
import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.loadedtemplate.LoadedTemplateDto; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.db.user.GroupDto; | |||
import org.sonar.server.organization.DefaultOrganizationProvider; | |||
import org.sonar.server.platform.PersistentSettings; | |||
import static org.sonar.db.loadedtemplate.LoadedTemplateDto.PERMISSION_TEMPLATE_TYPE; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.DEFAULT_TEMPLATE_KEY; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.DEFAULT_TEMPLATE_PROPERTY; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.defaultRootQualifierTemplateProperty; | |||
public class RegisterPermissionTemplates { | |||
private static final Logger LOG = Loggers.get(RegisterPermissionTemplates.class); | |||
private static final String DEFAULT_TEMPLATE_UUID = "default_template"; | |||
private final DbClient dbClient; | |||
private final PersistentSettings settings; | |||
private final DefaultOrganizationProvider defaultOrganizationProvider; | |||
public RegisterPermissionTemplates(DbClient dbClient, PersistentSettings settings, DefaultOrganizationProvider defaultOrganizationProvider) { | |||
public RegisterPermissionTemplates(DbClient dbClient, DefaultOrganizationProvider defaultOrganizationProvider) { | |||
this.dbClient = dbClient; | |||
this.settings = settings; | |||
this.defaultOrganizationProvider = defaultOrganizationProvider; | |||
} | |||
public void start() { | |||
Profiler profiler = Profiler.create(Loggers.get(getClass())).startInfo("Register permission templates"); | |||
boolean shouldRegister = shouldRegister(); | |||
if (hasExistingPermissionsConfig()) { | |||
// needs to be done at each startup in the case a plugin has just been installed. The default property must be the project one | |||
String defaultProjectPermissionTemplateUuid = settings.getString(defaultRootQualifierTemplateProperty(Qualifiers.PROJECT)); | |||
setDefaultProperty(defaultProjectPermissionTemplateUuid); | |||
} else if (shouldRegister) { | |||
PermissionTemplateDto template = insertDefaultTemplate(); | |||
setDefaultProperty(template.getUuid()); | |||
} | |||
if (shouldRegister) { | |||
registerInitialization(); | |||
try (DbSession dbSession = dbClient.openSession(false)) { | |||
String defaultOrganizationUuid = defaultOrganizationProvider.get().getUuid(); | |||
Optional<DefaultTemplates> defaultTemplates = dbClient.organizationDao().getDefaultTemplates(dbSession, defaultOrganizationUuid); | |||
if (!defaultTemplates.isPresent()) { | |||
PermissionTemplateDto defaultTemplate = getOrInsertDefaultTemplate(dbSession, defaultOrganizationUuid); | |||
dbClient.organizationDao().setDefaultTemplates(dbSession, defaultOrganizationUuid, new DefaultTemplates().setProjectUuid(defaultTemplate.getUuid())); | |||
dbSession.commit(); | |||
} | |||
} | |||
profiler.stopDebug(); | |||
} | |||
private boolean hasExistingPermissionsConfig() { | |||
return settings.getString(defaultRootQualifierTemplateProperty(Qualifiers.PROJECT)) != null; | |||
} | |||
private boolean shouldRegister() { | |||
return dbClient.loadedTemplateDao().countByTypeAndKey(PERMISSION_TEMPLATE_TYPE, DEFAULT_TEMPLATE_KEY) == 0; | |||
} | |||
private PermissionTemplateDto insertDefaultTemplate() { | |||
try (DbSession dbSession = dbClient.openSession(false)) { | |||
String orgUuid = defaultOrganizationProvider.get().getUuid(); | |||
PermissionTemplateDto template = new PermissionTemplateDto() | |||
.setOrganizationUuid(orgUuid) | |||
.setName("Default template") | |||
.setUuid(DEFAULT_TEMPLATE_KEY) | |||
.setDescription("This permission template will be used as default when no other permission configuration is available") | |||
.setCreatedAt(new Date()) | |||
.setUpdatedAt(new Date()); | |||
dbClient.permissionTemplateDao().insert(dbSession, template); | |||
insertDefaultGroupPermissions(dbSession, template); | |||
dbSession.commit(); | |||
return template; | |||
private PermissionTemplateDto getOrInsertDefaultTemplate(DbSession dbSession, String defaultOrganizationUuid) { | |||
PermissionTemplateDto permissionTemplateDto = dbClient.permissionTemplateDao().selectByUuid(dbSession, DEFAULT_TEMPLATE_UUID); | |||
if (permissionTemplateDto != null) { | |||
return permissionTemplateDto; | |||
} | |||
PermissionTemplateDto template = new PermissionTemplateDto() | |||
.setOrganizationUuid(defaultOrganizationUuid) | |||
.setName("Default template") | |||
.setUuid(DEFAULT_TEMPLATE_UUID) | |||
.setDescription("This permission template will be used as default when no other permission configuration is available") | |||
.setCreatedAt(new Date()) | |||
.setUpdatedAt(new Date()); | |||
dbClient.permissionTemplateDao().insert(dbSession, template); | |||
insertDefaultGroupPermissions(dbSession, template); | |||
dbSession.commit(); | |||
return template; | |||
} | |||
private void insertDefaultGroupPermissions(DbSession dbSession, PermissionTemplateDto template) { | |||
@@ -122,12 +103,4 @@ public class RegisterPermissionTemplates { | |||
} | |||
} | |||
private void registerInitialization() { | |||
LoadedTemplateDto loadedTemplate = new LoadedTemplateDto(DEFAULT_TEMPLATE_KEY, PERMISSION_TEMPLATE_TYPE); | |||
dbClient.loadedTemplateDao().insert(loadedTemplate); | |||
} | |||
private void setDefaultProperty(String defaultTemplate) { | |||
settings.saveProperty(DEFAULT_TEMPLATE_PROPERTY, defaultTemplate); | |||
} | |||
} |
@@ -2,7 +2,7 @@ | |||
"paging": { | |||
"pageIndex": 1, | |||
"pageSize": 25, | |||
"total": 4 | |||
"total": 3 | |||
}, | |||
"projects": [ | |||
{ | |||
@@ -36,24 +36,6 @@ | |||
} | |||
] | |||
}, | |||
{ | |||
"id": "4e607bf9-7ed0-484a-946d-d58ba7dab2fb", | |||
"key": "simon-brandhof", | |||
"name": "Simon Brandhof", | |||
"qualifier": "DEV", | |||
"permissions": [ | |||
{ | |||
"key": "admin", | |||
"usersCount": 0, | |||
"groupsCount": 1 | |||
}, | |||
{ | |||
"key": "issueadmin", | |||
"usersCount": 1, | |||
"groupsCount": 0 | |||
} | |||
] | |||
}, | |||
{ | |||
"id": "752d8bfd-420c-4a83-a4e5-8ab19b13c8fc", | |||
"key": "Java", |
@@ -1,44 +1,5 @@ | |||
{ | |||
"permissionTemplates": [ | |||
{ | |||
"id": "AU-TpxcA-iU5OvuD2FL0", | |||
"name": "Default template for Developers", | |||
"projectKeyPattern": ".*sonar.developer.*", | |||
"createdAt": "2004-11-15T07:26:40+0100", | |||
"updatedAt": "2004-11-19T22:33:20+0100", | |||
"permissions": [ | |||
{ | |||
"key": "admin", | |||
"usersCount": 0, | |||
"groupsCount": 0, | |||
"withProjectCreator": false | |||
}, | |||
{ | |||
"key": "codeviewer", | |||
"usersCount": 0, | |||
"groupsCount": 0, | |||
"withProjectCreator": false | |||
}, | |||
{ | |||
"key": "issueadmin", | |||
"usersCount": 0, | |||
"groupsCount": 0, | |||
"withProjectCreator": false | |||
}, | |||
{ | |||
"key": "scan", | |||
"usersCount": 0, | |||
"groupsCount": 0, | |||
"withProjectCreator": false | |||
}, | |||
{ | |||
"key": "user", | |||
"usersCount": 0, | |||
"groupsCount": 1, | |||
"withProjectCreator": false | |||
} | |||
] | |||
}, | |||
{ | |||
"id": "AU-Tpxb--iU5OvuD2FLy", | |||
"name": "Default template for Projects", | |||
@@ -127,10 +88,6 @@ | |||
{ | |||
"templateId": "AU-TpxcA-iU5OvuD2FLz", | |||
"qualifier": "VW" | |||
}, | |||
{ | |||
"templateId": "AU-TpxcA-iU5OvuD2FL0", | |||
"qualifier": "DEV" | |||
} | |||
] | |||
} |
@@ -26,7 +26,6 @@ import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.junit.rules.ExpectedException; | |||
import org.sonar.api.config.MapSettings; | |||
import org.sonar.api.config.Settings; | |||
import org.sonar.api.utils.System2; | |||
import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
@@ -48,6 +47,7 @@ import org.sonar.server.measure.index.ProjectMeasuresIndexDefinition; | |||
import org.sonar.server.measure.index.ProjectMeasuresIndexer; | |||
import org.sonar.server.permission.PermissionTemplateService; | |||
import org.sonar.server.permission.index.PermissionIndexer; | |||
import org.sonar.server.permission.ws.template.DefaultTemplatesResolverRule; | |||
import org.sonar.server.view.index.ViewIndexDefinition; | |||
import static com.google.common.collect.Lists.newArrayList; | |||
@@ -75,26 +75,23 @@ public class ComponentUpdaterTest { | |||
@Rule | |||
public ExpectedException expectedException = ExpectedException.none(); | |||
@Rule | |||
public DbTester db = DbTester.create(system2); | |||
@Rule | |||
public EsTester es = new EsTester( | |||
new ComponentIndexDefinition(new MapSettings()), | |||
new ProjectMeasuresIndexDefinition(new MapSettings()), | |||
new IssueIndexDefinition(new MapSettings()), | |||
new ViewIndexDefinition(new MapSettings())); | |||
@Rule | |||
public I18nRule i18n = new I18nRule().put("qualifier.TRK", "Project"); | |||
private Settings settings = new MapSettings(); | |||
@Rule | |||
public DefaultTemplatesResolverRule defaultTemplatesResolver = DefaultTemplatesResolverRule.withoutGovernance(); | |||
private PermissionTemplateDto permissionTemplateDto; | |||
ComponentUpdater underTest = new ComponentUpdater(db.getDbClient(), i18n, system2, | |||
new PermissionTemplateService(db.getDbClient(), settings, new PermissionIndexer(db.getDbClient(), es.client()), null), | |||
new PermissionTemplateService(db.getDbClient(), new PermissionIndexer(db.getDbClient(), es.client()), null, defaultTemplatesResolver), | |||
new FavoriteUpdater(db.getDbClient()), | |||
new ProjectMeasuresIndexer(system2, db.getDbClient(), es.client()), | |||
new ComponentIndexer(db.getDbClient(), es.client())); | |||
@@ -102,7 +99,7 @@ public class ComponentUpdaterTest { | |||
@Before | |||
public void setUp() throws Exception { | |||
permissionTemplateDto = db.permissionTemplates().insertTemplate(db.getDefaultOrganization()); | |||
setTemplateAsDefault(permissionTemplateDto); | |||
db.organizations().setDefaultTemplates(db.getDefaultOrganization(), permissionTemplateDto.getUuid(), null); | |||
} | |||
@Test | |||
@@ -305,6 +302,8 @@ public class ComponentUpdaterTest { | |||
@Test | |||
public void create_view() { | |||
defaultTemplatesResolver.installGovernance(); | |||
ComponentDto view = underTest.create(db.getSession(), | |||
NewComponent.newComponentBuilder() | |||
.setKey("view-key") | |||
@@ -324,8 +323,4 @@ public class ComponentUpdaterTest { | |||
assertThat(es.getIds(ViewIndexDefinition.INDEX, ViewIndexDefinition.TYPE_VIEW)).isEmpty(); | |||
} | |||
private void setTemplateAsDefault(PermissionTemplateDto permissionTemplateDto) { | |||
settings.appendProperty("sonar.permission.template.default", permissionTemplateDto.getUuid()); | |||
} | |||
} |
@@ -21,14 +21,13 @@ package org.sonar.server.permission; | |||
import java.util.List; | |||
import javax.annotation.Nullable; | |||
import org.junit.Before; | |||
import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.junit.rules.ExpectedException; | |||
import org.sonar.api.config.MapSettings; | |||
import org.sonar.api.config.Settings; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.utils.System2; | |||
import org.sonar.api.utils.internal.AlwaysIncreasingSystem2; | |||
import org.sonar.api.web.UserRole; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.DbTester; | |||
@@ -39,126 +38,125 @@ import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.db.user.GroupDto; | |||
import org.sonar.db.user.UserDto; | |||
import org.sonar.server.permission.index.PermissionIndexer; | |||
import org.sonar.server.permission.ws.template.DefaultTemplatesResolverRule; | |||
import org.sonar.server.tester.UserSessionRule; | |||
import static java.util.Collections.singletonList; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
import static org.mockito.Mockito.mock; | |||
import static org.mockito.Mockito.when; | |||
import static org.sonar.core.permission.GlobalPermissions.SCAN_EXECUTION; | |||
import static org.sonar.db.component.ComponentTesting.newProjectDto; | |||
import static org.sonar.db.organization.OrganizationTesting.newOrganizationDto; | |||
import static org.sonar.db.user.GroupTesting.newGroupDto; | |||
public class PermissionTemplateServiceTest { | |||
private static final OrganizationDto ORGANIZATION = newOrganizationDto().setUuid("org1"); | |||
private static final ComponentDto PROJECT = newProjectDto(ORGANIZATION).setId(123L).setUuid("THE_PROJECT_UUID"); | |||
private static final long NOW = 123456789L; | |||
@Rule | |||
public ExpectedException throwable = ExpectedException.none(); | |||
private System2 system2 = mock(System2.class); | |||
@Rule | |||
public DbTester dbTester = DbTester.create(system2); | |||
public DbTester dbTester = DbTester.create(new AlwaysIncreasingSystem2()); | |||
@Rule | |||
public DefaultTemplatesResolverRule defaultTemplatesResolver = DefaultTemplatesResolverRule.withGovernance(); | |||
private UserSessionRule userSession = UserSessionRule.standalone(); | |||
private PermissionTemplateDbTester templateDb = dbTester.permissionTemplates(); | |||
private DbSession session = dbTester.getSession(); | |||
private Settings settings = new MapSettings(); | |||
private PermissionIndexer permissionIndexer = mock(PermissionIndexer.class); | |||
private PermissionTemplateService underTest = new PermissionTemplateService(dbTester.getDbClient(), settings, | |||
permissionIndexer, userSession); | |||
@Before | |||
public void setUp() { | |||
when(system2.now()).thenReturn(NOW); | |||
} | |||
private PermissionTemplateService underTest = new PermissionTemplateService(dbTester.getDbClient(), permissionIndexer, userSession, defaultTemplatesResolver); | |||
@Test | |||
public void apply_permission_template() { | |||
dbTester.prepareDbUnit(getClass(), "should_apply_permission_template.xml"); | |||
assertThat(selectProjectPermissionsOfGroup("org1", 100L, PROJECT)).isEmpty(); | |||
assertThat(selectProjectPermissionsOfGroup("org1", 101L, PROJECT)).isEmpty(); | |||
assertThat(selectProjectPermissionsOfGroup("org1", null, PROJECT)).isEmpty(); | |||
assertThat(selectProjectPermissionsOfUser(200L, PROJECT)).isEmpty(); | |||
PermissionTemplateDto template = dbTester.getDbClient().permissionTemplateDao().selectByUuid(session, "default_20130101_010203"); | |||
underTest.apply(session, template, singletonList(PROJECT)); | |||
assertThat(selectProjectPermissionsOfGroup("org1", 100L, PROJECT)).containsOnly("admin", "issueadmin"); | |||
assertThat(selectProjectPermissionsOfGroup("org1", 101L, PROJECT)).containsOnly("user", "codeviewer"); | |||
assertThat(selectProjectPermissionsOfGroup("org1", null, PROJECT)).containsOnly("user", "codeviewer"); | |||
assertThat(selectProjectPermissionsOfUser(200L, PROJECT)).containsOnly("admin"); | |||
checkAuthorizationUpdatedAtIsUpdated(); | |||
OrganizationDto organization = dbTester.organizations().insert(); | |||
ComponentDto project = dbTester.components().insertProject(organization); | |||
GroupDto adminGroup = dbTester.users().insertGroup(organization); | |||
GroupDto userGroup = dbTester.users().insertGroup(organization); | |||
UserDto user = dbTester.users().insertUser(); | |||
dbTester.users().insertPermissionOnGroup(adminGroup, "admin"); | |||
dbTester.users().insertPermissionOnGroup(userGroup, "user"); | |||
dbTester.users().insertPermissionOnUser(organization, user, "admin"); | |||
PermissionTemplateDto permissionTemplate = dbTester.permissionTemplates().insertTemplate(organization); | |||
dbTester.permissionTemplates().addGroupToTemplate(permissionTemplate, adminGroup, "admin"); | |||
dbTester.permissionTemplates().addGroupToTemplate(permissionTemplate, adminGroup, "issueadmin"); | |||
dbTester.permissionTemplates().addGroupToTemplate(permissionTemplate, userGroup, "user"); | |||
dbTester.permissionTemplates().addGroupToTemplate(permissionTemplate, userGroup, "codeviewer"); | |||
dbTester.permissionTemplates().addAnyoneToTemplate(permissionTemplate, "user"); | |||
dbTester.permissionTemplates().addAnyoneToTemplate(permissionTemplate, "codeviewer"); | |||
dbTester.permissionTemplates().addUserToTemplate(permissionTemplate, user, "admin"); | |||
assertThat(selectProjectPermissionsOfGroup(organization, adminGroup, project)).isEmpty(); | |||
assertThat(selectProjectPermissionsOfGroup(organization, userGroup, project)).isEmpty(); | |||
assertThat(selectProjectPermissionsOfGroup(organization, null, project)).isEmpty(); | |||
assertThat(selectProjectPermissionsOfUser(user, project)).isEmpty(); | |||
underTest.apply(session, permissionTemplate, singletonList(project)); | |||
assertThat(selectProjectPermissionsOfGroup(organization, adminGroup, project)).containsOnly("admin", "issueadmin"); | |||
assertThat(selectProjectPermissionsOfGroup(organization, userGroup, project)).containsOnly("user", "codeviewer"); | |||
assertThat(selectProjectPermissionsOfGroup(organization, null, project)).containsOnly("user", "codeviewer"); | |||
assertThat(selectProjectPermissionsOfUser(user, project)).containsOnly("admin"); | |||
checkAuthorizationUpdatedAtIsUpdated(project); | |||
} | |||
private List<String> selectProjectPermissionsOfGroup(String organizationUuid, @Nullable Long groupId, ComponentDto project) { | |||
private List<String> selectProjectPermissionsOfGroup(OrganizationDto organizationDto, @Nullable GroupDto groupDto, ComponentDto project) { | |||
return dbTester.getDbClient().groupPermissionDao().selectProjectPermissionsOfGroup(session, | |||
organizationUuid, groupId != null ? groupId : null, project.getId()); | |||
organizationDto.getUuid(), groupDto != null ? groupDto.getId() : null, project.getId()); | |||
} | |||
private List<String> selectProjectPermissionsOfUser(long userId, ComponentDto project) { | |||
private List<String> selectProjectPermissionsOfUser(UserDto userDto, ComponentDto project) { | |||
return dbTester.getDbClient().userPermissionDao().selectProjectPermissionsOfUser(session, | |||
userId, project.getId()); | |||
userDto.getId(), project.getId()); | |||
} | |||
@Test | |||
public void would_user_have_permission_with_default_permission_template() { | |||
OrganizationDto organization = dbTester.organizations().insert(); | |||
UserDto user = dbTester.users().insertUser(); | |||
GroupDto group = dbTester.users().insertGroup(newGroupDto()); | |||
GroupDto group = dbTester.users().insertGroup(organization); | |||
dbTester.users().insertMember(group, user); | |||
PermissionTemplateDto template = templateDb.insertTemplate(); | |||
setDefaultTemplateUuid(template.getUuid()); | |||
PermissionTemplateDto template = templateDb.insertTemplate(organization); | |||
dbTester.organizations().setDefaultTemplates(organization, template.getUuid(), null); | |||
templateDb.addProjectCreatorToTemplate(template.getId(), SCAN_EXECUTION); | |||
templateDb.addUserToTemplate(template.getId(), user.getId(), UserRole.USER); | |||
templateDb.addGroupToTemplate(template.getId(), group.getId(), UserRole.CODEVIEWER); | |||
templateDb.addGroupToTemplate(template.getId(), null, UserRole.ISSUE_ADMIN); | |||
// authenticated user | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), user.getId(), UserRole.ADMIN, false); | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), user.getId(), SCAN_EXECUTION, true); | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), user.getId(), UserRole.USER, true); | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), user.getId(), UserRole.CODEVIEWER, true); | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), user.getId(), UserRole.ISSUE_ADMIN, true); | |||
checkWouldUserHavePermission(organization, user.getId(), UserRole.ADMIN, false); | |||
checkWouldUserHavePermission(organization, user.getId(), SCAN_EXECUTION, true); | |||
checkWouldUserHavePermission(organization, user.getId(), UserRole.USER, true); | |||
checkWouldUserHavePermission(organization, user.getId(), UserRole.CODEVIEWER, true); | |||
checkWouldUserHavePermission(organization, user.getId(), UserRole.ISSUE_ADMIN, true); | |||
// anonymous user | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), null, UserRole.ADMIN, false); | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), null, SCAN_EXECUTION, false); | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), null, UserRole.USER, false); | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), null, UserRole.CODEVIEWER, false); | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), null, UserRole.ISSUE_ADMIN, true); | |||
checkWouldUserHavePermission(organization, null, UserRole.ADMIN, false); | |||
checkWouldUserHavePermission(organization, null, SCAN_EXECUTION, false); | |||
checkWouldUserHavePermission(organization, null, UserRole.USER, false); | |||
checkWouldUserHavePermission(organization, null, UserRole.CODEVIEWER, false); | |||
checkWouldUserHavePermission(organization, null, UserRole.ISSUE_ADMIN, true); | |||
} | |||
@Test | |||
public void would_user_have_permission_with_unknown_default_permission_template() { | |||
setDefaultTemplateUuid("UNKNOWN_TEMPLATE_UUID"); | |||
dbTester.organizations().setDefaultTemplates(dbTester.getDefaultOrganization(), "UNKNOWN_TEMPLATE_UUID", null); | |||
checkWouldUserHavePermission(dbTester.getDefaultOrganization().getUuid(), null, UserRole.ADMIN, false); | |||
checkWouldUserHavePermission(dbTester.getDefaultOrganization(), null, UserRole.ADMIN, false); | |||
} | |||
@Test | |||
public void would_user_have_permission_with_empty_template() { | |||
PermissionTemplateDto template = templateDb.insertTemplate(); | |||
setDefaultTemplateUuid(template.getUuid()); | |||
checkWouldUserHavePermission(template.getOrganizationUuid(), null, UserRole.ADMIN, false); | |||
} | |||
PermissionTemplateDto template = templateDb.insertTemplate(dbTester.getDefaultOrganization()); | |||
dbTester.organizations().setDefaultTemplates(dbTester.getDefaultOrganization(), template.getUuid(), null); | |||
private void checkWouldUserHavePermission(String organizationUuid, @Nullable Long userId, String permission, boolean expectedResult) { | |||
assertThat(underTest.wouldUserHavePermissionWithDefaultTemplate(session, organizationUuid, userId, permission, null, "PROJECT_KEY", Qualifiers.PROJECT)).isEqualTo(expectedResult); | |||
checkWouldUserHavePermission(dbTester.getDefaultOrganization(), null, UserRole.ADMIN, false); | |||
} | |||
private void checkAuthorizationUpdatedAtIsUpdated() { | |||
assertThat(dbTester.getDbClient().componentDao().selectOrFailById(session, PROJECT.getId()).getAuthorizationUpdatedAt()).isEqualTo(NOW); | |||
private void checkWouldUserHavePermission(OrganizationDto organization, @Nullable Long userId, String permission, boolean expectedResult) { | |||
assertThat(underTest.wouldUserHavePermissionWithDefaultTemplate(session, organization.getUuid(), userId, permission, null, "PROJECT_KEY", Qualifiers.PROJECT)) | |||
.isEqualTo(expectedResult); | |||
} | |||
private void setDefaultTemplateUuid(String templateUuid) { | |||
settings.setProperty("sonar.permission.template.default", templateUuid); | |||
private void checkAuthorizationUpdatedAtIsUpdated(ComponentDto project) { | |||
assertThat(dbTester.getDbClient().componentDao().selectOrFailById(session, project.getId()).getAuthorizationUpdatedAt()) | |||
.isNotNull(); | |||
} | |||
} |
@@ -73,7 +73,7 @@ public abstract class BasePermissionWsTest<A extends PermissionsWsAction> { | |||
} | |||
protected ResourceTypesRule newRootResourceTypes() { | |||
return new ResourceTypesRule().setRootQualifiers(Qualifiers.PROJECT, Qualifiers.VIEW, "DEV"); | |||
return new ResourceTypesRule().setRootQualifiers(Qualifiers.PROJECT, Qualifiers.VIEW); | |||
} | |||
protected PermissionUpdater newPermissionUpdater() { | |||
@@ -110,11 +110,15 @@ public abstract class BasePermissionWsTest<A extends PermissionsWsAction> { | |||
return db.getDbClient().permissionTemplateDao().selectByName(db.getSession(), db.getDefaultOrganization().getUuid(), name); | |||
} | |||
protected PermissionTemplateDto addTemplateToDefaultOrganization() { | |||
protected PermissionTemplateDto addTemplate(OrganizationDto organizationDto) { | |||
PermissionTemplateDto dto = newPermissionTemplateDto() | |||
.setOrganizationUuid(db.getDefaultOrganization().getUuid()); | |||
.setOrganizationUuid(organizationDto.getUuid()); | |||
db.getDbClient().permissionTemplateDao().insert(db.getSession(), dto); | |||
db.commit(); | |||
return dto; | |||
} | |||
protected PermissionTemplateDto addTemplateToDefaultOrganization() { | |||
return addTemplate(db.getDefaultOrganization()); | |||
} | |||
} |
@@ -23,12 +23,13 @@ import org.junit.Test; | |||
import org.sonar.core.platform.ComponentContainer; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
import static org.sonar.core.platform.ComponentContainer.COMPONENTS_IN_EMPTY_COMPONENT_CONTAINER; | |||
public class PermissionsWsModuleTest { | |||
@Test | |||
public void verify_count_of_added_components() { | |||
ComponentContainer container = new ComponentContainer(); | |||
new PermissionsWsModule().configure(container); | |||
assertThat(container.size()).isEqualTo(2 + 28); | |||
assertThat(container.size()).isEqualTo(COMPONENTS_IN_EMPTY_COMPONENT_CONTAINER + 27); | |||
} | |||
} |
@@ -64,6 +64,8 @@ public class ApplyTemplateActionTest extends BasePermissionWsTest<ApplyTemplateA | |||
new IssueIndexDefinition(new MapSettings()), | |||
new ProjectMeasuresIndexDefinition(new MapSettings()), | |||
new ComponentIndexDefinition(new MapSettings())); | |||
@Rule | |||
public DefaultTemplatesResolverRule defaultTemplatesResolver = DefaultTemplatesResolverRule.withoutGovernance(); | |||
private UserDto user1; | |||
private UserDto user2; | |||
@@ -78,7 +80,7 @@ public class ApplyTemplateActionTest extends BasePermissionWsTest<ApplyTemplateA | |||
@Override | |||
protected ApplyTemplateAction buildWsAction() { | |||
PermissionTemplateService permissionTemplateService = new PermissionTemplateService(db.getDbClient(), | |||
new MapSettings(), permissionIndexer, userSession); | |||
permissionIndexer, userSession, defaultTemplatesResolver); | |||
return new ApplyTemplateAction(db.getDbClient(), userSession, permissionTemplateService, newPermissionWsSupport()); | |||
} | |||
@@ -22,7 +22,6 @@ package org.sonar.server.permission.ws.template; | |||
import java.util.List; | |||
import org.junit.Before; | |||
import org.junit.Test; | |||
import org.sonar.api.config.MapSettings; | |||
import org.sonar.api.server.ws.WebService.Param; | |||
import org.sonar.api.web.UserRole; | |||
import org.sonar.db.component.ComponentDto; | |||
@@ -40,7 +39,6 @@ import org.sonar.server.permission.ws.BasePermissionWsTest; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
import static org.mockito.Mockito.mock; | |||
import static org.sonar.db.component.ComponentTesting.newDeveloper; | |||
import static org.sonar.db.component.ComponentTesting.newProjectDto; | |||
import static org.sonar.db.component.ComponentTesting.newView; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_QUALIFIER; | |||
@@ -49,6 +47,9 @@ import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_T | |||
public class BulkApplyTemplateActionTest extends BasePermissionWsTest<BulkApplyTemplateAction> { | |||
@org.junit.Rule | |||
public DefaultTemplatesResolverRule defaultTemplatesResolver = DefaultTemplatesResolverRule.withoutGovernance(); | |||
private UserDto user1; | |||
private UserDto user2; | |||
private GroupDto group1; | |||
@@ -59,8 +60,8 @@ public class BulkApplyTemplateActionTest extends BasePermissionWsTest<BulkApplyT | |||
@Override | |||
protected BulkApplyTemplateAction buildWsAction() { | |||
PermissionTemplateService permissionTemplateService = new PermissionTemplateService(db.getDbClient(), new MapSettings(), | |||
issuePermissionIndexer, userSession); | |||
PermissionTemplateService permissionTemplateService = new PermissionTemplateService(db.getDbClient(), | |||
issuePermissionIndexer, userSession, defaultTemplatesResolver); | |||
return new BulkApplyTemplateAction(db.getDbClient(), userSession, permissionTemplateService, newPermissionWsSupport(), new I18nRule(), newRootResourceTypes()); | |||
} | |||
@@ -91,18 +92,16 @@ public class BulkApplyTemplateActionTest extends BasePermissionWsTest<BulkApplyT | |||
OrganizationDto organization = db.getDefaultOrganization(); | |||
ComponentDto project = db.components().insertComponent(newProjectDto(organization)); | |||
ComponentDto view = db.components().insertComponent(newView(organization)); | |||
ComponentDto developer = db.components().insertComponent(newDeveloper(organization, "developer-name")); | |||
db.users().insertProjectPermissionOnUser(user1, UserRole.ADMIN, developer); | |||
db.users().insertProjectPermissionOnUser(user2, UserRole.ADMIN, developer); | |||
db.users().insertProjectPermissionOnGroup(group1, UserRole.ADMIN, developer); | |||
db.users().insertProjectPermissionOnGroup(group2, UserRole.ADMIN, developer); | |||
db.users().insertProjectPermissionOnUser(user1, UserRole.ADMIN, view); | |||
db.users().insertProjectPermissionOnUser(user2, UserRole.ADMIN, view); | |||
db.users().insertProjectPermissionOnGroup(group1, UserRole.ADMIN, view); | |||
db.users().insertProjectPermissionOnGroup(group2, UserRole.ADMIN, view); | |||
loginAsAdminOnDefaultOrganization(); | |||
newRequest().setParam(PARAM_TEMPLATE_ID, template1.getUuid()).execute(); | |||
assertTemplate1AppliedToProject(project); | |||
assertTemplate1AppliedToProject(view); | |||
assertTemplate1AppliedToProject(developer); | |||
} | |||
@Test |
@@ -1,99 +0,0 @@ | |||
/* | |||
* SonarQube | |||
* Copyright (C) 2009-2016 SonarSource SA | |||
* mailto:contact 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.permission.ws.template; | |||
import java.util.List; | |||
import java.util.Set; | |||
import org.junit.Before; | |||
import org.junit.Test; | |||
import org.sonar.api.config.MapSettings; | |||
import org.sonar.api.config.Settings; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.resources.ResourceType; | |||
import org.sonar.api.resources.ResourceTypes; | |||
import org.sonar.server.permission.ws.template.DefaultPermissionTemplateFinder.TemplateUuidQualifier; | |||
import static java.util.Arrays.asList; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
import static org.assertj.core.groups.Tuple.tuple; | |||
import static org.mockito.Mockito.mock; | |||
import static org.mockito.Mockito.when; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.DEFAULT_TEMPLATE_PROPERTY; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.defaultRootQualifierTemplateProperty; | |||
public class DefaultPermissionTemplateFinderTest { | |||
private ResourceTypes resourceTypes = mock(ResourceTypes.class); | |||
private Settings settings = new MapSettings(); | |||
private DefaultPermissionTemplateFinder underTest; | |||
@Before | |||
public void setUp() { | |||
underTest = new DefaultPermissionTemplateFinder(settings, resourceTypes); | |||
when(resourceTypes.getRoots()).thenReturn(rootResourceTypes()); | |||
} | |||
@Test | |||
public void get_default_template_uuids_in_settings() { | |||
settings | |||
.setProperty(DEFAULT_TEMPLATE_PROPERTY, "default-template-uuid") | |||
.setProperty(defaultRootQualifierTemplateProperty(Qualifiers.PROJECT), "default-project-template-uuid") | |||
.setProperty(defaultRootQualifierTemplateProperty("DEV"), "default-dev-template-uuid") | |||
.setProperty(defaultRootQualifierTemplateProperty(Qualifiers.VIEW), "default-view-template-uuid"); | |||
Set<String> result = underTest.getDefaultTemplateUuids(); | |||
assertThat(result).containsOnly("default-project-template-uuid", "default-view-template-uuid", "default-dev-template-uuid"); | |||
} | |||
@Test | |||
public void get_default_template_uuid_if_no_property() { | |||
settings.setProperty(DEFAULT_TEMPLATE_PROPERTY, "default-template-uuid"); | |||
underTest = new DefaultPermissionTemplateFinder(settings, resourceTypes); | |||
Set<String> result = underTest.getDefaultTemplateUuids(); | |||
assertThat(result).containsOnly("default-template-uuid"); | |||
} | |||
@Test | |||
public void get_default_project_template_uuid_if_no_property_for_views() { | |||
settings | |||
.setProperty(DEFAULT_TEMPLATE_PROPERTY, "default-template-uuid") | |||
.setProperty(defaultRootQualifierTemplateProperty(Qualifiers.PROJECT), "default-project-template-uuid") | |||
.setProperty(defaultRootQualifierTemplateProperty("DEV"), "default-dev-template-uuid"); | |||
List<TemplateUuidQualifier> result = underTest.getDefaultTemplatesByQualifier(); | |||
assertThat(result).extracting(TemplateUuidQualifier::getQualifier, TemplateUuidQualifier::getTemplateUuid) | |||
.containsOnly( | |||
tuple(Qualifiers.PROJECT, "default-project-template-uuid"), | |||
tuple(Qualifiers.VIEW, "default-project-template-uuid"), | |||
tuple("DEV", "default-dev-template-uuid")); | |||
} | |||
private static List<ResourceType> rootResourceTypes() { | |||
ResourceType project = ResourceType.builder(Qualifiers.PROJECT).build(); | |||
ResourceType view = ResourceType.builder(Qualifiers.VIEW).build(); | |||
ResourceType dev = ResourceType.builder("DEV").build(); | |||
return asList(project, view, dev); | |||
} | |||
} |
@@ -0,0 +1,77 @@ | |||
/* | |||
* SonarQube | |||
* Copyright (C) 2009-2016 SonarSource SA | |||
* mailto:contact 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.permission.ws.template; | |||
import java.util.stream.Stream; | |||
import org.junit.Test; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.resources.ResourceType; | |||
import org.sonar.api.resources.ResourceTypeTree; | |||
import org.sonar.api.resources.ResourceTypes; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
public class DefaultTemplatesResolverImplTest { | |||
private static final ResourceTypes RESOURCE_TYPES_WITHOUT_VIEWS = new ResourceTypes(new ResourceTypeTree[] { | |||
ResourceTypeTree.builder().addType(ResourceType.builder(Qualifiers.PROJECT).build()).build() | |||
}); | |||
private static final ResourceTypes RESOURCE_TYPES_WITH_VIEWS = new ResourceTypes(new ResourceTypeTree[] { | |||
ResourceTypeTree.builder().addType(ResourceType.builder(Qualifiers.PROJECT).build()).build(), | |||
ResourceTypeTree.builder().addType(ResourceType.builder(Qualifiers.VIEW).build()).build() | |||
}); | |||
private DefaultTemplatesResolverImpl underTestWithoutViews = new DefaultTemplatesResolverImpl(RESOURCE_TYPES_WITHOUT_VIEWS); | |||
private DefaultTemplatesResolverImpl underTestWithViews = new DefaultTemplatesResolverImpl(RESOURCE_TYPES_WITH_VIEWS); | |||
@Test | |||
public void project_is_project_of_DefaultTemplates_no_matter_if_views_is_installed() { | |||
Stream.of( | |||
new DefaultTemplates().setProjectUuid("foo").setViewUuid(null), | |||
new DefaultTemplates().setProjectUuid("foo").setViewUuid("bar")).forEach( | |||
defaultTemplates -> { | |||
assertThat(underTestWithoutViews.resolve(defaultTemplates).getProject()).isEqualTo("foo"); | |||
assertThat(underTestWithViews.resolve(defaultTemplates).getProject()).isEqualTo("foo"); | |||
}); | |||
} | |||
@Test | |||
public void view_is_empty_no_matter_view_in_DefaultTemplates_if_views_is_not_installed() { | |||
DefaultTemplates defaultTemplatesNoView = new DefaultTemplates().setProjectUuid("foo").setViewUuid(null); | |||
DefaultTemplates defaultTemplatesView = new DefaultTemplates().setProjectUuid("foo").setViewUuid("bar"); | |||
assertThat(underTestWithoutViews.resolve(defaultTemplatesNoView).getView()).isEmpty(); | |||
assertThat(underTestWithoutViews.resolve(defaultTemplatesView).getView()).isEmpty(); | |||
} | |||
@Test | |||
public void view_is_project_of_DefaultTemplates_if_view_in_DefaultTemplates_is_null_and_views_is_installed() { | |||
DefaultTemplates defaultTemplates = new DefaultTemplates().setProjectUuid("foo").setViewUuid(null); | |||
assertThat(underTestWithViews.resolve(defaultTemplates).getView()).contains("foo"); | |||
} | |||
@Test | |||
public void view_is_view_of_DefaultTemplates_if_view_in_DefaultTemplates_is_not_null_and_views_is_installed() { | |||
DefaultTemplates defaultTemplates = new DefaultTemplates().setProjectUuid("foo").setViewUuid("bar"); | |||
assertThat(underTestWithViews.resolve(defaultTemplates).getView()).contains("bar"); | |||
} | |||
} |
@@ -0,0 +1,79 @@ | |||
/* | |||
* SonarQube | |||
* Copyright (C) 2009-2016 SonarSource SA | |||
* mailto:contact 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.permission.ws.template; | |||
import org.junit.rules.ExternalResource; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.resources.ResourceType; | |||
import org.sonar.api.resources.ResourceTypeTree; | |||
import org.sonar.api.resources.ResourceTypes; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
public class DefaultTemplatesResolverRule extends ExternalResource implements DefaultTemplatesResolver { | |||
private static final DefaultTemplatesResolver WITH_VIEWS = new DefaultTemplatesResolverImpl( | |||
new ResourceTypes(new ResourceTypeTree[] { | |||
ResourceTypeTree.builder() | |||
.addType(ResourceType.builder(Qualifiers.PROJECT).build()) | |||
.build(), | |||
ResourceTypeTree.builder() | |||
.addType(ResourceType.builder(Qualifiers.VIEW).build()) | |||
.build()})); | |||
private static final DefaultTemplatesResolver WITHOUT_VIEWS = new DefaultTemplatesResolverImpl( | |||
new ResourceTypes(new ResourceTypeTree[] {ResourceTypeTree.builder() | |||
.addType(ResourceType.builder(Qualifiers.PROJECT).build()) | |||
.build()})); | |||
private final boolean governanceInitiallyInstalled; | |||
private boolean governanceInstalled; | |||
private DefaultTemplatesResolverRule(boolean governanceInitiallyInstalled) { | |||
this.governanceInitiallyInstalled = governanceInitiallyInstalled; | |||
this.governanceInstalled = governanceInitiallyInstalled; | |||
} | |||
@Override | |||
protected void before() throws Throwable { | |||
this.governanceInstalled = governanceInitiallyInstalled; | |||
} | |||
public void installGovernance() { | |||
this.governanceInstalled = true; | |||
} | |||
public void uninstallGovernance() { | |||
this.governanceInstalled = false; | |||
} | |||
public static DefaultTemplatesResolverRule withoutGovernance() { | |||
return new DefaultTemplatesResolverRule(false); | |||
} | |||
public static DefaultTemplatesResolverRule withGovernance() { | |||
return new DefaultTemplatesResolverRule(true); | |||
} | |||
@Override | |||
public DefaultTemplatesResolverImpl.ResolvedDefaultTemplates resolve(DefaultTemplates defaultTemplates) { | |||
if (governanceInstalled) { | |||
return WITH_VIEWS.resolve(defaultTemplates); | |||
} | |||
return WITHOUT_VIEWS.resolve(defaultTemplates); | |||
} | |||
} |
@@ -19,126 +19,375 @@ | |||
*/ | |||
package org.sonar.server.permission.ws.template; | |||
import java.util.Collections; | |||
import java.util.Date; | |||
import java.util.Arrays; | |||
import javax.annotation.Nullable; | |||
import org.junit.Before; | |||
import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.junit.rules.ExpectedException; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.utils.internal.AlwaysIncreasingSystem2; | |||
import org.sonar.api.web.UserRole; | |||
import org.sonar.core.permission.GlobalPermissions; | |||
import org.sonar.db.permission.template.PermissionTemplateCharacteristicDto; | |||
import org.sonar.db.DbClient; | |||
import org.sonar.db.DbTester; | |||
import org.sonar.db.component.ResourceTypesRule; | |||
import org.sonar.db.organization.OrganizationDto; | |||
import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.db.permission.template.PermissionTemplateTesting; | |||
import org.sonar.db.user.GroupDto; | |||
import org.sonar.db.user.GroupTesting; | |||
import org.sonar.db.user.UserDto; | |||
import org.sonar.db.user.UserTesting; | |||
import org.sonar.server.component.ComponentFinder; | |||
import org.sonar.server.exceptions.BadRequestException; | |||
import org.sonar.server.exceptions.ForbiddenException; | |||
import org.sonar.server.exceptions.NotFoundException; | |||
import org.sonar.server.exceptions.UnauthorizedException; | |||
import org.sonar.server.permission.ws.BasePermissionWsTest; | |||
import org.sonar.server.organization.TestDefaultOrganizationProvider; | |||
import org.sonar.server.permission.ws.PermissionWsSupport; | |||
import org.sonar.server.tester.UserSessionRule; | |||
import org.sonar.server.usergroups.ws.GroupWsSupport; | |||
import org.sonar.server.ws.TestRequest; | |||
import org.sonar.server.ws.TestResponse; | |||
import org.sonar.server.ws.WsActionTester; | |||
import static com.google.common.primitives.Longs.asList; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
import static org.mockito.Mockito.mock; | |||
import static org.mockito.Mockito.when; | |||
import static org.mockito.internal.util.collections.Sets.newSet; | |||
import static org.assertj.core.api.Assertions.fail; | |||
import static org.sonar.core.permission.GlobalPermissions.SYSTEM_ADMIN; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_ORGANIZATION_KEY; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_TEMPLATE_ID; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_TEMPLATE_NAME; | |||
public class DeleteTemplateActionTest extends BasePermissionWsTest<DeleteTemplateAction> { | |||
public class DeleteTemplateActionTest { | |||
private DefaultPermissionTemplateFinder defaultTemplatePermissionFinder = mock(DefaultPermissionTemplateFinder.class); | |||
private PermissionTemplateDto template; | |||
@Rule | |||
public DbTester db = DbTester.create(new AlwaysIncreasingSystem2()); | |||
@Rule | |||
public ExpectedException expectedException = ExpectedException.none(); | |||
@Override | |||
protected DeleteTemplateAction buildWsAction() { | |||
return new DeleteTemplateAction(db.getDbClient(), userSession, newPermissionWsSupport(), defaultTemplatePermissionFinder); | |||
} | |||
private UserSessionRule userSession = UserSessionRule.standalone(); | |||
private DbClient dbClient = db.getDbClient(); | |||
private final ResourceTypesRule resourceTypes = new ResourceTypesRule().setRootQualifiers(Qualifiers.PROJECT); | |||
private final ResourceTypesRule resourceTypesWithViews = new ResourceTypesRule().setRootQualifiers(Qualifiers.PROJECT, Qualifiers.VIEW); | |||
private DefaultTemplatesResolver defaultTemplatesResolver = new DefaultTemplatesResolverImpl(resourceTypes); | |||
private DefaultTemplatesResolver defaultTemplatesResolverWithViews = new DefaultTemplatesResolverImpl(resourceTypesWithViews); | |||
private WsActionTester underTestWithoutViews; | |||
private WsActionTester underTestWithViews; | |||
@Before | |||
public void setUp() { | |||
loginAsAdminOnDefaultOrganization(); | |||
when(defaultTemplatePermissionFinder.getDefaultTemplateUuids()).thenReturn(Collections.emptySet()); | |||
template = insertTemplateAndAssociatedPermissions(); | |||
public void setUp() throws Exception { | |||
GroupWsSupport groupWsSupport = new GroupWsSupport(dbClient, TestDefaultOrganizationProvider.from(db)); | |||
this.underTestWithoutViews = new WsActionTester(new DeleteTemplateAction(dbClient, userSession, | |||
new PermissionWsSupport(dbClient, new ComponentFinder(dbClient), groupWsSupport, resourceTypes), | |||
defaultTemplatesResolver)); | |||
this.underTestWithViews = new WsActionTester(new DeleteTemplateAction(dbClient, userSession, | |||
new PermissionWsSupport(dbClient, new ComponentFinder(dbClient), groupWsSupport, resourceTypesWithViews), | |||
defaultTemplatesResolverWithViews)); | |||
} | |||
@Test | |||
public void delete_template_in_db() throws Exception { | |||
TestResponse result = newRequest(template.getUuid()); | |||
runOnAllUnderTests((underTest) -> { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
db.organizations().setDefaultTemplates(organization, "foo", "bar"); | |||
loginAsAdmin(organization); | |||
assertThat(result.getInput()).isEmpty(); | |||
assertThat(db.getDbClient().permissionTemplateDao().selectByUuid(db.getSession(), template.getUuid())).isNull(); | |||
TestResponse result = newRequestByUuid(underTest, template.getUuid()); | |||
assertThat(result.getInput()).isEmpty(); | |||
assertTemplateDoesNotExist(template); | |||
}); | |||
} | |||
@Test | |||
public void delete_template_by_name_case_insensitive() throws Exception { | |||
newRequest() | |||
.setParam(PARAM_TEMPLATE_NAME, template.getName().toUpperCase()) | |||
.execute(); | |||
runOnAllUnderTests((underTest) -> { | |||
OrganizationDto organization = db.organizations().insert(); | |||
db.organizations().setDefaultTemplates(organization, "project def template uuid", "view def template uuid"); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
loginAsAdmin(organization); | |||
newRequestByName(underTest, organization, template); | |||
assertThat(db.getDbClient().permissionTemplateDao().selectByUuid(db.getSession(), template.getUuid())).isNull(); | |||
assertTemplateDoesNotExist(template); | |||
}); | |||
} | |||
@Test | |||
public void delete_template_by_name_returns_empty_when_no_organization_is_provided_and_templates_does_not_belong_to_default_organization() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
db.organizations().setDefaultTemplates(organization, "project def template uuid", "view def template uuid"); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
loginAsAdmin(organization); | |||
runOnAllUnderTests((underTest) -> { | |||
try { | |||
newRequestByName(underTest, null, template); | |||
fail("NotFoundException should have been raised"); | |||
} catch (NotFoundException e) { | |||
assertThat(e).hasMessage("Permission template with name '" + template.getName() + "' is not found (case insensitive)"); | |||
} | |||
}); | |||
} | |||
@Test | |||
public void delete_template_by_name_returns_empty_when_wrong_organization_is_provided() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
db.organizations().setDefaultTemplates(organization, "project def template uuid", "view def template uuid"); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
OrganizationDto otherOrganization = db.organizations().insert(); | |||
loginAsAdmin(organization); | |||
runOnAllUnderTests((underTest) -> { | |||
try { | |||
newRequestByName(underTest, otherOrganization, template); | |||
fail("NotFoundException should have been raised"); | |||
} catch (NotFoundException e) { | |||
assertThat(e).hasMessage("Permission template with name '" + template.getName() + "' is not found (case insensitive)"); | |||
} | |||
}); | |||
} | |||
@Test | |||
public void fail_if_uuid_is_not_known_without_views() throws Exception { | |||
userSession.login(); | |||
expectedException.expect(NotFoundException.class); | |||
newRequestByUuid(underTestWithoutViews, "unknown-template-uuid"); | |||
} | |||
@Test | |||
public void fail_if_uuid_is_not_known() throws Exception { | |||
public void fail_if_uuid_is_not_known_with_views() throws Exception { | |||
userSession.login(); | |||
expectedException.expect(NotFoundException.class); | |||
newRequest("unknown-template-uuid"); | |||
newRequestByUuid(underTestWithViews, "unknown-template-uuid"); | |||
} | |||
@Test | |||
public void fail_if_template_is_default() throws Exception { | |||
when(defaultTemplatePermissionFinder.getDefaultTemplateUuids()).thenReturn(newSet(template.getUuid())); | |||
public void fail_to_delete_by_uuid_if_template_is_default_template_for_project_without_views() throws Exception { | |||
fail_to_delete_by_uuid_if_template_is_default_template_for_project(this.underTestWithoutViews); | |||
} | |||
@Test | |||
public void fail_to_delete_by_uuid_if_template_is_default_template_for_project_with_views() throws Exception { | |||
fail_to_delete_by_uuid_if_template_is_default_template_for_project(this.underTestWithViews); | |||
} | |||
private void fail_to_delete_by_uuid_if_template_is_default_template_for_project(WsActionTester underTest) throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
db.organizations().setDefaultTemplates(organization, template.getUuid(), "view def template uuid"); | |||
loginAsAdmin(organization); | |||
expectedException.expect(BadRequestException.class); | |||
expectedException.expectMessage("It is not possible to delete a default template"); | |||
expectedException.expectMessage("It is not possible to delete the default permission template for projects"); | |||
newRequestByUuid(underTest, template.getUuid()); | |||
} | |||
@Test | |||
public void fail_to_delete_by_name_if_template_is_default_template_for_project_without_views() throws Exception { | |||
fail_to_delete_by_name_if_template_is_default_template_for_project(this.underTestWithoutViews); | |||
} | |||
@Test | |||
public void fail_to_delete_by_name_if_template_is_default_template_for_project_with_views() throws Exception { | |||
fail_to_delete_by_name_if_template_is_default_template_for_project(this.underTestWithViews); | |||
} | |||
private void fail_to_delete_by_name_if_template_is_default_template_for_project(WsActionTester underTest) throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
db.organizations().setDefaultTemplates(organization, template.getUuid(), "view def template uuid"); | |||
loginAsAdmin(organization); | |||
expectedException.expect(BadRequestException.class); | |||
expectedException.expectMessage("It is not possible to delete the default permission template for projects"); | |||
newRequestByName(underTest, organization.getKey(), template.getName()); | |||
} | |||
@Test | |||
public void fail_to_delete_by_uuid_if_template_is_default_template_for_view_with_views() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
db.organizations().setDefaultTemplates(organization, "project def template uuid", template.getUuid()); | |||
loginAsAdmin(organization); | |||
expectedException.expect(BadRequestException.class); | |||
expectedException.expectMessage("It is not possible to delete the default permission template for views"); | |||
newRequestByUuid(this.underTestWithViews, template.getUuid()); | |||
} | |||
@Test | |||
public void default_template_for_views_can_be_deleted_by_uuid_if_views_is_not_installed_and_default_template_for_views_is_reset() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
db.organizations().setDefaultTemplates(organization, "project def template uuid", template.getUuid()); | |||
loginAsAdmin(organization); | |||
newRequestByUuid(this.underTestWithoutViews, template.getUuid()); | |||
assertTemplateDoesNotExist(template); | |||
assertThat(db.getDbClient().organizationDao().getDefaultTemplates(db.getSession(), organization.getUuid()) | |||
.get().getViewUuid()) | |||
.isNull(); | |||
} | |||
@Test | |||
public void fail_to_delete_by_uuid_if_not_logged_in_without_views() throws Exception { | |||
expectedException.expect(UnauthorizedException.class); | |||
newRequestByUuid(underTestWithoutViews, "uuid"); | |||
} | |||
@Test | |||
public void fail_to_delete_by_uuid_if_not_logged_in_with_views() throws Exception { | |||
expectedException.expect(UnauthorizedException.class); | |||
newRequest(template.getUuid()); | |||
newRequestByUuid(underTestWithViews, "uuid"); | |||
} | |||
@Test | |||
public void fail_if_not_logged_in() throws Exception { | |||
public void fail_to_delete_by_name_if_not_logged_in_without_views() throws Exception { | |||
expectedException.expect(UnauthorizedException.class); | |||
userSession.anonymous(); | |||
newRequest(template.getUuid()); | |||
newRequestByName(underTestWithoutViews, "whatever", "name"); | |||
} | |||
@Test | |||
public void fail_if_not_admin() throws Exception { | |||
public void fail_to_delete_by_name_if_not_logged_in_with_views() throws Exception { | |||
expectedException.expect(UnauthorizedException.class); | |||
newRequestByName(underTestWithViews, "whatever", "name"); | |||
} | |||
@Test | |||
public void fail_to_delete_by_uuid_if_not_admin_without_views() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
userSession.login(); | |||
expectedException.expect(ForbiddenException.class); | |||
newRequestByUuid(underTestWithoutViews, template.getUuid()); | |||
} | |||
@Test | |||
public void fail_to_delete_by_uuid_if_not_admin_with_views() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplateAndAssociatedPermissions(organization); | |||
userSession.login(); | |||
expectedException.expect(ForbiddenException.class); | |||
newRequestByUuid(underTestWithViews, template.getUuid()); | |||
} | |||
@Test | |||
public void fail_to_delete_by_name_if_not_admin_without_views() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = db.permissionTemplates().insertTemplate(organization); | |||
userSession.login(); | |||
expectedException.expect(ForbiddenException.class); | |||
userSession.login().setGlobalPermissions(GlobalPermissions.QUALITY_PROFILE_ADMIN); | |||
newRequest(template.getUuid()); | |||
newRequestByName(underTestWithoutViews, organization.getKey(), template.getName()); | |||
} | |||
@Test | |||
public void fail_if_uuid_is_not_provided() throws Exception { | |||
public void fail_to_delete_by_name_if_not_admin_with_views() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = db.permissionTemplates().insertTemplate(PermissionTemplateTesting.newPermissionTemplateDto() | |||
.setOrganizationUuid(organization.getUuid()) | |||
.setName("the name")); | |||
userSession.login(); | |||
expectedException.expect(ForbiddenException.class); | |||
newRequestByName(underTestWithViews, organization, template); | |||
} | |||
@Test | |||
public void fail_if_neither_uuid_nor_name_is_provided_without_views() throws Exception { | |||
userSession.login(); | |||
expectedException.expect(BadRequestException.class); | |||
newRequest(null); | |||
newRequestByUuid(underTestWithoutViews, null); | |||
} | |||
@Test | |||
public void delete_perm_tpl_characteristic_when_delete_template() throws Exception { | |||
db.getDbClient().permissionTemplateCharacteristicDao().insert(db.getSession(), new PermissionTemplateCharacteristicDto() | |||
.setPermission(UserRole.USER) | |||
.setTemplateId(template.getId()) | |||
.setWithProjectCreator(true) | |||
.setCreatedAt(new Date().getTime()) | |||
.setUpdatedAt(new Date().getTime())); | |||
db.commit(); | |||
public void fail_if_neither_uuid_nor_name_is_provided_with_views() throws Exception { | |||
userSession.login(); | |||
newRequest(template.getUuid()); | |||
expectedException.expect(BadRequestException.class); | |||
assertThat(db.getDbClient().permissionTemplateCharacteristicDao().selectByTemplateIds(db.getSession(), asList(template.getId()))).isEmpty(); | |||
newRequestByUuid(underTestWithViews, null); | |||
} | |||
private PermissionTemplateDto insertTemplateAndAssociatedPermissions() { | |||
PermissionTemplateDto dto = addTemplateToDefaultOrganization(); | |||
@Test | |||
public void fail_if_both_uuid_and_name_are_provided_without_views() throws Exception { | |||
userSession.login(); | |||
expectedException.expect(BadRequestException.class); | |||
underTestWithoutViews.newRequest().setMethod("POST") | |||
.setParam(PARAM_TEMPLATE_ID, "uuid") | |||
.setParam(PARAM_TEMPLATE_NAME, "name") | |||
.execute(); | |||
} | |||
@Test | |||
public void fail_if_both_uuid_and_name_are_provided_with_views() throws Exception { | |||
userSession.login(); | |||
expectedException.expect(BadRequestException.class); | |||
underTestWithViews.newRequest().setMethod("POST") | |||
.setParam(PARAM_TEMPLATE_ID, "uuid") | |||
.setParam(PARAM_TEMPLATE_NAME, "name") | |||
.execute(); | |||
} | |||
// @Test | |||
// public void delete_perm_tpl_characteristic_when_delete_template() throws Exception { | |||
// db.getDbClient().permissionTemplateCharacteristicDao().insert(db.getSession(), new PermissionTemplateCharacteristicDto() | |||
// .setPermission(UserRole.USER) | |||
// .setTemplateId(template.getId()) | |||
// .setWithProjectCreator(true) | |||
// .setCreatedAt(new Date().getTime()) | |||
// .setUpdatedAt(new Date().getTime())); | |||
// db.commit(); | |||
// | |||
// newRequest(template.getUuid()); | |||
// | |||
// assertThat(db.getDbClient().permissionTemplateCharacteristicDao().selectByTemplateIds(db.getSession(), | |||
// asList(template.getId()))).isEmpty(); | |||
// } | |||
private UserSessionRule loginAsAdmin(OrganizationDto organization) { | |||
return userSession.login().addOrganizationPermission(organization.getUuid(), SYSTEM_ADMIN); | |||
} | |||
private void runOnAllUnderTests(ConsumerWithException<WsActionTester> consumer) throws Exception { | |||
for (WsActionTester underTest : Arrays.asList(underTestWithoutViews, underTestWithViews)) { | |||
consumer.accept(underTest); | |||
} | |||
} | |||
private interface ConsumerWithException<T> { | |||
void accept(T e) throws Exception; | |||
} | |||
private PermissionTemplateDto insertTemplateAndAssociatedPermissions(OrganizationDto organization) { | |||
PermissionTemplateDto dto = db.permissionTemplates().insertTemplate(organization); | |||
UserDto user = db.getDbClient().userDao().insert(db.getSession(), UserTesting.newUserDto().setActive(true)); | |||
GroupDto group = db.getDbClient().groupDao().insert(db.getSession(), GroupTesting.newGroupDto()); | |||
db.getDbClient().permissionTemplateDao().insertUserPermission(db.getSession(), dto.getId(), user.getId(), UserRole.ADMIN); | |||
@@ -147,13 +396,36 @@ public class DeleteTemplateActionTest extends BasePermissionWsTest<DeleteTemplat | |||
return dto; | |||
} | |||
private TestResponse newRequest(@Nullable String id) throws Exception { | |||
TestRequest request = newRequest(); | |||
private TestResponse newRequestByUuid(WsActionTester actionTester, @Nullable String id) throws Exception { | |||
TestRequest request = actionTester.newRequest().setMethod("POST"); | |||
if (id != null) { | |||
request.setParam(PARAM_TEMPLATE_ID, id); | |||
} | |||
return request.execute(); | |||
} | |||
private TestResponse newRequestByName(WsActionTester actionTester, @Nullable OrganizationDto organizationDto, @Nullable PermissionTemplateDto permissionTemplateDto) | |||
throws Exception { | |||
return newRequestByName( | |||
actionTester, | |||
organizationDto == null ? null : organizationDto.getKey(), | |||
permissionTemplateDto == null ? null : permissionTemplateDto.getName()); | |||
} | |||
private TestResponse newRequestByName(WsActionTester actionTester, @Nullable String organizationKey, @Nullable String name) throws Exception { | |||
TestRequest request = actionTester.newRequest().setMethod("POST"); | |||
if (organizationKey != null) { | |||
request.setParam(PARAM_ORGANIZATION_KEY, organizationKey); | |||
} | |||
if (name != null) { | |||
request.setParam(PARAM_TEMPLATE_NAME, name); | |||
} | |||
return request.execute(); | |||
} | |||
private void assertTemplateDoesNotExist(PermissionTemplateDto template) { | |||
assertThat(db.getDbClient().permissionTemplateDao().selectByUuid(db.getSession(), template.getUuid())).isNull(); | |||
} | |||
} |
@@ -23,8 +23,6 @@ import java.util.Date; | |||
import javax.annotation.Nullable; | |||
import org.junit.Before; | |||
import org.junit.Test; | |||
import org.sonar.api.config.MapSettings; | |||
import org.sonar.api.config.Settings; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.web.UserRole; | |||
import org.sonar.db.DbClient; | |||
@@ -38,6 +36,8 @@ import org.sonar.db.user.UserDto; | |||
import org.sonar.server.exceptions.UnauthorizedException; | |||
import org.sonar.server.i18n.I18nRule; | |||
import org.sonar.server.permission.ws.BasePermissionWsTest; | |||
import org.sonar.server.ws.TestRequest; | |||
import org.sonar.server.ws.WsActionTester; | |||
import org.sonarqube.ws.MediaTypes; | |||
import org.sonarqube.ws.WsPermissions; | |||
@@ -46,11 +46,7 @@ import static org.sonar.api.server.ws.WebService.Param.TEXT_QUERY; | |||
import static org.sonar.core.permission.GlobalPermissions.SYSTEM_ADMIN; | |||
import static org.sonar.core.util.Uuids.UUID_EXAMPLE_01; | |||
import static org.sonar.core.util.Uuids.UUID_EXAMPLE_02; | |||
import static org.sonar.core.util.Uuids.UUID_EXAMPLE_03; | |||
import static org.sonar.db.permission.template.PermissionTemplateTesting.newPermissionTemplateDto; | |||
import static org.sonar.db.user.GroupTesting.newGroupDto; | |||
import static org.sonar.db.user.UserTesting.newUserDto; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.defaultRootQualifierTemplateProperty; | |||
import static org.sonar.test.JsonAssert.assertJson; | |||
public class SearchTemplatesActionTest extends BasePermissionWsTest<SearchTemplatesAction> { | |||
@@ -58,39 +54,41 @@ public class SearchTemplatesActionTest extends BasePermissionWsTest<SearchTempla | |||
private I18nRule i18n = new I18nRule(); | |||
private DbClient dbClient = db.getDbClient(); | |||
private DbSession dbSession = db.getSession(); | |||
private ResourceTypesRule resourceTypes = new ResourceTypesRule().setRootQualifiers(Qualifiers.PROJECT, Qualifiers.VIEW, "DEV"); | |||
private ResourceTypesRule resourceTypesWithViews = new ResourceTypesRule().setRootQualifiers(Qualifiers.PROJECT, Qualifiers.VIEW); | |||
private ResourceTypesRule resourceTypesWithoutViews = new ResourceTypesRule().setRootQualifiers(Qualifiers.PROJECT); | |||
private WsActionTester underTestWithoutViews; | |||
@Override | |||
protected SearchTemplatesAction buildWsAction() { | |||
Settings settings = new MapSettings(); | |||
settings.setProperty(defaultRootQualifierTemplateProperty(Qualifiers.PROJECT), UUID_EXAMPLE_01); | |||
settings.setProperty(defaultRootQualifierTemplateProperty(Qualifiers.VIEW), UUID_EXAMPLE_02); | |||
settings.setProperty(defaultRootQualifierTemplateProperty("DEV"), UUID_EXAMPLE_03); | |||
DefaultPermissionTemplateFinder defaultPermissionTemplateFinder = new DefaultPermissionTemplateFinder(settings, resourceTypes); | |||
SearchTemplatesDataLoader dataLoader = new SearchTemplatesDataLoader(dbClient, defaultPermissionTemplateFinder); | |||
return new SearchTemplatesAction(dbClient, userSession, i18n, newPermissionWsSupport(), dataLoader); | |||
DefaultTemplatesResolver defaultTemplatesResolverWithViews = new DefaultTemplatesResolverImpl(resourceTypesWithViews); | |||
SearchTemplatesDataLoader dataLoaderWithViews = new SearchTemplatesDataLoader(dbClient, defaultTemplatesResolverWithViews); | |||
SearchTemplatesAction searchTemplatesAction = new SearchTemplatesAction(dbClient, userSession, i18n, newPermissionWsSupport(), dataLoaderWithViews); | |||
return searchTemplatesAction; | |||
} | |||
@Before | |||
public void setUp() { | |||
DefaultTemplatesResolver defaultTemplatesResolverWithViews = new DefaultTemplatesResolverImpl(resourceTypesWithoutViews); | |||
SearchTemplatesDataLoader dataLoaderWithViews = new SearchTemplatesDataLoader(dbClient, defaultTemplatesResolverWithViews); | |||
underTestWithoutViews = new WsActionTester(new SearchTemplatesAction(dbClient, userSession, i18n, newPermissionWsSupport(), dataLoaderWithViews)); | |||
i18n.setProjectPermissions(); | |||
userSession.login().addOrganizationPermission(db.getDefaultOrganization().getUuid(), SYSTEM_ADMIN); | |||
} | |||
@Test | |||
public void search_project_permissions() { | |||
PermissionTemplateDto projectTemplate = insertProjectTemplateOnDefaultOrganization(); | |||
PermissionTemplateDto viewsTemplate = insertViewsTemplate(); | |||
PermissionTemplateDto developerTemplate = insertDeveloperTemplate(); | |||
OrganizationDto organization = db.getDefaultOrganization(); | |||
PermissionTemplateDto projectTemplate = insertProjectTemplate(organization); | |||
PermissionTemplateDto viewsTemplate = insertViewsTemplate(organization); | |||
UserDto user1 = insertUser(newUserDto()); | |||
UserDto user2 = insertUser(newUserDto()); | |||
UserDto user3 = insertUser(newUserDto()); | |||
UserDto user1 = db.users().insertUser(); | |||
UserDto user2 = db.users().insertUser(); | |||
UserDto user3 = db.users().insertUser(); | |||
GroupDto group1 = insertGroup(newGroupDto()); | |||
GroupDto group2 = insertGroup(newGroupDto()); | |||
GroupDto group3 = insertGroup(newGroupDto()); | |||
GroupDto group1 = db.users().insertGroup(organization); | |||
GroupDto group2 = db.users().insertGroup(organization); | |||
GroupDto group3 = db.users().insertGroup(organization); | |||
addUserToTemplate(projectTemplate.getId(), user1.getId(), UserRole.ISSUE_ADMIN); | |||
addUserToTemplate(projectTemplate.getId(), user2.getId(), UserRole.ISSUE_ADMIN); | |||
@@ -105,9 +103,7 @@ public class SearchTemplatesActionTest extends BasePermissionWsTest<SearchTempla | |||
addGroupToTemplate(viewsTemplate.getId(), group2.getId(), UserRole.ISSUE_ADMIN); | |||
addGroupToTemplate(viewsTemplate.getId(), group3.getId(), UserRole.ISSUE_ADMIN); | |||
addGroupToTemplate(developerTemplate.getId(), group1.getId(), UserRole.USER); | |||
db.commit(); | |||
db.organizations().setDefaultTemplates(organization, projectTemplate.getUuid(), viewsTemplate.getUuid()); | |||
String result = newRequest().execute().getInput(); | |||
@@ -117,23 +113,54 @@ public class SearchTemplatesActionTest extends BasePermissionWsTest<SearchTempla | |||
} | |||
@Test | |||
public void empty_result() { | |||
String result = newRequest().execute().getInput(); | |||
public void empty_result_with_views() { | |||
db.organizations().setDefaultTemplates(db.getDefaultOrganization(), "AU-Tpxb--iU5OvuD2FLy", "AU-TpxcA-iU5OvuD2FLz"); | |||
String result = newRequest(wsTester).execute().getInput(); | |||
assertJson(result) | |||
.withStrictArrayOrder() | |||
.ignoreFields("permissions") | |||
.isSimilarTo(getClass().getResource("SearchTemplatesActionTest/empty.json")); | |||
.isSimilarTo("{" + | |||
" \"permissionTemplates\": []," + | |||
" \"defaultTemplates\": [" + | |||
" {" + | |||
" \"templateId\": \"AU-Tpxb--iU5OvuD2FLy\"," + | |||
" \"qualifier\": \"TRK\"" + | |||
" }," + | |||
" {" + | |||
" \"templateId\": \"AU-TpxcA-iU5OvuD2FLz\"," + | |||
" \"qualifier\": \"VW\"" + | |||
" }" + | |||
" ]" + | |||
"}"); | |||
} | |||
@Test | |||
public void empty_result_without_views() { | |||
db.organizations().setDefaultTemplates(db.getDefaultOrganization(), "AU-Tpxb--iU5OvuD2FLy", "AU-TpxcA-iU5OvuD2FLz"); | |||
String result = newRequest(underTestWithoutViews).execute().getInput(); | |||
assertJson(result) | |||
.withStrictArrayOrder() | |||
.ignoreFields("permissions") | |||
.isSimilarTo("{" + | |||
" \"permissionTemplates\": []," + | |||
" \"defaultTemplates\": [" + | |||
" {" + | |||
" \"templateId\": \"AU-Tpxb--iU5OvuD2FLy\"," + | |||
" \"qualifier\": \"TRK\"" + | |||
" }" + | |||
" ]" + | |||
"}"); | |||
} | |||
@Test | |||
public void search_by_name_in_default_organization() { | |||
insertProjectTemplateOnDefaultOrganization(); | |||
insertViewsTemplate(); | |||
insertDeveloperTemplate(); | |||
db.commit(); | |||
db.organizations().setDefaultTemplates(db.getDefaultOrganization(), "foo", null); | |||
insertProjectTemplate(db.getDefaultOrganization()); | |||
insertViewsTemplate(db.getDefaultOrganization()); | |||
String result = newRequest() | |||
String result = newRequest(wsTester) | |||
.setParam(TEXT_QUERY, "views") | |||
.execute() | |||
.getInput(); | |||
@@ -146,16 +173,18 @@ public class SearchTemplatesActionTest extends BasePermissionWsTest<SearchTempla | |||
@Test | |||
public void search_in_organization() throws Exception { | |||
OrganizationDto org = db.organizations().insert(); | |||
db.organizations().setDefaultTemplates(org, "foo", null); | |||
PermissionTemplateDto templateInOrg = insertProjectTemplate(org); | |||
insertProjectTemplateOnDefaultOrganization(); | |||
insertProjectTemplate(db.getDefaultOrganization()); | |||
db.commit(); | |||
userSession.addOrganizationPermission(org.getUuid(), SYSTEM_ADMIN); | |||
WsPermissions.SearchTemplatesWsResponse result = WsPermissions.SearchTemplatesWsResponse.parseFrom(newRequest() | |||
.setParam("organization", org.getKey()) | |||
.setMediaType(MediaTypes.PROTOBUF) | |||
.execute() | |||
.getInputStream()); | |||
WsPermissions.SearchTemplatesWsResponse result = WsPermissions.SearchTemplatesWsResponse.parseFrom( | |||
newRequest(underTestWithoutViews) | |||
.setParam("organization", org.getKey()) | |||
.setMediaType(MediaTypes.PROTOBUF) | |||
.execute() | |||
.getInputStream()); | |||
assertThat(result.getPermissionTemplatesCount()).isEqualTo(1); | |||
assertThat(result.getPermissionTemplates(0).getId()).isEqualTo(templateInOrg.getUuid()); | |||
@@ -171,16 +200,45 @@ public class SearchTemplatesActionTest extends BasePermissionWsTest<SearchTempla | |||
@Test | |||
public void display_all_project_permissions() { | |||
db.organizations().setDefaultTemplates(db.getDefaultOrganization(), "foo", "bar"); | |||
String result = newRequest().execute().getInput(); | |||
assertJson(result) | |||
.withStrictArrayOrder() | |||
.ignoreFields("defaultTemplates", "permissionTemplates") | |||
.isSimilarTo(getClass().getResource("SearchTemplatesActionTest/display_all_project_permissions.json")); | |||
} | |||
private PermissionTemplateDto insertProjectTemplateOnDefaultOrganization() { | |||
return insertProjectTemplate(db.getDefaultOrganization()); | |||
.isSimilarTo( | |||
"{" + | |||
" \"permissions\": [" + | |||
" {" + | |||
" \"key\": \"admin\"," + | |||
" \"name\": \"Administer\"," + | |||
" \"description\": \"Ability to access project settings and perform administration tasks. (Users will also need \\\"Browse\\\" permission)\"" + | |||
" }," + | |||
" {" + | |||
" \"key\": \"codeviewer\"," + | |||
" \"name\": \"See Source Code\"," + | |||
" \"description\": \"Ability to view the project\\u0027s source code. (Users will also need \\\"Browse\\\" permission)\"" + | |||
" }," + | |||
" {" + | |||
" \"key\": \"issueadmin\"," + | |||
" \"name\": \"Administer Issues\"," + | |||
" \"description\": \"Grants the permission to perform advanced editing on issues: marking an issue False Positive / Won\\u0027t Fix or changing an Issue\\u0027s severity. (Users will also need \\\"Browse\\\" permission)\"" | |||
+ | |||
" }," + | |||
" {" + | |||
" \"key\": \"scan\"," + | |||
" \"name\": \"Execute Analysis\"," + | |||
" \"description\": \"Ability to execute analyses, and to get all settings required to perform the analysis, even the secured ones like the scm account password, the jira account password, and so on.\"" | |||
+ | |||
" }," + | |||
" {" + | |||
" \"key\": \"user\"," + | |||
" \"name\": \"Browse\"," + | |||
" \"description\": \"Ability to access a project, browse its measures, and create/edit issues for it.\"" + | |||
" }" + | |||
" ]" + | |||
"}"); | |||
} | |||
private PermissionTemplateDto insertProjectTemplate(OrganizationDto org) { | |||
@@ -194,9 +252,9 @@ public class SearchTemplatesActionTest extends BasePermissionWsTest<SearchTempla | |||
.setUpdatedAt(new Date(1_000_000_000_000L))); | |||
} | |||
private PermissionTemplateDto insertViewsTemplate() { | |||
private PermissionTemplateDto insertViewsTemplate(OrganizationDto organization) { | |||
return insertTemplate(newPermissionTemplateDto() | |||
.setOrganizationUuid(db.getDefaultOrganization().getUuid()) | |||
.setOrganizationUuid(organization.getUuid()) | |||
.setUuid(UUID_EXAMPLE_02) | |||
.setName("Default template for Views") | |||
.setDescription("Template for new views") | |||
@@ -205,35 +263,20 @@ public class SearchTemplatesActionTest extends BasePermissionWsTest<SearchTempla | |||
.setUpdatedAt(new Date(1_100_000_000_000L))); | |||
} | |||
private PermissionTemplateDto insertDeveloperTemplate() { | |||
return insertTemplate(newPermissionTemplateDto() | |||
.setOrganizationUuid(db.getDefaultOrganization().getUuid()) | |||
.setUuid(UUID_EXAMPLE_03) | |||
.setName("Default template for Developers") | |||
.setKeyPattern(".*sonar.developer.*") | |||
.setDescription(null) | |||
.setCreatedAt(new Date(1_100_500_000_000L)) | |||
.setUpdatedAt(new Date(1_100_900_000_000L))); | |||
} | |||
private PermissionTemplateDto insertTemplate(PermissionTemplateDto template) { | |||
return dbClient.permissionTemplateDao().insert(db.getSession(), template); | |||
} | |||
private GroupDto insertGroup(GroupDto groupDto) { | |||
return dbClient.groupDao().insert(db.getSession(), groupDto); | |||
} | |||
private UserDto insertUser(UserDto userDto) { | |||
return dbClient.userDao().insert(db.getSession(), userDto.setActive(true)); | |||
PermissionTemplateDto insert = dbClient.permissionTemplateDao().insert(db.getSession(), template); | |||
db.getSession().commit(); | |||
return insert; | |||
} | |||
private void addGroupToTemplate(long templateId, @Nullable Long groupId, String permission) { | |||
dbClient.permissionTemplateDao().insertGroupPermission(db.getSession(), templateId, groupId, permission); | |||
db.getSession().commit(); | |||
} | |||
private void addUserToTemplate(long templateId, long userId, String permission) { | |||
dbClient.permissionTemplateDao().insertUserPermission(db.getSession(), templateId, userId, permission); | |||
db.getSession().commit(); | |||
} | |||
private void addPermissionTemplateWithProjectCreator(long templateId, String permission) { | |||
@@ -245,4 +288,8 @@ public class SearchTemplatesActionTest extends BasePermissionWsTest<SearchTempla | |||
.setUpdatedAt(2_000_000_000L)); | |||
db.commit(); | |||
} | |||
private TestRequest newRequest(WsActionTester underTest) { | |||
return underTest.newRequest().setMethod("POST"); | |||
} | |||
} |
@@ -23,7 +23,6 @@ import com.google.common.collect.HashBasedTable; | |||
import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.junit.rules.ExpectedException; | |||
import org.sonar.api.resources.Qualifiers; | |||
import static java.util.Collections.singletonList; | |||
import static org.sonar.db.permission.template.PermissionTemplateTesting.newPermissionTemplateDto; | |||
@@ -33,7 +32,7 @@ public class SearchTemplatesDataTest { | |||
public ExpectedException expectedException = ExpectedException.none(); | |||
SearchTemplatesData.Builder underTest = SearchTemplatesData.builder() | |||
.defaultTemplates(singletonList(new DefaultPermissionTemplateFinder.TemplateUuidQualifier("template_uuid", Qualifiers.PROJECT))) | |||
.defaultTemplates(new DefaultTemplatesResolverImpl.ResolvedDefaultTemplates("template_uuid", null)) | |||
.templates(singletonList(newPermissionTemplateDto())) | |||
.userCountByTemplateIdAndPermission(HashBasedTable.create()) | |||
.groupCountByTemplateIdAndPermission(HashBasedTable.create()) |
@@ -20,12 +20,13 @@ | |||
package org.sonar.server.permission.ws.template; | |||
import javax.annotation.Nullable; | |||
import org.junit.Before; | |||
import org.junit.Test; | |||
import org.sonar.api.config.MapSettings; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.core.permission.GlobalPermissions; | |||
import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import org.sonar.db.organization.OrganizationDto; | |||
import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.db.permission.template.PermissionTemplateTesting; | |||
import org.sonar.server.exceptions.BadRequestException; | |||
@@ -34,94 +35,98 @@ import org.sonar.server.exceptions.NotFoundException; | |||
import org.sonar.server.exceptions.UnauthorizedException; | |||
import org.sonar.server.i18n.I18nRule; | |||
import org.sonar.server.permission.ws.BasePermissionWsTest; | |||
import org.sonar.server.platform.PersistentSettings; | |||
import org.sonar.server.platform.SettingsChangeNotifier; | |||
import org.sonar.server.ws.TestRequest; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
import static org.sonar.api.resources.Qualifiers.PROJECT; | |||
import static org.sonar.api.resources.Qualifiers.VIEW; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.DEFAULT_TEMPLATE_PROPERTY; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.defaultRootQualifierTemplateProperty; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_ORGANIZATION_KEY; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_QUALIFIER; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_TEMPLATE_ID; | |||
import static org.sonarqube.ws.client.permission.PermissionsWsParameters.PARAM_TEMPLATE_NAME; | |||
public class SetDefaultTemplateActionTest extends BasePermissionWsTest<SetDefaultTemplateAction> { | |||
private DbClient dbClient = db.getDbClient(); | |||
private I18nRule i18n = new I18nRule(); | |||
private PersistentSettings persistentSettings = new PersistentSettings(new MapSettings(), db.getDbClient(), new SettingsChangeNotifier()); | |||
private PermissionTemplateDto template; | |||
@Override | |||
protected SetDefaultTemplateAction buildWsAction() { | |||
return new SetDefaultTemplateAction(db.getDbClient(), newPermissionWsSupport(), newRootResourceTypes(), persistentSettings, userSession, i18n); | |||
return new SetDefaultTemplateAction(db.getDbClient(), newPermissionWsSupport(), newRootResourceTypes(), userSession, i18n); | |||
} | |||
@Before | |||
public void setUp() { | |||
DbClient dbClient = db.getDbClient(); | |||
persistentSettings.saveProperty(DEFAULT_TEMPLATE_PROPERTY, "any-template-uuid"); | |||
persistentSettings.saveProperty(defaultRootQualifierTemplateProperty(PROJECT), "any-template-uuid"); | |||
persistentSettings.saveProperty(defaultRootQualifierTemplateProperty(VIEW), "any-view-template-uuid"); | |||
persistentSettings.saveProperty(defaultRootQualifierTemplateProperty("DEV"), "any-dev-template-uuid"); | |||
loginAsAdminOnDefaultOrganization(); | |||
template = dbClient.permissionTemplateDao().insert(db.getSession(), PermissionTemplateTesting.newPermissionTemplateDto() | |||
.setOrganizationUuid(db.getDefaultOrganization().getUuid()) | |||
.setUuid("permission-template-uuid")); | |||
db.commit(); | |||
@Test | |||
public void update_project_default_template() throws Exception { | |||
db.organizations().setDefaultTemplates(db.getDefaultOrganization(), "project-template-uuid", "view-template-uuid"); | |||
PermissionTemplateDto template = insertTemplate(db.getDefaultOrganization()); | |||
loginAsAdmin(db.getDefaultOrganization()); | |||
newRequest(template.getUuid(), Qualifiers.PROJECT); | |||
assertDefaultTemplates(db.getDefaultOrganization(), template.getUuid(), "view-template-uuid"); | |||
} | |||
@Test | |||
public void update_settings_for_project_qualifier() throws Exception { | |||
public void update_project_default_template_without_qualifier_param() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
db.organizations().setDefaultTemplates(organization, "any-project-template-uuid", "any-view-template-uuid"); | |||
PermissionTemplateDto template = insertTemplate(organization); | |||
loginAsAdmin(organization); | |||
// default value is project qualifier's value | |||
String result = newRequest(template.getUuid(), null); | |||
newRequest(template.getUuid(), null); | |||
assertThat(result).isEmpty(); | |||
assertThat(persistentSettings.getString(DEFAULT_TEMPLATE_PROPERTY)).isEqualTo("any-template-uuid"); | |||
assertThat(persistentSettings.getString(defaultRootQualifierTemplateProperty(PROJECT))).isEqualTo(template.getUuid()); | |||
assertThat(persistentSettings.getString(defaultRootQualifierTemplateProperty(VIEW))).isEqualTo("any-view-template-uuid"); | |||
assertThat(persistentSettings.getString(defaultRootQualifierTemplateProperty("DEV"))).isEqualTo("any-dev-template-uuid"); | |||
assertDefaultTemplates(organization, template.getUuid(), "any-view-template-uuid"); | |||
} | |||
@Test | |||
public void update_settings_for_project_qualifier_by_template_name() throws Exception { | |||
public void update_project_default_template_by_template_name() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
db.organizations().setDefaultTemplates(organization, "bar", "roh"); | |||
PermissionTemplateDto template = insertTemplate(organization); | |||
loginAsAdmin(organization); | |||
newRequest() | |||
.setParam(PARAM_ORGANIZATION_KEY, organization.getKey()) | |||
.setParam(PARAM_TEMPLATE_NAME, template.getName().toUpperCase()) | |||
.execute(); | |||
db.getSession().commit(); | |||
assertThat(persistentSettings.getString(DEFAULT_TEMPLATE_PROPERTY)).isEqualTo("any-template-uuid"); | |||
assertThat(persistentSettings.getString(defaultRootQualifierTemplateProperty(PROJECT))).isEqualTo(template.getUuid()); | |||
assertThat(persistentSettings.getString(defaultRootQualifierTemplateProperty(VIEW))).isEqualTo("any-view-template-uuid"); | |||
assertThat(persistentSettings.getString(defaultRootQualifierTemplateProperty("DEV"))).isEqualTo("any-dev-template-uuid"); | |||
assertDefaultTemplates(organization, template.getUuid(), "roh"); | |||
} | |||
@Test | |||
public void update_settings_of_views_property() throws Exception { | |||
public void update_view_default_template() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
db.organizations().setDefaultTemplates(organization, "foo", null); | |||
PermissionTemplateDto template = insertTemplate(organization); | |||
loginAsAdmin(organization); | |||
newRequest(template.getUuid(), VIEW); | |||
assertThat(persistentSettings.getString(DEFAULT_TEMPLATE_PROPERTY)).isEqualTo("any-template-uuid"); | |||
assertThat(persistentSettings.getString(defaultRootQualifierTemplateProperty(PROJECT))).isEqualTo("any-template-uuid"); | |||
assertThat(persistentSettings.getString(defaultRootQualifierTemplateProperty(VIEW))).isEqualTo(template.getUuid()); | |||
assertThat(persistentSettings.getString(defaultRootQualifierTemplateProperty("DEV"))).isEqualTo("any-dev-template-uuid"); | |||
assertDefaultTemplates(organization, "foo", template.getUuid()); | |||
} | |||
@Test | |||
public void fail_if_anonymous() throws Exception { | |||
expectedException.expect(UnauthorizedException.class); | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplate(organization); | |||
userSession.anonymous(); | |||
expectedException.expect(UnauthorizedException.class); | |||
newRequest(template.getUuid(), PROJECT); | |||
} | |||
@Test | |||
public void fail_if_not_admin() throws Exception { | |||
expectedException.expect(ForbiddenException.class); | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplate(organization); | |||
userSession.login().setGlobalPermissions(GlobalPermissions.QUALITY_PROFILE_ADMIN); | |||
newRequest(template.getUuid(), PROJECT); | |||
expectedException.expect(ForbiddenException.class); | |||
newRequest(template.getUuid(), null); | |||
} | |||
@Test | |||
@@ -140,12 +145,28 @@ public class SetDefaultTemplateActionTest extends BasePermissionWsTest<SetDefaul | |||
@Test | |||
public void fail_if_qualifier_is_not_root() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplate(organization); | |||
loginAsAdmin(organization); | |||
expectedException.expect(IllegalArgumentException.class); | |||
expectedException.expectMessage("Value of parameter 'qualifier' (FIL) must be one of: [DEV, TRK, VW]"); | |||
expectedException.expectMessage("Value of parameter 'qualifier' (FIL) must be one of: [TRK, VW]"); | |||
newRequest(template.getUuid(), Qualifiers.FILE); | |||
} | |||
@Test | |||
public void fail_if_organization_has_no_default_templates() throws Exception { | |||
OrganizationDto organization = db.organizations().insert(); | |||
PermissionTemplateDto template = insertTemplate(organization); | |||
loginAsAdmin(organization); | |||
expectedException.expect(NotFoundException.class); | |||
expectedException.expectMessage("No Default templates for organization with uuid '" + organization.getUuid() + "'"); | |||
newRequest(template.getUuid(), null); | |||
} | |||
private String newRequest(@Nullable String templateUuid, @Nullable String qualifier) throws Exception { | |||
TestRequest request = newRequest(); | |||
if (templateUuid != null) { | |||
@@ -157,4 +178,22 @@ public class SetDefaultTemplateActionTest extends BasePermissionWsTest<SetDefaul | |||
return request.execute().getInput(); | |||
} | |||
private PermissionTemplateDto insertTemplate(OrganizationDto organization) { | |||
PermissionTemplateDto res = dbClient.permissionTemplateDao().insert(db.getSession(), PermissionTemplateTesting.newPermissionTemplateDto() | |||
.setOrganizationUuid(organization.getUuid()) | |||
.setUuid("permission-template-uuid")); | |||
db.commit(); | |||
return res; | |||
} | |||
private void assertDefaultTemplates(OrganizationDto organizationDto, | |||
@Nullable String projectDefaultTemplateUuid, @Nullable String viewDefaultTemplateUuid) { | |||
DbSession dbSession = db.getSession(); | |||
DefaultTemplates defaultTemplates = db.getDbClient().organizationDao().getDefaultTemplates(dbSession, organizationDto.getUuid()) | |||
.orElseThrow(() -> new IllegalStateException("No default templates for organization with uuid '" + organizationDto.getUuid() + "'")); | |||
assertThat(defaultTemplates.getProjectUuid()).isEqualTo(projectDefaultTemplateUuid); | |||
assertThat(defaultTemplates.getViewUuid()).isEqualTo(viewDefaultTemplateUuid); | |||
} | |||
} |
@@ -28,7 +28,6 @@ import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.junit.rules.ExpectedException; | |||
import org.sonar.api.config.MapSettings; | |||
import org.sonar.api.config.Settings; | |||
import org.sonar.api.server.ws.WebService; | |||
import org.sonar.api.utils.System2; | |||
import org.sonar.db.DbTester; | |||
@@ -50,6 +49,7 @@ import org.sonar.server.organization.DefaultOrganizationProvider; | |||
import org.sonar.server.organization.TestDefaultOrganizationProvider; | |||
import org.sonar.server.permission.PermissionTemplateService; | |||
import org.sonar.server.permission.index.PermissionIndexer; | |||
import org.sonar.server.permission.ws.template.DefaultTemplatesResolverRule; | |||
import org.sonar.server.tester.UserSessionRule; | |||
import org.sonar.server.ws.TestRequest; | |||
import org.sonar.server.ws.WsActionTester; | |||
@@ -79,30 +79,25 @@ public class CreateActionTest { | |||
@Rule | |||
public ExpectedException expectedException = ExpectedException.none(); | |||
@Rule | |||
public DbTester db = DbTester.create(system2); | |||
@Rule | |||
public EsTester es = new EsTester(new ComponentIndexDefinition(new MapSettings()), new ProjectMeasuresIndexDefinition(new MapSettings())); | |||
@Rule | |||
public UserSessionRule userSession = UserSessionRule.standalone(); | |||
@Rule | |||
public I18nRule i18n = new I18nRule().put("qualifier.TRK", "Project"); | |||
private Settings settings = new MapSettings(); | |||
@Rule | |||
public DefaultTemplatesResolverRule defaultTemplatesResolver = DefaultTemplatesResolverRule.withoutGovernance(); | |||
private DefaultOrganizationProvider defaultOrganizationProvider = TestDefaultOrganizationProvider.from(db); | |||
private PermissionTemplateDto permissionTemplateDto; | |||
private WsActionTester ws = new WsActionTester( | |||
new CreateAction( | |||
db.getDbClient(), userSession, | |||
new ComponentUpdater(db.getDbClient(), i18n, system2, | |||
new PermissionTemplateService(db.getDbClient(), settings, new PermissionIndexer(db.getDbClient(), es.client()), userSession), | |||
new PermissionTemplateService(db.getDbClient(), new PermissionIndexer(db.getDbClient(), es.client()), userSession, defaultTemplatesResolver), | |||
new FavoriteUpdater(db.getDbClient()), | |||
new ProjectMeasuresIndexer(system2, db.getDbClient(), es.client()), | |||
new ComponentIndexer(db.getDbClient(), es.client())), | |||
@@ -111,7 +106,7 @@ public class CreateActionTest { | |||
@Before | |||
public void setUp() throws Exception { | |||
permissionTemplateDto = db.permissionTemplates().insertTemplate(db.getDefaultOrganization()); | |||
setTemplateAsDefault(permissionTemplateDto); | |||
db.organizations().setDefaultTemplates(db.getDefaultOrganization(), permissionTemplateDto.getUuid(), null); | |||
} | |||
@Test | |||
@@ -315,8 +310,4 @@ public class CreateActionTest { | |||
} | |||
} | |||
private void setTemplateAsDefault(PermissionTemplateDto permissionTemplateDto) { | |||
settings.appendProperty("sonar.permission.template.default", permissionTemplateDto.getUuid()); | |||
} | |||
} |
@@ -21,44 +21,34 @@ package org.sonar.server.startup; | |||
import java.util.List; | |||
import java.util.Objects; | |||
import java.util.Optional; | |||
import org.junit.Rule; | |||
import org.junit.Test; | |||
import org.sonar.api.resources.Qualifiers; | |||
import org.sonar.api.security.DefaultGroups; | |||
import org.sonar.api.utils.System2; | |||
import org.sonar.api.utils.log.LogTester; | |||
import org.sonar.api.utils.log.LoggerLevel; | |||
import org.sonar.api.web.UserRole; | |||
import org.sonar.db.DbTester; | |||
import org.sonar.db.loadedtemplate.LoadedTemplateDto; | |||
import org.sonar.db.organization.DefaultTemplates; | |||
import org.sonar.db.permission.template.PermissionTemplateDto; | |||
import org.sonar.db.permission.template.PermissionTemplateGroupDto; | |||
import org.sonar.server.organization.DefaultOrganizationProvider; | |||
import org.sonar.server.organization.TestDefaultOrganizationProvider; | |||
import org.sonar.server.platform.PersistentSettings; | |||
import static org.assertj.core.api.Assertions.assertThat; | |||
import static org.mockito.Matchers.anyString; | |||
import static org.mockito.Matchers.eq; | |||
import static org.mockito.Mockito.mock; | |||
import static org.mockito.Mockito.never; | |||
import static org.mockito.Mockito.verify; | |||
import static org.mockito.Mockito.when; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.DEFAULT_TEMPLATE_KEY; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.DEFAULT_TEMPLATE_PROPERTY; | |||
import static org.sonar.server.permission.DefaultPermissionTemplates.defaultRootQualifierTemplateProperty; | |||
import static org.sonar.db.permission.template.PermissionTemplateTesting.newPermissionTemplateDto; | |||
public class RegisterPermissionTemplatesTest { | |||
private static final String DEFAULT_TEMPLATE_UUID = "default_template"; | |||
@Rule | |||
public DbTester db = DbTester.create(System2.INSTANCE); | |||
@Rule | |||
public LogTester logTester = new LogTester(); | |||
private PersistentSettings settings = mock(PersistentSettings.class); | |||
private DefaultOrganizationProvider defaultOrganizationProvider = TestDefaultOrganizationProvider.from(db); | |||
private RegisterPermissionTemplates underTest = new RegisterPermissionTemplates(db.getDbClient(), settings, defaultOrganizationProvider); | |||
private RegisterPermissionTemplates underTest = new RegisterPermissionTemplates(db.getDbClient(), defaultOrganizationProvider); | |||
@Test | |||
public void insert_default_permission_template_if_fresh_install() { | |||
@@ -76,8 +66,7 @@ public class RegisterPermissionTemplatesTest { | |||
expectGroupPermission(groupPermissions, UserRole.CODEVIEWER, DefaultGroups.ANYONE); | |||
expectGroupPermission(groupPermissions, UserRole.USER, DefaultGroups.ANYONE); | |||
// template is marked as default | |||
verify(settings).saveProperty(DEFAULT_TEMPLATE_PROPERTY, defaultTemplate.getUuid()); | |||
verifyDefaultTemplates(); | |||
assertThat(logTester.logs(LoggerLevel.ERROR)).isEmpty(); | |||
} | |||
@@ -94,39 +83,36 @@ public class RegisterPermissionTemplatesTest { | |||
expectGroupPermission(groupPermissions, UserRole.CODEVIEWER, DefaultGroups.ANYONE); | |||
expectGroupPermission(groupPermissions, UserRole.USER, DefaultGroups.ANYONE); | |||
// marked as default | |||
verify(settings).saveProperty(DEFAULT_TEMPLATE_PROPERTY, defaultTemplate.getUuid()); | |||
verifyDefaultTemplates(); | |||
assertThat(logTester.logs(LoggerLevel.ERROR)).contains("Cannot setup default permission for group: sonar-administrators"); | |||
} | |||
@Test | |||
public void do_not_create_default_template_if_already_exists() { | |||
markTaskAsAlreadyExecuted(); | |||
public void do_not_create_default_template_if_already_exists_but_register_when_it_is_not() { | |||
db.permissionTemplates().insertTemplate(newPermissionTemplateDto() | |||
.setOrganizationUuid(db.getDefaultOrganization().getUuid()) | |||
.setUuid(DEFAULT_TEMPLATE_UUID)); | |||
underTest.start(); | |||
assertThat(selectTemplate()).isNull(); | |||
verify(settings, never()).saveProperty(eq(DEFAULT_TEMPLATE_PROPERTY), anyString()); | |||
assertThat(logTester.logs(LoggerLevel.ERROR)).isEmpty(); | |||
verifyDefaultTemplates(); | |||
} | |||
@Test | |||
public void reference_TRK_template_as_default_when_present() { | |||
when(settings.getString(defaultRootQualifierTemplateProperty(Qualifiers.PROJECT))).thenReturn("my_projects_template"); | |||
markTaskAsAlreadyExecuted(); | |||
public void do_not_fail_if_default_template_exists_and_is_registered() { | |||
db.permissionTemplates().insertTemplate(newPermissionTemplateDto() | |||
.setOrganizationUuid(db.getDefaultOrganization().getUuid()) | |||
.setUuid(DEFAULT_TEMPLATE_UUID)); | |||
db.organizations().setDefaultTemplates(db.getDefaultOrganization(), DEFAULT_TEMPLATE_UUID, null); | |||
underTest.start(); | |||
verify(settings).saveProperty(DEFAULT_TEMPLATE_PROPERTY, "my_projects_template"); | |||
} | |||
private void markTaskAsAlreadyExecuted() { | |||
db.getDbClient().loadedTemplateDao().insert(new LoadedTemplateDto(DEFAULT_TEMPLATE_KEY, LoadedTemplateDto.PERMISSION_TEMPLATE_TYPE)); | |||
verifyDefaultTemplates(); | |||
} | |||
private PermissionTemplateDto selectTemplate() { | |||
return db.getDbClient().permissionTemplateDao().selectByUuid(db.getSession(), DEFAULT_TEMPLATE_KEY); | |||
return db.getDbClient().permissionTemplateDao().selectByUuid(db.getSession(), DEFAULT_TEMPLATE_UUID); | |||
} | |||
private List<PermissionTemplateGroupDto> selectGroupPermissions(PermissionTemplateDto template) { | |||
@@ -139,4 +125,11 @@ public class RegisterPermissionTemplatesTest { | |||
groupPermissions.stream().anyMatch(gp -> gp.getPermission().equals(expectedPermission) && Objects.equals(gp.getGroupName(), expectedGroupName))) | |||
.isTrue(); | |||
} | |||
private void verifyDefaultTemplates() { | |||
Optional<DefaultTemplates> defaultTemplates = db.getDbClient().organizationDao().getDefaultTemplates(db.getSession(), db.getDefaultOrganization().getUuid()); | |||
assertThat(defaultTemplates) | |||
.isPresent(); | |||
assertThat(defaultTemplates.get().getProjectUuid()).isEqualTo(DEFAULT_TEMPLATE_UUID); | |||
} | |||
} |
@@ -1,115 +0,0 @@ | |||
<dataset> | |||
<groups id="100" | |||
name="sonar-administrators" | |||
organization_uuid="org1"/> | |||
<groups id="101" | |||
name="sonar-users" | |||
organization_uuid="org1"/> | |||
<users id="200" | |||
login="marius" | |||
name="Marius" | |||
email="[null]" | |||
active="[true]" | |||
is_root="[false]"/> | |||
<users id="201" | |||
login="janette" | |||
name="Janette" | |||
email="[null]" | |||
active="[true]" | |||
is_root="[false]"/> | |||
<!-- on other resources --> | |||
<group_roles id="1" | |||
group_id="100" | |||
resource_id="1" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<group_roles id="2" | |||
group_id="101" | |||
resource_id="1" | |||
role="user" | |||
organization_uuid="org1"/> | |||
<user_roles id="1" | |||
user_id="200" | |||
resource_id="1" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<!-- new groups permissions : sonar-administrators (admin), sonar-users (user & codeviewer), Anyone (user & codeviewer) --> | |||
<group_roles id="3" | |||
group_id="100" | |||
resource_id="123" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<group_roles id="4" | |||
group_id="101" | |||
resource_id="123" | |||
role="user" | |||
organization_uuid="org1"/> | |||
<group_roles id="5" | |||
group_id="[null]" | |||
resource_id="123" | |||
role="user" | |||
organization_uuid="org1"/> | |||
<group_roles id="6" | |||
group_id="101" | |||
resource_id="123" | |||
role="codeviewer" | |||
organization_uuid="org1"/> | |||
<group_roles id="7" | |||
group_id="[null]" | |||
resource_id="123" | |||
role="codeviewer" | |||
organization_uuid="org1"/> | |||
<group_roles id="8" | |||
group_id="100" | |||
resource_id="123" | |||
role="issueadmin" | |||
organization_uuid="org1"/> | |||
<!-- new user permission : marius (admin) & janette (user) --> | |||
<user_roles id="2" | |||
user_id="200" | |||
resource_id="123" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<!-- default permission template for all qualifiers --> | |||
<permission_templates id="1" | |||
name="default" | |||
kee="default_20130101_010203" | |||
organization_uuid="org1"/> | |||
<perm_templates_groups id="1" | |||
template_id="1" | |||
group_id="100" | |||
permission_reference="admin"/> | |||
<perm_templates_groups id="2" | |||
template_id="1" | |||
group_id="101" | |||
permission_reference="user"/> | |||
<perm_templates_groups id="3" | |||
template_id="1" | |||
group_id="[null]" | |||
permission_reference="user"/> | |||
<perm_templates_groups id="4" | |||
template_id="1" | |||
group_id="101" | |||
permission_reference="codeviewer"/> | |||
<perm_templates_groups id="5" | |||
template_id="1" | |||
group_id="[null]" | |||
permission_reference="codeviewer"/> | |||
<perm_templates_groups id="6" | |||
template_id="1" | |||
group_id="100" | |||
permission_reference="issueadmin"/> | |||
<perm_templates_users id="1" | |||
template_id="1" | |||
user_id="200" | |||
permission_reference="admin"/> | |||
</dataset> |
@@ -1,99 +0,0 @@ | |||
<dataset> | |||
<projects organization_uuid="org1" | |||
uuid="A" | |||
uuid_path="NOT_USED" | |||
root_uuid="A" | |||
scope="PRJ" | |||
qualifier="TRK" | |||
kee="org.struts:struts" | |||
name="Struts" | |||
description="the description" | |||
long_name="Apache Struts" | |||
enabled="[true]" | |||
language="java" | |||
copy_component_uuid="[null]" | |||
developer_uuid="[null]" | |||
path="[null]" | |||
authorization_updated_at="123456789" | |||
id="123"/> | |||
<groups id="100" | |||
name="sonar-administrators" | |||
organization_uuid="org1"/> | |||
<groups id="101" | |||
name="sonar-users" | |||
organization_uuid="org1"/> | |||
<users id="200" | |||
login="marius" | |||
name="Marius" | |||
email="[null]" | |||
active="[true]" | |||
is_root="[false]"/> | |||
<!-- on other resources --> | |||
<group_roles id="1" | |||
group_id="100" | |||
resource_id="1" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<group_roles id="2" | |||
group_id="101" | |||
resource_id="1" | |||
role="user" | |||
organization_uuid="org1"/> | |||
<user_roles id="1" | |||
user_id="200" | |||
resource_id="1" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<!-- default permission template for all qualifiers --> | |||
<permission_templates id="1" | |||
name="default" | |||
kee="default_20130101_010203" | |||
organization_uuid="org1"/> | |||
<perm_templates_groups id="1" | |||
template_id="1" | |||
group_id="100" | |||
permission_reference="admin"/> | |||
<perm_templates_groups id="2" | |||
template_id="1" | |||
group_id="101" | |||
permission_reference="user"/> | |||
<perm_templates_groups id="3" | |||
template_id="1" | |||
group_id="[null]" | |||
permission_reference="user"/> | |||
<perm_templates_groups id="4" | |||
template_id="1" | |||
group_id="101" | |||
permission_reference="codeviewer"/> | |||
<perm_templates_groups id="5" | |||
template_id="1" | |||
group_id="[null]" | |||
permission_reference="codeviewer"/> | |||
<perm_templates_groups id="6" | |||
template_id="1" | |||
group_id="100" | |||
permission_reference="issueadmin"/> | |||
<perm_templates_users id="1" | |||
template_id="1" | |||
user_id="200" | |||
permission_reference="admin"/> | |||
<perm_tpl_characteristics id="1" | |||
template_id="1" | |||
permission_key="user" | |||
with_project_creator="[true]" | |||
created_at="1234567890" | |||
updated_at="123457890"/> | |||
<perm_tpl_characteristics id="2" | |||
template_id="2" | |||
permission_key="user" | |||
with_project_creator="[false]" | |||
created_at="1234567890" | |||
updated_at="1234567890"/> | |||
</dataset> |
@@ -1,109 +0,0 @@ | |||
<dataset> | |||
<groups id="100" | |||
name="sonar-administrators" | |||
organization_uuid="org1"/> | |||
<groups id="101" | |||
name="sonar-users" | |||
organization_uuid="org1"/> | |||
<users id="200" | |||
login="marius" | |||
name="Marius" | |||
email="[null]" | |||
active="[true]" | |||
is_root="[false]"/> | |||
<!-- on other resources --> | |||
<group_roles id="1" | |||
group_id="100" | |||
resource_id="1" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<group_roles id="2" | |||
group_id="101" | |||
resource_id="1" | |||
role="user" | |||
organization_uuid="org1"/> | |||
<user_roles id="1" | |||
user_id="200" | |||
resource_id="1" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<!-- new groups permissions : sonar-administrators (admin), sonar-users (user & codeviewer), Anyone (user & codeviewer) --> | |||
<group_roles id="3" | |||
group_id="100" | |||
resource_id="123" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<group_roles id="4" | |||
group_id="101" | |||
resource_id="123" | |||
role="user" | |||
organization_uuid="org1"/> | |||
<group_roles id="5" | |||
group_id="[null]" | |||
resource_id="123" | |||
role="user" | |||
organization_uuid="org1"/> | |||
<group_roles id="6" | |||
group_id="101" | |||
resource_id="123" | |||
role="codeviewer" | |||
organization_uuid="org1"/> | |||
<group_roles id="7" | |||
group_id="[null]" | |||
resource_id="123" | |||
role="codeviewer" | |||
organization_uuid="org1"/> | |||
<group_roles id="8" | |||
group_id="100" | |||
resource_id="123" | |||
role="issueadmin" | |||
organization_uuid="org1"/> | |||
<!-- new user permission : marius (admin) --> | |||
<user_roles id="2" | |||
user_id="200" | |||
resource_id="123" | |||
role="admin" | |||
organization_uuid="org1"/> | |||
<!-- default permission template for all qualifiers --> | |||
<permission_templates id="1" | |||
name="default" | |||
kee="default_20130101_010203" | |||
organization_uuid="org1"/> | |||
<perm_templates_groups id="1" | |||
template_id="1" | |||
group_id="100" | |||
permission_reference="admin"/> | |||
<perm_templates_groups id="2" | |||
template_id="1" | |||
group_id="101" | |||
permission_reference="user"/> | |||
<perm_templates_groups id="3" | |||
template_id="1" | |||
group_id="[null]" | |||
permission_reference="user"/> | |||
<perm_templates_groups id="4" | |||
template_id="1" | |||
group_id="101" | |||
permission_reference="codeviewer"/> | |||
<perm_templates_groups id="5" | |||
template_id="1" | |||
group_id="[null]" | |||
permission_reference="codeviewer"/> | |||
<perm_templates_groups id="6" | |||
template_id="1" | |||
group_id="100" | |||
permission_reference="issueadmin"/> | |||
<perm_templates_users id="1" | |||
template_id="1" | |||
user_id="200" | |||
permission_reference="admin"/> | |||
</dataset> |
@@ -1,29 +0,0 @@ | |||
{ | |||
"permissions": [ | |||
{ | |||
"key": "admin", | |||
"name": "Administer", | |||
"description": "Ability to access project settings and perform administration tasks. (Users will also need \"Browse\" permission)" | |||
}, | |||
{ | |||
"key": "codeviewer", | |||
"name": "See Source Code", | |||
"description": "Ability to view the project\u0027s source code. (Users will also need \"Browse\" permission)" | |||
}, | |||
{ | |||
"key": "issueadmin", | |||
"name": "Administer Issues", | |||
"description": "Grants the permission to perform advanced editing on issues: marking an issue False Positive / Won\u0027t Fix or changing an Issue\u0027s severity. (Users will also need \"Browse\" permission)" | |||
}, | |||
{ | |||
"key": "scan", | |||
"name": "Execute Analysis", | |||
"description": "Ability to execute analyses, and to get all settings required to perform the analysis, even the secured ones like the scm account password, the jira account password, and so on." | |||
}, | |||
{ | |||
"key": "user", | |||
"name": "Browse", | |||
"description": "Ability to access a project, browse its measures, and create/edit issues for it." | |||
} | |||
] | |||
} |
@@ -1,17 +0,0 @@ | |||
{ | |||
"permissionTemplates": [], | |||
"defaultTemplates": [ | |||
{ | |||
"templateId": "AU-Tpxb--iU5OvuD2FLy", | |||
"qualifier": "TRK" | |||
}, | |||
{ | |||
"templateId": "AU-TpxcA-iU5OvuD2FLz", | |||
"qualifier": "VW" | |||
}, | |||
{ | |||
"templateId": "AU-TpxcA-iU5OvuD2FL0", | |||
"qualifier": "DEV" | |||
} | |||
] | |||
} |
@@ -25,35 +25,39 @@ import javax.annotation.Nullable; | |||
import static java.util.Objects.requireNonNull; | |||
public class DefaultTemplates { | |||
private String project; | |||
private String view; | |||
private String projectUuid; | |||
private String viewUuid; | |||
@CheckForNull | |||
public String getProject() { | |||
return project; | |||
public String getProjectUuid() { | |||
checkProjectNotNull(this.projectUuid); | |||
return this.projectUuid; | |||
} | |||
public DefaultTemplates setProject(String project) { | |||
requireNonNull(project, "project default template can't be null"); | |||
this.project = project; | |||
public DefaultTemplates setProjectUuid(String projectUuid) { | |||
checkProjectNotNull(projectUuid); | |||
this.projectUuid = projectUuid; | |||
return this; | |||
} | |||
private static void checkProjectNotNull(String project) { | |||
requireNonNull(project, "defaultTemplates.project can't be null"); | |||
} | |||
@CheckForNull | |||
public String getView() { | |||
return view; | |||
public String getViewUuid() { | |||
return viewUuid; | |||
} | |||
public DefaultTemplates setView(@Nullable String view) { | |||
this.view = view; | |||
public DefaultTemplates setViewUuid(@Nullable String viewUuid) { | |||
this.viewUuid = viewUuid; | |||
return this; | |||
} | |||
@Override | |||
public String toString() { | |||
return "DefaultTemplates{" + | |||
"project='" + project + '\'' + | |||
", view='" + view + '\'' + | |||
"projectUuid='" + projectUuid + '\'' + | |||
", viewUuid='" + viewUuid + '\'' + | |||
'}'; | |||
} | |||
} |
@@ -115,6 +115,6 @@ public class OrganizationDao implements Dao { | |||
private static void checkDefaultTemplates(DefaultTemplates defaultTemplates) { | |||
requireNonNull(defaultTemplates, "defaultTemplates can't be null"); | |||
requireNonNull(defaultTemplates.getProject(), "defaultTemplates.project can't be null"); | |||
requireNonNull(defaultTemplates.getProjectUuid()); | |||
} | |||
} |
@@ -14,8 +14,8 @@ | |||
</sql> | |||
<sql id="defaultTemplatesColumns"> | |||
org.default_perm_template_project as "project", | |||
org.default_perm_template_view as "view" | |||
org.default_perm_template_project as "projectUuid", | |||
org.default_perm_template_view as "viewUuid" | |||
</sql> | |||
<select id="selectByUuid" resultType="Organization"> | |||
@@ -139,8 +139,8 @@ | |||
<update id="updateDefaultTemplates"> | |||
update organizations | |||
set | |||
default_perm_template_project = #{defaultTemplates.project, jdbcType=VARCHAR}, | |||
default_perm_template_view = #{defaultTemplates.view, jdbcType=VARCHAR}, | |||
default_perm_template_project = #{defaultTemplates.projectUuid, jdbcType=VARCHAR}, | |||
default_perm_template_view = #{defaultTemplates.viewUuid, jdbcType=VARCHAR}, | |||
updated_at = #{now, jdbcType=BIGINT} | |||
where | |||
uuid = #{organizationUuid, jdbcType=VARCHAR} |
@@ -34,22 +34,30 @@ public class DefaultTemplatesTest { | |||
@Test | |||
public void setProject_throws_NPE_if_argument_is_null() { | |||
expectedException.expect(NullPointerException.class); | |||
expectedException.expectMessage("project default template can't be null"); | |||
expectedException.expectMessage("defaultTemplates.project can't be null"); | |||
underTest.setProject(null); | |||
underTest.setProjectUuid(null); | |||
} | |||
@Test | |||
public void getProject_throws_NPE_if_project_is_null() { | |||
expectedException.expect(NullPointerException.class); | |||
expectedException.expectMessage("defaultTemplates.project can't be null"); | |||
underTest.getProjectUuid(); | |||
} | |||
@Test | |||
public void setView_accepts_null() { | |||
underTest.setView(null); | |||
underTest.setViewUuid(null); | |||
} | |||
@Test | |||
public void check_toString() { | |||
assertThat(underTest.toString()).isEqualTo("DefaultTemplates{project='null', view='null'}"); | |||
assertThat(underTest.toString()).isEqualTo("DefaultTemplates{projectUuid='null', viewUuid='null'}"); | |||
underTest | |||
.setProject("a project") | |||
.setView("a view"); | |||
assertThat(underTest.toString()).isEqualTo("DefaultTemplates{project='a project', view='a view'}"); | |||
.setProjectUuid("a project") | |||
.setViewUuid("a view"); | |||
assertThat(underTest.toString()).isEqualTo("DefaultTemplates{projectUuid='a project', viewUuid='a view'}"); | |||
} | |||
} |
@@ -460,7 +460,7 @@ public class OrganizationDaoTest { | |||
@Test | |||
public void getDefaultTemplates_returns_data_when_project_default_templates_column_is_not_null() { | |||
insertOrganization(ORGANIZATION_DTO_1); | |||
underTest.setDefaultTemplates(dbSession, ORGANIZATION_DTO_1.getUuid(), new DefaultTemplates().setProject("foo")); | |||
underTest.setDefaultTemplates(dbSession, ORGANIZATION_DTO_1.getUuid(), new DefaultTemplates().setProjectUuid("foo")); | |||
verifyGetDefaultTemplates(ORGANIZATION_DTO_1, "foo", null); | |||
} | |||
@@ -492,7 +492,7 @@ public class OrganizationDaoTest { | |||
@Test | |||
public void getDefaultTemplates_is_case_sensitive() { | |||
insertOrganization(ORGANIZATION_DTO_1); | |||
underTest.setDefaultTemplates(dbSession, ORGANIZATION_DTO_1.getUuid(), new DefaultTemplates().setProject("foo").setView("bar")); | |||
underTest.setDefaultTemplates(dbSession, ORGANIZATION_DTO_1.getUuid(), new DefaultTemplates().setProjectUuid("foo").setViewUuid("bar")); | |||
assertThat(underTest.getDefaultTemplates(dbSession, ORGANIZATION_DTO_1.getUuid().toUpperCase(Locale.ENGLISH))) | |||
.isEmpty(); | |||
@@ -503,7 +503,7 @@ public class OrganizationDaoTest { | |||
expectedException.expect(NullPointerException.class); | |||
expectedException.expectMessage("uuid can't be null"); | |||
underTest.setDefaultTemplates(dbSession, null, new DefaultTemplates().setProject("p")); | |||
underTest.setDefaultTemplates(dbSession, null, new DefaultTemplates().setProjectUuid("p")); | |||
} | |||
@Test | |||
@@ -527,7 +527,7 @@ public class OrganizationDaoTest { | |||
expectedException.expect(NullPointerException.class); | |||
expectedException.expectMessage("defaultTemplates.project can't be null"); | |||
underTest.setDefaultTemplates(dbSession, "uuid", new DefaultTemplates().setView("foo")); | |||
underTest.setDefaultTemplates(dbSession, "uuid", new DefaultTemplates().setViewUuid("foo")); | |||
} | |||
@Test | |||
@@ -731,7 +731,7 @@ public class OrganizationDaoTest { | |||
} | |||
private void setDefaultTemplate(OrganizationDto organizationDto1, @Nullable String project, @Nullable String view) { | |||
underTest.setDefaultTemplates(dbSession, organizationDto1.getUuid(), new DefaultTemplates().setProject(project).setView(view)); | |||
underTest.setDefaultTemplates(dbSession, organizationDto1.getUuid(), new DefaultTemplates().setProjectUuid(project).setViewUuid(view)); | |||
dbSession.commit(); | |||
} | |||
@@ -792,7 +792,7 @@ public class OrganizationDaoTest { | |||
Optional<DefaultTemplates> optional = underTest.getDefaultTemplates(dbSession, organizationDto.getUuid()); | |||
assertThat(optional).isNotEmpty(); | |||
DefaultTemplates defaultTemplates = optional.get(); | |||
assertThat(defaultTemplates.getProject()).isEqualTo(expectedProject); | |||
assertThat(defaultTemplates.getView()).isEqualTo(expectedView); | |||
assertThat(defaultTemplates.getProjectUuid()).isEqualTo(expectedProject); | |||
assertThat(defaultTemplates.getViewUuid()).isEqualTo(expectedView); | |||
} | |||
} |
@@ -19,6 +19,7 @@ | |||
*/ | |||
package org.sonar.db.organization; | |||
import javax.annotation.Nullable; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.DbTester; | |||
@@ -53,4 +54,12 @@ public class OrganizationDbTester { | |||
dbSession.commit(); | |||
return dto; | |||
} | |||
public void setDefaultTemplates(OrganizationDto defaultOrganization, | |||
String projectDefaultTemplateUuid, @Nullable String viewDefaultTemplateUuid) { | |||
DbSession dbSession = dbTester.getSession(); | |||
dbTester.getDbClient().organizationDao().setDefaultTemplates(dbSession, defaultOrganization.getUuid(), new DefaultTemplates().setProjectUuid(projectDefaultTemplateUuid).setViewUuid(viewDefaultTemplateUuid)); | |||
dbSession.commit(); | |||
} | |||
} |
@@ -25,6 +25,8 @@ import org.sonar.db.DbClient; | |||
import org.sonar.db.DbSession; | |||
import org.sonar.db.DbTester; | |||
import org.sonar.db.organization.OrganizationDto; | |||
import org.sonar.db.user.GroupDto; | |||
import org.sonar.db.user.UserDto; | |||
import static org.sonar.db.permission.template.PermissionTemplateTesting.newPermissionTemplateCharacteristicDto; | |||
import static org.sonar.db.permission.template.PermissionTemplateTesting.newPermissionTemplateDto; | |||
@@ -55,11 +57,23 @@ public class PermissionTemplateDbTester { | |||
return templateInDb; | |||
} | |||
public void addGroupToTemplate(PermissionTemplateDto permissionTemplate, GroupDto group, String permission) { | |||
addGroupToTemplate(permissionTemplate.getId(), group.getId(), permission); | |||
} | |||
public void addGroupToTemplate(long templateId, @Nullable Long groupId, String permission) { | |||
dbClient.permissionTemplateDao().insertGroupPermission(dbSession, templateId, groupId, permission); | |||
db.commit(); | |||
} | |||
public void addAnyoneToTemplate(PermissionTemplateDto permissionTemplate, String permission) { | |||
addGroupToTemplate(permissionTemplate.getId(), null, permission); | |||
} | |||
public void addUserToTemplate(PermissionTemplateDto permissionTemplate, UserDto user, String permission) { | |||
addUserToTemplate(permissionTemplate.getId(), user.getId(), permission); | |||
} | |||
public void addUserToTemplate(long templateId, long userId, String permission) { | |||
dbClient.permissionTemplateDao().insertUserPermission(dbSession, templateId, userId, permission); | |||
db.commit(); |