You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

MeasureRepositoryImpl.java 4.8KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122
  1. /*
  2. * SonarQube
  3. * Copyright (C) 2009-2021 SonarSource SA
  4. * mailto:info AT sonarsource DOT com
  5. *
  6. * This program is free software; you can redistribute it and/or
  7. * modify it under the terms of the GNU Lesser General Public
  8. * License as published by the Free Software Foundation; either
  9. * version 3 of the License, or (at your option) any later version.
  10. *
  11. * This program is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  14. * Lesser General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU Lesser General Public License
  17. * along with this program; if not, write to the Free Software Foundation,
  18. * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
  19. */
  20. package org.sonar.ce.task.projectanalysis.measure;
  21. import java.util.HashSet;
  22. import java.util.Map;
  23. import java.util.Optional;
  24. import java.util.Set;
  25. import org.sonar.ce.task.projectanalysis.batch.BatchReportReader;
  26. import org.sonar.ce.task.projectanalysis.component.Component;
  27. import org.sonar.ce.task.projectanalysis.measure.MapBasedRawMeasureRepository.OverridePolicy;
  28. import org.sonar.ce.task.projectanalysis.metric.Metric;
  29. import org.sonar.ce.task.projectanalysis.metric.MetricRepository;
  30. import org.sonar.ce.task.projectanalysis.metric.ReportMetricValidator;
  31. import org.sonar.core.util.CloseableIterator;
  32. import org.sonar.db.DbClient;
  33. import org.sonar.db.DbSession;
  34. import org.sonar.db.measure.MeasureDto;
  35. import org.sonar.scanner.protocol.output.ScannerReport;
  36. import static java.util.Objects.requireNonNull;
  37. import static org.sonar.ce.task.projectanalysis.component.ComponentFunctions.toComponentUuid;
  38. public class MeasureRepositoryImpl implements MeasureRepository {
  39. private final MapBasedRawMeasureRepository<String> delegate = new MapBasedRawMeasureRepository<>(toComponentUuid());
  40. private final DbClient dbClient;
  41. private final BatchReportReader reportReader;
  42. private final BatchMeasureToMeasure batchMeasureToMeasure;
  43. private final MetricRepository metricRepository;
  44. private final ReportMetricValidator reportMetricValidator;
  45. private MeasureDtoToMeasure measureTransformer = new MeasureDtoToMeasure();
  46. private final Set<Integer> loadedComponents = new HashSet<>();
  47. public MeasureRepositoryImpl(DbClient dbClient, BatchReportReader reportReader, MetricRepository metricRepository,
  48. ReportMetricValidator reportMetricValidator) {
  49. this.dbClient = dbClient;
  50. this.reportReader = reportReader;
  51. this.reportMetricValidator = reportMetricValidator;
  52. this.batchMeasureToMeasure = new BatchMeasureToMeasure();
  53. this.metricRepository = metricRepository;
  54. }
  55. @Override
  56. public Optional<Measure> getBaseMeasure(Component component, Metric metric) {
  57. // fail fast
  58. requireNonNull(component);
  59. requireNonNull(metric);
  60. try (DbSession dbSession = dbClient.openSession(false)) {
  61. Optional<MeasureDto> measureDto = dbClient.measureDao().selectLastMeasure(dbSession, component.getUuid(), metric.getKey());
  62. if (measureDto.isPresent()) {
  63. return measureTransformer.toMeasure(measureDto.get(), metric);
  64. }
  65. return Optional.empty();
  66. }
  67. }
  68. @Override
  69. public Optional<Measure> getRawMeasure(Component component, Metric metric) {
  70. Optional<Measure> local = delegate.getRawMeasure(component, metric);
  71. if (local.isPresent()) {
  72. return local;
  73. }
  74. // look up in batch after loading (if not yet loaded) measures from batch
  75. loadBatchMeasuresForComponent(component);
  76. return delegate.getRawMeasure(component, metric);
  77. }
  78. @Override
  79. public void add(Component component, Metric metric, Measure measure) {
  80. delegate.add(component, metric, measure);
  81. }
  82. @Override
  83. public void update(Component component, Metric metric, Measure measure) {
  84. delegate.update(component, metric, measure);
  85. }
  86. @Override
  87. public Map<String, Measure> getRawMeasures(Component component) {
  88. loadBatchMeasuresForComponent(component);
  89. return delegate.getRawMeasures(component);
  90. }
  91. private void loadBatchMeasuresForComponent(Component component) {
  92. Integer ref = component.getReportAttributes().getRef();
  93. if (ref == null || !loadedComponents.add(ref)) {
  94. return;
  95. }
  96. try (CloseableIterator<ScannerReport.Measure> readIt = reportReader.readComponentMeasures(component.getReportAttributes().getRef())) {
  97. while (readIt.hasNext()) {
  98. ScannerReport.Measure batchMeasure = readIt.next();
  99. String metricKey = batchMeasure.getMetricKey();
  100. if (reportMetricValidator.validate(metricKey)) {
  101. Metric metric = metricRepository.getByKey(metricKey);
  102. batchMeasureToMeasure.toMeasure(batchMeasure, metric).ifPresent(measure -> delegate.add(component, metric, measure, OverridePolicy.DO_NOT_OVERRIDE));
  103. }
  104. }
  105. }
  106. }
  107. }