Java High Level REST Client

ES java api.jpg

基本查询

请求

  1. GET /person/_search
  2. {
  3. "query": {
  4. "term": {
  5. "name.keyword": {
  6. "value": "张无忌",
  7. "boost": 1.0
  8. }
  9. }
  10. }
  11. }

响应

  1. {
  2. "took" : 0,
  3. "timed_out" : false,
  4. "_shards" : { // 分片信息
  5. "total" : 1, // 总计分片数
  6. "successful" : 1, // 查询成功的分片数
  7. "skipped" : 0, // 跳过查询的分片数
  8. "failed" : 0 // 查询失败的分片数
  9. },
  10. "hits" : { // 命中结果
  11. "total" : {
  12. "value" : 1, // 数量
  13. "relation" : "eq" // 关系:等于
  14. },
  15. "max_score" : 2.8526313, // 最高分数
  16. "hits" : [
  17. {
  18. "_index" : "person", // 索引
  19. "_type" : "_doc", // 类型
  20. "_id" : "1",
  21. "_score" : 2.8526313,
  22. "_source" : {
  23. "address" : "光明顶",
  24. "modifyTime" : "2021-06-29 16:48:56",
  25. "createTime" : "2021-05-14 16:50:33",
  26. "sect" : "明教",
  27. "sex" : "男",
  28. "skill" : "九阳神功",
  29. "name" : "张无忌",
  30. "id" : 1,
  31. "power" : 99,
  32. "age" : 18
  33. }
  34. }
  35. ]
  36. }
  37. }

Term查询

基本

  1. /**
  2. * term精确查询
  3. *
  4. * @throws IOException
  5. */
  6. @Autowired
  7. private RestHighLevelClient client;
  8. @Test
  9. public void queryTerm() throws IOException {
  10. // 根据索引创建查询请求
  11. SearchRequest searchRequest = new SearchRequest("person");
  12. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  13. // 构建查询语句
  14. searchSourceBuilder.query(QueryBuilders.termQuery("name.keyword", "张无忌"));
  15. System.out.println("searchSourceBuilder=====================" + searchSourceBuilder);
  16. searchRequest.source(searchSourceBuilder);
  17. SearchResponse response = client.search(searchRequest, RequestOptions.DEFAULT);
  18. System.out.println(JSONObject.toJSON(response));
  19. }

优化

  • 查询结果中会带有_score这一项,ES会根据结果匹配程度进行评分。打分是会耗费性能的,如果确认自己的查询不需要评分,就设置查询语句关闭评分
  • 可以通过Constant Score将查询转换为Filtering,避免算分,并利用缓存,提高性能 ```json

GET /person/_search { “query”: { “constant_score”: { “filter”: { “term”: { “sect.keyword”: { “value”: “张无忌”, “boost”: 1.0 } } }, “boost”: 1.0 } } }

SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder(); // 这样构造的查询条件,将不进行score计算,从而提高查询效率 searchSourceBuilder.query(QueryBuilders .constantScoreQuery(QueryBuilders .termQuery(“sect.keyword”, “明教”)));

  1. <a name="ZTfNr"></a>
  2. ### 多值查询
  3. ```json
  4. GET /person/_search
  5. {
  6. "query": {
  7. "terms": {
  8. "sect.keyword": [
  9. "明教",
  10. "武当派"
  11. ],
  12. "boost": 1.0
  13. }
  14. }
  15. }

java实现

  1. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  2. // 构建查询语句
  3. searchSourceBuilder.query(QueryBuilders
  4. .termsQuery("sect.keyword",
  5. Arrays.asList("明教", "武当派")));

范围查询

  1. GET /person/_search
  2. {
  3. "query":{
  4. "range":{
  5. "age":{
  6. "from":10,
  7. "to":20,
  8. "include_lower":true,
  9. "include_upper":true,
  10. "boost":1
  11. }
  12. }
  13. }
  14. }

Java实现

  1. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  2. // 构建查询语句
  3. searchSourceBuilder.query(QueryBuilders.rangeQuery("age").gte(10).lte(30));

前缀查询

  1. {
  2. "query": {
  3. "prefix": {
  4. "sect.keyword": {
  5. "value": "武当",
  6. "boost": 1.0
  7. }
  8. }
  9. }
  10. }

Java实现

  1. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  2. // 构建查询语句
  3. searchSourceBuilder.query(QueryBuilders.prefixQuery("sect.keyword","武当"));

通配符查询

  1. {
  2. "query": {
  3. "wildcard": {
  4. "sect.keyword": {
  5. "wildcard": "张*忌",
  6. "boost": 1.0
  7. }
  8. }
  9. }
  10. }

