]> source.dussan.org Git - sonarqube.git/commitdiff
SONAR-5590 When no more permission on a project, there should be nothing in the Issue...
authorJulien Lancelot <julien.lancelot@sonarsource.com>
Mon, 29 Sep 2014 08:46:31 +0000 (10:46 +0200)
committerJulien Lancelot <julien.lancelot@sonarsource.com>
Mon, 29 Sep 2014 09:11:29 +0000 (11:11 +0200)
server/sonar-server/src/main/java/org/sonar/server/computation/db/AnalysisReportDao.java
server/sonar-server/src/main/java/org/sonar/server/db/BaseDao.java
server/sonar-server/src/main/java/org/sonar/server/issue/db/IssueAuthorizationDao.java
server/sonar-server/src/main/java/org/sonar/server/search/DbSynchronizationHandler.java
server/sonar-server/src/test/java/org/sonar/server/component/ComponentTesting.java [new file with mode: 0644]
server/sonar-server/src/test/java/org/sonar/server/issue/index/IssueAuthorizationIndexMediumTest.java
server/sonar-server/src/test/java/org/sonar/server/issue/index/IssueIndexMediumTest.java
server/sonar-server/src/test/java/org/sonar/server/permission/InternalPermissionServiceMediumTest.java

index 2edd7402f0d97aa6030c98d1a95c1bc5c46a4ef6..88fa780a4eacc24aff8b86c69f557bf99cd8e70d 100644 (file)
@@ -67,7 +67,7 @@ public class AnalysisReportDao extends BaseDao<AnalysisReportMapper, AnalysisRep
   }
 
   @Override
-  protected Map getSynchronizationParams(Date date, Map<String, String> params) {
+  protected Map<String, Object> getSynchronizationParams(Date date, Map<String, String> params) {
     throw new UnsupportedOperationException();
   }
 }
index 388cde811a4578b89bf28a23bed36a31144a9cb8..097601a7326e82a860f5ef33b1146104f73becc5 100644 (file)
@@ -321,15 +321,15 @@ public abstract class BaseDao<MAPPER, DTO extends Dto<KEY>, KEY extends Serializ
 
   // Synchronization methods
 
