赞
踩
SearchSourceBuilder sourceBuilder = new SearchSourceBuilder();
sourceBuilder.query(
QueryBuilders.termQuery(“context”, “身份证”)
);
searchRequest.source(sourceBuilder);
searchRequest.scroll(TimeValue.timeValueMinutes(1));
SearchResponse result = client.search(searchRequest, RequestOptions.DEFAULT);
scrollId = result.getScrollId();
// step 1 end
// step 2 start
if(!StringUtils.isEmpty(scrollId)) {
System.out.println("step 2 start ");
SearchScrollRequest scrollRequest = new SearchScrollRequest(scrollId);
scrollRequest.scroll(TimeValue.timeValueMinutes(1));
while(true) { //循环遍历
SearchResponse scollResponse = client.scroll(scrollRequest, RequestOptions.DEFAULT);
if(scollResponse.getHits().getHits() == null ||
scollResponse.getHits().getHits().length < 1) {
break;
}
scrollId = scollResponse.getScrollId();
// 处理文档
scrollRequest.scrollId(scrollId);
}
// step 2 end
}
System.out.println(result);
} catch (Exception e) {
e.printStackTrace();
} finally {
if(!StringUtils.isEmpty(scrollId)) {
System.out.println("step 3 start ");
// step 3 start
ClearScrollRequest clearScrollRequest = new ClearScrollRequest();
clearScrollRequest.addScrollId(scrollId);
try {
client.clearScroll(clearScrollRequest, RequestOptions.DEFAULT);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
// step 3 end
}
}
}
这里重点阐述一下第一次查询时,不仅返回scrollId,也会返回第一批数据。
10.2 Keeping the search context alive
scroll参数(传递给搜索请求和每个滚动请求)告诉Elasticsearch它应该保持搜索上下文活动多长时间。它的值(例如1m,参见Time unitsedit)不需要足够长的时间来处理所有数据——它只需要足够长的时间来处理前一批结果。每个scroll请求(带有scroll参数)设置一个新的过期时间。如果scroll请求没有传入scroll,那么搜索上下文将作为scroll请求的一部分被释放。scroll其内部实现类似于快照,当第一次收到一个scroll请求时,就会为该搜索上下文所匹配的结果创建一个快照,随后文档的变化并不会反映到该API的结果。
10.3 sliced scroll
对于返回大量文档的scroll查询,可以将滚动分割为多个可以独立使用的片,通过slice指定。
例如:
GET /twitter/_search?scroll=1m // @1
{
“slice”: { // @11
“id”: 0, // @12
“max”: 2 // @13
},
“query”: {
“match” : {
“title” : “elasticsearch”
}
}
}
GET /twitter/_search?scroll=1m // @2
{
“slice”: {
“id”: 1,
“max”: 2
},
“query”: {
“match” : {
“title” : “elasticsearch”
}
}
}
@1,@2两个并列的查询,按分片去查询。
@11:通过slice定义分片查询。
@12:该分片查询的ID。
@13:本次查询总片数。
这个机制非常适合多线程处理数据。
具体分片机制是,首先将请求转发到各分片节点,然后在每个节点使用匹配到的文档(hashcode(_uid)%slice片数),然后各分片节点返回数据到协调节点。也就是默认情况下,分片是根据文档的_uid,为了提高分片过程,可以通过如下方式进行优化,并指定分片字段。
分片字段类型为数值型。
字段的doc_values设置为true。
每个文档中都索引了该字段。
该字段值只在创建时赋值,并不会更新。
字段的基数应该很高(相当于数据库索引选择度),这样能确保每个片返回的数据相当,数据分布较均匀。
注意,默认slice片数最大为1024,可以通过索引设置项index.max_slices_per_scroll来改变默认值。
例如:
GET /twitter/_search?scroll=1m
{
“slice”: {
“field”: “date”,
“id”: 0,
“max”: 10
},
“query”: {
“match” : {
“title” : “elasticsearch”
}
}
}
11、preference
查询选择副本分片的倾向性(即在一个复制组中选择副本的分片值。默认情况下,Elasticsearch以未指定的顺序从可用的碎片副本中进行选择,副本之间的路由将在集群章节更加详细的介绍 。可以通过该字段指定分片倾向与选择哪个副本。
prefe
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。