]> source.dussan.org Git - sonarqube.git/commitdiff
SONAR-5389 Skipe execution of Analyzers according to provided metadata
authorJulien HENRY <julien.henry@sonarsource.com>
Thu, 19 Jun 2014 06:59:17 +0000 (08:59 +0200)
committerJulien HENRY <julien.henry@sonarsource.com>
Thu, 19 Jun 2014 08:19:37 +0000 (10:19 +0200)
sonar-batch/src/main/java/org/sonar/batch/bootstrap/BatchExtensionDictionnary.java
sonar-batch/src/main/java/org/sonar/batch/scan/ModuleScanContainer.java
sonar-batch/src/main/java/org/sonar/batch/scan/SensorWrapper.java
sonar-batch/src/main/java/org/sonar/batch/scan2/AnalyzerOptimizer.java [new file with mode: 0644]
sonar-batch/src/main/java/org/sonar/batch/scan2/AnalyzersExecutor.java
sonar-batch/src/main/java/org/sonar/batch/scan2/ModuleScanContainer.java
sonar-batch/src/test/java/org/sonar/batch/bootstrap/BatchExtensionDictionnaryTest.java
sonar-plugin-api/src/main/java/org/sonar/api/batch/analyzer/internal/DefaultAnalyzerDescriptor.java

index fca38c4a4ce3086ef7a569c9928d2141dfcb4be4..622a7ef92b9bbd7b076ca9d3110a212b70c5d4b1 100644 (file)
@@ -29,6 +29,7 @@ import org.sonar.api.batch.fs.FileSystem;
 import org.sonar.api.platform.ComponentContainer;
 import org.sonar.api.resources.Project;
 import org.sonar.batch.scan.SensorWrapper;
+import org.sonar.batch.scan2.AnalyzerOptimizer;
 
 import javax.annotation.Nullable;
 
@@ -42,11 +43,13 @@ public class BatchExtensionDictionnary extends org.sonar.api.batch.BatchExtensio
 
   private FileSystem fs;
   private AnalyzerContext context;
+  private AnalyzerOptimizer analyzerOptimizer;
 
