]> source.dussan.org Git - sonarqube.git/blob
ca207f02f38f7f13e19a3adab1a84e0e94f88b16
[sonarqube.git] /
1 /*
2  * SonarQube
3  * Copyright (C) 2009-2023 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.server.measure.live;
21
22 import com.tngtech.java.junit.dataprovider.DataProviderRunner;
23 import java.util.List;
24 import java.util.Set;
25 import javax.annotation.Nullable;
26 import org.junit.Before;
27 import org.junit.Rule;
28 import org.junit.Test;
29 import org.junit.runner.RunWith;
30 import org.sonar.api.config.Configuration;
31 import org.sonar.api.config.PropertyDefinitions;
32 import org.sonar.api.config.internal.MapSettings;
33 import org.sonar.api.measures.Metric;
34 import org.sonar.api.resources.Qualifiers;
35 import org.sonar.api.utils.System2;
36 import org.sonar.core.config.CorePropertyDefinitions;
37 import org.sonar.db.DbSession;
38 import org.sonar.db.DbTester;
39 import org.sonar.db.component.BranchDto;
40 import org.sonar.db.component.ComponentDto;
41 import org.sonar.db.component.SnapshotDto;
42 import org.sonar.db.metric.MetricDto;
43 import org.sonar.server.es.TestProjectIndexers;
44 import org.sonar.server.qualitygate.EvaluatedQualityGate;
45 import org.sonar.server.qualitygate.QualityGate;
46 import org.sonar.server.qualitygate.changeevent.QGChangeEvent;
47 import org.sonar.server.setting.ProjectConfigurationLoader;
48 import org.sonar.server.setting.TestProjectConfigurationLoader;
49
50 import static org.assertj.core.api.Assertions.assertThat;
51 import static org.mockito.ArgumentMatchers.any;
52 import static org.mockito.ArgumentMatchers.eq;
53 import static org.mockito.Mockito.mock;
54 import static org.mockito.Mockito.verify;
55 import static org.mockito.Mockito.when;
56 import static org.sonar.api.measures.CoreMetrics.ALERT_STATUS_KEY;
57
58 @RunWith(DataProviderRunner.class)
59 public class LiveMeasureComputerImplIT {
60
61   @Rule
62   public DbTester db = DbTester.create(true);
63
64   private final TestProjectIndexers projectIndexer = new TestProjectIndexers();
65   private MetricDto metric1;
66   private MetricDto metric2;
67   private ComponentDto project;
68
69   private final LiveQualityGateComputer qGateComputer = mock(LiveQualityGateComputer.class);
70   private final QualityGate qualityGate = mock(QualityGate.class);
71   private final EvaluatedQualityGate newQualityGate = mock(EvaluatedQualityGate.class);
72   private final Configuration configuration = new MapSettings(new PropertyDefinitions(System2.INSTANCE, CorePropertyDefinitions.all())).asConfig();
73   private final ProjectConfigurationLoader configurationLoader = new TestProjectConfigurationLoader(configuration);
74   private final MeasureUpdateFormulaFactory measureUpdateFormulaFactory = mock(MeasureUpdateFormulaFactory.class);
75   private final ComponentIndexFactory componentIndexFactory = mock(ComponentIndexFactory.class);
76   private final ComponentIndex componentIndex = mock(ComponentIndex.class);
77   private final FakeLiveMeasureTreeUpdater treeUpdater = new FakeLiveMeasureTreeUpdater();
78   private final LiveMeasureComputerImpl liveMeasureComputer = new LiveMeasureComputerImpl(db.getDbClient(), measureUpdateFormulaFactory, componentIndexFactory,
79     qGateComputer, configurationLoader, projectIndexer, treeUpdater);
80   private BranchDto branch;
81
82   @Before
83   public void setUp() {
84     metric1 = db.measures().insertMetric();
85     metric2 = db.measures().insertMetric();
86
87     project = db.components().insertPublicProject().getMainBranchComponent();
88     branch = db.getDbClient().branchDao().selectByUuid(db.getSession(), project.uuid()).get();
89     db.measures().insertLiveMeasure(project, metric2, lm -> lm.setValue(1d));
90
91     when(componentIndexFactory.create(any(), any())).thenReturn(componentIndex);
92     when(measureUpdateFormulaFactory.getFormulaMetrics()).thenReturn(Set.of(toMetric(metric1), toMetric(metric2)));
93     when(componentIndex.getBranch()).thenReturn(project);
94   }
95
96   @Test
97   public void loads_measure_matrix_and_calls_tree_updater() {
98     SnapshotDto snapshot = markProjectAsAnalyzed(project);
99     when(componentIndex.getAllUuids()).thenReturn(Set.of(project.uuid()));
100
101     liveMeasureComputer.refresh(db.getSession(), List.of(project));
102
103     // tree updater was called
104     assertThat(treeUpdater.getMeasureMatrix()).isNotNull();
105
106     // measure matrix was loaded with formula's metrics and measures
107     assertThat(treeUpdater.getMeasureMatrix().getMetricByUuid(metric2.getUuid())).isNotNull();
108     assertThat(treeUpdater.getMeasureMatrix().getMeasure(project, metric2.getKey()).get().getValue()).isEqualTo(1d);
109
110     // new measures were persisted
111     assertThat(db.getDbClient().liveMeasureDao().selectMeasure(db.getSession(), project.uuid(), metric1.getKey()).get().getValue()).isEqualTo(2d);
112   }
113
114   @Test
115   public void refreshes_quality_gate() {
116     SnapshotDto snapshot = markProjectAsAnalyzed(project);
117     when(componentIndex.getAllUuids()).thenReturn(Set.of(project.uuid()));
118     when(qGateComputer.loadQualityGate(db.getSession(), db.components().getProjectDtoByMainBranch(project), branch)).thenReturn(qualityGate);
119
120     liveMeasureComputer.refresh(db.getSession(), List.of(project));
121
122     verify(qGateComputer).refreshGateStatus(eq(project), eq(qualityGate), any(MeasureMatrix.class), eq(configuration));
123   }
124
125   @Test
126   public void return_if_no_analysis_found() {
127     liveMeasureComputer.refresh(db.getSession(), List.of(project));
128     assertThat(treeUpdater.getMeasureMatrix()).isNull();
129   }
130
131   @Test
132   public void returns_qgate_event() {
133     SnapshotDto snapshot = markProjectAsAnalyzed(project);
134     when(componentIndex.getAllUuids()).thenReturn(Set.of(project.uuid()));
135
136     MetricDto alertStatusMetric = db.measures().insertMetric(m -> m.setKey(ALERT_STATUS_KEY));
137     db.measures().insertLiveMeasure(project, alertStatusMetric, lm -> lm.setData("OK"));
138
139     when(qGateComputer.loadQualityGate(db.getSession(), db.components().getProjectDtoByMainBranch(project), branch)).thenReturn(qualityGate);
140     when(qGateComputer.refreshGateStatus(eq(project), eq(qualityGate), any(MeasureMatrix.class), eq(configuration))).thenReturn(newQualityGate);
141
142     List<QGChangeEvent> qgChangeEvents = liveMeasureComputer.refresh(db.getSession(), List.of(project));
143
144     assertThat(qgChangeEvents).hasSize(1);
145     assertThat(qgChangeEvents.get(0).getBranch()).isEqualTo(branch);
146     assertThat(qgChangeEvents.get(0).getAnalysis()).isEqualTo(snapshot);
147     assertThat(qgChangeEvents.get(0).getProject()).isEqualTo(db.components().getProjectDtoByMainBranch(project));
148     assertThat(qgChangeEvents.get(0).getPreviousStatus()).contains(Metric.Level.OK);
149     assertThat(qgChangeEvents.get(0).getProjectConfiguration()).isEqualTo(configuration);
150     assertThat(qgChangeEvents.get(0).getQualityGateSupplier().get()).contains(newQualityGate);
151   }
152
153   private SnapshotDto markProjectAsAnalyzed(ComponentDto p) {
154     return markProjectAsAnalyzed(p, 1_490_000_000L);
155   }
156
157   private SnapshotDto markProjectAsAnalyzed(ComponentDto p, @Nullable Long periodDate) {
158     assertThat(p.qualifier()).isEqualTo(Qualifiers.PROJECT);
159     return db.components().insertSnapshot(p, s -> s.setPeriodDate(periodDate));
160   }
161
162   private static Metric<?> toMetric(MetricDto metric) {
163     return new Metric.Builder(metric.getKey(), metric.getShortName(), Metric.ValueType.valueOf(metric.getValueType())).create();
164   }
165
166   private class FakeLiveMeasureTreeUpdater implements LiveMeasureTreeUpdater {
167     private MeasureMatrix measureMatrix;
168
169     @Override
170     public void update(DbSession dbSession, SnapshotDto lastAnalysis, Configuration config, ComponentIndex components, BranchDto branch, MeasureMatrix measures) {
171       this.measureMatrix = measures;
172       measures.setValue(project, metric1.getKey(), 2d);
173     }
174
175     public MeasureMatrix getMeasureMatrix() {
176       return measureMatrix;
177     }
178   }
179
180 }