Java High Level Rest Client---查询文档

查询文档的基本步骤

  • 1)准备Request对象
  • 2)准备请求参数
  • 3)发起请求
  • 4)解析响应

示例解析
以match_all查询为例

代码解读:

  • 第一步,创建SearchRequest对象,指定索引库名
  • 第二步,利用request.source()构建DSL,DSL中可以包含查询、分页、排序、高亮等
    • query():代表查询条件,利用QueryBuilders.matchAllQuery()构建一个match_all查询的DSL
  • 第三步,利用client.search()发送请求,得到响应
    这里关键的API有两个,一个是request.source(),其中包含了查询、排序、分页、高亮等所有功能:

另一个是QueryBuilders,其中包含match、term、function_score、bool等各种查询:

解析响应

elasticsearch返回的结果是一个JSON字符串,结构包含:

  • hits:命中的结果
    • total:总条数,其中的value是具体的总条数值
    • max_score:所有结果中得分最高的文档的相关性算分
    • hits:搜索结果的文档数组,其中的每个文档都是一个json对象
      • _source:文档中的原始数据,也是json对象

因此,我们解析响应结果,就是逐层解析JSON字符串,流程如下:

  • SearchHits:通过response.getHits()获取,就是JSON中的最外层的hits,代表命中的结果
    • SearchHits#getTotalHits().value:获取总条数信息
    • SearchHits#getHits():获取SearchHit数组,也就是文档数组
      • SearchHit#getSourceAsString():获取文档结果中的_source,也就是原始的json文档数据

小结
查询的基本步骤是:

  1. 创建SearchRequest对象
  2. 准备Request.source(),也就是DSL。
    ① QueryBuilders来构建查询条件
    ② 传入Request.source() 的 query() 方法
  3. 发送请求,得到结果
  4. 解析结果(参考JSON结果,从外到内,逐层解析)

代码示例
查询全部

点击查看代码
//查询全部
    @Test
    public void getAll() throws Exception{
        // 1.准备Request
        SearchRequest request = new SearchRequest("hotel");
        // 2.准备DSL
        request.source()
                .query(QueryBuilders.matchAllQuery());
        // 3.发送请求
        SearchResponse response = client.search(request, RequestOptions.DEFAULT);
        //处理结果
        SearchHits responseHits = response.getHits();
        long hitsTotalHits = responseHits.getTotalHits().value;//获取总条数
        System.out.println("共获取数据"+hitsTotalHits+"条");
        SearchHit[] hits = responseHits.getHits();//文档数组
        //遍历文档数组
        for (int i = 0; i < hits.length; i++) {
            //获取文档的source
            String json = hits[i].getSourceAsString();
            //反序列化
            HotelDoc hotelDoc = JSON.parseObject(json, HotelDoc.class);
            System.out.println("hotelDoc--->"+hotelDoc);
        }
    }

match查询

点击查看代码
//match查询
    @Test
    public void match() throws Exception{
        //准备request
        SearchRequest request = new SearchRequest("hotel");
        // 准备dsl语句
        request.source().query(QueryBuilders.matchQuery("all","希尔顿"));
        //发送请求
        SearchResponse response = client.search(request, RequestOptions.DEFAULT);
        // 解析响应
        SearchHits responseHits = response.getHits();
        long total = responseHits.getTotalHits().value;//获取总条数
        System.out.println("共获取数据"+total+"条");
        SearchHit[] hits = responseHits.getHits();//文档数组
        for (int i = 0; i < hits.length; i++) {
            //获取文档的source
            String json = hits[i].getSourceAsString();
            //反序列化
            HotelDoc hotelDoc = JSON.parseObject(json, HotelDoc.class);
            System.out.println("hotelDoc--->"+hotelDoc);
        }
    }

精确查询

点击查看代码
@Test
    public void term() throws Exception{
        //准备request对象
        SearchRequest request = new SearchRequest("hotel");
        //准备dsl语句
        request.source().query(QueryBuilders.termQuery("city","北京"));
        //发送请求
        SearchResponse response = client.search(request, RequestOptions.DEFAULT);
        //解析数据
        SearchHits responseHits = response.getHits();
        long total = responseHits.getTotalHits().value;//获取总条数
        System.out.println("共获取数据"+total+"条");
        SearchHit[] hits = responseHits.getHits();//文档数组
        for (int i = 0; i < hits.length; i++) {
            //获取文档的source
            String json = hits[i].getSourceAsString();
            //反序列化
            HotelDoc hotelDoc = JSON.parseObject(json, HotelDoc.class);
            System.out.println("hotelDoc--->"+hotelDoc);
        }
    }

范围查询

点击查看代码
//范围查询
@Test
    public void range() throws Exception{
        //准备request对象
        SearchRequest request = new SearchRequest("hotel");
        //准备dsl语句
        request.source().query(QueryBuilders.rangeQuery("price").gte(100).lte(150));
        //发送请求
        SearchResponse response = client.search(request, RequestOptions.DEFAULT);
        //解析数据
        SearchHits responseHits = response.getHits();
        long total = responseHits.getTotalHits().value;//获取总条数
        System.out.println("共获取数据"+total+"条");
        SearchHit[] hits = responseHits.getHits();//文档数组
        for (int i = 0; i < hits.length; i++) {
            //获取文档的source
            String json = hits[i].getSourceAsString();
            //反序列化
            HotelDoc hotelDoc = JSON.parseObject(json, HotelDoc.class);
            System.out.println("hotelDoc--->"+hotelDoc);
        }
    }

