背景

公司内部 MySQL 只有一部,现在需要添加一个从库。办法把现有的 MySQL变成主库,新搭建一台 MySQL从库,组成一主一从让开发配置读写分离。

MySQL主库192.168.0.237
MySQL从库192.168.0.227

MySQL 主从复制图解

1. 从库执行 change master to ,ip pot user password binlog position 信息写入到 master.info
2. 从库执行 start slave 时,从库会启动 IO 线程 和 SQL 线程
3. IO_T 会读取 master.info 信息,获取主库信息连接主库
4. 主库会生成一个准备 binlog 的 DUMP 线程,来响应从库
5. IO_T 根据 master.info 记录的 binlog 文件名和 position 号,请求主库 DUMP 线程最新的日志
6. DUMP 线程检查主库的 binlog 日志,如果有新的,TP(传送)给从从库的 IO_T
7. IO_T 将收到的日志存储到了 TCP/IP 缓存,立即返回 ACK 给主库,主库工作完成
8. IO_T 将缓存中的数据,存储到 relay-log 日志文件, 更新 master.info 文件 binlog 文件名和 postion,IO_T 工作完成
9. SQL_T 读取 relay-log.info 文件,获取到上次执行到的 relay-log 的位置,作为起点,回放 relay-log
10. SQL_T 回放完成之后,会更新 relay-log.info 文件。
11. relay-log 会有自动清理的功能。

注意:主库一旦有新的日志生成,会发送 “信号” 给binlog dump线程,IO线程再请求

主库操作

vi /etc/my.cnf

[mysqld]
innodb_buffer_pool_size = 1024M
character_set_server = utf8mb4
skip-name-resolve
innodb_file_per_table = 1
basedir=/usr/local/mysql
datadir=/iba/mysql/data
port=3306
user=mysql

sql_mode=NO_ENGINE_SUBSTITUTION,STRICT_TRANS_TABLES
max_connections=1024
max_allowed_packet=128M
show_compatibility_56 = on

default_password_lifetime=0

server-id = 1                      # 配置主从新增
log-bin=/iba/mysql/mysql-bin       # 配置主从薪增

[mysql.server]
basedir=/usr/local/mysql

重启 MySQL

/etc/init.d/mysql stop
/etc/init.d/mysql start

创建复制用户

mysql -uroot -p

grant replication slave on *.* to rep@'192.168.0.%' identified by '123';
flush privileges;

从库操作

# 开放防火墙
firewall-cmd --permanent --add-rich-rule="rule family="ipv4" source address="192.168.0.0/16" accept"
firewall-cmd --reload

# 创建专用用户
mkdir /iba/software
groupadd mysql
useradd -r -g mysql mysql
cd /usr/local

# 上传软件 mysql-5.7.20-linux-glibc2.12-x86_64.tar.gz  导 /iba/software
tar zxvf /iba/software/mysql-5.7.20-linux-glibc2.12-x86_64.tar.gz
mv mysql-5.7.20-linux-glibc2.12-x86_64 mysql

cd /iba
mkdir -p mysql/data -p
chown -R mysql.mysql mysql
cd /usr/local/mysql/

# 初始化 mysql
bin/mysqld --initialize --basedir=/usr/local/mysql --datadir=/iba/mysql/data --user=mysql
# 需要记住密码

echo "export PATH=/usr/local/mysql/bin:$PATH" >> /etc/profile
source /etc/profile

# 编辑 my.cnf  文件
vi /etc/my.cnf
[mysqld]
innodb_buffer_pool_size = 1024M
character_set_server = utf8mb4
skip-name-resolve
innodb_file_per_table = 1
basedir=/usr/local/mysql
datadir=/iba/mysql/data
port=3306
user=mysql

sql_mode=NO_ENGINE_SUBSTITUTION,STRICT_TRANS_TABLES
max_connections=1024
max_allowed_packet=128M
show_compatibility_56 = on

default_password_lifetime=0

server-id = 2
read-only

[mysql.server]
basedir=/usr/local/mysql

# 配置启动脚本
cp support-files/mysql.server /etc/init.d/mysql
chmod +x /etc/init.d/mysql
chkconfig --add mysql
chkconfig --level 345 mysql on

# 启动 mysql
/etc/init.d/mysql start

# 备份MySQL主库的数据库
cd /iba/software
mysqldump -h192.168.0.237 -uroot -p'123456' --all-databases --master-data=1 |gzip > 237_bak.sql.gz

yum install gunzip -y
gunzip  237_bak.sql.gz

# 导入数据

mysql -uroot -p
# 输入上面获取的密码

source 237_bak.sql

flush privileges;

查看主库位置

head -n 40  237_bak.sql |grep "CHANGE"
# 得到下面信息,记录下来
CHANGE MASTER TO MASTER_LOG_FILE='mysql-bin.000001', MASTER_LOG_POS=4369252;

开启主从

mysql -uroot -p
change master to master_host='192.168.0.237', master_port=3306, master_user='rep', master_password='123',master_log_file='mysql-bin.000001',master_log_pos=4369252;

start slave;
flush privileges;

# 检查主从复制状态
show slave  status;

# 到下面两个进程正常即可
Slave_IO_Running: Yes
Slave_SQL_Running: Yes

相关命令详解

# mysqldump 命令解释
-A 表示备份所有库
-B 表示增加use DB 和 drop 等(导库时会直接覆盖原来的)
-F, --flush-logs
-R 备份存储过程(-- routines)
--triggers 备份触发器
-E 备份定时任务(-- events)
--master-data=2 在备份文件中以注释的形式记录备份开始时binlog的position,默认值是1,不注释
--single-transaction 可以保证在备份过程中,整个备份集的数据一致性

# 重置从库信息
reset slave all;

参考

https://www.jianshu.com/p/6ed2cc292077
01-06 16:47