Browse Source

SONAR-12508 Remove RuleRepository and RuleI18n APIs deprecated since 4.2

tags/8.1.0.31237
Duarte Meneses 4 years ago
parent
commit
c7a8da830b

+ 0
- 2
server/sonar-ce/src/main/java/org/sonar/ce/container/ComputeEngineContainerImpl.java View File

@@ -70,7 +70,6 @@ import org.sonar.core.component.DefaultResourceTypes;
import org.sonar.core.config.CorePropertyDefinitions;
import org.sonar.core.extension.CoreExtensionRepositoryImpl;
import org.sonar.core.extension.CoreExtensionsLoader;
import org.sonar.core.i18n.RuleI18nManager;
import org.sonar.core.platform.ComponentContainer;
import org.sonar.core.platform.EditionProvider;
import org.sonar.core.platform.Module;
@@ -341,7 +340,6 @@ public class ComputeEngineContainerImpl implements ComputeEngineContainer {

// depends on plugins
ServerI18n.class, // used by RuleI18nManager
RuleI18nManager.class, // used by DebtRulesXMLImporter
Durations.class // used in Web Services and DebtCalculator
);
}

+ 1
- 1
server/sonar-ce/src/test/java/org/sonar/ce/container/ComputeEngineContainerImplTest.java View File

