MySQL高可用搭建方案之(MHA)
有的时候博客内容会有变动,首发博客是最新的,其他博客地址可能会未同步,认准
https://blog.zysicyj.top
MHA架构介绍
MHA是Master High
Availability的缩写,它是目前MySQL高可用方面的一个相对成熟的解决方案,其核心是使用perl语言编写的一组脚本,是一套优秀的作为MySQL高可用性环境下故障切换和主从提升的高可用软件。在MySQL故障切换过程中,MHA能做到在0~
30秒之内自动完成数据库的故障切换操作,并且能在最大程度上保证数据的一致性,以达到真正意义上的高可用。
基于MHA的架构不像MMM那样需要搭建主主复制,只需要搭建基本的主从复制架构即可。因为MHA在主库挂掉时,是在多个从库中选取出一个从库作为新的主库。MHA集群中的各节点彼此之间均需要基于ssh
互信通信,以实现远程控制及数据管理功能。
MHA提供了什么功能:
- 可以监控Master节点是否可用
- 当Master不可用时,能在多个Slave中选举出新的Master
- 提供了主从切换和故障转移功能,MHA会尝试在宕机的Master上保存binlog,在最大程度上保证事务不丢失。但如果是Master所在的服务器已经无法访问,或硬件层面出现了问题,则无法成功保存binlog
- MHA可以与半同步复制结合,避免从库之间出现数据不一致的情况
- 支持MySQL基于GTID和基于日志点的两种复制方式
MHA故障转移过程:
- 尝试使用
ssh登录到宕机崩溃的Master节点上保存二进制日志事件(binlog events); - 从多个Slave中识别含有最新更新的Slave,将其作为备选的Master;
- 然后基于该Slave同步差异的中继日志(relaylog)到其他的Slave上;
- 接着同步从原Master上保存的二进制日志事件(binlog events);
- 将备选的Master提升为新的Master;
- 使其他的Slave连接新的Master进行复制;
- 在新的Master启动vip地址,保证前端请求可以发送到新的Master。
MHA的架构图如下:

动手搭建MHA架构
本文中所使用的机器说明:
| 名称 | IP | 角色 |
|---|---|---|
| master | 192.168.190.151 | 主库 |
| slave-01 | 192.168.190.152 | 从库 |
| slave-02 | 192.168.190.154 | 从库 |
| manager | 192.168.190.153 | 集群管理节点(MHA) |
环境版本说明:
- 操作系统版本:CentOS 7
- MySQL版本:8.0.19
- MHA版本:0.58
另外的说明:
- 会来了解MMM架构的小伙伴们想必都已经掌握了MySQL的安装方式,而且介绍MySQL的安装
也有很多文章,所以本文为了减少不必要的篇幅就不演示MySQL的安装了,文中所用到的机器都已经提前安装好了MySQL。
配置主从节点的配置文件
1、在所有主从节点上使用如下语句创建用于主从复制的MySQL用户,因为每个从库都有可能会被选举为主库,所以都需要拥有用于复制的用户:
create user 'repl'@'%' identified with mysql_native_password by 'Abc_123456';
grant replication slave on *.* to 'repl'@'%';
flush privileges;
2、然后修改master节点上的MySQL配置文件:
[root@master ~]# vim /etc/my.cnf
[mysqld]
# 设置当前节点的id
server_id=101
# 开启binlog,并指定binlog文件的名称
log_bin=mysql_bin
# 开启relay_log,并指定relay_log文件的名称
relay_log=relay_bin
# 将relaylog的同步内容记录到binlog中
log_slave_updates=on
# 开启GTID复制模式
gtid_mode=ON
enforce_gtid_consistency=1
3、在slave-01的配置文件中也是添加一样配置,只不过server_id不一样:
[root@slave-01 ~]# vim /etc/my.cnf
[mysqld]
server_id=102
log_bin=mysql_bin
relay_log=relay_bin
log_slave_updates=on
gtid_mode=ON
enforce_gtid_consistency=1
4、接着是配置slave-02:
[root@slave-02 ~]# vim /etc/my.cnf
[mysqld]
server_id=103
log_bin=mysql_bin
relay_log=relay_bin
log_slave_updates=on
gtid_mode=ON
enforce_gtid_consistency=1
完成以上配置文件的修改后,分别重启这三个节点上的MySQL服务:
[root@master ~]# systemctl restart mysqld
[root@slave-01 ~]# systemctl restart mysqld
[root@slave-02 ~]# systemctl restart mysqld
配置slave-01对master的主从关系
mysql> stop slave; -- 停止主从同步
mysql> change master to master_host='192.168.190.151', master_port=3306, master_user='repl', master_password='Abc_123456', master_auto_position=1; -- 配置master节点的连接信息
mysql> start slave; -- 启动主从同
-----------------------------------
著作权归作者所有:来自51CTO博客作者ZeroOne01的原创作品,请联系作者获取转载授权,否则将追究法律责任
基于MHA搭建MySQL Replication集群高可用架构
https://blog.51cto.com/zero01/2468767
进入slave-01节点的MySQL命令行终端,分别执行如下语句来配置主从复制链路:
配置完主从复制链路后,使用show slave status\G;语句查看主从同步状态,Slave_IO_Running和Slave_SQL_Running的值均为Yes
才能表示主从同步状态是正常的:

