操作系统:Centos 7.6
主机名 | 主机IP | 角色 | 备注 |
---|---|---|---|
master1 | 10.90.21.106 | MySQL主机、keepalived (BACKUP) | 全新的机器 |
master2 | 10.90.21.113 | MySQL主机、keepalived(MASTER) | 将由106克隆而得 |
虚拟IP | 10.90.21.114 | 虚拟IP | 未与任何机器绑定 |
在 master1(106) 上安装MySQL,具体操作请参考文章 Centos 7 安装系列(1):MySQL 5.7.35 ,在这里不再讲解。
打开配置文件进行修改:
vi /etc/my.cnf
在文件末尾添加以下内容:
#开启binlog日志
log-bin=/var/lib/mysql/mysql-bin
# 配置server-id 每个MySQL实例的server-id都不能相同
server-id=123
# 作为从库时 更新操作是否写入日志 on:写入 其他数据库以此数据库为主库时才能进行同步
log-slave-updates=on
# MySQL系统库的日志不计入binlog
binlog-ignore-db=information_schema
binlog-ignore-db=mysql
binlog-ignore-db=performance_schema
binlog-ignore-db=sys
#忽略所有复制产生的错误
slave-skip-errors = all
# MySQL系统库的数据不需要同步 我们这里写了3个 更加保险
# 同步数据时忽略一下数据库 但是必须在使用use db的情况下才会忽略;如果没有使用use db 比如create user
数据还是会同步的
replicate-ignore-db=information_schema
replicate-ignore-db=mysql
replicate-ignore-db=performance_schema
replicate-ignore-db=sys
# 使用通配符忽略MySQL系统库的表 这样在create user时也不会进行同步了
replicate_wild_ignore_table=information_schema.%
replicate_wild_ignore_table=mysql.%
replicate_wild_ignore_table=performance_schema.%
replicate_wild_ignore_table=sys.%
修改完配置文件后,重启MySQL:
service mysqld restart
克隆主机master1(106) ,并修改克隆机的静态IP 为10.90.21.113,名为master2。
打开配置文件进行修改:
server-id=124
修改完配置文件后,重启MySQL。
service mysqld restart
grant replication slave, replication client on . to ‘repl_master’@‘192.168.147.103’ identified by ‘Root123456+’;
这一步我们没有做,因为我们在MySQL 安装那一步已经给root 用户授予了所有的权限,在这里我们将使用该用户来进行操作。
若你想使用新的用户,可在MySQL 命令行界面执行上述命令(按实际情况修改)。
show master status;
结果如下:
记住binlog 文件名称及位置:mysql-bin.000004 | 154
执行以下命令:
CHANGE MASTER TO MASTER_HOST='10.90.21.113',MASTER_PORT=3306,MASTER_USER='root', MASTER_PASSWORD='xxxx',MASTER_LOG_FILE='mysql-bin.000004',MASTER_LOG_POS=154;
grant replication slave, replication client on . to ‘repl_master’@‘192.168.147.103’ identified by ‘Root123456+’;
这一步我们没有做,因为我们在MySQL 安装那一步已经给root 用户授予了所有的权限,在这里我们将使用该用户来进行操作。
若你想使用新的用户,可在MySQL 命令行界面执行上述命令(按实际情况修改)。
show master status;
记住binlog 文件名称及位置:mysql-bin.000002 | 154
执行以下命令:
CHANGE MASTER TO MASTER_HOST='10.90.21.106',MASTER_PORT=3306,MASTER_USER='root', MASTER_PASSWORD='xxxx',MASTER_LOG_FILE='mysql-bin.000002',MASTER_LOG_POS=154;
开启从库:
start slave;
在两台主机的MySQL 上都执行上述命令。
查看从库状态:
show slave status\G;
Slave_IO_Running 与 Slave_SQL_Running 均为Yes才算是完成了主从同步。
这里我们是出现了错误,查看MySQL 日志找寻报错信息:
tail /var/log/mysqld.log
之所以会出现这个报错是因为master2(113) 主机是由master1(106) 主机克隆而来,所以两者的配置是一模一样的。
那么我们就需要修改master2(113) 的uuid了,登录master2(113) 的MySQL:
执行以下命令:
select uuid();
find / -name 'auto.cnf'
vi /var/lib/mysql/auto.cnf
用在MySQL 中查出的uuid 替换文件中的uuid。
重启MySQL:
service mysqld restart
两台主机的MySQL 都执行以下命令:
stop slave;
start slave;
show slave status\G;
原始MySQL 状态:
在106 上新建一个数据库 test_jq:
可以看到106 上已经新增了test_jq 数据库,那么113 上是否会真的同时拥有该数据库呢?让我们刷新下113 的MySQL:
可以看到113 上也拥有test_jq 数据库。
在106 的test_jq 数据库中新建数据表test_table:
那么在113 上是否会将该数据表进行同步呢?打开113 的test_jq 数据库:
很明显,106 的数据表已经被成功的同步到113 了。
在113 的test_jq 数据库的test_table 数据表中新增一条数据(100,“张三”):
让我们也紧跟着查看106 对应的数据表:
显然,新增的数据也可以进行同步。
将113 中刚刚增加的数据修改为(100,“李四”):
此时我们还没刷新106 对应的数据表,所以看到的数据仍然是“张三”,那么我们接下来刷新下106 的test_table 数据表:
可以看出对应行数据的修改值也已经被同步了过来。
那么MySQL 主主模式备份已经算是圆满成功了。
MySQL 主主结构已经搭建好了,无论从哪个MySQL插入数据,都会同步到另外一个MySQL。
虽然有了MySQL主主结构,但是不能保证高可用,比如,我们的应用程序连接的是master1(106),master1(106) 的MySQL挂掉了,我们的应用程序并不能自动的切换到master2(113),我们的应用程序也是不可用的状态。
要做到这一点,就要借助于Keepalived。
Keepalived有两个主要的功能:
我们这里使用Keepalived,只需要使用其中的一个功能,提供虚IP,实现双机热备。
我们先在master2(113) 进行操作。
直接使用yum 安装keepalived:
yum install keepalived -y
报错了,提示缺少依赖libmysqlclient.so.18()
那么先安装这个依赖:
yum install -y wget
wget https://dev.mysql.com/get/Downloads/MySQL-5.7/mysql-community-libs-compat-5.7.25-1.el7.x86_64.rpm
rpm -ivh mysql-community-libs-compat-5.7.25-1.el7.x86_64.rpm
再次执行keepalived 的安装:
yum install keepalived -y
备份好原配置文件后,进行修改:
cp /etc/keepalived/keepalived.conf /etc/keepalived/keepalived.conf.original
vi /etc/keepalived/keepalived.conf
修改后文件所有内容如下:
! Configuration File for keepalived
global_defs {
notification_email {
acassen@firewall.loc
failover@firewall.loc
sysadmin@firewall.loc
}
notification_email_from Alexandre.Cassen@firewall.loc
smtp_server 192.168.200.1
smtp_connect_timeout 30
router_id LVS_DEVEL
vrrp_skip_check_adv_addr
#vrrp_strict
vrrp_garp_interval 0
vrrp_gna_interval 0
}
# 检查mysql服务是否存活的脚本
vrrp_script chk_mysql {
script "/usr/bin/killall -0 mysqld"
}
vrrp_instance VI_1 {
state MASTER
interface ens192
virtual_router_id 51
priority 100
advert_int 1
authentication {
auth_type PASS
auth_pass 1111
}
virtual_ipaddress {
10.90.21.114
}
# 检查脚本 vrrp_script的名字
track_script {
chk_mysql
}
}
主要修改内容:
killall命令不是系统自带的,需要安装。
先查询一下killall:
yum search killall
安装对应的组件:
yum install psmisc -y
killall -0 并不是杀掉进程,而是检查进程是否存在,如果存在则返回0,如果不存在则返回1。
当返回1时,keepalived 就会切换主备状态。
其中keepalived 的配置文件/etc/keepalived/keepalived.conf 的修改内容有以下变化:
通过keepalived 的配置,我们对外提供10.90.21.114 的IP,这个IP实际指向是10.90.21.113(master1),因为它的state 是MASTER。
当keepalived 检测到10.90.21.113(master1)上的MySQL 不可用时,会自动切换到10.90.21.106(master2)。对于外部用户是无感知的,因为外部统一使用的是10.90.21.114。
在两台主机上都执行以下命令:
service keepalived start
ip addr
可以看到在106 和113 两台主机上都有虚拟IP 的存在,也就是说我们的主备根本就没有成功。
setenforce 0
该命令可以临时关闭SELinux。
若要永久关闭SELinux ,可以修改 /etc/selinux/config 文件,将参数SELINUX=enforcing 修改为SELINUX=disabled,随后需要重启主机使该配置文件生效。
在防火墙规则中增加开放VRRP :
firewall-cmd --direct --permanent --add-rule ipv4 filter INPUT 0 --protocol vrrp -j ACCEPT
firewall-cmd --reload
开放防火墙112 端口:
firewall-cmd --zone=public --add-port=112/tcp --permanent
firewall-cmd --reload
再次查看两台主机的IP:
可以看到此时的虚拟IP 在10.90.21.113 上(state MASTER)。
我们停掉10.90.21.113 的MySQL,看下虚拟IP 会不会 ‘ 飘走 ’ :
service mysqld stop
ip addr
可以看到113 上面已经没有虚拟IP 114 了。
那么该虚拟IP 会不会 ‘ 漂移 ’ 到106 上面呢?
【提醒】
重启MySQL 的时候也需要重新启动keepalived ,因为keepalived 在MySQL 关闭时便紧跟着被停掉了。
在Navicat 上连接虚拟IP(114) 的MySQL 数据库(账号密码与master1(106) 的一致):
在Navicat 上连接虚拟IP(114) 的数据库,在SQL 命令行界面输入以下命令:
show variables like "server_id";
可以看到当前的server_id 值是123 ,这是master1(106) 的配置(113 的MySQL 在5.6.1 已经停掉了)。
我们先把master2(113) 的MySQL 和keepalived 重新启动:
service mysqld start
service keepalived start
此时虚拟IP(114) 仍挂在master1(106) 上。
接下来,我们停掉master1(106) 的MySQL,那么虚拟IP 应该就会漂移到master2(113) 上。
service mysqld stop
我们在虚拟IP(114) 的SQL 命令行界面再次查询server_id :
show variables like "server_id";
结果如下:
可以看到,虚拟IP(114) 已经漂移到了master2(113) 上了,故障切换成功。
好了,本文到此截至,主要介绍了如何在Centos 7 服务器上部署MySQL 双主结构以及使用keepalived 提供MySQL 双主结构的对外虚拟IP 。
注意要点:
同类型文章推荐:
Centos 7 安装系列(5):MySQL 8.0.26
Centos 7 安装系列(4):Redis 单主机集群
Centos 7 安装系列(3):Redis 6.2.5
Centos 7 安装系列(2):MongoDB 5.0.2
Centos 7 安装系列(1):MySQL 5.7.35
Linux 搭建Java 环境,部署项目
Centos 7 nginx+php 实现公网访问
2022年3月24日更新
以上述方法实现的keepalived 是抢占式的,即:
当MASTER 宕机时,VIP 会漂移到BACKUP 上;但当MASTER 恢复后,其会把VIP 抢占回来。
如何配置非抢占式:
2022年3月24日更新
上述方法是配置了监听MySQL 的keepalived,但是如果我想监听某个服务或者端口呢?例如,我想监听8888 端口,如果该端口没有被占用,那么该主机上的keepalived 就不生效。
监听其他服务或端口:
#!/bin/bash
nmap localhost -p 8888 | grep "8888/tcp open"
if [ $? -ne 0 ];then
service keepalived stop
exit 10
fi
赋予该脚本执行权限,否则当监听到8888 端口没有被占用后将无法执行响应的操作(关闭keepalived),那么VIP 就不会进行漂移:
chmod a+x check.sh
yum install nmap -y
yum install nc -y
注意要点: