当前位置: 首页 > news >正文

MySQL 主从复制完整配置指南

MySQL 主从复制完整配置指南

在企业级应用中,单台 MySQL 数据库面临数据丢失风险高、高并发下性能不足等问题。MySQL 主从复制通过「主库写、从库读」的架构,可实现实时灾备、读写分离与数据备份,是解决上述问题的核心方案。本文基于文档内容,详细拆解主从复制的原理、配置步骤与验证方法,并补充关键注意事项与扩展说明,确保架构稳定可用。

一、MySQL 主从复制基础认知

1. 为何需要主从复制?

单台 MySQL 数据库存在两大核心隐患,主从复制正是针对这些问题设计:

  • 数据安全风险:单库宕机(如硬件故障、误操作)可能导致数据永久丢失,主从复制可通过从库实现实时灾备,故障时快速切换。
  • 性能瓶颈问题:业务增长后,读请求(如查询)占比极高,单库无法承载高并发,主从复制可将读请求分流到从库,提升整体服务质量。

2. 主从复制的核心作用

作用分类具体说明
实时灾备从库实时同步主库数据,主库故障时,从库可立即切换为新主库,避免业务中断与数据丢失。
读写分离主库仅处理写操作(插入、更新、删除),从库处理读操作(查询),分散单库压力,提升并发能力。
数据备份从库可作为备份源,进行全量/增量备份,避免直接在主库备份占用资源,影响业务运行。

3. 主从复制的常见形式

根据业务需求,主从复制可灵活部署为以下架构:

  • 一主一从:最基础架构,1 台主库 + 1 台从库,适用于中小业务的灾备与简单读写分离。
  • 主主复制:2 台服务器互为主从,均可读写,适用于需双向同步数据的场景(如跨地域业务),但需注意冲突处理。
  • 一主多从:1 台主库 + 多台从库,可进一步扩展读性能(如 3 台从库分别承载不同业务的读请求),是高并发读场景的主流选择。
  • 多主一从:MySQL 5.7 及以上支持,多台主库数据同步到 1 台从库,适用于数据汇总场景(如多分支业务数据统一分析)。
  • 联级复制:从库作为「中间主库」,再同步给下一级从库(主库 → 从库1 → 从库2),减少主库的 I/O 压力,适用于从库数量极多的场景。

二、MySQL 主从复制原理(核心机制)

主从复制基于「日志同步 + 线程协作」实现,核心涉及 3 个关键线程与 2 类日志,具体流程如下:

  1. 主库生成 binlog 日志与 log dump 线程
    主库将所有写操作(INSERT/UPDATE/DELETE)记录到二进制日志(binlog)中,确保操作可追溯。同时,主库启动 log dump 线程,负责监听 binlog 日志的变化,并将新日志发送给从库的 I/O 线程。

  2. 从库 I/O 线程接收日志并写入中继日志
    从库启动 I/O 线程,主动连接主库的 log dump 线程,请求获取 binlog 日志。I/O 线程将接收到的 binlog 日志写入从库本地的「中继日志(relay log)」,避免直接解析日志导致业务延迟。

  3. 从库 SQL 线程解析中继日志并执行
    从库启动 SQL 线程,实时读取中继日志中的内容,将其解析为与主库一致的 SQL 操作,并在从库中执行。最终实现主从库的数据一致性。

总结:主库通过 binlog 记录操作,从库通过 I/O 线程拉取日志、SQL 线程执行操作,三者协作完成「主写从读、数据同步」的核心目标。

三、MySQL 主从复制配置实战(一主一从)

1. 环境准备与需求说明

本次配置为「一主一从」架构,主库负责写操作,从库负责读操作,环境信息如下:

数据库角色IP 地址操作系统MySQL 版本初始数据状态核心职责
主数据库172.16.12.128CentOS 7MySQL 5.7有数据(含 student、teacher 库)处理写操作,生成 binlog
从数据库172.16.12.129CentOS 7MySQL 5.7无业务数据(仅系统库)同步主库数据,处理读操作

前置条件

  • 两台服务器已安装 MySQL 5.7(安装步骤可参考前文「MySQL 多实例部署」中的软件下载、解压、权限配置流程)。
  • 主从服务器之间网络互通(可通过 ping 172.16.12.129 验证),且防火墙开放 3306 端口(MySQL 默认端口):
    # 主从服务器均执行,开放 3306 端口并重启防火墙
    [root@localhost ~]# firewall-cmd --zone=public --add-port=3306/tcp --permanent
    [root@localhost ~]# firewall-cmd --reload
    

2. 配置步骤详解(6 步完成)

步骤 1:确保主从库数据一致(全量备份与还原)

主从复制的前提是「初始数据完全一致」,否则后续同步会出现数据偏差。需先对主库进行全量备份,再将备份文件还原到从库:

1.1 主库锁表与全量备份

为避免备份期间主库有新写操作导致数据不一致,需先给主库加「读锁」,再执行备份:

# 1. 登录主库,执行读锁(此终端需保持打开,备份完成后再退出)
[root@localhost ~]# mysql -uroot -predhat
mysql> FLUSH TABLES WITH READ LOCK;  # 锁定所有表,仅允许读操作
Query OK, 0 rows affected (0.00 sec)# 2. 新开一个终端,执行全量备份(--all-databases 备份所有库,含系统库与业务库)
[root@localhost ~]# mysqldump -uroot -predhat --all-databases > /opt/all-202408050937.sql
# 提示 “Using a password on the command line interface can be insecure.” 为正常警告# 3. 查看备份文件是否生成
[root@localhost ~]# ls /opt/
all-202408050937.sql  # 备份文件存在,备份成功
1.2 备份文件传输到从库

通过 scp 命令将主库的备份文件传输到从库的 /opt/ 目录:

# 主库终端执行,将备份文件传给从库(需输入从库 root 密码)
[root@localhost ~]# scp /opt/all-202408050937.sql root@172.16.12.129:/opt/
root@172.16.12.129's password:  # 输入从库 root 密码
all-202408050937.sql  100%  786KB  10.6MB/s   00:00  # 传输完成
1.3 主库解锁表

备份文件传输完成后,回到主库的读锁终端,退出 MySQL 以解除锁表(若不解锁,主库将无法执行写操作):

mysql> quit  # 退出主库,自动解除读锁
Bye
1.4 从库还原备份数据

在从库终端,执行备份文件还原,确保从库数据与主库一致:

# 从库执行还原命令(将备份文件导入 MySQL)
[root@localhost ~]# mysql -uroot -predhat < /opt/all-202408050937.sql# 验证还原结果:查看从库数据库列表,应与主库一致(含 student、teacher 库)
[root@localhost ~]# mysql -uroot -predhat -e 'show databases;'
+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| student            |  # 业务库,主库同步过来
| sys                |
| teacher            |  # 业务库,主库同步过来
+--------------------+
步骤 2:主库创建同步账号并授权

从库需通过专用账号连接主库获取 binlog 日志,因此需在主库创建一个仅用于「主从同步」的账号(如 repl),并授予 REPLICATION SLAVE 权限:

# 登录主库
[root@localhost ~]# mysql -uroot -predhat# 1. 创建同步账号 repl,允许从库(172.16.12.129)连接,密码为 redhat
mysql> CREATE USER 'repl'@'172.16.12.129' IDENTIFIED BY 'redhat';
Query OK, 0 rows affected (0.00 sec)# 2. 授予 repl 账号同步权限(REPLICATION SLAVE 权限仅用于主从同步,无其他权限)
mysql> GRANT REPLICATION SLAVE ON *.* TO 'repl'@'172.16.12.129';
Query OK, 0 rows affected (0.00 sec)# 3. 刷新权限,使配置生效
mysql> FLUSH PRIVILEGES;
Query OK, 0 rows affected (0.00 sec)# (可选)验证账号权限:查看 repl 账号的权限列表
mysql> SHOW GRANTS FOR 'repl'@'172.16.12.129';
+---------------------------------------------------+
| Grants for repl@172.16.12.129                     |
+---------------------------------------------------+
| GRANT REPLICATION SLAVE ON *.* TO 'repl'@'172.16.12.129' |
+---------------------------------------------------+
步骤 3:配置主库(启用 binlog 与唯一标识)

