- Bulk请求将产生比单文档index请求有更好的性能。至于Bulk请求中文档数量的大小,建议使用单一节点单一分片进行测试,先试试看100个,而后200个,而后400这样,每次进行翻倍测试,只要速度稳定了,也就是最合适的大小了。可是要注意一下,并非速度最合适了就OK,由于每次请求总的大小要进行一下控制。并发发送的时候,ES内存压力会很大,必定要避免每次请求超过几十兆,即使是这样插入的性能更好(这个我踩过坑,我这测试超过10M,ES就不接受请求,直接拒绝了)。
- 通常来讲一个线程,即使是使用了Bulk方式进行Index,也没法达到ES集群的瓶颈,因此为了最大限度的利用集群资源,使用多线程或者多进程的方式进行Index是一个很好的选择。这样不只最大程度利用了集群资源,还帮助减小了fsync的成本。(这个fsync是什么 意思我暂时也没弄明白,后续补充)。
- 要注意一下TOO_MANY_REQUESTS (429) 相应(对应Java Client 则是EsRejectedExecutionException), 这说明ES集群已经跟不上你Index的速度了,使用一些适当的方式限制一下速度吧。(官方文档说暂停Index一会或者使用随机指数函数Backoff)。
- 相似Bulk Index 数量,多线程多进程Index也须要进行人工测试,直到找到一个合适线程数或者进程数。
- 默认的 index.refresh_interval 是1s,在index的时候若是没有实时性检索需求,建议能够设置大一些,好比30S,若是不须要检索,等index完成才进行检索的话,能够设置为-1,也就是禁用,等完成index以后在调整回来。
- 若是须要一次index大量数据,最好禁用refresh,也就是将refresh_interval设置为-1,同时index.number_of_replicas 设置为0,也就是不须要副本。尽管这样会增长一些风险(真的很小很小),也就是在索引的时候可能致使数据丢失,可是这样能够大幅度增长索引速度,等完成索引后在增长副本,这样也能够保证数据的可靠性。
- 必定确保操做系统禁用了swapping,这对ES性能有很大的提高。
- 你应该分配机器的一半内存给ES使用,用于文件系统的缓存。文件系统缓存用于缓冲I/O操做。
- 当你index一个document使用特定的id,ES须要去检查是否在同一个shard存在相同的ID的文档,这是一个至关昂贵的操做,而且随着文档数量的增长,花费呈指数增加。若是使用自动生成id,ES会跳过这个检查,使得Index速度更快。
- 若是I/O是瓶颈,那么最好考虑为文件系统提供更多内存或者购买更好的服务器。使用SSD硬盘能比通常的硬盘有更好的性能。另外尽可能使用本地存储,不要考虑远程存储。也尽量不要考虑Amazon等虚拟化存储,尽管比较简单的使用,可是性能比本地存储差不少。
- 还有要尽量冗余副本,以免节点故障致使数据丢失。也能够用快照备份还原进一步下降数据糗事风险。
若是节点仅仅是大量Index,确保每一个分片 indices.memory.index_buffer_size 大于512M,(尽管大于512M没有什么性能改善)。举个例子,默认值是10%,也是说若是你设置的jvm大小是10G,那么Index缓冲大小是1G,足以支撑2个shard的大量索引。缓存
- 简单来讲,若是你不须要运行exists查询,那么你就能够禁用_field_names。