正确遍历ElasticSearch索引
1:ElasticSearch的查询过程
2:由ES查询模式引起的深度分页问题
3:如何正确遍历索引中的数据
ElasticSearch的查询过程
es的数据查询分两步:
第一步是的结果是获取满足查询条件的,分布于各个shard上的_doc_id及对应_score;
第二步是根据第一步获取的所有的_doc_id,去各个shard上获取数据明细,合并返回客户端。
在第一步的查询中,es执行了一个类似map-reduce的查询模式:在各个shard上执行同样的查询,获取同样大小的数据(from+size),然后将各个 shard查询结果的_doc_id,_score返回给接收查询请求的节点,最终进行一次汇总。注意这里传输数据的数量是from+size,而不仅仅是size大小。
由ES查询模式引起的深度分页问题
通过ES的查询过程我们已经可以看出问题,对大数据量的Index进行遍历操作,如果使用from size的方式,将存在极大的资源浪费(因为from过大),当然如果size过大则问题更为严重,服务器内存会被吃光。因此很多站点的查询,都不会允许查看过大的page,深度分页的问题在关系数据库中同样存在。
如何正确遍历索引中的数据
在ES中遍历索引的推荐方式是采用scroll操作,或者在不需要排序而仅仅需要遍历的情况下,可以采用scroll_scan进一步提升性能。
详细可见:Scroll的官方说明
简单描述一下Scroll的工作原理:
1:对需要遍历(或获取某个满足条件的子集)的索引,规划一个合理的size作为分页大小;
2:在POST的查询中,增加?scroll=1m(expire time)的query string;
3:在该次查询中,返回结果中除了查询结果以外,还有一个scroll_id(很长),这个scroll_id可以看做是第一次查询时目标索引的快照的游标;
4:之后直接在GET请求中将scroll_id作为query string传递,或在POST请求中加入scroll_id即可获取下一批数据,直到没有数据为止,如此实现对所有目标数据的遍历。
(注:在使用scroll遍历的过程中,不需要再指定各种查询条件比如索引名,size大小什么的,只需要指定scroll_id即可,还可以指定scroll:1m之类的过期时间,相同条件下有效期内的scroll操作,返回的scroll_id是不会变的,仅仅是scroll_id这个游标向前走,返回下一批数据而已)
scroll_id可以被显式删除,如果你需要重置对查询目标的遍历过程的话。
如果遍历过程不需要对数据进行排序,可以使用更为高效的scroll_scan方式进行,如下:
POST ip:port/my_index/my_type/_search?search_type=scan&scroll=1m&size=
{
"query": { "match_all": {}}
}
这里需要注意的是,search_type指定为scan,即无需排序,而size=50是指每个shard上的size是50,最终返回数据是shard*size。
初次以外,scroll_scan与普通的scroll还有如下三点不同:
- Scroll-Scan 结果没有排序,按 index 顺序返回,没有排序,可以提高取数据性能。
- 初始化时只返回 _scroll_id,没有具体的 hits 结果。
- size 控制的是每个分片的返回的数据量而不是整个请求返回的数据量
关于scroll操作是否线程安全的问题,es的客户端(java&c#)均为线程安全,因此我认为通过客户端来进行的scroll请求也是线程安全的。如果有错误请指出。
2016-09-14补充:
利用scroll_id获取数据的同时,ES将返回当前查询的scroll_id,在其失效或被删除之前,这个scroll_id都不变,如果希望程序的可靠性更高,可以用每次返回的scroll_id更新查询POST所发送的scroll_id;同时,对通过scroll_id查询返回的结果集进行判空,以确定当前scroll_id是否已失效,从而需要重新获取scroll_id。
正确遍历ElasticSearch索引的更多相关文章
- Elasticsearch索引(company)_Centos下CURL增删改
目录 返回目录:http://www.cnblogs.com/hanyinglong/p/5464604.html 1.Elasticsearch索引说明 a. 通过上面几篇博客已经将Elastics ...
- Elasticsearch索引原理
转载 http://blog.csdn.net/endlu/article/details/51720299 最近在参与一个基于Elasticsearch作为底层数据框架提供大数据量(亿级)的实时统计 ...
- Elasticsearch入门教程(三):Elasticsearch索引&映射
原文:Elasticsearch入门教程(三):Elasticsearch索引&映射 版权声明:本文为博主原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明. 本文 ...
- 带你走进神一样的Elasticsearch索引机制
更多精彩内容请看我的个人博客 前言 相比于大多数人熟悉的MySQL数据库的索引,Elasticsearch的索引机制是完全不同于MySQL的B+Tree结构.索引会被压缩放入内存用于加速搜索过程,这一 ...
- ES3:ElasticSearch 索引
ElasticSearch是文档型数据库,索引(Index)定义了文档的逻辑存储和字段类型,每个索引可以包含多个文档类型,文档类型是文档的集合,文档以索引定义的逻辑存储模型,比如,指定分片和副本的数量 ...
- Elasticsearch索引和文档操作
列出所有索引 现在来看看我们的索引 GET /_cat/indices?v 响应 health status index uuid pri rep docs.count docs.deleted st ...
- ElasticSearch 索引 剖析
ElasticSearch index 剖析 在看ElasticSearch权威指南基础入门中关于:分片内部原理这一小节内容后,大致对ElasticSearch的索引.搜索底层实现有了一个初步的认识. ...
- Elasticsearch 索引、更新、删除文档
一.Elasticsearch 索引(新建)一个文档的命令: curl XPUT ' http://localhost:9200/test_es_order_index/test_es_order_t ...
- Elasticsearch 索引的全量/增量更新
Elasticsearch 索引的全量/增量更新 当你的es 索引数据从mysql 全量导入之后,如何根据其他客户端改变索引数据源带来的变动来更新 es 索引数据呢. 首先用 Python 全量生成 ...
随机推荐
- Android Fragment使用(一) 基础篇 温故知新
Fragment使用的基本知识点总结, 包括Fragment的添加, 参数传递和通信, 生命周期和各种操作. Fragment使用基础 Fragment添加 方法一: 布局里的标签 标识符: tag, ...
- Google C++单元测试框架GoogleTest---Extending Google Test by Handling Test Events
Google TestExtending Google Test by Handling Test Events Google测试提供了一个事件侦听器API,让您接收有关测试程序进度和测试失败的通知. ...
- xcode8打包ipa文件, application loader上传成功,但是iTunes Connect不显示构建版本
最近更新的Xcode8.今天提交新项目时.按照以往的流程走 Xcode 编译ipa文件.applicaiton loader提交成功 但是.iTunes connect构建版本不显示.非常疑惑.平时等 ...
- centos6.5和centos7如何搭建php环境
作者:白狼 出处:http://www.manks.top/linux_php.html 本文版权归作者,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责 ...
- [转]HDFS中JAVA API的使用
HDFS是一个分布式文件系统,既然是文件系统,就可以对其文件进行操作,比如说新建文件.删除文件.读取文件内容等操作.下面记录一下使用JAVA API对HDFS中的文件进行操作的过程. 对分HDFS中的 ...
- TNS-12540: TNS:internal limit restriction exceeded
应用程序以及客户端工具(Toad.PL/SQL Developer等)出现突然连接不上数据库服务器的情况,监听日志listener.log里面出现了TSN-12518与TSN-12540错误,如下所示 ...
- js获取URL地址栏中的参数
function getUrlParam(name) { var reg = new RegExp("(^|&)" + name + "=([^&]*)( ...
- Migrate Instance 操作详解 - 每天5分钟玩转 OpenStack(40)
Migrate 操作的作用是将 instance 从当前的计算节点迁移到其他节点上. Migrate 不要求源和目标节点必须共享存储,当然共享存储也是可以的. Migrate 前必须满足一个条件:计算 ...
- android Intent使用
ntent.setType(“image/*”);//图片格式 intent.setType(“audio/*”); //选择音频 intent.setType(“video/*”); //选择视频 ...
- 3、DNS服务器功能(正向、反向解析)
实验目的: 建立gr.org域的主名称服务器.解析: 名称 IP 用途 ns.gr.org 192.168.170.3 名称服务器 www.gr.org 192 ...