]> source.dussan.org Git - sonarqube.git/commitdiff
SONAR-12717 default status of hotspot is TO_REVIEW
authorSébastien Lesaint <sebastien.lesaint@sonarsource.com>
Thu, 2 Jan 2020 13:26:22 +0000 (14:26 +0100)
committerSonarTech <sonartech@sonarsource.com>
Mon, 13 Jan 2020 19:46:35 +0000 (20:46 +0100)
server/sonar-db-migration/src/main/java/org/sonar/server/platform/db/migration/version/v82/DbVersion82.java
server/sonar-db-migration/src/main/java/org/sonar/server/platform/db/migration/version/v82/EnsureHotspotDefaultStatusIsToReview.java [new file with mode: 0644]
server/sonar-db-migration/src/test/java/org/sonar/server/platform/db/migration/version/v82/DbVersion82Test.java
server/sonar-db-migration/src/test/java/org/sonar/server/platform/db/migration/version/v82/EnsureHotspotDefaultStatusIsToReviewTest.java [new file with mode: 0644]
server/sonar-db-migration/src/test/resources/org/sonar/server/platform/db/migration/version/v82/EnsureHotspotDefaultStatusIsToReviewTest/issues.sql [new file with mode: 0644]

index ccaa809ef8038a6fa6c6c6873beaf4990b32d8d5..ba11ce147974f0bc0161e8b95898df54ed30d3b1 100644 (file)
@@ -28,6 +28,7 @@ public class DbVersion82 implements DbVersion {
     registry
       .add(3200, "Drop 'In Review' Security Hotspots status ", DropSecurityHotSpotsInReviewStatus.class)
       .add(3201, "Migrate Manual Vulnerabilities to Security Hotspots ", MigrateManualVulnerabilitiesToSecurityHotSpots.class)
-      .add(3202, "Remove 'newsbox.dismiss.hotspots' user property", RemoveNewsboxDismissHotspotsProperty.class);
+      .add(3202, "Remove 'newsbox.dismiss.hotspots' user property", RemoveNewsboxDismissHotspotsProperty.class)
+      .add(3203, "Ensure Security Hotspots have status TO_REVIEW", EnsureHotspotDefaultStatusIsToReview.class);
   }
 }