@@ -123,7 +123,7 @@ public class ComputeEngineContainerImplTest {
assertThat(picoContainer.getParent().getParent().getComponentAdapters()).hasSize(
CONTAINER_ITSELF
+ 6 // MigrationConfigurationModule
+ 16 // level 2
+ 15 // level 2
);
assertThat(picoContainer.getParent().getParent().getParent().getComponentAdapters()).hasSize(
COMPONENTS_IN_LEVEL_1_AT_CONSTRUCTION

+ 0
- 216
server/sonar-webserver-core/src/main/java/org/sonar/server/rule/DeprecatedRulesDefinitionLoader.java View File

@@ -1,216 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2019 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.server.rule;

import com.google.common.base.Predicate;
import com.google.common.collect.Iterables;
import java.io.Reader;
import java.util.Collection;
import java.util.List;
import javax.annotation.CheckForNull;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang.StringUtils;
import org.sonar.api.rule.RuleKey;
import org.sonar.api.rule.RuleStatus;
import org.sonar.api.rules.RuleParam;
import org.sonar.api.rules.RuleRepository;
import org.sonar.api.server.ServerSide;
import org.sonar.api.server.debt.DebtRemediationFunction;
import org.sonar.api.server.rule.RuleParamType;
import org.sonar.api.server.rule.RulesDefinition;
import org.sonar.api.utils.ValidationMessages;
import org.sonar.api.utils.log.Logger;
import org.sonar.api.utils.log.Loggers;
import org.sonar.core.i18n.RuleI18nManager;
import org.sonar.server.debt.DebtModelPluginRepository;
import org.sonar.server.debt.DebtModelXMLExporter;
import org.sonar.server.debt.DebtModelXMLExporter.RuleDebt;
import org.sonar.server.debt.DebtRulesXMLImporter;
import org.sonar.server.plugins.ServerPluginRepository;

import static com.google.common.collect.Lists.newArrayList;

/**
* Inject deprecated RuleRepository into {@link org.sonar.api.server.rule.RulesDefinition} for backward-compatibility.
*/
@ServerSide
public class DeprecatedRulesDefinitionLoader {

private static final Logger LOG = Loggers.get(DeprecatedRulesDefinitionLoader.class);

private final RuleI18nManager i18n;
private final RuleRepository[] repositories;

private final DebtModelPluginRepository languageModelFinder;
private final DebtRulesXMLImporter importer;
private final ServerPluginRepository serverPluginRepository;

public DeprecatedRulesDefinitionLoader(RuleI18nManager i18n, DebtModelPluginRepository languageModelFinder, DebtRulesXMLImporter importer,
ServerPluginRepository serverPluginRepository, RuleRepository[] repositories) {
this.i18n = i18n;
this.serverPluginRepository = serverPluginRepository;
this.repositories = repositories;
this.languageModelFinder = languageModelFinder;
this.importer = importer;
}

/**
* Used when no deprecated repositories
*/
public DeprecatedRulesDefinitionLoader(RuleI18nManager i18n, DebtModelPluginRepository languageModelFinder, DebtRulesXMLImporter importer,
ServerPluginRepository serverPluginRepository) {
this(i18n, languageModelFinder, importer, serverPluginRepository, new RuleRepository[0]);
}

void complete(RulesDefinition.Context context) {
// Load rule debt definitions from xml files provided by plugin
List<RuleDebt> ruleDebts = loadRuleDebtList();

for (RuleRepository repository : repositories) {
context.setCurrentPluginKey(serverPluginRepository.getPluginKey(repository));
// RuleRepository API does not handle difference between new and extended repositories,
RulesDefinition.NewRepository newRepository;
if (context.repository(repository.getKey()) == null) {
newRepository = context.createRepository(repository.getKey(), repository.getLanguage());
newRepository.setName(repository.getName());
} else {
newRepository = context.extendRepository(repository.getKey(), repository.getLanguage());
}
for (org.sonar.api.rules.Rule rule : repository.createRules()) {
RulesDefinition.NewRule newRule = newRepository.createRule(rule.getKey());
newRule.setName(ruleName(repository.getKey(), rule));
newRule.setHtmlDescription(ruleDescription(repository.getKey(), rule));
newRule.setInternalKey(rule.getConfigKey());
newRule.setTemplate(rule.isTemplate());
newRule.setSeverity(rule.getSeverity().toString());
newRule.setStatus(rule.getStatus() == null ? RuleStatus.defaultStatus() : RuleStatus.valueOf(rule.getStatus()));
newRule.setTags(rule.getTags());
for (RuleParam param : rule.getParams()) {
RulesDefinition.NewParam newParam = newRule.createParam(param.getKey());
newParam.setDefaultValue(param.getDefaultValue());
newParam.setDescription(paramDescription(repository.getKey(), rule.getKey(), param));
newParam.setType(RuleParamType.parse(param.getType()));
}
updateRuleDebtDefinitions(newRule, repository.getKey(), rule.getKey(), ruleDebts);
}
newRepository.done();
}
}

private static void updateRuleDebtDefinitions(RulesDefinition.NewRule newRule, String repoKey, String ruleKey, List<RuleDebt> ruleDebts) {
RuleDebt ruleDebt = findRequirement(ruleDebts, repoKey, ruleKey);
if (ruleDebt != null) {
newRule.setDebtRemediationFunction(remediationFunction(DebtRemediationFunction.Type.valueOf(ruleDebt.function()),
ruleDebt.coefficient(),
ruleDebt.offset(),
newRule.debtRemediationFunctions(),
repoKey, ruleKey));
}
}

private static DebtRemediationFunction remediationFunction(DebtRemediationFunction.Type function, @Nullable String coefficient, @Nullable String offset,
RulesDefinition.DebtRemediationFunctions functions, String repoKey, String ruleKey) {
if (DebtRemediationFunction.Type.LINEAR.equals(function) && coefficient != null) {
return functions.linear(coefficient);
} else if (DebtRemediationFunction.Type.CONSTANT_ISSUE.equals(function) && offset != null) {
return functions.constantPerIssue(offset);
} else if (DebtRemediationFunction.Type.LINEAR_OFFSET.equals(function) && coefficient != null && offset != null) {
return functions.linearWithOffset(coefficient, offset);
} else {
throw new IllegalArgumentException(String.format("Debt definition on rule '%s:%s' is invalid", repoKey, ruleKey));
}
}

@CheckForNull
private String ruleName(String repositoryKey, org.sonar.api.rules.Rule rule) {
String name = i18n.getName(repositoryKey, rule.getKey());
if (StringUtils.isNotBlank(name)) {
return name;
}
return StringUtils.defaultIfBlank(rule.getName(), null);
}

@CheckForNull
private String ruleDescription(String repositoryKey, org.sonar.api.rules.Rule rule) {
String description = i18n.getDescription(repositoryKey, rule.getKey());
if (StringUtils.isNotBlank(description)) {
return description;
}
return StringUtils.defaultIfBlank(rule.getDescription(), null);
}

@CheckForNull
private String paramDescription(String repositoryKey, String ruleKey, RuleParam param) {
String desc = StringUtils.defaultIfEmpty(
i18n.getParamDescription(repositoryKey, ruleKey, param.getKey()),
param.getDescription());
return StringUtils.defaultIfBlank(desc, null);
}

public List<DebtModelXMLExporter.RuleDebt> loadRuleDebtList() {
List<RuleDebt> ruleDebtList = newArrayList();
for (String pluginKey : getContributingPluginListWithoutSqale()) {
ruleDebtList.addAll(loadRuleDebtsFromXml(pluginKey));
}
return ruleDebtList;
}

public List<RuleDebt> loadRuleDebtsFromXml(String pluginKey) {
Reader xmlFileReader = null;
try {
xmlFileReader = languageModelFinder.createReaderForXMLFile(pluginKey);
ValidationMessages validationMessages = ValidationMessages.create();
List<RuleDebt> rules = importer.importXML(xmlFileReader, validationMessages);
validationMessages.log(LOG);
return rules;
} finally {
IOUtils.closeQuietly(xmlFileReader);
}
}

private Collection<String> getContributingPluginListWithoutSqale() {
Collection<String> pluginList = newArrayList(languageModelFinder.getContributingPluginList());
pluginList.remove(DebtModelPluginRepository.DEFAULT_MODEL);
return pluginList;
}

@CheckForNull
private static RuleDebt findRequirement(List<RuleDebt> requirements, final String repoKey, final String ruleKey) {
return Iterables.find(requirements, new RuleDebtMatchRepoKeyAndRuleKey(repoKey, ruleKey), null);
}

private static class RuleDebtMatchRepoKeyAndRuleKey implements Predicate<RuleDebt> {

private final String repoKey;
private final String ruleKey;

public RuleDebtMatchRepoKeyAndRuleKey(String repoKey, String ruleKey) {
this.repoKey = repoKey;
this.ruleKey = ruleKey;
}

@Override
public boolean apply(@Nonnull RuleDebt input) {
return input.ruleKey().equals(RuleKey.of(repoKey, ruleKey));
}
}
}

+ 3
- 8
server/sonar-webserver-core/src/main/java/org/sonar/server/rule/RuleDefinitionsLoader.java View File

@@ -29,14 +29,11 @@ import org.sonar.server.plugins.ServerPluginRepository;
*/
public class RuleDefinitionsLoader {

private final DeprecatedRulesDefinitionLoader deprecatedDefConverter;
private final CommonRuleDefinitions coreCommonDefs;
private final RulesDefinition[] pluginDefs;
private final ServerPluginRepository serverPluginRepository;

public RuleDefinitionsLoader(DeprecatedRulesDefinitionLoader deprecatedDefConverter,
CommonRuleDefinitions coreCommonDefs, ServerPluginRepository serverPluginRepository, RulesDefinition[] pluginDefs) {
this.deprecatedDefConverter = deprecatedDefConverter;
public RuleDefinitionsLoader(CommonRuleDefinitions coreCommonDefs, ServerPluginRepository serverPluginRepository, RulesDefinition[] pluginDefs) {
this.coreCommonDefs = coreCommonDefs;
this.serverPluginRepository = serverPluginRepository;
this.pluginDefs = pluginDefs;
@@ -45,9 +42,8 @@ public class RuleDefinitionsLoader {
/**
* Used when no definitions at all.
*/
public RuleDefinitionsLoader(DeprecatedRulesDefinitionLoader converter,
CommonRuleDefinitions coreCommonDefs, ServerPluginRepository serverPluginRepository) {
this(converter, coreCommonDefs, serverPluginRepository, new RulesDefinition[0]);
public RuleDefinitionsLoader(CommonRuleDefinitions coreCommonDefs, ServerPluginRepository serverPluginRepository) {
this(coreCommonDefs, serverPluginRepository, new RulesDefinition[0]);
}

public RulesDefinition.Context load() {
@@ -56,7 +52,6 @@ public class RuleDefinitionsLoader {
context.setCurrentPluginKey(serverPluginRepository.getPluginKey(pluginDefinition));
pluginDefinition.define(context);
}
deprecatedDefConverter.complete(context);
context.setCurrentPluginKey(null);
coreCommonDefs.define(context);
return context;

+ 0
- 219
server/sonar-webserver-core/src/test/java/org/sonar/server/rule/DeprecatedRulesDefinitionLoaderTest.java View File

@@ -1,219 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2019 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.server.rule;

import java.io.Reader;
import java.util.Arrays;
import java.util.List;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.runners.MockitoJUnitRunner;
import org.sonar.api.rule.RuleKey;
import org.sonar.api.rule.RuleStatus;
import org.sonar.api.rule.Severity;
import org.sonar.api.rules.Rule;
import org.sonar.api.rules.RulePriority;
import org.sonar.api.rules.RuleRepository;
import org.sonar.api.server.debt.DebtRemediationFunction;
import org.sonar.api.server.rule.RulesDefinition;
import org.sonar.api.utils.ValidationMessages;
import org.sonar.core.i18n.RuleI18nManager;
import org.sonar.api.impl.server.RulesDefinitionContext;
import org.sonar.server.debt.DebtModelPluginRepository;
import org.sonar.server.debt.DebtModelXMLExporter;
import org.sonar.server.debt.DebtRulesXMLImporter;
import org.sonar.server.plugins.ServerPluginRepository;

import static com.google.common.collect.Lists.newArrayList;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.fail;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;

@RunWith(MockitoJUnitRunner.class)
public class DeprecatedRulesDefinitionLoaderTest {

@Mock
RuleI18nManager i18n;

@Mock
DebtModelPluginRepository debtModelRepository;

@Mock
DebtRulesXMLImporter importer;

@Mock
ServerPluginRepository pluginRepository;

static class CheckstyleRules extends RuleRepository {
public CheckstyleRules() {
super("checkstyle", "java");
setName("Checkstyle");
}

@Override
public List<Rule> createRules() {
Rule rule = Rule.create("checkstyle", "ConstantName", "Constant Name");
rule.setDescription("Checks that constant names conform to the specified format");
rule.setConfigKey("Checker/TreeWalker/ConstantName");
rule.setSeverity(RulePriority.BLOCKER);
rule.setStatus(Rule.STATUS_BETA);
rule.setTags(new String[] {"style", "clumsy"});
rule.createParameter("format").setDescription("Regular expression").setDefaultValue("A-Z").setType("REGULAR_EXPRESSION");
return Arrays.asList(rule);
}
}

static class UseBundles extends RuleRepository {
public UseBundles() {
super("checkstyle", "java");
setName("Checkstyle");
}

@Override
public List<Rule> createRules() {
Rule rule = Rule.create("checkstyle", "ConstantName");
rule.createParameter("format");
return Arrays.asList(rule);
}
}

@Test
public void wrap_deprecated_rule_repositories() {
RulesDefinition.Context context = new RulesDefinitionContext();
CheckstyleRules checkstyleRules = new CheckstyleRules();
when(pluginRepository.getPluginKey(checkstyleRules)).thenReturn("unittest");
new DeprecatedRulesDefinitionLoader(i18n, debtModelRepository, importer, pluginRepository, new RuleRepository[] {checkstyleRules}).complete(context);

assertThat(context.repositories()).hasSize(1);
RulesDefinition.Repository checkstyle = context.repository("checkstyle");
assertThat(checkstyle).isNotNull();
assertThat(checkstyle.key()).isEqualTo("checkstyle");
assertThat(checkstyle.name()).isEqualTo("Checkstyle");
assertThat(checkstyle.language()).isEqualTo("java");
assertThat(checkstyle.rules()).hasSize(1);
RulesDefinition.Rule rule = checkstyle.rule("ConstantName");
assertThat(rule).isNotNull();
assertThat(rule.key()).isEqualTo("ConstantName");
assertThat(rule.pluginKey()).isEqualTo("unittest");
assertThat(rule.name()).isEqualTo("Constant Name");
assertThat(rule.htmlDescription()).isEqualTo("Checks that constant names conform to the specified format");
assertThat(rule.severity()).isEqualTo(Severity.BLOCKER);
assertThat(rule.internalKey()).isEqualTo("Checker/TreeWalker/ConstantName");
assertThat(rule.status()).isEqualTo(RuleStatus.BETA);
assertThat(rule.tags()).containsOnly("style", "clumsy");
assertThat(rule.params()).hasSize(1);
RulesDefinition.Param param = rule.param("format");
assertThat(param).isNotNull();
assertThat(param.key()).isEqualTo("format");
assertThat(param.name()).isEqualTo("format");
assertThat(param.description()).isEqualTo("Regular expression");
assertThat(param.defaultValue()).isEqualTo("A-Z");
}

@Test
public void emulate_the_day_deprecated_api_can_be_dropped() {
RulesDefinition.Context context = new RulesDefinitionContext();

// no more RuleRepository !
new DeprecatedRulesDefinitionLoader(i18n, debtModelRepository, importer, pluginRepository);

assertThat(context.repositories()).isEmpty();
}

@Test
public void use_l10n_bundles() {
RulesDefinition.Context context = new RulesDefinitionContext();
when(i18n.getName("checkstyle", "ConstantName")).thenReturn("Constant Name");
when(i18n.getDescription("checkstyle", "ConstantName")).thenReturn("Checks that constant names conform to the specified format");
when(i18n.getParamDescription("checkstyle", "ConstantName", "format")).thenReturn("Regular expression");

new DeprecatedRulesDefinitionLoader(i18n, debtModelRepository, importer, pluginRepository, new RuleRepository[] {new UseBundles()}).complete(context);

RulesDefinition.Repository checkstyle = context.repository("checkstyle");
RulesDefinition.Rule rule = checkstyle.rule("ConstantName");
assertThat(rule.key()).isEqualTo("ConstantName");
assertThat(rule.name()).isEqualTo("Constant Name");
assertThat(rule.htmlDescription()).isEqualTo("Checks that constant names conform to the specified format");
RulesDefinition.Param param = rule.param("format");
assertThat(param.key()).isEqualTo("format");
assertThat(param.name()).isEqualTo("format");
assertThat(param.description()).isEqualTo("Regular expression");
}

@Test
public void define_rule_debt() {
RulesDefinition.Context context = new RulesDefinitionContext();

List<DebtModelXMLExporter.RuleDebt> ruleDebts = newArrayList(
new DebtModelXMLExporter.RuleDebt()
.setRuleKey(RuleKey.of("checkstyle", "ConstantName"))
.setFunction(DebtRemediationFunction.Type.LINEAR_OFFSET.name())
.setCoefficient("1d")
.setOffset("10min"));

Reader javaModelReader = mock(Reader.class);
when(debtModelRepository.createReaderForXMLFile("java")).thenReturn(javaModelReader);
when(debtModelRepository.getContributingPluginList()).thenReturn(newArrayList("java"));
when(importer.importXML(eq(javaModelReader), any(ValidationMessages.class))).thenReturn(ruleDebts);

new DeprecatedRulesDefinitionLoader(i18n, debtModelRepository, importer, pluginRepository, new RuleRepository[] {new CheckstyleRules()}).complete(context);

assertThat(context.repositories()).hasSize(1);
RulesDefinition.Repository checkstyle = context.repository("checkstyle");
assertThat(checkstyle.rules()).hasSize(1);

RulesDefinition.Rule rule = checkstyle.rule("ConstantName");
assertThat(rule).isNotNull();
assertThat(rule.key()).isEqualTo("ConstantName");
assertThat(rule.debtRemediationFunction().type()).isEqualTo(DebtRemediationFunction.Type.LINEAR_OFFSET);
assertThat(rule.debtRemediationFunction().gapMultiplier()).isEqualTo("1d");
assertThat(rule.debtRemediationFunction().baseEffort()).isEqualTo("10min");
}

@Test
public void fail_on_invalid_rule_debt() {
RulesDefinition.Context context = new RulesDefinitionContext();

List<DebtModelXMLExporter.RuleDebt> ruleDebts = newArrayList(
new DebtModelXMLExporter.RuleDebt()
.setRuleKey(RuleKey.of("checkstyle", "ConstantName"))
.setFunction(DebtRemediationFunction.Type.LINEAR_OFFSET.name())
.setCoefficient("1d"));

Reader javaModelReader = mock(Reader.class);
when(debtModelRepository.createReaderForXMLFile("java")).thenReturn(javaModelReader);
when(debtModelRepository.getContributingPluginList()).thenReturn(newArrayList("java"));
when(importer.importXML(eq(javaModelReader), any(ValidationMessages.class))).thenReturn(ruleDebts);

try {
new DeprecatedRulesDefinitionLoader(i18n, debtModelRepository, importer, pluginRepository, new RuleRepository[] {new CheckstyleRules()}).complete(context);
fail();
} catch (Exception e) {
assertThat(e).isInstanceOf(IllegalArgumentException.class);
}

assertThat(context.repositories()).isEmpty();
}

}

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

@@ -1019,7 +1019,7 @@ public class RegisterRulesTest {
private void execute(RulesDefinition... defs) {
ServerPluginRepository pluginRepository = mock(ServerPluginRepository.class);
when(pluginRepository.getPluginKey(any(RulesDefinition.class))).thenReturn(FAKE_PLUGIN_KEY);
RuleDefinitionsLoader loader = new RuleDefinitionsLoader(mock(DeprecatedRulesDefinitionLoader.class), mock(CommonRuleDefinitionsImpl.class), pluginRepository,
RuleDefinitionsLoader loader = new RuleDefinitionsLoader(mock(CommonRuleDefinitionsImpl.class), pluginRepository,
defs);
Languages languages = mock(Languages.class);
when(languages.get(any())).thenReturn(mock(Language.class));

+ 4
- 4
server/sonar-webserver-core/src/test/java/org/sonar/server/rule/RuleDefinitionsLoaderTest.java View File

@@ -31,7 +31,7 @@ public class RuleDefinitionsLoaderTest {
@Test
public void no_definitions() {
CommonRuleDefinitions commonRulesDefinitions = mock(CommonRuleDefinitions.class);
RulesDefinition.Context context = new RuleDefinitionsLoader(mock(DeprecatedRulesDefinitionLoader.class), commonRulesDefinitions, mock(ServerPluginRepository.class)).load();
RulesDefinition.Context context = new RuleDefinitionsLoader(commonRulesDefinitions, mock(ServerPluginRepository.class)).load();

assertThat(context.repositories()).isEmpty();
}
@@ -39,7 +39,7 @@ public class RuleDefinitionsLoaderTest {
@Test
public void load_definitions() {
CommonRuleDefinitions commonRulesDefinitions = mock(CommonRuleDefinitions.class);
RulesDefinition.Context context = new RuleDefinitionsLoader(mock(DeprecatedRulesDefinitionLoader.class), commonRulesDefinitions, mock(ServerPluginRepository.class),
RulesDefinition.Context context = new RuleDefinitionsLoader(commonRulesDefinitions, mock(ServerPluginRepository.class),
new RulesDefinition[] {
new FindbugsDefinitions(), new SquidDefinitions()
}).load();
@@ -52,7 +52,7 @@ public class RuleDefinitionsLoaderTest {
@Test
public void define_common_rules() {
CommonRuleDefinitions commonRulesDefinitions = new FakeCommonRuleDefinitions();
RulesDefinition.Context context = new RuleDefinitionsLoader(mock(DeprecatedRulesDefinitionLoader.class), commonRulesDefinitions, mock(ServerPluginRepository.class),
RulesDefinition.Context context = new RuleDefinitionsLoader(commonRulesDefinitions, mock(ServerPluginRepository.class),
new RulesDefinition[] {
new SquidDefinitions()
}).load();
@@ -68,7 +68,7 @@ public class RuleDefinitionsLoaderTest {
@Test
public void plugin_common_rules_are_overridden() {
CommonRuleDefinitions commonRulesDefinitions = new FakeCommonRuleDefinitions();
RulesDefinition.Context context = new RuleDefinitionsLoader(mock(DeprecatedRulesDefinitionLoader.class), commonRulesDefinitions, mock(ServerPluginRepository.class),
RulesDefinition.Context context = new RuleDefinitionsLoader(commonRulesDefinitions, mock(ServerPluginRepository.class),
new RulesDefinition[] {
new PluginCommonRuleDefinitions()
}).load();

+ 0
- 2
server/sonar-webserver/src/main/java/org/sonar/server/platform/platformlevel/PlatformLevel2.java View File

@@ -21,7 +21,6 @@ package org.sonar.server.platform.platformlevel;

import org.sonar.api.utils.Durations;
import org.sonar.core.extension.CoreExtensionsInstaller;
import org.sonar.core.i18n.RuleI18nManager;
import org.sonar.core.platform.ComponentContainer;
import org.sonar.core.platform.PluginClassloaderFactory;
import org.sonar.core.platform.PluginLoader;
@@ -81,7 +80,6 @@ public class PlatformLevel2 extends PlatformLevel {

// depends on plugins
ServerI18n.class,
RuleI18nManager.class,

OfficialDistribution.class);


+ 0
- 2
server/sonar-webserver/src/main/java/org/sonar/server/platform/platformlevel/PlatformLevel4.java View File

@@ -172,7 +172,6 @@ import org.sonar.server.qualityprofile.index.ActiveRuleIndexer;
import org.sonar.server.qualityprofile.ws.QProfilesWsModule;
import org.sonar.server.root.ws.RootWsModule;
import org.sonar.server.rule.CommonRuleDefinitionsImpl;
import org.sonar.server.rule.DeprecatedRulesDefinitionLoader;
import org.sonar.server.rule.RuleCreator;
import org.sonar.server.rule.RuleDefinitionsLoader;
import org.sonar.server.rule.RuleUpdater;
@@ -303,7 +302,6 @@ public class PlatformLevel4 extends PlatformLevel {
AnnotationRuleParser.class,
XMLRuleParser.class,
WebServerRuleFinderImpl.class,
DeprecatedRulesDefinitionLoader.class,
RuleDefinitionsLoader.class,
CommonRuleDefinitionsImpl.class,
RulesDefinitionXmlLoader.class,

+ 0
- 134
sonar-core/src/main/java/org/sonar/core/i18n/RuleI18nManager.java View File

@@ -1,134 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2019 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.core.i18n;

import java.util.Locale;
import javax.annotation.CheckForNull;
import org.apache.commons.lang.StringUtils;
import org.sonar.api.ce.ComputeEngineSide;
import org.sonar.api.i18n.RuleI18n;
import org.sonar.api.rules.Rule;
import org.sonar.api.server.ServerSide;

/**
* @deprecated in 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Deprecated
@ServerSide
@ComputeEngineSide
public class RuleI18nManager implements RuleI18n {

private static final String NAME_SUFFIX = ".name";
private static final String RULE_PREFIX = "rule.";

private DefaultI18n defaultI18n;

public RuleI18nManager(DefaultI18n defaultI18n) {
this.defaultI18n = defaultI18n;
}

/**
* @deprecated in 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Override
@Deprecated
public String getName(String repositoryKey, String ruleKey, Locale locale) {
return getName(repositoryKey, ruleKey);
}

/**
* @deprecated in 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Override
@Deprecated
public String getName(Rule rule, Locale locale) {
return getName(rule);
}

/**
* @deprecated in 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Override
@Deprecated
public String getDescription(String repositoryKey, String ruleKey, Locale locale) {
return getDescription(repositoryKey, ruleKey);
}

/**
* @deprecated in 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Override
@Deprecated
public String getParamDescription(String repositoryKey, String ruleKey, String paramKey, Locale locale) {
return getParamDescription(repositoryKey, ruleKey, paramKey);
}

@Override
@CheckForNull
public String getName(String repositoryKey, String ruleKey) {
return message(repositoryKey, ruleKey, NAME_SUFFIX);
}

@Override
@CheckForNull
public String getName(Rule rule) {
String name = message(rule.getRepositoryKey(), rule.getKey(), NAME_SUFFIX);
return name != null ? name : rule.getName();
}

@Override
public String getDescription(String repositoryKey, String ruleKey) {
String relatedProperty = new StringBuilder().append(RULE_PREFIX).append(repositoryKey).append(".").append(ruleKey).append(NAME_SUFFIX).toString();

String ruleDescriptionFilePath = "rules/" + repositoryKey + "/" + ruleKey + ".html";
String description = defaultI18n.messageFromFile(Locale.ENGLISH, ruleDescriptionFilePath, relatedProperty);
if (description == null) {
// Following line is to ensure backward compatibility (SONAR-3319)
description = lookUpDescriptionInFormerLocation(ruleKey, relatedProperty);
}
return description;
}

/*
* Method used to ensure backward compatibility for language plugins that store HTML rule description files in the former
* location (which was used prior to Sonar 3.0).
*
* See http://jira.sonarsource.com/browse/SONAR-3319
*/
private String lookUpDescriptionInFormerLocation(String ruleKey, String relatedProperty) {
return defaultI18n.messageFromFile(Locale.ENGLISH, ruleKey + ".html", relatedProperty);
}

@Override
@CheckForNull
public String getParamDescription(String repositoryKey, String ruleKey, String paramKey) {
return message(repositoryKey, ruleKey, ".param." + paramKey);
}

@CheckForNull
String message(String repositoryKey, String ruleKey, String suffix) {
String propertyKey = new StringBuilder().append(RULE_PREFIX).append(repositoryKey).append(".").append(ruleKey).append(suffix).toString();
return defaultI18n.message(Locale.ENGLISH, propertyKey, null);
}

static boolean isRuleProperty(String propertyKey) {
return StringUtils.startsWith(propertyKey, RULE_PREFIX) && StringUtils.endsWith(propertyKey, NAME_SUFFIX) && !propertyKey.contains(".param.");
}
}

+ 0
- 113
sonar-core/src/test/java/org/sonar/core/i18n/RuleI18nManagerTest.java View File

@@ -1,113 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2019 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.core.i18n;

import java.util.Locale;
import org.junit.Test;

import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.verifyNoMoreInteractions;
import static org.mockito.Mockito.when;

public class RuleI18nManagerTest {

@Test
public void shouldGetName() {
DefaultI18n i18n = mock(DefaultI18n.class);
RuleI18nManager ruleI18n = new RuleI18nManager(i18n);

ruleI18n.getName("checkstyle", "com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck", Locale.ENGLISH);

String propertyKey = "rule.checkstyle.com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.name";
verify(i18n).message(Locale.ENGLISH, propertyKey, null /* no default value */);
verifyNoMoreInteractions(i18n);
}

@Test
public void shouldGetParamDescription() {
DefaultI18n i18n = mock(DefaultI18n.class);
RuleI18nManager ruleI18n = new RuleI18nManager(i18n);

ruleI18n.getParamDescription("checkstyle", "com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck", "pattern", Locale.ENGLISH);

String propertyKey = "rule.checkstyle.com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.param.pattern";
verify(i18n).message(Locale.ENGLISH, propertyKey, null /* no default value */);
verifyNoMoreInteractions(i18n);
}

@Test
public void shouldGetDescriptionFromFile() {
String propertyKeyForName = "rule.checkstyle.com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.name";

DefaultI18n i18n = mock(DefaultI18n.class);
when(i18n.messageFromFile(Locale.ENGLISH, "rules/checkstyle/com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.html", propertyKeyForName)).thenReturn(
"Description");

RuleI18nManager ruleI18n = new RuleI18nManager(i18n);
String description = ruleI18n.getDescription("checkstyle", "com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck", Locale.ENGLISH);
assertThat(description).isEqualTo("Description");

verify(i18n).messageFromFile(Locale.ENGLISH, "rules/checkstyle/com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.html", propertyKeyForName);
verifyNoMoreInteractions(i18n);
}

// see http://jira.sonarsource.com/browse/SONAR-3319
@Test
public void shouldGetDescriptionFromFileWithBackwardCompatibility() {
String propertyKeyForName = "rule.checkstyle.com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.name";

DefaultI18n i18n = mock(DefaultI18n.class);
// this is the "old" way of storing HTML description files for rules (they are not in the "rules/<repo-key>" folder)
when(i18n.messageFromFile(Locale.ENGLISH, "com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.html", propertyKeyForName)).thenReturn("Description");

RuleI18nManager ruleI18n = new RuleI18nManager(i18n);
String description = ruleI18n.getDescription("checkstyle", "com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck", Locale.ENGLISH);
assertThat(description).isEqualTo("Description");

verify(i18n).messageFromFile(Locale.ENGLISH, "rules/checkstyle/com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.html", propertyKeyForName);
verify(i18n).messageFromFile(Locale.ENGLISH, "com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.html", propertyKeyForName);
verifyNoMoreInteractions(i18n);
}

@Test
public void shoudlReturnNullIfMissingDescription() {
DefaultI18n i18n = mock(DefaultI18n.class);
RuleI18nManager ruleI18n = new RuleI18nManager(i18n);

assertThat(ruleI18n.getDescription("checkstyle", "com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck", Locale.ENGLISH)).isNull();
}

@Test
public void shouldBeRuleKey() {
assertThat(RuleI18nManager.isRuleProperty("rule.checkstyle.com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.name")).isTrue();
assertThat(RuleI18nManager.isRuleProperty("rule.pmd.Header.name")).isTrue();
}

@Test
public void shouldNotBeRuleKey() {
// this is the parameter "name"
assertThat(RuleI18nManager.isRuleProperty("rule.checkstyle.com.puppycrawl.tools.checkstyle.checks.annotation.AnnotationUseStyleCheck.param.name")).isFalse();
assertThat(RuleI18nManager.isRuleProperty("by")).isFalse();
assertThat(RuleI18nManager.isRuleProperty("something.else")).isFalse();
assertThat(RuleI18nManager.isRuleProperty("checkstyle.page.name")).isFalse();
}
}

+ 0
- 152
sonar-plugin-api/src/main/java/org/sonar/api/i18n/RuleI18n.java View File

@@ -1,152 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2019 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.i18n;

import java.util.Locale;
import javax.annotation.CheckForNull;
import org.sonar.api.ce.ComputeEngineSide;
import org.sonar.api.rules.Rule;
import org.sonar.api.server.ServerSide;

/**
* {@link I18n}-companion component that provides translation facilities for rule names, descriptions and parameter names.
*
* @since 3.2
* @deprecated in 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Deprecated
@ServerSide
@ComputeEngineSide
public interface RuleI18n {

/**
* Returns the localized name of the rule identified by its repository key and rule key.
* <br>
* If the name is not found in the given locale, then the default name is returned (the English one).
* This method could return null if no default name found. This is the cause for instance the copies rules.
*
* @param repositoryKey the repository key
* @param ruleKey the rule key
* @param locale not used
* @return the translated name of the rule, or the default English one if the given locale is not supported, or null
* @deprecated since 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Deprecated
@CheckForNull
String getName(String repositoryKey, String ruleKey, Locale locale);

/**
* Returns the name of the rule identified by its repository key and rule key.
* <br>
* This method could return null if no default name found. This is the cause for instance the copies rules.
*
* @param repositoryKey the repository key
* @param ruleKey the rule key
* @return the nullable name of the rule
* @since 4.1
*/
@CheckForNull
String getName(String repositoryKey, String ruleKey);

/**
* Returns the localized name or the name of the rule.
* <br>
* If the name is not found in the given locale, then the default name is returned (the English one).
* It the default name is not found, then the rule name is returned.
*
* @param rule the rule
* @param locale the locale to translate into
* @return the translated name of the rule, or the default English one if the given locale is not supported, or the rule name.
* @deprecated since 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Deprecated
@CheckForNull
String getName(Rule rule, Locale locale);

/**
* Returns the name of the rule.
* <br>
* It the default name is not found, then the rule name is returned.
*
* @param rule the rule
* @return the nullable name of the rule
* @since 4.1
*/
@CheckForNull
String getName(Rule rule);

/**
* Returns the localized description of the rule identified by its repository key and rule key.
* <br>
* If the description is not found in the given locale, then the default description is returned (the English one).
* As a rule must have a description (this is a constraint in Sonar), this method never returns null.
*
* @param repositoryKey the repository key
* @param ruleKey the rule key
* @param locale the locale to translate into
* @return the translated description of the rule, or the default English one if the given locale is not supported
* @deprecated since 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Deprecated
String getDescription(String repositoryKey, String ruleKey, Locale locale);

/**
* Returns the description of the rule identified by its repository key and rule key.
* <br>
* As a rule must have a description (this is a constraint in SonarQube), this method never returns null.
*
* @param repositoryKey the repository key
* @param ruleKey the rule key
* @return the description of the rule
* @since 4.1
*/
String getDescription(String repositoryKey, String ruleKey);

/**
* Returns the localized name of the rule parameter identified by the rules's key and repository key, and by the parameter key.
* <br>
* If the name is not found in the given locale, then the English translation is searched and return if found. Otherwise,
* this method returns null (= if no translation can be found).
*
* @param repositoryKey the repository key
* @param ruleKey the rule key
* @param paramKey the parameter key
* @param locale the locale to translate into
* @return the translated name of the rule parameter, or the default English one if the given locale is not supported, or null if
* no translation can be found.
* @deprecated since 4.1. Rules are not localized anymore. See http://jira.sonarsource.com/browse/SONAR-4885
*/
@Deprecated
@CheckForNull
String getParamDescription(String repositoryKey, String ruleKey, String paramKey, Locale locale);

/**
* Returns the name of the rule parameter identified by the rules's key and repository key, and by the parameter key.
*
* @param repositoryKey the repository key
* @param ruleKey the rule key
* @param paramKey the parameter key
* @return the nullable name of the rule parameter
* @since 4.1
*/
@CheckForNull
String getParamDescription(String repositoryKey, String ruleKey, String paramKey);

}

+ 0
- 83
sonar-plugin-api/src/main/java/org/sonar/api/rules/RuleRepository.java View File

@@ -1,83 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2019 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.rules;

import java.util.List;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.lang.builder.ToStringBuilder;
import org.apache.commons.lang.builder.ToStringStyle;
import org.sonar.api.ExtensionPoint;
import org.sonar.api.ce.ComputeEngineSide;
import org.sonar.api.server.ServerSide;

/**
* @since 2.3
* @deprecated in 4.2. Replaced by org.sonar.api.server.rule.RulesDefinition
*/
@Deprecated
@ServerSide
@ComputeEngineSide
@ExtensionPoint
public abstract class RuleRepository {

private String key;
private String language;
private String name;

protected RuleRepository(String key, String language) {
this.key = key;
this.language = language;
}

public final String getKey() {
return key;
}

public final String getLanguage() {
return language;
}

public final String getName() {
return name;
}

public final String getName(boolean useKeyIfEmpty) {
if (useKeyIfEmpty) {
return StringUtils.defaultIfEmpty(name, key);
}
return name;
}

public final RuleRepository setName(String s) {
this.name = s;
return this;
}

public abstract List<Rule> createRules();

@Override
public String toString() {
return new ToStringBuilder(this, ToStringStyle.SHORT_PREFIX_STYLE)
.append("key", key)
.append("language", language)
.append("name", name)
.toString();
}
}

+ 0
- 69
sonar-plugin-api/src/main/java/org/sonar/api/server/rule/RulesDefinitionI18nLoader.java View File

@@ -1,69 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2019 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.server.rule;

import org.apache.commons.lang.StringUtils;
import org.sonar.api.i18n.RuleI18n;

/**
* Loads the English bundles of rules (name, description and parameters) that are
* deprecated since 4.2. It can be useful when loading existing XML files that
* do not contain rule names and descriptions.
* <br>
* This class must be executed after declaring rules on {@link RulesDefinition.NewRepository}.
* <br>
* Note that localization of rules was dropped in version 4.2. All texts are English.
*
* @see org.sonar.api.server.rule.RulesDefinition for an example
* @since 4.3
*/
public class RulesDefinitionI18nLoader {

private final RuleI18n i18n;

public RulesDefinitionI18nLoader(RuleI18n i18n) {
this.i18n = i18n;
}

/**
* Loads descriptions of rules and related rule parameters. Existing descriptions
* are overridden if English labels exist in bundles.
*/
public void load(RulesDefinition.NewRepository repo) {
for (RulesDefinition.NewRule rule : repo.rules()) {
String name = i18n.getName(repo.key(), rule.key());
if (StringUtils.isNotBlank(name)) {
rule.setName(name);
}

String desc = i18n.getDescription(repo.key(), rule.key());
if (StringUtils.isNotBlank(desc)) {
rule.setHtmlDescription(desc);
}

for (RulesDefinition.NewParam param : rule.params()) {
String paramDesc = i18n.getParamDescription(repo.key(), rule.key(), param.key());
if (StringUtils.isNotBlank(paramDesc)) {
param.setDescription(paramDesc);
}
}
}
}
}

+ 0
- 100
sonar-plugin-api/src/test/java/org/sonar/api/server/rule/RulesDefinitionI18nLoaderTest.java View File

@@ -1,100 +0,0 @@
/*
* SonarQube
* Copyright (C) 2009-2019 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.server.rule;

import org.junit.Test;
import org.sonar.api.i18n.RuleI18n;
import org.sonar.api.impl.server.RulesDefinitionContext;

import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;

public class RulesDefinitionI18nLoaderTest {

RuleI18n i18n = mock(RuleI18n.class);
RulesDefinitionI18nLoader loader = new RulesDefinitionI18nLoader(i18n);

@Test
public void complete_rule_name_and_description() {
when(i18n.getName("squid", "S0001")).thenReturn("SOne");
when(i18n.getDescription("squid", "S0001")).thenReturn("S One");

RulesDefinition.Context context = new RulesDefinitionContext();
RulesDefinition.NewRepository repo = context.createRepository("squid", "java");
// rule without description
repo.createRule("S0001");

loader.load(repo);
repo.done();

RulesDefinition.Rule rule = context.repository("squid").rule("S0001");
assertThat(rule.name()).isEqualTo("SOne");
assertThat(rule.htmlDescription()).isEqualTo("S One");
}

@Test
public void do_not_override_if_no_bundle() {
// i18n returns null values

RulesDefinition.Context context = new RulesDefinitionContext();
RulesDefinition.NewRepository repo = context.createRepository("squid", "java");
repo.createRule("S0001").setName("SOne").setHtmlDescription("S One");

loader.load(repo);
repo.done();

RulesDefinition.Rule rule = context.repository("squid").rule("S0001");
assertThat(rule.name()).isEqualTo("SOne");
assertThat(rule.htmlDescription()).isEqualTo("S One");
}

@Test
public void override_existing() {
when(i18n.getName("squid", "S0001")).thenReturn("SOne");
when(i18n.getDescription("squid", "S0001")).thenReturn("S One");

RulesDefinition.Context context = new RulesDefinitionContext();
RulesDefinition.NewRepository repo = context.createRepository("squid", "java");
repo.createRule("S0001").setName("Bad").setHtmlDescription("Bad");

loader.load(repo);
repo.done();

RulesDefinition.Rule rule = context.repository("squid").rule("S0001");
assertThat(rule.name()).isEqualTo("SOne");
assertThat(rule.htmlDescription()).isEqualTo("S One");
}

@Test
public void complete_param_description() {
when(i18n.getParamDescription("squid", "S0001", "max")).thenReturn("Maximum");

RulesDefinition.Context context = new RulesDefinitionContext();
RulesDefinition.NewRepository repo = context.createRepository("squid", "java");
repo.createRule("S0001").setName("SOne").setHtmlDescription("S One").createParam("max");

loader.load(repo);
repo.done();

RulesDefinition.Rule rule = context.repository("squid").rule("S0001");
assertThat(rule.param("max").description()).isEqualTo("Maximum");
}
}

Loading…
Cancel
Save