Browse Source

SONAR-13019 Keys of rules created from template are not renamed when template rule key is renamed

tags/8.2.0.32929
Duarte Meneses 4 years ago
parent
commit
e94172d9ea

+ 17
- 17
server/sonar-webserver-core/src/main/java/org/sonar/server/rule/RegisterRules.java View File

@@ -70,7 +70,6 @@ import org.sonar.server.rule.index.RuleIndexer;

import static com.google.common.base.Preconditions.checkNotNull;
import static com.google.common.base.Preconditions.checkState;
import static com.google.common.collect.Lists.newArrayList;
import static com.google.common.collect.Sets.difference;
import static com.google.common.collect.Sets.intersection;
import static java.lang.String.format;
@@ -170,16 +169,14 @@ public class RegisterRules implements Startable {
}

private RegisterRulesContext createRegisterRulesContext(DbSession dbSession) {
Map<RuleKey, RuleDefinitionDto> allRules = dbClient.ruleDao().selectAllDefinitions(dbSession)
.stream()
Map<RuleKey, RuleDefinitionDto> allRules = dbClient.ruleDao().selectAllDefinitions(dbSession).stream()
.collect(uniqueIndex(RuleDefinitionDto::getKey));
Map<Integer, Set<SingleDeprecatedRuleKey>> existingDeprecatedKeysById = loadDeprecatedRuleKeys(dbSession);
return new RegisterRulesContext(allRules, existingDeprecatedKeysById);
}

private Map<Integer, Set<SingleDeprecatedRuleKey>> loadDeprecatedRuleKeys(DbSession dbSession) {
return dbClient.ruleDao().selectAllDeprecatedRuleKeys(dbSession)
.stream()
return dbClient.ruleDao().selectAllDeprecatedRuleKeys(dbSession).stream()
.map(SingleDeprecatedRuleKey::from)
.collect(Collectors.groupingBy(SingleDeprecatedRuleKey::getRuleId, Collectors.toSet()));
}
@@ -231,7 +228,7 @@ public class RegisterRules implements Startable {
RuleDefinitionDto rule = dbRulesByRuleId.get(ruleId);
if (rule == null) {
LOG.warn("Could not retrieve rule with id %s referenced by a deprecated rule key. " +
"The following deprecated rule keys seem to be referencing a non-existing rule",
"The following deprecated rule keys seem to be referencing a non-existing rule",
ruleId, entry.getValue());
} else {
entry.getValue().forEach(d -> builder.put(d.getOldRuleKeyAsRuleKey(), rule));
@@ -641,11 +638,9 @@ public class RegisterRules implements Startable {
changed = true;
} else if (dto.getSystemTags().size() != ruleDef.tags().size() ||
!dto.getSystemTags().containsAll(ruleDef.tags())) {
dto.setSystemTags(ruleDef.tags());
// FIXME this can't be implemented easily with organization support: remove end-user tags that are now declared as system
// RuleTagHelper.applyTags(dto, ImmutableSet.copyOf(dto.getTags()));
changed = true;
}
dto.setSystemTags(ruleDef.tags());
changed = true;
}
return changed;
}

@@ -657,15 +652,15 @@ public class RegisterRules implements Startable {
changed = true;
} else if (dto.getSecurityStandards().size() != ruleDef.securityStandards().size() ||
!dto.getSecurityStandards().containsAll(ruleDef.securityStandards())) {
dto.setSecurityStandards(ruleDef.securityStandards());
changed = true;
}
dto.setSecurityStandards(ruleDef.securityStandards());
changed = true;
}
return changed;
}

