主从复制
最后更新: 2026-01-22
作者: MySQL Team
页面目录
第十二章:主从复制
12.1 复制原理
复制架构
┌─────────────┐ ┌─────────────┐
│ Master │ ──── binlog ────> │ Slave │
│ (主库) │ │ (从库) │
└─────────────┘ └─────────────┘
│ │
v v
binlog file relay-log file
+ 本地执行
复制流程
1. Master: 将数据变更写入 binlog
2. Master: 发送 binlog 事件到 Slave
3. Slave: 接收事件写入 relay-log
4. Slave: 读取 relay-log 并在本地执行
复制方式
| 方式 | 说明 | 优点 | 缺点 |
|---|---|---|---|
| 异步复制 | 主库不等待从库确认 | 性能高 | 可能丢失数据 |
| 半同步复制 | 至少一个从库确认 | 数据安全性高 | 有延迟 |
| 全同步复制 | 所有从库确认 | 数据安全 | 性能低 |
12.2 配置主库
配置文件
[mysqld]
server-id = 1
log_bin = /var/lib/mysql/mysql-bin
binlog_format = ROW
expire_logs_days = 7
sync_binlog = 1
创建复制账号
-- 创建专用复制账号
CREATE USER 'repl'@'%' IDENTIFIED WITH mysql_native_password BY 'ReplPassword123!';
GRANT REPLICATION SLAVE ON *.* TO 'repl'@'%';
FLUSH PRIVILEGES;
获取 binlog 位置
-- 查看当前 binlog 状态
SHOW MASTER STATUS;
-- 输出示例:
-- File: mysql-bin.000001
-- Position: 1234
-- Binlog_Do_DB: mydb
-- Binlog_Ignore_DB: mysql
锁表备份
# 方式1: 使用 mysqldump
mysqldump -u root -p --all-databases --master-data=2 > backup.sql
# 方式2: 手动锁表
FLUSH TABLES WITH READ LOCK;
SHOW MASTER STATUS;
-- 记录 File 和 Position
-- 执行备份...
UNLOCK TABLES;
12.3 配置从库
配置文件
[mysqld]
server-id = 2
relay_log = /var/lib/mysql/mysql-relay-bin
log_slave_updates = 1
read_only = 1
super_read_only = 1
启动复制
-- 设置主库信息
CHANGE MASTER TO
MASTER_HOST = '192.168.1.100',
MASTER_PORT = 3306,
MASTER_USER = 'repl',
MASTER_PASSWORD = 'ReplPassword123!',
MASTER_LOG_FILE = 'mysql-bin.000001',
MASTER_LOG_POS = 1234;
-- 启动复制
START SLAVE;
-- 查看复制状态
SHOW SLAVE STATUS\G
重要参数
-- 设置中继日志过期时间
SET GLOBAL relay_log_expire_logs_days = 7;
-- 跳过复制错误
SET GLOBAL sql_slave_skip_counter = 1;
STOP SLAVE; SET GLOBAL sql_slave_skip_counter = 1; START SLAVE;
-- 半同步复制(需要安装插件)
INSTALL PLUGIN rpl_semi_sync_master SONAME 'semisync_master.so';
INSTALL PLUGIN rpl_semi_sync_slave SONAME 'semisync_slave.so';
12.4 复制管理
查看复制状态
-- 查看从库状态
SHOW SLAVE STATUS\G
-- 关键字段说明:
-- Slave_IO_Running: IO 线程运行状态
-- Slave_SQL_Running: SQL 线程运行状态
-- Last_Error: 最近的错误
-- Seconds_Behind_Master: 复制延迟(秒)
-- Master_Log_File: 读取的主库 binlog
-- Relay_Master_Log_File: 执行的 binlog
常用管理命令
-- 停止复制
STOP SLAVE;
-- 重置复制
RESET SLAVE ALL;
-- 查看所有从库
SHOW SLAVE HOSTS;
-- 查看主库信息
SHOW MASTER INFO;
-- 重连主库
STOP SLAVE IO_THREAD;
START SLAVE IO_THREAD;
常见问题处理
-- 问题1: 复制中断
SHOW SLAVE STATUS\G
-- 查看 Last_Error
-- 根据错误类型修复
-- 问题2: 主键冲突
-- 从库已有数据,需要跳过或删除
STOP SLAVE;
SET GLOBAL sql_slave_skip_counter = 1;
START SLAVE;
-- 问题3: 数据不一致
-- 重新同步数据
STOP SLAVE;
-- 重新导入主库数据
CHANGE MASTER TO ...;
START SLAVE;
12.5 GTID 复制
什么是 GTID
GTID(Global Transaction Identifier)全局事务标识符,是事务的唯一标识。
配置 GTID
[mysqld]
gtid_mode = ON
enforce_gtid_consistency = ON
使用 GTID 复制
-- 主库和从库都需要配置 GTID
-- 从库配置
CHANGE MASTER TO
MASTER_HOST = '192.168.1.100',
MASTER_PORT = 3306,
MASTER_USER = 'repl',
MASTER_PASSWORD = 'ReplPassword123!',
MASTER_AUTO_POSITION = 1;
-- 启动复制
START SLAVE;
-- 自动定位 binlog 位置,无需指定 FILE 和 POS
GTID 管理
-- 查看 GTID 执行状态
SHOW MASTER STATUS;
SHOW SLAVE STATUS;
-- 查看 GTID 集合
SELECT @@GLOBAL.gtid_executed;
SELECT @@GLOBAL.gtid_purged;
-- 设置从库跳过某些 GTID
SET GTID_NEXT = 'duplicate_transaction_uuid:1';
BEGIN; COMMIT;
SET GTID_NEXT = AUTOMATIC;
12.6 级联复制
配置示意图
Master -> Slave1 -> Slave2 -> Slave3
Slave1 配置(作为其他从库的主库)
[mysqld]
server-id = 2
log_bin = /var/lib/mysql/mysql-bin
log_slave_updates = ON
binlog_format = ROW
Slave2 配置
-- Slave2 以 Slave1 为源
CHANGE MASTER TO
MASTER_HOST = '192.168.1.102', -- Slave1 IP
MASTER_PORT = 3306,
MASTER_USER = 'repl',
MASTER_PASSWORD = 'ReplPassword123!',
MASTER_AUTO_POSITION = 1;
12.7 复制优化
监控复制延迟
-- 查看延迟
SHOW SLAVE STATUS\G
-- Seconds_Behind_Master: 0 表示无延迟
-- 使用心跳表检测延迟
CREATE TABLE heartbeat (
ts datetime NOT NULL DEFAULT current_timestamp,
PRIMARY KEY (id)
) ENGINE=InnoDB;
-- 主库定期更新
UPDATE heartbeat SET ts = NOW() WHERE id = 1;
-- 从库计算延迟
SELECT UNIX_TIMESTAMP() - UNIX_TIMESTAMP(ts) FROM heartbeat;
优化复制性能
-- 从库参数优化
[mysqld]
slave_parallel_workers = 4 -- 并行复制线程数
slave_parallel_type = LOGICAL_CLOCK -- 并行复制类型
slave_preserve_commit_order = 1 -- 保持提交顺序
-- 主库参数优化
[mysqld]
sync_binlog = 1000 -- 组提交优化
binlog_rows_query_log_events = ON -- 记录原始查询
12.8 本章小结
✅ 主从复制:通过 binlog 实现数据同步
✅ 异步复制:性能高但可能丢数据
✅ GTID 复制:全局事务标识,更易管理
✅ 半同步复制:提高数据安全性
✅ 复制监控:关注延迟和错误状态