一、概述

在此之前,一直想写关于 ES 相关的文章,但是工作实在太忙,没能抽空完成,今天刚好有时间,那我们就先来总结一下 ES 相关的知识点,学习一个新东西一定要先从整体去看全局,然后再到局部去了解细节,学 ES 也是一样,ES 是什么?其实你可以完完全全把它当做是一个数据库,这个数据库和 MySQL 一样有自己的实现机制来管理一堆数据,看到这里想必你对它感官上的认识就清晰了,至于它是如何工作的,对数据的 CRUD 原理是怎么进行的,这些都是细节,需要我们花大量的时间和精力去学习,另外一点你还需要知道的是,ES 数据库是基于 lucene 来实现的,说白了 lucene 有些类似于内核的概念,ES 只是在它的基础上层做了封装,好了到这里想必我已经从全局上说清楚了 ES 是什么的问题,接下来就开始深入,死扣细节。

二、ES 核心概念

在学习一个理论,或者一个产品之前,必须先理解一些与其相关的核心原理,接下来我就罗列一些我认为对理解 ES 有较大帮助的概念。

  • Near Realtime

    近实时,有两层含义:1、从写入数到可以被搜索到有一个小延迟 (大概是 1s 这和 ESbuffer 刷到 os cache 机制有关,后门会细说) 2、基于 ES 执行搜索和分析可以达到秒级。

  • Cluster 集群

    集群里包含一个或多个节点,每一个节点属于哪一个集群通过配置文件来指定,对于单实例的 ES 来说他也是一个集群,只不过这个集群只有一个节点。

  • Node 节点

    Node 是集群中的一个节点,每个节点都有一个名称,如果不指定,默认会随机分配,多个节点可以通过配置加入或移出一个集群。

  • Document & field

    文档是 ES 中最小的数据单元,类似于 MySQL 中的一行,它通过 json 格式组织数据,一个文档包含多个 field ,每一个 field 就类似于 MySQL 中的一个字段。

  • Index

    索引包含一堆有相似结构的文档数据,可以类比成 MySQL 中的数据库的概念,但是正常情况下索引里只会创建一个Type(表),是 ES 存储数据的基本单位。ES 中关键概念直接的关系:Index → Type → mapping → document → field

  • Type

    类型,每一个 Index 下都有一个或多个 TypeType 可以类比为数据库中的表,一个 Index下可以创建多个 Type 但是一般在使用的时候我们都只会在一个 Index 下创建一个 TypeType 这个概念在 7.x 的版本中被完全移除。

  • shard

    分片,将索引中的数据切分为多个 shard,分布在多台服务器上存储,保证 ES 具备横向扩展能力,通过协调节点,将搜索分散到多台机器上去计算,提高性能。

  • mapping

    你可以类比成数据库中的表结构定义,例如字段名称,字段类型,这个概念在 7.x 的版本中也被弃用。

  • replica

    表示分片的副本,保证故障时能切换回去并提供服务。replica 分为 primary shardreplica shard,创建一个索引时候默认被分为 5primary shard,主分片的数量在创建时指定,之后不能再修改;replica shard 副本分片,默认创建一个,副本分片的数量可以在 ES 运行过程中动态调整,最小的高可用配置为 2 台机器(分片分布在不同机器上的形式,有点类似于 Kafkapartition 机制)

  • 倒排索引

    在使用 MySQL 时知道,索引会有长度的,你有么有思考过,如果一数据库字段专门用来存储文章,那么如何对这个字段创建索引?在 MySQL 中没有倒排索引的概念,因此只能截取一部分内容作为索引。ES 提供的倒排索引,就是将文本中的关键字提取出来,并维护关键字与 doc id 的对应关系,查询数据时就可以根据关键字在倒排索引中查询到 doc id ,最终获取查询到的 document。下面通过一个栗子来说明:

    有以下文档:

    DocId Doc
    1 谷歌地图之父跳槽 Facebook
    2 谷歌地图之父加盟 Facebook
    3 谷歌地图创始人拉斯离开谷歌加盟 Facebook
    4 谷歌地图之父跳槽 Facebook 与 Wave 项目取消有关
    5 谷歌地图之父拉斯加盟社交网站 Facebook

    对文档进行分词之后,得到以下倒排索引

    WordId Word DocIds
    1 谷歌 1, 2, 3, 4, 5
    2 地图 1, 2, 3, 4, 5
    3 之父 1, 2, 4, 5
    4 跳槽 1, 4
    5 Facebook 1, 2, 3, 4, 5
    6 加盟 2, 3, 5
    7 创始人 3
    8 拉斯 3, 5
    9 离开 3
    10 4

