From faa74b33eb99d62ad8c6ee760a9367ec62b8dc00 Mon Sep 17 00:00:00 2001 From: simonbrandhof Date: Thu, 3 Dec 2015 18:37:23 +0100 Subject: [PATCH] SONAR-7049 check max length of rule/rule param fields --- .../main/java/org/sonar/db/rule/RuleDto.java | 21 ++++++---- .../java/org/sonar/db/rule/RuleParamDto.java | 17 +++++--- .../java/org/sonar/db/rule/RuleDtoTest.java | 40 +++++++++++++++++++ .../api/server/rule/RulesDefinition.java | 18 ++++++++- .../server/rule/RulesDefinitionXmlLoader.java | 7 ++-- 5 files changed, 85 insertions(+), 18 deletions(-) diff --git a/sonar-db/src/main/java/org/sonar/db/rule/RuleDto.java b/sonar-db/src/main/java/org/sonar/db/rule/RuleDto.java index 2c5a17b4f59..9b3a347d908 100644 --- a/sonar-db/src/main/java/org/sonar/db/rule/RuleDto.java +++ b/sonar-db/src/main/java/org/sonar/db/rule/RuleDto.java @@ -36,6 +36,8 @@ import org.sonar.api.rule.RuleStatus; import org.sonar.core.rule.SeverityUtil; import org.sonar.db.Dto; +import static com.google.common.base.Preconditions.checkArgument; + public class RuleDto extends Dto { public static final int DISABLED_CHARACTERISTIC_ID = -1; @@ -95,8 +97,9 @@ public class RuleDto extends Dto { return repositoryKey; } - public RuleDto setRepositoryKey(String repositoryKey) { - this.repositoryKey = repositoryKey; + public RuleDto setRepositoryKey(String s) { + checkArgument(s.length() <= 255, "Rule repository is too long: %s", s); + this.repositoryKey = s; return this; } @@ -104,8 +107,9 @@ public class RuleDto extends Dto { return ruleKey; } - public RuleDto setRuleKey(String ruleKey) { - this.ruleKey = ruleKey; + public RuleDto setRuleKey(String s) { + checkArgument(s.length() <= 200, "Rule key is too long: %s", s); + this.ruleKey = s; return this; } @@ -140,8 +144,9 @@ public class RuleDto extends Dto { return name; } - public RuleDto setName(@Nullable String name) { - this.name = name; + public RuleDto setName(@Nullable String s) { + checkArgument(s== null || s.length() <= 255, "Rule name is too long: %s", s); + this.name = s; return this; } @@ -362,7 +367,9 @@ public class RuleDto extends Dto { } public RuleDto setTags(Set tags) { - this.tags = tags.isEmpty() ? null : StringUtils.join(tags, ','); + String raw = tags.isEmpty() ? null : StringUtils.join(tags, ','); + checkArgument(raw == null || raw.length() <= 4000, "Rule tags are too long: %s", raw); + this.tags = raw; return this; } diff --git a/sonar-db/src/main/java/org/sonar/db/rule/RuleParamDto.java b/sonar-db/src/main/java/org/sonar/db/rule/RuleParamDto.java index 2df5c541a93..a84bb037342 100644 --- a/sonar-db/src/main/java/org/sonar/db/rule/RuleParamDto.java +++ b/sonar-db/src/main/java/org/sonar/db/rule/RuleParamDto.java @@ -25,6 +25,8 @@ import javax.annotation.Nullable; import org.apache.commons.lang.builder.ReflectionToStringBuilder; import org.apache.commons.lang.builder.ToStringStyle; +import static com.google.common.base.Preconditions.checkArgument; + public class RuleParamDto { private Integer id; @@ -56,8 +58,9 @@ public class RuleParamDto { return name; } - public RuleParamDto setName(String name) { - this.name = name; + public RuleParamDto setName(String s) { + checkArgument(s.length() <= 128, "Rule parameter name is too long: %s", s); + this.name = s; return this; } @@ -75,8 +78,9 @@ public class RuleParamDto { return defaultValue; } - public RuleParamDto setDefaultValue(@Nullable String defaultValue) { - this.defaultValue = defaultValue; + public RuleParamDto setDefaultValue(@Nullable String s) { + checkArgument(s == null || s.length() <= 4000, "Rule parameter default value is too long: %s", s); + this.defaultValue = s; return this; } @@ -84,8 +88,9 @@ public class RuleParamDto { return description; } - public RuleParamDto setDescription(String description) { - this.description = description; + public RuleParamDto setDescription(@Nullable String s) { + checkArgument(s == null || s.length() <= 4000, "Rule parameter description is too long: %s", s); + this.description = s; return this; } diff --git a/sonar-db/src/test/java/org/sonar/db/rule/RuleDtoTest.java b/sonar-db/src/test/java/org/sonar/db/rule/RuleDtoTest.java index 7c170e7c8df..c6ac840691c 100644 --- a/sonar-db/src/test/java/org/sonar/db/rule/RuleDtoTest.java +++ b/sonar-db/src/test/java/org/sonar/db/rule/RuleDtoTest.java @@ -19,8 +19,14 @@ */ package org.sonar.db.rule; +import com.google.common.collect.ImmutableSet; +import java.util.Collections; +import java.util.Set; +import org.junit.Rule; import org.junit.Test; +import org.junit.rules.ExpectedException; +import static org.apache.commons.lang.StringUtils.repeat; import static org.assertj.core.api.Assertions.assertThat; import static org.sonar.db.rule.RuleDto.DISABLED_CHARACTERISTIC_ID; @@ -29,6 +35,9 @@ public class RuleDtoTest { public static final int FAKE_SUB_CHAR_1 = 27; public static final int FAKE_SUB_CHAR_2 = 42; + @Rule + public ExpectedException expectedException = ExpectedException.none(); + @Test public void effective_sub_characteristic_id() { RuleDto dto = new RuleDto(); @@ -57,4 +66,35 @@ public class RuleDtoTest { dto.setSubCharacteristicId(DISABLED_CHARACTERISTIC_ID).setDefaultSubCharacteristicId(FAKE_SUB_CHAR_2); assertThat(dto.getEffectiveSubCharacteristicId()).isNull(); } + + @Test + public void fail_if_key_is_too_long() { + expectedException.expect(IllegalArgumentException.class); + expectedException.expectMessage("Rule key is too long: "); + + new RuleDto().setRuleKey(repeat("x", 250)); + } + + @Test + public void fail_if_name_is_too_long() { + expectedException.expect(IllegalArgumentException.class); + expectedException.expectMessage("Rule name is too long: "); + + new RuleDto().setName(repeat("x", 300)); + } + + @Test + public void fail_if_tags_are_too_long() { + expectedException.expect(IllegalArgumentException.class); + expectedException.expectMessage("Rule tags are too long: "); + + Set tags = ImmutableSet.of(repeat("a", 2000), repeat("b", 1000), repeat("c", 2000)); + new RuleDto().setTags(tags); + } + + @Test + public void tags_are_optional() { + RuleDto dto = new RuleDto().setTags(Collections.emptySet()); + assertThat(dto.getTags()).isEmpty(); + } } diff --git a/sonar-plugin-api/src/main/java/org/sonar/api/server/rule/RulesDefinition.java b/sonar-plugin-api/src/main/java/org/sonar/api/server/rule/RulesDefinition.java index e9c878c0218..15e96c7189c 100644 --- a/sonar-plugin-api/src/main/java/org/sonar/api/server/rule/RulesDefinition.java +++ b/sonar-plugin-api/src/main/java/org/sonar/api/server/rule/RulesDefinition.java @@ -426,6 +426,9 @@ public interface RulesDefinition { } interface NewExtendedRepository { + /** + * Create a rule with specified key. Max length of key is 200 characters. + */ NewRule createRule(String ruleKey); @CheckForNull @@ -692,6 +695,10 @@ public interface RulesDefinition { return this; } + /** + * The optional description, in HTML format, has no max length. It's exclusive with markdown description + * (see {@link #setMarkdownDescription(String)}) + */ public NewRule setHtmlDescription(@Nullable String s) { if (markdownDescription != null) { throw new IllegalStateException(String.format("Rule '%s' already has a Markdown description", this)); @@ -716,6 +723,10 @@ public interface RulesDefinition { return this; } + /** + * The optional description, in a restricted Markdown format, has no max length. It's exclusive with HTML description + * (see {@link #setHtmlDescription(String)}) + */ public NewRule setMarkdownDescription(@Nullable String s) { if (htmlDescription != null) { throw new IllegalStateException(String.format("Rule '%s' already has an HTML description", this)); @@ -792,6 +803,9 @@ public interface RulesDefinition { return this; } + /** + * Create a parameter with given unique key. Max length of key is 128 characters. + */ public NewParam createParam(String paramKey) { if (paramsByKey.containsKey(paramKey)) { throw new IllegalArgumentException(String.format("The parameter '%s' is declared several times on the rule %s", paramKey, this)); @@ -1020,7 +1034,7 @@ public interface RulesDefinition { } /** - * Plain-text description. Can be null. + * Plain-text description. Can be null. Max length is 4000 characters. */ public NewParam setDescription(@Nullable String s) { this.description = StringUtils.defaultIfBlank(s, null); @@ -1028,7 +1042,7 @@ public interface RulesDefinition { } /** - * Empty default value will be converted to null. + * Empty default value will be converted to null. Max length is 4000 characters. */ public NewParam setDefaultValue(@Nullable String s) { this.defaultValue = Strings.emptyToNull(s); diff --git a/sonar-plugin-api/src/main/java/org/sonar/api/server/rule/RulesDefinitionXmlLoader.java b/sonar-plugin-api/src/main/java/org/sonar/api/server/rule/RulesDefinitionXmlLoader.java index 8a8096e4ebf..f088221b883 100644 --- a/sonar-plugin-api/src/main/java/org/sonar/api/server/rule/RulesDefinitionXmlLoader.java +++ b/sonar-plugin-api/src/main/java/org/sonar/api/server/rule/RulesDefinitionXmlLoader.java @@ -74,10 +74,10 @@ import static org.apache.commons.lang.StringUtils.trim; *
  * <rules>
  *   <rule>
- *     <!-- required key -->
+ *     <!-- required key. Max length is 200. -->
  *     <key>the-rule-key</key>
  *
- *     <!-- required name -->
+ *     <!-- required name. Max length is 200. -->
  *     <name>The purpose of the rule</name>
  *
  *     <!-- required description, in HTML format -->
@@ -98,11 +98,12 @@ import static org.apache.commons.lang.StringUtils.trim;
  *     <!-- Status displayed in rules console. Possible values are BETA, READY (default), DEPRECATED. -->
  *     <status>BETA</status>
  *
- *     <!-- Optional tags. See org.sonar.api.server.rule.RuleTagFormat. -->
+ *     <!-- Optional tags. See org.sonar.api.server.rule.RuleTagFormat. The maximal length of all tags is 4000. -->
  *     <tag>style</tag>
  *     <tag>security</tag>
  *
  *     <param>
+ *       <!-- Status displayed in rules console. Possible values are BETA, READY (default), DEPRECATED. -->
  *       <key>the-param-key</key>
  *       <description>
  *         <![CDATA[the optional description, in HTML format]]>
-- 
2.39.5