MHA-Failover(GTID,Auto_Position=0)
最近一位同学遇到的案例:凌晨数据库意外宕机,要求在一主两从的基础上,搭建MHA做故障切换。在部署测试中遇到一些问题找到我,交流的过程挖出一些之前忽略的坑,感谢这位同学无私分享!
• GTID环境,KILL主库,新主库和从库丢失数据(之前已知)
• 在数据库进程挂掉、数据库服务器关机或重启、开启防火墙、关闭网络服务等状况下,测试MHA是否正常切换(之前没考虑脑裂问题)
• 线上部分环境GTID,Auto_Position=0,故障切换会变成GTID,Auto_Position=1(之前没考虑)
• 梳理故障切换流程(之前梳理)
一、GTID环境,KILL主库,新主库和从库丢失数据
需在配置文件将Master/Binlog Server配置到[binlogN],才能补全Dead Master上的差异数据,否则只应用到Latest Slave
发散:[binlogN]指定到Binlog Server,kill -9 master_mysqld,MHA是从Binlog Server上获取还是从Dead Master上获取差异binlog?
指定到Binlog Server就从Binlog Server上获取,指定到Dead Master就到Dead Master获取;如果没有指定,就不会补全差异数据
二、MHA切换测试
在数据库进程挂掉,数据库服务器关机或重启、开启防火墙、关闭网络服务等状况下,测试MHA是否正常切换
MySQL5.7.21,基于Row+Gtid搭建的一主两从复制结构:Master132->{Slave133、Slave134};VIP在132上,mha-manager 0.56在134上
测试场景 | XX.132 | XX.133 | XX.134 | 说明 |
132:kill -9 mysqld | 不可用 | 主 | 从 | MHA正常切换,数据不丢失 |
132:关闭或重启132服务器 | 不可用 | 主 | 从 | MHA正常切换,数据可能丢失 |
134:iptables -I INPUT -s XX.132 -j DROP | 可用 | 主 | 从 | MHA正常切换,原主库正常访问,133成为新主库,132和133同时存在VIP |
132:service network stop/ifconfig eth0 down | 不可用 | 主 | 从 | MHA正常切换,数据可能丢失 |
注:上述表格是配置[binlogN]指定到Binlog Server,没有指定secondary_check_script的测试结果
关闭数据库服务器,数据可能丢失的原因:Binlog Server是异步,高并发下binlog延迟可以理解
开启防火墙,模拟主库与mha-manager不通讯,出现脑裂。配置文件添加"secondary_check_script=masterha_secondary_check -s remote_host1 -s remote_host2",remote_host1、remote_host2尽量与mha-manager、MySQL Server处于不同网段
三、GTID,Auto_Position=0,故障切换变成GTID,Auto_Position=1
3.1、Auto_Position
线上部分环境GTID,Auto_Position=0,故障切换会变成GTID,Auto_Position=1
• 有何风险
如果S1从库的GTIDs存在空洞,S2从库的GTIDs正常,随着时间推移,S2将S1上GTIDs空洞对应的binlog删除。此时发生故障切换,且选择S2做为新Master,在S1 change master to S2 master_auto_position=1会报错
Got fatal error 1236 from master when reading data from binary log: 'The slave is connecting using CHANGE MASTER TO MASTER_AUTO_POSITION = 1, but the master has purged binary logs containing GTIDs that the slave requires.'
从库存在GTIDs空洞可能会导致切换异常:VIP正常切换,新主可用,新从到新主之间的复制报错,只有修复主从报错,才会做后续操作(new master cleanup、Failover Report、send mail)
• 为何不直接修改为GTID,Auto_Position=1
Slave GTIDs<Master GTIDs,如果Diff GTIDs对应的binlog在Master已被purge,修改为Auto_Position=1会继续报错
Slave GTIDs>Master GTIDs,5.7下主从直接报错
• 如何解决
修改源码~~~
shell> vim /usr/share/perl5/vendor_perl/MHA/ServerManager.pm 1550 return 1 if ( $_->{use_gtid_auto_pos} ); -->修改为 1550 #return 1 if ( $_->{use_gtid_auto_pos} ); shell> vim /usr/share/perl5/vendor_perl/MHA/MasterMonitor.pm 367 if ( !$_server_manager->is_gtid_auto_pos_enabled() ) { 368 $log->info("GTID (with auto-pos) is not supported"); -->修改为 367 if ( $_server_manager->is_gtid_auto_pos_enabled() !=1 ) { 368 $log->info("GTID (with auto-pos) is not supported");