###################################################################################
注意:脑裂的前提是所有节点都是存活状态,若存在部分节点、部分节点没有存活,请检查其他异常!!!
ElasticSearch 脑裂(split-brain),在维护ElasticSearch集群的时候,基本都会遇到(无奈~~~)
指若干个ElasticSearch节点并未形成一个完整的集群,或者形成若干个小集群,遇到过两种情况:
1.形成多个小集群,有多个master;
2.有一个master,但是集群中节点的个数和ElasticSearch节点个数不一致;
网络:因为选举master,网络延迟导致有些节点并没有加入到集群;
负载:有一个节点master:true和data:true ,同时有被选举为master,若数据传输较大或索引较大,停顿时间长造成节点长时间没有响应,可能被其他节点认为失效,从而重新选举
1.设置一个节点,最好做第一个启动节点,一般第一个启动节点,容易被作为master(Let masters be masters)
master:true
data:false
这样做的好处是:让master节点只负责master节点的职责,其他的查询、索引都使用data节点。
2.ElasticSerch 2.x后在Discovery 模块已经不再推荐使用 multicast,只用unicast(Using Unicast over Multicast)
node1,node2 表示master标记为true,可能选举为master的节点
discovery.zen.ping.unicast.hosts: ["node1", "node2"]
3.提高节点的响应时间(Default Ping timeout)
discovery.zen.ping_timeout: 5(默认值是3秒)
4.ping超时重试次数,默认3次(Default Ping Retry)
discovery.zen.fd.ping_retries: 3
5.一个节点多久ping一次,默认1s(Default Ping Interval)
discovery.zen.fd.ping_interval: 1s
6.官方给出建议:
文档ElasticSearch6.5 Discover Settings(Minimum master nodes)
discovery.zen.minimum_master_nodes:M/2+1(M:表示设置为master的节点个数)
master-eligible_node—— A node that has
node.master
set totrue
(default), which makes it eligible to be elected as the masternode, which controls the cluster。"A more detailed explanation is provided in Avoiding split brain with
minimum_master_nodes
To avoid a split brain, this setting should be set to a quorum of master-eligible nodes:
(master_eligible_nodes / 2) + 1
In other words, if there are three master-eligible nodes, then minimum master nodes should be set to
(3 / 2) + 1
or2
:discovery.zen.minimum_master_nodes: 2(向上取整数)"
7. No master block
对于一个具有全功能的ES节点,必须要有一个活动的Master节点。当集群没有Master时,有一个阻塞集群操作设置:discovery.zen.no_master_block: write(默认值)
当集群中没有活动的Master节点后,该设置指定了哪些操作(read、write)需要被拒绝(即阻塞执行)。
有两个设置值:all和write,默认为wirte。
这项配置不会对基本api(例如集群状态、节点信息和状态API)产生影响,这些节点在任何节点上执行都不会被阻塞。
脑裂(split-brain)也不能完全禁止,ElasticSearch使用自己的选择机制选举master,而不是和Zookeeper等其他第三方框架做集成。
集群脑裂发生后,需要的是恢复。此时,重启集群是十分危险的。当elasticsearch 集群启动时, 会选出一个主节点( 一般是启动的第一个节点被选为主) 。 由于索引的两份拷贝已经不一样了, elasticsearch 会认为选出来的主保留的分片是“主拷贝”并将这份拷贝推送给集群中的其他节点。 这很严重。 让我们设想下你是用的是 node 客户端并且一个节点保留了索引中的正确数据。 但如果是另外的一个节点先启动并被选为主, 它会将一份过期的索引数据推送给另一个节点, 覆盖它, 导致丢失了有效数据。
所以怎么从脑裂中恢复?
第一个 :建议是给所有数据重新索引。
第二个 :如果脑裂发生了, 要十分小心的重启你的集群。 停掉所有节点并决定哪一个节点第一个启动。
(1)如果需要, 单独启动每个节点并分析它保存的数据;
(2) 如果不是有效的, 关掉它, 并删除它数据目录的内容( 删前先做个备份) ;
(3)如果你找到了你想要保存数据的节点, 启动它并且检查日志确保它被选为主节点;
之后,可以安全的启动你集群里的其他节点了。
参考:
how-to-avoid-the-split-brain-problem-in-elasticsearch
Elasticsearch原理(五):Master机制及脑裂分析
[译]elasticsearch发生脑裂时JAVA客户端的行为
Analytics split-brain-From IBM