我们知道了Elasticsearch能够做什么,接下来我们将见识Elasticsearch另一个很强的-----扩展能力,也就是,Elasticsearch如何能够处理更多的索引和搜索请求,或者是更快地处理索引和搜索请求。在处理百万级甚至数十亿级的文档时,扩展性是一个非常重要的因素。 没有了某种形式的扩展,在单一的 Elasticsearch运行实例或节点( node)上就无法一直支持规模持续增大的流量。Elaticsearch很容易扩展。所以我们来了解 Elasticsearch所拥有的扩展能力,以及如何使用这些特性来给予Elasticsearch更多的性能、更多的可靠性。
一、理解物理设计
1、节点和分片
为了有个全局的理解,我们首先要知道Elasticsearch索引创建的时候,究竟发生了什么,理解数据在物理是如何上组织的?
默认情况下,每个索引由5个主要分片组成,而每份主要分片又有一个副本, 一共10份分片。副本分片对于可靠性和搜索性能很有益处。技术上而言,一份分片是一个目录中的文件,Lucene用这些文件存储索引数据。分片也是Elasticsearch将数据从一个节点迁移到另一个节点的最小单位。
一个节点是一个Elasticsearch的实例。在服务器上启动Elasticsearch之后,你就拥有了一个节点。如果在另一台服务器上启动Elasticsearch,这就是另一个节点。甚至可以通过启动多个Elasticsearch进程,在同一台服务器上拥有多个节点。
多个节点可以加入同一个集群。在多节点的集群上,同样的数据可以在多台服务器上传播。这有助于性能,因为Elasticsearch有了更多的资源;这同样有助于稳定性,如果每份分片至少有1个副本分片,那么任何一个节点都可以宕机,而Elasticsearch依然可以进行服务,并返回所有数据。
对于使用Elasticsearch的应用程序,集群中有1个还是多个节点都是透明的。默认情况下,可以连接集群中的任一节点并访问完整的数据集,就好像集群只有单独的一个节点。
尽管集群对于性能和稳定性都有好处,但它也有缺点:必须确定节点之间能够足够快速地通信,并且不会产生脑裂。为了解决这个问题,我们后面会来讨论。
一份分片是Lucene的索引:一个包含倒排索引的文件目录。倒排索引的结构使得Elasticsearch在不扫描所有文档的情况下,就能告诉你哪些文档包含特定的词条( 单词)。
1.1、Elasticsearch索引和Lucene索引的对比:
Elasticsearch索引被分解为多块分片,一份分片是一个Lucene的索引,所以一个Elasticsearch的索引由多个Lucene的索引组成。 一个分片是一个Lucene索引(一个倒排索引)。它默认存储原始文档的内容,再加上一些额外的信息,如词条字典和词频,这些都能帮助到搜索。词条字典将每个词条和包含该词条的文档映射起来。搜索的时候,Elasticsearch没有必要为了某个词条扫描所有的文档,而是根据这个字典快速地识别匹配的文档。
词频使得Elasticsearch可以快速地获取某篇文档中某个词条出现的次数。这对于计算结果的相关性得分非常重要。例如,如果搜索“denver",包含多个“denver”的文档通常更为相关。Elasticsearch将给它们更高的得分,让它们出现在结果列表的更前面。
接下来看看主分片和副本分片的细节,以及它们是如何在Elasticsearch集群中分配的。
1.2、附:ES中的节点类型
Master-eligible nodes与Master node每个节点启动后,默认就是一个Master eligible节点,可以通过设置node.master:false来改变,Master-eligible节点可以参加选主流程,成为Master节点,每个节点都保存了集群的状态,但只有Master节点才能修改集群的状态信息,主节点主要负责集群方面的轻量级的动作,比如:创建或删除索引,跟踪集群中的节点,决定分片分配到哪一个节点,在集群再平衡的过程中,如何在节点间移动数据等。
1)Data Node
可以保存数据的节点,叫做Data Node,负责保存分片数据。在数据扩展上起到了至关重要的作用,每个节点启动后,默认就是一个Data Node节点,可以通过设置node. data:false来改变。
2)Ingest Node
可以在文档建立索引之前设置一些ingest pipeline的预处理逻辑,来丰富和转换文档。每个节点默认启动就是Ingest Node,可用通过node.ingest = false来禁用。
3)Coordinating Node
Coordinating Node负责接收Client的请求,将请求分发到合适的节点,最终把结果汇集到一起,每个节点默认都起到了Coordinating Node的职责,当然如果把master、Data、Ingest全部禁用,那这个节点就仅是Coordinating Node节点了。
4)Machine Learning Node
用于机器学习处理的节点。
2、主分片和副本分片
分片可以是主分片,也可以是副本分片,其中副本分片是主分片的完整副本, 副本分片可以用于搜索,或者是在原有主分片丢失后成为新的主分片。主分片是权威数据,写过程先写主分片,成功后再写副分片。
Elasticsearch 索引由一个或多个主分片以及零个或多个副本分片构成。副本分片可以在运行的时候进行添加和移除,而主分片不可以。
可以在任何时候改变每个分片的副本分片的数量,因为副本分片总是可以被创建和移除。这并不适用于索引划分为主分片的数量,在创建索引之前,你必须决定主分片的数量。请记住,过少的分片将限制可扩展性,但是过多的分片会影响性能。默认设置主分片的数量是5份。
索引主分片的设置:
put test1{
"settings":{
"index.number_of_shards":3,
"index.codec":"best_compression"
}
}
索引副本分片的设置:
put test1/_settings
{
"index.number_of_replicas":2
}
3、在集群中分发分片
最简单的Elasticsearch集群只有一个节点: 一台机器运行着一个Elasticsearch进程。我们安装并启动了Elasticsearch之后,就已经建立了一个拥有单节点的集群。随着越来越多的节点被添加到同一个集群中,现有的分片将在所有的节点中自动进行负载均衡。因此,在那些分片上的索引和搜索请求都可以从额外增加的节点中获益。以这种方式进行扩展(在节点中加入更多节点)被称为水平扩展。此方式增加更多节点,然后请求被分发到这些节点上,工作负载就被分摊了。
水平扩展的另一个替代方案是垂直扩展,这种方式为Elasticsearch的节点增加更多硬件资源,可能是为虚拟机分配更多处理器,或是为物理机增加更多的内存。尽管垂直扩展几乎每次都能提升性能,它并非总是可行的或经济的。
4、分布式索引和搜索
在多个节点的多个分片上是如何进行索引和搜索的呢?
4.1、当索引一篇文档时
默认情况下,当索引一篇文档的时候,系统首先根据文档ID的散列值选择一个主分片,并将文档发送到该主分片。这份主分片可能位于另一个节点,不过对于应用程序这一点是透明的。
默认地,文档在分片中均匀分布:对于每篇文档,分片是通过其ID字符串的散列决定的。每份分片拥有相同的散列范围,接收新文档的机会均等。
一旦目标主分片确定,接受请求的节点将文档转发到该主分片所在的节点。随后,索引操作在该主分片的所有副本分片中进行。在所有可用副本分片完成文档的索引后,索引命令就会成功返回。这使得副本分片和主分片之间保持数据的同步。数据同步使得副本分片可以服务于搜索请求,并在原有主分片无法访问时自动升级为主分片。
4.2、搜索索引时
当搜索一个索引时,Elasticsearch需要在该索引的完整分片集合中进行查找。 这些分片可以是主分片,也可以是副本分片,原因是对应的主分片和副本分片通常包含一样的文档。Elasticsearch在索引的主分片和副本分片中进行搜索请求的负载均衡,使得副本分片对于搜索性能和容错都有所帮助。
在搜索的时候,接受请求的节点将请求转发到一组包含所有数据的分片。Elasticsearch使用round-robin的轮询机制选择可用的分片(主分片或副本分片),并将搜索请求转发过去,Elasticsearch然后从这些分片收集结果,将其聚集为单一的回复,然后将回复返回给客户端应用程序。在默认情况下,搜索请求通过round-robin轮询机制选中主分片和副本分片。
二、向集群中加入节点
1、单机集群(伪集群)
创建Elasticsearch集群的第一步, 是为单个节点加入另一个节点(或多个节点),组成节点的集群。 没有加入第二个节点前:http://xxxxxx:9200/_cluster/state/master_node,nodes?pretty
1.1、如何加入第二个节点
1)解压缩压缩包elasticsearch-7.7.0-linux-x86_64.tar.gzip到另外一个目录,比如elasticsearch-2,并且保证这个es中不包含任何数据;
2)修改配置文件
将cluster.name改为和第一个节点一样(cluster.name: my-elk);
给第二个节点配置独立的名字(例如:node.name: node-2);
network.host改为本机地址:
vim /etc/elasticsearch