diff options
author | Duarte Meneses <duarte.meneses@sonarsource.com> | 2021-03-11 17:04:42 -0600 |
---|---|---|
committer | sonartech <sonartech@sonarsource.com> | 2021-03-17 20:08:34 +0000 |
commit | 398550aef256c12cd680795699890038af2dbf8d (patch) | |
tree | a0043bb86c3a3bfcf9357e8d5dbdb3ac68fd5859 /sonar-plugin-api-impl | |
parent | 4e76eae61a9cc708dde1e71d1895dfbb810f63ce (diff) | |
download | sonarqube-398550aef256c12cd680795699890038af2dbf8d.tar.gz sonarqube-398550aef256c12cd680795699890038af2dbf8d.zip |
SONAR-14192 Deprecating rule keys may break users' exclusion settings
Diffstat (limited to 'sonar-plugin-api-impl')
5 files changed, 99 insertions, 2 deletions
diff --git a/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/ActiveRulesBuilder.java b/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/ActiveRulesBuilder.java index 50de775d2cf..bdb93d0f7f0 100644 --- a/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/ActiveRulesBuilder.java +++ b/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/ActiveRulesBuilder.java @@ -21,7 +21,6 @@ package org.sonar.api.batch.rule.internal; import java.util.LinkedHashMap; import java.util.Map; -import org.sonar.api.batch.rule.ActiveRules; import org.sonar.api.rule.RuleKey; /** @@ -42,7 +41,7 @@ public class ActiveRulesBuilder { return this; } - public ActiveRules build() { + public DefaultActiveRules build() { return new DefaultActiveRules(map.values()); } } diff --git a/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/DefaultActiveRule.java b/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/DefaultActiveRule.java index eaf74a2bd53..ecfdaad4926 100644 --- a/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/DefaultActiveRule.java +++ b/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/DefaultActiveRule.java @@ -21,7 +21,9 @@ package org.sonar.api.batch.rule.internal; import java.util.Collections; import java.util.HashMap; +import java.util.HashSet; import java.util.Map; +import java.util.Set; import javax.annotation.concurrent.Immutable; import org.sonar.api.batch.rule.ActiveRule; import org.sonar.api.rule.RuleKey; @@ -37,6 +39,7 @@ public class DefaultActiveRule implements ActiveRule { private final long createdAt; private final long updatedAt; private final String qProfileKey; + private final Set<RuleKey> deprecatedKeys; public DefaultActiveRule(NewActiveRule newActiveRule) { this.severity = newActiveRule.severity; @@ -48,6 +51,7 @@ public class DefaultActiveRule implements ActiveRule { this.createdAt = newActiveRule.createdAt; this.updatedAt = newActiveRule.updatedAt; this.qProfileKey = newActiveRule.qProfileKey; + this.deprecatedKeys = Collections.unmodifiableSet(new HashSet<>(newActiveRule.deprecatedKeys)); } @Override @@ -98,4 +102,9 @@ public class DefaultActiveRule implements ActiveRule { public String qpKey() { return qProfileKey; } + + public Set<RuleKey> getDeprecatedKeys() { + // already immutable + return deprecatedKeys; + } } diff --git a/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/DefaultActiveRules.java b/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/DefaultActiveRules.java index bcfc1601d62..f6b12065580 100644 --- a/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/DefaultActiveRules.java +++ b/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/DefaultActiveRules.java @@ -23,16 +23,22 @@ import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.HashMap; +import java.util.LinkedHashMap; import java.util.List; import java.util.Map; +import java.util.Set; import java.util.stream.Collectors; import javax.annotation.concurrent.Immutable; import org.sonar.api.batch.rule.ActiveRule; import org.sonar.api.batch.rule.ActiveRules; import org.sonar.api.rule.RuleKey; +import org.sonar.api.utils.WildcardPattern; + +import static java.util.Collections.emptySet; @Immutable public class DefaultActiveRules implements ActiveRules { + private final Map<RuleKey, Set<String>> deprecatedRuleKeysByRuleKey = new LinkedHashMap<>(); private final Map<String, List<ActiveRule>> activeRulesByRepository = new HashMap<>(); private final Map<String, Map<String, ActiveRule>> activeRulesByRepositoryAndKey = new HashMap<>(); private final Map<String, Map<String, ActiveRule>> activeRulesByRepositoryAndInternalKey = new HashMap<>(); @@ -52,9 +58,19 @@ public class DefaultActiveRules implements ActiveRules { if (internalKey != null) { activeRulesByRepositoryAndInternalKey.computeIfAbsent(repo, r -> new HashMap<>()).put(internalKey, ar); } + + deprecatedRuleKeysByRuleKey.put(ar.ruleKey(), ar.getDeprecatedKeys().stream().map(RuleKey::toString).collect(Collectors.toSet())); } } + public Set<String> getDeprecatedRuleKeys(RuleKey ruleKey) { + return deprecatedRuleKeysByRuleKey.getOrDefault(ruleKey, emptySet()); + } + + public boolean matchesDeprecatedKeys(RuleKey ruleKey, WildcardPattern rulePattern) { + return getDeprecatedRuleKeys(ruleKey).contains(rulePattern.toString()); + } + @Override public ActiveRule find(RuleKey ruleKey) { return activeRulesByRepositoryAndKey.getOrDefault(ruleKey.repository(), Collections.emptyMap()) diff --git a/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/NewActiveRule.java b/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/NewActiveRule.java index d22819c643b..64b762a02e8 100644 --- a/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/NewActiveRule.java +++ b/sonar-plugin-api-impl/src/main/java/org/sonar/api/batch/rule/internal/NewActiveRule.java @@ -20,7 +20,9 @@ package org.sonar.api.batch.rule.internal; import java.util.HashMap; +import java.util.HashSet; import java.util.Map; +import java.util.Set; import javax.annotation.Nullable; import javax.annotation.concurrent.Immutable; import org.apache.commons.lang.StringUtils; @@ -42,6 +44,7 @@ public class NewActiveRule { final String language; final String templateRuleKey; final String qProfileKey; + final Set<RuleKey> deprecatedKeys; NewActiveRule(Builder builder) { this.ruleKey = builder.ruleKey; @@ -54,6 +57,7 @@ public class NewActiveRule { this.language = builder.language; this.templateRuleKey = builder.templateRuleKey; this.qProfileKey = builder.qProfileKey; + this.deprecatedKeys = builder.deprecatedKeys; } public RuleKey ruleKey() { @@ -71,6 +75,7 @@ public class NewActiveRule { private String language; private String templateRuleKey; private String qProfileKey; + private Set<RuleKey> deprecatedKeys = new HashSet<>(); public Builder setRuleKey(RuleKey ruleKey) { this.ruleKey = ruleKey; @@ -127,6 +132,11 @@ public class NewActiveRule { return this; } + public Builder setDeprecatedKeys(Set<RuleKey> deprecatedKeys) { + this.deprecatedKeys = deprecatedKeys; + return this; + } + public NewActiveRule build() { return new NewActiveRule(this); } diff --git a/sonar-plugin-api-impl/src/test/java/org/sonar/api/batch/rule/internal/DefaultActiveRulesTest.java b/sonar-plugin-api-impl/src/test/java/org/sonar/api/batch/rule/internal/DefaultActiveRulesTest.java new file mode 100644 index 00000000000..32a60c6c8b8 --- /dev/null +++ b/sonar-plugin-api-impl/src/test/java/org/sonar/api/batch/rule/internal/DefaultActiveRulesTest.java @@ -0,0 +1,63 @@ +/* + * SonarQube + * Copyright (C) 2009-2021 SonarSource SA + * mailto:info AT sonarsource DOT com + * + * This program 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. + * + * This program 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.api.batch.rule.internal; + +import com.google.common.collect.ImmutableSet; +import java.util.Collections; +import org.junit.Test; +import org.sonar.api.rule.RuleKey; +import org.sonar.api.utils.WildcardPattern; + +import static java.util.Collections.singleton; +import static org.assertj.core.api.Assertions.assertThat; + +public class DefaultActiveRulesTest { + private final RuleKey ruleKey = RuleKey.of("repo", "rule"); + + @Test + public void empty_returns_nothing() { + DefaultActiveRules underTest = new DefaultActiveRules(Collections.emptyList()); + + assertThat(underTest.getDeprecatedRuleKeys(ruleKey)).isEmpty(); + assertThat(underTest.matchesDeprecatedKeys(ruleKey, WildcardPattern.create("**"))).isFalse(); + } + + @Test + public void finds_match() { + DefaultActiveRules underTest = new DefaultActiveRules(ImmutableSet.of(new NewActiveRule.Builder() + .setRuleKey(ruleKey) + .setDeprecatedKeys(singleton(RuleKey.of("oldrepo", "oldrule"))) + .build())); + + assertThat(underTest.getDeprecatedRuleKeys(ruleKey)).containsOnly("oldrepo:oldrule"); + assertThat(underTest.matchesDeprecatedKeys(ruleKey, WildcardPattern.create("oldrepo:oldrule"))).isTrue(); + } + + @Test + public void finds_match_with_multiple_deprecated_keys() { + DefaultActiveRules underTest = new DefaultActiveRules(ImmutableSet.of(new NewActiveRule.Builder() + .setRuleKey(ruleKey) + .setDeprecatedKeys(ImmutableSet.of(RuleKey.of("oldrepo", "oldrule"), (RuleKey.of("oldrepo2", "oldrule2")))) + .build())); + + assertThat(underTest.getDeprecatedRuleKeys(ruleKey)).containsOnly("oldrepo:oldrule", "oldrepo2:oldrule2"); + assertThat(underTest.matchesDeprecatedKeys(ruleKey, WildcardPattern.create("oldrepo:oldrule"))).isTrue(); + } +} |