主库需启用二进制日志(binlog),并设置唯一的 server-id(主库 server-id 必须小于从库,避免冲突),配置文件为 /etc/my.cnf

# 编辑主库配置文件
[root@localhost ~]# vim /etc/my.cnf# 在 [mysqld] 段落中添加以下配置(原有配置保留,新增关键参数)
[mysqld]
datadir=/var/lib/mysql
socket=/var/lib/mysql/mysql.sock
log-bin=mysql-bin  # 启用 binlog 日志,日志文件前缀为 mysql-bin(如 mysql-bin.000001)
server-id=1        # 主库唯一标识,取值范围 1-4294967295,必须与从库不同且更小
symbolic-links=0
log-error=/var/log/mysqld.log
pid-file=/var/run/mysqld/mysqld.pid# 重启 MySQL 服务,使配置生效
[root@localhost ~]# systemctl restart mysqld# 验证主库是否启动成功(查看 3306 端口是否监听)
[root@localhost ~]# ss -antl
LISTEN     0      80                     :::3306                               :::*  # 3306 端口监听,启动成功# 查看主库 binlog 状态(记录 log 文件名称与 Position 值,后续从库配置需用到)
[root@localhost ~]# mysql -uroot -predhat
mysql> SHOW MASTER STATUS;
+------------------+----------+--------------+------------------+-------------------+
| File             | Position | Binlog_Do_DB | Binlog_Ignore_DB | Executed_Gtid_Set |
+------------------+----------+--------------+------------------+-------------------+
| mysql-bin.000001 |      154 |              |                  |                   |
+------------------+----------+--------------+------------------+-------------------+
# 关键信息:File=mysql-bin.000001,Position=154(从库需指定这两个值同步)
步骤 4:配置从库(启用中继日志与唯一标识)

从库需设置唯一的 server-id(大于主库),并启用中继日志(relay log),配置文件同样为 /etc/my.cnf

# 编辑从库配置文件
[root@localhost ~]# vim /etc/my.cnf# 在 [mysqld] 段落中添加以下配置(原有配置保留,新增关键参数)
[mysqld]
datadir=/var/lib/mysql
socket=/var/lib/mysql/mysql.sock
server-id=2        # 从库唯一标识,必须大于主库的 server-id(主库为 1,此处设为 2)
relay-log=mysql-relay-bin  # 启用中继日志,日志文件前缀为 mysql-relay-bin
symbolic-links=0
log-error=/var/log/mysqld.log
pid-file=/var/run/mysqld/mysqld.pid# 重启 MySQL 服务,使配置生效
[root@localhost ~]# systemctl restart mysqld# 验证从库是否启动成功(查看 3306 端口监听)
[root@localhost ~]# ss -antl
LISTEN     0      80                     :::3306                               :::*  # 启动成功
步骤 5:从库关联主库并启动同步

从库需通过 CHANGE MASTER TO 命令关联主库信息(主库 IP、同步账号、binlog 文件名与 Position 值),再启动同步线程:

