corosync qnet挂死场景分析解决
qnet挂死场景的矛盾点:
- 网络分区依靠qnet来进行判断,当qnet挂死时,集群无法处理网络分区,此时发生网络分区不提供服务
- 当qnet恢复后,qnet选择出来的多数派分区有可能和之前的多数派分区不一致(或者说选出来的多数派分区有可能不包含上一次提供服务的节点)
记录下上一次提供服务的节点数量,当网络分区时,继续提供服务的分区节点数量会发生改变,而未继续服务的分区节点数量不会改变,因而可以使用本次投票时的节点数量与上一次提供服务时的节点数量进行比较来判断分区是否是上次提供服务的分区。
- 若节点数量减少,则不是上一次提供服务的分区,无法提供服务
- 若节点数量不变或者增多,则是上一次提供服务的分区,可以提供服务
- 若节点数量不变,说明分区未发生变化,可以继续提供服务
- 若节点数量增大,说明分区内有新节点加入,可以继续提供服务
三节点集群qnet挂死恢复情况分析
qnet挂死后只有所有节点都存活时才能写入数据。
根据网络分区情况,可以有以下几种组合,以A、B、C三个节点为例说明:
-
qnet挂死前未发生网络分区,挂死过程中也未发生网络分区
qnet挂死前与恢复后网络状态一致,可以根据选举规则提供服务。
A的状态变更:
1->0(qnet挂死)->1(qnet恢复获取到投票)
A的节点数变更:
3->3->3
A的当前节点数变更:
3->3->3
B的状态变更:
1->0(qnet挂死)->1(qnet恢复获取到投票)
B的节点数变更:
3->3->3
B的当前节点数变更:
3->3->3
C的状态变更:
1->0(qnet挂死)->1(qnet恢复获取到投票)
C的节点数变更:
3->3->3
C的当前节点数变更:
3->3->3qnet恢复后节点数未减少,可以提供服务
-
qnet挂死前未发生网络分区,挂死过程中发生网络分区
挂死过程中发生网络分区,数据无法写入,qnet恢复后识别分区,可以根据选举规则提供服务。
A的状态变更:
1->0(qnet挂死)->0(C节点分区)->1(qnet恢复获取到投票)
A的节点数变更:
3->3->3->3
A的当前节点数变更:
3->3->2->2
B的状态变更:
1->0(qnet挂死)->0(C节点分区)->1(qnet恢复获取到投票)
B的节点数变更:
3->3->3->3
B的当前节点数变更:
3->3->2->2
C的状态变更:
1->0(qnet挂死)->0(C节点分区)->0(qnet恢复获取到投票)
C的节点数变更:
3->3->3->3
C的当前节点数变更:
3->3->1->1无论哪个分区获得投票,节点数都变少,无法提供服务。
-
qnet挂死前发生网络分区,挂死过程中未发生网络分区
qnet挂死前发生网络分区,则qnet挂死前已经识别出分区,qnet挂死后无法提供服务,当qnet恢复时还是根据相同的规则识别网络分区,可以根据选举规则提供服务。
上一次提供服务的分区获取到投票可以继续提供服务:
A的状态变更:
1->1(C节点分区)->0(qnet挂死)->1(qnet恢复获取到投票)
A的节点数变更:
3->2->2->2
A的当前节点数变更:
3->2->2->2
B的状态变更:
1->1(C节点分区)->0(qnet挂死)->1(qnet恢复获取到投票)
B的节点数变更:
3->2->2->2
B的当前节点数变更:
3->2->2->2
C的状态变更:
1->0(C节点分区)->0(qnet挂死)->0(qnet恢复未获取到投票)
C的节点数变更:
3->3->3—>3
C的当前节点数变更:
3->1->1->1上一次提供服务的分区未获取到投票不可以继续提供服务:
A的状态变更:
1->1(C节点分区)->0(qnet挂死)->0(qnet恢复未获取到投票)
A的节点数变更:
3->2->2->2
A的当前节点数变更:
3->2->2->2
B的状态变更:
1->1(C节点分区)->0(qnet挂死)->0(qnet恢复未获取到投票)
B的节点数变更:
3->2->2->2
B的当前节点数变更:
3->2->2->2
C的状态变更:
1->0(C节点分区)->0(qnet挂死)->1(qnet恢复获取到投票)
C的节点数变更:
3->3->3—>3
C的当前节点数变更:
3->1->1->1qnet恢复后1节点分区获取到投票,但其节点数量减少,无法提供服务。
-
qnet挂死前发生网络分区,挂死过程中发生网络分区
A的状态变更:
1->1(C节点分区)->0(qnet挂死)->0(B节点分区)->1(qnet恢复获取到投票)
A的节点数变更:
3->2->2->2->2
A的当前节点数变更:
3->2->2->2->1
B的状态变更:
1->1(C节点分区)->0(qnet挂死)->0(B节点分区)->0(qnet恢复获取到投票)
B的节点数变更:
3->2->2->2->2
B的当前节点数变更:
3->2->2->2->1
C的状态变更:
1->0(C节点分区)->0(qnet挂死)->0(qnet恢复未获取到投票)
C的节点数变更:
3->3->3—>3->3
C的当前节点数变更:
3->1->1->1->1此时A节点分区虽然获取到qnet投票,但其节点数量减少,无法获取到投票。
特别的,C分区后,B再分区,并且C重新回来,可以提供服务。
A的状态变更:
1->1(C节点分区)->0(qnet挂死)->0(B节点分区)->0(C节点重新回来)->1(qnet恢复获取到投票)
A的节点数变更:
3->2->2->2->2->2
A的当前节点数变更:
3->2->2->1->2->2
B的状态变更:
1->1(C节点分区)->0(qnet挂死)->0(B节点分区)->0(qnet恢复获取到投票)
B的节点数变更:
3->2->2->2->2
B的当前节点数变更:
3->2->2->1->1
C的状态变更:
1->0(C节点分区)->0(qnet挂死)->0(C节点重新回来)->0(qnet恢复未获取到投票)
C的节点数变更:
3->3->3—>3->3
C的当前节点数变更:
3->1->1->2->2此时AC分区重新获得quorate,且因为A分区节点数量未减少可以继续提供服务。
qnet挂死前网络分区判断
节点本身无法判断qnet是否挂死,只能感知到是否获取qnet投票,则无法获取到投票,则有两种情况:
- 网络分区
- qnet挂死
n节点集群
n个节点集群,分死种情况讨论:(挂死也认为是网络分区,挂死节点单独一个分区)
-
qnet挂死前未发生网络分区
-
qnet挂死过程中未发生网络分区
-
qnet挂死过程中发生网络分区
-
-
qnet挂死前发生网络分区
- qnet挂死过程中未发生网络分区
- qnet挂死过程中发生网络分区
qnet挂死前未发生网络分区,挂死过程中也未发生网络分区
假设挂死前为n个节点,挂死后仍为n个节点,集群可以提供服务。
如集群有3个节点,qnet挂死后恢复仍为3个节点,集群可以提供服务;
特别的,集群挂死前网络分区,2节点分区获得quorate并提供服务,qnet挂死后恢复2节点分区继续获得quorate,可以继续提供服务;
特别的,集群挂死前网络分区,2节点分区获得quorate并提供服务,qnet挂死后恢复1节点分区获得quorate,节点个数减少无法提供服务;
qnet挂死前未发生网络分区,挂死过程中发生网络分区
假设挂死前为n个节点,挂死后为n-1个节点,集群不可以提供服务。
如3节点集群,qnet挂死前为3个节点,qnet挂死后网络分区(2节点和1节点),qnet恢复后2节点分区获得quorate,无法提供服务。
qnet挂死前发生网络分区,挂死过程中未发生网络分区
假设挂死前为n-1个节点,挂死后仍为n-1个节点,集群可以提供服务。
qnet挂死前发生网络分区时可以继续提供服务,其场景与qnet挂死前未发生网络分区,挂死过程中也未发生网络分区一致。
qnet挂死前发生网络分区,挂死过程发生网络分区
假设挂死前为n个节点,挂死前分为m个分区,其中p分区获得quorate,此时p分区节点个数为q,其他分区的节点个数仍为n;
qnet恢复后,若p分区获得quorate,且p分区节点个数不变或者增加,则集群可以提供服务;
qnet恢复后,若其他分区获得quorate,则其他分区节点数一定减少,则集群不可以提供服务;
qnet挂死前发生网络分区时可以继续提供服务,其场景与qnet挂死前未发生网络分区,挂死过程中发生网络分区一致。
qnet恢复后节点数量减少情况分析
A、B、C三个节点
qnet挂死前,A在提供服务。
qnet挂死后,A也挂死,此时B获得qnet的投票,B无法提供服务。