From 46aa95c524ab9bb753c38de7ed4bc3ec9674de46 Mon Sep 17 00:00:00 2001 From: Simon Brandhof Date: Thu, 16 Aug 2018 00:20:01 +0200 Subject: [PATCH] SONAR-9904 fix author of issue to not depend on analyzer implementations The Xoo plugin used in QA tests declares the component on all the issue locations. That is not the case with SonarJava for instance. It assumes that the component is the one declared on the issue. --- .../projectanalysis/issue/IssueLocations.java | 10 ++++++- .../issue/IssueLocationsTest.java | 27 ++++++++++++++++--- 2 files changed, 32 insertions(+), 5 deletions(-) diff --git a/server/sonar-ce-task-projectanalysis/src/main/java/org/sonar/ce/task/projectanalysis/issue/IssueLocations.java b/server/sonar-ce-task-projectanalysis/src/main/java/org/sonar/ce/task/projectanalysis/issue/IssueLocations.java index ed356f02427..d5de3e02ab8 100644 --- a/server/sonar-ce-task-projectanalysis/src/main/java/org/sonar/ce/task/projectanalysis/issue/IssueLocations.java +++ b/server/sonar-ce-task-projectanalysis/src/main/java/org/sonar/ce/task/projectanalysis/issue/IssueLocations.java @@ -22,6 +22,7 @@ package org.sonar.ce.task.projectanalysis.issue; import java.util.Objects; import java.util.stream.IntStream; import java.util.stream.Stream; +import org.apache.commons.lang.StringUtils; import org.sonar.core.issue.DefaultIssue; import org.sonar.db.protobuf.DbCommons; import org.sonar.db.protobuf.DbIssues; @@ -50,8 +51,15 @@ class IssueLocations { locations.hasTextRange() ? Stream.of(locations.getTextRange()) : Stream.empty(), locations.getFlowList().stream() .flatMap(f -> f.getLocationList().stream()) - .filter(l -> Objects.equals(l.getComponentId(), componentId)) + .filter(l -> Objects.equals(componentIdOf(issue, l), componentId)) .map(DbIssues.Location::getTextRange)); return textRanges.flatMapToInt(range -> IntStream.rangeClosed(range.getStartLine(), range.getEndLine())); } + + private static String componentIdOf(DefaultIssue issue, DbIssues.Location location) { + if (location.hasComponentId()) { + return StringUtils.defaultIfEmpty(location.getComponentId(), issue.componentUuid()); + } + return issue.componentUuid(); + } } diff --git a/server/sonar-ce-task-projectanalysis/src/test/java/org/sonar/ce/task/projectanalysis/issue/IssueLocationsTest.java b/server/sonar-ce-task-projectanalysis/src/test/java/org/sonar/ce/task/projectanalysis/issue/IssueLocationsTest.java index 4d23cf46457..4588e420d8e 100644 --- a/server/sonar-ce-task-projectanalysis/src/test/java/org/sonar/ce/task/projectanalysis/issue/IssueLocationsTest.java +++ b/server/sonar-ce-task-projectanalysis/src/test/java/org/sonar/ce/task/projectanalysis/issue/IssueLocationsTest.java @@ -19,8 +19,10 @@ */ package org.sonar.ce.task.projectanalysis.issue; +import javax.annotation.Nullable; import org.junit.Test; import org.sonar.core.issue.DefaultIssue; +import org.sonar.core.util.Protobuf; import org.sonar.db.protobuf.DbCommons; import org.sonar.db.protobuf.DbIssues; @@ -80,10 +82,27 @@ public class IssueLocationsTest { assertThat(IssueLocations.allLinesFor(issue, "file1")).isEmpty(); } - private static DbIssues.Location newLocation(String componentId, int startLine, int endLine) { - return DbIssues.Location.newBuilder() - .setComponentId(componentId) - .setTextRange(DbCommons.TextRange.newBuilder().setStartLine(startLine).setEndLine(endLine).build()) + @Test + public void allLinesFor_default_component_of_location_is_the_issue_component() { + DbIssues.Locations.Builder locations = DbIssues.Locations.newBuilder(); + locations.addFlowBuilder() + .addLocation(newLocation("", 5, 5)) + .addLocation(newLocation(null, 7, 7)) + .addLocation(newLocation("file2", 9, 9)) .build(); + DefaultIssue issue = new DefaultIssue() + .setComponentUuid("file1") + .setLocations(locations.build()); + + assertThat(IssueLocations.allLinesFor(issue, "file1")).containsExactlyInAnyOrder(5, 7); + assertThat(IssueLocations.allLinesFor(issue, "file2")).containsExactlyInAnyOrder(9); + assertThat(IssueLocations.allLinesFor(issue, "file3")).isEmpty(); + } + + private static DbIssues.Location newLocation(@Nullable String componentId, int startLine, int endLine) { + DbIssues.Location.Builder builder = DbIssues.Location.newBuilder() + .setTextRange(DbCommons.TextRange.newBuilder().setStartLine(startLine).setEndLine(endLine).build()); + Protobuf.setNullable(componentId, builder::setComponentId); + return builder.build(); } } -- 2.39.5