1. 程式人生 > >elasticsearch-java客戶端測試

elasticsearch-java客戶端測試

edge bool testin ram ring update pre dsquery name

1、環境準備

(1)添加依賴

    <dependency>
        <groupId>org.elasticsearch.client</groupId>
        <artifactId>elasticsearch-rest-high-level-client</artifactId>
    </dependency>
    <dependency>
        <groupId>org.elasticsearch</groupId>
        <artifactId
>elasticsearch</artifactId> </dependency>

(2)配置文件

application.yml

server:
  port: ${port:40100}
spring:
  application: service-search
elasticsearch: 
  hostlist: 
    - 127.0.0.1:9200 #多個節點中間用逗號分隔[addr1,addr2]
      

(3)創建配置類

package com.search.config;

import java.util.ArrayList;
import java.util.List; import org.apache.http.HttpHost; import org.elasticsearch.client.RestClient; import org.elasticsearch.client.RestHighLevelClient; import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration;
import lombok.Getter; import lombok.Setter; @Configuration @ConfigurationProperties(prefix="elasticsearch") @Getter @Setter public class ElasticSearchConfig { private List<String> hostlist; @Bean public RestHighLevelClient restHighLevelClient(){ List<HttpHost> httpHostList = new ArrayList<>(hostlist.size()); //封裝es服務端地址 for(String host:hostlist){ HttpHost httpHost = new HttpHost(host.split(":")[0], Integer.parseInt(host.split(":")[1]), "http"); httpHostList.add(httpHost); } return new RestHighLevelClient(RestClient.builder(httpHostList.toArray(new HttpHost[0]))); } //把低級客戶端也註入,但是基本不用 @Bean public RestClient restClient(){ List<HttpHost> httpHostList = new ArrayList<>(hostlist.size()); //封裝es服務端地址 for(String host:hostlist){ HttpHost httpHost = new HttpHost(host.split(":")[0], Integer.parseInt(host.split(":")[1]), "http"); httpHostList.add(httpHost); } return RestClient.builder(httpHostList.toArray(new HttpHost[0])).build(); } }

2、索引管理測試

package com.search.test;

import java.io.FileInputStream;

import org.apache.commons.io.IOUtils;
import org.elasticsearch.action.admin.indices.create.CreateIndexRequest;
import org.elasticsearch.action.admin.indices.create.CreateIndexResponse;
import org.elasticsearch.action.admin.indices.delete.DeleteIndexRequest;
import org.elasticsearch.action.admin.indices.delete.DeleteIndexResponse;
import org.elasticsearch.client.IndicesClient;
import org.elasticsearch.client.RestClient;
import org.elasticsearch.client.RestHighLevelClient;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.common.xcontent.XContentType;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;


@SpringBootTest
@RunWith(SpringRunner.class)
public class TestIndex {

    @Autowired
    RestHighLevelClient client;
    
    @Autowired
    RestClient restClient;
    
    
    //創建索引庫
    @Test
    public void testCreateIndex()throws Exception{
        //創建索引請求對象、並設置索引名稱
        CreateIndexRequest createIndexRequest = new CreateIndexRequest("course");
        //設置參數
        Settings settings = Settings.builder().put("number_of_shards", 1)
                          .put("number_of_replicas",0)
                          .build();
        createIndexRequest.settings(settings);
        FileInputStream is = new FileInputStream(this.getClass().getResource("/").getPath()+"mapping.json");
        String mappingJson = IOUtils.toString(is);
        System.err.println(mappingJson);
        //設置映射
        createIndexRequest.mapping("doc",mappingJson,XContentType.JSON);
        //創建索引操作對象
        IndicesClient indices = client.indices();
        CreateIndexResponse createIndexResponse = indices.create(createIndexRequest);
        //獲得相應是否成功
        boolean acknowledged = createIndexResponse.isAcknowledged();
        System.out.println(acknowledged);
    }
    
    //刪除索引庫
    @Test
    public void testDeleteIndex()throws Exception{
        //穿建刪除索引庫請求對象
        DeleteIndexRequest deleteIndexRequest = new DeleteIndexRequest("course");
        //刪除索引庫
        DeleteIndexResponse deleteIndexResponse= client.indices().delete(deleteIndexRequest);        
        //刪除結果
        boolean acknowledged = deleteIndexResponse.isAcknowledged();
        System.out.println(acknowledged);
    }
}

mapping.json

         {
                "properties": {
                    "description": {
                        "type": "text",
                        "analyzer": "ik_max_word",
                        "search_analyzer": "ik_smart"
                    },
                    "name": {
                        "type": "text",
                        "analyzer": "ik_max_word",
                        "search_analyzer": "ik_smart"
                    },
                    "pic":{
                        "type":"text",
                        "index":false
                    },
                    "price": {
                        "type": "float"
                    },
                    "studymodel": {
                        "type": "keyword"
                    },
                    "timestamp": {
                        "type": "date",
                        "format": "yyyy-MM-dd HH:mm:ss||yyyy-MM-dd||epoch_millis"
                    }
                }
            }

這裏特別註意: 使用了比例因子浮點數 ,索引庫創建成功之後,在head客戶端,數據瀏覽的字段結構中沒有展示,但是實際數據中是存在的,已經成功了

3、文檔管理測試

package com.xuecheng.search.test;

import java.io.FileInputStream;
import java.io.InputStream;
import java.util.HashMap;
import java.util.Map;

import org.apache.commons.io.IOUtils;
import org.elasticsearch.action.delete.DeleteRequest;
import org.elasticsearch.action.delete.DeleteResponse;
import org.elasticsearch.action.get.GetRequest;
import org.elasticsearch.action.get.GetResponse;
import org.elasticsearch.action.index.IndexRequest;
import org.elasticsearch.action.index.IndexResponse;
import org.elasticsearch.action.update.UpdateRequest;
import org.elasticsearch.action.update.UpdateResponse;
import org.elasticsearch.client.RestHighLevelClient;
import org.elasticsearch.common.xcontent.XContentType;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;

@SpringBootTest
@RunWith(SpringRunner.class)
public class TestDocument {

    @Autowired
    private RestHighLevelClient client;
    
    //添加文檔
    @Test
    public void testAddDoc() throws Exception{
        
        //加載準備好了的json數據
        InputStream is = new FileInputStream(this.getClass().getResource("/").getPath()+"document.json");
        String docJsonStr = IOUtils.toString(is);
        System.err.println(docJsonStr);
        //獲取索引庫對象
        IndexRequest indexRequest = new IndexRequest("course","doc"); //特別註意doc不要掉、否則報錯org.elasticsearch.action.ActionRequestValidationException: Validation Failed: 1: type is missing;
        indexRequest.source(docJsonStr, XContentType.JSON);
        //往索引庫添加文檔,這個動作也叫索引
        IndexResponse indexResponse = client.index(indexRequest);
        //打印結果
        System.out.println(indexResponse.getResult());
    }
    
    /**
     * 查詢文檔(根據id查)
     * 結果
     * {
     *   "description":"Bootstrap是由Twitter推出的一個前臺頁面開發框架,在行業之中使用較為廣泛。
     *                 此開發框架包 含了大量的CSS、JS程序代碼,可以幫助開發者(尤其是不擅長頁面開發的程序人員)
     *                 輕松的實現一個不受瀏覽器限制的 精美界面效果。",
     *   "name":"Bootstrap開發框架",
     *   "studymodel":"201001",
     *   "price":62.658
     * }
     */
    
    @Test
    public void testGetDoc()throws Exception{
        
        GetRequest getRequest = new GetRequest("course",
                                               "doc",
                                               "TOFP1mcBf3IfcTiHcsXB");
        GetResponse getResponse = client.get(getRequest);
        if(getResponse.isExists()){
            String sourceAsString = getResponse.getSourceAsString();
            System.out.println(sourceAsString);
        }
    }
    
    /**
     * 更新文檔
     * 打印結果: OK
     * 註意這裏采用的是局部更新:只修改map中設置的字段,沒有的不會更新。
     * 更新文檔的實際順序是: 檢索文檔、標記刪除、創建新文檔、刪除原文檔
     * 創建新文檔就會重構索引(分詞-重構倒排索引樹)
     * 
     */
    @Test
    public void testUpdateDoc()throws Exception{
        UpdateRequest updateRequest = new UpdateRequest("course",
                          "doc",
                          "TOFP1mcBf3IfcTiHcsXB");
        Map<String, String> map = new HashMap<String,String>();
        map.put("name", "Bootstrap框架");
        updateRequest.doc(map);
        UpdateResponse updateResponse = client.update(updateRequest);
        System.out.println(updateResponse.status());
    }
    
    /**
     * 刪除文檔
     * 打印結果:DELETED
     */
    @Test
    public void testDelDoc() throws Exception{
        
        DeleteRequest deleteRequest = new DeleteRequest("course",
                                                        "doc",
                                                        "TOFP1mcBf3IfcTiHcsXB");
        DeleteResponse deleteResponse = client.delete(deleteRequest);
        System.out.println(deleteResponse.getResult());
    }

}

4、搜索管理測試

準備數據

初始化文檔:
{
"name": "Bootstrap開發",
"description": "Bootstrap是由Twitter推出的一個前臺頁面開發框架,是一個非常流行的開發框架,此框架集成了多種頁面效果。此開發框架包含了大量的CSS、JS程序代碼,可以幫助開發者(尤其是不擅長頁面開發的程序人員)輕松的實現一個不受瀏覽器限制的精美界面效果。",
"studymodel": "201002",
"price":38.6,
"timestamp":"2018-04-25 19:11:35",
"pic":"group1/M00/00/00/wKhlQFs6RCeAY0pHAAJx5ZjNDEM428.jpg"
}

{
"name": "java編程基礎",
"description": "java語言是世界第一編程語言,在軟件開發領域使用人數最多。",
"studymodel": "201001",
"price":68.6,
"timestamp":"2018-03-25 19:11:35",
"pic":"group1/M00/00/00/wKhlQFs6RCeAY0pHAAJx5ZjNDEM428.jpg"
}

{
"name": "spring開發基礎",
"description": "spring 在java領域非常流行,java程序員都在用。",
"studymodel": "201001",
"price":88.6,
"timestamp":"2018-02-24 19:11:35",
"pic":"group1/M00/00/00/wKhlQFs6RCeAY0pHAAJx5ZjNDEM428.jpg"
}

測試

package com.xuecheng.search.test;

import org.elasticsearch.action.search.SearchRequest;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.client.RestClient;
import org.elasticsearch.client.RestHighLevelClient;
import org.elasticsearch.index.query.BoolQueryBuilder;
import org.elasticsearch.index.query.MatchQueryBuilder;
import org.elasticsearch.index.query.MultiMatchQueryBuilder;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.index.query.TermQueryBuilder;
import org.elasticsearch.index.query.TermsQueryBuilder;
import org.elasticsearch.search.SearchHit;
import org.elasticsearch.search.SearchHits;
import org.elasticsearch.search.builder.SearchSourceBuilder;
import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder;
import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder.Field;
import org.elasticsearch.search.sort.FieldSortBuilder;
import org.elasticsearch.search.sort.SortOrder;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;

@SpringBootTest
@RunWith(SpringRunner.class)
public class TeseSearch {

    @Autowired
    RestHighLevelClient client;
    
    @Autowired
    RestClient restClient;
    
    
    /**
     * 查詢type下所有文檔
     * 打印結果:
     *  {"studymodel":"201002","name":"Bootstrap開發"}
        {"studymodel":"201001","name":"java編程基礎"}
        {"studymodel":"201001","name":"spring開發基礎"}
    
       對應http請求json
       {
         "query": {
           "match_all": {}
         },
         "_source": ["name","studymodel"]
       }
           
     */
    @Test
    public void testSearchAll()throws Exception{
        
        
        //1、構造sourceBuild(source源)
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        searchSourceBuilder.fetchSource(new String[]{"name","studymodel"}, new String[]{})
                           .query(QueryBuilders.matchAllQuery());
        //2、構造查詢請求對象
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc")
                     .source(searchSourceBuilder);
        //3、client 執行查詢
        SearchResponse searchResponse = client.search(searchRequest);
        
        //4、打印結果
        SearchHits hits = searchResponse.getHits();
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    
    /**
     * 分頁查詢type下所有文檔
     * 
     * json 參數
     * {
     *   "from":0,
     *   "size":1,
     *   "query": {
     *      "match_all": {}
     *   },
     *   "_source": ["name","studymodel"]
     * }
     * 
     * 打印結果
     * {"studymodel":"201002","name":"Bootstrap開發"}
       {"studymodel":"201001","name":"java編程基礎"}
     */
    @Test
    public void testSearchAllByPage()throws Exception{
        
        //1、構造sourceBuild
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        searchSourceBuilder.fetchSource(new String[]{"name","studymodel"}, new String[]{})
                           .query(QueryBuilders.matchAllQuery())
                           .from(0).size(2);//分頁查詢,下表從0開始
        
        //2、構造searchRequest請求對象
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc")
                     .source(searchSourceBuilder);
        //3、client執行請求
        SearchResponse searchResponse = client.search(searchRequest);
        
        //4、打印結果
        SearchHits hits = searchResponse.getHits();
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    /**
     * term query: 精確查詢、在搜索是會精確匹配關鍵字、搜索關鍵字不分詞
     * 
     * json 參數
     * {
     *   
     *   "query": {
     *      "term": {
     *          name: "spring"
     *      }
     *   },
     *   "_source": ["name","studymodel"]
     * }
     */
    @Test
    public void testTermQuery()throws Exception{
        
        //1、設置queryBuilder
        TermQueryBuilder termQueryBuild = QueryBuilders.termQuery("name","spring");
        
        //2、設置sourceBuilder
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        searchSourceBuilder.query(termQueryBuild)//設置Term query查詢
                           .fetchSource(new String[]{"name","studymodel"}, new String[]{});
        
        //3、構造searchRequest
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc")
                     .source(searchSourceBuilder);
        //4、client發出請求
        SearchResponse searchResponse = client.search(searchRequest);
        
        //5、打印結果
        SearchHits hits = searchResponse.getHits();
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    
    /**
     * 根據id精確查詢:根據提供的多個id去匹配
     * 
     * json 參數
     * {
     *   query{
             "ids": {
                "type": "doc",
                "values": ["TeH_2WcBH5cUK","TuEB2mcBf3IfcTiHccWJ"]
             }
     *   },
     *   "_source": ["name","studymodel"]
     * }
     */
    @Test
    public void testIdsQuery()throws Exception{
        
        //1、夠著queryBuild
        //構造idList,註意數組每個元素必須是一個完整的id能匹配的上,第一條沒有記錄匹配上,第二條中
        String[] idList = new String[]{"TeH_2WcBH5cUK","TuEB2mcBf3IfcTiHccWJ"};
        TermsQueryBuilder termsQueryBuilder = QueryBuilders.termsQuery("_id",idList);//特別註意用termsQuery,不要用termQuery
        
        //2、構造sourceBuilder
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        searchSourceBuilder.query(termsQueryBuilder)
                           .fetchSource(new String[]{"name","studymodel"}, new String[]{});;
        
        //3、構造searchRequest
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc")
                     .source(searchSourceBuilder);
        //4、client執行
        SearchResponse searchResponse = client.search(searchRequest);
        SearchHits hits = searchResponse.getHits();
        
        //5、打印結果
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    
    /**
     * match Query就是全文檢索,收縮方式就是先將搜索字符串分詞、然後到索引分詞列表去匹配
     * json 參數
     * {
     *   query{
     *     "match": {
     *         "descrition":{  //還是需要指定字段的,description是字段名
     *                 "query": "世界第一",
     *              "operate": "or"  //or表示分詞之後,只要有一個匹配即可,and表示分詞在文檔中都匹配才行
     *         }
     *      },
     *      "_source": ["name","studymodel"]
     *   }
     * }
     */
    @Test
    public void testmatchQuery()throws Exception{
        
        //queryBuild
        MatchQueryBuilder matchQueryBuilder = QueryBuilders.matchQuery("description", "世界第一");
        
        //searchSorcebuilder
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        searchSourceBuilder.query(matchQueryBuilder)
                           .fetchSource(new String[]{"name","studymodel"}, new String[]{});
        
        
        //searchRequest
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc")
                     .source(searchSourceBuilder);
        //client->search
        SearchResponse searchResponse = client.search(searchRequest);
        SearchHits hits = searchResponse.getHits();
        //print end
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    /**
     * minimum_should_match:
     *   or只能表示只要匹配一個即可、minimum_should_match可以指定文檔匹配詞的占比,註意這個占比的基數是搜索字符串分詞的個數
     * json 參數
     * {
     *   query{
     *     "match": {
     *         "descrition":{  //還是需要指定字段的,description是字段名
     *                 "query": "spring開發",
     *              "minimun_should_match": "80%"
     *         }
     *      },
     *      "_source": ["name","studymodel"]
     *   }
     * }
     */
    @Test
    public void testMinimumShouldMatchQuery()throws Exception{
        
        //queryBuild
        MatchQueryBuilder matchQueryBuilder = QueryBuilders.matchQuery("description", "世界第一")
                     .minimumShouldMatch("80%");
        
        
        //searchSourceBuilder
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        searchSourceBuilder.query(matchQueryBuilder)
                           .fetchSource(new String[]{"name","studymodel"}, new String[]{});
        
        //searchRequest
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc")
                     .source(searchSourceBuilder);
        
        SearchResponse searchResponse = client.search(searchRequest);
        SearchHits hits = searchResponse.getHits();
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    /**
     * multi_match Query:
     *   用於一次匹配多個File進行全文檢索、前面match都是一個Field
     *   多個字段可以通過提升boost(權重),來提高得分,實現排序靠前
     *   
     * json 參數
     * {
     *   query{
     *     "multi_match": {
     *         "query": "spring css", //搜索字符串
     *         "minimum_should_match": "50%",
     *         "fields": ["name^10","description"] //設置匹配name 和 description字段,將boost的boost提10倍
     *      }
     *   }
     * }
     */
    @Test
    public void testMultiMatchQuery()throws Exception{
        
        
        //queryBuilder
        MultiMatchQueryBuilder matchQueryBuilder = QueryBuilders.multiMatchQuery("Spring框架","name","description")
                                                                .minimumShouldMatch("50%")//設置百分比
                                                                .field("name", 10);//提升boost
        //searchSourceBuild
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        searchSourceBuilder.query(matchQueryBuilder); 
        
        //searchRequest
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc")
                     .source(searchSourceBuilder);
        //search
        SearchResponse searchResponse = client.search(searchRequest);
        SearchHits hits = searchResponse.getHits();
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    /**
     * 布爾查詢
     *   對應lucene的Boolean查詢、實現將多個查詢條件結合起來
     *   三個參數:
     *      must:只有符合所有查詢的文檔才被查詢出來,相當於AND
     *      should:至少符合其中一個,相當於OR
     *      must_not:不能符合任意查詢條件,相當於NOT
     *      
     * json 參數
     * {
     *   "_source": ["name","pic"],
     *   "from": 0,
     *   "size": 1,
     *   query{
     *     bool:{
     *      must: [
     *         {
     *           "multi_match": {
     *             "query": "spring框架",
     *             "minimum_should_match": "50%",
     *             "fields": ["name^10","description"]
     *           }
     *         },{
     *           "term": {
     *             "studymodel": "201001"
     *           }
     *         }
     *      ]
     *    }  
     *   }
     * }
     */
    @Test
    public void testBooleanQuery()throws Exception{
        
        //1、夠著QueryBuild
        
        //構造multiQureyBuilder
        MultiMatchQueryBuilder multiQueryBuilder = QueryBuilders.multiMatchQuery("Spring框架","name","description")
                                                                .minimumShouldMatch("50%")//設置百分比
                                                                .field("name", 10);
         //構造termQueryBuilder
        TermQueryBuilder termQueryBuilder = QueryBuilders.termQuery("studymodel", "201001");
        
        //構造booleanQueryBuilder
        BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery()
                     .must(multiQueryBuilder)
                     .must(termQueryBuilder);
        
        //2、構造查詢源
        SearchSourceBuilder ssb = new SearchSourceBuilder();
        ssb.fetchSource(new String[]{"name","pic"}, new String[]{});
        ssb.query(boolQueryBuilder);
        
        //3、構造請求對象查詢
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc");
        searchRequest.source(ssb);
        
        //4、client執行查詢
        SearchResponse searchResponse = client.search(searchRequest);
        SearchHits hits = searchResponse.getHits();
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    
    /**
     * 過濾器:
     *   過濾器判斷的是文檔是否匹配,不去計算和判斷文檔的匹配度得分,所以過濾器性能比查詢高、方便緩存
     *   推薦盡量使用過濾器、或則過濾器搭配查詢使用
     *   過濾器使用的前提是bool查詢
     *   過濾器可以單獨使用,但是不能提點multi Query, 因為過濾器每個Query都是單字段過濾
     *      
     * json 參數
     * {
     *   "_source": ["name","pic"],
     *   "from": 0,
     *   "size": 1,
     *   query{
     *     bool:{
     *      must: [
     *         {
     *           "multi_match": {
     *             "query": "spring框架",
     *             "minimum_should_match": "50%",
     *             "fields": ["name^10","description"]
     *           }
     *         }
     *      ],
     *      fileter: [
     *         {
     *            term: {"studymodel": "21001"} //針對字段進行過濾
     *         },{
     *            range: {  //針對範圍進行過濾
     *              "price": {"gte":60,"lte":100}
     *            }
     *         }
     *      ]
     *    }  
     *   }
     * }
     */
    @Test
    public void testFileter()throws Exception{
        
        //1、構造QueryBuild
        
        //構造multiQureyBuilder
        MultiMatchQueryBuilder multiQueryBuilder = QueryBuilders.multiMatchQuery("Spring框架","name","description")
                                                                .minimumShouldMatch("50%")//設置百分比
                                                                .field("name", 10);
        
        //構造booleanQueryBuilder
        BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery()
                     .must(multiQueryBuilder);
        
        //過濾
        boolQueryBuilder.filter(QueryBuilders.termQuery("studymodel", "201001"))
                        .filter(QueryBuilders.rangeQuery("price").gte(60).lte(100));
        
        //2、構造查詢源
        SearchSourceBuilder ssb = new SearchSourceBuilder();
        ssb.fetchSource(new String[]{"name","pic"}, new String[]{});
        ssb.query(boolQueryBuilder);
        
        //3、構造請求對象查詢
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc");
        searchRequest.source(ssb);
        
        //4、client執行查詢
        SearchResponse searchResponse = client.search(searchRequest);
        SearchHits hits = searchResponse.getHits();
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    
    /**
     * 排序:
     * 可以設置排序字段對查詢結果進行排序
     * keyword 、date 、float 等可以加
     * 註意text 不能加
     *      
     * json 參數
     * {
     *   "_source": ["name","pic","description","price],
     *   query{
     *     bool:{
     *      fileter: [ //過濾器也可以單獨使用,但是只能用於單個字段
     *         {
     *            term: {"studymodel": "21001"} //針對字段進行過濾
     *         },{
     *            range: {  //針對範圍進行過濾
     *              "price": {"gte":60,"lte":100}
     *            }
     *         }
     *      ]
     *    }  
     *   },
     *   "sort": [
     *     {
     *       "studymodel": "desc"
     *     },{
     *       "price": "asc"
     *     }
     *   ]
     * }
     */
    @Test
    public void testSort()throws Exception{
        
        //1、構造QueryBuild
        
        //構造booleanQueryBuilder
        BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery();
        
        //過濾
        boolQueryBuilder.filter(QueryBuilders.termQuery("studymodel", "201001"))
                        .filter(QueryBuilders.rangeQuery("price").gte(60).lte(100));
        
        //2、構造查詢源
        SearchSourceBuilder ssb = new SearchSourceBuilder();
        ssb.fetchSource(new String[]{"name","pic","studymodel","price"}, new String[]{});
        ssb.query(boolQueryBuilder);
        ssb.sort(new FieldSortBuilder("studymodel").order(SortOrder.DESC));
        ssb.sort(new FieldSortBuilder("price").order(SortOrder.ASC));
        
        //3、構造請求對象查詢
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc");
        searchRequest.source(ssb);
        
        //4、client執行查詢
        SearchResponse searchResponse = client.search(searchRequest);
        SearchHits hits = searchResponse.getHits();
        for(SearchHit hit:hits){
            System.out.println(hit.getSourceAsString());
        }
    }
    
    
    /**
     * 高亮顯示:
     * 將搜索結果中的一個或多個字突出顯示,以便向用戶展示匹配的關鍵字的位置
     *      
     * json 參數
     */
    @Test
    public void testHighlight()throws Exception{
        
        //1、構造QueryBuild
        
        MultiMatchQueryBuilder multiQueryBuilder = QueryBuilders.multiMatchQuery("開發框架", "name","description")
                     .field("name", 10)
                     .minimumShouldMatch("50%");
        
        //構造booleanQueryBuilder
        BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery()
                                                         .must(multiQueryBuilder);
        
        //過濾
        boolQueryBuilder.filter(QueryBuilders.termQuery("studymodel", "201001"))
                        .filter(QueryBuilders.rangeQuery("price").gte(60).lte(100));
        
        //2、設置高亮
        //設置標簽        
        HighlightBuilder highlightBuilder = new HighlightBuilder();
        highlightBuilder.preTags("<tag>")//設置簽綴
                        .postTags("</tag>");//設置後綴
        //設置高亮字段
        highlightBuilder.fields().add(new Field("name"));
        highlightBuilder.fields().add(new Field("description"));
        
        
        //3、構造查詢源
          SearchSourceBuilder ssb = new SearchSourceBuilder();
          ssb.fetchSource(new String[]{"name","pic","studymodel","price"}, new String[]{})
             .query(boolQueryBuilder)
             .sort(new FieldSortBuilder("studymodel").order(SortOrder.DESC))
             .sort(new FieldSortBuilder("price").order(SortOrder.ASC))
           .highlighter(highlightBuilder);
          
        //4、構造請求對象查詢
        SearchRequest searchRequest = new SearchRequest("xc_course");
        searchRequest.types("doc")
                     .source(ssb);
        
        //5、client執行查詢
        SearchResponse searchResponse = client.search(searchRequest);
        //6、取出高亮字段
        SearchHits hits = searchResponse.getHits();
        for(SearchHit hit:hits){
            System.out.println(hit.getHighlightFields());
        }
    }
    
    
    
    
    
}

elasticsearch-java客戶端測試