소스 검색

SONAR-6959 Performance improvements

* Avoid creation of intermediary array

* SONAR-6959 Speed-up copy of custom measures in Compute Engine

* Use light object to get key/uuid map of components

* Avoid always formatting string

* Minor refactoring

* Avoid cost of hash

* Ajust perf tests
tags/6.6-RC1
Duarte Meneses 6 년 전
부모
커밋
8115d8b7e4
20개의 변경된 파일163개의 추가작업 그리고 79개의 파일을 삭제
  1. 2
    0
      server/sonar-db-dao/src/main/java/org/sonar/db/MyBatis.java
  2. 5
    1
      server/sonar-db-dao/src/main/java/org/sonar/db/component/ComponentDao.java
  3. 5
    0
      server/sonar-db-dao/src/main/java/org/sonar/db/component/ComponentMapper.java
  4. 42
    0
      server/sonar-db-dao/src/main/java/org/sonar/db/component/KeyWithUuidDto.java
  5. 9
    0
      server/sonar-db-dao/src/main/resources/org/sonar/db/component/ComponentMapper.xml
  6. 30
    0
      server/sonar-db-dao/src/test/java/org/sonar/db/component/ComponentDaoTest.java
  7. 6
    7
      server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/component/ComponentImpl.java
  8. 4
    2
      server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/component/ComponentTreeBuilder.java
  9. 4
    4
      server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/component/ComponentUuidFactory.java
  10. 1
    3
      server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/filemove/FileMoveDetectionStep.java
  11. 2
    2
      server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ComponentIssuesRepositoryImpl.java
  12. 11
    15
      server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/measure/MapBasedRawMeasureRepository.java
  13. 2
    2
      server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/source/SymbolsLineReader.java
  14. 15
    13
      server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/step/CustomMeasuresCopyStep.java
  15. 1
    4
      server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/step/PersistMeasuresStep.java
  16. 2
    1
      server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/component/ComponentImplTest.java
  17. 13
    13
      server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/step/CustomMeasuresCopyStepTest.java
  18. 2
    3
      sonar-core/src/main/java/org/sonar/core/issue/DefaultIssue.java
  19. 6
    8
      sonar-plugin-api/src/main/java/org/sonar/api/ce/measure/RangeDistributionBuilder.java
  20. 1
    1
      tests/src/test/java/org/sonarqube/tests/performance/scanner/MemoryTest.java

+ 2
- 0
server/sonar-db-dao/src/main/java/org/sonar/db/MyBatis.java 파일 보기