# 登录从库
[root@localhost ~]# mysql -uroot -predhat# 1. 配置主库信息(替换为实际主库参数,Position 与 File 需与主库 SHOW MASTER STATUS 结果一致)
mysql> CHANGE MASTER TO-> MASTER_HOST='172.16.12.128',  # 主库 IP 地址-> MASTER_USER='repl',           # 主库创建的同步账号-> MASTER_PASSWORD='redhat',     # 同步账号密码-> MASTER_LOG_FILE='mysql-bin.000001',  # 主库 binlog 文件名(来自 SHOW MASTER STATUS)-> MASTER_LOG_POS=154;           # 主库 binlog 位置(来自 SHOW MASTER STATUS)
Query OK, 0 rows affected, 2 warnings (0.33 sec)# 2. 启动从库同步线程(I/O 线程与 SQL 线程)
mysql> START SLAVE;
Query OK, 0 rows affected (0.01 sec)# 3. 查看从库同步状态(核心验证步骤,需确保 Slave_IO_Running 与 Slave_SQL_Running 均为 Yes)
mysql> SHOW SLAVE STATUS \G  # \G 表示纵向显示结果,更易读
*************************** 1. row ***************************Slave_IO_State: Waiting for master to send event  # I/O 线程状态:等待主库发送日志Master_Host: 172.16.12.128  # 主库 IP 正确Master_User: repl           # 同步账号正确Master_Port: 3306           # 主库端口正确Connect_Retry: 60             # 连接失败重试间隔(秒)Master_Log_File: mysql-bin.000001  # 主库 binlog 文件名正确Read_Master_Log_Pos: 154             # 主库 binlog 位置正确Relay_Log_File: mysql-relay-bin.000002  # 中继日志文件名Relay_Log_Pos: 320             # 中继日志位置Relay_Master_Log_File: mysql-bin.000001  # 关联的主库 binlog 文件名Slave_IO_Running: Yes             # ✅ I/O 线程运行正常(必须为 Yes)Slave_SQL_Running: Yes             # ✅ SQL 线程运行正常(必须为 Yes)Replicate_Do_DB:                 # 需同步的数据库(默认所有库)Replicate_Ignore_DB:                 # 忽略同步的数据库(默认无)

常见问题排查

  • Slave_IO_Running: No:检查主从网络是否互通、同步账号密码是否正确、主库 binlog 文件名/Position 是否正确。
  • Slave_SQL_Running: No:检查主从初始数据是否一致(如备份还原是否成功)、从库是否有未同步的 SQL 冲突(可通过 relay_log_recovery=1 配置自动恢复中继日志)。
步骤 6:测试主从同步效果

通过在主库执行写操作,验证从库是否能实时同步数据,确保架构生效:

6.1 主库执行写操作(插入数据)
# 登录主库,切换到 student 库,向 bj2 表插入数据
[root@localhost ~]# mysql -uroot -predhat
mysql> USE student;
Database changed# 查看 bj2 表初始状态(为空)
mysql> SELECT * FROM bj2;
Empty set (0.00 sec)# 插入 3 条测试数据
mysql> INSERT INTO bj2 VALUES (1,'sean',20),(2,'tom',23),(3,'jerry',30);
Query OK, 3 rows affected (0.00 sec)# 验证主库数据插入成功
mysql> SELECT * FROM bj2;
+----+-------+------+
| id | name  | age  |
+----+-------+------+
|  1 | sean  |   20 |
|  2 | tom   |   23 |
|  3 | jerry |   30 |
+----+-------+------+
6.2 从库验证数据同步
# 登录从库,切换到 student 库,查看 bj2 表数据
[root@localhost ~]# mysql -uroot -predhat
mysql> USE student;
Database changed# 查看 bj2 表数据(应与主库完全一致,说明同步成功)
mysql> SELECT * FROM bj2;
+----+-------+------+
| id | name  | age  |
+----+-------+------+
|  1 | sean  |   20 |
|  2 | tom   |   23 |
|  3 | jerry |   30 |
+----+-------+------+

四、主从复制进阶配置与注意事项

1. 读写分离实现(扩展)

主从复制仅完成数据同步,需通过「应用层配置」或「中间件」实现读写分离:

  • 应用层配置:在代码中判断 SQL 类型,写操作(INSERT/UPDATE/DELETE)路由到主库,读操作(SELECT)路由到从库(如 Java 中通过 MyBatis 拦截器实现)。
  • 中间件方案:使用 MySQL 中间件(如 MyCat、ProxySQL)统一管理主从地址,中间件自动实现读写分离,应用只需连接中间件地址,无需修改代码,适用于复杂架构。

2. 主从延迟优化(关键问题解决)

主从复制存在「延迟」(从库数据比主库晚几秒到几分钟),主要原因与优化方案如下:

