3 * Copyright (C) 2009-2022 SonarSource SA
4 * mailto:info AT sonarsource DOT com
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.
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.
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.
20 package org.sonar.server.qualityprofile.builtin;
22 import java.util.Arrays;
23 import java.util.List;
24 import org.junit.After;
25 import org.junit.Rule;
26 import org.junit.Test;
27 import org.sonar.api.PropertyType;
28 import org.sonar.api.impl.utils.AlwaysIncreasingSystem2;
29 import org.sonar.api.rule.Severity;
30 import org.sonar.api.server.profile.BuiltInQualityProfilesDefinition;
31 import org.sonar.api.server.profile.BuiltInQualityProfilesDefinition.NewBuiltInQualityProfile;
32 import org.sonar.api.utils.System2;
33 import org.sonar.core.util.SequenceUuidFactory;
34 import org.sonar.core.util.UuidFactory;
35 import org.sonar.db.DbSession;
36 import org.sonar.db.DbTester;
37 import org.sonar.db.qualityprofile.ActiveRuleDto;
38 import org.sonar.db.qualityprofile.ActiveRuleKey;
39 import org.sonar.db.qualityprofile.ActiveRuleParamDto;
40 import org.sonar.db.qualityprofile.QProfileChangeDto;
41 import org.sonar.db.qualityprofile.QProfileChangeQuery;
42 import org.sonar.db.qualityprofile.QProfileDto;
43 import org.sonar.db.rule.RuleDefinitionDto;
44 import org.sonar.db.rule.RuleParamDto;
45 import org.sonar.server.qualityprofile.ActiveRuleChange;
46 import org.sonar.server.qualityprofile.index.ActiveRuleIndexer;
47 import org.sonar.server.rule.DefaultRuleFinder;
48 import org.sonar.server.rule.ServerRuleFinder;
49 import org.sonar.server.util.StringTypeValidation;
50 import org.sonar.server.util.TypeValidations;
52 import static java.util.Collections.singletonList;
53 import static org.assertj.core.api.Assertions.assertThat;
54 import static org.mockito.Mockito.mock;
56 public class BuiltInQProfileInsertImplTest {
59 public BuiltInQProfileRepositoryRule builtInQProfileRepository = new BuiltInQProfileRepositoryRule();
61 public DbTester db = DbTester.create();
63 private final System2 system2 = new AlwaysIncreasingSystem2();
64 private final UuidFactory uuidFactory = new SequenceUuidFactory();
65 private final TypeValidations typeValidations = new TypeValidations(singletonList(new StringTypeValidation()));
66 private final DbSession dbSession = db.getSession();
67 private final DbSession batchDbSession = db.getDbClient().openSession(true);
68 private final ServerRuleFinder ruleFinder = new DefaultRuleFinder(db.getDbClient());
69 private final ActiveRuleIndexer activeRuleIndexer = mock(ActiveRuleIndexer.class);
70 private final BuiltInQProfileInsertImpl underTest = new BuiltInQProfileInsertImpl(db.getDbClient(), ruleFinder, system2, uuidFactory, typeValidations, activeRuleIndexer);
73 public void tearDown() {
74 batchDbSession.close();
78 public void insert_active_rules_and_changelog() {
79 RuleDefinitionDto rule1 = db.rules().insert(r -> r.setLanguage("xoo"));
80 RuleDefinitionDto rule2 = db.rules().insert(r -> r.setLanguage("xoo"));
82 BuiltInQualityProfilesDefinition.Context context = new BuiltInQualityProfilesDefinition.Context();
83 NewBuiltInQualityProfile newQp = context.createBuiltInQualityProfile("the name", "xoo");
85 newQp.activateRule(rule1.getRepositoryKey(), rule1.getRuleKey()).overrideSeverity(Severity.CRITICAL);
86 newQp.activateRule(rule2.getRepositoryKey(), rule2.getRuleKey()).overrideSeverity(Severity.MAJOR);
89 BuiltInQProfile builtIn = builtInQProfileRepository.create(context.profile("xoo", "the name"), rule1, rule2);
92 verifyTableSize("rules_profiles", 1);
93 verifyTableSize("org_qprofiles", 1);
94 verifyTableSize("active_rules", 2);
95 verifyTableSize("active_rule_parameters", 0);
96 verifyTableSize("qprofile_changes", 2);
97 verifyTableSize("default_qprofiles", 0);
99 QProfileDto profile = verifyProfileInDb(builtIn);
100 verifyActiveRuleInDb(profile, rule1, Severity.CRITICAL);
101 verifyActiveRuleInDb(profile, rule2, Severity.MAJOR);
105 public void insert_default_qp() {
106 BuiltInQualityProfilesDefinition.Context context = new BuiltInQualityProfilesDefinition.Context();
107 context.createBuiltInQualityProfile("the name", "xoo")
111 BuiltInQProfile builtIn = builtInQProfileRepository.create(context.profile("xoo", "the name"));
114 verifyTableSize("rules_profiles", 1);
115 verifyTableSize("org_qprofiles", 1);
116 verifyTableSize("active_rules", 0);
117 verifyTableSize("active_rule_parameters", 0);
118 verifyTableSize("qprofile_changes", 0);
119 verifyTableSize("default_qprofiles", 1);
121 verifyProfileInDb(builtIn);
125 public void insert_active_rules_with_params() {
126 RuleDefinitionDto rule1 = db.rules().insert(r -> r.setLanguage("xoo"));
127 RuleParamDto param1 = db.rules().insertRuleParam(rule1, p -> p.setType(PropertyType.STRING.name()));
128 RuleParamDto param2 = db.rules().insertRuleParam(rule1, p -> p.setType(PropertyType.STRING.name()));
130 BuiltInQualityProfilesDefinition.Context context = new BuiltInQualityProfilesDefinition.Context();
131 NewBuiltInQualityProfile newQp = context.createBuiltInQualityProfile("the name", "xoo");
133 newQp.activateRule(rule1.getRepositoryKey(), rule1.getRuleKey()).overrideSeverity(Severity.CRITICAL);
136 BuiltInQProfile builtIn = builtInQProfileRepository.create(context.profile("xoo", "the name"), rule1);
139 verifyTableSize("rules_profiles", 1);
140 verifyTableSize("org_qprofiles", 1);
141 verifyTableSize("active_rules", 1);
142 verifyTableSize("active_rule_parameters", 2);
143 verifyTableSize("qprofile_changes", 1);
145 QProfileDto profile = verifyProfileInDb(builtIn);
146 verifyActiveRuleInDb(profile, rule1, Severity.CRITICAL, param1, param2);
150 public void flag_profile_as_default_if_declared_as_default_by_api() {
151 BuiltInQualityProfilesDefinition.Context context = new BuiltInQualityProfilesDefinition.Context();
152 NewBuiltInQualityProfile newQp = context.createBuiltInQualityProfile("the name", "xoo").setDefault(true);
155 BuiltInQProfile builtIn = builtInQProfileRepository.create(context.profile("xoo", "the name"));
159 QProfileDto profile = verifyProfileInDb(builtIn);
160 QProfileDto defaultProfile = db.getDbClient().qualityProfileDao().selectDefaultProfile(dbSession, "xoo");
161 assertThat(defaultProfile.getKee()).isEqualTo(profile.getKee());
165 public void existing_default_profile_must_not_be_changed() {
166 BuiltInQualityProfilesDefinition.Context context = new BuiltInQualityProfilesDefinition.Context();
167 NewBuiltInQualityProfile newQp = context.createBuiltInQualityProfile("the name", "xoo").setDefault(true);
169 BuiltInQProfile builtIn = builtInQProfileRepository.create(context.profile("xoo", "the name"));
171 QProfileDto currentDefault = db.qualityProfiles().insert(p -> p.setLanguage("xoo"));
172 db.qualityProfiles().setAsDefault(currentDefault);
176 QProfileDto defaultProfile = db.getDbClient().qualityProfileDao().selectDefaultProfile(dbSession, "xoo");
177 assertThat(defaultProfile.getKee()).isEqualTo(currentDefault.getKee());
178 verifyTableSize("rules_profiles", 2);
182 public void dont_flag_profile_as_default_if_not_declared_as_default_by_api() {
183 BuiltInQualityProfilesDefinition.Context context = new BuiltInQualityProfilesDefinition.Context();
184 NewBuiltInQualityProfile newQp = context.createBuiltInQualityProfile("the name", "xoo").setDefault(false);
186 BuiltInQProfile builtIn = builtInQProfileRepository.create(context.profile("xoo", "the name"));
190 QProfileDto defaultProfile = db.getDbClient().qualityProfileDao().selectDefaultProfile(dbSession, "xoo");
191 assertThat(defaultProfile).isNull();
194 // TODO test lot of active_rules, params, orgas
196 private void verifyActiveRuleInDb(QProfileDto profile, RuleDefinitionDto rule, String expectedSeverity, RuleParamDto... paramDtos) {
197 ActiveRuleDto activeRule = db.getDbClient().activeRuleDao().selectByKey(dbSession, ActiveRuleKey.of(profile, rule.getKey())).get();
198 assertThat(activeRule.getUuid()).isNotNull();
199 assertThat(activeRule.getInheritance()).isNull();
200 assertThat(activeRule.doesOverride()).isFalse();
201 assertThat(activeRule.getRuleUuid()).isEqualTo(rule.getUuid());
202 assertThat(activeRule.getProfileUuid()).isEqualTo(profile.getRulesProfileUuid());
203 assertThat(activeRule.getSeverityString()).isEqualTo(expectedSeverity);
204 assertThat(activeRule.getCreatedAt()).isPositive();
205 assertThat(activeRule.getUpdatedAt()).isPositive();
207 List<ActiveRuleParamDto> params = db.getDbClient().activeRuleDao().selectParamsByActiveRuleUuid(dbSession, activeRule.getUuid());
208 assertThat(params).extracting(ActiveRuleParamDto::getKey).containsOnly(Arrays.stream(paramDtos).map(RuleParamDto::getName).toArray(String[]::new));
210 QProfileChangeQuery changeQuery = new QProfileChangeQuery(profile.getKee());
211 QProfileChangeDto change = db.getDbClient().qProfileChangeDao().selectByQuery(dbSession, changeQuery).stream()
212 .filter(c -> c.getDataAsMap().get("ruleUuid").equals(rule.getUuid()))
215 assertThat(change.getChangeType()).isEqualTo(ActiveRuleChange.Type.ACTIVATED.name());
216 assertThat(change.getCreatedAt()).isPositive();
217 assertThat(change.getUuid()).isNotEmpty();
218 assertThat(change.getUserUuid()).isNull();
219 assertThat(change.getRulesProfileUuid()).isEqualTo(profile.getRulesProfileUuid());
220 assertThat(change.getDataAsMap()).containsEntry("severity", expectedSeverity);
223 private QProfileDto verifyProfileInDb(BuiltInQProfile builtIn) {
224 QProfileDto profileOnOrg1 = db.getDbClient().qualityProfileDao().selectByNameAndLanguage(dbSession, builtIn.getName(), builtIn.getLanguage());
225 assertThat(profileOnOrg1.getLanguage()).isEqualTo(builtIn.getLanguage());
226 assertThat(profileOnOrg1.getName()).isEqualTo(builtIn.getName());
227 assertThat(profileOnOrg1.getParentKee()).isNull();
228 assertThat(profileOnOrg1.getLastUsed()).isNull();
229 assertThat(profileOnOrg1.getUserUpdatedAt()).isNull();
230 assertThat(profileOnOrg1.getRulesUpdatedAt()).isNotEmpty();
231 assertThat(profileOnOrg1.getKee()).isNotEqualTo(profileOnOrg1.getRulesProfileUuid());
232 assertThat(profileOnOrg1.getRulesProfileUuid()).isNotNull();
233 return profileOnOrg1;
236 private void verifyTableSize(String table, int expectedSize) {
237 assertThat(db.countRowsOfTable(dbSession, table)).as("table " + table).isEqualTo(expectedSize);
240 private void call(BuiltInQProfile builtIn) {
241 underTest.create(dbSession, builtIn);
243 batchDbSession.commit();