有了倒排索引,搜索引擎可以很方便地响应用户的查询。比如用户输入查询 Facebook ,搜索系统查找倒排索引,从中读出包含这个单词的文档,这些文档就是提供给用户的搜索结果。

倒排索引的两个重要细节说明:

1、倒排索引中所有词项对应一个或多个文档

2、倒排索引中的词项根据词的升序排序(注意:上面的栗子仅仅是为了表达倒排索引的含义,没有严格按照升序排列)

三、ES 分布式架构原理

我们都知道 ES 是支持分布式、并行计算的,分布式解决保证了横向扩展的能力,并行计算指的是一个请求在集群环境下会分发到不同节点进行并行计算,提高性能。接下来我就以一个 3 个节点 3 个主分片 1 个副本分片的架构对 ES 分布式架构原理进行介绍,假设 order 索引有 3T 的数据量,将这个 index 分成 3 个分片分别保存在不同节点上,并且每一个分片会有一个副本,也就意味着每一个节点上存在 1 个主分片及非这个主分片的另外一个分片的副本,通过这种方式保证了集群的可用性,如果一个节点挂了,那么该节点上的主分片在其它节点上还有副本,该副本会变成分片的主分片,此时的集群架构是,其中一个节点上有两个主分片(宕机了一台嘛)。ES 集群的多个主节点中,会自动选一个节点作为 master 节点,该节点主要用于管理集群,例如,维护索引元数据、切换 primary shardreplica shard 身份,如果 master 节点宕机,那么会重选择一个节点作为 master 节点,如果非 master 节点宕机,那么此节点上的 primary shard 就没有了, master 节点负责把该分片在其它节点上的 replica shard 设置为 primary shard ,如果宕机的节点恢复后,其内部原来的分片变成 replica shard