Java实现

  1. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  2. // 构建查询语句
  3. searchSourceBuilder.query(QueryBuilders.wildcardQuery("sect.keyword","张*忌"));

复合查询

  • must:所有的语句都必须匹配,与 ‘=’ 等价。
  • must_not:所有的语句都不能匹配,与 ‘!=’ 或 not in 等价。
  • should:至少有n个语句要匹配,n由参数控制。
    1. {
    2. "query": {
    3. "bool": {
    4. "must": [
    5. {
    6. "term": {
    7. "sex": {
    8. "value": "女",
    9. "boost": 1.0
    10. }
    11. }
    12. },
    13. {
    14. "term": {
    15. "sect.keywords": {
    16. "value": "明教",
    17. "boost": 1.0
    18. }
    19. }
    20. }
    21. ],
    22. "adjust_pure_negative": true,
    23. "boost": 1.0
    24. }
    25. }
    26. }

    Java实现

    ```json 示例1: SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder(); // 构建查询语句 searchSourceBuilder.query(QueryBuilders.boolQuery()
    1. .must(QueryBuilders.termQuery("sex", "女"))
    2. .must(QueryBuilders.termQuery("sect.keyword", "明教"))
    ); 示例2: SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder(); // 构建查询语句 BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery()
    1. .must(QueryBuilders.termQuery("sex", "女"))
    2. .must(QueryBuilders.rangeQuery("age").gte(30).lte(40))
    3. .mustNot(QueryBuilders.termQuery("sect.keyword", "明教"))
    4. .should(QueryBuilders.termQuery("address.keyword", "峨眉山"))
    5. .should(QueryBuilders.rangeQuery("power.keyword").gte(50).lte(80))
    6. .minimumShouldMatch(1); // 设置should至少需要满足几个条件

// 将BoolQueryBuilder构建到SearchSourceBuilder中 searchSourceBuilder.query(boolQueryBuilder);

  1. <a name="SGjop"></a>
  2. ### Filter查询
  3. - query和filter的区别:query查询的时候,会先比较查询条件,然后计算分值,最后返回文档结果;而filter是先判断是否满足查询条件,如果不满足会缓存查询结果(记录该文档不满足结果),满足的话,就直接缓存结果,filter不会对结果进行评分,能够提高查询效率。
  4. ```json
  5. {
  6. "query":{
  7. "bool":{
  8. "filter":[
  9. {
  10. "term":{
  11. "sex":{
  12. "value":"男",
  13. "boost":1
  14. }
  15. }
  16. }
  17. ],
  18. "adjust_pure_negative":true,
  19. "boost":1
  20. }
  21. }
  22. }

Java实现

  1. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  2. // 构建查询语句
  3. searchSourceBuilder.query(QueryBuilders.boolQuery()
  4. .filter(QueryBuilders.termQuery("sex", "男"))
  5. );

将must、must_not置于filter下,这种方式是最常用的

  1. {
  2. "query": {
  3. "bool": {
  4. "filter": [
  5. {
  6. "bool": {
  7. "must": [
  8. {
  9. "term": {
  10. "sect.keyword": {
  11. "value": "明教",
  12. "boost": 1.0
  13. }
  14. }
  15. },
  16. {
  17. "range": {
  18. "age": {
  19. "from": 20,
  20. "to": 35,
  21. "include_lower": true,
  22. "include_upper": true,
  23. "boost": 1.0
  24. }
  25. }
  26. }
  27. ],
  28. "must_not": [
  29. {
  30. "term": {
  31. "sex.keyword": {
  32. "value": "女",
  33. "boost": 1.0
  34. }
  35. }
  36. }
  37. ],
  38. "adjust_pure_negative": true,
  39. "boost": 1.0
  40. }
  41. }
  42. ],
  43. "adjust_pure_negative": true,
  44. "boost": 1.0
  45. }
  46. }
  47. }
  1. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  2. // 构建查询语句
  3. searchSourceBuilder.query(QueryBuilders.boolQuery()
  4. .filter(QueryBuilders.boolQuery()
  5. .must(QueryBuilders.termQuery("sect.keyword", "明教"))
  6. .must(QueryBuilders.rangeQuery("age").gte(20).lte(35))
  7. .mustNot(QueryBuilders.termQuery("sex.keyword", "女")))
  8. );

聚合查询

  1. SearchRequest searchRequest = new SearchRequest("person");
  2. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  3. searchSourceBuilder.size(0);
  4. // sect分组
  5. AggregationBuilder aggBuilder = AggregationBuilders.terms("sect_count").field("sect.keyword");
  6. searchSourceBuilder.aggregation(aggBuilder);