aboutsummaryrefslogtreecommitdiffstats
path: root/server
diff options
context:
space:
mode:
authorJulien HENRY <julien.henry@sonarsource.com>2017-10-11 12:07:37 +0200
committerJulien HENRY <julien.henry@sonarsource.com>2017-10-20 18:45:15 +1000
commit777701594f14b0886684d1d81bf32539a7522146 (patch)
treef17366d12b04ba7dee87c01f03f4596e293ca08f /server
parentd41338e67fd95bfe18aa7bcf10e50b98898928c2 (diff)
downloadsonarqube-777701594f14b0886684d1d81bf32539a7522146.tar.gz
sonarqube-777701594f14b0886684d1d81bf32539a7522146.zip
SONAR-9913 Match issues from short living branches more aggressively
When there are multiple candidates (from multiple branches), prefer any of the RESOLVED one, before taking any of the CONFIRMED ones.
Diffstat (limited to 'server')
-rw-r--r--server/sonar-db-dao/src/main/java/org/sonar/core/issue/ShortBranchIssue.java1
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/container/ProjectAnalysisTaskContainerPopulator.java8
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitor.java4
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ShortBranchIssueStatusCopier.java (renamed from server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/IssueStatusCopier.java)11
-rw-r--r--server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ShortBranchIssuesLoader.java (renamed from server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ResolvedShortBranchIssuesLoader.java)6
-rw-r--r--server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitorTest.java2
-rw-r--r--server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/ShortBranchIssueStatusCopierTest.java (renamed from server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/IssueStatusCopierTest.java)45
7 files changed, 48 insertions, 29 deletions
diff --git a/server/sonar-db-dao/src/main/java/org/sonar/core/issue/ShortBranchIssue.java b/server/sonar-db-dao/src/main/java/org/sonar/core/issue/ShortBranchIssue.java
index f13c0167797..0e2f88f94b9 100644
--- a/server/sonar-db-dao/src/main/java/org/sonar/core/issue/ShortBranchIssue.java
+++ b/server/sonar-db-dao/src/main/java/org/sonar/core/issue/ShortBranchIssue.java
@@ -65,6 +65,7 @@ public class ShortBranchIssue implements Trackable {
return ruleKey;
}
+ @Override
public String getStatus() {
return status;
}
diff --git a/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/container/ProjectAnalysisTaskContainerPopulator.java b/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/container/ProjectAnalysisTaskContainerPopulator.java
index 267a4523e0f..2e5be262543 100644
--- a/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/container/ProjectAnalysisTaskContainerPopulator.java
+++ b/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/container/ProjectAnalysisTaskContainerPopulator.java
@@ -64,7 +64,7 @@ import org.sonar.server.computation.task.projectanalysis.issue.IssueCache;
import org.sonar.server.computation.task.projectanalysis.issue.IssueCounter;
import org.sonar.server.computation.task.projectanalysis.issue.IssueCreationDateCalculator;
import org.sonar.server.computation.task.projectanalysis.issue.IssueLifecycle;
-import org.sonar.server.computation.task.projectanalysis.issue.IssueStatusCopier;
+import org.sonar.server.computation.task.projectanalysis.issue.ShortBranchIssueStatusCopier;
import org.sonar.server.computation.task.projectanalysis.issue.IssueTrackingDelegator;
import org.sonar.server.computation.task.projectanalysis.issue.IssueVisitors;
import org.sonar.server.computation.task.projectanalysis.issue.IssuesRepositoryVisitor;
@@ -73,7 +73,7 @@ import org.sonar.server.computation.task.projectanalysis.issue.MergeBranchTracke
import org.sonar.server.computation.task.projectanalysis.issue.MovedIssueVisitor;
import org.sonar.server.computation.task.projectanalysis.issue.NewEffortAggregator;
import org.sonar.server.computation.task.projectanalysis.issue.RemoveProcessedComponentsVisitor;
-import org.sonar.server.computation.task.projectanalysis.issue.ResolvedShortBranchIssuesLoader;
+import org.sonar.server.computation.task.projectanalysis.issue.ShortBranchIssuesLoader;
import org.sonar.server.computation.task.projectanalysis.issue.RuleRepositoryImpl;
import org.sonar.server.computation.task.projectanalysis.issue.RuleTagsCopier;
import org.sonar.server.computation.task.projectanalysis.issue.RuleTypeCopier;
@@ -252,8 +252,8 @@ public final class ProjectAnalysisTaskContainerPopulator implements ContainerPop
BaseIssuesLoader.class,
IssueTrackingDelegator.class,
BranchPersister.class,
- ResolvedShortBranchIssuesLoader.class,
- IssueStatusCopier.class,
+ ShortBranchIssuesLoader.class,
+ ShortBranchIssueStatusCopier.class,
// filemove
SourceSimilarityImpl.class,
diff --git a/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitor.java b/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitor.java
index 76cbed32dcf..26db336fcf5 100644
--- a/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitor.java
+++ b/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitor.java
@@ -37,11 +37,11 @@ public class IntegrateIssuesVisitor extends TypeAwareVisitorAdapter {
private final IssueLifecycle issueLifecycle;
private final IssueVisitors issueVisitors;
private final IssueTrackingDelegator issueTracking;
- private final IssueStatusCopier issueStatusCopier;
+ private final ShortBranchIssueStatusCopier issueStatusCopier;
private final AnalysisMetadataHolder analysisMetadataHolder;
public IntegrateIssuesVisitor(IssueCache issueCache, IssueLifecycle issueLifecycle, IssueVisitors issueVisitors,
- AnalysisMetadataHolder analysisMetadataHolder, IssueTrackingDelegator issueTracking, IssueStatusCopier issueStatusCopier) {
+ AnalysisMetadataHolder analysisMetadataHolder, IssueTrackingDelegator issueTracking, ShortBranchIssueStatusCopier issueStatusCopier) {
super(CrawlerDepthLimit.FILE, POST_ORDER);
this.issueCache = issueCache;
this.issueLifecycle = issueLifecycle;
diff --git a/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/IssueStatusCopier.java b/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ShortBranchIssueStatusCopier.java
index 40f50c1d90c..8b49759aae6 100644
--- a/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/IssueStatusCopier.java
+++ b/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ShortBranchIssueStatusCopier.java
@@ -27,23 +27,24 @@ import org.sonar.core.issue.tracking.SimpleTracker;
import org.sonar.core.issue.tracking.Tracking;
import org.sonar.server.computation.task.projectanalysis.component.Component;
-public class IssueStatusCopier {
- private final ResolvedShortBranchIssuesLoader resolvedShortBranchIssuesLoader;
+public class ShortBranchIssueStatusCopier {
+ private final ShortBranchIssuesLoader resolvedShortBranchIssuesLoader;
private final SimpleTracker<DefaultIssue, ShortBranchIssue> tracker;
private final IssueLifecycle issueLifecycle;
- public IssueStatusCopier(ResolvedShortBranchIssuesLoader resolvedShortBranchIssuesLoader, IssueLifecycle issueLifecycle) {
+ public ShortBranchIssueStatusCopier(ShortBranchIssuesLoader resolvedShortBranchIssuesLoader, IssueLifecycle issueLifecycle) {
this(resolvedShortBranchIssuesLoader, new SimpleTracker<>(), issueLifecycle);
}
- public IssueStatusCopier(ResolvedShortBranchIssuesLoader resolvedShortBranchIssuesLoader, SimpleTracker<DefaultIssue, ShortBranchIssue> tracker, IssueLifecycle issueLifecycle) {
+ public ShortBranchIssueStatusCopier(ShortBranchIssuesLoader resolvedShortBranchIssuesLoader, SimpleTracker<DefaultIssue, ShortBranchIssue> tracker,
+ IssueLifecycle issueLifecycle) {
this.resolvedShortBranchIssuesLoader = resolvedShortBranchIssuesLoader;
this.tracker = tracker;
this.issueLifecycle = issueLifecycle;
}
public void updateStatus(Component component, Collection<DefaultIssue> newIssues) {
- Collection<ShortBranchIssue> shortBranchIssues = resolvedShortBranchIssuesLoader.create(component);
+ Collection<ShortBranchIssue> shortBranchIssues = resolvedShortBranchIssuesLoader.loadCandidateIssuesForMergingInTargetBranch(component);
Tracking<DefaultIssue, ShortBranchIssue> tracking = tracker.track(newIssues, shortBranchIssues);
for (Map.Entry<DefaultIssue, ShortBranchIssue> e : tracking.getMatchedRaws().entrySet()) {
diff --git a/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ResolvedShortBranchIssuesLoader.java b/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ShortBranchIssuesLoader.java
index 4e3e5c33af9..ebac0c2f982 100644
--- a/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ResolvedShortBranchIssuesLoader.java
+++ b/server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ShortBranchIssuesLoader.java
@@ -31,17 +31,17 @@ import org.sonar.db.issue.ShortBranchIssueDto;
import org.sonar.server.computation.task.projectanalysis.component.Component;
import org.sonar.server.computation.task.projectanalysis.component.ShortBranchComponentsWithIssues;
-public class ResolvedShortBranchIssuesLoader {
+public class ShortBranchIssuesLoader {
private final ShortBranchComponentsWithIssues shortBranchComponentsWithIssues;
private final DbClient dbClient;
- public ResolvedShortBranchIssuesLoader(ShortBranchComponentsWithIssues shortBranchComponentsWithIssues, DbClient dbClient) {
+ public ShortBranchIssuesLoader(ShortBranchComponentsWithIssues shortBranchComponentsWithIssues, DbClient dbClient) {
this.shortBranchComponentsWithIssues = shortBranchComponentsWithIssues;
this.dbClient = dbClient;
}
- public Collection<ShortBranchIssue> create(Component component) {
+ public Collection<ShortBranchIssue> loadCandidateIssuesForMergingInTargetBranch(Component component) {
String componentKey = ComponentDto.removeBranchFromKey(component.getKey());
Set<String> uuids = shortBranchComponentsWithIssues.getUuids(componentKey);
if (uuids.isEmpty()) {
diff --git a/server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitorTest.java b/server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitorTest.java
index 6dd63fa7f24..8f30a438333 100644
--- a/server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitorTest.java
+++ b/server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/IntegrateIssuesVisitorTest.java
@@ -113,7 +113,7 @@ public class IntegrateIssuesVisitorTest {
@Mock
private MergeBranchComponentUuids mergeBranchComponentsUuids;
@Mock
- private IssueStatusCopier issueStatusCopier;
+ private ShortBranchIssueStatusCopier issueStatusCopier;
ArgumentCaptor<DefaultIssue> defaultIssueCaptor;
diff --git a/server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/IssueStatusCopierTest.java b/server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/ShortBranchIssueStatusCopierTest.java
index 9716ed4dbca..c5948cfc60b 100644
--- a/server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/IssueStatusCopierTest.java
+++ b/server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/issue/ShortBranchIssueStatusCopierTest.java
@@ -19,11 +19,14 @@
*/
package org.sonar.server.computation.task.projectanalysis.issue;
+import java.util.Arrays;
import java.util.Collections;
+import javax.annotation.Nullable;
import org.junit.Before;
import org.junit.Test;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
+import org.sonar.api.issue.Issue;
import org.sonar.api.rule.RuleKey;
import org.sonar.core.issue.DefaultIssue;
import org.sonar.core.issue.ShortBranchIssue;
@@ -34,59 +37,73 @@ import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.verifyZeroInteractions;
import static org.mockito.Mockito.when;
-public class IssueStatusCopierTest {
+public class ShortBranchIssueStatusCopierTest {
@Mock
- private ResolvedShortBranchIssuesLoader resolvedShortBranchIssuesLoader;
+ private ShortBranchIssuesLoader resolvedShortBranchIssuesLoader;
@Mock
private IssueLifecycle issueLifecycle;
@Mock
private Component component;
private SimpleTracker<DefaultIssue, ShortBranchIssue> tracker = new SimpleTracker<>();
- private IssueStatusCopier copier;
+ private ShortBranchIssueStatusCopier copier;
@Before
public void setUp() {
MockitoAnnotations.initMocks(this);
- copier = new IssueStatusCopier(resolvedShortBranchIssuesLoader, tracker, issueLifecycle);
+ copier = new ShortBranchIssueStatusCopier(resolvedShortBranchIssuesLoader, tracker, issueLifecycle);
}
@Test
public void do_nothing_if_no_match() {
- when(resolvedShortBranchIssuesLoader.create(component)).thenReturn(Collections.emptyList());
- DefaultIssue i = createIssue("issue1", "rule1");
+ when(resolvedShortBranchIssuesLoader.loadCandidateIssuesForMergingInTargetBranch(component)).thenReturn(Collections.emptyList());
+ DefaultIssue i = createIssue("issue1", "rule1", Issue.STATUS_CONFIRMED, null);
copier.updateStatus(component, Collections.singleton(i));
- verify(resolvedShortBranchIssuesLoader).create(component);
+ verify(resolvedShortBranchIssuesLoader).loadCandidateIssuesForMergingInTargetBranch(component);
verifyZeroInteractions(issueLifecycle);
}
@Test
public void do_nothing_if_no_new_issue() {
- DefaultIssue i = createIssue("issue1", "rule1");
- when(resolvedShortBranchIssuesLoader.create(component)).thenReturn(Collections.singleton(newShortBranchIssue(i)));
+ DefaultIssue i = createIssue("issue1", "rule1", Issue.STATUS_CONFIRMED, null);
+ when(resolvedShortBranchIssuesLoader.loadCandidateIssuesForMergingInTargetBranch(component)).thenReturn(Collections.singleton(newShortBranchIssue(i)));
copier.updateStatus(component, Collections.emptyList());
- verify(resolvedShortBranchIssuesLoader).create(component);
+ verify(resolvedShortBranchIssuesLoader).loadCandidateIssuesForMergingInTargetBranch(component);
verifyZeroInteractions(issueLifecycle);
}
@Test
public void update_status_on_matches() {
- ShortBranchIssue shortBranchIssue = newShortBranchIssue(createIssue("issue1", "rule1"));
- DefaultIssue newIssue = createIssue("issue2", "rule1");
+ ShortBranchIssue shortBranchIssue = newShortBranchIssue(createIssue("issue1", "rule1", Issue.STATUS_CONFIRMED, null));
+ DefaultIssue newIssue = createIssue("issue2", "rule1", Issue.STATUS_OPEN, null);
- when(resolvedShortBranchIssuesLoader.create(component)).thenReturn(Collections.singleton(shortBranchIssue));
+ when(resolvedShortBranchIssuesLoader.loadCandidateIssuesForMergingInTargetBranch(component)).thenReturn(Collections.singleton(shortBranchIssue));
copier.updateStatus(component, Collections.singleton(newIssue));
verify(issueLifecycle).copyResolution(newIssue, shortBranchIssue.getStatus(), shortBranchIssue.getResolution());
}
- private static DefaultIssue createIssue(String key, String ruleKey) {
+ @Test
+ public void prefer_resolved_issues() {
+ ShortBranchIssue shortBranchIssue1 = newShortBranchIssue(createIssue("issue1", "rule1", Issue.STATUS_CONFIRMED, null));
+ ShortBranchIssue shortBranchIssue2 = newShortBranchIssue(createIssue("issue2", "rule1", Issue.STATUS_CONFIRMED, null));
+ ShortBranchIssue shortBranchIssue3 = newShortBranchIssue(createIssue("issue3", "rule1", Issue.STATUS_RESOLVED, Issue.RESOLUTION_FALSE_POSITIVE));
+ DefaultIssue newIssue = createIssue("newIssue", "rule1", Issue.STATUS_OPEN, null);
+
+ when(resolvedShortBranchIssuesLoader.loadCandidateIssuesForMergingInTargetBranch(component)).thenReturn(Arrays.asList(shortBranchIssue1, shortBranchIssue2, shortBranchIssue3));
+ copier.updateStatus(component, Collections.singleton(newIssue));
+ verify(issueLifecycle).copyResolution(newIssue, Issue.STATUS_RESOLVED, Issue.RESOLUTION_FALSE_POSITIVE);
+ }
+
+ private static DefaultIssue createIssue(String key, String ruleKey, String status, @Nullable String resolution) {
DefaultIssue issue = new DefaultIssue();
issue.setKey(key);
issue.setRuleKey(RuleKey.of("repo", ruleKey));
issue.setMessage("msg");
issue.setLine(1);
+ issue.setStatus(status);
+ issue.setResolution(resolution);
return issue;
}