]> source.dussan.org Git - sonarqube.git/commitdiff
SONAR-6017 Add query and page size fields to issues tags search (for manual selection)
authorJean-Baptiste Lievremont <jean-baptiste.lievremont@sonarsource.com>
Tue, 20 Jan 2015 09:42:19 +0000 (10:42 +0100)
committerJean-Baptiste Lievremont <jean-baptiste.lievremont@sonarsource.com>
Tue, 20 Jan 2015 14:56:24 +0000 (15:56 +0100)
server/sonar-server/src/main/java/org/sonar/server/issue/ws/TagsAction.java
server/sonar-server/src/main/java/org/sonar/server/rule/RuleService.java
server/sonar-server/src/main/java/org/sonar/server/rule/index/RuleIndex.java
server/sonar-server/src/main/java/org/sonar/server/rule/ws/TagsAction.java
server/sonar-server/src/test/java/org/sonar/server/rule/ws/RulesWebServiceMediumTest.java
server/sonar-server/src/test/resources/org/sonar/server/rule/ws/RulesWebServiceMediumTest/get_tags_filtered.json [new file with mode: 0644]
server/sonar-server/src/test/resources/org/sonar/server/rule/ws/RulesWebServiceMediumTest/get_tags_limited.json [new file with mode: 0644]

index a657e5cdd392adae8d9876cdad4f0c3c22a88028..b89f667106a6816606d4210da92a0854c232fb35 100644 (file)
 package org.sonar.server.issue.ws;
 
 import com.google.common.io.Resources;
-
-import org.sonar.api.server.ws.WebService.NewAction;
-import org.sonar.server.issue.IssueService;
-import org.sonar.api.utils.text.JsonWriter;
-import org.sonar.api.server.ws.WebService;
 import org.sonar.api.server.ws.Request;
-import org.sonar.api.server.ws.Response;
 import org.sonar.api.server.ws.RequestHandler;