private void processRemainingDbRules(RegisterRulesContext recorder, DbSession dbSession) {
// custom rules check status of template, so they must be processed at the end
List<RuleDefinitionDto> customRules = newArrayList();
List<RuleDefinitionDto> customRules = new ArrayList<>();

recorder.getRemaining().forEach(rule -> {
if (rule.isCustomRule()) {
@@ -681,6 +676,7 @@ public class RegisterRules implements Startable {
Optional<RuleDefinitionDto> template = dbClient.ruleDao().selectDefinitionById(templateId, dbSession);
if (template.isPresent() && template.get().getStatus() != RuleStatus.REMOVED) {
if (updateCustomRuleFromTemplateRule(customRule, template.get())) {
recorder.updated(customRule);
update(dbSession, customRule);
}
} else {
@@ -743,6 +739,10 @@ public class RegisterRules implements Startable {
customRule.setSeverity(templateRule.getSeverityString());
changed = true;
}
if (!StringUtils.equals(customRule.getRepositoryKey(), templateRule.getRepositoryKey())) {
customRule.setRepositoryKey(templateRule.getRepositoryKey());
changed = true;
}
return changed;
}

@@ -813,7 +813,7 @@ public class RegisterRules implements Startable {
.collect(Collectors.toSet());

checkState(incorrectRuleKeyMessage.isEmpty(), "An incorrect state of deprecated rule keys has been detected.\n %s",
lazyToString(() -> incorrectRuleKeyMessage.stream().collect(Collectors.joining("\n"))));
lazyToString(() -> String.join("\n", incorrectRuleKeyMessage)));
}

private static Stream<String> filterInvalidDeprecatedRuleKeys(ImmutableMap<RuleKey, SingleDeprecatedRuleKey> dbDeprecatedRuleKeysByOldRuleKey,
@@ -855,7 +855,7 @@ public class RegisterRules implements Startable {
Set<T> duplicates = new HashSet<>();
Set<T> uniques = new HashSet<>();

list.stream().forEach(t -> {
list.forEach(t -> {
if (!uniques.add(t)) {
duplicates.add(t);
}

+ 41
- 2
server/sonar-webserver-core/src/test/java/org/sonar/server/rule/RegisterRulesTest.java View File

@@ -460,6 +460,45 @@ public class RegisterRulesTest {
assertThat(ruleIndex.search(new RuleQuery().setQueryText("Name1"), new SearchOptions()).getTotal()).isEqualTo(0);
}

@Test
public void update_template_rule_key_should_also_update_custom_rules() {
when(system.now()).thenReturn(DATE1.getTime());
execute(context -> {
NewRepository repo = context.createRepository("squid", "java");
repo.createRule("rule")
.setName("Name1")
.setHtmlDescription("Description")
.setTemplate(true);
repo.done();
});

RuleDto rule1 = dbClient.ruleDao().selectOrFailByKey(db.getSession(), defaultOrganization, RuleKey.of("squid", "rule"));

// insert custom rule
dbClient.ruleDao().insert(db.getSession(), new RuleDefinitionDto()
.setRuleKey(RuleKey.of("squid", "custom"))
.setLanguage("java")
.setScope(Scope.ALL)
.setTemplateId(rule1.getId())
.setName("custom1"));
db.commit();

// re-key rule
execute(context -> {
NewRepository repo = context.createRepository("java", "java");
repo.createRule("rule")
.setName("Name1")
.setHtmlDescription("Description")
.addDeprecatedRuleKey("squid", "rule")
.setTemplate(true);
repo.done();
});

// template rule and custom rule have been updated
rule1 = dbClient.ruleDao().selectOrFailByKey(db.getSession(), defaultOrganization, RuleKey.of("java", "rule"));
RuleDto custom = dbClient.ruleDao().selectOrFailByKey(db.getSession(), defaultOrganization, RuleKey.of("java", "custom"));
}

@Test
public void update_if_rule_key_renamed_and_deprecated_key_declared() {
String ruleKey1 = "rule1";
@@ -1057,8 +1096,8 @@ public class RegisterRulesTest {
}

private void verifyIndicesMarkedAsInitialized() {
verify(metadataIndex).setInitialized(RuleIndexDefinition.TYPE_RULE,true);
verify(metadataIndex).setInitialized(RuleIndexDefinition.TYPE_RULE_EXTENSION,true);
verify(metadataIndex).setInitialized(RuleIndexDefinition.TYPE_RULE, true);
verify(metadataIndex).setInitialized(RuleIndexDefinition.TYPE_RULE_EXTENSION, true);
verify(metadataIndex).setInitialized(RuleIndexDefinition.TYPE_ACTIVE_RULE, true);
reset(metadataIndex);
}

Loading…
Cancel
Save