配置slave-02对master的主从关系
mysql> stop slave; -- 停止主从同步
mysql> change master to master_host='192.168.190.151', master_port=3306, master_user='repl', master_password='Abc_123456', master_auto_position=1; -- 配置master节点的连接信息
mysql> start slave; -- 启动主从同步
同样的步骤,进入slave-02节点的MySQL命令行终端,分别执行如下语句来配置主从复制链路:
配置完主从复制链路后,使用show slave status\G;语句查看主从同步状态,Slave_IO_Running和Slave_SQL_Running的值均为Yes
才能表示主从同步状态是正常的:

配置ssh免密登录
配置集群内所有主机之间能够通过ssh免密登录,因为MHA是基于ssh去实现远程控制及数据管理的。例如,故障转移过程中保存原Master节点的二进制日志以及配置虚拟IP等。
1、生成ssh登录密钥:
[root@master ~]# ssh-keygen
Generating public/private rsa key pair.
Enter file in which to save the key (/root/.ssh/id_rsa):
Enter passphrase (empty for no passphrase):
Enter same passphrase again:
Your identification has been saved in /root/.ssh/id_rsa.
Your public key has been saved in /root/.ssh/id_rsa.pub.
The key fingerprint is:
SHA256:LzRXziRQPrqaKEteH6KrZpCiV6uGP6GTi6RonE7Hhms root@master
The key's randomart image is:
+---[RSA 2048]----+
| ... |
| o |
| + o |
| . B |
| . S . o |
|+ + . . = |
|=Bo*o.. o . |
|%EOo.+ + . |
|%XB*. + |
+----[SHA256]-----+
2、将密钥拷贝到其他服务器上:
[root@master ~]# ssh-copy-id -i /root/.ssh/id_rsa root@192.168.190.151
[root@master ~]# ssh-copy-id -i /root/.ssh/id_rsa root@192.168.190.152
[root@master ~]# ssh-copy-id -i /root/.ssh/id_rsa root@192.168.190.154
[root@master ~]# ssh-copy-id -i /root/.ssh/id_rsa root@192.168.190.153
然后到集群中其他节点上进行同样的操作,由于是重复的操作这里就不演示了。最后简单测试下能否正常免密登录即可:
[root@master ~]# ssh root@192.168.190.152
Last failed login: Sat Feb 1 15:29:38 CST 2020 from 192.168.190.151 on ssh:notty
There was 1 failed login attempt since the last successful login. # 没有要求输入密码,测试成功
Last login: Sat Feb 1 14:14:03 2020 from 192.168.190.1
[root@slave-01 ~]#
安装MHA软件包
1、首先在所有的节点上安装mha4mysql-node软件包,安装包可到如下地址进行下载:
下载好的rpm文件如下:
[root@master ~]# ls *.rpm
mha4mysql-node-0.58-0.el7.centos.noarch.rpm
[root@master ~]#
在安装该rpm包之前需要先安装perl相关依赖:
[root@master ~]# yum -y install epel-release
[root@master ~]# yum -y install perl-DBD-MySQL perl-DBI ncftp
现在就可以安装mha4mysql-node了,命令如下:
- **Tips:**另外的两个Slave节点和监控节点按如上步骤安装即可,这里就不重复演示了
2、接着是在监控节点manager上安装mha4mysql-manager软件包,安装包到如下地址进行下载:
[root@master ~]# rpm -ivh mha4mysql-node-0.58-0.el7.centos.noarch.rpm
下载好的rpm文件如下:
[root@manager ~]# ls *.rpm
mha4mysql-manager-0.58-0.el7.centos.noarch.rpm
[root@manager ~]#
同样,在安装该rpm包之前需要先安装perl相关依赖:
[root@manager ~]# yum -y install epel-release
[root@manager ~]# yum -y install perl-Config-Tiny perl-Time-HiRes perl-Parallel-ForkManager perl-Log-Dispatch perl-DBD-MySQL ncftp
然后安装mha4mysql-manager包,命令如下:
[root@manager ~]# rpm -ivh mha4mysql-manager-0.58-0.el7.centos.noarch.rpm
配置MHA管理节点
1、创建MHA的配置文件存放目录和工作目录:
[root@manager ~]# mkdir /etc/mha
[root@manager ~]# mkdir /home/mysql_mha
2、创建MHA的配置文件,并添加如下内容:
[root@manager ~]# vim /etc/mha/mysql_mha.cnf
[server default]
# mha用于访问数据库的账户和密码
user=mha
password=Abc_123456
# 指定mha的工作目录
manager_workdir=/home/mysql_mha
# mha日志文件的存放路径
manager_log=/home/mysql_mha/manager.log
# 指定mha在远程节点上的工作目录
remote_workdir=/home/mysql_mha
# 可以使用ssh登录的用户
ssh_user=root
# 用于主从复制的MySQL用户和密码
repl_user=repl
repl_password=Abc_123456
# 指定间隔多少秒检测一次
ping_interval=1
# 指定master节点存放binlog日志文件的目录
master_binlog_dir=/var/lib/mysql
# 指定一个脚本,该脚本实现了在主从切换之后,将虚拟IP漂移到新的Master上
master_ip_failover_script=/usr/bin/master_ip_failover
# 指定用于二次检查节点状态的脚本
secondary_check_script=/usr/bin/masterha_secondary_check -s 192.168.190.151 -s 192.168.190.152 -s 192.168.190.154
# 配置集群中的节点信息
[server1]
hostname=192.168.190.151
# 指定该节点可以参与Master选举
candidate_master=1
[server2]
hostname=192.168.190.152
candidate_master=1
[server3]
hostname=192.168.190.154
# 指定该节点不能参与Master选举
no_master=1
3、编写配置文件中所配置的master_ip_failover脚本,该脚本是根据MHA的官方示例修改的,MHA默认并没有提供。需要注意脚本中的几处地方需要根据实际情况进行修改,已用注释标明:
[root@manager ~]# vim /usr/bin/master_ip_failover
#!/usr/bin/env perl
use strict;
use warnings FATAL => 'all';
use Getopt::Long;
my (
$command, $orig_master_host, $orig_master_ip,$ssh_user,
$orig_master_port, $new_master_host, $new_master_ip,$new_master_port,
$orig_master_ssh_port,$new_master_ssh_port,$new_master_user,$new_master_password
);
# 这里定义的虚拟IP可以根据实际情况进行修改
my $vip = '192.168.190.80/24';
my $key = '1';
# 这里的网卡名称 “ens32” 需要根据你机器的网卡名称进行修改
my $ssh_start_vip = "sudo /sbin/ifconfig ens32:$key $vip";
my $ssh_stop_vip = "sudo /sbin/ifconfig ens32:$key down";
my $ssh_Bcast_arp= "sudo /sbin/arping -I bond0 -c 3 -A $vip";
GetOptions(
'command=s' => \$command,
'ssh_user=s' => \$ssh_user,
'orig_master_host=s' => \$orig_master_host,
'orig_master_ip=s' => \$orig_master_ip,
'orig_master_port=i' => \$orig_master_port,
'orig_master_ssh_port=i' => \$orig_master_ssh_port,
'new_master_host=s' => \$new_master_host,
'new_master_ip=s' => \$new_master_ip,
'new_master_port=i' => \$new_master_port,
'new_master_ssh_port' => \$new_master_ssh_port,
'new_master_user' => \$new_master_user,
'new_master_password' => \$new_master_password
);
exit &main();
sub main {
$ssh_user = defined $ssh_user ? $ssh_user : 'root';
print "\n\nIN SCRIPT TEST====$ssh_user|$ssh_stop_vip==$ssh_user|$ssh_start_vip===\n\n";
if ( $command eq "stop" || $command eq "stopssh" ) {
my $exit_code = 1;
eval {
print "Disabling the VIP on old master: $orig_master_host \n";
&stop_vip();
$exit_code = 0;
};
if ($@) {
warn "Got Error: $@\n";
exit $exit_code;
}
exit $exit_code;
}
elsif ( $command eq "start" ) {
my $exit_code = 10;
eval {
print "Enabling the VIP - $vip on the new master - $new_master_host \n";
&start_vip();
&start_arp();
$exit_code = 0;
};
if ($@) {
warn $@;
exit $exit_code;
}
exit $exit_code;
}
elsif ( $command eq "status" ) {
print "Checking the Status of the script.. OK \n";
exit 0;
}
else {
&usage();
exit 1;
}
}
sub start_vip() {
`ssh $ssh_user\@$new_master_host \" $ssh_start_vip \"`;
}
sub stop_vip() {
`ssh $ssh_user\@$orig_master_host \" $ssh_stop_vip \"`;
}
sub start_arp() {
`ssh $ssh_user\@$new_master_host \" $ssh_Bcast_arp \"`;
}
sub usage {
print
"Usage: master_ip_failover --command=start|stop|stopssh|status --ssh_user=user --orig_master_host=host --orig_master_ip=ip --orig_master_port=port --new_master_host=host --new_master_ip=ip --new_master_port=port\n";
}
还需要给该脚本添加可执行权限,否则MHA是无法调用的:
[root@manager ~]# chmod a+x /usr/bin/master_ip_failover
4、根据配置文件中remote_workdir的配置,需在其他节点上创建MHA的远程工作目录:
[root@master ~]# mkdir /home/mysql_mha
[root@slave-01 ~]# mkdir /home/mysql_mha
[root@slave-02 ~]# mkdir /home/mysql_mha
5、在配置文件中指定了让manager使用mha这个用户来访问数据库节点,所以需要在master节点上创建mha用户:
create user 'mha'@'%' identified with mysql_native_password by 'Abc_123456';
grant all privileges on *.* to 'mha'@'%';
flush privileges;
6、完成以上所有步骤后,在manager节点上使用masterha_check_ssh和masterha_check_repl
对配置进行检查,其中masterha_check_ssh用于检查ssh登录是否正常,而masterha_check_repl则用于检查主从节点的复制链路是否正常:
[root@manager ~]# masterha_check_ssh --conf=/etc/mha/mysql_mha.cnf
[root@manager ~]# masterha_check_repl --conf=/etc/mha/mysql_mha.cnf
执行结果如下:


7、以上检测都通过后,就可以启动MHA服务了。启动命令如下:
[root@manager ~]# nohup masterha_manager --conf=/etc/mha/mysql_mha.cnf &
启动完成后,可以使用ps命令查看masterha_manager进程是否存在,如下存在则代表启动成功:
[root@manager ~]# ps aux |grep masterha_manager
root 2842 0.3 1.1 299648 22032 pts/0 S 18:30 0:00 perl /usr/bin/masterha_manager --conf=/etc/mha/mysql_mha.cnf
root 2901 0.0 0.0 112728 976 pts/0 R+ 18:31 0:00 grep --color=auto masterha_manager
[root@manager ~]#
8、最后我们需要到master节点上,手动去配置虚拟IP。因为MHA只会在主从切换时漂移虚拟IP到新的Master节点,而不会在第一次启动时主动去设置Master的虚拟IP,所以我们需要手动设置。设置虚拟IP的命令如下:
[root@master ~]# ifconfig ens32:1 192.168.190.80/24
设置成功后,使用ip addr命令可以看到网卡上绑定的虚拟IP:

测试MHA服务
到此为止,我们就已经完成了MHA高可用架构的搭建,接下来我们对其进行一些简单的测试。例如,测试下是否能正常ping
通虚拟IP,毕竟应用端访问数据库时连接的是虚拟IP,所以首先得确保虚拟IP是能够被访问的。如下:

