事务日志
Lucene 为了加快写索引的速度,采用了延迟写入的策略。
虽然这种策略提高了写入的效率,但其最大的弊端是,如果数据在内存中还没有持久化到磁盘上时发生了类似断电等不可控情况,就可能丢失数据。
为了避免丢失数据,Elasticsearch 添加了事务日志(Translog),事务日志记录了所有还没有被持久化磁盘的数据。
写操作及操作系统缓存
Elasticsearch数据的写入并不是直接写入磁盘,这样效率太低,而是先写入内存。
因为内存中的数据还会继续写入,所以内存中的数据并不是以段的形式存储的,是检索不到的。
所以,Elasticsearch 是一个准实时的搜索引擎,而不是一个实时的搜索引擎。
刷新:
当达到默认的时间(1 秒钟)或者内存的数据达到一定量时,会触发一次刷新(Refresh)。
将内存中的数据刷新到一个新的段中,但是该段并没有持久化到硬盘中,而是缓存在操作系统的文件缓存系统中。虽然数据还在内存中,但是内存里的数据和文件缓存系统里的数据有以下区别。
内存中的数据是搜索不到,文件缓存系统中的数据是可以搜索的。
打开操作系统缓存,使其可被搜索。
清空内存,日志不做处理
当日志数据的大小超过 512MB 或者时间超过 30 分钟时,需要触发一次刷新。
在文件缓存系统中创建一个新的段,并把内存中的数据写入,使其可被搜索。
清空内存,准备接收新的数据。
将文件系统缓存中的数据通过 Fsync 函数刷新到硬盘中。
生成提交点。
删除旧的日志,创建一个空的日志。
读操作
根据 Routing 字段进行的单个文档的查询,在 Elasticsearch 集群中可以在主分片或者副本分片上进行。
客户端向集群发送查询请求,集群再随机选择一个节点作为协调点(Node 1),负责处理这次查询。
Node 1 使用文档的 routing id 来计算要查询的文档在哪个分片上(在本例中落在了 0 分片上)分片 0 的副本分片存在所有的三个节点上。
在这种情况下,协调节点可以把请求转发到任意节点,本例将请求转发到 Node 2 上。
Node 2 执行查找,并将查找结果返回给协调节点 Node 1,Node 1 再将文档返回给客户端。