]> source.dussan.org Git - sonarqube.git/commitdiff
SONAR-7835 Select user permissions
authorTeryk Bellahsene <teryk.bellahsene@sonarsource.com>
Tue, 5 Jul 2016 22:31:45 +0000 (00:31 +0200)
committerStas Vilchik <vilchiks@gmail.com>
Tue, 12 Jul 2016 08:16:53 +0000 (10:16 +0200)
sonar-db/src/main/java/org/sonar/db/permission/PermissionDao.java
sonar-db/src/main/java/org/sonar/db/permission/PermissionMapper.java
sonar-db/src/main/java/org/sonar/db/permission/PermissionQuery.java
sonar-db/src/main/resources/org/sonar/db/permission/PermissionMapper.xml
sonar-db/src/test/java/org/sonar/db/permission/UserWithPermissionDaoTest.java

index dbf7d0f38311b53a6643a60e2219c4608879ef1a..9f4426021d77abc24e1d34e6a99d5df878538889 100644 (file)
@@ -33,6 +33,7 @@ import org.sonar.db.MyBatis;
 import org.sonar.db.user.UserPermissionDto;
 
 import static com.google.common.collect.Maps.newHashMap;
+import static java.util.Collections.emptyList;
 import static org.sonar.db.DatabaseUtils.executeLargeInputsWithoutOutput;
 
 public class PermissionDao implements Dao {
@@ -70,6 +71,10 @@ public class PermissionDao implements Dao {
   }
 
   public List<UserPermissionDto> selectUserPermissionsByQuery(DbSession dbSession, PermissionQuery query) {
+    if (query.getLogins() != null && query.getLogins().isEmpty()) {
+      return emptyList();
+    }
+
     return mapper(dbSession).selectUserPermissionsByQuery(query);
   }
 
index f2b94da1b3f6cab67a201c4e88ba102ce82c09f0..cad5ff80c40075eb7adb73501c85ff350d111503 100644 (file)
@@ -36,7 +36,7 @@ public interface PermissionMapper {
 
   int countUsersByQuery(@Param("query") PermissionQuery query);
 
-  List<UserPermissionDto> selectUserPermissionsByQuery(PermissionQuery query);
+  List<UserPermissionDto> selectUserPermissionsByQuery(@Param("query") PermissionQuery query);
 
   List<GroupWithPermissionDto> selectGroups(Map<String, Object> parameters);
 
index d58357d13bca9736deec0d8c55ca0849f70b8f88..1d76a9dd426c452822917cd21d6266e1edc44013 100644 (file)
@@ -19,6 +19,7 @@
  */
 package org.sonar.db.permission;
 
+import java.util.List;
 import java.util.Locale;
 import javax.annotation.CheckForNull;
 import javax.annotation.Nullable;
@@ -34,7 +35,6 @@ import static org.sonar.db.DatabaseUtils.buildLikeValue;
  * Query used to get users and groups permissions
  */
 public class PermissionQuery {
-
   public static final int RESULTS_MAX_SIZE = 100;
   public static final int SEARCH_QUERY_MIN_LENGTH = 3;
   public static final int DEFAULT_PAGE_SIZE = 20;
@@ -46,6 +46,7 @@ public class PermissionQuery {
   private final String searchQuery;
   private final String searchQueryToSql;
   private final boolean withPermissionOnly;
+  private final List<String> logins;
 
   private final int pageSize;
   private final int pageOffset;
@@ -59,6 +60,7 @@ public class PermissionQuery {
     this.searchQueryToSql = builder.searchQuery == null ? null : buildLikeValue(builder.searchQuery, WildcardPosition.BEFORE_AND_AFTER).toLowerCase(Locale.ENGLISH);
     this.pageSize = builder.pageSize;
     this.pageOffset = offset(builder.pageIndex, builder.pageSize);
+    this.logins = builder.logins;
   }
 
   @CheckForNull
@@ -97,6 +99,11 @@ public class PermissionQuery {
     return pageOffset;
   }
 
+  @CheckForNull
+  public List<String> getLogins() {
+    return logins;
+  }
+
   public static Builder builder() {
     return new Builder();
   }
@@ -107,6 +114,7 @@ public class PermissionQuery {
     private String template;
     private String searchQuery;
     private boolean withPermissionOnly;
+    private List<String> logins;
 
     private Integer pageIndex = DEFAULT_PAGE_INDEX;
     private Integer pageSize = DEFAULT_PAGE_SIZE;
@@ -150,11 +158,16 @@ public class PermissionQuery {
       return this;
     }
 
+    public Builder setLogins(@Nullable List<String> logins) {
+      this.logins = logins;
+      return this;
+    }
+
     public PermissionQuery build() {
       this.pageIndex = firstNonNull(pageIndex, DEFAULT_PAGE_INDEX);
       this.pageSize = firstNonNull(pageSize, DEFAULT_PAGE_SIZE);
       checkArgument(searchQuery == null || searchQuery.length() >= 3);
-      checkArgument(!(withPermissionOnly && permission == null));
+      checkArgument(logins == null || !logins.isEmpty());
       return new PermissionQuery(this);
     }
   }
index f93c971998fa429fe119d0219e57c8236ad37122..79297f8659d49d2e667a9ef30af79be942186a97 100644 (file)
@@ -3,17 +3,20 @@
 
 <mapper namespace="org.sonar.db.permission.PermissionMapper">
 
+  <!-- TODO delete when not used anymore -->
   <select id="selectUsers" parameterType="map" resultType="UserWithPermission">
     SELECT u.login as login, u.name as name, u.email as email, user_role.role as permission
     <include refid="usersSelection"/>
     ORDER BY u.name
   </select>
 
+  <!-- TODO delete when not used anymore -->
   <select id="countUsers" parameterType="map" resultType="int">
     SELECT count(u.login)
     <include refid="usersSelection"/>
   </select>
 
+  <!-- TODO delete when not used anymore -->
   <sql id="usersSelection">
     FROM users u
     LEFT JOIN user_roles user_role ON user_role.user_id=u.id
     </where>
   </sql>
 
+  <sql id="userColumns">
+    <!-- lower(u.name) and u.id are present to order by with select distinct -->
+    u.login as login, u.name as name, u.email as email, lower(u.name), u.id
+  </sql>
+
   <select id="selectUsersByQuery" parameterType="map" resultType="org.sonar.db.permission.UserRef">
     select distinct <include refid="userColumns" />
     <include refid="usersByQuery"/>
     order by lower(u.name), u.name, u.id
   </select>
 
-  <sql id="userColumns">
-    <!-- lower(u.name) and u.id are present to order by with select distinct -->
-    u.login as login, u.name as name, u.email as email, lower(u.name), u.id
-  </sql>
-
   <select id="countUsersByQuery" parameterType="map" resultType="int">
     select count(1)
     from (
       <include refid="usersByQuery"/>)
   </select>
 
+  <select id="selectUserPermissionsByQuery" parameterType="map" resultType="UserRole">
+    select ur.user_id as userId, ur.resource_id as componentId, ur.role as permission
+    <include refid="usersByQuery" />
+  </select>
+
   <sql id="usersByQuery">
     from users u
       left join user_roles ur ON ur.user_id=u.id
         left join projects p on ur.resource_id = p.id
     <where>
       and u.active = ${_true}
+      <if test="query.logins != null">
+        and u.login in
+        <foreach collection="query.logins" open="(" close=")" item="login" separator=",">
+          #{login}
+        </foreach>
+      </if>
       <if test="query.searchQueryToSql != null">
         and lower(u.name) like #{query.searchQueryToSql} ESCAPE '/'
       </if>
     </where>
   </sql>
 
-  <select id="selectUserPermissionsByQuery" parameterType="map" resultType="UserRole">
-    select ur.user_id as userId, ur.resource_id as componentId, ur.role as permission
-    from user_roles ur
-      inner join users u on ur.user_id = u.id
-      left outer join projects p on ur.resource_id=p.id
-    <where>
-      <if test="query.logins != null">
-      and u.login in
-        <foreach collection="query.logins" open="(" close=")" item="login" separator=",">
-          #{login}
-        </foreach>
-      </if>
-      <if test="query.searchQueryToSql != null">
-        and (lower(u.name) like #{query.searchQueryToSql} ESCAPE '/')
-      </if>
-    </where>
-
-  </select>
-
   <select id="usersCountByProjectIdAndPermission" parameterType="map"
           resultType="org.sonar.db.permission.CountByProjectAndPermissionDto">
     SELECT user_role.resource_id as componentId, user_role.role as permission, count(u.login) as count
index a85760ec55e1edf0a4263600d3516dbe29968eb3..77b63a0adbe892cbeb7a3460922c40c197e6dabd 100644 (file)
@@ -38,7 +38,9 @@ import org.sonar.db.user.UserDbTester;
 import org.sonar.db.user.UserDto;
 import org.sonar.db.user.UserRoleDto;
 
+import static java.util.Collections.singletonList;
 import static org.assertj.core.api.Assertions.assertThat;
+import static org.assertj.core.api.Assertions.tuple;
 import static org.sonar.api.web.UserRole.ADMIN;
 import static org.sonar.api.web.UserRole.ISSUE_ADMIN;
 import static org.sonar.api.web.UserRole.USER;
@@ -159,16 +161,25 @@ public class UserWithPermissionDaoTest {
     permissionDb.addProjectPermissionToUser(UserRole.USER, user4.getId(), project.getId());
 
     PermissionQuery.Builder dbQuery = PermissionQuery.builder();
-    List<UserRef> result = selectUsersByQuery(dbQuery);
+    List<UserRef> users = selectUsersByQuery(dbQuery);
     int count = countUsersByQuery(dbQuery);
+    List<UserPermissionDto> permissions = selectUserPermissionsByQuery(dbQuery);
 
-    assertThat(result)
+    assertThat(users)
       .hasSize(4)
       .extracting(UserRef::getName)
       .containsExactly("1-name", "2-name", "3-name", "4-name");
-    assertThat(result.get(0)).extracting(UserRef::getEmail, UserRef::getLogin)
+    assertThat(users.get(0)).extracting(UserRef::getEmail, UserRef::getLogin)
       .containsExactly(user1.getEmail(), user1.getLogin());
     assertThat(count).isEqualTo(4);
+
+    assertThat(permissions).hasSize(5).extracting(UserPermissionDto::getUserId, UserPermissionDto::getPermission)
+      .containsOnlyOnce(
+        tuple(user1.getId(), GlobalPermissions.SYSTEM_ADMIN),
+        tuple(user2.getId(), GlobalPermissions.SYSTEM_ADMIN),
+        tuple(user3.getId(), GlobalPermissions.SYSTEM_ADMIN),
+        tuple(user3.getId(), GlobalPermissions.PROVISIONING),
+        tuple(user4.getId(), UserRole.USER));
   }
 
   @Test
@@ -191,14 +202,35 @@ public class UserWithPermissionDaoTest {
     userDb.insertUser(newUserDto().setName("unknown"));
 
     PermissionQuery.Builder dbQuery = PermissionQuery.builder().setSearchQuery("nam");
-    List<UserRef> result = selectUsersByQuery(dbQuery);
+    List<UserRef> users = selectUsersByQuery(dbQuery);
     int count = countUsersByQuery(dbQuery);
 
-    assertThat(result).hasSize(1);
-    assertThat(result.get(0).getName()).isEqualTo("1-name");
+    assertThat(users).hasSize(1);
+    assertThat(users.get(0).getName()).isEqualTo("1-name");
     assertThat(count).isEqualTo(1);
   }
 
+  @Test
+  public void select_user_permissions() {
+    UserDto user = userDb.insertUser(newUserDto().setLogin("user-login"));
+    UserDto anotherUser = userDb.insertUser(newUserDto().setLogin("another-login"));
+    ComponentDto project = componentDb.insertComponent(newProjectDto());
+    permissionDb.addProjectPermissionToUser(UserRole.ADMIN, user.getId(), project.getId());
+    permissionDb.addProjectPermissionToUser(UserRole.ADMIN, anotherUser.getId(), project.getId());
+
+    PermissionQuery.Builder dbQuery = PermissionQuery.builder()
+      .setComponentUuid(project.uuid())
+      .setLogins(singletonList("user-login"))
+      .withPermissionOnly();
+    List<UserPermissionDto> result = selectUserPermissionsByQuery(dbQuery);
+
+    assertThat(result).hasSize(1);
+    UserPermissionDto userPermission = result.get(0);
+    assertThat(userPermission.getComponentId()).isEqualTo(project.getId());
+    assertThat(userPermission.getPermission()).isEqualTo(UserRole.ADMIN);
+    assertThat(userPermission.getUserId()).isEqualTo(user.getId());
+  }
+
   @Test
   public void select_users_with_global_permissions() {
     UserDto user3 = userDb.insertUser(newUserDto().setName("3-name"));
@@ -322,6 +354,10 @@ public class UserWithPermissionDaoTest {
     return underTest.countUsersByQuery(session, query.build());
   }
 
+  private List<UserPermissionDto> selectUserPermissionsByQuery(PermissionQuery.Builder query) {
+    return underTest.selectUserPermissionsByQuery(session, query.build());
+  }
+
   private void addPermissionToUser(String permission, long userId, long resourceId) {
     dbTester.getDbClient().roleDao().insertUserRole(dbTester.getSession(), new UserRoleDto()
       .setRole(permission)