]> source.dussan.org Git - sonarqube.git/commitdiff
Sanitize package org.sonar.server.search
authorSimon Brandhof <simon.brandhof@sonarsource.com>
Thu, 12 May 2016 15:56:49 +0000 (17:56 +0200)
committerSimon Brandhof <simon.brandhof@sonarsource.com>
Mon, 16 May 2016 12:29:04 +0000 (14:29 +0200)
Keep only deprecated classes in package
org.sonar.server.search. Valid classes
are moved to org.sonar.server.es.

27 files changed:
server/sonar-ce/src/main/java/org/sonar/ce/container/ComputeEngineContainerImpl.java
server/sonar-ce/src/main/java/org/sonar/ce/es/EsIndexerEnabler.java
server/sonar-server/src/main/java/org/sonar/server/activity/index/ActivityDoc.java
server/sonar-server/src/main/java/org/sonar/server/es/BaseDoc.java [new file with mode: 0644]
server/sonar-server/src/main/java/org/sonar/server/es/BaseIndexer.java
server/sonar-server/src/main/java/org/sonar/server/es/EsUtils.java
server/sonar-server/src/main/java/org/sonar/server/es/IndexerStartupTask.java [new file with mode: 0644]
server/sonar-server/src/main/java/org/sonar/server/es/SearchResult.java
server/sonar-server/src/main/java/org/sonar/server/es/StickyFacetBuilder.java [new file with mode: 0644]
server/sonar-server/src/main/java/org/sonar/server/issue/index/IssueDoc.java
server/sonar-server/src/main/java/org/sonar/server/issue/index/IssueIndex.java
server/sonar-server/src/main/java/org/sonar/server/platform/platformlevel/PlatformLevelStartup.java
server/sonar-server/src/main/java/org/sonar/server/qualityprofile/index/ActiveRuleDoc.java
server/sonar-server/src/main/java/org/sonar/server/rule/index/RuleDoc.java
server/sonar-server/src/main/java/org/sonar/server/rule/index/RuleIndex.java
server/sonar-server/src/main/java/org/sonar/server/search/BaseDoc.java [deleted file]
server/sonar-server/src/main/java/org/sonar/server/search/IndexSynchronizer.java [deleted file]
server/sonar-server/src/main/java/org/sonar/server/search/StickyFacetBuilder.java [deleted file]
server/sonar-server/src/main/java/org/sonar/server/search/ws/BaseMapping.java
server/sonar-server/src/main/java/org/sonar/server/search/ws/SearchOptions.java
server/sonar-server/src/main/java/org/sonar/server/test/index/CoveredFileDoc.java
server/sonar-server/src/main/java/org/sonar/server/test/index/TestDoc.java
server/sonar-server/src/main/java/org/sonar/server/user/index/UserDoc.java
server/sonar-server/src/main/java/org/sonar/server/view/index/ViewDoc.java
server/sonar-server/src/test/java/org/sonar/server/es/EsTester.java
server/sonar-server/src/test/java/org/sonar/server/es/EsUtilsTest.java
server/sonar-server/src/test/java/org/sonar/server/search/BaseDocTest.java