四、ES 读写工作原理

  • 写数据的过程
    1. ES 的客户端选择一个节点,并将请求发给选中的节点,此时对于这个请求而言,选中的节点称为 coordination node (协调节点)

    2. 协调节点对 document 进行路由,将请求转发到具有此时操作 Index 对应的 primary shard 的所有节点上,此时在每一个 primary shard 节点上并行写入,并将数据同步到其对应的副本分片上。

    3. 一个节点完成 primary shard 的写入及其所有副本分片的同步后,会将结果返回给协调节点,协调节点在收到返回后,就响应客户端此次写操作的处理结果,此时如果并发写入很高,请求会转发到其它主分片上进行写入。

  • 写数据底层原理

    当一个写请求到来时,协调节点会将写请求分发到其中一个主分片上,接下来写入的工作细节如下:

    1. 写入请求到被协调节点分发到操作 Index 的协调节点

    2. 先写到 ES 的内存 buffer,同时记录 translog 日志到 translog 日志文件中(可以类比为数据库 redo log),需要注意的是,停留在 buffer 中的数据,是无法被搜索到的。

    3. 如果 buffer 快满或 buffer 中有数据在每 1 秒后,会将 buffer 中的数据 reflash 到一个新的 segment file 中(此时也要记录 translog),需要注意的是此时的 segment file 是操作系统创建的,还停留在 os cache 中,没有刷到磁盘,磁盘上还没有从物理上看到这个文件,也就意味着,如果 buffer 非空的情况下,每 1 秒会创建一个内存状态的 segment file ,并且这个 segment file 中存储的是一秒内的数据。如果数据被 reflashos cachesegment file 中 此时的数据就可以被搜索到,reflash 操作完成后 buffer 中的数据被清空。

    4. 重复上面的过程,会有两个问题出现 segment file 会越来越多,因此需要定期合并; translog 日志文件会越来越大,需要定期 commit 后,将数据全部持久化到磁盘的 segment file 中,然后清空自己。

    5. commit 操作发生时,第一步会将 buffer 中的数据 reflashos cache 中,清空 buffer ,然后将 commit point 写入磁盘 commit point 文件,里面标识着此时 commit 操作 commit point 对应的所有 segment file,同时强行将 os cache 中的数据 fsync 到磁盘 segment file 中去,最后清空 translog 日志文件,此时 commit 的操作完成。

      1、为什么说 ES 是准实时?

      因为数据如果停留在 buffer 中是不能被查到的,ES 会每一秒执行一次 reflash 操作,reflash完毕后数据才能查到

      2、多久执行一次 commit?

      commit 操作也叫做 flush ,默认 30 分钟自动执行一次 flush ,当然如果 translog 文件过大时,也会触发 flush,flush 操作对应 commit 的全过程,可以通过 es api 手动执行 flush 操作,手动将 os cache 中的数据进行 fsync

      3、translog 日志文件的作用?

      执行 commit 之前,新写入的数据要么停留在 buffer 或 os cache 内存中,如果此时宕机那么数据不就丢失了么, translog 就是达到日志保护的作用,如果宕机会通过 translog 将数据恢复到 buffer 和 os cache 中(这两种数据状态不同,buffer 中的数据需要日志保护,reflash后的数据,日志文件也要记录数据的状态,在恢复时决定将数据恢复到buffer 还是 os cache);但是需要注意的是 translog 日志也是先写内存缓冲区的,默认每隔 5 秒刷一次磁盘,所以默认情况下,如果宕机,可能会此时 5 秒钟的数据,当然也可以配置每次写操作都将日志刷盘,这样性能会差一些。

      4、倒排索引什么时候创建?

      数据写入 segment file 之后,同时会创建倒排索引。

      5、segment file merge 原理

      buffer 每次 reflash ,都会产生一个 segment file , 所以默认 1s 生成一个 segment file,随着时间推移,这种文件会越来越多,因此需要定义执行 merge 合并操作,将多个小的 segment file 合并为一个大的 segment file,删除旧的 segment file文件,在合并的过程中会将标记为 deleted 状态的 doc 物理删除,合并完毕后会写一个 commit point。

      **总结一下:**数据先写入内存 buffer 然后每隔 1 秒,数据被 reflashos cache 中,os cache 中的数据可以被搜索到(所以说 ES 是近实时的),每隔 5 秒将数据写入 translog 文件(这样如果机器宕机,内存数据没了,最多会有 5s 的数据丢失),translog 大到一定程度,或每隔 30 分钟,会触发 commit 操作,将 buffer 、oa cache、tanslog buffer 中的数据都刷盘。

  • 删除/更新数据的底层实现原理

    删除操作:如果是删除操作,会生成一个 .del 文件,里面将删除的 doc 标记为 deleted 状态,搜索的时候根据 .del 文件过滤掉被删除的 doc

    更新操作:将原来的 doc 标记为 deleted 状态,然后插入一条新的数据。

  • 读数据的过程
    1. 客户端发送查询请求到任意一个节点,此时被选中的节点称为协调节点
    2. 协调节点对查询的 document id 进行 hash ,路由到不同的节点上去分别查询数据,此时可能会路由到主分片或副本分片,采用的是随机轮询算法来选择 primary shardreplica shard 来处理该分片上的查询任务。
    3. 每一个节点并行计算完毕后,将数据返回协调节点,然后响应客户端。
  • 搜索数据的过程

    接下来通过在 ES 中搜索 java 关键字的案例为例,来介绍 ES 是如何把数据查出来的:

    java真好玩儿啊
    java好难学啊
    j2ee特别牛
    

    将包含 javadocument 搜索出来,最终 ES 会返回 java 真好玩啊,java 好难学啊,过程如下:

    1. 客户端选择集群中的一个节点作为协调节点

    2. 协调节点将搜索请求转发到所有的 shard 对应的 primary shardreplica shard ,具体是到主分片还是副本分片根据轮询算法来选择

    3. query phase:每一个节点将自己的搜索结果(注意:这里返回的不是 document 的真实数据,其实就包含一些 doc id 及元数据信息)返回给协调节点,协调节点对数据进行合并、排序、分页等操作得到最终要获取的数据 doc id

    4. fetch phase:接着由协调节点根据 doc id 去各个节点上拉取实际的 document 数据,最后返回给客户端。

      值得注意的是,写请求首先会写入一个分片的 primary shard上,然后同步到每一个 replica shard 分片;读数据可以从 primary shard上读取也可以从 replica shard 上读取,采用的是随机轮询算法。

五、数十亿级别数据下优化查询

六、ES 集群搭建

请看下一篇《ES集群搭建与Kibana+head+IK配置》

