"REMEDIATION_GAP_MULT" VARCHAR(20),
"REMEDIATION_BASE_EFFORT" VARCHAR(20),
"TAGS" VARCHAR(4000),
+ "AD_HOC_NAME" VARCHAR(200),
+ "AD_HOC_DESCRIPTION" VARCHAR(16777215),
+ "AD_HOC_SEVERITY" VARCHAR(10),
+ "AD_HOC_TYPE" TINYINT,
"CREATED_AT" BIGINT NOT NULL,
"UPDATED_AT" BIGINT NOT NULL,
return this;
}
+ @CheckForNull
+ public String getAdHocName() {
+ return metadata.getAdHocName();
+ }
+
+ public RuleDto setAdHocName(@Nullable String adHocName) {
+ metadata.setAdHocName(adHocName);
+ return this;
+ }
+
+ @CheckForNull
+ public String getAdHocDescription() {
+ return metadata.getAdHocDescription();
+ }
+
+ public RuleDto setAdHocDescription(@Nullable String adHocDescription) {
+ metadata.setAdHocDescription(adHocDescription);
+ return this;
+ }
+
+ @CheckForNull
+ public String getAdHocSeverity() {
+ return metadata.getAdHocSeverity();
+ }
+
+ public RuleDto setAdHocSeverity(@Nullable String adHocSeverity) {
+ metadata.setAdHocSeverity(adHocSeverity);
+ return this;
+ }
+
+ @CheckForNull
+ public Integer getAdHocType() {
+ return metadata.getAdHocType();
+ }
+
+ public RuleDto setAdHocType(@Nullable Integer type) {
+ metadata.setAdHocType(type);
+ return this;
+ }
+
+ public RuleDto setAdHocType(@Nullable RuleType adHocType) {
+ metadata.setAdHocType(adHocType);
+ return this;
+ }
+
public boolean isTemplate() {
return definition.isTemplate();
}
import javax.annotation.CheckForNull;
import javax.annotation.Nullable;
import org.apache.commons.lang.StringUtils;
+import org.sonar.api.rules.RuleType;
import static com.google.common.base.Preconditions.checkArgument;
private String remediationGapMultiplier;
private String remediationBaseEffort;
private String tags;
+
+ /**
+ * Name of on ad hoc rule.
+ * When {@link RuleDefinitionDto#isAdHoc} is true, this field should always be set
+ */
+ private String adHocName;
+
+ /**
+ * Optional description of on ad hoc rule.
+ */
+ private String adHocDescription;
+
+ /**
+ * Severity of on ad hoc rule.
+ * When {@link RuleDefinitionDto#isAdHoc} is true, this field should always be set
+ */
+ private String adHocSeverity;
+
+ /**
+ * Type of on ad hoc rule.
+ * When {@link RuleDefinitionDto#isAdHoc} is true, this field should always be set
+ */
+ private Integer adHocType;
+
private long createdAt;
private long updatedAt;
tags = s;
}
+ @CheckForNull
+ public String getAdHocName() {
+ return adHocName;
+ }
+
+ public RuleMetadataDto setAdHocName(@Nullable String adHocName) {
+ this.adHocName = adHocName;
+ return this;
+ }
+
+ @CheckForNull
+ public String getAdHocDescription() {
+ return adHocDescription;
+ }
+
+ public RuleMetadataDto setAdHocDescription(@Nullable String adHocDescription) {
+ this.adHocDescription = adHocDescription;
+ return this;
+ }
+
+ @CheckForNull
+ public String getAdHocSeverity() {
+ return adHocSeverity;
+ }
+
+ public RuleMetadataDto setAdHocSeverity(@Nullable String adHocSeverity) {
+ this.adHocSeverity = adHocSeverity;
+ return this;
+ }
+
+ @CheckForNull
+ public Integer getAdHocType() {
+ return adHocType;
+ }
+
+ public RuleMetadataDto setAdHocType(@Nullable Integer adHocType) {
+ this.adHocType = adHocType;
+ return this;
+ }
+
+ public RuleMetadataDto setAdHocType(@Nullable RuleType adHocType) {
+ setAdHocType(adHocType != null ? adHocType.getDbConstant() : null);
+ return this;
+ }
+
public long getCreatedAt() {
return createdAt;
}
rm.remediation_gap_mult as "remediationGapMultiplier",
rm.remediation_base_effort as "remediationBaseEffort",
rm.tags as "tagsField",
+ rm.ad_hoc_name as "adHocName",
+ rm.ad_hoc_description as "adHocDescription",
+ rm.ad_hoc_severity as "adHocSeverity",
+ rm.ad_hoc_type as "adHocType",
rm.created_at as "createdAtFromMetadata",
rm.updated_at as "updatedAtFromMetadata"
</sql>
rm.remediation_gap_mult as "remediationGapMultiplier",
rm.remediation_base_effort as "remediationBaseEffort",
rm.tags as "tagsField",
- rm.created_at as "createdAt",
+ rm.ad_hoc_name as "adHocName",
+ rm.ad_hoc_description as "adHocDescription",
+ rm.ad_hoc_severity as "adHocSeverity",
+ rm.ad_hoc_type as "adHocType",
+ rm.created_at as "createdAt",
rm.updated_at as "updatedAt"
from
rules_metadata rm
remediation_gap_mult,
remediation_base_effort,
tags,
+ ad_hoc_name,
+ ad_hoc_description,
+ ad_hoc_severity,
+ ad_hoc_type,
created_at,
updated_at
)
#{remediationGapMultiplier,jdbcType=VARCHAR},
#{remediationBaseEffort,jdbcType=VARCHAR},
#{tagsField,jdbcType=VARCHAR},
+ #{adHocName,jdbcType=VARCHAR},
+ #{adHocDescription,jdbcType=CLOB},
+ #{adHocSeverity,jdbcType=VARCHAR},
+ #{adHocType,jdbcType=TINYINT},
#{createdAt,jdbcType=BIGINT},
#{updatedAt,jdbcType=BIGINT}
)
remediation_gap_mult=#{remediationGapMultiplier,jdbcType=VARCHAR},
remediation_base_effort=#{remediationBaseEffort,jdbcType=VARCHAR},
tags=#{tagsField,jdbcType=VARCHAR},
+ ad_hoc_name=#{adHocName,jdbcType=VARCHAR},
+ ad_hoc_description=#{adHocDescription,jdbcType=CLOB},
+ ad_hoc_severity=#{adHocSeverity,jdbcType=VARCHAR},
+ ad_hoc_type=#{adHocType,jdbcType=TINYINT},
updated_at=#{updatedAt,jdbcType=BIGINT}
where
rule_id=#{ruleId,jdbcType=INTEGER}
.setNoteUserUuid("noteUserUuid_" + randomAlphanumeric(5))
.setNoteCreatedAt(System.currentTimeMillis() - 200)
.setNoteUpdatedAt(System.currentTimeMillis() - 150)
+ .setAdHocName("adHocName_" + randomAlphanumeric(5))
+ .setAdHocDescription("adHocDescription_" + randomAlphanumeric(5))
+ .setAdHocSeverity(Severity.ALL.get(nextInt(Severity.ALL.size())))
+ .setAdHocType(RuleType.values()[nextInt(RuleType.values().length - 1)])
.setCreatedAt(System.currentTimeMillis() - 100)
.setUpdatedAt(System.currentTimeMillis() - 50);
}
--- /dev/null
+/*
+ * SonarQube
+ * Copyright (C) 2009-2018 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.platform.db.migration.version.v74;
+
+import java.sql.SQLException;
+import org.sonar.db.Database;
+import org.sonar.server.platform.db.migration.SupportsBlueGreen;
+import org.sonar.server.platform.db.migration.sql.AddColumnsBuilder;
+import org.sonar.server.platform.db.migration.step.DdlChange;
+
+import static org.sonar.server.platform.db.migration.def.ClobColumnDef.newClobColumnDefBuilder;
+import static org.sonar.server.platform.db.migration.def.TinyIntColumnDef.newTinyIntColumnDefBuilder;
+import static org.sonar.server.platform.db.migration.def.VarcharColumnDef.newVarcharColumnDefBuilder;
+
+@SupportsBlueGreen
+public class AddAdHocColumnsInInRulesMetadata extends DdlChange {
+
+ public AddAdHocColumnsInInRulesMetadata(Database db) {
+ super(db);
+ }
+
+ @Override
+ public void execute(Context context) throws SQLException {
+ context.execute(new AddColumnsBuilder(getDialect(), "rules_metadata")
+ .addColumn(newVarcharColumnDefBuilder()
+ .setColumnName("ad_hoc_name")
+ .setLimit(200)
+ .setIsNullable(true)
+ .build())
+ .addColumn(newClobColumnDefBuilder()
+ .setColumnName("ad_hoc_description")
+ .setIsNullable(true)
+ .build())
+ .addColumn(newVarcharColumnDefBuilder()
+ .setColumnName("ad_hoc_severity")
+ .setIsNullable(true)
+ .setLimit(10)
+ .build())
+ .addColumn(newTinyIntColumnDefBuilder()
+ .setColumnName("ad_hoc_type")
+ .setIsNullable(true)
+ .build())
+ .build());
+ }
+}
.add(2301, "Add IS_ADHOC column to RULES table", AddIsAdHocToRules.class)
.add(2302, "Populate IS_AD_HOC in RULES", PopulateIsAdHocOnRules.class)
.add(2303, "Set IS_EXTERNAL and IS_AD_HOC not nullable in RULES", SetIsExternalAndIsAdHocNotNullableInRules.class)
+ .add(2304, "Add ad hoc related columns in RULES_METADATA", AddAdHocColumnsInInRulesMetadata.class)
;
}
}
--- /dev/null
+/*
+ * SonarQube
+ * Copyright (C) 2009-2018 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.platform.db.migration.version.v74;
+
+import java.sql.SQLException;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.rules.ExpectedException;
+import org.sonar.db.CoreDbTester;
+
+import static java.sql.Types.CLOB;
+import static java.sql.Types.TINYINT;
+import static java.sql.Types.VARCHAR;
+
+public class AddAdHocColumnsInInRulesMetadataTest {
+ @Rule
+ public final CoreDbTester db = CoreDbTester.createForSchema(AddAdHocColumnsInInRulesMetadataTest.class, "rules_metadata.sql");
+
+ @Rule
+ public ExpectedException expectedException = ExpectedException.none();
+
+ private AddAdHocColumnsInInRulesMetadata underTest = new AddAdHocColumnsInInRulesMetadata(db.database());
+
+ @Test
+ public void columns_are_updated() throws SQLException {
+ underTest.execute();
+
+ db.assertColumnDefinition("rules_metadata", "ad_hoc_name", VARCHAR, 200, true);
+ db.assertColumnDefinition("rules_metadata", "ad_hoc_description", CLOB, null, true);
+ db.assertColumnDefinition("rules_metadata", "ad_hoc_severity", VARCHAR, 10, true);
+ db.assertColumnDefinition("rules_metadata", "ad_hoc_type", TINYINT, null, true);
+ }
+
+ @Test
+ public void migration_is_not_reentrant() throws SQLException {
+ underTest.execute();
+
+ expectedException.expect(IllegalStateException.class);
+
+ underTest.execute();
+ }
+
+}
@Test
public void verify_migration_count() {
- verifyMigrationCount(underTest, 4);
+ verifyMigrationCount(underTest, 5);
}
}
--- /dev/null
+CREATE TABLE "RULES_METADATA" (
+ "RULE_ID" INTEGER NOT NULL,
+ "ORGANIZATION_UUID" VARCHAR(40) NOT NULL,
+ "NOTE_DATA" CLOB,
+ "NOTE_USER_UUID" VARCHAR(255),
+ "NOTE_CREATED_AT" BIGINT,
+ "NOTE_UPDATED_AT" BIGINT,
+ "REMEDIATION_FUNCTION" VARCHAR(20),
+ "REMEDIATION_GAP_MULT" VARCHAR(20),
+ "REMEDIATION_BASE_EFFORT" VARCHAR(20),
+ "TAGS" VARCHAR(4000),
+ "CREATED_AT" BIGINT NOT NULL,
+ "UPDATED_AT" BIGINT NOT NULL,
+
+ CONSTRAINT "PK_RULES_METADATA" PRIMARY KEY ("RULE_ID", "ORGANIZATION_UUID")
+);
\ No newline at end of file