diff options
author | Simon Brandhof <simon.brandhof@sonarsource.com> | 2016-10-19 16:04:34 +0200 |
---|---|---|
committer | Simon Brandhof <simon.brandhof@sonarsource.com> | 2016-10-20 15:10:12 +0200 |
commit | f4a5e4e037a991e435b58afeedbe7bc5e639f9cb (patch) | |
tree | 7d6fe4c2490637c6ce0d37a31543340170133f2c /sonar-db | |
parent | e5285d032d730fab3d8d2da8350cb7c60e37082d (diff) | |
download | sonarqube-f4a5e4e037a991e435b58afeedbe7bc5e639f9cb.tar.gz sonarqube-f4a5e4e037a991e435b58afeedbe7bc5e639f9cb.zip |
SONAR-8263 isolate organizations when removing user permissions
Diffstat (limited to 'sonar-db')
9 files changed, 114 insertions, 7 deletions
diff --git a/sonar-db/src/main/java/org/sonar/db/permission/AuthorizationDao.java b/sonar-db/src/main/java/org/sonar/db/permission/AuthorizationDao.java index dc6677e63d1..c85bf9732d0 100644 --- a/sonar-db/src/main/java/org/sonar/db/permission/AuthorizationDao.java +++ b/sonar-db/src/main/java/org/sonar/db/permission/AuthorizationDao.java @@ -79,13 +79,22 @@ public class AuthorizationDao implements Dao { /** * The number of users who will still have the permission when the group {@code excludedGroupId} - * is deleted. + * is deleted. The anyone virtual group is not taken into account. */ public int countRemainingUserIdsWithGlobalPermissionIfExcludeGroup(DbSession dbSession, String organizationUuid, String permission, long excludedGroupId) { return mapper(dbSession).countRemainingUserIdsWithGlobalPermissionIfExcludeGroup(organizationUuid, permission, excludedGroupId); } + /** + * The number of users who will still have the permission when the user {@code excludedUserId} + * is deleted. The anyone virtual group is not taken into account. + */ + public int countRemainingUsersWithGlobalPermissionExcludingUser(DbSession dbSession, String organizationUuid, + String permission, long excludedUSerId) { + return mapper(dbSession).countRemainingUsersWithGlobalPermissionExcludingUser(organizationUuid, permission, excludedUSerId); + } + public Collection<Long> keepAuthorizedProjectIds(DbSession dbSession, Collection<Long> componentIds, @Nullable Integer userId, String role) { return executeLargeInputs( componentIds, diff --git a/sonar-db/src/main/java/org/sonar/db/permission/AuthorizationMapper.java b/sonar-db/src/main/java/org/sonar/db/permission/AuthorizationMapper.java index dc422f10476..0d83a18acbd 100644 --- a/sonar-db/src/main/java/org/sonar/db/permission/AuthorizationMapper.java +++ b/sonar-db/src/main/java/org/sonar/db/permission/AuthorizationMapper.java @@ -39,6 +39,8 @@ public interface AuthorizationMapper { int countRemainingUserIdsWithGlobalPermissionIfExcludeGroup(@Param("organizationUuid") String organizationUuid, @Param("permission") String permission, @Param("excludedGroupId") long excludedGroupId); + int countRemainingUsersWithGlobalPermissionExcludingUser(@Param("organizationUuid") String organizationUuid, @Param("permission") String permission, @Param("excludedUserId") long excludedUserId); + List<Long> keepAuthorizedProjectIdsForAnonymous(@Param("role") String role, @Param("componentIds") Collection<Long> componentIds); List<Long> keepAuthorizedProjectIdsForUser(@Param("userId") long userId, @Param("role") String role, @Param("componentIds") Collection<Long> componentIds); diff --git a/sonar-db/src/main/java/org/sonar/db/permission/UserPermissionDao.java b/sonar-db/src/main/java/org/sonar/db/permission/UserPermissionDao.java index 6772ff8f3ea..bb170254026 100644 --- a/sonar-db/src/main/java/org/sonar/db/permission/UserPermissionDao.java +++ b/sonar-db/src/main/java/org/sonar/db/permission/UserPermissionDao.java @@ -100,6 +100,24 @@ public class UserPermissionDao implements Dao { return mapper(dbSession).countRowsByRootComponentId(rootComponentId) > 0; } + /** + * Gets all the global permissions granted to user for the specified organization. + * + * @return the global permissions. An empty list is returned if user or organization do not exist. + */ + public List<String> selectGlobalPermissionsOfUser(DbSession dbSession, long userId, String organizationUuid) { + return mapper(dbSession).selectGlobalPermissionsOfUser(userId, organizationUuid); + } + + /** + * Gets all the project permissions granted to user for the specified project. + * + * @return the project permissions. An empty list is returned if project or user do not exist. + */ + public List<String> selectProjectPermissionsOfUser(DbSession dbSession, long userId, long projectId) { + return mapper(dbSession).selectProjectPermissionsOfUser(userId, projectId); + } + public void insert(DbSession dbSession, UserPermissionDto dto) { mapper(dbSession).insert(dto); } diff --git a/sonar-db/src/main/java/org/sonar/db/permission/UserPermissionMapper.java b/sonar-db/src/main/java/org/sonar/db/permission/UserPermissionMapper.java index fffc729fac1..1782c2ed499 100644 --- a/sonar-db/src/main/java/org/sonar/db/permission/UserPermissionMapper.java +++ b/sonar-db/src/main/java/org/sonar/db/permission/UserPermissionMapper.java @@ -60,4 +60,7 @@ public interface UserPermissionMapper { void deleteProjectPermissions(@Param("projectId") long projectId); + List<String> selectGlobalPermissionsOfUser(@Param("userId") long userId, @Param("organizationUuid") String organizationUuid); + + List<String> selectProjectPermissionsOfUser(@Param("userId") long userId, @Param("projectId") long projectId); } diff --git a/sonar-db/src/main/resources/org/sonar/db/permission/AuthorizationMapper.xml b/sonar-db/src/main/resources/org/sonar/db/permission/AuthorizationMapper.xml index 504dc552c31..28d66d9f536 100644 --- a/sonar-db/src/main/resources/org/sonar/db/permission/AuthorizationMapper.xml +++ b/sonar-db/src/main/resources/org/sonar/db/permission/AuthorizationMapper.xml @@ -94,6 +94,29 @@ ) remaining </select> + <select id="countRemainingUsersWithGlobalPermissionExcludingUser" parameterType="map" resultType="int"> + select count(1) from + ( + select gu.user_id + from groups_users gu + inner join group_roles gr on gr.group_id = gu.group_id + where + gr.organization_uuid = #{organizationUuid,jdbcType=VARCHAR} and + gr.role = #{permission,jdbcType=VARCHAR} and + gr.resource_id is null and + gr.group_id is not null + + union + + select ur.user_id + from user_roles ur + where + ur.resource_id is null and + ur.role = #{permission,jdbcType=VARCHAR} and + ur.user_id != #{excludedUserId,jdbcType=BIGINT} + ) remaining + </select> + <select id="keepAuthorizedProjectIdsForUser" parameterType="map" resultType="long"> SELECT gr.resource_id FROM group_roles gr diff --git a/sonar-db/src/main/resources/org/sonar/db/permission/UserPermissionMapper.xml b/sonar-db/src/main/resources/org/sonar/db/permission/UserPermissionMapper.xml index 248b6f3c99b..3e0ee88616a 100644 --- a/sonar-db/src/main/resources/org/sonar/db/permission/UserPermissionMapper.xml +++ b/sonar-db/src/main/resources/org/sonar/db/permission/UserPermissionMapper.xml @@ -50,6 +50,23 @@ </where> </sql> + <select id="selectGlobalPermissionsOfUser" parameterType="map" resultType="string"> + select ur.role + from user_roles ur + where + ur.organization_uuid = #{organizationUuid,jdbcType=VARCHAR} and + ur.user_id = #{userId,jdbcType=BIGINT} and + ur.resource_id is null + </select> + + <select id="selectProjectPermissionsOfUser" parameterType="map" resultType="string"> + select ur.role + from user_roles ur + where + ur.user_id = #{userId,jdbcType=BIGINT} and + ur.resource_id = #{projectId,jdbcType=BIGINT} + </select> + <select id="countUsersByProjectPermission" resultType="org.sonar.db.permission.CountPerProjectPermission"> select ur.resource_id as componentId, ur.role as permission, count(u.login) as count from users u diff --git a/sonar-db/src/test/java/org/sonar/db/permission/PermissionRepositoryTest.java b/sonar-db/src/test/java/org/sonar/db/permission/PermissionRepositoryTest.java index 4b8ea83df2a..5d7247fd90a 100644 --- a/sonar-db/src/test/java/org/sonar/db/permission/PermissionRepositoryTest.java +++ b/sonar-db/src/test/java/org/sonar/db/permission/PermissionRepositoryTest.java @@ -73,11 +73,12 @@ public class PermissionRepositoryTest { public void apply_permission_template() { dbTester.prepareDbUnit(getClass(), "should_apply_permission_template.xml"); + UserDto marius = dbTester.users().selectUserByLogin("marius").get(); RoleDao roleDao = dbTester.getDbClient().roleDao(); assertThat(roleDao.selectGroupPermissions(session, "sonar-administrators", PROJECT.getId())).isEmpty(); assertThat(roleDao.selectGroupPermissions(session, "sonar-users", PROJECT.getId())).isEmpty(); assertThat(roleDao.selectGroupPermissions(session, "Anyone", PROJECT.getId())).isEmpty(); - assertThat(dbTester.getDbClient().userPermissionDao().selectPermissionsByLogin(session, "marius", PROJECT.uuid())).isEmpty(); + assertThat(dbTester.getDbClient().userPermissionDao().selectProjectPermissionsOfUser(session, marius.getId(), PROJECT.getId())).isEmpty(); PermissionTemplateDto template = dbTester.getDbClient().permissionTemplateDao().selectByUuid(session, "default_20130101_010203"); underTest.apply(session, template, PROJECT, null); @@ -85,7 +86,7 @@ public class PermissionRepositoryTest { assertThat(roleDao.selectGroupPermissions(session, "sonar-administrators", PROJECT.getId())).containsOnly("admin", "issueadmin"); assertThat(roleDao.selectGroupPermissions(session, "sonar-users", PROJECT.getId())).containsOnly("user", "codeviewer"); assertThat(roleDao.selectGroupPermissions(session, "Anyone", PROJECT.getId())).containsOnly("user", "codeviewer"); - assertThat(dbTester.getDbClient().userPermissionDao().selectPermissionsByLogin(session, "marius", PROJECT.uuid())).containsOnly("admin"); + assertThat(dbTester.getDbClient().userPermissionDao().selectProjectPermissionsOfUser(session, marius.getId(), PROJECT.getId())).containsOnly("admin"); checkAuthorizationUpdatedAtIsUpdated(); } diff --git a/sonar-db/src/test/java/org/sonar/db/permission/UserPermissionDaoTest.java b/sonar-db/src/test/java/org/sonar/db/permission/UserPermissionDaoTest.java index 52e16f21b43..8cfe4d3c5bc 100644 --- a/sonar-db/src/test/java/org/sonar/db/permission/UserPermissionDaoTest.java +++ b/sonar-db/src/test/java/org/sonar/db/permission/UserPermissionDaoTest.java @@ -33,6 +33,7 @@ import org.sonar.db.DbSession; import org.sonar.db.DbTester; import org.sonar.db.component.ComponentDto; import org.sonar.db.organization.OrganizationDto; +import org.sonar.db.organization.OrganizationTesting; import org.sonar.db.user.UserDto; import static java.util.Arrays.asList; @@ -42,6 +43,7 @@ import static org.sonar.api.web.UserRole.USER; import static org.sonar.core.permission.GlobalPermissions.PROVISIONING; import static org.sonar.core.permission.GlobalPermissions.SYSTEM_ADMIN; import static org.sonar.db.component.ComponentTesting.newProjectDto; +import static org.sonar.db.organization.OrganizationTesting.newOrganizationDto; import static org.sonar.db.user.UserTesting.newUserDto; public class UserPermissionDaoTest { @@ -305,7 +307,6 @@ public class UserPermissionDaoTest { assertThatProjectHasNoPermissions(project1); } - @Test public void projectHasPermissions() { addGlobalPermissionOnDefaultOrganization(SYSTEM_ADMIN, user1); @@ -315,6 +316,36 @@ public class UserPermissionDaoTest { assertThat(underTest.hasRootComponentPermissions(dbSession, project2.getId())).isFalse(); } + @Test + public void selectGlobalPermissionsOfUser() { + OrganizationDto org = OrganizationTesting.insert(dbTester, newOrganizationDto()); + addGlobalPermissionOnDefaultOrganization("perm1", user1); + addGlobalPermissionOnDefaultOrganization("perm2", user2); + addGlobalPermission(org, "perm3", user1); + addProjectPermissionOnDefaultOrganization("perm4", user1, project1); + addProjectPermission(org, "perm5", user1, project1); + + assertThat(underTest.selectGlobalPermissionsOfUser(dbSession, user1.getId(), org.getUuid())).containsOnly("perm3"); + assertThat(underTest.selectGlobalPermissionsOfUser(dbSession, user1.getId(), dbTester.getDefaultOrganization().getUuid())).containsOnly("perm1"); + assertThat(underTest.selectGlobalPermissionsOfUser(dbSession, user1.getId(), "otherOrg")).isEmpty(); + assertThat(underTest.selectGlobalPermissionsOfUser(dbSession, user3.getId(), org.getUuid())).isEmpty(); + } + + @Test + public void selectProjectPermissionsOfUser() { + OrganizationDto org = OrganizationTesting.insert(dbTester, newOrganizationDto()); + ComponentDto project3 = dbTester.components().insertProject(); + addGlobalPermission(org, "perm1", user1); + addProjectPermission(org, "perm2", user1, project1); + addProjectPermission(org, "perm3", user1, project1); + addProjectPermission(org, "perm4", user1, project2); + addProjectPermission(org, "perm5", user2, project1); + + assertThat(underTest.selectProjectPermissionsOfUser(dbSession, user1.getId(), project1.getId())).containsOnly("perm2", "perm3"); + assertThat(underTest.selectProjectPermissionsOfUser(dbSession, user1.getId(), project2.getId())).containsOnly("perm4"); + assertThat(underTest.selectProjectPermissionsOfUser(dbSession, user1.getId(), project3.getId())).isEmpty(); + } + private void expectCount(List<Long> projectIds, CountPerProjectPermission... expected) { List<CountPerProjectPermission> got = underTest.countUsersByProjectPermission(dbSession, projectIds); assertThat(got).hasSize(expected.length); diff --git a/sonar-db/src/test/java/org/sonar/db/user/UserDbTester.java b/sonar-db/src/test/java/org/sonar/db/user/UserDbTester.java index 3f8e9f63dfb..d81044aa564 100644 --- a/sonar-db/src/test/java/org/sonar/db/user/UserDbTester.java +++ b/sonar-db/src/test/java/org/sonar/db/user/UserDbTester.java @@ -22,7 +22,6 @@ package org.sonar.db.user; import java.util.Arrays; import java.util.List; import java.util.Optional; -import java.util.Set; import javax.annotation.CheckForNull; import javax.annotation.Nullable; import org.sonar.core.permission.GlobalPermissions; @@ -344,7 +343,11 @@ public class UserDbTester { return dto; } - public Set<String> selectUserPermissions(UserDto user, @Nullable ComponentDto project) { - return db.getDbClient().userPermissionDao().selectPermissionsByLogin(db.getSession(), user.getLogin(), project == null ? null : project.uuid()); + public List<String> selectGlobalPermissionsOfUser(UserDto user, OrganizationDto organization) { + return db.getDbClient().userPermissionDao().selectGlobalPermissionsOfUser(db.getSession(), user.getId(), organization.getUuid()); + } + + public List<String> selectProjectPermissionsOfUser(UserDto user, ComponentDto project) { + return db.getDbClient().userPermissionDao().selectProjectPermissionsOfUser(db.getSession(), user.getId(), project.getId()); } } |