Elasticsearch集群脑裂问题详解

当节点崩溃或由于某种原因而导致节点之间的通信中断时,就会出现问题。如果一个从属节点无法与主节点进行通信,则它会从仍与之连接的主节点开始选举一个新的主节点。然后,该新的主节点将接管先前的主节点的职责。如果较旧的主节点重新加入群集或恢复了通信,则新的主节点会将其降级为从节点,因此不会发生冲突。在大多数情况下,此过程是无缝的,并且“有效”。

但是,请考虑只有两个节点的情况:一个主节点和一个从节点。如果两者之间的通信中断,则将从属服务器将被提升为主服务器,但是一旦恢复通信,您将拥有两个主服务器节点。原来的主节点认为从节点掉线,应该重新作为从节点,而新的主节点认为原来的主节点掉线,应该重新作为从节点。因此,据说您的集群大脑裂。

什么是裂脑?

让我们考虑一个具有两个节点的简单Elasticsearch集群。 

d1.png

集群包含一个带有一个分片和一个副本的索引。节点A在群集启动时被选为主节点,并拥有主分片(在以下架构中标记为0P),而节点B则拥有副本分片(0R)。

d2.png

如果由于某种原因两个节点之间的通信由于网络故障或仅由于其中一个节点变得无响应(例如在世界停止垃圾回收的情况下)而失败,该怎么办?

d3.png

两个节点都认为另一个已失败。节点A不会执行任何操作,因为它已被选为主节点。但是节点B会自动将自己选举为主节点,因为它认为它是不再具有主节点的群集的一部分。

d4.png

在Elasticsearch集群中,主节点负责在节点之间平均分配分片。节点B拥有一个副本分片,但它认为主分片不再可用,因此它将自动将副本分片提升为主分片。

d5.png

 

现在,我们的集群处于不一致状态或红色状态。在这种情况下,分片的两个副本已经分开,并且如果不进行完全重新索引将很难重新对齐它们。对将要命中节点A的索引请求进行索引将为其主碎片的副本中的数据编制索引,而去往节点B的请求将填充碎片的第二个副本。 

d6.png

更糟糕的是,对于不了解群集的索引客户端(例如REST接口),此群集状态将是完全透明的,因为无论每次命中哪个节点,索引请求都会成功完成。搜索数据时,裂脑问题只会变得稍微明显:根据搜索请求命中的节点,结果将有所不同。 

主节点选举

所述discovery.zen.minimum_master_nodes控制合格主节点的最小数量,一个节点应“看到”为了在集群内操作。当在集群中运行两个以上节点时,建议将其设置为大于1的值。一种计算此值的方法是N/2 + 1,其中N是主节点数。此设置必须设置为我们的主合格节点的标准个数。我们建议只有两个主合格节点,因为标准个数为两个。因此,任一主合格节点的丢失都将导致群集无法运行。

对于两个节点的群集,将minimum_master_nodes参数设置为2是不直观的,但是在这种情况下,如果一个节点发生故障,则整个群集都会发生故障。尽管这消除了发生脑裂的可能性,但它也通过使用副本碎片来消除内置的高可用性机制。

如果您刚开始使用Elasticsearch,建议您计划一个3节点集群并将其设置minimum_master_nodes为2,以限制出现脑裂问题的机会,但仍要保持高可用性优势。我们可以承受丢失已配置的副本节点的损失,但仍可以保持群集正常运行。

2节点群集提供了以下可能性:要么选择在保持高可用性的同时忍受裂脑的可能性,要么选择避免裂脑但失去高可用性。如果您确实只想使用2个节点,则仍然可以通过使用另一个Elasticsearch配置设置来防止脑裂node.data。通过在集群中的两个节点之一上简单地将其设置为false,可以有效地防止该节点成为主节点。但是,这样做还会失去任何故障转移功能,因为如果主节点出现故障,则整个集群都将发生故障。

但是,在这种情况下,最好的选择是将节点添加到群集中,并避免妥协。这听起来很激烈,但不一定如此。对于每个Elasticsearch节点,您可以通过设置node.data参数来选择该节点是否保留数据。默认值为“ true”,这意味着默认情况下,每个Elasticsearch节点也将是一个数据节点。

node.data参数设置为“ false”的第三个节点将永远不会保留任何碎片,但可以将其选为主节点。由于该第三节点将成为无数据节点,因此也可以在价格相对便宜的硬件上进行初始化。的minimum_master_nodes最终可设定为2,因为我们有一个缩放到3节点群集从2节点的群集,从而,避免了脑裂,并且仍然承受丢失的节点,而不会丢失数据。

配置Zen发现

配置该discovery.zen.minimum_master_nodes设置(默认为1)至关重要,以便每个符合主机要求的节点都知道为形成群集而必须可见的符合主机要求的最小数量。

