MySQL集群 主从复制 和 高可用 配置详解

安装数据库

1、环境依赖

复制代码
[root@mysql-node10 ~]# yum install cmake gcc-c++ openssl-devel ncurses-devel.x86_64 libtirpc-devel-1.3.3-8.el9_4.x86_64.rpm rpcgen.x86_64 -y

2、下载软件包

3、进行解压

复制代码
[root@mysql ~]# tar zxf mysql-boost-5.7.44.tar.gz

4、生成源码

复制代码
#进入到解压的软件目录
[root@mysql-node10 mysql-5.7.44]# cmake \
-DCMAKE_INSTALL_PREFIX=/usr/local/mysql \ 		#指定安装路径
-DMYSQL_DATADIR=/data/mysql \ 					#指定数据目录
-DMYSQL_UNIX_ADDR=/data/mysql/mysql.sock \ 		#指定套接字文件
-DWITH_INNOBASE_STORAGE_ENGINE=1 \ 				#指定启用INNODB存储引擎,默认用myisam
-DWITH_EXTRA_CHARSETS=all \ 					#扩展字符集
-DDEFAULT_CHARSET=utf8mb4 \ 					#指定默认字符集
-DDEFAULT_COLLATION=utf8mb4_unicode_ci \ 		#指定默认校验字符集
-DWITH_BOOST=/root/mysql-5.7.44/boost/boost_1_59_0	#指定c++库依赖

5、编译和安装

复制代码
[root@mysql-node10 mysql-5.7.44]# make -j2
#-j2 表示有几个核心就跑几个进程