ElasticSearch工作原理解读及一些思考相关推荐

  1. Asp.Net Core EndPoint 终结点路由工作原理解读

    Asp.Net Core EndPoint 终点路由工作原理解读 一.背景 在本打算写一篇关于Identityserver4 的文章时候,却发现自己对EndPoint -终结点路由还不是很了解,故暂时 ...

  2. Elasticsearch工作原理

    一.关于搜索引擎 各位知道,搜索程序一般由索引链及搜索组件组成. 索引链功能的实现需要按照几个独立的步骤依次完成:检索原始内容.根据原始内容来创建对应的文档.对创建的文档进行索引. 搜索组件用于接收用 ...

  3. elasticsearch 工作原理_【154期】面试官:你能说说 Elasticsearch 查询数据的工作原理是什么吗?...

    点击上方"Java面试题精选",关注公众号 面试刷图,查缺补漏 >>号外:往期面试题,10篇为一个单位归置到本公众号菜单栏->面试题,有需要的欢迎翻阅 阶段汇总集 ...

  4. 显卡结构与工作原理解读

    什么是显卡? 显卡的工作非常复杂,但其原理和部件很容易理解.在本文中,我们先来了解显卡的基本部件和它们的作用.此外,我们还将考察那些共同发挥作用以使显卡能够快速.高效工作的因素. 显示卡(videoc ...

  5. 【开源共享】全网最简单易用的imx6ull烧写工具设计初衷工作原理设计前的思考

    在线课堂:https://www.100ask.net/index(课程观看) 论  坛:http://bbs.100ask.net/(学术答疑) 开 发 板:https://100ask.taoba ...

  6. 详细解读神经网络十大误解,再也不会弄错它的工作原理

    来源:http://www.cstor.cn/textdetail_10544.html_biz=MjM5OTA1MDUyMA==&mid=407358558&idx=2&sn ...

  7. 深入解读RabbitMQ工作原理及简单使用

    深入解读RabbitMQ工作原理及简单使用 RabbitMQ系列目录 RabbitMQ在Ubuntu上的环境搭建 深入解读RabbitMQ工作原理及简单使用 Rabbit的几种工作模式介绍与实践 Ra ...

  8. ElasticSearch面试 - es 写入数据的工作原理是什么啊?

    ElasticSearch面试 - es 写入数据的工作原理是什么啊? 面试题 es 写入数据的工作原理是什么啊?es 查询数据的工作原理是什么啊?底层的 lucene 介绍一下呗?倒排索引了解吗? ...

  9. 显卡结构及工作原理详细解读

    显卡结构及工作原理详细解读 标签: 显卡三维图像 2016-01-16 20:58 864人阅读 评论(0) 收藏 举报  分类: 3D原理(11)  什么是显卡? 显卡的工作非常复杂,但其原理和部件 ...

最新文章

  1. Java并发同步器AQS
  2. angularjs-ngModel 控制页面的宽度
  3. Cmd使用方式--命令行运行程序
  4. 信号相参性(相干性)(转)
  5. java 桥梁模设计,Java设计模式学习篇(九)桥接设计模式
  6. Java微信订单查询
  7. LeetCode 1638. 统计只差一个字符的子串数目(DP)
  8. SignalR---DOTNET客户端
  9. ORACLE HANDBOOK系列之五:PL/SQL中的集合类型(Collections in PL/SQL)
  10. 【心电信号】基于matlab心电信号采集与处理【含Matlab源码 954期】
  11. 读《About Face 4 交互设计精髓》19
  12. mysql合并两个表_MYSQL如何合并两个表
  13. JAVA开发(神乎其神的区块链概念和技术)
  14. 干支纪年法简便算法_初中历史四种纪年法,每一种都要掌握
  15. Xshell连接ubuntu后vi编辑器中数字小键盘乱码
  16. SystemUI之NavigationBar导航栏
  17. CSS 学习笔记 - 盒模型
  18. git错误'fatal: cannot do a partial commit during a merge'
  19. 神武可以同时登陆服务器账号吗,解读新系统神武账号仓库 同号共用仓库
  20. IOS开发百度地图API-用点生成路线,导航,气泡响应

热门文章

  1. 2D游戏引擎Allegro 系列教程(二) Hello world!
  2. 游戏开发中的人工智能(五):以势函数实现移动
  3. idea iu 2021 Mac版本的使用,如何创建java web项目,包括tomcat和web包
  4. linux 查看动态日志tail tailf
  5. 娶一位俄罗斯姑娘当老婆是一种什么样的感觉?
  6. [应用方案]基于DP5020点阵屏的显示驱动
  7. 德语环境下 小数点格式化时数字格式异常问题
  8. RecyclerView多级目录实现
  9. Asterisk 开启日志,记录SIP信令
  10. 树莓派TF卡低格,存储空间还原