假设您有一个包含两个主节点的节点组成的集群。网络故障会中断这两个节点之间的通信。每个节点本身都会看到一个符合主机要求的节点。用minimum_master_nodes设置为默认的1,这是足以形成群集。每个节点都将自己选举为新的主节点(认为另一个符合主节点资格的节点已经死亡),结果是两个集群或一个裂脑。在重新启动一个节点之前,这两个节点将永远不会重新加入。已写入重新启动的节点的所有数据都将丢失。

现在,假设您有一个具有三个主节点的集群,并将其minimum_master_nodes设置为2。如果网络拆分将一个节点与其他两个节点分开,则具有一个节点的一侧将看不到足够的符合主机资格的节点,并且将意识到自己无法选举为主机。具有两个节点的一侧将选举一个新的主机,并继续正常运行。解决网络拆分后,单个节点将重新加入群集,并再次开始处理请求。

此设置应设置为符合主机资格的节点的标准个数:

(master_eligible_nodes / 2)+ 1

换句话说,如果有3个符合主条件的节点,则最小主节点应设置为(3/2)+ 1或2discovery.zen.minimum_master_nodes: 2//默认为1 

也可以使用集群更新设置API在活动集群上动态更改此设置: 

卷曲-XPUT ‘ES_HOST:ES_PORT / _cluster /设置漂亮吗?’ -H ‘内容 – 类型:应用程序/ JSON的’ -d“{ “ 瞬间”:{ “discovery.zen.minimum_master_nodes” :2 } }’

在专用节点之间划分主角色和数据角色的优点是,您只能拥有3个符合主条件的节点,并将其设置minimum_master_nodes2。无论您添加到集群中有多少个专用数据节点,都无需更改此设置。

最小主节点

minimum_master_nodes设置对于群集的稳定性非常重要。此设置有助于防止大脑分裂。 

当您的大脑裂开时,您的集群就有丢失数据的危险。因为主服务器被认为是集群的最高统治者,所以它决定何时可以创建新索引,如何移动分片等等。如果您有2个主节点,则数据完整性将变得很危险,因为您有2个认为它们负责的节点。

此设置告诉Elasticsearch除非有足够的符合主机资格的节点,否则不要选择主机。只有这样才能进行选举。

此设置应始终配置为符合主资格的节点的标准个数(多数)。标准个数是(number of master-eligible nodes / 2) + 1。这里有些例子:

  • 如果您有10个常规节点(可以容纳数据,可以成为主节点),则标准个数为6。

  • 如果您有3个专用主节点和100个数据节点,则标准个数为2,因为您只需要计算符合主条件的节点。

  • 如果您有2个常规节点,那么您将处于一个难题中。标准个数为2,但这意味着节点丢失将使您的群集无法运行。设置为1将使您的集群正常运行,但是不能防止大脑分裂。在这种情况下,最好至少有3个节点。

可以在elasticsearch.yml文件中配置此设置:

发现.zen .minimum_master_nodes:2

但是,由于Elasticsearch集群是动态的,因此您可以轻松添加或删除将更改仲裁的节点。如果您不得不将新配置推送到每个节点并重新启动整个集群以更改设置,那将非常烦人。

因此,minimum_master_nodes可以通过动态API调用来配置(和其他设置),如前所述。集群在线时可以对其进行更新:

curl -XPUT 'ES_HOST:ES_PORT/_cluster/settings?pretty' -H 'Content-Type: application/json' -d '{
 "transient": {
   "discovery.zen.minimum_master_nodes": 2
 }
}'

这将成为持久设置,优先于静态配置中的设置。每当您添加或删除符合主机资格的节点时,都应修改此设置。

没有活动的主节点

discovery.zen.no_master_block设置控制在没有活动主服务器时应拒绝哪些操作。该discovery.zen.no_master_block设置有2个有效选项:

  1. all -节点上的所有操作,即读和写都将被拒绝。

  2. write-写操作将被拒绝(默认)。读取操作将根据最新的已知群集配置成功进行。

ES 的基本discovery.zen属性可以配置如下:

discovery.zen.fd.ping_timeout: 10s
discovery.zen.minimum_master_nodes: 2
discovery.zen.ping.unicast.hosts: ["master_node_01″,"master_node_02″,"master_node_03″]

上面的设置_discovery.zen.fd.ping_timeout_说节点检测应该在10秒内发生。单播主机是“ master_node_01”,“ master_node_02”,“ master_node_03”。另外,为了完成选举并使被选节点接受其主控权,需要最少2个最小主节点加入新选举的主节点。我们有3个主节点。

Elasticsearch集群节点个数

群集应具有多少个节点?这是一个难题。最终,它将归结为以下问题: 

  1. 您正在处理多少数据?

  2. 您将处理多少个搜索?

  3. 您的搜索有多复杂?

  4. 每个节点必须使用多少资源?

  5. 您将使用多少个索引/应用程序?

该问题的答案取决于许多因素,例如预期的负载,数据大小,硬件等。

mysql必须掌握的15个命令
每日一句话科技资讯 | 20200710