import org.sonar.server.computation.measure.api.MeasureComputerWrapper;
import org.sonar.server.computation.metric.MetricRepository;
+import static org.sonar.server.computation.component.Component.Type.FILE;
+import static org.sonar.server.computation.component.Component.Type.SUBVIEW;
import static org.sonar.server.computation.component.ComponentVisitor.Order.POST_ORDER;
public class MeasureComputersVisitor extends TypeAwareVisitorAdapter {
public MeasureComputersVisitor(MetricRepository metricRepository, MeasureRepository measureRepository, SettingsRepository settings,
MeasureComputersHolder measureComputersHolder, ComponentIssuesRepository componentIssuesRepository) {
- super(CrawlerDepthLimit.FILE, POST_ORDER);
+ super(CrawlerDepthLimit.reportMaxDepth(FILE).withViewsMaxDepth(SUBVIEW), POST_ORDER);
this.metricRepository = metricRepository;
this.measureRepository = measureRepository;
this.settings = settings;
--- /dev/null
+/*
+ * 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.computation.measure;
+
+import java.util.ArrayList;
+import java.util.List;
+import org.junit.After;
+import org.junit.rules.ExternalResource;
+import org.sonar.api.ce.measure.MeasureComputer;
+import org.sonar.server.computation.measure.api.MeasureComputerWrapper;
+
+import static java.util.Objects.requireNonNull;
+
+public class MeasureComputersHolderRule extends ExternalResource implements MeasureComputersHolder {
+
+ private final MeasureComputer.MeasureComputerDefinitionContext context;
+
+ private List<MeasureComputerWrapper> measureComputers = new ArrayList<>();
+
+ public MeasureComputersHolderRule(MeasureComputer.MeasureComputerDefinitionContext context) {
+ this.context = context;
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ measureComputers.clear();
+ }
+
+ @Override
+ public Iterable<MeasureComputerWrapper> getMeasureComputers() {
+ return measureComputers;
+ }
+
+ public void addMeasureComputer(MeasureComputer measureComputer) {
+ requireNonNull(measureComputer, "Measure computer cannot be null");
+ MeasureComputer.MeasureComputerDefinition definition = measureComputer.define(context);
+ this.measureComputers.add(new MeasureComputerWrapper(measureComputer, definition));
+ }
+}
+++ /dev/null
-/*
- * 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.computation.measure;
-
-import java.util.Arrays;
-import java.util.Collections;
-import org.junit.Rule;
-import org.junit.Test;
-import org.sonar.api.ce.measure.MeasureComputer;
-import org.sonar.server.computation.batch.TreeRootHolderRule;
-import org.sonar.server.computation.component.Component;
-import org.sonar.server.computation.component.ComponentVisitor;
-import org.sonar.server.computation.component.VisitorsCrawler;
-import org.sonar.server.computation.issue.ComponentIssuesRepository;
-import org.sonar.server.computation.measure.api.MeasureComputerDefinitionImpl;
-import org.sonar.server.computation.measure.api.MeasureComputerWrapper;
-import org.sonar.server.computation.metric.MetricRepositoryRule;
-
-import static com.google.common.collect.Lists.newArrayList;
-import static org.assertj.core.api.Assertions.assertThat;
-import static org.mockito.Mockito.mock;
-import static org.sonar.api.measures.CoreMetrics.COMMENT_LINES;
-import static org.sonar.api.measures.CoreMetrics.COMMENT_LINES_KEY;
-import static org.sonar.api.measures.CoreMetrics.NCLOC;
-import static org.sonar.api.measures.CoreMetrics.NCLOC_KEY;
-import static org.sonar.server.computation.component.Component.Type.DIRECTORY;
-import static org.sonar.server.computation.component.Component.Type.FILE;
-import static org.sonar.server.computation.component.Component.Type.MODULE;
-import static org.sonar.server.computation.component.Component.Type.PROJECT;
-import static org.sonar.server.computation.component.ReportComponent.builder;
-import static org.sonar.server.computation.measure.Measure.newMeasureBuilder;
-import static org.sonar.server.computation.measure.MeasureRepoEntry.entryOf;
-import static org.sonar.server.computation.measure.MeasureRepoEntry.toEntries;
-
-public class MeasureComputersVisitorTest {
-
- private static final String NEW_METRIC_KEY = "new_metric_key";
- private static final String NEW_METRIC_NAME = "new metric name";
-
- private static final org.sonar.api.measures.Metric<Integer> NEW_METRIC = new org.sonar.api.measures.Metric.Builder(NEW_METRIC_KEY, NEW_METRIC_NAME,
- org.sonar.api.measures.Metric.ValueType.INT)
- .create();
-
- private static final int ROOT_REF = 1;
- private static final int MODULE_REF = 12;
- private static final int DIRECTORY_REF = 123;
- private static final int FILE_1_REF = 1231;
- private static final int FILE_2_REF = 1232;
-
- private static final Component ROOT = builder(PROJECT, ROOT_REF).setKey("project")
- .addChildren(
- builder(MODULE, MODULE_REF).setKey("module")
- .addChildren(
- builder(DIRECTORY, DIRECTORY_REF).setKey("directory")
- .addChildren(
- builder(FILE, FILE_1_REF).setKey("file1").build(),
- builder(FILE, FILE_2_REF).setKey("file2").build()
- ).build()
- ).build()
- ).build();
-
- @Rule
- public TreeRootHolderRule treeRootHolder = new TreeRootHolderRule().setRoot(ROOT);
-
- @Rule
- public MetricRepositoryRule metricRepository = new MetricRepositoryRule()
- .add(NCLOC)
- .add(COMMENT_LINES)
- .add(NEW_METRIC);
-
- @Rule
- public MeasureRepositoryRule measureRepository = MeasureRepositoryRule.create(ROOT, metricRepository);
-
- ComponentIssuesRepository componentIssuesRepository = mock(ComponentIssuesRepository.class);
-
- MeasureComputersHolderImpl measureComputersHolder = new MeasureComputersHolderImpl();
-
- @Test
- public void compute_plugin_measure() throws Exception {
- measureRepository.addRawMeasure(FILE_1_REF, NCLOC_KEY, newMeasureBuilder().create(10));
- measureRepository.addRawMeasure(FILE_1_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(2));
- measureRepository.addRawMeasure(FILE_2_REF, NCLOC_KEY, newMeasureBuilder().create(40));
- measureRepository.addRawMeasure(FILE_2_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(5));
- measureRepository.addRawMeasure(DIRECTORY_REF, NCLOC_KEY, newMeasureBuilder().create(50));
- measureRepository.addRawMeasure(DIRECTORY_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(7));
- measureRepository.addRawMeasure(MODULE_REF, NCLOC_KEY, newMeasureBuilder().create(50));
- measureRepository.addRawMeasure(MODULE_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(7));
- measureRepository.addRawMeasure(ROOT_REF, NCLOC_KEY, newMeasureBuilder().create(50));
- measureRepository.addRawMeasure(ROOT_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(7));
-
- final MeasureComputer.MeasureComputerDefinition definition = new MeasureComputerDefinitionImpl.BuilderImpl()
- .setInputMetrics(NCLOC_KEY, COMMENT_LINES_KEY)
- .setOutputMetrics(NEW_METRIC_KEY)
- .build();
- measureComputersHolder.setMeasureComputers(newArrayList(
- new MeasureComputerWrapper(
- new MeasureComputer() {
- @Override
- public MeasureComputerDefinition define(MeasureComputerDefinitionContext defContext) {
- return definition;
- }
-
- @Override
- public void compute(MeasureComputerContext context) {
- org.sonar.api.ce.measure.Measure ncloc = context.getMeasure(NCLOC_KEY);
- org.sonar.api.ce.measure.Measure comment = context.getMeasure(COMMENT_LINES_KEY);
- if (ncloc != null && comment != null) {
- context.addMeasure(NEW_METRIC_KEY, ncloc.getIntValue() + comment.getIntValue());
- }
- }
- },
- definition
- )));
-
- VisitorsCrawler visitorsCrawler = new VisitorsCrawler(Arrays.<ComponentVisitor>asList(new MeasureComputersVisitor(metricRepository, measureRepository, null,
- measureComputersHolder, componentIssuesRepository)));
- visitorsCrawler.visit(ROOT);
-
- assertThat(toEntries(measureRepository.getAddedRawMeasures(FILE_1_REF))).containsOnly(entryOf(NEW_METRIC_KEY, newMeasureBuilder().create(12)));
- assertThat(toEntries(measureRepository.getAddedRawMeasures(FILE_2_REF))).containsOnly(entryOf(NEW_METRIC_KEY, newMeasureBuilder().create(45)));
- assertThat(toEntries(measureRepository.getAddedRawMeasures(DIRECTORY_REF))).containsOnly(entryOf(NEW_METRIC_KEY, newMeasureBuilder().create(57)));
- assertThat(toEntries(measureRepository.getAddedRawMeasures(MODULE_REF))).containsOnly(entryOf(NEW_METRIC_KEY, newMeasureBuilder().create(57)));
- assertThat(toEntries(measureRepository.getAddedRawMeasures(ROOT_REF))).containsOnly(entryOf(NEW_METRIC_KEY, newMeasureBuilder().create(57)));
- }
-
- @Test
- public void nothing_to_compute() throws Exception {
- measureRepository.addRawMeasure(FILE_1_REF, NCLOC_KEY, newMeasureBuilder().create(10));
- measureRepository.addRawMeasure(FILE_1_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(2));
- measureRepository.addRawMeasure(FILE_2_REF, NCLOC_KEY, newMeasureBuilder().create(40));
- measureRepository.addRawMeasure(FILE_2_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(5));
- measureRepository.addRawMeasure(DIRECTORY_REF, NCLOC_KEY, newMeasureBuilder().create(50));
- measureRepository.addRawMeasure(DIRECTORY_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(7));
- measureRepository.addRawMeasure(MODULE_REF, NCLOC_KEY, newMeasureBuilder().create(50));
- measureRepository.addRawMeasure(MODULE_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(7));
- measureRepository.addRawMeasure(ROOT_REF, NCLOC_KEY, newMeasureBuilder().create(50));
- measureRepository.addRawMeasure(ROOT_REF, COMMENT_LINES_KEY, newMeasureBuilder().create(7));
-
- measureComputersHolder.setMeasureComputers(Collections.<MeasureComputerWrapper>emptyList());
- VisitorsCrawler visitorsCrawler = new VisitorsCrawler(Arrays.<ComponentVisitor>asList(new MeasureComputersVisitor(metricRepository, measureRepository, null,
- measureComputersHolder, componentIssuesRepository)));
- visitorsCrawler.visit(ROOT);
-
- assertThat(toEntries(measureRepository.getAddedRawMeasures(FILE_1_REF))).isEmpty();
- assertThat(toEntries(measureRepository.getAddedRawMeasures(FILE_2_REF))).isEmpty();
- assertThat(toEntries(measureRepository.getAddedRawMeasures(DIRECTORY_REF))).isEmpty();
- assertThat(toEntries(measureRepository.getAddedRawMeasures(MODULE_REF))).isEmpty();
- assertThat(toEntries(measureRepository.getAddedRawMeasures(ROOT_REF))).isEmpty();
- }
-
-}
--- /dev/null
+/*
+ * 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.computation.measure;
+
+import java.util.Arrays;
+import java.util.Collections;
+import org.junit.Rule;
+import org.junit.Test;
+import org.sonar.api.ce.measure.MeasureComputer;
+import org.sonar.server.computation.batch.TreeRootHolderRule;
+import org.sonar.server.computation.component.Component;
+import org.sonar.server.computation.component.ComponentVisitor;
+import org.sonar.server.computation.component.VisitorsCrawler;
+import org.sonar.server.computation.issue.ComponentIssuesRepository;
+import org.sonar.server.computation.measure.api.MeasureComputerDefinitionImpl;
+import org.sonar.server.computation.measure.api.MeasureComputerWrapper;
+import org.sonar.server.computation.metric.MetricRepositoryRule;
+
+import static com.google.common.collect.Lists.newArrayList;
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.mockito.Mockito.mock;
+import static org.sonar.api.measures.CoreMetrics.COMMENT_LINES;
+import static org.sonar.api.measures.CoreMetrics.COMMENT_LINES_KEY;
+import static org.sonar.api.measures.CoreMetrics.NCLOC;
+import static org.sonar.api.measures.CoreMetrics.NCLOC_KEY;
+import static org.sonar.server.computation.component.Component.Type.DIRECTORY;
+import static org.sonar.server.computation.component.Component.Type.FILE;
+import static org.sonar.server.computation.component.Component.Type.MODULE;
+import static org.sonar.server.computation.component.Component.Type.PROJECT;
+import static org.sonar.server.computation.component.ReportComponent.builder;
+import static org.sonar.server.computation.measure.Measure.newMeasureBuilder;
+import static org.sonar.server.computation.measure.MeasureRepoEntry.entryOf;
+import static org.sonar.server.computation.measure.MeasureRepoEntry.toEntries;
+
+public class ReportMeasureComputersVisitorTest {
+
+ private static final String NEW_METRIC_KEY = "new_metric_key";
+ private static final String NEW_METRIC_NAME = "new metric name";
+
+ private static final org.sonar.api.measures.Metric<Integer> NEW_METRIC = new org.sonar.api.measures.Metric.Builder(NEW_METRIC_KEY, NEW_METRIC_NAME,
+ org.sonar.api.measures.Metric.ValueType.INT)
+ .create();
+
+ private static final int ROOT_REF = 1;
+ private static final int MODULE_REF = 12;
+ private static final int DIRECTORY_REF = 123;
+ private static final int FILE_1_REF = 1231;
+ private static final int FILE_2_REF = 1232;
+
+ private static final Component ROOT = builder(PROJECT, ROOT_REF).setKey("project")
+ .addChildren(
+ builder(MODULE, MODULE_REF).setKey("module")
+ .addChildren(
+ builder(DIRECTORY, DIRECTORY_REF).setKey("directory")
+ .addChildren(
+ builder(FILE, FILE_1_REF).setKey("file1").build(),
+ builder(FILE, FILE_2_REF).setKey("file2").build()
+ ).build()
+ ).build()
+ ).build();
+
+ @Rule
+ public TreeRootHolderRule treeRootHolder = new TreeRootHolderRule().setRoot(ROOT);
+
+ @Rule
+ public MetricRepositoryRule metricRepository = new MetricRepositoryRule()
+ .add(NCLOC)
+ .add(COMMENT_LINES)
+ .add(NEW_METRIC);
+
+ @Rule
+ public MeasureRepositoryRule measureRepository = MeasureRepositoryRule.create(ROOT, metricRepository);
+
+ ComponentIssuesRepository componentIssuesRepository = mock(ComponentIssuesRepository.class);
+
+ MeasureComputersHolderImpl measureComputersHolder = new MeasureComputersHolderImpl();
+
+ @Test
+ public void compute_plugin_measure() throws Exception {
+ addRawMeasure(FILE_1_REF, NCLOC_KEY, 10);
+ addRawMeasure(FILE_1_REF, COMMENT_LINES_KEY, 2);
+ addRawMeasure(FILE_2_REF, NCLOC_KEY, 40);
+ addRawMeasure(FILE_2_REF, COMMENT_LINES_KEY, 5);
+ addRawMeasure(DIRECTORY_REF, NCLOC_KEY, 50);
+ addRawMeasure(DIRECTORY_REF, COMMENT_LINES_KEY, 7);
+ addRawMeasure(MODULE_REF, NCLOC_KEY, 50);
+ addRawMeasure(MODULE_REF, COMMENT_LINES_KEY, 7);
+ addRawMeasure(ROOT_REF, NCLOC_KEY, 50);
+ addRawMeasure(ROOT_REF, COMMENT_LINES_KEY, 7);
+
+ final MeasureComputer.MeasureComputerDefinition definition = new MeasureComputerDefinitionImpl.BuilderImpl()
+ .setInputMetrics(NCLOC_KEY, COMMENT_LINES_KEY)
+ .setOutputMetrics(NEW_METRIC_KEY)
+ .build();
+ measureComputersHolder.setMeasureComputers(newArrayList(
+ new MeasureComputerWrapper(
+ new MeasureComputer() {
+ @Override
+ public MeasureComputerDefinition define(MeasureComputerDefinitionContext defContext) {
+ return definition;
+ }
+
+ @Override
+ public void compute(MeasureComputerContext context) {
+ org.sonar.api.ce.measure.Measure ncloc = context.getMeasure(NCLOC_KEY);
+ org.sonar.api.ce.measure.Measure comment = context.getMeasure(COMMENT_LINES_KEY);
+ if (ncloc != null && comment != null) {
+ context.addMeasure(NEW_METRIC_KEY, ncloc.getIntValue() + comment.getIntValue());
+ }
+ }
+ },
+ definition
+ )));
+
+ VisitorsCrawler visitorsCrawler = new VisitorsCrawler(Arrays.<ComponentVisitor>asList(new MeasureComputersVisitor(metricRepository, measureRepository, null,
+ measureComputersHolder, componentIssuesRepository)));
+ visitorsCrawler.visit(ROOT);
+
+ assertAddedRawMeasure(12, FILE_1_REF, NEW_METRIC_KEY);
+ assertAddedRawMeasure(45, FILE_2_REF, NEW_METRIC_KEY);
+ assertAddedRawMeasure(57, DIRECTORY_REF, NEW_METRIC_KEY);
+ assertAddedRawMeasure(57, MODULE_REF, NEW_METRIC_KEY);
+ assertAddedRawMeasure(57, ROOT_REF, NEW_METRIC_KEY);
+ }
+
+ @Test
+ public void nothing_to_compute() throws Exception {
+ addRawMeasure(FILE_1_REF, NCLOC_KEY, 10);
+ addRawMeasure(FILE_1_REF, COMMENT_LINES_KEY, 2);
+ addRawMeasure(FILE_2_REF, NCLOC_KEY, 40);
+ addRawMeasure(FILE_2_REF, COMMENT_LINES_KEY, 5);
+ addRawMeasure(DIRECTORY_REF, NCLOC_KEY, 50);
+ addRawMeasure(DIRECTORY_REF, COMMENT_LINES_KEY, 7);
+ addRawMeasure(MODULE_REF, NCLOC_KEY, 50);
+ addRawMeasure(MODULE_REF, COMMENT_LINES_KEY, 7);
+ addRawMeasure(ROOT_REF, NCLOC_KEY, 50);
+ addRawMeasure(ROOT_REF, COMMENT_LINES_KEY, 7);
+
+ measureComputersHolder.setMeasureComputers(Collections.<MeasureComputerWrapper>emptyList());
+ VisitorsCrawler visitorsCrawler = new VisitorsCrawler(Arrays.<ComponentVisitor>asList(new MeasureComputersVisitor(metricRepository, measureRepository, null,
+ measureComputersHolder, componentIssuesRepository)));
+ visitorsCrawler.visit(ROOT);
+
+ assertNoAddedRawMeasure(FILE_1_REF);
+ assertNoAddedRawMeasure(FILE_2_REF);
+ assertNoAddedRawMeasure(DIRECTORY_REF);
+ assertNoAddedRawMeasure(MODULE_REF);
+ assertNoAddedRawMeasure(ROOT_REF);
+ }
+
+ private void addRawMeasure(int componentRef, String metricKey, int value) {
+ measureRepository.addRawMeasure(componentRef, metricKey, newMeasureBuilder().create(value));
+ }
+
+ private void assertNoAddedRawMeasure(int componentRef) {
+ assertThat(toEntries(measureRepository.getAddedRawMeasures(componentRef))).isEmpty();
+ }
+
+ private void assertAddedRawMeasure(int value, int componentRef, String metricKey) {
+ assertThat(toEntries(measureRepository.getAddedRawMeasures(componentRef))).containsOnly(entryOf(metricKey, newMeasureBuilder().create(value)));
+ }
+
+}
--- /dev/null
+/*
+ * 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.computation.measure;
+
+import java.util.Arrays;
+import org.junit.Rule;
+import org.junit.Test;
+import org.sonar.api.ce.measure.MeasureComputer;
+import org.sonar.api.ce.measure.test.TestMeasureComputerDefinitionContext;
+import org.sonar.server.computation.batch.TreeRootHolderRule;
+import org.sonar.server.computation.component.Component;
+import org.sonar.server.computation.component.ComponentVisitor;
+import org.sonar.server.computation.component.VisitorsCrawler;
+import org.sonar.server.computation.issue.ComponentIssuesRepository;
+import org.sonar.server.computation.measure.api.MeasureComputerDefinitionImpl;
+import org.sonar.server.computation.metric.MetricRepositoryRule;
+
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.mockito.Mockito.mock;
+import static org.sonar.api.measures.CoreMetrics.COMMENT_LINES;
+import static org.sonar.api.measures.CoreMetrics.COMMENT_LINES_KEY;
+import static org.sonar.api.measures.CoreMetrics.NCLOC;
+import static org.sonar.api.measures.CoreMetrics.NCLOC_KEY;
+import static org.sonar.server.computation.component.Component.Type.PROJECT_VIEW;
+import static org.sonar.server.computation.component.Component.Type.SUBVIEW;
+import static org.sonar.server.computation.component.Component.Type.VIEW;
+import static org.sonar.server.computation.component.ViewsComponent.builder;
+import static org.sonar.server.computation.measure.Measure.newMeasureBuilder;
+import static org.sonar.server.computation.measure.MeasureRepoEntry.entryOf;
+import static org.sonar.server.computation.measure.MeasureRepoEntry.toEntries;
+
+public class ViewsMeasureComputersVisitorTest {
+
+ private static final String NEW_METRIC_KEY = "new_metric_key";
+ private static final String NEW_METRIC_NAME = "new metric name";
+
+ private static final org.sonar.api.measures.Metric<Integer> NEW_METRIC = new org.sonar.api.measures.Metric.Builder(NEW_METRIC_KEY, NEW_METRIC_NAME,
+ org.sonar.api.measures.Metric.ValueType.INT)
+ .create();
+
+ private static final int ROOT_REF = 1;
+ private static final int VIEW_REF = 12;
+ private static final int SUB_SUBVIEW_REF = 123;
+ private static final int PROJECT_VIEW_1_REF = 1231;
+ private static final int PROJECT_VIEW_2_REF = 1232;
+
+ private static final Component TREE_WITH_SUB_VIEWS = builder(VIEW, ROOT_REF)
+ .addChildren(
+ builder(SUBVIEW, VIEW_REF)
+ .addChildren(
+ builder(SUBVIEW, SUB_SUBVIEW_REF)
+ .addChildren(
+ builder(PROJECT_VIEW, PROJECT_VIEW_1_REF).build(),
+ builder(PROJECT_VIEW, PROJECT_VIEW_2_REF).build())
+ .build())
+ .build())
+ .build();
+
+ private static final Component TREE_WITH_DIRECT_PROJECT_VIEW = builder(VIEW, ROOT_REF)
+ .addChildren(
+ builder(PROJECT_VIEW, PROJECT_VIEW_1_REF).build(),
+ builder(PROJECT_VIEW, PROJECT_VIEW_2_REF).build())
+ .build();
+
+ private static final MeasureComputer MEASURE_COMPUTER = new MeasureComputer() {
+ @Override
+ public MeasureComputer.MeasureComputerDefinition define(MeasureComputer.MeasureComputerDefinitionContext defContext) {
+ return new MeasureComputerDefinitionImpl.BuilderImpl()
+ .setInputMetrics(NCLOC_KEY, COMMENT_LINES_KEY)
+ .setOutputMetrics(NEW_METRIC_KEY)
+ .build();
+ }
+
+ @Override
+ public void compute(MeasureComputer.MeasureComputerContext context) {
+ org.sonar.api.ce.measure.Measure ncloc = context.getMeasure(NCLOC_KEY);
+ org.sonar.api.ce.measure.Measure comment = context.getMeasure(COMMENT_LINES_KEY);
+ if (ncloc != null && comment != null) {
+ context.addMeasure(NEW_METRIC_KEY, ncloc.getIntValue() + comment.getIntValue());
+ }
+ }
+ };
+
+ @Rule
+ public TreeRootHolderRule treeRootHolder = new TreeRootHolderRule();
+
+ @Rule
+ public MetricRepositoryRule metricRepository = new MetricRepositoryRule()
+ .add(NCLOC)
+ .add(COMMENT_LINES)
+ .add(NEW_METRIC);
+
+ @Rule
+ public MeasureRepositoryRule measureRepository = MeasureRepositoryRule.create(TREE_WITH_SUB_VIEWS, metricRepository);
+
+ @Rule
+ public MeasureComputersHolderRule measureComputersHolder = new MeasureComputersHolderRule(new TestMeasureComputerDefinitionContext());
+
+ ComponentIssuesRepository componentIssuesRepository = mock(ComponentIssuesRepository.class);
+
+ @Test
+ public void compute_plugin_measure() throws Exception {
+ treeRootHolder.setRoot(TREE_WITH_SUB_VIEWS);
+
+ addRawMeasure(PROJECT_VIEW_1_REF, NCLOC_KEY, 10);
+ addRawMeasure(PROJECT_VIEW_1_REF, COMMENT_LINES_KEY, 2);
+ addRawMeasure(PROJECT_VIEW_2_REF, NCLOC_KEY, 40);
+ addRawMeasure(PROJECT_VIEW_2_REF, COMMENT_LINES_KEY, 5);
+ addRawMeasure(SUB_SUBVIEW_REF, NCLOC_KEY, 50);
+ addRawMeasure(SUB_SUBVIEW_REF, COMMENT_LINES_KEY, 7);
+ addRawMeasure(VIEW_REF, NCLOC_KEY, 50);
+ addRawMeasure(VIEW_REF, COMMENT_LINES_KEY, 7);
+ addRawMeasure(ROOT_REF, NCLOC_KEY, 50);
+ addRawMeasure(ROOT_REF, COMMENT_LINES_KEY, 7);
+
+ measureComputersHolder.addMeasureComputer(MEASURE_COMPUTER);
+
+ VisitorsCrawler visitorsCrawler = new VisitorsCrawler(Arrays.<ComponentVisitor>asList(new MeasureComputersVisitor(metricRepository, measureRepository, null,
+ measureComputersHolder, componentIssuesRepository)));
+ visitorsCrawler.visit(treeRootHolder.getRoot());
+
+ assertNoAddedRawMeasureOnProjectViews();
+ assertAddedRawMeasure(57, SUB_SUBVIEW_REF, NEW_METRIC_KEY);
+ assertAddedRawMeasure(57, VIEW_REF, NEW_METRIC_KEY);
+ assertAddedRawMeasure(57, ROOT_REF, NEW_METRIC_KEY);
+ }
+
+ @Test
+ public void compute_plugin_measure_on_views_tree_having_only_one_view_with_a_project_view() throws Exception {
+ treeRootHolder.setRoot(TREE_WITH_DIRECT_PROJECT_VIEW);
+
+ addRawMeasure(PROJECT_VIEW_1_REF, NCLOC_KEY, 10);
+ addRawMeasure(PROJECT_VIEW_1_REF, COMMENT_LINES_KEY, 2);
+ addRawMeasure(PROJECT_VIEW_2_REF, NCLOC_KEY, 40);
+ addRawMeasure(PROJECT_VIEW_2_REF, COMMENT_LINES_KEY, 5);
+ addRawMeasure(ROOT_REF, NCLOC_KEY, 50);
+ addRawMeasure(ROOT_REF, COMMENT_LINES_KEY, 7);
+
+ measureComputersHolder.addMeasureComputer(MEASURE_COMPUTER);
+
+ VisitorsCrawler visitorsCrawler = new VisitorsCrawler(Arrays.<ComponentVisitor>asList(new MeasureComputersVisitor(metricRepository, measureRepository, null,
+ measureComputersHolder, componentIssuesRepository)));
+ visitorsCrawler.visit(treeRootHolder.getRoot());
+
+ assertNoAddedRawMeasureOnProjectViews();
+ assertAddedRawMeasure(57, ROOT_REF, NEW_METRIC_KEY);
+ }
+
+ @Test
+ public void nothing_to_compute_when_no_project_view() throws Exception {
+ treeRootHolder.setRoot(builder(VIEW, ROOT_REF)
+ .addChildren(
+ builder(SUBVIEW, VIEW_REF)
+ .addChildren(
+ builder(SUBVIEW, SUB_SUBVIEW_REF)
+ .build())
+ .build())
+ .build());
+
+ measureComputersHolder.addMeasureComputer(MEASURE_COMPUTER);
+
+ VisitorsCrawler visitorsCrawler = new VisitorsCrawler(Arrays.<ComponentVisitor>asList(new MeasureComputersVisitor(metricRepository, measureRepository, null,
+ measureComputersHolder, componentIssuesRepository)));
+ visitorsCrawler.visit(treeRootHolder.getRoot());
+
+ assertNoAddedRawMeasureOnProjectViews();
+ assertNoAddedRawMeasure(SUB_SUBVIEW_REF);
+ assertNoAddedRawMeasure(VIEW_REF);
+ assertNoAddedRawMeasure(ROOT_REF);
+ }
+
+ @Test
+ public void nothing_to_compute_when_no_measure_computers() throws Exception {
+ treeRootHolder.setRoot(TREE_WITH_SUB_VIEWS);
+
+ addRawMeasure(PROJECT_VIEW_1_REF, NCLOC_KEY, 10);
+ addRawMeasure(PROJECT_VIEW_1_REF, COMMENT_LINES_KEY, 2);
+ addRawMeasure(PROJECT_VIEW_2_REF, NCLOC_KEY, 40);
+ addRawMeasure(PROJECT_VIEW_2_REF, COMMENT_LINES_KEY, 5);
+ addRawMeasure(SUB_SUBVIEW_REF, NCLOC_KEY, 50);
+ addRawMeasure(SUB_SUBVIEW_REF, COMMENT_LINES_KEY, 7);
+ addRawMeasure(VIEW_REF, NCLOC_KEY, 50);
+ addRawMeasure(VIEW_REF, COMMENT_LINES_KEY, 7);
+ addRawMeasure(ROOT_REF, NCLOC_KEY, 50);
+ addRawMeasure(ROOT_REF, COMMENT_LINES_KEY, 7);
+
+ VisitorsCrawler visitorsCrawler = new VisitorsCrawler(Arrays.<ComponentVisitor>asList(new MeasureComputersVisitor(metricRepository, measureRepository, null,
+ measureComputersHolder, componentIssuesRepository)));
+ visitorsCrawler.visit(treeRootHolder.getRoot());
+
+ assertNoAddedRawMeasureOnProjectViews();
+ assertNoAddedRawMeasure(SUB_SUBVIEW_REF);
+ assertNoAddedRawMeasure(VIEW_REF);
+ assertNoAddedRawMeasure(ROOT_REF);
+ }
+
+ private void assertNoAddedRawMeasureOnProjectViews() {
+ assertNoAddedRawMeasure(PROJECT_VIEW_1_REF);
+ assertNoAddedRawMeasure(PROJECT_VIEW_2_REF);
+ }
+
+ private void addRawMeasure(int componentRef, String metricKey, int value) {
+ measureRepository.addRawMeasure(componentRef, metricKey, newMeasureBuilder().create(value));
+ }
+
+ private void assertNoAddedRawMeasure(int componentRef) {
+ assertThat(toEntries(measureRepository.getAddedRawMeasures(componentRef))).isEmpty();
+ }
+
+ private void assertAddedRawMeasure(int value, int componentRef, String metricKey) {
+ assertThat(toEntries(measureRepository.getAddedRawMeasures(componentRef))).containsOnly(entryOf(metricKey, newMeasureBuilder().create(value)));
+ }
+
+}
public interface Component {
enum Type {
- PROJECT, MODULE, DIRECTORY, FILE
+ PROJECT, MODULE, DIRECTORY, FILE, VIEW, SUBVIEW
}
Type getType();