]> source.dussan.org Git - sonarqube.git/commitdiff
SONAR-12718 don't index twice rules and activeRule on first startup
authorSébastien Lesaint <sebastien.lesaint@sonarsource.com>
Wed, 18 Dec 2019 16:14:51 +0000 (17:14 +0100)
committerSonarTech <sonartech@sonarsource.com>
Mon, 13 Jan 2020 19:46:31 +0000 (20:46 +0100)
server/sonar-webserver-core/src/main/java/org/sonar/server/rule/RegisterRules.java
server/sonar-webserver-core/src/test/java/org/sonar/server/rule/RegisterRulesTest.java

index 9e9d53ae0a674f2fb3398b9e01513690649ffd6b..a1542d9265b4f9e47e2e280bbcdf9962c6d7a5f4 100644 (file)
@@ -61,6 +61,7 @@ import org.sonar.db.rule.RuleDto.Format;
 import org.sonar.db.rule.RuleDto.Scope;
 import org.sonar.db.rule.RuleParamDto;
 import org.sonar.db.rule.RuleRepositoryDto;
+import org.sonar.server.es.metadata.MetadataIndex;
 import org.sonar.server.organization.OrganizationFlags;
 import org.sonar.server.qualityprofile.ActiveRuleChange;
 import org.sonar.server.qualityprofile.QProfileRules;
@@ -95,10 +96,11 @@ public class RegisterRules implements Startable {
   private final OrganizationFlags organizationFlags;
   private final WebServerRuleFinder webServerRuleFinder;
   private final UuidFactory uuidFactory;
+  private final MetadataIndex metadataIndex;
 
   public RegisterRules(RuleDefinitionsLoader defLoader, QProfileRules qProfileRules, DbClient dbClient, RuleIndexer ruleIndexer,
     ActiveRuleIndexer activeRuleIndexer, Languages languages, System2 system2, OrganizationFlags organizationFlags,
-    WebServerRuleFinder webServerRuleFinder, UuidFactory uuidFactory) {
+    WebServerRuleFinder webServerRuleFinder, UuidFactory uuidFactory, MetadataIndex metadataIndex) {
     this.defLoader = defLoader;
     this.qProfileRules = qProfileRules;
     this.dbClient = dbClient;
@@ -109,6 +111,7 @@ public class RegisterRules implements Startable {
     this.organizationFlags = organizationFlags;
     this.webServerRuleFinder = webServerRuleFinder;
     this.uuidFactory = uuidFactory;
+    this.metadataIndex = metadataIndex;
   }
 
   @Override
@@ -145,6 +148,11 @@ public class RegisterRules implements Startable {
       registerRulesContext.getRenamed().forEach(e -> LOG.info("Rule {} re-keyed to {}", e.getValue(), e.getKey().getKey()));
       profiler.stopDebug();
 
+      if (!registerRulesContext.hasDbRules()) {
+        Stream.concat(ruleIndexer.getIndexTypes().stream(), activeRuleIndexer.getIndexTypes().stream())
+          .forEach(t -> metadataIndex.setInitialized(t, true));
+      }
+
       webServerRuleFinder.startCaching();
     }
   }
@@ -223,7 +231,7 @@ public class RegisterRules implements Startable {
         RuleDefinitionDto rule = dbRulesByRuleId.get(ruleId);
         if (rule == null) {
           LOG.warn("Could not retrieve rule with id %s referenced by a deprecated rule key. " +
-              "The following deprecated rule keys seem to be referencing a non-existing rule",
+            "The following deprecated rule keys seem to be referencing a non-existing rule",
             ruleId, entry.getValue());
         } else {
           entry.getValue().forEach(d -> builder.put(d.getOldRuleKeyAsRuleKey(), rule));
@@ -232,6 +240,10 @@ public class RegisterRules implements Startable {
       return builder.build();
     }
 
+    private boolean hasDbRules() {
+      return !dbRules.isEmpty();
+    }
+
     private Optional<RuleDefinitionDto> getDbRuleFor(RulesDefinition.Rule ruleDef) {
       RuleKey ruleKey = RuleKey.of(ruleDef.repository().key(), ruleDef.key());
       Optional<RuleDefinitionDto> res = Stream.concat(Stream.of(ruleKey), ruleDef.deprecatedRuleKeys().stream())
@@ -629,11 +641,11 @@ public class RegisterRules implements Startable {
       changed = true;
     } else if (dto.getSystemTags().size() != ruleDef.tags().size() ||
       !dto.getSystemTags().containsAll(ruleDef.tags())) {
-      dto.setSystemTags(ruleDef.tags());
-      // FIXME this can't be implemented easily with organization support: remove end-user tags that are now declared as system
-      // RuleTagHelper.applyTags(dto, ImmutableSet.copyOf(dto.getTags()));
-      changed = true;
-    }
+        dto.setSystemTags(ruleDef.tags());
+        // FIXME this can't be implemented easily with organization support: remove end-user tags that are now declared as system
+        // RuleTagHelper.applyTags(dto, ImmutableSet.copyOf(dto.getTags()));
+        changed = true;
+      }
     return changed;
   }
 
@@ -645,9 +657,9 @@ public class RegisterRules implements Startable {
       changed = true;
     } else if (dto.getSecurityStandards().size() != ruleDef.securityStandards().size() ||
       !dto.getSecurityStandards().containsAll(ruleDef.securityStandards())) {
-      dto.setSecurityStandards(ruleDef.securityStandards());
-      changed = true;
-    }
+        dto.setSecurityStandards(ruleDef.securityStandards());
+        changed = true;
+      }
     return changed;
   }
 
