import org.sonar.api.ServerComponent;
import org.sonar.api.rule.RuleKey;
import org.sonar.api.rule.Severity;
-import org.sonar.api.utils.System2;
import org.sonar.check.Cardinality;
import org.sonar.core.persistence.DbSession;
import org.sonar.core.rule.RuleDto;
public class RuleCreator implements ServerComponent {
private final DbClient dbClient;
- private final System2 system;
- public RuleCreator(DbClient dbClient, System2 system) {
+ public RuleCreator(DbClient dbClient) {
this.dbClient = dbClient;
- this.system = system;
}
public RuleKey create(NewRule newRule) {
try {
RuleKey templateKey = newRule.templateKey();
if (templateKey != null) {
- RuleDto templateRule = dbClient.ruleDao().getByKey(dbSession, newRule.templateKey());
+ RuleDto templateRule = dbClient.ruleDao().getByKey(dbSession, templateKey);
if (!Cardinality.MULTIPLE.equals(templateRule.getCardinality())) {
throw new IllegalArgumentException("This rule is not a template rule: " + templateKey.toString());
}
validateRule(newRule);
- RuleKey customRuleKey = createCustomRule(newRule, templateRule, dbSession);
+
+ RuleKey customRuleKey = RuleKey.of(templateRule.getRepositoryKey(), newRule.ruleKey());
+ checkRuleKeyUnicity(customRuleKey, dbSession);
+ createCustomRule(customRuleKey, newRule, templateRule, dbSession);
dbSession.commit();
return customRuleKey;
}
}
private static void validateRule(NewRule newRule) {
+ validateRuleKey(newRule.ruleKey());
if (Strings.isNullOrEmpty(newRule.name())) {
throw new IllegalArgumentException("The name is missing");
}
}
}
- private RuleKey createCustomRule(NewRule newRule, RuleDto templateRuleDto, DbSession dbSession){
- RuleKey ruleKey = RuleKey.of(templateRuleDto.getRepositoryKey(), templateRuleDto.getRuleKey() + "_" + system.now());
+ private static void validateRuleKey(String ruleKey) {
+ if (Strings.isNullOrEmpty(ruleKey)) {
+ throw new IllegalArgumentException("The rule key is missing");
+ } else {
+ if (!ruleKey.matches("^[\\w]+$")) {
+ throw new IllegalArgumentException(String.format("The rule key '%s' is invalid, it should only contains : a-z, 0-9, '_'", ruleKey));
+ }
+ }
+ }
+
+ private void checkRuleKeyUnicity(RuleKey ruleKey, DbSession dbSession){
+ if (dbClient.ruleDao().getNullableByKey(dbSession, ruleKey) != null) {
+ throw new IllegalArgumentException(String.format("A rule with the key '%s' already exits", ruleKey.rule()));
+ }
+ }
+
+ private RuleKey createCustomRule(RuleKey ruleKey, NewRule newRule, RuleDto templateRuleDto, DbSession dbSession){
RuleDto ruleDto = RuleDto.createFor(ruleKey)
.setParentId(templateRuleDto.getId())
.setConfigKey(templateRuleDto.getConfigKey())
// Create custom rule
NewRule newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
.setTemplateKey(templateRule.getKey())
.setName("My custom")
.setHtmlDescription("Some description")
RuleDto rule = db.ruleDao().getNullableByKey(dbSession, customRuleKey);
assertThat(rule).isNotNull();
+ assertThat(rule.getKey()).isEqualTo(RuleKey.of("java", "CUSTOM_RULE"));
assertThat(rule.getParentId()).isEqualTo(templateRule.getId());
assertThat(rule.getName()).isEqualTo("My custom");
assertThat(rule.getDescription()).isEqualTo("Some description");
assertThat(param.getDefaultValue()).isEqualTo("a.*");
}
+ @Test
+ public void fail_to_create_custom_rule_when_missing_key() throws Exception {
+ // insert template rule
+ RuleDto templateRule = createTemplateRule();
+
+ NewRule newRule = new NewRule()
+ .setName("My custom")
+ .setTemplateKey(templateRule.getKey())
+ .setHtmlDescription("Some description")
+ .setSeverity(Severity.MAJOR)
+ .setStatus(RuleStatus.READY)
+ .setParameters(ImmutableMap.of("regex", "a.*"));
+
+ try {
+ creator.create(newRule);
+ fail();
+ } catch (Exception e) {
+ assertThat(e).isInstanceOf(IllegalArgumentException.class).hasMessage("The rule key is missing");
+ }
+ }
+
+ @Test
+ public void fail_to_create_custom_rule_when_invalid_key() throws Exception {
+ // insert template rule
+ RuleDto templateRule = createTemplateRule();
+
+ NewRule newRule = new NewRule()
+ .setRuleKey("*INVALID*")
+ .setName("My custom")
+ .setTemplateKey(templateRule.getKey())
+ .setHtmlDescription("Some description")
+ .setSeverity(Severity.MAJOR)
+ .setStatus(RuleStatus.READY)
+ .setParameters(ImmutableMap.of("regex", "a.*"));
+
+ try {
+ creator.create(newRule);
+ fail();
+ } catch (Exception e) {
+ assertThat(e).isInstanceOf(IllegalArgumentException.class).hasMessage("The rule key '*INVALID*' is invalid, it should only contains : a-z, 0-9, '_'");
+ }
+ }
+
+ @Test
+ public void fail_to_create_custom_rule_when_rule_key_already_exits() throws Exception {
+ // insert template rule
+ RuleDto templateRule = createTemplateRule();
+
+ // Create a custom rule
+ NewRule newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
+ .setName("My custom")
+ .setTemplateKey(templateRule.getKey())
+ .setHtmlDescription("Some description")
+ .setSeverity(Severity.MAJOR)
+ .setStatus(RuleStatus.READY)
+ .setParameters(ImmutableMap.of("regex", "a.*"));
+ creator.create(newRule);
+
+ try {
+ // Create another custom rule having same key
+ newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
+ .setName("My another custom")
+ .setTemplateKey(templateRule.getKey())
+ .setHtmlDescription("Some description")
+ .setSeverity(Severity.MAJOR)
+ .setStatus(RuleStatus.READY)
+ .setParameters(ImmutableMap.of("regex", "a.*"));
+ creator.create(newRule);
+ fail();
+ } catch (Exception e) {
+ assertThat(e).isInstanceOf(IllegalArgumentException.class).hasMessage("A rule with the key 'CUSTOM_RULE' already exits");
+ }
+ }
+
@Test
public void fail_to_create_custom_rule_when_missing_name() throws Exception {
// insert template rule
RuleDto templateRule = createTemplateRule();
- // Create custom rule without name
NewRule newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
.setTemplateKey(templateRule.getKey())
.setHtmlDescription("Some description")
.setSeverity(Severity.MAJOR)
// insert template rule
RuleDto templateRule = createTemplateRule();
- // Create custom rule without description
NewRule newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
.setTemplateKey(templateRule.getKey())
.setName("My custom")
.setSeverity(Severity.MAJOR)
// insert template rule
RuleDto templateRule = createTemplateRule();
- // Create custom rule without description
NewRule newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
.setTemplateKey(templateRule.getKey())
.setName("My custom")
.setHtmlDescription("Some description")
// insert template rule
RuleDto templateRule = createTemplateRule();
- // Create custom rule without description
NewRule newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
.setTemplateKey(templateRule.getKey())
.setName("My custom")
.setHtmlDescription("Some description")
// insert template rule
RuleDto templateRule = createTemplateRule();
- // Create custom rule without description
NewRule newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
.setTemplateKey(templateRule.getKey())
.setName("My custom")
.setHtmlDescription("Some description")
// Create custom rule with unknown template rule
NewRule newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
.setTemplateKey(rule.getKey())
.setName("My custom")
.setHtmlDescription("Some description")
// insert template rule
RuleDto templateRule = createTemplateRule();
- // Create custom rule
NewRule newRule = new NewRule()
+ .setRuleKey("CUSTOM_RULE")
.setTemplateKey(templateRule.getKey())
.setName("My custom")
.setHtmlDescription("Some description")