中文字幕av专区_日韩电影在线播放_精品国产精品久久一区免费式_av在线免费观看网站

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

如何解決ES深度分頁問題

發布時間:2021-10-12 11:19:58 來源:億速云 閱讀:867 作者:iii 欄目:編程語言

這篇文章主要介紹“如何解決ES深度分頁問題”,在日常操作中,相信很多人在如何解決ES深度分頁問題問題上存在疑惑,小編查閱了各式資料,整理出簡單好用的操作方法,希望對大家解答”如何解決ES深度分頁問題”的疑惑有所幫助!接下來,請跟著小編一起來學習吧!

ES深度分頁問題:

ES 默認采用的分頁方式是 from+ size 的形式,類似于MySQL的分頁offset+limit。當請求數據量比較大時,Elasticsearch會對分頁做出限制,因為此時性能消耗會很大。例如查詢1000條數據,假設我們有5個分片,那么每個shard都需要返回1000條數據給 coordinating node,而 coordinating node 需要接收 5*1000 條數據,進行排序后返回1000條數據給客戶端。即使每條數據只有 _doc _id 和 _score,這數據量也很大了,如果請請求量很大的情況下,很容易造成ES的OOM。ES中有個設置index.max_result_window ,默認是10000條數據,如果分頁的數據超過第1萬條,就拒絕返回結果了。如果集群配置比較好,查詢請求量不是特別大,可以適當的放大這個參數。

解決方案:

1:使用scroll遍歷

scroll 分為初始化和遍歷兩步,初始化時將所有符合搜索條件的搜索結果緩存起來,可以想象成快照,在遍歷時,從這個快照里取數據,也就是說,在初始化后對索引插入、刪除、更新數據都不會影響遍歷結果。因此,scroll 并不適合用來做實時搜索,而更適用于后臺批處理任務等

API說明:

1)初始化

POST /book/_search?scroll=1m&size=2
{
"query": { "match_all": {}}
}
  1. 遍歷

GET /_search/scroll
{
"scroll": "1m",
"scroll_id" : "步驟1中查詢出來的值"
}

使用java RestHighLevelClient代碼參考如下:

@Autowired
private RestHighLevelClient restHighLevelClient;

public Result<GoodsDTo>  scrollSearch(...查詢參數){
     BoolQueryBuilder queryBuilder.te = QueryBuilders.boolQuery();
     //添加自己的搜索條件....
     queryBuilder.must(QueryBuilders.termQuery("type", "商品所屬分類);
     queryBuilder.must(QueryBuilders.matchQuery("name", "商品名稱");
     //搜索
     SearchSourceBuilder searchSourceBuilder = SearchSourceBuilder.searchSource();
     searchSourceBuilder.query(queryBuilder);
     //排序
     searchSourceBuilder.sort(SortBuilders.fieldSort("order").order(SortOrder.DESC));
     //搜索結果
     SearchResponse searchResponse = null;
     //根據實際情況,判斷是多次調用還是一次while遍歷查詢全部
  	if (StringUtils.isBlank("scrollId")) {
            //首屏
            searchSourceBuilder.size("每次查詢的條數");
            SearchRequest searchRequest = new SearchRequest();
            searchRequest.indices("索引名").source(searchSourceBuilder);
            searchRequest.scroll(new Scroll(TimeValue.timeValueMinutes(scrollKeepAliveTime)));
            searchResponse = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT);
     } else {
            //后續根據上次的id滾動
            SearchScrollRequest searchScrollRequest = new SearchScrollRequest("scrollId");
            searchScrollRequest.scroll(new Scroll(TimeValue.timeValueMinutes(scrollKeepAliveTime)));
            searchResponse = restHighLevelClient.scroll(searchScrollRequest, RequestOptions.DEFAULT);
     }
        
     SearchHit[] hits = searchResponse.getHits().getHits();
     //根據業務需求,處理搜索結果
     GoodsDTO result= handleSearchData(hits);
     //scrollId,往下滾動需要使用
     String scrollId = searchResponse.getScrollId();
     return Result.succcess(result);
}

2:使用search after

滿足實時獲取下一頁的文檔信息,search_after 分頁的方式是根據上一頁的最后一條數據來確定下一頁的位置,同時在分頁請求的過程中,如果有索引數據的增刪改,這些變更也會實時的反映到游標上,這種方式是在es-5.X之后才提供的。為了找到每一頁最后一條數據,每個文檔的排序字段必須有一個全局唯一值使用 _id 就可以了。

API說明:

GET /book/_search
{
    "query": {"match_all": {}},
    "size": 2,
    "sort": [{"_id": "desc"}]
}
GET /book/_search
{
    "query": {"match_all": {}},
    "size": 2,
    "search_after": [3],
    "sort": [{"_id": "desc"}]
}

下一頁的數據依賴上一頁的最后一條的信息 所以不能跳頁

使用java RestHighLevelClient代碼參考如下:

@Autowired
private RestHighLevelClient restHighLevelClient;

public Result<GoodsDTo>  searchAfter(...查詢參數){
        SearchRequest searchRequest = new SearchRequest(index);
        SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
        searchSourceBuilder.query(...搜索條件);
        searchSourceBuilder.size(1000);
        searchSourceBuilder.sort("_id", SortOrder.ASC);
        searchSourceBuilder.searchAfter("上一頁最后一條數據的id");
        searchRequest.source(searchSourceBuilder);
        SearchResponse searchResponse = client.search(searchRequest, RequestOptions.DEFAULT);
        SearchHit[] hits = searchResponse.getHits().getHits();
         //根據業務需求,處理搜索結果
         GoodsDTO result= handleSearchData(hits);
         return Result.succcess(result);
}

到此,關于“如何解決ES深度分頁問題”的學習就結束了,希望能夠解決大家的疑惑。理論與實踐的搭配能更好的幫助大家學習,快去試試吧!若想繼續學習更多相關知識,請繼續關注億速云網站,小編會繼續努力為大家帶來更多實用的文章!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

罗平县| 钦州市| 甘孜| 呼和浩特市| 郯城县| 松滋市| 舞阳县| 宁津县| 黄石市| 松原市| 万山特区| 民勤县| 永顺县| 闽侯县| 望谟县| 宜章县| 驻马店市| 兰西县| 云阳县| 正蓝旗| 郓城县| 东莞市| 江油市| 修文县| 合山市| 潢川县| 常德市| 韶关市| 西峡县| 济阳县| 武平县| 正镶白旗| 喀什市| 酒泉市| 襄城县| 桦南县| 古交市| 六枝特区| 广饶县| 西青区| 汝阳县|