能ping通之后,使用Navicat等远程连接工具测试下能否正常通过虚拟IP连接上数据库:

确定了虚拟IP能正常访问后,接着测试MHA是否能够正常进行主从切换,首先将master节点上的MySQL服务给停掉,模拟Master宕机:
[root@master ~]# systemctl stop mysqld
正常情况下,此时master节点上的网卡就不会再绑定该虚拟IP:

而是会被MHA漂移到slave-01节点的网卡上,因为此时该Slave就是新的Master:

接着进入slave-02节点上的MySQL命令行终端,确认下该Slave是否已经正常与新的Master进行同步。之前我们配置slave-02
的主库是master,现在将master停掉后,可以看到slave-02的Master_Host已经被MHA切换成了slave-01的IP:

经过以上测试后,可以看到我们搭建的MHA架构是能够正常运行的,已经使得Replication集群拥有了基本的高可用能力,即便Master下线后也能正常从Slave中选举新的Master并进行切换,也正确建立了其他Slave与新Master的复制链路。
MHA架构优缺点
优点:
- 使用Perl脚本语言开发并且完全开源,开发者可以根据自己的需求进行二次开发
- 能够支持基于GTID和基于日志点的复制模式
- MHA在进行故障转移时更不易产生数据丢失
- 在一个监控节点上可以监控多个Replication集群
缺点:
- MHA默认不提供虚拟IP功能,需要自行编写脚本或利用第三方工具来实现虚拟IP的配置
- MHA启动后只会对Master进行监控,不会对Slave进行监控,也无法监控复制链路的情况
- 集群环境需要能够通过
ssh免密登录,存在一定的安全隐患 - MHA没有提供对Slave的读负载均衡功能,需要通过第三方工具来实现
本文由mdnice多平台发布
MySQL高可用搭建方案之(MHA)的更多相关文章
- MySQL高可用架构之基于MHA的搭建
一.MySQL MHA架构介绍: MHA(Master High Availability)目前在MySQL高可用方面是一个相对成熟的解决方案,它由日本DeNA公司youshimaton(现就职于Fa ...
- 优酷土豆资深工程师:MySQL高可用之MaxScale与MHA
本文根据DBAplus社群第67期线上分享整理而成 本次分享主要包括以下内容: 1.MySQL高可用方案 2.为什么选择MHA 3.读写分离方案的寻找以及为什么选择Maxscale 一.MySQL ...
- MYSQL高可用集群架构-MHA架构
1 MHA简介:MHA(Master High Availability)目前在MySQL高可用方面是一个相对成熟的解决方案,它由日本DeNA公司youshimaton(现就职于Facebook公司 ...
- mysql高可用研究(一) 主从+MHA架构 (转)
最近在研究mysql的高可用架构,自己想总结下常用的高可用方案都有哪些.有哪些优缺点以及应用的场景?搞得是头昏脑涨,天昏地暗,看了诸多资料,每次都觉得公说公有理婆说婆有理.其实嘛,大家说的都有一定的道 ...
- mysql高可用研究(一) 主从+MHA架构
最近在研究mysql的高可用架构,自己想总结下常用的高可用方案都有哪些.有哪些优缺点以及应用的场景?搞得是头昏脑涨,天昏地暗,看了诸多资料,每次都觉得公说公有理婆说婆有理.其实嘛,大家说的都有一定的道 ...
- MySQL高可用架构-MMM、MHA、MGR、PXC
主从复制如何工作 在主库把数据记录到binlog(二进制日志). 备库开IO线程把binlog复制到自己的relaylog(中继日志). 备库读取中继日志,重放到备库上. 半同步复制 半同步复制可以确 ...
- MySQL高可用架构-MMM、MHA、MGR、分库分表
总结 MMM是是Perl语言开发的用于管理MySQL主主同步架构的工具包.主要作用:管理MySQL的主主复制拓扑,在主服务器失效时,进行主备切换和故障转移. MMM缺点:故障切换可能会丢事务(主备使用 ...
- mysql高可用架构方案之二(keepalived+lvs+读写分离+负载均衡)
mysql主从复制与lvs+keepalived实现负载高可用 文件夹 1.前言 4 2.原理 4 2.1.概要介绍 4 2.2.工作原理 4 2.3.实际作用 4 3方 ...
- mysql高可用研究(二) 主从+MHA+Atlas
关于Atlas的详细介绍请访问:https://github.com/Qihoo360/Atlas/blob/master/README_ZH.md 为什么要使用Atlas?应用程序直连数据库不好吗? ...
- mysql高可用架构方案之中的一个(keepalived+主主双活)
Mysql双主双活+keepalived实现高可用 文件夹 1.前言... 4 2.方案... 4 2.1.环境及软件... 4 2.2.IP规划... 4 2.3.架构图... ...
随机推荐
- 使用cgroup控制内存
关键文件 memory.limit_in_bytes memory.soft_limit_in_bytes memory.memsw.limit_in_bytes tasks cgroup.procs ...
- 单位换算详解:bit、Byte、bps、Bps、pps、Gbps的单位详细说明及换算
当谈论计算机存储和数据传输时,"bit"(比特)和"Byte"(字节)是两个常见的术语,它们具有不同的含义和用途. 位(bit):"位"来自 ...
- electron入门之通知Notification(二)
electron入门到入土,从渲染线程中创建新窗口.2022-03-21入门版本17.1.2 electron重要概念,只有一个主线程,其他都是渲染进程或者叫子线程,他们不能直接相互操作,可以通过ip ...
- MySQL 基础(三)事务与 MVCC
事务 事务是一组原子性的 SQL 操作,或者被称为一个独立的工作单元,如果数据库引擎能够成功地对数据库应用该组的全部 SQL 语句,那么就会全部执行,否则全部不执行. 事务的特性 在关系数据库管理系统 ...
- 斯坦福 UE4 C++ ActionRoguelike游戏实例教程 07.在C++中使用UMG
斯坦福 UE4 C++ ActionRoguelike游戏实例教程 07.在C++中使用UMG 斯坦福课程 UE4 C++ ActionRoguelike游戏实例教程 0.绪论 概述 本篇文章的目标是 ...
- 7、Flutter GridView网格布局组件(遍历)
GridView创建网格列表主要有下面三种方式 1.可以通过GridView.count 实现网格布局 一行的 Widget 数量 class HomePage extends Stateles ...
- Ocelot(.NET API Gateway)
一.介绍 Ocelot 是一个.NET API 网关 面向使用.NET运行微服务/面向服务的体系结构的人员,这些体系结构需要统一的系统入口点. Ocelot将HttpRequest对象操作到由其配置指 ...
- 全量通过,华为云GaussDB首批完成信通院全密态数据库评测
摘要:100%全量通过!基于全栈创新计算架构的全密态数据库华为云GaussDB,完成了中国信通院组织的首批"全密态数据库"产品能力评测. 本文分享自华为云社区<全量通过!华为 ...
- 详解JQuery框架的五大选择器
摘要:今天来和大家分享一下JQuery的五种选择器的详细使用方法. 本文分享自华为云社区<[JQuery框架]五大选择器"全家桶"详解!!!>,原文作者:灰小猿 . 今 ...
- Error: Could not find or load main class org.elasticsearch.tools.java_version_checker.JavaVersionChecker
把elasticsearch目录换到不属于root目录的其他目录就行了