@@ -43,6 +43,7 @@ import org.sonar.db.component.ComponentLinkDto;
import org.sonar.db.component.ComponentLinkMapper;
import org.sonar.db.component.ComponentMapper;
import org.sonar.db.component.FilePathWithHashDto;
import org.sonar.db.component.KeyWithUuidDto;
import org.sonar.db.component.ResourceDto;
import org.sonar.db.component.SnapshotDto;
import org.sonar.db.component.SnapshotMapper;
@@ -150,6 +151,7 @@ public class MyBatis implements Startable {
confBuilder.loadAlias("DuplicationUnit", DuplicationUnitDto.class);
confBuilder.loadAlias("Event", EventDto.class);
confBuilder.loadAlias("FilePathWithHash", FilePathWithHashDto.class);
confBuilder.loadAlias("KeyWithUuid", KeyWithUuidDto.class);
confBuilder.loadAlias("Group", GroupDto.class);
confBuilder.loadAlias("GroupMembership", GroupMembershipDto.class);
confBuilder.loadAlias("GroupPermission", GroupPermissionDto.class);

+ 5
- 1
server/sonar-db-dao/src/main/java/org/sonar/db/component/ComponentDao.java 파일 보기

@@ -164,6 +164,10 @@ public class ComponentDao implements Dao {
return mapper(session).selectComponentsFromProjectKeyAndScope(projectKey, null, false);
}

public List<KeyWithUuidDto> selectUuidsByKeyFromProjectKey(DbSession session, String projectKey) {
return mapper(session).selectUuidsByKeyFromProjectKey(projectKey);
}

public List<ComponentDto> selectEnabledModulesFromProjectKey(DbSession session, String projectKey) {
return mapper(session).selectComponentsFromProjectKeyAndScope(projectKey, Scopes.PROJECT, true);
}
@@ -174,7 +178,7 @@ public class ComponentDao implements Dao {

public List<ComponentDto> selectByKeysAndBranch(DbSession session, Collection<String> keys, String branch) {
List<String> dbKeys = keys.stream().map(k -> generateBranchKey(k, branch)).collect(toList());
List<String> allKeys = Stream.of(keys, dbKeys) .flatMap(Collection::stream) .collect(toList());
List<String> allKeys = Stream.of(keys, dbKeys).flatMap(Collection::stream).collect(toList());
return executeLargeInputs(allKeys, subKeys -> mapper(session).selectByKeysAndBranch(subKeys, branch));
}


+ 5
- 0
server/sonar-db-dao/src/main/java/org/sonar/db/component/ComponentMapper.java 파일 보기

@@ -116,6 +116,11 @@ public interface ComponentMapper {
List<ComponentDto> selectComponentsFromProjectKeyAndScope(@Param("projectKey") String projectKey, @Nullable @Param("scope") String scope,
@Param(value = "excludeDisabled") boolean excludeDisabled);

/**
* Return keys and UUIDs of all components belonging to a project
*/
List<KeyWithUuidDto> selectUuidsByKeyFromProjectKey(@Param("projectKey") String projectKey);

/**
* Return technical projects from a view or a sub-view
*/

+ 42
- 0
server/sonar-db-dao/src/main/java/org/sonar/db/component/KeyWithUuidDto.java 파일 보기

@@ -0,0 +1,42 @@
/*
* SonarQube
* Copyright (C) 2009-2017 SonarSource SA
* mailto:info AT sonarsource DOT com
*
* This program 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.
*
* This program 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.db.component;

import javax.annotation.concurrent.Immutable;

@Immutable
public class KeyWithUuidDto {

private final String kee;
private final String uuid;

public KeyWithUuidDto(String kee, String uuid) {
this.kee = kee;
this.uuid = uuid;
}

public String key() {
return kee;
}

public String uuid() {
return uuid;
}
}

+ 9
- 0
server/sonar-db-dao/src/main/resources/org/sonar/db/component/ComponentMapper.xml 파일 보기

@@ -414,6 +414,15 @@
</if>
</where>
</select>
<select id="selectUuidsByKeyFromProjectKey" parameterType="string" resultType="KeyWithUuid">
SELECT
p.kee, p.uuid
FROM
projects p
INNER JOIN
projects root ON root.uuid=p.project_uuid AND root.kee=#{projectKey,jdbcType=VARCHAR}
</select>

<select id="selectGhostProjects" parameterType="map" resultType="Component">
select distinct

+ 30
- 0
server/sonar-db-dao/src/test/java/org/sonar/db/component/ComponentDaoTest.java 파일 보기

@@ -27,6 +27,7 @@ import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.function.Supplier;
import java.util.stream.Collectors;
import javax.annotation.Nullable;
import org.assertj.core.api.ListAssert;
import org.junit.Rule;
@@ -47,6 +48,7 @@ import static java.util.Collections.emptyList;
import static java.util.Collections.emptySet;
import static java.util.Collections.singletonList;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.entry;
import static org.assertj.core.api.Assertions.tuple;
import static org.assertj.guava.api.Assertions.assertThat;
import static org.sonar.db.component.ComponentTesting.newDirectory;
@@ -580,6 +582,34 @@ public class ComponentDaoTest {
assertThat(underTest.selectAllComponentsFromProjectKey(dbSession, "UNKNOWN")).isEmpty();
}

@Test
public void select_uuids_by_key_from_project() {
ComponentDto project = db.components().insertPrivateProject();
ComponentDto removedProject = db.components().insertPrivateProject(p -> p.setEnabled(false));
ComponentDto module = db.components().insertComponent(newModuleDto(project));
ComponentDto removedModule = db.components().insertComponent(newModuleDto(project).setEnabled(false));
ComponentDto subModule = db.components().insertComponent(newModuleDto(module));
ComponentDto removedSubModule = db.components().insertComponent(newModuleDto(module).setEnabled(false));
ComponentDto directory = db.components().insertComponent(newDirectory(subModule, "src"));
ComponentDto removedDirectory = db.components().insertComponent(newDirectory(subModule, "src2").setEnabled(false));
ComponentDto file = db.components().insertComponent(newFileDto(subModule, directory));
ComponentDto removedFile = db.components().insertComponent(newFileDto(subModule, directory).setEnabled(false));

Map<String, String> uuidsByKey = underTest.selectUuidsByKeyFromProjectKey(dbSession, project.getDbKey())
.stream().collect(Collectors.toMap(KeyWithUuidDto::key, KeyWithUuidDto::uuid));

assertThat(uuidsByKey).containsOnly(
entry(project.getDbKey(), project.uuid()),
entry(module.getDbKey(), module.uuid()),
entry(removedModule.getDbKey(), removedModule.uuid()),
entry(subModule.getDbKey(), subModule.uuid()),
entry(removedSubModule.getDbKey(), removedSubModule.uuid()),
entry(directory.getDbKey(), directory.uuid()),
entry(removedDirectory.getDbKey(), removedDirectory.uuid()),
entry(file.getDbKey(), file.uuid()),
entry(removedFile.getDbKey(), removedFile.uuid()));
}

@Test
public void select_enabled_modules_from_project() {
ComponentDto project = db.components().insertPrivateProject();

+ 6
- 7
server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/component/ComponentImpl.java 파일 보기

@@ -28,7 +28,6 @@ import javax.annotation.concurrent.Immutable;

import static com.google.common.base.Preconditions.checkArgument;
import static com.google.common.base.Preconditions.checkState;
import static java.util.Arrays.asList;
import static java.util.Objects.requireNonNull;
import static org.apache.commons.lang.StringUtils.trimToNull;

@@ -66,7 +65,7 @@ public class ComponentImpl implements Component {
public Type getType() {
return type;
}
@Override
public Status getStatus() {
return status;
@@ -140,7 +139,7 @@ public class ComponentImpl implements Component {
private static final String REPORT_ATTRIBUTES_CANNOT_BE_NULL = "reportAttributes can't be null";
private static final String NAME_CANNOT_BE_NULL = "name can't be null";
private static final String STATUS_CANNOT_BE_NULL = "status can't be null";
private final Type type;
private Status status;
private ReportAttributes reportAttributes;
@@ -170,7 +169,7 @@ public class ComponentImpl implements Component {
public String getUuid() {
return uuid;
}
public Builder setStatus(Status status) {
this.status = requireNonNull(status, STATUS_CANNOT_BE_NULL);
return this;
@@ -201,11 +200,11 @@ public class ComponentImpl implements Component {
return this;
}

public Builder addChildren(Component... c) {
for (Component component : c) {
public Builder addChildren(List<Component> components) {
for (Component component : components) {
checkArgument(component.getType().isReportType());
}
this.children.addAll(asList(c));
this.children.addAll(components);
return this;
}


+ 4
- 2
server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/component/ComponentTreeBuilder.java 파일 보기

@@ -19,7 +19,9 @@
*/
package org.sonar.server.computation.task.projectanalysis.component;

import java.util.List;
import java.util.function.Function;
import java.util.stream.Collectors;
import javax.annotation.CheckForNull;
import javax.annotation.Nullable;
import org.sonar.db.component.SnapshotDto;
@@ -80,12 +82,12 @@ public class ComponentTreeBuilder {
return buildComponent(project, project);
}

private Component[] buildChildren(ScannerReport.Component component, ScannerReport.Component parentModule) {
private List<Component> buildChildren(ScannerReport.Component component, ScannerReport.Component parentModule) {
return component.getChildRefList()
.stream()
.map(scannerComponentSupplier::apply)
.map(c -> buildComponent(c, parentModule))
.toArray(Component[]::new);
.collect(Collectors.toList());
}

private ComponentImpl buildComponent(ScannerReport.Component component, ScannerReport.Component closestModule) {

+ 4
- 4
server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/component/ComponentUuidFactory.java 파일 보기

@@ -25,16 +25,16 @@ import java.util.Map;
import org.sonar.core.util.Uuids;
import org.sonar.db.DbClient;
import org.sonar.db.DbSession;
import org.sonar.db.component.ComponentDto;
import org.sonar.db.component.KeyWithUuidDto;

public class ComponentUuidFactory {

private final Map<String, String> uuidsByKey = new HashMap<>();

public ComponentUuidFactory(DbClient dbClient, DbSession dbSession, String rootKey) {
List<ComponentDto> components = dbClient.componentDao().selectAllComponentsFromProjectKey(dbSession, rootKey);
for (ComponentDto dto : components) {
uuidsByKey.put(dto.getDbKey(), dto.uuid());
List<KeyWithUuidDto> keys = dbClient.componentDao().selectUuidsByKeyFromProjectKey(dbSession, rootKey);
for (KeyWithUuidDto dto : keys) {
uuidsByKey.put(dto.key(), dto.uuid());
}
}


+ 1
- 3
server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/filemove/FileMoveDetectionStep.java 파일 보기

@@ -45,7 +45,6 @@ import org.sonar.db.component.ComponentDto;
import org.sonar.db.component.ComponentTreeQuery;
import org.sonar.db.component.ComponentTreeQuery.Strategy;
import org.sonar.db.source.FileSourceDto;
import org.sonar.server.computation.task.projectanalysis.analysis.Analysis;
import org.sonar.server.computation.task.projectanalysis.analysis.AnalysisMetadataHolder;
import org.sonar.server.computation.task.projectanalysis.component.Component;
import org.sonar.server.computation.task.projectanalysis.component.CrawlerDepthLimit;
@@ -93,8 +92,7 @@ public class FileMoveDetectionStep implements ComputationStep {
@Override
public void execute() {
// do nothing if no files in db (first analysis)
Analysis baseProjectAnalysis = analysisMetadataHolder.getBaseAnalysis();
if (baseProjectAnalysis == null) {
if (analysisMetadataHolder.isFirstAnalysis()) {
LOG.debug("First analysis. Do nothing.");
return;
}

+ 2
- 2
server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/issue/ComponentIssuesRepositoryImpl.java 파일 보기

@@ -46,8 +46,8 @@ public class ComponentIssuesRepositoryImpl implements MutableComponentIssuesRepo
public List<DefaultIssue> getIssues(Component component) {
checkState(this.component != null && this.issues != null, "Issues have not been initialized");
checkArgument(component.equals(this.component),
String.format("Only issues from component '%s' are available, but wanted component is '%s'.",
this.component.getReportAttributes().getRef(), component.getReportAttributes().getRef()));
"Only issues from component '%s' are available, but wanted component is '%s'.",
this.component.getReportAttributes().getRef(), component.getReportAttributes().getRef());
return issues;
}
}

+ 11
- 15
server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/measure/MapBasedRawMeasureRepository.java 파일 보기

@@ -19,28 +19,25 @@
*/
package org.sonar.server.computation.task.projectanalysis.measure;

import static com.google.common.base.Preconditions.checkArgument;
import static com.google.common.collect.FluentIterable.from;
import static java.lang.String.format;
import static java.util.Objects.requireNonNull;
import com.google.common.base.Function;
import com.google.common.base.Optional;
import com.google.common.base.Predicate;
import com.google.common.collect.ImmutableSetMultimap;
import com.google.common.collect.SetMultimap;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;

import javax.annotation.Nonnull;
import javax.annotation.Nullable;

import org.sonar.server.computation.task.projectanalysis.component.Component;
import org.sonar.server.computation.task.projectanalysis.metric.Metric;

import com.google.common.base.Function;
import com.google.common.base.Optional;
import com.google.common.base.Predicate;
import com.google.common.collect.ImmutableSetMultimap;
import com.google.common.collect.SetMultimap;
import static com.google.common.base.Preconditions.checkArgument;
import static com.google.common.collect.FluentIterable.from;
import static java.lang.String.format;
import static java.util.Objects.requireNonNull;

/**
* Map based implementation of MeasureRepository which supports only raw measures.
@@ -112,9 +109,8 @@ public final class MapBasedRawMeasureRepository<T> implements MeasureRepository
private static void checkValueTypeConsistency(Metric metric, Measure measure) {
checkArgument(
measure.getValueType() == Measure.ValueType.NO_VALUE || measure.getValueType() == metric.getType().getValueType(),
format(
"Measure's ValueType (%s) is not consistent with the Metric's ValueType (%s)",
measure.getValueType(), metric.getType().getValueType()));
"Measure's ValueType (%s) is not consistent with the Metric's ValueType (%s)",
measure.getValueType(), metric.getType().getValueType());
}

@Override

+ 2
- 2
server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/source/SymbolsLineReader.java 파일 보기

@@ -25,7 +25,7 @@ import com.google.common.collect.SetMultimap;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.IdentityHashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
@@ -115,7 +115,7 @@ public class SymbolsLineReader implements LineReader {
}

private static Map<ScannerReport.Symbol, Integer> createIdsBySymbolMap(List<ScannerReport.Symbol> symbols) {
Map<ScannerReport.Symbol, Integer> map = new HashMap<>(symbols.size());
Map<ScannerReport.Symbol, Integer> map = new IdentityHashMap<>(symbols.size());
int symbolId = 1;
for (ScannerReport.Symbol symbol : symbols) {
map.put(symbol, symbolId);

+ 15
- 13
server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/step/CustomMeasuresCopyStep.java 파일 보기

@@ -54,17 +54,21 @@ public class CustomMeasuresCopyStep implements ComputationStep {

@Override
public void execute() {
new DepthTraversalTypeAwareCrawler(
new TypeAwareVisitorAdapter(CrawlerDepthLimit.LEAVES, ComponentVisitor.Order.PRE_ORDER) {
@Override
public void visitAny(Component component) {
copy(component);
}
}).visit(treeRootHolder.getRoot());
try (DbSession session = dbClient.openSession(false)) {
CrawlerDepthLimit depthLimit = new CrawlerDepthLimit.Builder(Component.Type.MODULE)
.withViewsMaxDepth(Component.Type.PROJECT_VIEW);
new DepthTraversalTypeAwareCrawler(
new TypeAwareVisitorAdapter(depthLimit, ComponentVisitor.Order.PRE_ORDER) {
@Override
public void visitAny(Component component) {
copy(component, session);
}
}).visit(treeRootHolder.getRoot());
}
}

private void copy(Component component) {
for (CustomMeasureDto dto : loadCustomMeasures(component)) {
private void copy(Component component, DbSession session) {
for (CustomMeasureDto dto : loadCustomMeasures(component, session)) {
Metric metric = metricRepository.getById(dto.getMetricId());
// else metric is not found and an exception is raised
Measure measure = dtoToMeasure(dto, metric);
@@ -72,10 +76,8 @@ public class CustomMeasuresCopyStep implements ComputationStep {
}
}

private List<CustomMeasureDto> loadCustomMeasures(Component component) {
try (DbSession session = dbClient.openSession(false)) {
return dbClient.customMeasureDao().selectByComponentUuid(session, component.getUuid());
}
private List<CustomMeasureDto> loadCustomMeasures(Component component, DbSession session) {
return dbClient.customMeasureDao().selectByComponentUuid(session, component.getUuid());
}

@VisibleForTesting

+ 1
- 4
server/sonar-server/src/main/java/org/sonar/server/computation/task/projectanalysis/step/PersistMeasuresStep.java 파일 보기

@@ -82,12 +82,9 @@ public class PersistMeasuresStep implements ComputationStep {

@Override
public void execute() {
DbSession dbSession = dbClient.openSession(true);
try {
try (DbSession dbSession = dbClient.openSession(true)) {
new DepthTraversalTypeAwareCrawler(new MeasureVisitor(dbSession)).visit(treeRootHolder.getRoot());
dbSession.commit();
} finally {
dbSession.close();
}
}


+ 2
- 1
server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/component/ComponentImplTest.java 파일 보기

@@ -20,6 +20,7 @@
package org.sonar.server.computation.task.projectanalysis.component;

import java.util.Arrays;
import java.util.Collections;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.ExpectedException;
@@ -183,7 +184,7 @@ public class ComponentImplTest {
.setUuid(UUID)
.setStatus(Status.UNAVAILABLE)
.setReportAttributes(ReportAttributes.newBuilder(1).build())
.addChildren(child)
.addChildren(Collections.singletonList(child))
.build();

assertThat(componentImpl.getChildren()).hasSize(1);

+ 13
- 13
server/sonar-server/src/test/java/org/sonar/server/computation/task/projectanalysis/step/CustomMeasuresCopyStepTest.java 파일 보기

@@ -52,11 +52,11 @@ import static org.sonar.server.computation.task.projectanalysis.measure.MeasureR
import static org.sonar.server.computation.task.projectanalysis.measure.MeasureRepoEntry.toEntries;
import static org.sonar.server.computation.task.projectanalysis.step.CustomMeasuresCopyStep.dtoToMeasure;


public class CustomMeasuresCopyStepTest {

private static final int PROJECT_REF = 1;
private static final int MODULE_REF = 11;
private static final int MODULE2_REF = 12;
private static final int SUB_MODULE_REF = 111;
private static final int DIR_REF = 1111;
private static final int FILE1_REF = 11111;
@@ -64,6 +64,7 @@ public class CustomMeasuresCopyStepTest {

private static final String PROJECT_UUID = "PROJECT";
private static final String MODULE_UUID = "MODULE";
private static final String MODULE2_UUID = "MODULE2";
private static final String SUB_MODULE_UUID = "SUB_MODULE";
private static final String DIR_UUID = "DIR";
private static final String FILE1_UUID = "FILE1";
@@ -102,12 +103,12 @@ public class CustomMeasuresCopyStepTest {

@Test
public void copy_custom_measures_on_report() {
// File2 has no custom measure
insertCustomMeasure(FILE1_UUID, FLOAT_METRIC, 3.14);
insertCustomMeasure(DIR_UUID, FLOAT_METRIC, 123d);
insertCustomMeasure(SUB_MODULE_UUID, STRING_METRIC, "sub-module");
insertCustomMeasure(MODULE_UUID, STRING_METRIC, "module");
insertCustomMeasure(PROJECT_UUID, STRING_METRIC, "project");
// Module2 has no custom measure

treeRootHolder.setRoot(
builder(PROJECT, PROJECT_REF).setUuid(PROJECT_UUID)
@@ -119,23 +120,23 @@ public class CustomMeasuresCopyStepTest {
ReportComponent.builder(DIRECTORY, DIR_REF).setUuid(DIR_UUID)
.addChildren(
ReportComponent.builder(FILE, FILE1_REF).setUuid(FILE1_UUID).build(),
ReportComponent.builder(FILE, FILE2_REF).setUuid(FILE2_UUID).build()
)
.build()
)
.build()
)
.build())
ReportComponent.builder(FILE, FILE2_REF).setUuid(FILE2_UUID).build())
.build())
.build())
.build(),
ReportComponent.builder(MODULE, MODULE2_REF).setUuid(MODULE2_UUID).build())
.build());

underTest.execute();

assertRawMeasureValue(FILE1_REF, FLOAT_METRIC.getKey(), 3.1d);
assertNoRawMeasureValue(FILE1_REF);
assertNoRawMeasureValue(FILE2_REF);
assertRawMeasureValue(DIR_REF, FLOAT_METRIC.getKey(), 123d);
assertNoRawMeasureValue(DIR_REF);
assertRawMeasureValue(SUB_MODULE_REF, STRING_METRIC.getKey(), "sub-module");
assertRawMeasureValue(MODULE_REF, STRING_METRIC.getKey(), "module");
assertRawMeasureValue(PROJECT_REF, STRING_METRIC.getKey(), "project");
assertNoRawMeasureValue(MODULE2_REF);

}

@Test
@@ -148,8 +149,7 @@ public class CustomMeasuresCopyStepTest {
ViewsComponent.builder(VIEW, VIEW_REF).setUuid("VIEW")
.addChildren(
ViewsComponent.builder(SUBVIEW, SUBVIEW_REF).setUuid("SUBVIEW").build(),
ViewsComponent.builder(PROJECT_VIEW, PROJECT_VIEW_REF).setUuid("PROJECT_VIEW").build()
)
ViewsComponent.builder(PROJECT_VIEW, PROJECT_VIEW_REF).setUuid("PROJECT_VIEW").build())
.build());

underTest.execute();

+ 2
- 3
sonar-core/src/main/java/org/sonar/core/issue/DefaultIssue.java 파일 보기

@@ -48,7 +48,6 @@ import org.sonar.api.rules.RuleType;
import org.sonar.api.utils.Duration;
import org.sonar.core.issue.tracking.Trackable;

import static java.lang.String.format;
import static org.sonar.api.utils.DateUtils.truncateToSeconds;

public class DefaultIssue implements Issue, Trackable, org.sonar.api.ce.measure.Issue {
@@ -258,7 +257,7 @@ public class DefaultIssue implements Issue, Trackable, org.sonar.api.ce.measure.
}

public DefaultIssue setLine(@Nullable Integer l) {
Preconditions.checkArgument(l == null || l > 0, format("Line must be null or greater than zero (got %d)", l));
Preconditions.checkArgument(l == null || l > 0, "Line must be null or greater than zero (got %d)", l);
this.line = l;
return this;
}
@@ -280,7 +279,7 @@ public class DefaultIssue implements Issue, Trackable, org.sonar.api.ce.measure.
}

public DefaultIssue setGap(@Nullable Double d) {
Preconditions.checkArgument(d == null || d >= 0, format("Gap must be greater than or equal 0 (got %s)", d));
Preconditions.checkArgument(d == null || d >= 0, "Gap must be greater than or equal 0 (got %s)", d);
this.gap = d;
return this;
}

+ 6
- 8
sonar-plugin-api/src/main/java/org/sonar/api/ce/measure/RangeDistributionBuilder.java 파일 보기

@@ -93,8 +93,8 @@ public class RangeDistributionBuilder {
*/
public RangeDistributionBuilder add(String data) {
Map<Double, Double> map = KeyValueFormat.parse(data, KeyValueFormat.newDoubleConverter(), KeyValueFormat.newDoubleConverter());
Number[] limits = map.keySet().toArray(new Number[map.size()]);
if (bottomLimits == null) {
Number[] limits = map.keySet().toArray(new Number[map.size()]);
init(limits);

} else if (!areSameLimits(bottomLimits, map.keySet())) {
@@ -118,16 +118,14 @@ public class RangeDistributionBuilder {
}

private void changeDoublesToInts() {
boolean onlyInts = true;
for (Number bottomLimit : bottomLimits) {
if (NumberComparator.INSTANCE.compare(bottomLimit.intValue(), bottomLimit.doubleValue()) != 0) {
onlyInts = false;
// it's not only ints
return;
}
}
if (onlyInts) {
for (int i = 0; i < bottomLimits.length; i++) {
bottomLimits[i] = bottomLimits[i].intValue();
}
for (int i = 0; i < bottomLimits.length; i++) {
bottomLimits[i] = bottomLimits[i].intValue();
}
}

@@ -204,7 +202,7 @@ public class RangeDistributionBuilder {

@Override
public int compare(Number n1, Number n2) {
return ((Double) n1.doubleValue()).compareTo(n2.doubleValue());
return Double.compare(n1.doubleValue(), n2.doubleValue());
}
}


+ 1
- 1
tests/src/test/java/org/sonarqube/tests/performance/scanner/MemoryTest.java 파일 보기

@@ -89,7 +89,7 @@ public class MemoryTest extends AbstractPerfTest {
.setProjectDir(baseDir);

BuildResult result = orchestrator.executeBuild(scanner);
perfRule.assertDurationAround(MavenLogs.extractTotalTime(result.getLogs()), 8950);
perfRule.assertDurationAround(MavenLogs.extractTotalTime(result.getLogs()), 8200);

// Second execution with a property on server side
orchestrator.getServer().newHttpCall("/api/settings/set")

Loading…
취소
저장