+import org.sonar.api.server.ws.Response;
+import org.sonar.api.server.ws.WebService;
+import org.sonar.api.server.ws.WebService.NewAction;
+import org.sonar.api.utils.text.JsonWriter;
+import org.sonar.server.issue.IssueService;
 
 /**
  * List issue tags matching a given query.
index bae141797a22ea28696b093b7965b5c8408f8740..cfb15e659826c06eda4e0e786786f3119a7e7a5a 100644 (file)
@@ -31,6 +31,7 @@ import org.sonar.server.search.Result;
 import org.sonar.server.user.UserSession;
 
 import javax.annotation.CheckForNull;
+import javax.annotation.Nullable;
 
 import java.util.Collection;
 import java.util.List;
@@ -86,6 +87,14 @@ public class RuleService implements ServerComponent {
     return index.terms(RuleNormalizer.RuleField.ALL_TAGS.field());
   }
 
+  /**
+   * List tags matching a given criterion
+   */
+  public Set<String> listTags(@Nullable String query, int size) {
+    /** using combined ALL_TAGS field of ES until ES update that has multiTerms aggregation */
+    return index.terms(RuleNormalizer.RuleField.ALL_TAGS.field(), query, size);
+  }
+
   public void update(RuleUpdate update) {
     checkPermission();
     ruleUpdater.update(update, UserSession.get());
index 71a806c197fa82ccdb149300fbcf0e9847f7e762..d63b25dc6d02d0140b8556ce74874ad8aced58f7 100644 (file)
@@ -45,6 +45,7 @@ import org.elasticsearch.search.aggregations.AggregationBuilder;
 import org.elasticsearch.search.aggregations.AggregationBuilders;
 import org.elasticsearch.search.aggregations.bucket.global.GlobalBuilder;
 import org.elasticsearch.search.aggregations.bucket.terms.Terms;
+import org.elasticsearch.search.aggregations.bucket.terms.TermsBuilder;
 import org.elasticsearch.search.sort.FieldSortBuilder;
 import org.elasticsearch.search.sort.SortBuilders;
 import org.elasticsearch.search.sort.SortOrder;
@@ -64,6 +65,7 @@ import org.sonar.server.search.SearchClient;
 import org.sonar.server.search.StickyFacetBuilder;
 
 import javax.annotation.CheckForNull;
+import javax.annotation.Nullable;
 
 import java.util.ArrayList;
 import java.util.Arrays;
@@ -484,16 +486,24 @@ public class RuleIndex extends BaseIndex<Rule, RuleDto, RuleKey> {
   }
 
   public Set<String> terms(String fields) {
+    return terms(fields, null, Integer.MAX_VALUE);
+  }
+
+  public Set<String> terms(String fields, @Nullable String query, int size) {
     Set<String> tags = new HashSet<String>();
     String key = "_ref";
 
+    TermsBuilder terms = AggregationBuilders.terms(key)
+      .field(fields)
+      .size(size)
+      .minDocCount(1);
+    if (query != null) {
+      terms.include(".*" + query + ".*");
+    }
     SearchRequestBuilder request = this.getClient()
       .prepareSearch(this.getIndexName())
       .setQuery(QueryBuilders.matchAllQuery())
-      .addAggregation(AggregationBuilders.terms(key)
-        .field(fields)
-        .size(Integer.MAX_VALUE)
-        .minDocCount(1));
+      .addAggregation(terms);
 
     SearchResponse esResponse = request.get();
 
index 9d5785adbca54ac66c01d9508e3dcc81c8c43d23..8d4c3d037e47783aacd03e04dc798b9eb266095f 100644 (file)
@@ -24,6 +24,7 @@ import org.sonar.api.server.ws.Request;
 import org.sonar.api.server.ws.RequestHandler;
 import org.sonar.api.server.ws.Response;
 import org.sonar.api.server.ws.WebService;
+import org.sonar.api.server.ws.WebService.NewAction;
 import org.sonar.api.utils.text.JsonWriter;
 import org.sonar.server.rule.RuleService;
 
@@ -38,17 +39,27 @@ public class TagsAction implements RequestHandler {
   }
 
   void define(WebService.NewController controller) {
-    controller
+    NewAction action = controller
       .createAction("tags")
-      .setDescription("List all rule tags")
+      .setDescription("List rule tags")
       .setSince("4.4")
       .setHandler(this)
       .setResponseExample(Resources.getResource(getClass(), "example-tags.json"));
+
+    action.createParam("q")
+      .setDescription("A pattern to match tags against")
+      .setExampleValue("misra");
+    action.createParam("ps")
+      .setDescription("The size of the list to return, 0 for all tags")
+      .setExampleValue("25")
+      .setDefaultValue("0");
   }
 
   @Override
   public void handle(Request request, Response response) {
-    Set<String> tags = service.listTags();
+    String query = request.param("q");
+    int pageSize = request.mandatoryParamAsInt("ps");
+    Set<String> tags = service.listTags(query, pageSize);
     JsonWriter json = response.newJsonWriter().beginObject();
     json.name("tags").beginArray();
     for (String tag : tags) {
index ba5a067b41489e77582dd155be0c66f94adeec1a..97cb91a606b84fc23b10de658fc8ac3e161621d1 100644 (file)
@@ -446,16 +446,17 @@ public class RulesWebServiceMediumTest {
     ruleDao.insert(session, rule);
 
     RuleDto rule2 = RuleTesting.newXooX2()
-      .setTags(ImmutableSet.of("java"))
+      .setTags(ImmutableSet.of("hello", "java"))
       .setSystemTags(ImmutableSet.of("sys1"));
     ruleDao.insert(session, rule2);
     session.commit();
 
     MockUserSession.set();
-    WsTester.TestRequest request = tester.wsTester().newGetRequest(API_ENDPOINT, API_TAGS_METHOD);
-    WsTester.Result result = request.execute();
-
-    result.assertJson(this.getClass(), "get_tags.json", false);
+    tester.wsTester().newGetRequest(API_ENDPOINT, API_TAGS_METHOD).execute().assertJson(this.getClass(), "get_tags.json", false);
+    tester.wsTester().newGetRequest(API_ENDPOINT, API_TAGS_METHOD)
+      .setParam("ps", "1").execute().assertJson(this.getClass(), "get_tags_limited.json", false);
+    tester.wsTester().newGetRequest(API_ENDPOINT, API_TAGS_METHOD)
+      .setParam("q", "ll").execute().assertJson(this.getClass(), "get_tags_filtered.json", false);
   }
 
   @Test
diff --git a/server/sonar-server/src/test/resources/org/sonar/server/rule/ws/RulesWebServiceMediumTest/get_tags_filtered.json b/server/sonar-server/src/test/resources/org/sonar/server/rule/ws/RulesWebServiceMediumTest/get_tags_filtered.json
new file mode 100644 (file)
index 0000000..0ce4ec6
--- /dev/null
@@ -0,0 +1 @@
+{"tags": ["hello"]}
\ No newline at end of file
diff --git a/server/sonar-server/src/test/resources/org/sonar/server/rule/ws/RulesWebServiceMediumTest/get_tags_limited.json b/server/sonar-server/src/test/resources/org/sonar/server/rule/ws/RulesWebServiceMediumTest/get_tags_limited.json
new file mode 100644 (file)
index 0000000..0ce4ec6
--- /dev/null
@@ -0,0 +1 @@
+{"tags": ["hello"]}
\ No newline at end of file