index 2dcf5dcd9ec0d9780fe74676a4a8532c98b20611..4fe2f430a130eb4d881d82bb89af6f90fb9f3eba 100644 (file)
@@ -562,7 +562,7 @@ public class ComputeEngineContainerImpl implements ComputeEngineContainer {
     // NavigationWs.class, no Web Service in CE
   };
   private static final Object[] STARTUP_COMPONENTS = new Object[] {
-    // IndexSynchronizer.class, ES maintenance, responsibility of Web Server
+    // IndexerStartupTask.class, ES maintenance, responsibility of Web Server
     EsIndexerEnabler.class,
     // RegisterMetrics.class, DB maintenance, responsibility of Web Server
     // RegisterQualityGates.class, DB maintenance, responsibility of Web Server
index bd038fa68079d2d5fd06b31aae763288e687d28e..716567e9756b3b99aa59118e92c0028185881a94 100644 (file)
@@ -21,6 +21,7 @@ package org.sonar.ce.es;
 
 import org.picocontainer.Startable;
 import org.sonar.server.activity.index.ActivityIndexer;
+import org.sonar.server.es.IndexerStartupTask;
 import org.sonar.server.issue.index.IssueAuthorizationIndexer;
 import org.sonar.server.issue.index.IssueIndexer;
 import org.sonar.server.test.index.TestIndexer;
@@ -28,7 +29,7 @@ import org.sonar.server.user.index.UserIndexer;
 import org.sonar.server.view.index.ViewIndexer;
 
 /**
- * Replaces the {@link org.sonar.server.search.IndexSynchronizer} to enable indexers but without triggering a full
+ * Replaces the {@link IndexerStartupTask} to enable indexers but without triggering a full
  * indexation (it's the WebServer's responsibility).
  */
 public class EsIndexerEnabler implements Startable {
index fe139aebdf16dc7be4c247f1e76361341bb46946..02e17fd4beb0946e506be8451e4d29a37ddd98ed 100644 (file)
 package org.sonar.server.activity.index;
 
 import com.google.common.annotations.VisibleForTesting;
-import org.apache.commons.lang.builder.ReflectionToStringBuilder;
-import org.sonar.server.search.BaseDoc;
-
-import javax.annotation.CheckForNull;
-import javax.annotation.Nullable;
-
 import java.util.Date;
 import java.util.HashMap;
 import java.util.Map;
+import javax.annotation.CheckForNull;
+import javax.annotation.Nullable;
+import org.apache.commons.lang.builder.ReflectionToStringBuilder;
+import org.sonar.server.es.BaseDoc;
 
 public class ActivityDoc extends BaseDoc {
 
diff --git a/server/sonar-server/src/main/java/org/sonar/server/es/BaseDoc.java b/server/sonar-server/src/main/java/org/sonar/server/es/BaseDoc.java
new file mode 100644 (file)
index 0000000..4a1226f
--- /dev/null
@@ -0,0 +1,104 @@
+/*
+ * SonarQube
+ * Copyright (C) 2009-2016 SonarSource SA
+ * mailto:contact 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.es;
+
+import java.util.Date;
+import java.util.Map;
+import javax.annotation.CheckForNull;
+import javax.annotation.Nullable;
+import org.sonar.server.search.IndexUtils;
+
+import static com.google.common.collect.Maps.newHashMap;
+
+/**
+ * Base implementation for business objects based on elasticsearch document
+ */
+public abstract class BaseDoc {
+
+  protected final Map<String, Object> fields;
+
+  protected BaseDoc() {
+    this.fields = newHashMap();
+  }
+
+  protected BaseDoc(Map<String, Object> fields) {
+    this.fields = fields;
+  }
+
+  public String keyField() {
+    return (String) fields.get("key");
+  }
+
+  /**
+   * Use this method when field value can be null. See warning in {@link #getField(String)}
+   */
+  @CheckForNull
+  public <K> K getNullableField(String key) {
+    if (!fields.containsKey(key)) {
+      throw new IllegalStateException(String.format("Field %s not specified in query options", key));
+    }
+    return (K) fields.get(key);
+  }
+
+  @CheckForNull
+  public Date getNullableFieldAsDate(String key) {
+    Object val = getNullableField(key);
+    if (val != null) {
+      if (val instanceof Date) {
+        return (Date)val;
+      }
+      return IndexUtils.parseDateTime((String) val);
+    }
+    return null;
+  }
+
+  /**
+   * Use this method when you are sure that the value can't be null in ES document.
+   * <p/>
+   * Warning with numbers - even if mapping declares long field, value can be an Integer
+   * instead of an expected Long. The reason is that ES delegates the deserialization of JSON
+   * to Jackson, which doesn't know the field type declared in mapping. See
+   * https://groups.google.com/forum/#!searchin/elasticsearch/getsource$20integer$20long/elasticsearch/jxIY22TmA8U/PyqZPPyYQ0gJ
+   * for more details. Workaround is to cast to java.lang.Number and then to call {@link Number#longValue()}
+   */
+  public <K> K getField(String key) {
+    K value = getNullableField(key);
+    if (value == null) {
+      throw new IllegalStateException("Value of index field is null: " + key);
+    }
+    return value;
+  }
+
+  public Date getFieldAsDate(String key) {
+    Object value = getField(key);
+    if (value instanceof Date) {
+      return (Date)value;
+    }
+    return IndexUtils.parseDateTime((String)value);
+  }
+
+  public void setField(String key, @Nullable Object value) {
+    fields.put(key, value);
+  }
+
+  public Map<String, Object> getFields() {
+    return fields;
+  }
+}
index d4375262dcc48a4f6190f5602f6f554493b6265f..9978f7d45362baba2e43e95842330f260ccf73a3 100644 (file)
@@ -21,14 +21,13 @@ package org.sonar.server.es;
 
 import com.google.common.base.Throwables;
 import com.google.common.util.concurrent.Uninterruptibles;
-import org.picocontainer.Startable;
-import org.sonar.api.server.ServerSide;
-
 import java.util.concurrent.ExecutionException;
 import java.util.concurrent.Future;
 import java.util.concurrent.LinkedBlockingQueue;
 import java.util.concurrent.ThreadPoolExecutor;
 import java.util.concurrent.TimeUnit;
+import org.picocontainer.Startable;
+import org.sonar.api.server.ServerSide;
 
 @ServerSide
 public abstract class BaseIndexer implements Startable {
@@ -47,7 +46,7 @@ public abstract class BaseIndexer implements Startable {
    * asks for index refresh -> big performance hit.
    *
    * Indices are populated and refreshed when all startup components have been executed. See
-   * {@link org.sonar.server.search.IndexSynchronizer}
+   * {@link IndexerStartupTask}
    */
   private boolean enabled = false;
 
index c506e7bea26a5a72d68988d35a33064cf32470bf..9c74c0e3a4a065522c3d7632b4af72f3be912f4d 100644 (file)
@@ -39,7 +39,6 @@ import org.elasticsearch.common.unit.TimeValue;
 import org.elasticsearch.search.SearchHit;
 import org.elasticsearch.search.SearchHits;
 import org.elasticsearch.search.aggregations.bucket.terms.Terms;
-import org.sonar.server.search.BaseDoc;
 
 public class EsUtils {
 
diff --git a/server/sonar-server/src/main/java/org/sonar/server/es/IndexerStartupTask.java b/server/sonar-server/src/main/java/org/sonar/server/es/IndexerStartupTask.java
new file mode 100644 (file)
index 0000000..e3d2347
--- /dev/null
@@ -0,0 +1,81 @@
+/*
+ * SonarQube
+ * Copyright (C) 2009-2016 SonarSource SA
+ * mailto:contact 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.es;
+
+import org.sonar.api.config.Settings;
+import org.sonar.api.utils.log.Logger;
+import org.sonar.api.utils.log.Loggers;
+import org.sonar.server.activity.index.ActivityIndexer;
+import org.sonar.server.issue.index.IssueAuthorizationIndexer;
+import org.sonar.server.issue.index.IssueIndexer;
+import org.sonar.server.test.index.TestIndexer;
+import org.sonar.server.user.index.UserIndexer;
+import org.sonar.server.view.index.ViewIndexer;
+
+public class IndexerStartupTask {
+
+  private static final Logger LOG = Loggers.get(IndexerStartupTask.class);
+
+  private final TestIndexer testIndexer;
+  private final IssueAuthorizationIndexer issueAuthorizationIndexer;
+  private final IssueIndexer issueIndexer;
+  private final UserIndexer userIndexer;
+  private final ViewIndexer viewIndexer;
+  private final ActivityIndexer activityIndexer;
+  private final Settings settings;
+
+  /**
+   * Limitation - {@link org.sonar.server.es.BaseIndexer} are not injected through an array or a collection
+   * because we need {@link org.sonar.server.issue.index.IssueAuthorizationIndexer} to be executed before
+   * {@link org.sonar.server.issue.index.IssueIndexer}
+   */
+  public IndexerStartupTask(TestIndexer testIndexer, IssueAuthorizationIndexer issueAuthorizationIndexer, IssueIndexer issueIndexer,
+    UserIndexer userIndexer, ViewIndexer viewIndexer, ActivityIndexer activityIndexer,
+    Settings settings) {
+    this.testIndexer = testIndexer;
+    this.issueAuthorizationIndexer = issueAuthorizationIndexer;
+    this.issueIndexer = issueIndexer;
+    this.userIndexer = userIndexer;
+    this.viewIndexer = viewIndexer;
+    this.activityIndexer = activityIndexer;
+    this.settings = settings;
+  }
+
+  public void execute() {
+    if (!settings.getBoolean("sonar.internal.es.disableIndexes")) {
+      LOG.info("Index activities");
+      activityIndexer.setEnabled(true).index();
+
+      LOG.info("Index issues");
+      issueAuthorizationIndexer.setEnabled(true).index();
+      issueIndexer.setEnabled(true).index();
+
+      LOG.info("Index tests");
+      testIndexer.setEnabled(true).index();
+
+      LOG.info("Index users");
+      userIndexer.setEnabled(true).index();
+
+      LOG.info("Index views");
+      viewIndexer.setEnabled(true).index();
+    }
+  }
+
+}
index 74e916130d6ae434413b4df634dccb5b23e618d6..c98c4303a629901e4a9ba6be0a8cb0439a993664 100644 (file)
 package org.sonar.server.es;
 
 import com.google.common.base.Function;
-import org.apache.commons.lang.builder.ReflectionToStringBuilder;
-import org.elasticsearch.action.search.SearchResponse;
-import org.sonar.server.search.BaseDoc;
-
 import java.util.List;
 import java.util.Map;
+import org.apache.commons.lang.builder.ReflectionToStringBuilder;
+import org.elasticsearch.action.search.SearchResponse;
 
 public class SearchResult<DOC extends BaseDoc> {
 
diff --git a/server/sonar-server/src/main/java/org/sonar/server/es/StickyFacetBuilder.java b/server/sonar-server/src/main/java/org/sonar/server/es/StickyFacetBuilder.java
new file mode 100644 (file)
index 0000000..b4d2109
--- /dev/null
@@ -0,0 +1,121 @@
+/*
+ * SonarQube
+ * Copyright (C) 2009-2016 SonarSource SA
+ * mailto:contact 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.es;
+
+import com.google.common.base.Joiner;
+import java.util.Map;
+import javax.annotation.Nullable;
+import org.apache.commons.lang.ArrayUtils;
+import org.elasticsearch.index.query.BoolFilterBuilder;
+import org.elasticsearch.index.query.FilterBuilder;
+import org.elasticsearch.index.query.FilterBuilders;
+import org.elasticsearch.index.query.QueryBuilder;
+import org.elasticsearch.search.aggregations.AbstractAggregationBuilder;
+import org.elasticsearch.search.aggregations.AggregationBuilder;
+import org.elasticsearch.search.aggregations.AggregationBuilders;
+import org.elasticsearch.search.aggregations.bucket.filter.FilterAggregationBuilder;
+import org.elasticsearch.search.aggregations.bucket.terms.Terms;
+import org.elasticsearch.search.aggregations.bucket.terms.Terms.Order;
+import org.elasticsearch.search.aggregations.bucket.terms.TermsBuilder;
+
+public class StickyFacetBuilder {
+
+  private static final int FACET_DEFAULT_MIN_DOC_COUNT = 1;
+  private static final int FACET_DEFAULT_SIZE = 10;
+  private static final Order FACET_DEFAULT_ORDER = Terms.Order.count(false);
+
+  private final QueryBuilder query;
+  private final Map<String, FilterBuilder> filters;
+  private final AbstractAggregationBuilder subAggregation;
+  private final Order order;
+
+  public StickyFacetBuilder(QueryBuilder query, Map<String, FilterBuilder> filters) {
+    this(query, filters, null, FACET_DEFAULT_ORDER);
+  }
+
+  public StickyFacetBuilder(QueryBuilder query, Map<String, FilterBuilder> filters, @Nullable AbstractAggregationBuilder subAggregation, @Nullable Order order) {
+    this.query = query;
+    this.filters = filters;
+    this.subAggregation = subAggregation;
+    this.order = order;
+  }
+
+  public QueryBuilder query() {
+    return query;
+  }
+
+  public Map<String, FilterBuilder> filters() {
+    return filters;
+  }
+
+  public AggregationBuilder buildStickyFacet(String fieldName, String facetName, Object... selected) {
+    return buildStickyFacet(fieldName, facetName, FACET_DEFAULT_SIZE, selected);
+  }
+
+  public AggregationBuilder buildStickyFacet(String fieldName, String facetName, int size, Object... selected) {
+    BoolFilterBuilder facetFilter = getStickyFacetFilter(fieldName);
+    FilterAggregationBuilder facetTopAggregation = buildTopFacetAggregation(fieldName, facetName, facetFilter, size);
+    facetTopAggregation = addSelectedItemsToFacet(fieldName, facetName, facetTopAggregation, selected);
+
+    return AggregationBuilders
+      .global(facetName)
+      .subAggregation(facetTopAggregation);
+  }
+
+  public BoolFilterBuilder getStickyFacetFilter(String... fieldNames) {
+    BoolFilterBuilder facetFilter = FilterBuilders.boolFilter().must(FilterBuilders.queryFilter(query));
+    for (Map.Entry<String, FilterBuilder> filter : filters.entrySet()) {
+      if (filter.getValue() != null && !ArrayUtils.contains(fieldNames, filter.getKey())) {
+        facetFilter.must(filter.getValue());
+      }
+    }
+    return facetFilter;
+  }
+
+  public FilterAggregationBuilder buildTopFacetAggregation(String fieldName, String facetName, BoolFilterBuilder facetFilter, int size) {
+    TermsBuilder termsAggregation = AggregationBuilders.terms(facetName)
+      .field(fieldName)
+      .order(order)
+      // .order(Terms.Order.aggregation("debt", false))
+      .size(size)
+      .minDocCount(FACET_DEFAULT_MIN_DOC_COUNT);
+    if (subAggregation != null) {
+      termsAggregation = termsAggregation.subAggregation(subAggregation);
+    }
+    return AggregationBuilders
+      .filter(facetName + "_filter")
+      .filter(facetFilter)
+      .subAggregation(termsAggregation);
+  }
+
+  public FilterAggregationBuilder addSelectedItemsToFacet(String fieldName, String facetName, FilterAggregationBuilder facetTopAggregation, Object... selected) {
+    if (selected.length > 0) {
+      TermsBuilder selectedTerms = AggregationBuilders.terms(facetName + "_selected")
+        .field(fieldName)
+        .include(Joiner.on('|').join(selected));
+      if (subAggregation != null) {
+        selectedTerms = selectedTerms.subAggregation(subAggregation);
+      }
+      facetTopAggregation.subAggregation(
+        selectedTerms);
+    }
+    return facetTopAggregation;
+  }
+}
index 777f4b14dfdcaee7c9cbdd7f43149cf06170de7d..e43853c91347c4dd26e5deaf5ec11cc978a68632 100644 (file)
@@ -35,7 +35,7 @@ import org.sonar.api.rule.Severity;
 import org.sonar.api.rules.RuleType;
 import org.sonar.api.utils.Duration;
 import org.sonar.api.utils.KeyValueFormat;
-import org.sonar.server.search.BaseDoc;
+import org.sonar.server.es.BaseDoc;
 
 public class IssueDoc extends BaseDoc implements Issue {
 
index 0631d8e00c5f6efa14799dfb29d9077d8bc23ddc..0739bda24337aee9095f9fe775999a176fc2e694 100644 (file)
@@ -74,10 +74,10 @@ import org.sonar.server.es.EsUtils;
 import org.sonar.server.es.SearchOptions;
 import org.sonar.server.es.SearchResult;
 import org.sonar.server.es.Sorting;
+import org.sonar.server.es.StickyFacetBuilder;
 import org.sonar.server.exceptions.NotFoundException;
 import org.sonar.server.issue.IssueQuery;
 import org.sonar.server.rule.index.RuleIndexDefinition;
-import org.sonar.server.search.StickyFacetBuilder;
 import org.sonar.server.user.UserSession;
 import org.sonar.server.view.index.ViewIndexDefinition;
 
index 3ad05d77909182a2e44b10a609c0c9f09e889f75..662d46becabf4a787c0e41277b36839c3adf291d 100644 (file)
 package org.sonar.server.platform.platformlevel;
 
 import org.sonar.server.app.ProcessCommandWrapper;
+import org.sonar.server.es.IndexerStartupTask;
 import org.sonar.server.issue.filter.RegisterIssueFilters;
 import org.sonar.server.platform.ServerLifecycleNotifier;
 import org.sonar.server.qualitygate.RegisterQualityGates;
 import org.sonar.server.qualityprofile.RegisterQualityProfiles;
 import org.sonar.server.rule.RegisterRules;
-import org.sonar.server.search.IndexSynchronizer;
 import org.sonar.server.startup.ClearRulesOverloadedDebt;
 import org.sonar.server.startup.DisplayLogOnDeprecatedProjects;
 import org.sonar.server.startup.FeedUsersLocalStartupTask;
@@ -49,7 +49,7 @@ public class PlatformLevelStartup extends PlatformLevel {
   @Override
   protected void configureLevel() {
     add(
-      IndexSynchronizer.class,
+      IndexerStartupTask.class,
       RegisterMetrics.class,
       RegisterQualityGates.class,
       RegisterRules.class,
@@ -76,7 +76,7 @@ public class PlatformLevelStartup extends PlatformLevel {
       @Override
       protected void doPrivileged() {
         PlatformLevelStartup.super.start();
-        getComponentByType(IndexSynchronizer.class).execute();
+        getComponentByType(IndexerStartupTask.class).execute();
         getComponentByType(ServerLifecycleNotifier.class).notifyStart();
         getComponentByType(ProcessCommandWrapper.class).notifyOperational();
       }
index 5be909fa23b7bb6c20966801e030d92042e1282a..bfebf07fd3146d2de8b1d6bec41f0460a58577ac 100644 (file)
@@ -22,8 +22,8 @@ package org.sonar.server.qualityprofile.index;
 import com.google.common.collect.Maps;
 import javax.annotation.Nullable;
 import org.sonar.db.qualityprofile.ActiveRuleKey;
+import org.sonar.server.es.BaseDoc;
 import org.sonar.server.qualityprofile.ActiveRule;
-import org.sonar.server.search.BaseDoc;
 
 import static com.google.common.base.Preconditions.checkNotNull;
 import static org.apache.commons.lang.StringUtils.containsIgnoreCase;
index a2908fb8e6f6144ecb40f4c2d55de412c82f00bc..0f20bb301bb788b7026f8ff316ccae0768c9cf05 100644 (file)
@@ -27,7 +27,7 @@ import org.apache.commons.lang.builder.ReflectionToStringBuilder;
 import org.sonar.api.rule.RuleKey;
 import org.sonar.api.rule.RuleStatus;
 import org.sonar.api.rules.RuleType;
-import org.sonar.server.search.BaseDoc;
+import org.sonar.server.es.BaseDoc;
 
 /**
  * Implementation of Rule based on an Elasticsearch document
index 7e7fccfc38b69c4636eaaf9e37255d5e7d475d96..9578a8c0979b8557fecdb01e59ebce7b69deca8d 100644 (file)
@@ -64,7 +64,7 @@ import org.sonar.server.es.BaseIndex;
 import org.sonar.server.es.EsClient;
 import org.sonar.server.es.SearchIdResult;
 import org.sonar.server.es.SearchOptions;
-import org.sonar.server.search.StickyFacetBuilder;
+import org.sonar.server.es.StickyFacetBuilder;
 
 import static org.elasticsearch.index.query.QueryBuilders.matchQuery;
 import static org.elasticsearch.index.query.QueryBuilders.simpleQueryStringQuery;
diff --git a/server/sonar-server/src/main/java/org/sonar/server/search/BaseDoc.java b/server/sonar-server/src/main/java/org/sonar/server/search/BaseDoc.java
deleted file mode 100644 (file)
index 69b3dfa..0000000
+++ /dev/null
@@ -1,104 +0,0 @@
-/*
- * SonarQube
- * Copyright (C) 2009-2016 SonarSource SA
- * mailto:contact 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.search;
-
-import javax.annotation.CheckForNull;
-import javax.annotation.Nullable;
-
-import java.util.Date;
-import java.util.Map;
-
-import static com.google.common.collect.Maps.newHashMap;
-
-/**
- * Base implementation for business objects based on elasticsearch document
- */
-public abstract class BaseDoc {
-
-  protected final Map<String, Object> fields;
-
-  protected BaseDoc() {
-    this.fields = newHashMap();
-  }
-
-  protected BaseDoc(Map<String, Object> fields) {
-    this.fields = fields;
-  }
-
-  public String keyField() {
-    return (String) fields.get("key");
-  }
-
-  /**
-   * Use this method when field value can be null. See warning in {@link #getField(String)}
-   */
-  @CheckForNull
-  public <K> K getNullableField(String key) {
-    if (!fields.containsKey(key)) {
-      throw new IllegalStateException(String.format("Field %s not specified in query options", key));
-    }
-    return (K) fields.get(key);
-  }
-
-  @CheckForNull
-  public Date getNullableFieldAsDate(String key) {
-    Object val = getNullableField(key);
-    if (val != null) {
-      if (val instanceof Date) {
-        return (Date)val;
-      }
-      return IndexUtils.parseDateTime((String) val);
-    }
-    return null;
-  }
-
-  /**
-   * Use this method when you are sure that the value can't be null in ES document.
-   * <p/>
-   * Warning with numbers - even if mapping declares long field, value can be an Integer
-   * instead of an expected Long. The reason is that ES delegates the deserialization of JSON
-   * to Jackson, which doesn't know the field type declared in mapping. See
-   * https://groups.google.com/forum/#!searchin/elasticsearch/getsource$20integer$20long/elasticsearch/jxIY22TmA8U/PyqZPPyYQ0gJ
-   * for more details. Workaround is to cast to java.lang.Number and then to call {@link Number#longValue()}
-   */
-  public <K> K getField(String key) {
-    K value = getNullableField(key);
-    if (value == null) {
-      throw new IllegalStateException("Value of index field is null: " + key);
-    }
-    return value;
-  }
-
-  public Date getFieldAsDate(String key) {
-    Object value = getField(key);
-    if (value instanceof Date) {
-      return (Date)value;
-    }
-    return IndexUtils.parseDateTime((String)value);
-  }
-
-  public void setField(String key, @Nullable Object value) {
-    fields.put(key, value);
-  }
-
-  public Map<String, Object> getFields() {
-    return fields;
-  }
-}
diff --git a/server/sonar-server/src/main/java/org/sonar/server/search/IndexSynchronizer.java b/server/sonar-server/src/main/java/org/sonar/server/search/IndexSynchronizer.java
deleted file mode 100644 (file)
index 657d027..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * SonarQube
- * Copyright (C) 2009-2016 SonarSource SA
- * mailto:contact 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.search;
-
-import org.sonar.api.config.Settings;
-import org.sonar.api.utils.log.Logger;
-import org.sonar.api.utils.log.Loggers;
-import org.sonar.server.activity.index.ActivityIndexer;
-import org.sonar.server.issue.index.IssueAuthorizationIndexer;
-import org.sonar.server.issue.index.IssueIndexer;
-import org.sonar.server.test.index.TestIndexer;
-import org.sonar.server.user.index.UserIndexer;
-import org.sonar.server.view.index.ViewIndexer;
-
-public class IndexSynchronizer {
-
-  private static final Logger LOG = Loggers.get(IndexSynchronizer.class);
-
-  private final TestIndexer testIndexer;
-  private final IssueAuthorizationIndexer issueAuthorizationIndexer;
-  private final IssueIndexer issueIndexer;
-  private final UserIndexer userIndexer;
-  private final ViewIndexer viewIndexer;
-  private final ActivityIndexer activityIndexer;
-  private final Settings settings;
-
-  /**
-   * Limitation - {@link org.sonar.server.es.BaseIndexer} are not injected through an array or a collection
-   * because we need {@link org.sonar.server.issue.index.IssueAuthorizationIndexer} to be executed before
-   * {@link org.sonar.server.issue.index.IssueIndexer}
-   */
-  public IndexSynchronizer(TestIndexer testIndexer, IssueAuthorizationIndexer issueAuthorizationIndexer, IssueIndexer issueIndexer,
-    UserIndexer userIndexer, ViewIndexer viewIndexer, ActivityIndexer activityIndexer,
-    Settings settings) {
-    this.testIndexer = testIndexer;
-    this.issueAuthorizationIndexer = issueAuthorizationIndexer;
-    this.issueIndexer = issueIndexer;
-    this.userIndexer = userIndexer;
-    this.viewIndexer = viewIndexer;
-    this.activityIndexer = activityIndexer;
-    this.settings = settings;
-  }
-
-  public void execute() {
-    if (!settings.getBoolean("sonar.internal.es.disableIndexes")) {
-      LOG.info("Index activities");
-      activityIndexer.setEnabled(true).index();
-
-      LOG.info("Index issues");
-      issueAuthorizationIndexer.setEnabled(true).index();
-      issueIndexer.setEnabled(true).index();
-
-      LOG.info("Index tests");
-      testIndexer.setEnabled(true).index();
-
-      LOG.info("Index users");
-      userIndexer.setEnabled(true).index();
-
-      LOG.info("Index views");
-      viewIndexer.setEnabled(true).index();
-    }
-  }
-
-}
diff --git a/server/sonar-server/src/main/java/org/sonar/server/search/StickyFacetBuilder.java b/server/sonar-server/src/main/java/org/sonar/server/search/StickyFacetBuilder.java
deleted file mode 100644 (file)
index 546b4ac..0000000
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * SonarQube
- * Copyright (C) 2009-2016 SonarSource SA
- * mailto:contact 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.search;
-
-import com.google.common.base.Joiner;
-import java.util.Map;
-import javax.annotation.Nullable;
-import org.apache.commons.lang.ArrayUtils;
-import org.elasticsearch.index.query.BoolFilterBuilder;
-import org.elasticsearch.index.query.FilterBuilder;
-import org.elasticsearch.index.query.FilterBuilders;
-import org.elasticsearch.index.query.QueryBuilder;
-import org.elasticsearch.search.aggregations.AbstractAggregationBuilder;
-import org.elasticsearch.search.aggregations.AggregationBuilder;
-import org.elasticsearch.search.aggregations.AggregationBuilders;
-import org.elasticsearch.search.aggregations.bucket.filter.FilterAggregationBuilder;
-import org.elasticsearch.search.aggregations.bucket.terms.Terms;
-import org.elasticsearch.search.aggregations.bucket.terms.Terms.Order;
-import org.elasticsearch.search.aggregations.bucket.terms.TermsBuilder;
-
-public class StickyFacetBuilder {
-
-  private static final int FACET_DEFAULT_MIN_DOC_COUNT = 1;
-  private static final int FACET_DEFAULT_SIZE = 10;
-  private static final Order FACET_DEFAULT_ORDER = Terms.Order.count(false);
-
-  private final QueryBuilder query;
-  private final Map<String, FilterBuilder> filters;
-  private final AbstractAggregationBuilder subAggregation;
-  private final Order order;
-
-  public StickyFacetBuilder(QueryBuilder query, Map<String, FilterBuilder> filters) {
-    this(query, filters, null, FACET_DEFAULT_ORDER);
-  }
-
-  public StickyFacetBuilder(QueryBuilder query, Map<String, FilterBuilder> filters, @Nullable AbstractAggregationBuilder subAggregation, @Nullable Order order) {
-    this.query = query;
-    this.filters = filters;
-    this.subAggregation = subAggregation;
-    this.order = order;
-  }
-
-  public QueryBuilder query() {
-    return query;
-  }
-
-  public Map<String, FilterBuilder> filters() {
-    return filters;
-  }
-
-  public AggregationBuilder buildStickyFacet(String fieldName, String facetName, Object... selected) {
-    return buildStickyFacet(fieldName, facetName, FACET_DEFAULT_SIZE, selected);
-  }
-
-  public AggregationBuilder buildStickyFacet(String fieldName, String facetName, int size, Object... selected) {
-    BoolFilterBuilder facetFilter = getStickyFacetFilter(fieldName);
-    FilterAggregationBuilder facetTopAggregation = buildTopFacetAggregation(fieldName, facetName, facetFilter, size);
-    facetTopAggregation = addSelectedItemsToFacet(fieldName, facetName, facetTopAggregation, selected);
-
-    return AggregationBuilders
-      .global(facetName)
-      .subAggregation(facetTopAggregation);
-  }
-
-  public BoolFilterBuilder getStickyFacetFilter(String... fieldNames) {
-    BoolFilterBuilder facetFilter = FilterBuilders.boolFilter().must(FilterBuilders.queryFilter(query));
-    for (Map.Entry<String, FilterBuilder> filter : filters.entrySet()) {
-      if (filter.getValue() != null && !ArrayUtils.contains(fieldNames, filter.getKey())) {
-        facetFilter.must(filter.getValue());
-      }
-    }
-    return facetFilter;
-  }
-
-  public FilterAggregationBuilder buildTopFacetAggregation(String fieldName, String facetName, BoolFilterBuilder facetFilter, int size) {
-    TermsBuilder termsAggregation = AggregationBuilders.terms(facetName)
-      .field(fieldName)
-      .order(order)
-      // .order(Terms.Order.aggregation("debt", false))
-      .size(size)
-      .minDocCount(FACET_DEFAULT_MIN_DOC_COUNT);
-    if (subAggregation != null) {
-      termsAggregation = termsAggregation.subAggregation(subAggregation);
-    }
-    return AggregationBuilders
-      .filter(facetName + "_filter")
-      .filter(facetFilter)
-      .subAggregation(termsAggregation);
-  }
-
-  public FilterAggregationBuilder addSelectedItemsToFacet(String fieldName, String facetName, FilterAggregationBuilder facetTopAggregation, Object... selected) {
-    if (selected.length > 0) {
-      TermsBuilder selectedTerms = AggregationBuilders.terms(facetName + "_selected")
-        .field(fieldName)
-        .include(Joiner.on('|').join(selected));
-      if (subAggregation != null) {
-        selectedTerms = selectedTerms.subAggregation(subAggregation);
-      }
-      facetTopAggregation.subAggregation(
-        selectedTerms);
-    }
-    return facetTopAggregation;
-  }
-}
index 69169996bd9125bf22d59edfb93fe5433fc0f9c4..3438f6a7f9f5a683d40ff3c4faa1cb5ddc660818 100644 (file)
@@ -27,14 +27,15 @@ import java.util.Set;
 import javax.annotation.Nullable;
 import org.sonar.api.server.ServerSide;
 import org.sonar.api.utils.text.JsonWriter;
-import org.sonar.server.search.BaseDoc;
+import org.sonar.server.es.BaseDoc;
 import org.sonar.server.search.IndexUtils;
 import org.sonar.server.search.QueryContext;
 
 /**
- * Mapping of search documents (see {@link org.sonar.server.search.BaseDoc}) to WS JSON responses
+ * Mapping of search documents (see {@link BaseDoc}) to WS JSON responses
  */
 @ServerSide
+@Deprecated
 public abstract class BaseMapping<DOC extends BaseDoc, CTX> {
 
   private final Multimap<String, String> indexFieldsByWsFields = LinkedHashMultimap.create();
index be75b06e49fd23643957d44f5f6c674c4458dde6..9dd44f98897f6aa19a8661b2bab1391fc72d16d6 100644 (file)
  */
 package org.sonar.server.search.ws;
 
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.List;
+import javax.annotation.CheckForNull;
+import javax.annotation.Nullable;
 import org.sonar.api.server.ws.Request;
 import org.sonar.api.server.ws.WebService;
 import org.sonar.api.utils.text.JsonWriter;
 import org.sonar.server.search.QueryContext;
 import org.sonar.server.search.Result;
 
-import javax.annotation.CheckForNull;
-import javax.annotation.Nullable;
-
-import java.util.Collection;
-import java.util.Iterator;
-import java.util.List;
-
 /**
  * Generic options for search web services
- *
  */
+@Deprecated
 public class SearchOptions {
 
   private int pageSize;
index dc4b0fb6fc78bee67fe75b25ee45b0d590460d2d..9668bf24b7fc49f948e5811706b5036d3279f003 100644 (file)
@@ -21,10 +21,9 @@ package org.sonar.server.test.index;
 
 import com.google.common.annotations.VisibleForTesting;
 import com.google.common.collect.Maps;
-import org.sonar.server.search.BaseDoc;
-
 import java.util.List;
 import java.util.Map;
+import org.sonar.server.es.BaseDoc;
 
 import static org.sonar.server.test.index.TestIndexDefinition.FIELD_COVERED_FILE_LINES;
 import static org.sonar.server.test.index.TestIndexDefinition.FIELD_COVERED_FILE_UUID;
index 614f8ba7ba1de85797b41b93a2ba9b88e6b6c0dd..7a3d9b10d4ac738c8b598b50ce520bfd5e3ae191 100644 (file)
@@ -21,12 +21,11 @@ package org.sonar.server.test.index;
 
 import com.google.common.annotations.VisibleForTesting;
 import com.google.common.collect.Maps;
-import org.sonar.server.search.BaseDoc;
-
-import javax.annotation.CheckForNull;
 import java.util.ArrayList;
 import java.util.List;
 import java.util.Map;
+import javax.annotation.CheckForNull;
+import org.sonar.server.es.BaseDoc;
 
 import static org.sonar.server.test.index.TestIndexDefinition.FIELD_COVERED_FILES;
 import static org.sonar.server.test.index.TestIndexDefinition.FIELD_DURATION_IN_MS;
index f075ed0ba7df3c67f1200b1031075e31b7add491..65c6fe7251889a559c37d9ba0c89ecedba732ed0 100644 (file)
 package org.sonar.server.user.index;
 
 import com.google.common.collect.Maps;
-import org.sonar.api.user.User;
-import org.sonar.server.search.BaseDoc;
-
-import javax.annotation.Nullable;
-
 import java.util.List;
 import java.util.Map;
+import javax.annotation.Nullable;
+import org.sonar.api.user.User;
+import org.sonar.server.es.BaseDoc;
 
 public class UserDoc extends BaseDoc implements User {
 
index 5afea72b5aa6286bb81fdd5451c84449225e6959..910055ab2435a8ffa5a0e1c3ce211606b7a8a6d9 100644 (file)
 package org.sonar.server.view.index;
 
 import com.google.common.collect.Maps;
-import org.sonar.server.search.BaseDoc;
-
 import java.util.List;
 import java.util.Map;
+import org.sonar.server.es.BaseDoc;
 
 public class ViewDoc extends BaseDoc {
 
index c08b19d6f55f20e0dcf320c9634a7ea120f93d7d..6d706d1d7759fb42660625adcbabc72576f3ac15 100644 (file)
@@ -50,7 +50,6 @@ import org.elasticsearch.search.SearchHit;
 import org.junit.rules.ExternalResource;
 import org.sonar.api.config.Settings;
 import org.sonar.core.platform.ComponentContainer;
-import org.sonar.server.search.BaseDoc;
 import org.sonar.test.TestUtils;
 
 import static com.google.common.collect.Lists.newArrayList;
index 017caf140c19745fe0e13cf5782ad05f4f7eea4a..25c6f83b40347a4fc6745331f817037d5d334d8e 100644 (file)
 package org.sonar.server.es;
 
 import com.google.common.base.Function;
+import java.util.Date;
+import java.util.List;
+import java.util.Map;
 import org.elasticsearch.search.SearchHit;
 import org.elasticsearch.search.SearchHits;
 import org.junit.Test;
 import org.mockito.Mockito;
 import org.sonar.server.issue.index.IssueDoc;
-import org.sonar.server.search.BaseDoc;
 import org.sonar.test.TestUtils;
 
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
 import static org.assertj.core.api.Assertions.assertThat;
 import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.when;
index a626beaafb6df568af7da6876ad85d5d040e0c41..53bea5371f3587d84545c94de4e61bf79b61144d 100644 (file)
 package org.sonar.server.search;
 
 import com.google.common.collect.Maps;
-import org.junit.Test;
-
 import java.util.Collections;
 import java.util.Date;
 import java.util.Map;
+import org.junit.Test;
+import org.sonar.server.es.BaseDoc;
 
 import static org.assertj.core.api.Assertions.assertThat;
 import static org.junit.Assert.fail;