index 95f58c05bb933faab1497c2db60fd3d049625752..14c5834c17d6eb795f8ec381f4538c8014088953 100644 (file)
@@ -59,6 +59,7 @@ import org.sonar.db.rule.RuleRepositoryDto;
 import org.sonar.server.es.EsTester;
 import org.sonar.server.es.SearchIdResult;
 import org.sonar.server.es.SearchOptions;
+import org.sonar.server.es.metadata.MetadataIndex;
 import org.sonar.server.organization.OrganizationFlags;
 import org.sonar.server.organization.TestOrganizationFlags;
 import org.sonar.server.plugins.ServerPluginRepository;
@@ -78,6 +79,7 @@ import static org.mockito.ArgumentMatchers.any;
 import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.reset;
 import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.verifyNoInteractions;
 import static org.mockito.Mockito.when;
 import static org.sonar.api.rule.RuleStatus.READY;
 import static org.sonar.api.rule.RuleStatus.REMOVED;
@@ -119,6 +121,7 @@ public class RegisterRulesTest {
   private RuleIndexer ruleIndexer;
   private ActiveRuleIndexer activeRuleIndexer;
   private RuleIndex ruleIndex;
+  private MetadataIndex metadataIndex = mock(MetadataIndex.class);
   private OrganizationDto defaultOrganization;
   private OrganizationFlags organizationFlags = TestOrganizationFlags.standalone();
   private UuidFactory uuidFactory = UuidFactoryFast.getInstance();
@@ -174,6 +177,7 @@ public class RegisterRulesTest {
     // verify index
     RuleDto rule2 = dbClient.ruleDao().selectOrFailByKey(db.getSession(), db.getDefaultOrganization(), RULE_KEY2);
     assertThat(ruleIndex.search(new RuleQuery(), new SearchOptions()).getIds()).containsOnly(rule1.getId(), rule2.getId(), hotspotRule.getId());
+    verifyIndicesMarkedAsInitialized();
 
     // verify repositories
     assertThat(dbClient.ruleRepositoryDao().selectAll(db.getSession())).extracting(RuleRepositoryDto::getKey).containsOnly("fake");
@@ -237,6 +241,7 @@ public class RegisterRulesTest {
     // verify index
     assertThat(ruleIndex.search(new RuleQuery(), new SearchOptions()).getIds())
       .containsExactly(rule.getId());
+    verifyIndicesMarkedAsInitialized();
 
     // register no rule
     execute(context -> context.createRepository("fake", "java").done());
@@ -253,6 +258,7 @@ public class RegisterRulesTest {
     // verify index
     assertThat(ruleIndex.search(new RuleQuery(), new SearchOptions()).getIds())
       .isEmpty();
+    verifyIndicesNotMarkedAsInitialized();
   }
 
   @Test
@@ -316,6 +322,7 @@ public class RegisterRulesTest {
     RuleDto rule2 = dbClient.ruleDao().selectOrFailByKey(db.getSession(), defaultOrganization, RULE_KEY2);
     RuleDto hotspotRule = dbClient.ruleDao().selectOrFailByKey(db.getSession(), defaultOrganization, HOTSPOT_RULE_KEY);
     assertThat(es.getIds(RuleIndexDefinition.TYPE_RULE)).containsOnly(valueOf(rule1.getId()), valueOf(rule2.getId()), valueOf(hotspotRule.getId()));
+    verifyIndicesMarkedAsInitialized();
 
     // user adds tags and sets markdown note
     rule1.setTags(newHashSet("usertag1", "usertag2"));
@@ -327,6 +334,7 @@ public class RegisterRulesTest {
     when(system.now()).thenReturn(DATE2.getTime());
     execute(new FakeRepositoryV2());
 
+    verifyIndicesNotMarkedAsInitialized();
     // rule1 has been updated
     rule1 = dbClient.ruleDao().selectOrFailByKey(db.getSession(), defaultOrganization, RULE_KEY1);
     assertThat(rule1.getName()).isEqualTo("One v2");
@@ -1026,7 +1034,7 @@ public class RegisterRulesTest {
     reset(webServerRuleFinder);
 
     RegisterRules task = new RegisterRules(loader, qProfileRules, dbClient, ruleIndexer, activeRuleIndexer,
-      languages, system, organizationFlags, webServerRuleFinder, uuidFactory);
+      languages, system, organizationFlags, webServerRuleFinder, uuidFactory, metadataIndex);
     task.start();
     // Execute a commit to refresh session state as the task is using its own session
     db.getSession().commit();
@@ -1048,6 +1056,17 @@ public class RegisterRulesTest {
     repo.done();
   }
 
+  private void verifyIndicesMarkedAsInitialized() {
+    verify(metadataIndex).setInitialized(RuleIndexDefinition.TYPE_RULE,true);
+    verify(metadataIndex).setInitialized(RuleIndexDefinition.TYPE_RULE_EXTENSION,true);
+    verify(metadataIndex).setInitialized(RuleIndexDefinition.TYPE_ACTIVE_RULE, true);
+    reset(metadataIndex);
+  }
+
+  private void verifyIndicesNotMarkedAsInitialized() {
+    verifyNoInteractions(metadataIndex);
+  }
+
   private RuleParamDto getParam(List<RuleParamDto> params, String key) {
     for (RuleParamDto param : params) {
       if (param.getName().equals(key)) {