-  protected DbSynchronizationHandler getSynchronizationResultHandler(final DbSession session) {
-    return new DbSynchronizationHandler() {
+  protected DbSynchronizationHandler getSynchronizationResultHandler(final DbSession session, Map<String, String> params) {
+    return new DbSynchronizationHandler(session, params) {
       private int count = 0;
 
       @Override
       public void handleResult(ResultContext resultContext) {
         DTO dto = (DTO) resultContext.getResultObject();
         // session.enqueue(new UpsertDto<DTO>(getIndexType(), dto, false));
-        session.enqueue(new InsertDto<DTO>(getIndexType(), dto, false));
+        getSession().enqueue(new InsertDto<DTO>(getIndexType(), dto, false));
         count++;
         if (count % 100000 == 0) {
           LOGGER.info(" - synchronized {} {}", count, getIndexType());
@@ -361,7 +361,7 @@ public abstract class BaseDao<MAPPER, DTO extends Dto<KEY>, KEY extends Serializ
   @Override
   public void synchronizeAfter(final DbSession session, Date date, Map<String, String> params) {
     try {
-      DbSynchronizationHandler handler = getSynchronizationResultHandler(session);
+      DbSynchronizationHandler handler = getSynchronizationResultHandler(session, params);
       session.select(getSynchronizeStatementFQN(), getSynchronizationParams(date, params), handler);
       handler.enqueueCollected();
       session.enqueue(new RefreshIndex(this.getIndexType()));
index 80ddf10c32e5034e26cf00e41db1ffdf41de6697..96937905230d3e7ff5d4eb2746709ed30632f36b 100644 (file)
@@ -32,6 +32,7 @@ import org.sonar.core.persistence.DbSession;
 import org.sonar.server.db.BaseDao;
 import org.sonar.server.search.DbSynchronizationHandler;
 import org.sonar.server.search.IndexDefinition;
+import org.sonar.server.search.action.DeleteKey;
 import org.sonar.server.search.action.UpsertDto;
 
 import java.util.Date;
@@ -57,8 +58,8 @@ public class IssueAuthorizationDao extends BaseDao<IssueAuthorizationMapper, Iss
   }
 
   @Override
-  protected DbSynchronizationHandler getSynchronizationResultHandler(final DbSession session) {
-    return new DbSynchronizationHandler() {
+  protected DbSynchronizationHandler getSynchronizationResultHandler(final DbSession session, Map<String, String> params) {
+    return new DbSynchronizationHandler(session, params) {
       private final Map<String, IssueAuthorizationDto> authorizationDtoMap = new HashMap<String, IssueAuthorizationDto>();
 
       @Override
@@ -86,15 +87,20 @@ public class IssueAuthorizationDao extends BaseDao<IssueAuthorizationMapper, Iss
 
       @Override
       public void enqueueCollected() {
-        for (IssueAuthorizationDto authorization : authorizationDtoMap.values()) {
-          session.enqueue(new UpsertDto<IssueAuthorizationDto>(getIndexType(), authorization, true));
+        String projectKey = getParams().get("project");
+        if (authorizationDtoMap.isEmpty() && projectKey != null) {
+          getSession().enqueue(new DeleteKey<String>(getIndexType(), projectKey));
+        } else {
+          for (IssueAuthorizationDto authorization : authorizationDtoMap.values()) {
+            getSession().enqueue(new UpsertDto<IssueAuthorizationDto>(getIndexType(), authorization, true));
+          }
         }
       }
     };
   }
 
   @Override
-  protected Map getSynchronizationParams(Date date, Map<String, String> params) {
+  protected Map<String, Object> getSynchronizationParams(Date date, Map<String, String> params) {
     Map<String, Object> finalParams = super.getSynchronizationParams(date, params);
     finalParams.put("permission", UserRole.USER);
     finalParams.put("anyone", DefaultGroups.ANYONE);
index 8e56aa61f5f260becf6cebf8b344483e3ff7ab9f..b750a4d0474dab3c5f549cc9768c4afd1639d676 100644 (file)
@@ -22,14 +22,33 @@ package org.sonar.server.search;
 
 import org.apache.ibatis.session.ResultContext;
 import org.apache.ibatis.session.ResultHandler;
+import org.sonar.core.persistence.DbSession;
 
 import javax.annotation.CheckForNull;
 
-public interface DbSynchronizationHandler extends ResultHandler {
+import java.util.Map;
+
+public abstract class DbSynchronizationHandler implements ResultHandler {
+
+  private final DbSession session;
+  private final Map<String, String> params;
+
+  protected DbSynchronizationHandler(DbSession session, Map<String, String> params) {
+    this.session = session;
+    this.params = params;
+  }
 
   @Override
-  void handleResult(ResultContext context);
+  public abstract void handleResult(ResultContext context);
 
   @CheckForNull
-  void enqueueCollected();
+  public abstract void enqueueCollected();
+
+  public final DbSession getSession() {
+    return session;
+  }
+
+  public final Map<String, String> getParams() {
+    return params;
+  }
 }
diff --git a/server/sonar-server/src/test/java/org/sonar/server/component/ComponentTesting.java b/server/sonar-server/src/test/java/org/sonar/server/component/ComponentTesting.java
new file mode 100644 (file)
index 0000000..493ca99
--- /dev/null
@@ -0,0 +1,68 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2014 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube 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.
+ *
+ * SonarQube 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.component;
+
+import org.sonar.api.resources.Qualifiers;
+import org.sonar.api.resources.Scopes;
+import org.sonar.core.component.ComponentDto;
+
+public class ComponentTesting {
+
+  public static ComponentDto newFileDto(ComponentDto subProjectOrProject) {
+    return new ComponentDto()
+      .setKey("file")
+      .setName("File")
+      .setLongName("File")
+      .setSubProjectId(subProjectOrProject.getId())
+      .setScope(Scopes.FILE)
+      .setQualifier(Qualifiers.FILE)
+      .setPath("src/main/xoo/org/sonar/samples/File.xoo")
+      .setLanguage("xoo")
+      .setEnabled(true);
+  }
+
+  public static ComponentDto newModuleDto(ComponentDto subProjectOrProject) {
+    return new ComponentDto()
+      .setKey("module")
+      .setName("Module")
+      .setLongName("Module")
+      .setSubProjectId(subProjectOrProject.getId())
+      .setScope(Scopes.FILE)
+      .setQualifier(Qualifiers.MODULE)
+      .setPath("module")
+      .setLanguage(null)
+      .setEnabled(true);
+  }
+
+  public static ComponentDto newProjectDto() {
+    return new ComponentDto()
+      .setKey("project")
+      .setName("Project")
+      .setLongName("Project")
+      .setSubProjectId(null)
+      .setScope(Scopes.PROJECT)
+      .setQualifier(Qualifiers.PROJECT)
+      .setPath(null)
+      .setLanguage(null)
+      .setEnabled(true);
+  }
+  
+}
index 6e7d90830e106c9cc4908fbaf823c330ae1be542..11abdf1d0d92d94bb2f6d81c09bcfa1a33c22c1f 100644 (file)
@@ -20,6 +20,7 @@
 
 package org.sonar.server.issue.index;
 
+import com.google.common.collect.ImmutableMap;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.ClassRule;
@@ -32,6 +33,7 @@ import org.sonar.core.persistence.DbSession;
 import org.sonar.core.user.GroupDto;
 import org.sonar.core.user.UserDto;
 import org.sonar.server.db.DbClient;
+import org.sonar.server.issue.db.IssueAuthorizationDao;
 import org.sonar.server.platform.Platform;
 import org.sonar.server.tester.ServerTester;
 
@@ -65,7 +67,7 @@ public class IssueAuthorizationIndexMediumTest {
   }
 
   @Test
-  public void synchronize() throws Exception {
+  public void synchronize_all() throws Exception {
     project = new ComponentDto()
       .setKey("Sample")
       .setAuthorizationUpdatedAt(DateUtils.parseDate("2014-09-11"));
@@ -99,6 +101,82 @@ public class IssueAuthorizationIndexMediumTest {
     assertThat(index.getNullableByKey(project.getKey())).isNotNull();
   }
 
+  @Test
+  public void synchronize_all_on_startup_tasks() throws Exception {
+    project = new ComponentDto()
+      .setKey("Sample")
+      .setAuthorizationUpdatedAt(DateUtils.parseDate("2014-09-11"));
+    db.componentDao().insert(session, project);
+
+    GroupDto sonarUsers = new GroupDto().setName("devs");
+    db.groupDao().insert(session, sonarUsers);
+
+    tester.get(PermissionFacade.class).insertGroupPermission(project.getId(), "devs", UserRole.USER, session);
+    session.commit();
+
+    assertThat(index.getNullableByKey(project.getKey())).isNull();
+
+    tester.get(Platform.class).executeStartupTasks();
+    assertThat(index.getNullableByKey(project.getKey())).isNotNull();
+  }
+
+  @Test
+  public void synchronize_project() throws Exception {
+    project = new ComponentDto()
+      .setKey("Sample")
+      .setAuthorizationUpdatedAt(DateUtils.parseDate("2014-09-11"));
+    db.componentDao().insert(session, project);
+
+    GroupDto sonarUsers = new GroupDto().setName("devs");
+    db.groupDao().insert(session, sonarUsers);
+
+    UserDto john = new UserDto().setLogin("john").setName("John").setActive(true);
+    db.userDao().insert(session, john);
+
+    tester.get(PermissionFacade.class).insertGroupPermission(project.getId(), "devs", UserRole.USER, session);
+    tester.get(PermissionFacade.class).insertUserPermission(project.getId(), john.getId(), UserRole.USER, session);
+
+    session.commit();
+
+    assertThat(index.getNullableByKey(project.getKey())).isNull();
+    db.issueAuthorizationDao().synchronizeAfter(session, new Date(0), ImmutableMap.of(IssueAuthorizationDao.PROJECT_KEY, project.key()));
+    session.commit();
+
+    IssueAuthorizationDoc issueAuthorizationDoc = index.getByKey(project.getKey());
+    assertThat(issueAuthorizationDoc).isNotNull();
+    assertThat(issueAuthorizationDoc.project()).isEqualTo("Sample");
+    assertThat(issueAuthorizationDoc.permission()).isEqualTo("user");
+    assertThat(issueAuthorizationDoc.groups()).containsExactly("devs");
+    assertThat(issueAuthorizationDoc.users()).containsExactly("john");
+    assertThat(issueAuthorizationDoc.updatedAt()).isNotNull();
+  }
+
+  @Test
+  public void remove_data_when_synchronizing_project_with_empty_permission() throws Exception {
+    project = new ComponentDto()
+      .setKey("Sample")
+      .setAuthorizationUpdatedAt(DateUtils.parseDate("2014-09-11"));
+    db.componentDao().insert(session, project);
+
+    GroupDto sonarUsers = new GroupDto().setName("devs");
+    db.groupDao().insert(session, sonarUsers);
+
+    UserDto john = new UserDto().setLogin("john").setName("John").setActive(true);
+    db.userDao().insert(session, john);
+
+    // Insert one permission
+    tester.get(PermissionFacade.class).insertGroupPermission(project.getId(), "devs", UserRole.USER, session);
+    db.issueAuthorizationDao().synchronizeAfter(session, new Date(0), ImmutableMap.of(IssueAuthorizationDao.PROJECT_KEY, project.key()));
+    session.commit();
+    assertThat(index.getByKey(project.getKey())).isNotNull();
+
+    // Delete the permission
+    tester.get(PermissionFacade.class).deleteGroupPermission(project.getId(), "devs", UserRole.USER, session);
+    db.issueAuthorizationDao().synchronizeAfter(session, new Date(0), ImmutableMap.of(IssueAuthorizationDao.PROJECT_KEY, project.key()));
+    session.commit();
+    assertThat(index.getNullableByKey(project.getKey())).isNull();
+  }
+
   @Test
   public void delete_index() throws Exception {
     project = new ComponentDto()
index f2d10efe05edf37b16f77ab24d2532eafa6f0a83..3493a8e9ff14493500ca23f41408168d2bc7f3e1 100644 (file)
@@ -39,6 +39,7 @@ import org.sonar.core.persistence.DbSession;
 import org.sonar.core.rule.RuleDto;
 import org.sonar.core.user.GroupDto;
 import org.sonar.core.user.UserDto;
+import org.sonar.server.component.ComponentTesting;
 import org.sonar.server.component.db.ComponentDao;
 import org.sonar.server.db.DbClient;
 import org.sonar.server.exceptions.NotFoundException;
@@ -53,7 +54,6 @@ import org.sonar.server.user.MockUserSession;
 
 import java.util.Date;
 import java.util.List;
-import java.util.UUID;
 
 import static com.google.common.collect.Lists.newArrayList;
 import static org.fest.assertions.Assertions.assertThat;
@@ -82,16 +82,10 @@ public class IssueIndexMediumTest {
     rule = RuleTesting.newXooX1();
     tester.get(RuleDao.class).insert(session, rule);
 
-    project = new ComponentDto()
-      .setId(1L)
-      .setKey("MyProject")
-      .setProjectId_unit_test_only(1L);
+    project = ComponentTesting.newProjectDto();
     tester.get(ComponentDao.class).insert(session, project);
 
-    file = new ComponentDto()
-      .setProjectId_unit_test_only(1L)
-      .setKey("MyComponent")
-      .setId(2L);
+    file = ComponentTesting.newFileDto(project);
     tester.get(ComponentDao.class).insert(session, file);
 
     // project can be seen by anyone
@@ -111,7 +105,7 @@ public class IssueIndexMediumTest {
 
   @Test
   public void get_by_key() throws Exception {
-    IssueDto issue = createIssue();
+    IssueDto issue = IssueTesting.newDto(rule, file, project);
     db.issueDao().insert(session, issue);
     session.commit();
 
@@ -121,7 +115,7 @@ public class IssueIndexMediumTest {
 
   @Test
   public void get_by_key_with_attributes() throws Exception {
-    IssueDto issue = createIssue();
+    IssueDto issue = IssueTesting.newDto(rule, file, project);
     db.issueDao().insert(session, issue).setIssueAttributes(KeyValueFormat.format(ImmutableMap.of("jira-issue-key", "SONAR-1234")));
     session.commit();
 
@@ -133,7 +127,7 @@ public class IssueIndexMediumTest {
 
   @Test(expected = IllegalStateException.class)
   public void comments_field_is_not_available() throws Exception {
-    IssueDto issue = createIssue();
+    IssueDto issue = IssueTesting.newDto(rule, file, project);
     db.issueDao().insert(session, issue);
     session.commit();
 
@@ -143,7 +137,7 @@ public class IssueIndexMediumTest {
 
   @Test(expected = IllegalStateException.class)
   public void is_new_field_is_not_available() throws Exception {
-    IssueDto issue = createIssue();
+    IssueDto issue = IssueTesting.newDto(rule, file, project);
     db.issueDao().insert(session, issue);
     session.commit();
 
@@ -159,8 +153,8 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_keys() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setKee("1"),
-      createIssue().setKee("2"));
+      IssueTesting.newDto(rule, file, project).setKee("1"),
+      IssueTesting.newDto(rule, file, project).setKee("2"));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().issueKeys(newArrayList("1", "2")).build(), new QueryContext()).getHits()).hasSize(2);
@@ -171,7 +165,7 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_projects() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setRootComponentKey(project.key()));
+      IssueTesting.newDto(rule, file, project).setRootComponentKey(project.key()));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().componentRoots(newArrayList(project.key())).build(), new QueryContext()).getHits()).hasSize(1);
@@ -182,8 +176,8 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_components() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setComponentKey("file1"),
-      createIssue().setComponentKey("file2"));
+      IssueTesting.newDto(rule, file, project).setComponentKey("file1"),
+      IssueTesting.newDto(rule, file, project).setComponentKey("file2"));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().components(newArrayList("file1", "file2")).build(), new QueryContext()).getHits()).hasSize(2);
@@ -195,8 +189,8 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_severities() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setSeverity(Severity.INFO),
-      createIssue().setSeverity(Severity.MAJOR));
+      IssueTesting.newDto(rule, file, project).setSeverity(Severity.INFO),
+      IssueTesting.newDto(rule, file, project).setSeverity(Severity.MAJOR));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().severities(newArrayList(Severity.INFO, Severity.MAJOR)).build(), new QueryContext()).getHits()).hasSize(2);
@@ -207,8 +201,8 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_statuses() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setStatus(Issue.STATUS_CLOSED),
-      createIssue().setStatus(Issue.STATUS_OPEN));
+      IssueTesting.newDto(rule, file, project).setStatus(Issue.STATUS_CLOSED),
+      IssueTesting.newDto(rule, file, project).setStatus(Issue.STATUS_OPEN));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().statuses(newArrayList(Issue.STATUS_CLOSED, Issue.STATUS_OPEN)).build(), new QueryContext()).getHits()).hasSize(2);
@@ -219,8 +213,8 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_resolutions() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setResolution(Issue.RESOLUTION_FALSE_POSITIVE),
-      createIssue().setResolution(Issue.RESOLUTION_FIXED));
+      IssueTesting.newDto(rule, file, project).setResolution(Issue.RESOLUTION_FALSE_POSITIVE),
+      IssueTesting.newDto(rule, file, project).setResolution(Issue.RESOLUTION_FIXED));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().resolutions(newArrayList(Issue.RESOLUTION_FALSE_POSITIVE, Issue.RESOLUTION_FIXED)).build(), new QueryContext()).getHits())
@@ -232,9 +226,9 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_resolved() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setStatus(Issue.STATUS_CLOSED).setResolution(Issue.RESOLUTION_FIXED),
-      createIssue().setStatus(Issue.STATUS_OPEN).setResolution(null),
-      createIssue().setStatus(Issue.STATUS_OPEN).setResolution(null));
+      IssueTesting.newDto(rule, file, project).setStatus(Issue.STATUS_CLOSED).setResolution(Issue.RESOLUTION_FIXED),
+      IssueTesting.newDto(rule, file, project).setStatus(Issue.STATUS_OPEN).setResolution(null),
+      IssueTesting.newDto(rule, file, project).setStatus(Issue.STATUS_OPEN).setResolution(null));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().resolved(true).build(), new QueryContext()).getHits()).hasSize(1);
@@ -245,8 +239,8 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_action_plans() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setActionPlanKey("plan1"),
-      createIssue().setActionPlanKey("plan2"));
+      IssueTesting.newDto(rule, file, project).setActionPlanKey("plan1"),
+      IssueTesting.newDto(rule, file, project).setActionPlanKey("plan2"));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().actionPlans(newArrayList("plan1")).build(), new QueryContext()).getHits()).hasSize(1);
@@ -257,9 +251,9 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_planned() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setActionPlanKey("AP-KEY"),
-      createIssue().setActionPlanKey(null),
-      createIssue().setActionPlanKey(null));
+      IssueTesting.newDto(rule, file, project).setActionPlanKey("AP-KEY"),
+      IssueTesting.newDto(rule, file, project).setActionPlanKey(null),
+      IssueTesting.newDto(rule, file, project).setActionPlanKey(null));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().planned(true).build(), new QueryContext()).getHits()).hasSize(1);
@@ -269,7 +263,7 @@ public class IssueIndexMediumTest {
 
   @Test
   public void filter_by_rules() throws Exception {
-    db.issueDao().insert(session, createIssue().setRule(rule));
+    db.issueDao().insert(session, IssueTesting.newDto(rule, file, project).setRule(rule));
 
     tester.get(RuleDao.class).insert(session, RuleTesting.newDto(RuleKey.of("rule", "without issue")));
     session.commit();
@@ -280,7 +274,7 @@ public class IssueIndexMediumTest {
 
   @Test
   public void filter_by_languages() throws Exception {
-    db.issueDao().insert(session, createIssue().setRule(rule));
+    db.issueDao().insert(session, IssueTesting.newDto(rule, file, project).setRule(rule));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().languages(newArrayList(rule.getLanguage())).build(), new QueryContext()).getHits()).hasSize(1);
@@ -290,9 +284,9 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_assignees() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setAssignee("steph"),
-      createIssue().setAssignee("simon"),
-      createIssue());
+      IssueTesting.newDto(rule, file, project).setAssignee("steph"),
+      IssueTesting.newDto(rule, file, project).setAssignee("simon"),
+      IssueTesting.newDto(rule, file, project));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().assignees(newArrayList("steph")).build(), new QueryContext()).getHits()).hasSize(1);
@@ -303,9 +297,9 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_assigned() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setAssignee("steph"),
-      createIssue().setAssignee(null),
-      createIssue().setAssignee(null));
+      IssueTesting.newDto(rule, file, project).setAssignee("steph"),
+      IssueTesting.newDto(rule, file, project).setAssignee(null),
+      IssueTesting.newDto(rule, file, project).setAssignee(null));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().assigned(true).build(), new QueryContext()).getHits()).hasSize(1);
@@ -316,8 +310,8 @@ public class IssueIndexMediumTest {
   @Test
   public void filter_by_reporters() throws Exception {
     db.issueDao().insert(session,
-      createIssue().setReporter("fabrice"),
-      createIssue().setReporter("stephane"));
+      IssueTesting.newDto(rule, file, project).setReporter("fabrice"),
+      IssueTesting.newDto(rule, file, project).setReporter("stephane"));
     session.commit();
 
     assertThat(index.search(IssueQuery.builder().reporters(newArrayList("fabrice", "stephane")).build(), new QueryContext()).getHits()).hasSize(2);
@@ -327,8 +321,8 @@ public class IssueIndexMediumTest {
 
   @Test
   public void filter_by_created_after() throws Exception {
-    IssueDto issue1 = createIssue().setIssueCreationDate(DateUtils.parseDate("2014-09-20"));
-    IssueDto issue2 = createIssue().setIssueCreationDate(DateUtils.parseDate("2014-09-23"));
+    IssueDto issue1 = IssueTesting.newDto(rule, file, project).setIssueCreationDate(DateUtils.parseDate("2014-09-20"));
+    IssueDto issue2 = IssueTesting.newDto(rule, file, project).setIssueCreationDate(DateUtils.parseDate("2014-09-23"));
     db.issueDao().insert(session, issue1, issue2);
     session.commit();
 
@@ -340,8 +334,8 @@ public class IssueIndexMediumTest {
 
   @Test
   public void filter_by_created_before() throws Exception {
-    IssueDto issue1 = createIssue().setIssueCreationDate(DateUtils.parseDate("2014-09-20"));
-    IssueDto issue2 = createIssue().setIssueCreationDate(DateUtils.parseDate("2014-09-23"));
+    IssueDto issue1 = IssueTesting.newDto(rule, file, project).setIssueCreationDate(DateUtils.parseDate("2014-09-20"));
+    IssueDto issue2 = IssueTesting.newDto(rule, file, project).setIssueCreationDate(DateUtils.parseDate("2014-09-23"));
     db.issueDao().insert(session, issue1, issue2);
     session.commit();
 
@@ -353,7 +347,7 @@ public class IssueIndexMediumTest {
 
   @Test
   public void filter_by_created_at() throws Exception {
-    IssueDto issue = createIssue().setIssueCreationDate(DateUtils.parseDate("2014-09-20"));
+    IssueDto issue = IssueTesting.newDto(rule, file, project).setIssueCreationDate(DateUtils.parseDate("2014-09-20"));
     db.issueDao().insert(session, issue);
     session.commit();
 
@@ -364,7 +358,7 @@ public class IssueIndexMediumTest {
   @Test
   public void paging() throws Exception {
     for (int i = 0; i < 12; i++) {
-      IssueDto issue = createIssue();
+      IssueDto issue = IssueTesting.newDto(rule, file, project);
       tester.get(IssueDao.class).insert(session, issue);
     }
     session.commit();
@@ -387,7 +381,7 @@ public class IssueIndexMediumTest {
   @Test
   public void search_with_limit() throws Exception {
     for (int i = 0; i < 20; i++) {
-      IssueDto issue = createIssue();
+      IssueDto issue = IssueTesting.newDto(rule, file, project);
       tester.get(IssueDao.class).insert(session, issue);
     }
     session.commit();
@@ -398,7 +392,7 @@ public class IssueIndexMediumTest {
   public void search_with_max_limit() throws Exception {
     List<String> issueKeys = newArrayList();
     for (int i = 0; i < 500; i++) {
-      IssueDto issue = createIssue();
+      IssueDto issue = IssueTesting.newDto(rule, file, project);
       tester.get(IssueDao.class).insert(session, issue);
       issueKeys.add(issue.getKey());
     }
@@ -411,8 +405,8 @@ public class IssueIndexMediumTest {
 
   @Test
   public void sort_by_assignee() throws Exception {
-    IssueDto issue1 = createIssue().setAssignee("steph");
-    IssueDto issue2 = createIssue().setAssignee("simon");
+    IssueDto issue1 = IssueTesting.newDto(rule, file, project).setAssignee("steph");
+    IssueDto issue2 = IssueTesting.newDto(rule, file, project).setAssignee("simon");
     db.issueDao().insert(session, issue1, issue2);
     session.commit();
 
@@ -431,8 +425,8 @@ public class IssueIndexMediumTest {
 
   @Test
   public void sort_by_creation_date() throws Exception {
-    IssueDto issue1 = createIssue().setIssueCreationDate(DateUtils.parseDate("2014-09-23"));
-    IssueDto issue2 = createIssue().setIssueCreationDate(DateUtils.parseDate("2014-09-24"));
+    IssueDto issue1 = IssueTesting.newDto(rule, file, project).setIssueCreationDate(DateUtils.parseDate("2014-09-23"));
+    IssueDto issue2 = IssueTesting.newDto(rule, file, project).setIssueCreationDate(DateUtils.parseDate("2014-09-24"));
     db.issueDao().insert(session, issue1, issue2);
     session.commit();
 
@@ -451,8 +445,8 @@ public class IssueIndexMediumTest {
 
   @Test
   public void sort_by_update_date() throws Exception {
-    IssueDto issue1 = createIssue().setIssueUpdateDate(DateUtils.parseDate("2014-09-23"));
-    IssueDto issue2 = createIssue().setIssueUpdateDate(DateUtils.parseDate("2014-09-24"));
+    IssueDto issue1 = IssueTesting.newDto(rule, file, project).setIssueUpdateDate(DateUtils.parseDate("2014-09-23"));
+    IssueDto issue2 = IssueTesting.newDto(rule, file, project).setIssueUpdateDate(DateUtils.parseDate("2014-09-24"));
     db.issueDao().insert(session, issue1, issue2);
     session.commit();
 
@@ -471,9 +465,9 @@ public class IssueIndexMediumTest {
 
   @Test
   public void sort_by_close_date() throws Exception {
-    IssueDto issue1 = createIssue().setIssueCloseDate(DateUtils.parseDate("2014-09-23"));
-    IssueDto issue2 = createIssue().setIssueCloseDate(DateUtils.parseDate("2014-09-24"));
-    IssueDto issue3 = createIssue().setIssueCloseDate(null);
+    IssueDto issue1 = IssueTesting.newDto(rule, file, project).setIssueCloseDate(DateUtils.parseDate("2014-09-23"));
+    IssueDto issue2 = IssueTesting.newDto(rule, file, project).setIssueCloseDate(DateUtils.parseDate("2014-09-24"));
+    IssueDto issue3 = IssueTesting.newDto(rule, file, project).setIssueCloseDate(null);
     db.issueDao().insert(session, issue1, issue2, issue3);
     session.commit();
 
@@ -494,13 +488,15 @@ public class IssueIndexMediumTest {
 
   @Test
   public void authorized_issues_on_groups() throws Exception {
-    ComponentDto project1 = new ComponentDto()
-      .setId(10L)
-      .setKey("project1");
-    ComponentDto project2 = new ComponentDto()
-      .setId(11L)
-      .setKey("project2");
-    tester.get(ComponentDao.class).insert(session, project1, project2);
+    ComponentDto project1 = ComponentTesting.newProjectDto().setKey("project1");
+    ComponentDto project2 = ComponentTesting.newProjectDto().setKey("project2");
+    ComponentDto project3 = ComponentTesting.newProjectDto().setKey("project3");
+
+    ComponentDto file1 = ComponentTesting.newFileDto(project1).setKey("file1");
+    ComponentDto file2 = ComponentTesting.newFileDto(project1).setKey("file2");
+    ComponentDto file3 = ComponentTesting.newFileDto(project1).setKey("file3");
+
+    tester.get(ComponentDao.class).insert(session, project1, project2, project3, file1, file2, file3);
 
     // project1 can be seen by sonar-users
     GroupDto groupDto = new GroupDto().setName("sonar-users");
@@ -512,11 +508,14 @@ public class IssueIndexMediumTest {
     db.groupDao().insert(session, groupDto);
     tester.get(PermissionFacade.class).insertGroupPermission(project2.getId(), groupDto.getName(), UserRole.USER, session);
 
+    // project3 cannot be seen by anyone
+
     db.issueAuthorizationDao().synchronizeAfter(session, new Date(0));
 
-    IssueDto issue1 = createIssue().setRootComponent(project1);
-    IssueDto issue2 = createIssue().setRootComponent(project2);
-    db.issueDao().insert(session, issue1, issue2);
+    db.issueDao().insert(session,
+      IssueTesting.newDto(rule, file1, project1),
+      IssueTesting.newDto(rule, file2, project2),
+      IssueTesting.newDto(rule, file3, project3));
 
     session.commit();
     session.clearCache();
@@ -534,17 +533,22 @@ public class IssueIndexMediumTest {
 
     MockUserSession.set().setUserGroups("another group");
     assertThat(index.search(query.build(), new QueryContext()).getHits()).hasSize(0);
+
+    MockUserSession.set().setUserGroups("sonar-users", "sonar-admins");
+    assertThat(index.search(query.componentRoots(newArrayList(project3.key())).build(), new QueryContext()).getHits()).hasSize(0);
   }
 
   @Test
   public void authorized_issues_on_user() throws Exception {
-    ComponentDto project1 = new ComponentDto()
-      .setId(10L)
-      .setKey("project1");
-    ComponentDto project2 = new ComponentDto()
-      .setId(11L)
-      .setKey("project2");
-    tester.get(ComponentDao.class).insert(session, project1, project2);
+    ComponentDto project1 = ComponentTesting.newProjectDto().setKey("project1");
+    ComponentDto project2 = ComponentTesting.newProjectDto().setKey("project2");
+    ComponentDto project3 = ComponentTesting.newProjectDto().setKey("project3");
+
+    ComponentDto file1 = ComponentTesting.newFileDto(project1).setKey("file1");
+    ComponentDto file2 = ComponentTesting.newFileDto(project1).setKey("file2");
+    ComponentDto file3 = ComponentTesting.newFileDto(project1).setKey("file3");
+
+    tester.get(ComponentDao.class).insert(session, project1, project2, project3, file1, file2, file3);
 
     // project1 can be seen by john
     UserDto john = new UserDto().setLogin("john").setName("john").setActive(true);
@@ -556,11 +560,15 @@ public class IssueIndexMediumTest {
     db.userDao().insert(session, max);
     tester.get(PermissionFacade.class).insertUserPermission(project2.getId(), max.getId(), UserRole.USER, session);
 
+    // project3 cannot be seen by anyone
+
     db.issueAuthorizationDao().synchronizeAfter(session, new Date(0));
 
-    IssueDto issue1 = createIssue().setRootComponent(project1);
-    IssueDto issue2 = createIssue().setRootComponent(project2);
-    db.issueDao().insert(session, issue1, issue2);
+    db.issueDao().insert(session,
+      IssueTesting.newDto(rule, file1, project1),
+      IssueTesting.newDto(rule, file2, project2),
+      IssueTesting.newDto(rule, file2, project3)
+    );
 
     session.commit();
     session.clearCache();
@@ -575,16 +583,15 @@ public class IssueIndexMediumTest {
 
     MockUserSession.set().setLogin("another guy");
     assertThat(index.search(query.build(), new QueryContext()).getHits()).hasSize(0);
+
+    MockUserSession.set().setLogin("john");
+    assertThat(index.search(query.componentRoots(newArrayList(project3.key())).build(), new QueryContext()).getHits()).hasSize(0);
   }
 
   @Test
-  public void authorized_issues_on_user_with_group() throws Exception {
-    ComponentDto project1 = new ComponentDto()
-      .setId(10L)
-      .setKey("project1");
-    ComponentDto project2 = new ComponentDto()
-      .setId(11L)
-      .setKey("project2");
+  public void authorized_issues_on_user_and_group() throws Exception {
+    ComponentDto project1 = ComponentTesting.newProjectDto().setKey("project1");
+    ComponentDto project2 = ComponentTesting.newProjectDto().setKey("project2");
     tester.get(ComponentDao.class).insert(session, project1, project2);
 
     // project1 can be seen by john
@@ -599,9 +606,9 @@ public class IssueIndexMediumTest {
 
     db.issueAuthorizationDao().synchronizeAfter(session, new Date(0));
 
-    IssueDto issue1 = createIssue().setRootComponent(project1);
-    IssueDto issue2 = createIssue().setRootComponent(project2);
-    db.issueDao().insert(session, issue1, issue2);
+    db.issueDao().insert(session,
+      IssueTesting.newDto(rule, file, project1),
+      IssueTesting.newDto(rule, file, project2));
 
     session.commit();
     session.clearCache();
@@ -612,16 +619,4 @@ public class IssueIndexMediumTest {
     assertThat(index.search(query.build(), new QueryContext()).getHits()).hasSize(1);
   }
 
-  private IssueDto createIssue() {
-    return new IssueDto()
-      .setIssueCreationDate(DateUtils.parseDate("2014-09-04"))
-      .setIssueUpdateDate(DateUtils.parseDate("2014-12-04"))
-      .setRule(rule)
-      .setDebt(10L)
-      .setRootComponent(project)
-      .setComponent(file)
-      .setStatus("OPEN").setResolution("OPEN")
-      .setSeverity("MAJOR")
-      .setKee(UUID.randomUUID().toString());
-  }
 }
index 4a6a88f975eeaf77bac1d420caecedfc2419e5ae..4795da679ed58bce1545e8fa64c0fc069082746c 100644 (file)
@@ -31,6 +31,7 @@ import org.sonar.core.persistence.DbSession;
 import org.sonar.core.user.RoleDao;
 import org.sonar.core.user.UserDto;
 import org.sonar.server.db.DbClient;
+import org.sonar.server.issue.index.IssueAuthorizationDoc;
 import org.sonar.server.issue.index.IssueAuthorizationIndex;
 import org.sonar.server.tester.ServerTester;
 import org.sonar.server.user.MockUserSession;
@@ -55,7 +56,6 @@ public class InternalPermissionServiceMediumTest {
   InternalPermissionService service;
 
   ComponentDto project;
-  UserDto user;
 
   @Before
   public void setUp() throws Exception {
@@ -65,12 +65,8 @@ public class InternalPermissionServiceMediumTest {
     index = tester.get(IssueAuthorizationIndex.class);
     service = tester.get(InternalPermissionService.class);
 
-    user = new UserDto().setLogin("john").setName("John");
-    db.userDao().insert(session, user);
-
     project = new ComponentDto().setKey("Sample").setProjectId_unit_test_only(1L);
     db.componentDao().insert(session, project);
-
     session.commit();
   }
 
@@ -83,14 +79,75 @@ public class InternalPermissionServiceMediumTest {
   public void add_component_user_permission() throws Exception {
     MockUserSession.set().setLogin("admin").addProjectPermissions(UserRole.ADMIN, project.key());
 
+    UserDto user = new UserDto().setLogin("john").setName("John");
+    db.userDao().insert(session, user);
+    session.commit();
+
     assertThat(tester.get(RoleDao.class).selectUserPermissions(session, user.getLogin(), project.getId())).isEmpty();
     assertThat(index.getNullableByKey(project.getKey())).isNull();
 
     service.addPermission(params(user.getLogin(), null, project.key(), UserRole.USER));
     session.commit();
 
+    // Check in db
     assertThat(tester.get(RoleDao.class).selectUserPermissions(session, user.getLogin(), project.getId())).hasSize(1);
-    assertThat(index.getNullableByKey(project.getKey())).isNotNull();
+
+    // Check in index
+    IssueAuthorizationDoc issueAuthorizationDoc = index.getNullableByKey(project.getKey());
+    assertThat(issueAuthorizationDoc).isNotNull();
+    assertThat(issueAuthorizationDoc.project()).isEqualTo(project.getKey());
+    assertThat(issueAuthorizationDoc.permission()).isEqualTo(UserRole.USER);
+    assertThat(issueAuthorizationDoc.users()).containsExactly(user.getLogin());
+    assertThat(issueAuthorizationDoc.groups()).isEmpty();
+  }
+
+  @Test
+  public void remove_component_user_permission() throws Exception {
+    MockUserSession.set().setLogin("admin").addProjectPermissions(UserRole.ADMIN, project.key());
+
+    UserDto user1 = new UserDto().setLogin("user1").setName("User1");
+    db.userDao().insert(session, user1);
+
+    UserDto user2 = new UserDto().setLogin("user2").setName("User2");
+    db.userDao().insert(session, user2);
+    session.commit();
+
+    service.addPermission(params(user1.getLogin(), null, project.key(), UserRole.USER));
+    service.addPermission(params(user2.getLogin(), null, project.key(), UserRole.USER));
+    service.removePermission(params(user1.getLogin(), null, project.key(), UserRole.USER));
+    session.commit();
+
+    // Check in db
+    assertThat(tester.get(RoleDao.class).selectUserPermissions(session, user1.getLogin(), project.getId())).isEmpty();
+    assertThat(tester.get(RoleDao.class).selectUserPermissions(session, user2.getLogin(), project.getId())).hasSize(1);
+
+    // Check in index
+    IssueAuthorizationDoc issueAuthorizationDoc = index.getNullableByKey(project.getKey());
+    assertThat(issueAuthorizationDoc).isNotNull();
+    assertThat(issueAuthorizationDoc.project()).isEqualTo(project.getKey());
+    assertThat(issueAuthorizationDoc.permission()).isEqualTo(UserRole.USER);
+    assertThat(issueAuthorizationDoc.users()).containsExactly(user2.getLogin());
+    assertThat(issueAuthorizationDoc.groups()).isEmpty();
+  }
+
+  @Test
+  public void remove_all_component_user_permissions() throws Exception {
+    MockUserSession.set().setLogin("admin").addProjectPermissions(UserRole.ADMIN, project.key());
+
+    UserDto user = new UserDto().setLogin("user1").setName("User1");
+    db.userDao().insert(session, user);
+    session.commit();
+
+    service.addPermission(params(user.getLogin(), null, project.key(), UserRole.USER));
+    service.removePermission(params(user.getLogin(), null, project.key(), UserRole.USER));
+    session.commit();
+
+    // Check in db
+    assertThat(tester.get(RoleDao.class).selectUserPermissions(session, user.getLogin(), project.getId())).isEmpty();
+
+    // Check in index
+    IssueAuthorizationDoc issueAuthorizationDoc = index.getNullableByKey(project.getKey());
+    assertThat(issueAuthorizationDoc).isNull();
   }
 
   private Map<String, Object> params(@Nullable String login, @Nullable String group, @Nullable String component, String permission) {