[root@mysql-node10 mysql-5.7.44# make install
#进行安装

#当cmake出错时,想重新检测,删除 mysql-5.7.44 中 CMakeCache.txt 即可

数据库初始化配置

1、创建mysql的用户和目录

复制代码
[root@mysql1 ~]# useradd -s /sbin/nologin mysql
#创建mysql用户

[root@mysql1 ~]# mkdir /data/mysql -p
#创建mysql数据库目录,该目录在生成源码时指定了路径,不可随意更改

2、生成配置文件

复制代码
[root@mysql1 ~]# cp /usr/local/mysql/support-files/mysql.server /etc/init.d/mysql
#将mysql服务配置文件复制到系统配置文件下

[root@mysql1 ~]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql 			#指定数据目录
socket=/data/mysql/mysql.sock 	#指定套接字
symbolic-links=0 				#数据只能存放到数据目录中,禁止链接到数据目录

3、数据库初始化基本数据

复制代码
[root@mysql1 ~]# vim /root/.bash_profile
#编辑环境变量
PATH=$PATH:$HOME/bin:/usr/local/mysql/bin
复制代码
[root@mysql1 ~]# mysqld --user mysql --initialize
#初始化数据库并生成默认初始密码
复制代码
[root@mysql1 ~]# /etc/init.d/mysql start
#启用mysql

4、数据库安全初始化

复制代码
[root@mysql1 ~]# mysql_secure_installation

Enter password for user root:	#初始化的默认密码

New password: 					#设置新密码

Re-enter new password:			#再次输入新密码

Press y|Y for Yes, any other key for No: no	#是否启用密码插件;为实验方便则未开启

Change the password for root ? ((Press y|Y for Yes, any other key for No) : no	#是否重置密码

Remove anonymous users? (Press y|Y for Yes, any other key for No) : y


Disallow root login remotely? (Press y|Y for Yes, any other key for No) : y


Remove test database and access to it? (Press y|Y for Yes, any other key for No) : y

Reload privilege tables now? (Press y|Y for Yes, any other key for No) : y

5、登录成功

复制代码
[root@mysql1 ~]# mysql -uroot -p密码	#登录数据库

MySQL 主从复制

MySQL 主从复制原理


三个线程

实际上主从同步的原理就是基于 bin-log 日志进行数据同步的。在主从复制过程中,会基于3 个线程来操作,一个主库线程,两个从库线程。

1、二进制日志转储线程(Binlog dump thread)是一个主库线程。当从库线程连接的时候, 主库可以将二进制日志发送给从库,当主库读取事件(Event)的时候,会在 Binlog 上加锁,读取完成之后,再将锁释放掉。

2、从库 I/O 线程会连接到主库,向主库发送请求更新 Binlog。这时从库的 I/O 线程就可以读取到主库的二进制日志转储线程发送的 Binlog 更新部分,并且拷贝到本地的中继日志 (Relay log)。

3、从库 SQL 线程会读取从库中的中继日志,并且执行日志中的事件,将从库中的数据与主库保持同步。

复制三步骤

步骤1:Master将写操作记录到二进制日志(binlog)。

步骤2:Slave将Master的binary log events拷贝到它的中继日志(relay log);

步骤3:Slave重做中继日志中的事件,将改变应用到自己的数据库中。 MySQL复制是异步的且串行化的,而且重启后从接入点开始复制。

具体操作

1、slaves端中设置了master端的ip,用户,日志,和日志的Position,通过这些信息取得master的认证及信息

2、master端在设定好binlog启动后会开启binlog dump的线程

3、master端的binlog dump把二进制的更新发送到slave端的

4、slave端开启两个线程,一个是I/O线程,一个是sql线程:i/o线程用于接收master端的二进制日志,此线程会在本地打开relaylog中继日志,并且保存到本地磁盘;sql线程读取本地relog中继日志进行回放

5、什么时候我们需要多个slave?

​ 当读取的操作远远高于写操作时,我们采用一主多从架构

​ 数据库外层接入负载均衡层并搭配高可用机制

架构缺陷

主从架构采用的是异步机制:

1、master更新完成后直接发送二进制日志到slave,但是slaves是否真正保存了数据master端不会检测

2、master端直接保存二进制日志到磁盘

3、当master端到slave端的网络出现问题时或者master端直接挂掉,二进制日志可能根本没有到达slave端

4、master出现问题slave端接管master,这个过程中数据会丢失

这样的问题出现就无法达到数据的强一致性,零数据丢失

master 配置

1、修改配置文件

复制代码
[root@mysql1 ~]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
symbolic-links=0
log-bin=mysql-bin		#开启二进制日志(默认不开启)
server-id=1				#设置数据库ID

2、重新加载配置

复制代码
[root@mysql1 ~]# /etc/init.d/mysqld restart

3、进入数据库配置用户权限

复制代码
[root@mysql1 ~]# mysql -p123
复制代码
mysql> CREATE USER tym@'%' IDENTIFIED BY '123';
#生成专门用来做复制的用户,此用户是用于slave端做认证用

mysql> GRANT REPLICATION SLAVE ON *.* TO tym@'%';
#对这个用户进行授权

mysql> SHOW MASTER STATUS;
#查看master的状态

4、查看mysql二进制日志

复制代码
[root@mysql1 ~]# mysqlbinlog mysql-bin.000002 -vv

slave 配置

注意

在slave中是默认开启写的功能,但写入的数据只限于存在进行写的slave设备中,建议将slave写功能关闭

复制代码
[root@mysql2 ~]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
symbolic-links=0
server-id=2				#设置数据库ID
super_read_only=on		#开启只读不写

1、修改配置文件

复制代码
[root@mysql2 ~]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
symbolic-links=0
server-id=2				#设置数据库ID

2、重新加载配置

复制代码
[root@mysql2 ~]# /etc/init.d/mysqld restart

3、进入数据库配置master认证

登录mysql数据库

复制代码
[root@mysql2 ~]# mysql -p123

master用户认证

复制代码
mysql> CHANGE MASTER TO MASTER_HOST='172.25.254.10',MASTER_USER='tym',MASTER_PASSWORD='123',MASTER_LOG_FILE='mysql-bin.000001',MASTER_LOG_POS=593;

4、开启slave

复制代码
mysql> START SLAVE;

5、查看本地slave状态

复制代码
mysql> SHOW SLAVE STATUS\G;
验证

1、在 master 内新建数据库和表,并插入数据

2、可在 salve 查看到master新插入的内容

当数据库内存在数据时添加新的slave

1、修改配置文件

复制代码
[root@mysql3 ~]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
symbolic-links=0
server-id=3				#设置数据库ID

2、重新加载配置

复制代码
[root@mysql3 ~]# /etc/init.d/mysqld restart

3、将master设备的数据拷贝传输至新的slave设备内

拷贝数据

复制代码
[root@mysql1 ~]# mysqldump -uroot -p test >/root/test.sql
Enter password:密码

传输数据

复制代码
[root@mysql1 ~]# scp test.sql 172.25.254.30:/root/
#可根据自己的情况选择合适的拷贝方式

4、将拷贝的数据导入新的slave设备数据库内

注意事项

#生产环境中备份时需要锁表,保证备份前后的数据一致

mysql> FLUSH TABLES WITH READ LOCK;

#备份后再解锁

mysql> UNLOCK TABLES;

mysqldump命令备份的数据文件,在拷贝至新设备时,会先DROP TABLE,需要合并数据时需要删除此语句

5、进入数据库配置master认证

登录mysql数据库

复制代码
[root@mysql3 ~]# mysql -p123

master用户认证

复制代码
mysql> CHANGE MASTER TO MASTER_HOST='172.25.254.10',MASTER_USER='tym',MASTER_PASSWORD='123',MASTER_LOG_FILE='mysql-bin.000001',MASTER_LOG_POS=593;

6、开启slave

复制代码
mysql> START SLAVE;

7、查看本地slave状态

复制代码
mysql> SHOW SLAVE STATUS\G;

延迟复制

1、延迟复制时用来控制sql线程的,和i/o线程无关

2、这个延迟复制不是i/o线程过段时间来复制,i/o是正常工作的

3、日志已经保存在slave端了,而是那个 sql 要到了设定的时间才进行回放操作

1、进入mysql内进行配置

复制代码
#在slave端

[root@mysql2 ~]# mysql -p123
mysql> STOP SLAVE SQL_THREAD;
mysql> CHANGE MASTER TO MASTER_DELAY=60;	#延迟时间为60s
mysql> START SLAVE SQL_THREAD;

慢日志查询

1、慢查询,顾名思义,执行很慢的查询

2、当执行SQL超过long_query_time参数设定的时间阈值(默认10s)时,就被认为是慢查询,这个SQL语句就是需要优化的

3、慢查询被记录在慢查询日志里

4、慢查询日志默认是不开启的

5、如果需要优化SQL语句,就可以开启这个功能,它可以让你很容易地知道哪些语句是需要优化的。

1、进入mysql内进行配置(也可在配置文件内编辑,但需重启服务才可生效)

复制代码
[root@mysql2 ~]# mysql -p123
mysql> SET GLOBAL slow_query_log=ON;	#开启慢日志查询

mysql> SET long_query_time=4;			#设定查询时间为4s


测试

查询时间超过4s的语句

MySQL的并行复制

查看slave设备的线程信息

1、默认情况下slave中使用的是sql单线程回放

2、在master中时多用户读写,如果使用sql单线程回放那么会造成组从延迟严重

3、开启MySQL的多线程回放可以解决上述问题

1、修改配置文件(未开启延迟复制的slave设备)

复制代码
[root@mysql2 ~]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
server-id=2

slave-parallel-type=LOGICAL_CLOCK 		#基于组提交,
slave-parallel-workers=16 				#开启线程数量
master_info_repository=TABLE 			#master信息在表中记录,默认记录在/data/mysql/master.info
relay_log_info_repository=TABLE 		#回放日志信息在表中记录,默认记录在/data/mysql/relay-log.info
relay_log_recovery=ON 					#日志回放恢复功能开启

2、重新加载配置

复制代码
[root@mysql2 ~]# /etc/init.d/mysql start

此时sql线程转化为协调线程,16个worker负责处理sql协调线程发送过来的处理请求

MySQL 组提交(Group commit)是一个性能优化特性,它允许在一个事务日志同步操作中将多个事务的日志记录一起写入。这样做可以减少磁盘I/O的次数,从而提高数据库的整体性能。

效果演示

半同步模式

半同步模式原理

1、用户线程写入完成后master中的dump会把日志推送到slave端

2、slave中的i/o线程接收后保存到relaylog中继日志

3、保存完成后slave向master端返回ack

4、在未接受到slave的ack时master端不做提交数据,一直处于等待状态,当收到ack后提交到存储引擎

5、在5.6版本中用到的时after_commit模式,after_commit模式时先提交在等待ack返回后输出ok

gtid 模式

未启用gtid时

1、在master端写入时为多用户读写,slave端在复制时采用单线程日志回放,所以slave端一定会与master端有数据的延迟

2、这种延迟在不同的slave端可能会不一致,当master挂掉后由slave接管,一般会挑选一个和master延迟日志最接近的充当新的master

3、那么未成为master的主机将继续充当slave角色,并指向其新的master上

4、当这种情况发生时,按照之前的配置我们需要知道新的master上的pos的id,但我们无法确定新的master和slave之间差多少

激活gtid后

1、当master出现问题后,slave*与master的数据最接近,会被作为新的master

2、其它的 slave 会指向新的master,但是他不会去检测新的master的pos id,只需要继续读取自己gtid_next即可

gtid 配置

1、修改master端和slave端的配置文件

复制代码
[root@mysql1 ~]# vim /etc/my.cnf
[mysqld]
......
gtid_mode=ON
enforce-gtid-consistency=ON

2、在全部设备修改完成后,重启服务

复制代码
[root@mysql1 ~]# /etc/init.d/mysql restart

3、查看master设备的bin-log日志,gtid模式是否生效

复制代码
[root@mysql1 ~]# mysqlbinlog -vv /data/mysql/mysql-bin.000004
#该日志为最新的binlog日志

3、修改slave端的master用户配置

效果演示

开启半同步功能

master 配置

1、启用半同步功能

复制代码
[root@mysql1 ~]# vim /etc/my.cnf
[mysqld]
......
rpl_semi_sync_master_enabled=1		#开启半同步功能

2、安装半同步功能插件

复制代码
mysql> INSTALL PLUGIN rpl_semi_sync_master SONAME 'semisync_master.so';

3、重启mysql服务

复制代码
[root@mysql1 ~]# /etc/init.d/mysql restart

4、查看其半同步状态

复制代码
mysql> SHOW VARIABLES LIKE 'rpl_semi_sync%';

slave 配置

1、启用半同步功能

复制代码
[root@mysql2 ~]# vim /etc/my.cnf
[mysqld]
......
rpl_semi_sync_master_enabled=1		#开启半同步功能

2、安装半同步功能插件

复制代码
mysql> INSTALL PLUGIN rpl_semi_sync_master SONAME 'semisync_master.so';

3、开启半同步功能

复制代码
mysql> SET GLOBAL rpl_semi_sync_slave_enabled =1;

4、重启io线程,半同步功能才能生效

复制代码
mysql> STOP SLAVE IO_THREAD;

5、查看其半同步功能状态

复制代码
mysql> SHOW STATUS LIKE 'Rpl_semi_sync%';

测试

当master设备插入数据时:

slave设备快速复制到本地设备

当关闭 slave 端 io 线程时,显示数据插入超时,此时master自动切换为异步模式,开始正常写入数据

MySQL 高可用之组复制(MGR)

MySQL Group Replication(简称 MGR )是 MySQL 官方于 2016 年 12 月推出的一个全新的高可用与高扩展的解决方案

1、组复制是 MySQL 5.7.17 版本出现的新特性,它提供了高可用、高扩展、高可靠的 MySQL 集群服务

2、MySQL 组复制分单主模式和多主模式,传统的mysql复制技术仅解决了数据同步的问题,

3、MGR 对属于同一组的服务器自动进行协调。对于要提交的事务,组成员必须就全局事务序列中给定事务的顺序达成一致

4、提交或回滚事务由每个服务器单独完成,但所有服务器都必须做出相同的决定

5、如果存在网络分区,导致成员无法达成事先定义的分割策略,则在解决此问题之前系统不会继续进行,这是一种内置的自动裂脑保护机制

6、MGR由组通信系统( Group Communication System ,GCS ) 协议支持

7、该系统提供故障检测机制、组成员服务以及安全且有序的消息传递

组复制流程

1、首先我们将多个节点共同组成一个复制组,在执行读写(RW)事务的时候,需要通过一致性协议层(Consensus 层)的同意,也就是读写事务想要进行提交,必须要经过组里"大多数人"(对应 Node 节点)的同意,大多数指的是同意的节点数量需要大于 (N/2+1),这样才可以进行提交,而不是原发起方一个说了算

2、而针对只读(RO)事务则不需要经过组内同意,直接提交即可

3、节点数量不能超过9台

组复制的单主和多主模式

单主模式

single-primary mode

单写模式 group 内只有一台节点可写可读,其他节点只可以读。当主服务器失败时,会自动选择新的主服务器

多主模式

multi-primary mode

组内的所有机器都是 primary 节点,同时可以进行读写操作,并且数据是最终一致的。

组复制(MGR)部署

1、修改配置文件

复制代码
[root@mysql1 mysql]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
symbolic-links=0
server-id=1 						#配置server唯一标识号
disabled_storage_engines="MyISAM,BLACKHOLE,FEDERATED,ARCHIVE,MEMORY" 	#禁用指定存储引擎
gtid_mode=ON 						#启用全局事件标识
enforce_gtid_consistency=ON 		#强制gtid一致
master_info_repository=TABLE 		#复制事件数据到表中而不记录在数据目录中
relay_log_info_repository=TABLE
binlog_checksum=NONE 				#禁止对二进制日志校验
log_slave_updates=ON 				#打开数据库中继,当slave中sql线程读取日志后也会写入到自己的binlog中
log_bin=binlog 						#重新指定log名称
binlog_format=ROW							#使用行日志格式
plugin_load_add='group_replication.so'		#加载组复制插件
transaction_write_set_extraction=XXHASH64	#把每个事件编码为加密散列
group_replication_group_name="aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa" #通知插件正式加入或创建的组名,名称为uuid格式
group_replication_start_on_boot=off 								#在server启动时不自动启动组复制
group_replication_local_address="172.25.254.10:33061"				#指定插件接受其他成员的信息端口
group_replication_group_seeds="172.25.254.10:33061,172.25.254.20:33061,172.25.254.30:33061"	#本地地址允许访问成员列表
group_replication_ip_whitelist="172.25.254.0/24,127.0.0.1/8"		#主机白名单
																	#不随系统自启而启动,只在初始成员主机中手动开启,
																	#需要在两种情况下做设定:1.初始化建组时 2.关闭并重新启动整个组时
group_replication_bootstrap_group=off
group_replication_single_primary_mode=OFF							#使用多主模式
group_replication_enforce_update_everywhere_checks=ON				#组同步中有任何改变检测更新
group_replication_allow_local_disjoint_gtids_join=1 				#放弃自己信息以master事件为主

2、将数据库清空,重新初始化数据库(企业内决不允许这样操作)

复制代码
[root@mysql1 ~]# rm -rf /data/mysql/*
#清空原有的数据库内容

[root@mysql1 ~]# mysqld --user=mysql --initialize
#初始化数据库

3、进入数据库进行配置

复制代码
[root@mysql1 ~]# mysql -uroot -p'密码'

mysql> alter user root@localhost identified by '新密码';
#修改密码

mysql> SET SQL_LOG_BIN=0;
#关闭日志功能

mysql> CREATE USER rpl_user@'%' IDENTIFIED BY 'lee';
#创建用来做组复制的用户

mysql> GRANT REPLICATION SLAVE ON *.* TO rpl_user@'%';
#给予用户权限

mysql> FLUSH PRIVILEGES;
#刷新缓存

mysql> SET SQL_LOG_BIN=1;
#开启日志功能

mysql> CHANGE MASTER TO MASTER_USER='用户名',MASTER_PASSWORD='密码' FOR CHANNEL 'group_replication_recovery';
#登录组复制的用户

mysql> SET GLOBAL group_replication_bootstrap_group=ON;
#用以指定初始成员,仅在第一台主机中执行,开启组复制加入功能

mysql> START GROUP_REPLICATION;
#开启组复制功能

mysql> SET GLOBAL group_replication_bootstrap_group=OFF;
#用以指定初始成员,仅在第一台主机中执行,关闭组复制加入功能

组复制的第一台设备

其余设备

组成员

当某台设备因故障退出组时,需在恢复的故障设备内重新开启组复制功能才可加入组内(进入mysql内开启组复制功能)

每台设备的数据库都可以完成读写操作

确保数据库内存在主键(primary key),才可正常同步数据



MySQL Router

MySQL Router

是一个对应用程序透明的InnoDB Cluster连接路由服务,提供负载均衡、应用连接故障转移和客户端路由。

利用路由器的连接路由特性,用户可以编写应用程序来连接到路由器,并令路由器使用相应的路由策略来处理连接,使其连接到正确的MySQL数据库服务器

Mysql router的部署

使用一台新设备用于mysql router 的部署

mysql router 并不能限制数据库的读写,但可实现访问分流

1、下载软件包

复制代码
[root@mysql-router ~]# rpm -ivh mysql-router-community-8.4.0-1.el7.x86_64.rpm

2、修改配置文件

复制代码
#配置mysql-router
[root@mysql-router ~]# vim /etc/mysqlrouter/mysqlrouter.conf
......

[routing:ro]
bind_address = 0.0.0.0
bind_port = 7001
destinations = 172.25.254.10:3306,172.25.254.20:3306,172.25.254.30:3306
routing_strategy = round-robin	#轮询调度

[routing:rw]
bind_address = 0.0.0.0
bind_port = 7002
destinations = 172.25.254.30:3306,172.25.254.20:3306,172.25.254.10:3306
routing_strategy = first-available	#最先响应调度(最少链接)

效果演示

用户远程登录

MySQL 高可用之 MHA

MHA 概述

使用MHA的原因

Master的单点故障问题

什么是MHA

1、MHA(Master High Availability)是一套优秀的MySQL高可用环境下故障切换和主从复制的软件。

2、MHA 的出现就是解决MySQL 单点的问题。

3、MySQL故障切换过程中,MHA能做到0-30秒内自动完成故障切换操作。

4、MHA能在故障切换的过程中最大程度上保证数据的一致性,以达到真正意义上的高可用。

MHA的组成

1、MHA由两部分组成:MHAManager (管理节点) MHA Node (数据库节点)

2、MHA Manager 可以单独部署在一台独立的机器上管理多个master-slave集群,也可以部署在一台 slave 节点上

3、MHA Manager 会定时探测集群中的 master 节点

4、当 master 出现故障时,它可以自动将最新数据的 slave 提升为新的 master, 然后将所有其他的slave 重新指向新的 master

MHA的特点

1、自动故障切换过程中,MHA从宕机的主服务器上保存二进制日志,最大程度的保证数据不丢失

2、使用半同步复制,可以大大降低数据丢失的风险,如果只有一个slave已经收到了最新的二进制日志,MHA可以将最新的二进制日志应用于其他所有的slave服务器上,因此可以保证所有节点的数据一致性

3、目前MHA支持一主多从架构,最少三台服务,即一主两从

故障切换备选主库的算法

1、一般是判断从库的 " position/GTID " 来判断优劣,数据有差异时,最接近于master的slave,成为备选主。

2、数据一致的情况下,按照配置文件顺序,选择备选主库。

3、设定有权重(candidate_master=1),按照权重强制指定备选主。

(1)默认情况下如果一个slave落后master 100M的relay logs的话,即使有权重,也会失效。

(2)如果check_repl_delay=0的话,即使落后很多日志,也强制选择其为备选主。

MHA工作原理

1、目前MHA主要支持一主多从的架构,要搭建MHA,要求一个复制集群必须最少有3台数据库服务器,一主二从,即一台充当Master,一台充当备用Master,另一台充当从库。

2、MHA Node 运行在每台 MySQL 服务器上

3、MHAManager 会定时探测集群中的master 节点

4、当master 出现故障时,它可以自动将最新数据的slave 提升为新的master

5、然后将所有其他的slave 重新指向新的master,VIP自动漂移到新的master上

6、整个故障转移过程对应用程序完全透明

MHA 部署

1、将数据库设定为半同步模式,开启数据库主/备设备的binlog日志和中继日志功能

复制代码
[root@mysql1 ~]# /etc/init.d/mysql stop

[root@mysql1 ~]# vim /etc/my.cnf

[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
symbolic-links=0
server-id=1
gtid_mode=ON
enforce_gtid_consistency=ON
log-bin=mysql-bin
log_slave_updates=ON

2、数据库初始化,建立远程登录的root用户和用于半同步模式的普通用户

master设备

复制代码
[root@mysql1 ~]# rm -rf /data/mysql/*
#清空原本数据库内容

[root@mysql1 ~]# mysqld --user=mysql --initialize
#初始化数据库

[root@mysql1 ~]# /etc/init.d/mysql start
#重启数据库

[root@mysql1 ~]# mysql -uroot -p'初始密码'

mysql> alter user root@localhost identified by '新密码';
#修改初始密码

mysql> CREATE USER 'tym'@'%' IDENTIFIED by '密码';
#创建用于复制数据库的用户

mysql> GRANT REPLICATION SLAVE ON *.* TO tym@'%';
#给予用户权限

mysql> GRANT ALL ON *.* TO root@'%' identified by '新密码';
#远程登录root用户

mysql> INSTALL PLUGIN rpl_semi_sync_master SONAME 'semisync_master.so';
#安装半同步模式插件

mysql> SET GLOBAL rpl_semi_sync_master_enabled = 1;
#开启半同步模式

salve 设备

复制代码
[root@mysql2 ~]# rm -rf /data/mysql/*

[root@mysql2 ~]# mysqld --user=mysql --initialize

[root@mysql2 ~]# /etc/init.d/mysql start

[root@mysql2 ~]# mysql -uroot -p'初始密码'

mysql> alter user root@localhost identified by '新密码';

mysql> CREATE USER 'tym'@'%' IDENTIFIED by '密码';

mysql> GRANT REPLICATION SLAVE ON *.* TO tym@'%';

mysql> CHANGE MASTER TO MASTER_HOST='172.25.254.10',MASTER_USER='tym',MASTER_PASSWORD='123',MASTER_AUTO_POSITION=1;

mysql> INSTALL PLUGIN rpl_semi_sync_master SONAME 'semisync_master.so';

mysql> SET GLOBAL rpl_semi_sync_master_enabled = 1;

mysql> STOP SLAVE IO_THREAD;
#重启IO线程
mysql> START SLAVE IO_THREAD;

3、开启MHA管理设备对于数据库节点设备的免密登录

复制代码
#生成秘钥
[root@mysql-router ~]# ssh-keygen -f /root/.ssh/id_rsa -P ""


#传输秘钥至需免密登录的主机
[root@mysql-router ~]# scp /root/.ssh/id_rsa.pub root@172.25.254.10:/root/.ssh/

4、下载软件包,MHA管理设备对于管理和节点的安装包都需进行安装,数据库节点设备只需安装节点的软件包

MHA 设备

复制代码
[root@mysql-router MHA-7]# yum install *rpm -y

数据库节点设备

复制代码
[root@mysql1 ~]# yum install mha4mysql-node-0.58-0.el7.centos.noarch.rpm -y

5、MHA管理设备下载并安装masterha软件包

将软件包解压

复制代码
[root@mysql-router MHA-7]# tar xzf mha4mysql-manager-0.58.tar.gz

Manager工具包主要包括以下几个工具

masterha_check_ssh #检查MHA的SSH配置状况

masterha_check_repl #检查MySQL复制状况

masterha_manger #启动MHA

masterha_check_status #检测当前MHA运行状态

masterha_master_monitor #检测master是否宕机

masterha_master_switch #控制故障转移(自动或者手动)

masterha_conf_host #添加或删除配置的server信息

Node工具包

(通常由masterHA主机直接调用,无需人为执行)

save_binary_logs #保存和复制master的二进制日志

apply_diff_relay_logs #识别差异的中继日志事件并将其差异的事件应用于其他的slave

filter_mysqlbinlog #去除不必要的ROLLBACK事件(MHA已不再使用这个工具)

purge_relay_logs #清除中继日志(不会阻塞SQL线程)

6、将配置文件模版重定向到指定位置

复制代码
[root@mysql-router ~]# cd /root/MHA-7/mha4mysql-manager-0.58/samples/conf/

[root@mysql-router conf]# cat masterha_default.cnf app1.cnf >/etc/mastermha/mha.conf

7、编辑配置文件

负责不同区域的配置文件

复制代码
[root@mysql-mha ~]# masterha_manager --help
Usage:
masterha_manager --global_conf=/etc/masterha_default.cnf
#全局配置文件,记录公共设定

--conf=/usr/local/masterha/conf/app1.cnf
#不同的管理区域都有自己区域的配置文件,记录各自配置

编辑本地单个区域配置文件

复制代码
[root@mysql-router mastermha]# vim mha.conf
[server default]
user=root 				#mysql管理员用户,因为需要做自动化配置
password=123 			#mysql管理用户密码

ssh_user=root 			#ssh远程登陆用户

repl_user=tym 			#mysql主从复制中负责认证的用户
repl_password=123 		#mysql主从复制中负责认证的用户密码

master_binlog_dir= /data/mysql	#二进制日志目录
remote_workdir=/tmp				#远程工作目录
				
secondary_check_script= masterha_secondary_check -s 172.25.254.10 -s 172.25.254.11
						#(-s 172.25.254.11)此参数是为了提供冗余检测,
						#当mha主机自身的网络出现问题时,也是不能连通集群之外的主机的
ping_interval=3			#每隔3秒检测一次

# master_ip_failover_script= /script/masterha/master_ip_failover		#发生故障后调用的脚本,用来迁移vip
# shutdown_script= /script/masterha/power_manager						#电源管理脚本
# report_script= /script/masterha/send_report							#当发生故障后用此脚本发邮件或者告警通知
# master_ip_online_change_script= /script/masterha/master_ip_online_change	#手动在线切换时调用的vip迁移脚本

manager_workdir=/etc/masterha				#mha工作目录
manager_log=/var/etc/masterha/manager.log	#mha日志

[server1]
hostname=172.25.254.10
candidate_master=1		#可能作为master的主机
check_repl_delay=0		#默认情况下如果一个slave落后master 100M的relay logs的话,
			#MHA将不会选择该slave作为一个新的master,
			#因为对于这个slave的恢复需要花费很长时间,
			#通过设置check_repl_delay=0,
			#MHA触发切换在选择一个新的master的时候将会忽略复制延时,
			#这个参数对于设置了candidate_master=1的主机非常有用
			#因为这个候选主在切换的过程中一定是新的master
[server2]
hostname=172.25.254.20
candidate_master=1 	#可能作为master的主机
check_repl_delay=0

[server3]
hostname=172.25.254.30
no_master=1 		#不会作为master的主机

8、进行免密认证和网络是否通畅的测试

复制代码
[root@mysql-router masterha]# masterha_check_ssh --conf=/etc/masterha/mha.conf

9、进行数据库主从复制是否正常的测试

复制代码
[root@mysql-router masterha]# masterha_check_repl --conf=/etc/masterha/mha.conf

MHA的故障切换

MHA的故障切换过程

共包括以下的步骤:

1、配置文件检查阶段,这个阶段会检查整个集群配置文件配置

2、宕机的master处理,这个阶段包括虚拟ip摘除操作,主机关机操作

3、复制dead master和最新slave相差的relay log,并保存到MHA Manger具体的目录下

4、识别含有最新更新的slave

5、应用从master保存的二进制日志事件(binlog events)

6、提升一个slave为新的master进行复制

7、使其他的slave连接新的master进行复制

master主机未故障时手动切换

复制代码
[root@mysql-router ~]# masterha_master_switch --conf=/etc/masterha/mha.conf --master_state=alive --new_master_host=172.25.254.20 --new_master_port=3306 --orig_master_is_new_slave --running_updates_limit=10000

#回车命令行后出现以下的内容
It is better to execute FLUSH NO_WRITE_TO_BINLOG TABLES on the master before switching. Is it ok to execute on 172.25.254.10(172.25.254.10:3306)? (YES/no): yes

Starting master switch from 172.25.254.10(172.25.254.10:3306) to 172.25.254.20(172.25.254.20:3306)? (yes/NO): yes

master_ip_online_change_script is not defined. If you do not disable writes on the current master manually, applications keep writing on the current master. Is it ok to proceed? (yes/NO): yes

切换成功后进行检测主从复制是否正常:

复制代码
[root@mysql-router masterha]# masterha_check_repl --conf=/etc/masterha/mha.conf

master主机故障时手动切换

复制代码
[root@mysql1 ~]# /etc/init.d/mysql stop
#模拟master故障

[root@mysql-router masterha]# masterha_master_switch --master_state=dead --conf=/etc/masterha/mha.conf --dead_master_host=172.25.254.10 --dead_master_port=3306 --new_master_host=172.25.254.20 --new_master_port=3306 --ignore_last_failover

#(--ignore_last_failover)表示忽略切换时生成在/etc/masterha/目录中的锁文件

锁文件(mha.failover.complete):

切换成功:

恢复故障的mysql节点

1、当数据库节点恢复后,需手动将其变为新master的slave节点

进入到数据库内进行操作

复制代码
[root@mysql1 ~]# mysql -p123

mysql> CHANGE MASTER TO MASTER_HOST='172.25.254.20',MASTER_USER='tym',MASTER_PASSWORD='123',MASTER_AUTO_POSITION=1;

3、检测一主两从的状态是否正常

复制代码
[root@mysql-router masterha]# masterha_check_repl --conf=/etc/masterha/mha.conf

自动切换

1、删掉锁文件

复制代码
[root@mysql-router masterha]# rm mha.failover.complete  -f

2、开启监控

复制代码
[root@mysql-mha masterha]# masterha_manager --conf=/etc/masterha/mha.conf

#监控程序通过指定配置文件监控master状态,当master出问题后自动切换并退出避免重复做故障切换

3、当master设备出现故障时,会自动切换,生成新的master设备,此时监控状态结束(冗余检测的IP地址 "在MHA功能的配置文件内的设定 -s 172.25.254.11 " 是否能正常ping通,如果错误,则系统认为自身的网络出现问题,不会执行自动切换)

4、需要再次监控时,需将生成在 /etc/masterha/ 下的锁文件删除

复制代码
[root@mysql-router masterha]# rm -rf mha.failover.complete manager.log

5、手动将恢复的设备重新加入,成为新master的slave设备

复制代码
[root@mysql1 ~]# mysql -p123

mysql> CHANGE MASTER TO MASTER_HOST='172.25.254.20',MASTER_USER='tym',MASTER_PASSWORD='123',MASTER_AUTO_POSITION=1;

6、检测一组两从的状态是否正常

复制代码
[root@mysql-router masterha]# masterha_check_repl --conf=/etc/masterha/mha.conf

MHA 添加 VIP 功能

1、添加脚本

2、将脚本移动至 /usr/local/bin/ 下,并给可执行权限

复制代码
[root@mysql-router ~]# cp master_ip_failover master_ip_online_change /usr/local/bin/

[root@mysql-router ~]# chmod +x /usr/local/bin/master_ip_*

3、检测一主两从的状态是否正常

复制代码
[root@mysql-router masterha]# masterha_check_repl --conf=/etc/masterha/mha.conf

4、修改两个脚本内容

复制代码
[root@mysql-router ~]# vim /usr/local/bin/master_ip_failover

[root@mysql-router ~]# vim /usr/local/bin/master_ip_online_change

5、进行测试

启用自动切换

复制代码
[root@mysql-router ~]# masterha_manager --conf=/etc/masterha/mha.conf

未关闭mysql时,VIP 200 在 mysql2 上

关闭 mysql2,VIP 200 漂移至 mysql1 上

相关推荐
CYRUS_STUDIO19 小时前
利用 Linux 信号机制(SIGTRAP)实现 Android 下的反调试
android·安全·逆向
CYRUS_STUDIO20 小时前
Android 反调试攻防实战:多重检测手段解析与内核级绕过方案
android·操作系统·逆向
得物技术20 小时前
MySQL单表为何别超2000万行?揭秘B+树与16KB页的生死博弈|得物技术
数据库·后端·mysql
xiaok21 小时前
mysql中怎么创建一个可控权限数据库账号密码给到开发者
mysql
黄林晴1 天前
如何判断手机是否是纯血鸿蒙系统
android
火柴就是我1 天前
flutter 之真手势冲突处理
android·flutter
法的空间1 天前
Flutter JsonToDart 支持 JsonSchema
android·flutter·ios
循环不息优化不止1 天前
深入解析安卓 Handle 机制
android
恋猫de小郭1 天前
Android 将强制应用使用主题图标,你怎么看?
android·前端·flutter
jctech1 天前
这才是2025年的插件化!ComboLite 2.0:为Compose开发者带来极致“爽”感
android·开源