本套技术专栏是做者(秦凯新)平时工做的总结和升华,经过从真实商业环境抽取案例进行总结和分享,并给出商业应用的调优建议和集群环境容量规划等内容,请持续关注本套博客。QQ邮箱地址:1120746959@qq.com,若有任何学术交流,可随时联系。java
elasticsearch设计的理念就是分布式搜索引擎,底层其实仍是基于lucene的。node
es中存储数据的基本单位是索引,好比说你如今要在es中存储一些订单数据,你就应该在es中建立一个索引,order_idx,全部的订单数据就都写到这个索引里面去,一个索引差很少就是至关因而mysql里的一张表。mysql
-> index(mysql里的一张表)
-> type(一个index里能够有多个type,每一个type的字段都是差很少的,可是有一些略微的差异。
好比在订单index里,建两个type,一个是实物商品订单type,一个是虚拟商品订单type,
这两个type大部分字段是同样的,少部分字段是不同的)
-> mapping (mapping就是这个type的表结构定义)
-> document (一条document就表明了mysql中某个表里的一行,每一个document有多个field,每一个field就表明了这个document中的一个字段的值)
-> field(具体索引字段)
复制代码
步骤一(buffer缓冲和写入translog日志阶段):ES 写数据先写入buffer,在buffer里的时候数据是搜索不到的,并同时将数据写入translog日志文件。sql
步骤二(refresh刷写os cache阶段):当写入数据buffer快满了,或者到必定时间,就会将buffer数据refresh到一个新的segment file中,可是此时数据不是直接进入segment file的磁盘文件的,而是先进入os cache的,这个过程就是refresh。segment file位于os cache中。api
(1) 每隔1秒钟,es将buffer中的数据写入一个新的segment file,
每秒钟会产生一个新的磁盘文件,segment file,这个segment file
中就存储最近1秒内buffer中写入的数据。
(2) 若是buffer里面此时没有数据,那固然不会执行refresh操做,每秒建立换一个空的
segment file,若是buffer里面有数据,默认1秒钟执行一次refresh操做,刷入一个
新的segment file中
(3) 只要buffer中的数据被refresh操做,刷入os cache中,就表明这个数据就能够被搜索到了
(4) 为何叫es是准实时的?NRT,near real-time,准实时。
默认是每隔1秒refresh一次的,因此es是准实时的,由于写入的数据1秒以后才能被看到。
(5) 能够经过es的restful api或者java api,
手动执行一次refresh操做,就是手动将buffer中的数据刷入os cache中,让数据立马就能够被搜索到。
复制代码
步骤三(清空buffer阶段):只要数据被输入os cache中,buffer就会被清空了,由于不须要保留buffer了,数据在translog里面已经持久化到磁盘去一份了。restful
步骤四(commit阶段flush操做):重复1~3步骤,新的数据不断进入buffer和translog,不断将buffer数据写入一个又一个新的segment file中去,每次refresh完buffer清空,translog保留。随着这个过程推动,translog会变得愈来愈大。当translog达到必定长度的时候,就会触发commit操做。架构
(1)commit操做发生第一步,就是将buffer中现有数据refresh到os cache中去,清空buffer
(2)将一个commit point写入磁盘文件,里面标识着这个commit point对应的全部segment file
(3)强行将os cache中目前全部的数据(全部的segment file文件)都fsync到磁盘文件中去。
(4)将现有的translog清空,而后再次重启启用一个translog,此时commit操做完成。
默认每隔30分钟会自动执行一次commit,可是若是translog过大,也会触发
commit。整个commit的过程,叫作flush操做。咱们能够手动执行flush操做,
就是将全部os cache数据刷到磁盘文件中去。
(5)es中的flush操做,就对应着commit的全过程。咱们也能够经过es api,
手动执行flush操做,手动将os cache中的数据fsync强刷到磁盘上去,
记录一个commit point,清空translog日志文件。
(6)translog其实也是先写入os cache的,默认每隔5秒刷一次到磁盘中去,因此默认状况下,
可能有5秒的数据会仅仅停留在buffer或者translog文件的
os cache中,若是此时机器挂了,会丢失5秒钟的数据。可是这样性能比较好,最多
丢5秒的数据。也能够将translog设置成每次写操做必须是直接fsync到磁盘,可是性能会差不少。
(7) es是准实时的,数据写入1秒后能够搜索到;可是却可能会丢失数据,由于
有5秒的数据停留在buffer、translog os cache、segment file os cache中,
有5秒的数据不在磁盘上,此时若是宕机,会致使5秒的数据丢失。
(8) 若是你但愿必定不能丢失数据的话,你能够设置个参数,官方文档,百度一下。
每次写入一条数据,都是写入buffer,同时写入磁盘上的translog,可是
这会致使写性能、写入吞吐量会降低一个数量级。原本一秒钟能够写2000条,
如今你一秒钟只能写200条,都有可能。
复制代码
步骤五(删除操做):commit的时候会生成一个.del文件,里面将某个doc标识为deleted状态,那么搜索的时候根据.del文件就知道这个doc被删除了app
步骤六(更新操做):就是将原来的doc标识为deleted状态,而后新写入一条数据elasticsearch
步骤七 (merge阶段操做):buffer每次refresh一次,就会产生一个segment file,因此默认状况下是1秒钟一个segment file,segment file会愈来愈多,此时会按期执行merge。 每次merge的时候,会将多个segment file合并成一个,同时这里会将标识为deleted的doc给物理删除掉,而后将新的segment file写入磁盘,这里会写一个commit point,标识全部新的segment file,而后打开segment file供搜索使用,同时删除旧的segment file。分布式
生产部署还有不少工做要作,本文从初级思路切入,进行了问题的整合。
本套技术专栏做者(秦凯新)专一于大数据及容器云核心技术解密,具有5年工业级IOT大数据云平台建设经验,可提供全栈的大数据+云原平生台咨询方案,请持续关注本套博客。QQ邮箱地址:1120746959@qq.com,若有任何学术交流,可随时联
秦凯新