布尔查询

点击查看代码
//布尔查询
    @Test
    public void bool() throws Exception{
        //准备request对象
        SearchRequest request = new SearchRequest("hotel");
        //准备dsl语句
        //准备BooleanQuery
        BoolQueryBuilder boolQuery = QueryBuilders.boolQuery();
        //添加term条件,城市必须在上海
        boolQuery.must(QueryBuilders.termQuery("city","上海"));
        //添加range条件,过滤掉价格在200元以上的
        boolQuery.filter(QueryBuilders.rangeQuery("price").lte(200));
        request.source().query(boolQuery);
        //发送请求
        SearchResponse response = client.search(request, RequestOptions.DEFAULT);
        //解析数据
        SearchHits responseHits = response.getHits();
        long total = responseHits.getTotalHits().value;//获取总条数
        System.out.println("共获取数据"+total+"条");
        SearchHit[] hits = responseHits.getHits();//文档数组
        for (int i = 0; i < hits.length; i++) {
            //获取文档的source
            String json = hits[i].getSourceAsString();
            //反序列化
            HotelDoc hotelDoc = JSON.parseObject(json, HotelDoc.class);
            System.out.println("hotelDoc--->"+hotelDoc);
        }
    }

排序,分页查询

点击查看代码
//排序,分页查询
    @Test
    public void sortAndPage() throws Exception{
        // 页码,每页大小
        int page = 1, size = 5;
        //准备request对象
        SearchRequest request = new SearchRequest("hotel");
        //准备dsl语句
        request.source().query(QueryBuilders.matchAllQuery());//查询
        request.source().from((page - 1) * size).size(size);//分页
        request.source().sort("price", SortOrder.ASC);//价格升序
        //发送请求
        SearchResponse response = client.search(request, RequestOptions.DEFAULT);
        //解析数据
        SearchHits responseHits = response.getHits();
        long total = responseHits.getTotalHits().value;//获取总条数
        System.out.println("共获取数据"+total+"条");
        SearchHit[] hits = responseHits.getHits();//文档数组
        for (int i = 0; i < hits.length; i++) {
            //获取文档的source
            String json = hits[i].getSourceAsString();
            //反序列化
            HotelDoc hotelDoc = JSON.parseObject(json, HotelDoc.class);
            System.out.println("hotelDoc--->"+hotelDoc);
        }
    }

高亮处理

点击查看代码
//高亮处理
    @Test
    public void highlight() throws Exception{
        // 1.准备Request
        SearchRequest request = new SearchRequest("hotel");
        // 2.准备DSL
        // 2.1.query
        request.source().query(QueryBuilders.matchQuery("all", "如家"));
        // 2.2.高亮
        request.source().highlighter(new HighlightBuilder().field("name").requireFieldMatch(false));
        // 3.发送请求
        SearchResponse response = client.search(request, RequestOptions.DEFAULT);
        // 4.解析响应
        // 4.解析响应
        SearchHits searchHits = response.getHits();
        // 4.1.获取总条数
        long total = searchHits.getTotalHits().value;
        System.out.println("共搜索到" + total + "条数据");
        // 4.2.文档数组
        SearchHit[] hits = searchHits.getHits();
        // 4.3.遍历
        for (SearchHit hit : hits) {
            // 获取文档source
            String json = hit.getSourceAsString();
            // 反序列化
            HotelDoc hotelDoc = JSON.parseObject(json, HotelDoc.class);
            // 获取高亮结果
            Map<String, HighlightField> highlightFields = hit.getHighlightFields();
            if (!CollectionUtils.isEmpty(highlightFields)) {
                // 根据字段名获取高亮结果
                HighlightField highlightField = highlightFields.get("name");
                if (highlightField != null) {
                    // 获取高亮值
                    String name = highlightField.getFragments()[0].string();
                    // 覆盖非高亮结果
                    hotelDoc.setName(name);
                }
            }
            System.out.println("hotelDoc --->" + hotelDoc);
        }
    }

坐标查询

点击查看代码
//根据坐标查询
    @Test
    public void geoDistance() throws Exception{
        String location="31.21,121.5";
        //准备request对象
        SearchRequest request = new SearchRequest("hotel");
        //准备dsl语句
        request.source().sort(SortBuilders
                .geoDistanceSort("location",new GeoPoint(location))
                .order(SortOrder.ASC)
                .unit(DistanceUnit.KILOMETERS)
        );
        //发送请求
        SearchResponse response = client.search(request, RequestOptions.DEFAULT);
        //解析数据
        SearchHits responseHits = response.getHits();
        long total = responseHits.getTotalHits().value;//获取总条数
        System.out.println("共获取数据"+total+"条");
        SearchHit[] hits = responseHits.getHits();//文档数组
        for (int i = 0; i < hits.length; i++) {
            //获取文档的source
            String json = hits[i].getSourceAsString();
            //反序列化
            HotelDoc hotelDoc = JSON.parseObject(json, HotelDoc.class);
            System.out.println("hotelDoc--->"+hotelDoc);
            //获取距离值
            Object[] sortValues = hits[i].getSortValues();
            System.out.println("距离坐标距离--->"+sortValues[0]+"km");
        }
    }
posted @   wzh_Official  阅读(129)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· C#/.NET/.NET Core技术前沿周刊 | 第 29 期(2025年3.1-3.9)
· 从HTTP原因短语缺失研究HTTP/2和HTTP/3的设计差异
点击右上角即可分享
微信分享提示