diff --git a/server/sonar-db-migration/src/main/java/org/sonar/server/platform/db/migration/version/v82/EnsureHotspotDefaultStatusIsToReview.java b/server/sonar-db-migration/src/main/java/org/sonar/server/platform/db/migration/version/v82/EnsureHotspotDefaultStatusIsToReview.java
new file mode 100644 (file)
index 0000000..9753bd8
--- /dev/null
@@ -0,0 +1,50 @@
+/*
+ * SonarQube
+ * Copyright (C) 2009-2020 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.v82;
+
+import java.sql.SQLException;
+import org.sonar.api.rules.RuleType;
+import org.sonar.db.Database;
+import org.sonar.server.platform.db.migration.step.DataChange;
+import org.sonar.server.platform.db.migration.step.MassUpdate;
+
+import static org.sonar.api.issue.Issue.STATUS_OPEN;
+import static org.sonar.api.issue.Issue.STATUS_TO_REVIEW;
+
+public class EnsureHotspotDefaultStatusIsToReview extends DataChange {
+  public EnsureHotspotDefaultStatusIsToReview(Database db) {
+    super(db);
+  }
+
+  @Override
+  protected void execute(Context context) throws SQLException {
+    MassUpdate massUpdate = context.prepareMassUpdate();
+    massUpdate.select("select id from issues where issue_type = ? and status = ?")
+      .setInt(1, RuleType.SECURITY_HOTSPOT.getDbConstant())
+      .setString(2, STATUS_OPEN);
+    massUpdate.update("update issues set status = ? where id = ?");
+    massUpdate.execute((row, update) -> {
+      long id = row.getLong(1);
+      update.setString(1, STATUS_TO_REVIEW);
+      update.setLong(2, id);
+      return true;
+    });
+  }
+}
index 0776c6275e6aaafa249522cdfbbd2fed54f3bca6..9baea99797f5d8a5a0a75f9e56ead491575221ff 100644 (file)
@@ -36,7 +36,7 @@ public class DbVersion82Test {
 
   @Test
   public void verify_migration_count() {
-    verifyMigrationCount(underTest, 3);
+    verifyMigrationCount(underTest, 4);
   }
 
 }
diff --git a/server/sonar-db-migration/src/test/java/org/sonar/server/platform/db/migration/version/v82/EnsureHotspotDefaultStatusIsToReviewTest.java b/server/sonar-db-migration/src/test/java/org/sonar/server/platform/db/migration/version/v82/EnsureHotspotDefaultStatusIsToReviewTest.java
new file mode 100644 (file)
index 0000000..c753636
--- /dev/null
@@ -0,0 +1,121 @@
+/*
+ * SonarQube
+ * Copyright (C) 2009-2020 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.v82;
+
+import com.tngtech.java.junit.dataprovider.DataProvider;
+import com.tngtech.java.junit.dataprovider.DataProviderRunner;
+import com.tngtech.java.junit.dataprovider.UseDataProvider;
+import java.sql.SQLException;
+import java.util.Arrays;
+import java.util.Random;
+import javax.annotation.Nullable;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.rules.ExpectedException;
+import org.junit.runner.RunWith;
+import org.sonar.api.issue.Issue;
+import org.sonar.api.rules.RuleType;
+import org.sonar.db.CoreDbTester;
+
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.sonar.api.issue.Issue.STATUS_OPEN;
+import static org.sonar.api.issue.Issue.STATUS_TO_REVIEW;
+import static org.sonar.api.rules.RuleType.SECURITY_HOTSPOT;
+
+@RunWith(DataProviderRunner.class)
+public class EnsureHotspotDefaultStatusIsToReviewTest {
+
+  @Rule
+  public CoreDbTester db = CoreDbTester.createForSchema(EnsureHotspotDefaultStatusIsToReviewTest.class, "issues.sql");
+  @Rule
+  public ExpectedException expectedException = ExpectedException.none();
+
+  private Random random = new Random();
+
+  private EnsureHotspotDefaultStatusIsToReview underTest = new EnsureHotspotDefaultStatusIsToReview(db.database());
+
+  @Test
+  public void does_not_fail_if_table_is_empty() throws SQLException {
+    underTest.execute();
+
+    assertThat(db.countRowsOfTable("issues")).isEqualTo(0);
+  }
+
+  @Test
+  public void changes_OPEN_security_hotspot_to_TO_REVIEW_whatever_resolution() throws SQLException {
+    insertIssue("Kee_none", SECURITY_HOTSPOT, STATUS_OPEN, null);
+    Issue.RESOLUTIONS.forEach(resolution -> insertIssue("Kee_" + resolution, SECURITY_HOTSPOT, STATUS_OPEN, resolution));
+
+    underTest.execute();
+
+    assertThat(db.select("select distinct STATUS from issues").stream().map(t -> t.get("STATUS")))
+      .containsExactly(STATUS_TO_REVIEW);
+  }
+
+  @Test
+  @UseDataProvider("allStatusesButOpen")
+  public void changes_non_OPEN_security_hotspot_to_TO_REVIEW_whatever_resolution(String status) throws SQLException {
+    insertIssue("Kee_none", SECURITY_HOTSPOT, status, null);
+    Issue.RESOLUTIONS.forEach(resolution -> insertIssue("Kee_" + resolution, SECURITY_HOTSPOT, status, resolution));
+
+    underTest.execute();
+
+    assertThat(db.select("select distinct STATUS from issues").stream().map(t -> t.get("STATUS")))
+      .containsExactly(status);
+  }
+
+  @DataProvider
+  public static Object[][] allStatusesButOpen() {
+    return Issue.STATUSES.stream()
+      .filter(t -> !STATUS_OPEN.equals(t))
+      .map(t -> new Object[] {t})
+      .toArray(Object[][]::new);
+  }
+
+  @Test
+  @UseDataProvider("allRuleTypeButHotspot")
+  public void does_not_change_OPEN_issues_to_TO_REVIEW_whatever_resolution(RuleType ruleType) throws SQLException {
+    insertIssue("Kee_none", ruleType, STATUS_OPEN, null);
+    Issue.RESOLUTIONS.forEach(resolution -> insertIssue("Kee_" + resolution, ruleType, STATUS_OPEN, resolution));
+
+    underTest.execute();
+
+    assertThat(db.select("select distinct STATUS from issues").stream().map(t -> t.get("STATUS")))
+      .containsExactly(STATUS_OPEN);
+  }
+
+  @DataProvider
+  public static Object[][] allRuleTypeButHotspot() {
+    return Arrays.stream(RuleType.values())
+      .filter(t -> t != SECURITY_HOTSPOT)
+      .map(t -> new Object[] {t})
+      .toArray(Object[][]::new);
+  }
+
+  private void insertIssue(String kee, RuleType ruleType, String status, @Nullable String resolution) {
+    db.executeInsert(
+      "ISSUES",
+      "KEE", kee,
+      "MANUAL_SEVERITY", random.nextBoolean(),
+      "ISSUE_TYPE", ruleType.getDbConstant(),
+      "STATUS", status,
+      "RESOLUTION", resolution);
+  }
+}
diff --git a/server/sonar-db-migration/src/test/resources/org/sonar/server/platform/db/migration/version/v82/EnsureHotspotDefaultStatusIsToReviewTest/issues.sql b/server/sonar-db-migration/src/test/resources/org/sonar/server/platform/db/migration/version/v82/EnsureHotspotDefaultStatusIsToReviewTest/issues.sql
new file mode 100644 (file)
index 0000000..cf65bc4
--- /dev/null
@@ -0,0 +1,39 @@
+CREATE TABLE "ISSUES"(
+    "ID" BIGINT NOT NULL AUTO_INCREMENT (1,1),
+    "KEE" VARCHAR(50) NOT NULL,
+    "RULE_ID" INTEGER,
+    "SEVERITY" VARCHAR(10),
+    "MANUAL_SEVERITY" BOOLEAN NOT NULL,
+    "MESSAGE" VARCHAR(4000),
+    "LINE" INTEGER,
+    "GAP" DOUBLE,
+    "STATUS" VARCHAR(20),
+    "RESOLUTION" VARCHAR(20),
+    "CHECKSUM" VARCHAR(1000),
+    "REPORTER" VARCHAR(255),
+    "ASSIGNEE" VARCHAR(255),
+    "AUTHOR_LOGIN" VARCHAR(255),
+    "ACTION_PLAN_KEY" VARCHAR(50),
+    "ISSUE_ATTRIBUTES" VARCHAR(4000),
+    "EFFORT" INTEGER,
+    "CREATED_AT" BIGINT,
+    "UPDATED_AT" BIGINT,
+    "ISSUE_CREATION_DATE" BIGINT,
+    "ISSUE_UPDATE_DATE" BIGINT,
+    "ISSUE_CLOSE_DATE" BIGINT,
+    "TAGS" VARCHAR(4000),
+    "COMPONENT_UUID" VARCHAR(50),
+    "PROJECT_UUID" VARCHAR(50),
+    "LOCATIONS" BLOB,
+    "ISSUE_TYPE" TINYINT,
+    "FROM_HOTSPOT" BOOLEAN
+);
+ALTER TABLE "ISSUES" ADD CONSTRAINT "PK_ISSUES" PRIMARY KEY("ID");
+CREATE INDEX "ISSUES_ASSIGNEE" ON "ISSUES"("ASSIGNEE");
+CREATE INDEX "ISSUES_COMPONENT_UUID" ON "ISSUES"("COMPONENT_UUID");
+CREATE INDEX "ISSUES_CREATION_DATE" ON "ISSUES"("ISSUE_CREATION_DATE");
+CREATE UNIQUE INDEX "ISSUES_KEE" ON "ISSUES"("KEE");
+CREATE INDEX "ISSUES_PROJECT_UUID" ON "ISSUES"("PROJECT_UUID");
+CREATE INDEX "ISSUES_RESOLUTION" ON "ISSUES"("RESOLUTION");
+CREATE INDEX "ISSUES_RULE_ID" ON "ISSUES"("RULE_ID");
+CREATE INDEX "ISSUES_UPDATED_AT" ON "ISSUES"("UPDATED_AT");