Elasticsearch分布式文档存储
Posted gc65
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Elasticsearch分布式文档存储相关的知识,希望对你有一定的参考价值。
Elasticsearch如何知道文档属于哪个分片?当我们创建一个新文档时,它是如何知道它是否应该将该文档存储在分片1或分片2上?
该过程不能是随机的,因为我们将来可能需要检索文档。事实上,它由一个简单的公式决定:
shard = hash(routing)%number_of_primary_shards
该routing
值是一个任意字符串,默认为文档 _id,
但也可以设置为自定义值。
此routing
字符串通过散列函数传递以生成一个数字,该数字除以索引中的主分片数以返回余数。其结果范围为[0,number_of_primary_shards - 1]
,结果的值正好和某个分片对应。
这解释了为什么主分片的数量 只有在创建索引并且永远不会更改时才能设置:如果将来更改主分片的数量,则所有先前的路由值都将无效,并且永远不会找到文档。
所有文件的API( get
,index
,delete
,bulk
,update
和mget
)都接受一个routing
参数可用于自定义文档到分片映射。
可以使用自定义路由值来确保所有相关文档(例如,属于同一用户的所有文档)存储在同一个分片上。
出于解释目的,让我们来 想象一下,我们有一个由三个节点组成的集群。它包含一个名为的索引blogs
,它有两个主分片。每个主分片都有两个副本。
同一个分片的副本永远不会分配给同一个节点,因此我们的集群看起来像下图。
我们可以将请求发送到集群中的任何节点。 每个节点完全能够满足任何请求。
每个节点都知道集群中每个文档的位置,因此可以将请求直接转发到实际处理数据的节点。在后面的示例中,我们将发送所有请求Node 1
,我们将其称为协调节点(直接和客户端交互的节点)。
创建,索引和删除 请求是写操作,必须在主分片上成功完成,然后才能将它们复制到任何关联的副本分片,如下图所示
下面是在主分片和任何副本分片上成功创建,索引或删除文档所需的主要步骤:
客户端发送创建,索引或删除请求给Node 1
。
节点使用文档_id
来确定文档属于分片0
。它将请求转发到主分片0所在的节点Node3上。
Node 3
在主分片上执行请求。如果是成功的,它并行转发请求给Node 1
和 Node 2
。一旦所有副本分片报告成功,Node 3
向协调节点(这里是Node0)报告成功,该协调节点向客户端报告成功。
当客户端收到成功响应时,已在主分片和所有副本分片上执行文档更改。修改是安全的。
有许多可选的请求参数允许您改变此过程,可能以数据安全性为代价提高性能。
这些选项很少使用,因为Elasticsearch已经很快了,但为了完整起见,这里解释了它们:
consistency
-
默认情况下,主分片需要法定数量或大部分的分片副本(其中分片副本可以是主分片或副本分片)在尝试写入操作之前可用。这是为了防止将数据写入网络分区的“错误方”(少数派)。法定人数定义如下:
int((primary + number_of_replicas)/ 2)+ 1
允许的值
consistency
是one
(仅主要分片),all
(主要和所有副本),或默认quorum
或大多数分片副本。请注意,它
number_of_replicas
是索引设置中指定的副本数,而不是当前活动的副本数。如果您已指定索引应具有三个副本,则仲裁将如下所示:int((主要+3个复制品)/ 2)+ 1 = 3
但是,如果仅启动两个节点,则将没有足够的活动分片副本来满足仲裁,并且您将无法索引或删除任何文档。
timeout
- 如果可用的分片副本不足,会发生什么?Elasticsearch等待,希望会出现更多的分片。默认情况下,它将等待最多1分钟。如果需要,可以使用
timeout
参数让它更快地中止:100
是100毫秒,30s
是30秒。
quorum
。但是,这些默认设置会阻止我们对单节点群集执行任何有用的操作。为避免此问题,仅当number_of_replicas
大于1时才强制要求仲裁。可以从主分片或其任何副本分片检索文档,如下图所示。
以下是从主分片或副本分片检索文档的步骤:
客户端发送get请求Node 1
。
节点使用文档_id
来确定文档属于分片0
。所有三个节点上都存在分片0的副本。在这种情况下,它将请求转发给Node 2(此时理论上任何一个节点都可以处理)
。
Node 2
将文档返回到Node 1
,Node1将文档返回给客户端。
对于读取请求,协调节点将在每个请求上选择不同的分片副本以平衡负载; 它循环遍历所有分片副本。
在索引文档时,文档可能已经存在于主分片上但尚未复制到副本分片。在这种情况下,副本可能会报告文档不存在,而主副本可能会成功返回文档。索引请求将成功返回给用户后,该文档将在主分片和所有副本分片上可用。
5.文档部分更新
以下是用于对文档执行部分更新的步骤序列:
- 客户端发送更新请求到
Node 1
。 - 它将请求转发到主分片所在的位置
Node 3
。 Node 3
从主分片中检索文档,更改_source
字段中的JSON ,并尝试在主分片上重新索引文档。如果文档已被其他进程更改,则会在放弃之前重试第3步retry_on_conflict次
。- 如果
Node 3
已成功更新文档,则会将要重新编制索引的新版本的文档并行转发到副本分片Node 1
和Node 2
。所有副本分片报告成功后,Node 3
向协调节点报告成功,协调节点向客户端报告成功。
以上是关于Elasticsearch分布式文档存储的主要内容,如果未能解决你的问题,请参考以下文章
ElasticSearch探索之路分布式原理:分布式路由存储搜索原理