延迟原因优化方案
从库 SQL 线程执行慢1. 从库使用更高配置的 CPU(SQL 线程为单线程,CPU 性能影响大);2. 避免在主库执行大事务(如批量更新),拆分为小事务。
主库 binlog 传输慢1. 主从使用内网高速网络(如万兆网卡);2. 主库启用 binlog_group_commit(MySQL 5.7+ 特性,批量提交 binlog,减少 I/O 次数)。
从库中继日志堆积1. 从库启用 relay_log_info_repository=TABLE(将中继日志信息存入表,避免文件 I/O 瓶颈);2. 定期清理过期中继日志(通过 expire_logs_days 配置日志保留天数)。

3. 主库故障切换(灾备实战)

当主库宕机时,需将从库切换为新主库,步骤如下:

  1. 确认主库故障:通过 pingtelnet 172.16.12.128 3306 验证主库是否不可用。
  2. 停止从库同步:在从库执行 STOP SLAVE;,避免主库恢复后数据冲突。
  3. 从库提升为主库:在从库执行 RESET MASTER;,生成新的 binlog 日志,从库变为新主库。
  4. 应用切换地址:将应用的数据库地址从原主库(172.16.12.128)改为新主库(172.16.12.129)。
  5. 原主库恢复后处理:原主库修复后,配置为新主库的从库(执行 CHANGE MASTER TO 关联新主库),实现新的主从架构。

4. 安全加固建议

  • 同步账号权限最小化:仅授予 REPLICATION SLAVE 权限,避免授予 ALL PRIVILEGES 等高危权限。
  • binlog 日志加密:MySQL 8.0+ 支持 binlog 加密(binlog_encryption=ON),防止日志被篡改或窃取。
  • 定期备份从库:从库作为灾备源,需定期执行全量备份(如每天一次),并测试备份文件的可用性。
  • 禁用符号链接:配置文件中 symbolic-links=0,避免通过符号链接篡改数据文件。

五、总结

MySQL 主从复制是企业级数据库架构的基础,通过「主写从读、数据同步」解决了单库的数据安全与性能问题。本文基于 CentOS 7 + MySQL 5.7 环境,详细讲解了一主一从架构的配置流程,核心步骤可概括为「数据一致 → 账号授权 → 主库配置 → 从库关联 → 同步验证」。在实际应用中,需结合业务需求选择合适的主从形式,并通过读写分离、延迟优化、故障切换等进阶配置,确保架构稳定、高效、可靠。

http://www.dtcms.com/a/394150.html

相关文章:

  • 力扣每日一刷Day 23
  • LeetCode 53. 最大子数组和(四种解题思路)包含扩展返回最大和的数组
  • RTX 4090助力深度学习:从PyTorch到生产环境的完整实践指南——高效模型训练与优化策略
  • 23种设计模式之【桥接模式】-核心原理与 Java实践
  • LabVIEW手部运动机能实验
  • 669. 修剪二叉搜索树
  • 大QMT自动可转债申购
  • PolarCTF PWN 网络安全2023秋季个人挑战赛刷题
  • MySQL-day4_02(事务)
  • JUC(8)线程安全集合类
  • springboot中@EnableAsync有什么作用
  • Spark专题-第二部分:Spark SQL 入门(6)-算子介绍-Generate
  • C#练习题——Dictionary
  • Feign
  • SPA小说集之三《森林城市反甩锅战:ERP的权责边界》
  • Qt(模态对话框和非模态对话框)
  • 【无标题】物联网 frid卡控制
  • 【LLM LangChain】 模型绑定工具+调用工具(手动调用/LangGraph/AgentExecutor)+相关注意事项
  • 图神经网络(GNN)入门:用PyG库处理分子结构与社会网络
  • 【C++】编码表 STL简介:STL是什么,版本,六大组件,重要性以及学习方法总结
  • show_interrupts函数的进一步解析及irq_desc结构体
  • Kafka面试精讲 Day 19:JVM调优与内存管理
  • 10.vector容器
  • Linux系统介绍
  • MFC中的CMFCDynamicLayout类的介绍
  • UniScene 统一驾驶场景 | 生成语义占据 | 生成多视角视频 | 生成激光点云 CVPR2025
  • Git 简明教程:从原理到实战
  • 【设计模式】中介者模式
  • nginx添加modsecurity插件
  • 代码上传Github:SSH法