备份是数据库运维的最后一道防线。没有备份的数据库,数据丢失时只能认栽。 本文系统讲解 MySQL 的备份方案(逻辑备份 vs 物理备份)、备份策略、以及基于 binlog 的 PITR(时间点恢复),并给出完整的恢复演练流程。
| 分类 | 说明 | 工具 |
|---|---|---|
| 逻辑备份 | 导出 SQL/数据文件,跨版本可移植 | mysqldump |
| 物理备份 | 直接复制数据文件,恢复快 | xtrabackup(Percona) |
| 全量备份 | 备份全部数据 | 两者都支持 |
| 增量备份 | 只备份上次备份以来的变化 | 物理增量 + binlog |
| 在线备份 | 不停服务备份(热备) | xtrabackup |
| 离线备份 | 停服备份(冷备) | 停库复制文件 |
# 导出整个数据库(含结构 + 数据)
mysqldump -uroot -p --single-transaction --master-data=2 mydb > mydb.sql
# 导出单表
mysqldump -uroot -p mydb users > users.sql
# 只导出结构(不导出数据)
mysqldump -uroot -p --no-data mydb > mydb_schema.sql关键参数:
--single-transaction:在事务内备份,保证一致性快照(InnoDB),避免锁表。在线备份必备。--master-data=2:在备份文件中记录 binlog 位置,做增量/PITR 必需。--routines --triggers:同时导出存储过程、触发器。mysql -uroot -p mydb < mydb.sql逻辑备份特点:
xtrabackup(Percona XtraBackup)是在线物理备份的主流工具,直接复制数据文件,恢复速度快,适合大数据量。
# 全量备份
xtrabackup --backup --target-dir=/backup/full --host=localhost --user=root --password=xxx
# 应用日志(使备份一致)
xtrabackup --prepare --target-dir=/backup/full# 基于全量做增量1
xtrabackup --backup --target-dir=/backup/inc1 --incremental-basedir=/backup/full
# 基于增量1做增量2
xtrabackup --backup --target-dir=/backup/inc2 --incremental-basedir=/backup/inc1
# 恢复时:先 prepare 全量,再 apply 各增量
xtrabackup --prepare --target-dir=/backup/full --apply-log-only
xtrabackup --prepare --target-dir=/backup/full --incremental-dir=/backup/inc1
xtrabackup --prepare --target-dir=/backup/full --incremental-dir=/backup/inc2# 停止 MySQL
systemctl stop mysql
# 清空数据目录,拷回备份文件
rm -rf /var/lib/mysql/*
cp -r /backup/full/* /var/lib/mysql/
chown -R mysql:mysql /var/lib/mysql
# 启动
systemctl start mysql物理备份特点:
只恢复全量备份,会丢失备份之后的所有变更。PITR 通过全量备份 + binlog 恢复到任意时间点:
时间线:
A(全量备份点) ----binlog----> B(误删时刻) ---- 恢复到B之前思路:
--master-data=2 记录的 binlog 位置,回放该位置之后、误删时刻之前的 binlog。log_bin=ON。--master-data=2 记录 binlog 坐标。# 1. 恢复全量备份
mysql -uroot -p mydb < mydb.sql
# 2. 确认全量备份的 binlog 位置(mydb.sql 头部的 CHANGE MASTER 语句)
# 例: MASTER_LOG_POS=100, MASTER_LOG_FILE='mysql-bin.000003'
# 3. 将 binlog 转为 SQL
mysqlbinlog --start-position=100 --stop-datetime='2026-08-07 10:00:00' \
mysql-bin.000003 > pitr.sql
# 4. 应用增量 SQL
mysql -uroot -p < pitr.sqlmysqlbinlog 关键参数:
--start-position / --stop-position:按位置截取。--start-datetime / --stop-datetime:按时间截取(恢复"误删前一刻")。--database=mydb:只恢复指定库。恢复误删建议:先恢复到误删之前的时间点,且建议在临时实例上演练,确认无误再切换。
推荐组合策略:
- 每日全量备份(物理 xtrabackup,凌晨低峰)
- 每小时/每 N 分钟备份 binlog(或开启 binlog 归档)
- 全量备份保留 N 天,binlog 保留足够时长--slave-info),减少对主库压力。| 特性 | 旧版(本文编写时,MySQL 5.7) | 当前(MySQL 8.0/8.4 LTS) |
|---|---|---|
| 默认字符集 | utf8(需显式配置 utf8mb4) | utf8mb4(MySQL 8.0 起默认) |
| 索引 | 普通 B+Tree | 降序索引、隐藏索引、函数索引(8.0+) |
| SQL 能力 | 常规查询 | 递归 CTE、窗口函数(8.0+) |
| 版本策略 | 5.7 | 8.0(主流)/ 8.4 LTS / 9.x(创新版) |
| Java 驱动 | mysql-connector-java 5.x/8.0 | mysql-connector-j 8.x/9.x |
本文基于 MySQL 5.7 编写,核心概念(索引、事务、锁、MVCC、InnoDB)在 8.0/8.4 中依然适用;8.0 的默认字符集、隐藏索引与 SQL 增强(CTE/窗口函数)是升级后的主要差异。