-  public BatchExtensionDictionnary(ComponentContainer componentContainer, FileSystem fs, AnalyzerContext context) {
+  public BatchExtensionDictionnary(ComponentContainer componentContainer, FileSystem fs, AnalyzerContext context, AnalyzerOptimizer analyzerOptimizer) {
     super(componentContainer);
     this.fs = fs;
     this.context = context;
+    this.analyzerOptimizer = analyzerOptimizer;
   }
 
   public <T> Collection<T> select(Class<T> type, @Nullable Project project, boolean sort, @Nullable ExtensionMatcher matcher) {
@@ -61,7 +64,7 @@ public class BatchExtensionDictionnary extends org.sonar.api.batch.BatchExtensio
     List<T> result = Lists.newArrayList();
     for (Object extension : getExtensions(type)) {
       if (type == Sensor.class && extension instanceof Analyzer) {
-        extension = new SensorWrapper((Analyzer) extension, context, fs);
+        extension = new SensorWrapper((Analyzer) extension, context, fs, analyzerOptimizer);
       }
       if (shouldKeep(type, extension, project, matcher)) {
         result.add((T) extension);
index a0584e490d93439d38f5590f73f3c394803ecc92..0935b576062661809f961fcd1877d823264086c9 100644 (file)
@@ -81,6 +81,7 @@ import org.sonar.batch.scan.filesystem.PreviousFileHashLoader;
 import org.sonar.batch.scan.filesystem.ProjectFileSystemAdapter;
 import org.sonar.batch.scan.filesystem.StatusDetectionFactory;
 import org.sonar.batch.scan.report.JsonReport;
+import org.sonar.batch.scan2.AnalyzerOptimizer;
 import org.sonar.core.component.ScanPerspectives;
 import org.sonar.core.measure.MeasurementFilters;
 
@@ -137,6 +138,8 @@ public class ModuleScanContainer extends ComponentContainer {
       ProjectFileSystemAdapter.class,
       QProfileVerifier.class,
 
+      AnalyzerOptimizer.class,
+
       // the Snapshot component will be removed when asynchronous measures are improved (required for AsynchronousMeasureSensor)
       getComponentByType(ResourcePersister.class).getSnapshot(module),
 
index ac53dbec1db9944bdf199aab2d98bb09a69eb47e..6f2e09acc3fdf3eede3c582bf4d10d3884875075 100644 (file)
@@ -29,6 +29,7 @@ import org.sonar.api.batch.analyzer.internal.DefaultAnalyzerDescriptor;
 import org.sonar.api.batch.fs.FileSystem;
 import org.sonar.api.batch.measures.Metric;
 import org.sonar.api.resources.Project;
+import org.sonar.batch.scan2.AnalyzerOptimizer;
 
 import java.util.Arrays;
 import java.util.List;
@@ -39,9 +40,11 @@ public class SensorWrapper implements Sensor {
   private AnalyzerContext adaptor;
   private FileSystem fs;
   private DefaultAnalyzerDescriptor descriptor;
+  private AnalyzerOptimizer optimizer;
 
-  public SensorWrapper(Analyzer analyzer, AnalyzerContext adaptor, FileSystem fs) {
+  public SensorWrapper(Analyzer analyzer, AnalyzerContext adaptor, FileSystem fs, AnalyzerOptimizer optimizer) {
     this.analyzer = analyzer;
+    this.optimizer = optimizer;
     descriptor = new DefaultAnalyzerDescriptor();
     analyzer.describe(descriptor);
     this.adaptor = adaptor;
@@ -60,19 +63,7 @@ public class SensorWrapper implements Sensor {
 
   @Override
   public boolean shouldExecuteOnProject(Project project) {
-    if (!descriptor.languages().isEmpty()) {
-      if (project.getLanguageKey() != null && !descriptor.languages().contains(project.getLanguageKey())) {
-        return false;
-      }
-      boolean hasFile = false;
-      for (String languageKey : descriptor.languages()) {
-        hasFile |= fs.hasFiles(fs.predicates().hasLanguage(languageKey));
-      }
-      if (!hasFile) {
-        return false;
-      }
-    }
-    return true;
+    return optimizer.shouldExecute(descriptor);
   }
 
   @Override
diff --git a/sonar-batch/src/main/java/org/sonar/batch/scan2/AnalyzerOptimizer.java b/sonar-batch/src/main/java/org/sonar/batch/scan2/AnalyzerOptimizer.java
new file mode 100644 (file)
index 0000000..3ad0a29
--- /dev/null
@@ -0,0 +1,49 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2014 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube 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.
+ *
+ * SonarQube 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.batch.scan2;
+
+import org.sonar.api.BatchComponent;
+import org.sonar.api.batch.analyzer.internal.DefaultAnalyzerDescriptor;
+import org.sonar.api.batch.fs.FilePredicate;
+import org.sonar.api.batch.fs.FileSystem;
+
+public class AnalyzerOptimizer implements BatchComponent {
+
+  private FileSystem fs;
+
+  public AnalyzerOptimizer(FileSystem fs) {
+    this.fs = fs;
+  }
+
+  /**
+   * Decide if the given Analyzer should be executed.
+   */
+  public boolean shouldExecute(DefaultAnalyzerDescriptor descriptor) {
+    FilePredicate predicate = fs.predicates().hasLanguages(descriptor.languages());
+    if (descriptor.types().size() == 1) {
+      // Size = 0 or Size = 2 means both main and test type
+      predicate = fs.predicates().and(
+        predicate,
+        fs.predicates().hasType(descriptor.types().iterator().next()));
+    }
+    return fs.hasFiles(predicate);
+  }
+
+}
index f90cb5ad4a4aa929871636f47fd9e3fa395d8a0a..7bb802e301c333ca0131b85880ddb1b29ab1f6be 100644 (file)
@@ -34,9 +34,11 @@ public class AnalyzersExecutor implements BatchComponent {
   private static final Logger LOG = LoggerFactory.getLogger(AnalyzersExecutor.class);
 
   private BatchExtensionDictionnary selector;
+  private AnalyzerOptimizer optimizer;
 
-  public AnalyzersExecutor(BatchExtensionDictionnary selector) {
+  public AnalyzersExecutor(BatchExtensionDictionnary selector, AnalyzerOptimizer optimizer) {
     this.selector = selector;
+    this.optimizer = optimizer;
   }
 
   public void execute(AnalyzerContext context) {
@@ -47,6 +49,11 @@ public class AnalyzersExecutor implements BatchComponent {
       DefaultAnalyzerDescriptor descriptor = new DefaultAnalyzerDescriptor();
       analyzer.describe(descriptor);
 
+      if (!optimizer.shouldExecute(descriptor)) {
+        LOG.debug("Analyzer skipped: " + descriptor.name());
+        continue;
+      }
+
       LOG.info("Execute analyzer: " + descriptor.name());
 
       executeSensor(context, analyzer);
index 6982d3da3b28e1b0984140161f781422b79ce6e1..fc6c0e85b3b8e7f67d71de4aa38ce4764a3b19e6 100644 (file)
@@ -98,6 +98,8 @@ public class ModuleScanContainer extends ComponentContainer {
       ModuleFileSystemInitializer.class,
       QProfileVerifier.class,
 
+      AnalyzerOptimizer.class,
+
       DefaultAnalyzerContext.class,
       BatchExtensionDictionnary.class,
       IssueFilters.class,
index ff878582c68ab479350933bf686674282bee6753..55518ac42d27bfd2b0c3793478f898d4cbfd257d 100644 (file)
  */
 package org.sonar.batch.bootstrap;
 
-import org.sonar.api.batch.analyzer.AnalyzerContext;
-
 import org.junit.Test;
 import org.sonar.api.BatchExtension;
 import org.sonar.api.batch.Sensor;
 import org.sonar.api.batch.SensorContext;
+import org.sonar.api.batch.analyzer.AnalyzerContext;
 import org.sonar.api.batch.fs.FileSystem;
 import org.sonar.api.platform.ComponentContainer;
 import org.sonar.api.resources.Project;
+import org.sonar.batch.scan2.AnalyzerOptimizer;
 
 import java.util.Collection;
 
@@ -43,7 +43,7 @@ public class BatchExtensionDictionnaryTest {
     for (BatchExtension extension : extensions) {
       iocContainer.addSingleton(extension);
     }
-    return new BatchExtensionDictionnary(iocContainer, mock(FileSystem.class), mock(AnalyzerContext.class));
+    return new BatchExtensionDictionnary(iocContainer, mock(FileSystem.class), mock(AnalyzerContext.class), mock(AnalyzerOptimizer.class));
   }
 
   @Test
index 29fb8730fc1f623b9b177f3c608837808ac5bd84..9fc41b65dd083e85c703f5cf26eda033d6289f67 100644 (file)
@@ -50,8 +50,8 @@ public class DefaultAnalyzerDescriptor implements AnalyzerDescriptor {
     return Arrays.asList(languages);
   }
 
-  public InputFile.Type[] types() {
-    return types;
+  public Collection<InputFile.Type> types() {
+    return Arrays.asList(types);
   }
 
   @Override