物理备份与逻辑备份
|--------|---------------------|-----------------------------------------------|
| 方式 | 逻辑备份 | 物理备份 |
| 内容 | 备份的是数据库的结构、数据 | 备份的是数据库文件 物理数据文件; 日志文件binlog二进制日志; 配置文件my.cnf |
| 工具 | 常用 mysqldump | 常用 xtrabackup |
| 特点 | 可读性强,跨平台,可用于部分恢复和迁移 | 备份速度快,恢复效率高 |
| 场景 | 适合中小型数据库 | 适合大规模数据库 |
逻辑备份备份的是一些命令,create啊insert into啊 所以可读性强
物理备份备份的是MySQL下面的一个data的文件,所以效率高
逻辑备份
完整灾备组合:mysqldump(逻辑全量基线) + binlog(逻辑增量变更流水)
表级的全量备份与还原
例子:现在库里有两个表

退出MySQL,对tb_student进行备份
格式是:mysqldump -u用户名 -p密码 库名 表名 > 路径/文件名.sql
mysqldump -uroot -p123456 db_itheima tb_student > /root/tbstu.sql
进入mysql删除tb_student,现在只剩下一个表

还原备份,
格式:mysql -u用户名 -p密码 库名 < 存放备份的路径/备份文件
mysql -uroot -p123456 db_itheima < /root/tbstu.sql
方法2,
格式:
use 空数据库
source /存放备份的路径/备份名.sql
指定库的全量备份与还原
例如:
现在有用户root 密码123456 数据库db_itheima,给数据库备份,备份放在root下
mysqldump -uroot -p123456 --databases -F db_itheima > /root/db_itheima.sql
databases
db_itheima:库级备份核心参数
- 不加
--databases:备份文件只有建表、插入数据语句,恢复前必须手动先创建库、use 库名- 加
--databases:备份文件自带CREATE DATABASE IF NOT EXISTS db_itheima; USE db_itheima;恢复时不用手动建库,直接导入自动创建数据库-F 备份前刷新日志,主要是刷新二进制日志
还原
mysql -uroot -p'密码' < 后缀为.sql文件位置
mysql -uroot -p123456 < /root/db_itheima.sql
方法2,进入MySQL用source导入
source /root/db_itheima.sql;
这里不用手动新建库,执行 source /xxx/db_itheima.sql; 时,MySQL 会自动判断库是否存在,不存在就创建,存在就直接切换进去导入表数据。
全库的全量备份与还原
全库备份(-A 所有库一起导出)
用户root,密码123456,备份文件存放位置/root 备份文件名all_db_backup
mysqldump -uroot -p123456 -A > /root/all_db_backup.sql
等价写法
mysqldump -uroot -p --all-databases > all_db_backup.sql
搭配常用参数 --routines
# 全库备份 + 包含存储过程/函数 + 定时推荐写法
mysqldump -uroot -p -A --routines --events > all_full.sql
恢复全库备份文件
mysql -uroot -p123456 < all_db_backup.sql
方法2,
进入MySQL后source导入
mysql -uroot -p123456
source /root/all_db_backup.sql
☆ mysqldump 高级选项说明
|-----------------------|--------------------------------------------------------------------|
| 选项 | 正确描述 |
| --flush-logs, -F | 备份前刷新日志,主要是刷新二进制日志,创建一个新的二进制日志文件 |
| --flush-privileges | 在备份文件中添加FLUSH PRIVILEGES语句(当备份包含mysql系统库时自动添加) |
| --lock-all-tables, -x | 对所有数据库的所有表加全局读锁,保证一致性但影响服务可用性 |
| --lock-tables, -l | 对当前备份的每个数据库的所有表分别加锁(不如--single-transaction常用) |
| --single-transaction | 对InnoDB表使用事务隔离,通过START TRANSACTION WITH CONSISTENT SNAPSHOT获取一致性视图 |
逻辑增量日志【binlog】
- binlog:增量流水日志,不能单独恢复数据库,必须依赖一份 mysqldump 全量备份做基线,二者搭配才能恢复完整数据。
- mysqldump:全量逻辑备份(单独导入就能恢复完整库)
mysqldump 只是某一刻的全量快照,只能恢复到备份那一刻的数据。举个例子:
- 凌晨 2 点执行 mysqldump 全量备份;
- 上午 10 点误删整张表;
- 只靠 dump 恢复,只能回到凌晨 2 点,2 点~10 点之间 6 小时的数据全部丢失。
开启 binlog 后:全量备份 + 备份之后的 binlog 日志,就能恢复到故障发生前任意一秒,把中间所有新增 / 修改数据补回来。完整恢复流程:
- 导入 mysqldump 全量基线;
- 回放对应时间段的 binlog,补全增量操作。
binlog小命令
查看binlog 文件的存储路径与文件名前缀
show variables like 'log_bin_basename';

/export/software/mysql/data/:binlog 文件存放目录binlog:日志文件前缀,真实生成文件为:binlog.000001、binlog.000002、binlog.index
看看binlog打开没有,打开显示on,没打开显示off
show variables like 'log_bin';

查看正在写入的biglog文件,增量恢复的核心查询
show master status;

- binlog.000021:现在所有新增写操作都会写到这个文件
- Position:当前文件内的写入偏移位点(字节位置)
- 43094709:下一条 SQL 会写入这个字节位置,恢复时从这个位点之后取增量数据
故障恢复流程:
- 第一步:导入 mysqldump 全量备份(还原到备份那一刻的数据)
- 第二步:回放
binlog.000021,从位点43094709开始,把备份之后所有新增操作补回来
查看已生成的binlog文件
show binary logs;
开启binlog
需要修改my.cnf文件在哪 我们找一下他的路径
MySQL 读取配置文件有固定优先级,按顺序扫描这几个位置:
/etc/my.cnf/etc/mysql/my.cnf/usr/local/mysql/my.cnf~/.my.cnf(当前用户家目录隐藏文件)
直接全盘找
find / -name "my.cnf" 2>/dev/null

vim /etc/my.cnf
在**[mysqld]**段添加 / 修改配置:
如果日志文件路径不存在需要手动创建,并且赋予MySQL所属用户所属组的权限
# 开启二进制日志
log_bin = /export/software/mysql/data/binlog
# 日志文件名前缀,和你查到的basename保持一致
log_bin_basename = /export/software/mysql/data/binlog
# 可选:设置日志过期自动清理,避免磁盘占满
expire_logs_days = 7
# 生产推荐行模式binlog
binlog_format = ROW
重启
# CentOS7/8
systemctl restart mysqld
# 或传统service
service mysqld restart
查看,输出ON即开启完成。
show variables like 'log_bin';
增量备份
做完全量备份后,先记录当前位点,后续新增数据都从这个位点开始:
show master status;
查看binlog日志
show binary logs;
恢复单个 binlog 文件
mysqlbinlog --start-position=全量备份位点 /日志存放路径/binlog.000022 | mysql -uroot -p123456
有多个连续 binlog 文件(000022、000023)
# 先恢复第一个增量日志
mysqlbinlog --start-position=23 /data/sqlbak/binlog.000022 | mysql -uroot -p123456
# 再恢复后续完整日志(不用加start-position,从头读到尾)
mysqlbinlog /data/sqlbak/binlog.000023 | mysql -uroot -p123456
全量备份+增量备份完整实操
我们预设每周1进行全量备份,234567进行增量备份,突然发生灾难时,恢复周一的全量备份,再回复周一后的一些数据,也就是周一到现在这几天的增量备份
全量备份
现在有数据库db_itheima,数据库中有两张表,其中一个叫tb_student的表长这样,

我们现在开始对,指定数据库,db_itheima库,进行全量备份
mysqldump -uroot -p123456 --databases -F --routines db_itheima > /root/0624a.sql
-F:刷新 binlog(flush logs),全量备份完新开一个 binlog,方便后续增量恢复,这个是增量备份必带参数。--databases:备份时自带CREATE DATABASE + USE,恢复不用手动建库。- 专门备份存储过程、函数(procedure /function)

注意文件大小
记录当前的点位
show master status;

也就是发生灾难的时候,binlog.000023以及,后面的都是我们需要回复的
模拟灾难
【周一到灾难这天中间新加入了数据】

现在有一条数据是我们之前进行的全量备份里没有的
再创建一个视图
create view stu as select id,name,age,subject from tb_student;

这个视图也是全量备份里没有的
模拟【数据库丢失】

还原所有数据
还原全量备份
source /root/0624a.sql;

还原增量备份
也就是,还原,我们之前的一个视图和小乔的数据
看一下binlog日志
show binary logs;
还记得我们前面在全量备份后查看的点位吗 23 也就是23和!之后的binglog日志全部都是我们需要的

执行增量恢复命令(mysqlbinlog)
先看一下bin_log存放路径
show variables like 'log_bin%';

mysqlbinlog -v /export/software/mysql/data/binlog.000023 | head -300
输出示例,圈错了,起始点位要begin后面的也就是317
我们记住想要恢复的数据的上下的at后面的数字
增量恢复
mysqlbinlog --start-position=317 --stop-position=491 /export/software/mysql/data/binlog.000023 | mysql -uroot -p123456
视图那条不在这里 就找视图的上下文后面的at后面的数字 再执行一次这个命令
Xtrabackup 物理备份
Xtrabackup 是 Percona 开发的开源 MySQL 备份工具,主打高性能、低影响,能在不锁表的情况下,在线备份 InnoDB、XtraDB 等协议的数据库
**自学推荐的论坛:**https://opensource.actionsky.com/blog/
凌晨02:00开始备份,整个备份需要30分钟!
备份开始实际上只备份截止到02:00这段时间内的所有数据
**问题:**02:00 ~ 02:30这段时间,也可能会有增删改操作 => redo log重做日志中
**解决:**Xtrabackup不仅会备份截止到02:00这段时间内的所有数据,备份结束,其会把2:00-2:30这段时间的重写日志也执行一遍,写入到备份文件中。这样咱们得到的备份数据就是截止到02:30的所有内容。
- 工具:
percona-xtrabackup-80 - 原理对应:
xtrabackup --backup:拷贝磁盘数据文件(2:00 快照),同步抓取备份期间 redo 日志xtrabackup --prepare:回放包里的 redo 日志,把数据统一到备份结束时间点(原理图核心步骤)
- 环境:MySQL 默认数据目录
/var/lib/mysql
xtrabackup的下载安装
官方下载地址:www.percona.com/

dnf install -y ./percona-xtrabackup-80-8.0.35-31.1.el9.x86_64.rpm

学习物理备份的操作前我们需要了解一下redo log(重做日志) 和 **binlog(二进制日志),**MySQL 中的两种核心日志系统,分别服务于不同的场景
☆ redo log vs binlog
binlog 的设计目的,是为了支持复制(Replication)、数据恢复(Recovery)和审计(Audit);binlog(二进制日志)是逻辑日志(记录 SQL 语句 / 行变更)
-
复制:主库将 binlog 发送到从库,从库重放以同步数据;
-
恢复:基于时间点或位置恢复数据(如误删表后,通过回放 binlog 恢复部分操作);
-
审计:记录所有数据变更,可以用于做合规性检查;
redo log 是为了保障事务的持久性(Durability)和原子性(Atomicity)。redo log(重做日志)物理日志(记录 "磁盘哪一页改了、改成什么样")
-
通过顺序写日志替代随机写数据页,减少磁盘I/O;
-
确保事务提交后,即使数据库崩溃,未写入磁盘的数据也能通过redo log重做恢复;
所属维度
|------------|---------------------|------------------------|
| | redo log | binlog |
| 所属层级 | InnoDB 存储引擎层(其他引擎无) | MySQL 服务器层(与引擎无关) |
| 存储引擎依赖 | 仅 InnoDB 使用(核心机制) | 所有存储引擎的变更均记录(如 MyISAM) |
| 日志类型 | 物理日志(Physical Log) | 逻辑日志(Logical Log) |
| 格式 | InnoDB内部二进制格式,不可读 | mysqlbinlog工具解析 |
| 设计目的 | 事务保障,崩溃恢复 | 主从复制 |
| 常用关联工具 | Xtrbackup | mysqldump |
全量备份
本机正在运行的 MySQL 数据库做完整物理备份
- 连接对象:通过
-S /tmp/mysql.sock+bkuser账号,连的是当前服务器本地的 MySQL 服务; - 备份内容:MySQL 里所有库、表、索引、事务 redo 日志、表结构文件;
- 备份性质:热备份------ 不用停 MySQL,业务正常读写,不锁 InnoDB 表;
- 存放位置:你自己随便指定一个空目录(比如
/full_bak),所有备份文件全存在这里,和 MySQL 原数据目录完全分开。
简单说:把正在跑的 MySQL 整份数据,复制一份存到别的文件夹留作备用,防止删库、磁盘损坏丢数据
创建备份存放目录/full_alldata
mkdir /full_alldata
创建一个备份账号
日常备份只需要少量固定权限(锁表、读取事务、备份管理),没必要动用最高权限:
-
万一备份脚本泄露账号密码,黑客拿到 bkuser 只能做备份,无法删除业务数据;
-
root 泄露会导致整个数据库被篡改、清空,风险极大
-- 创建备份账号,允许本地登录,密码123456
create user if not exists bkuser@localhost identified by '123456';-- 给xtrabackup必备备份权限
grant backup_admin,reload,lock tables,process,replication client on . to bkuser@localhost;grant select on performance_schema.* to bkuser@localhost;
grant select on mysql.* to bkuser@localhost;-- 刷新权限生效
flush privileges;
exit;
执行全量备份(核心命令)
xtrabackup -S /tmp/mysql.sock --user=bkuser --password=123456 --backup --target-dir=/full_alldata
xtrabackup执行物理备份工具(你之前安装的 percona-xtrabackup-80)-S /tmp/mysql.sock指定 MySQL 本地套接字文件,用来本地免端口连接数据库;你环境sock不在默认/var/lib/mysql/,不加这个参数会报连接失败。--user=bkuser --password=123456使用专门创建的备份账号连接 MySQL,账号需要拥有备份相关权限。--backup【核心动作,对应原理图】开启备份模式,内部自动完成 2 件关键操作:- ① 拷贝磁盘上全部原始数据文件(原理图左侧:页 1 / 页 2 / 页 3 静态快照)
- ② 拷贝文件的同时持续抓取备份期间新生成的 redo 日志(原理图右侧所有 LSN 变更记录)全程不阻塞 InnoDB 表的增删改,属于热备份。
--target-dir=/full_alldata指定备份文件存放目录,所有拷贝的数据、redo 日志、元数据都会存在这里。
备份完成校验
执行完后查看目录,能看到完整数据文件 + 备份期间 redo 日志:
ls /full_alldata

所有文件就是一整套完整的 MySQL 物理副本,包含:
- 业务库文件夹(db_itheima 就是你上课测试的学生表库)
- InnoDB 核心文件 ibdata1、undo 回滚日志
- binlog 二进制日志
- redo 事务日志
xtrabackup_logfile - 备份记录元文件
数据恢复
步骤 1:预备恢复(关键!回放 redo 日志,统一 LSN 版本)
xtrabackup --prepare --target-dir=/full_alldata
步骤 2:停止 MySQL、清空旧库、还原数据文件
#mv 迁移原有旧数据(替代 rm 删除,更安全)
mv /export/software/mysql/data /export/software/mysql/data001
#停止 MySQL 数据库服务,查看状态
systemctl stop mysqld
systemctl status mysqld
#把备份文件还原到 MySQL 数据目录
xtrabackup --copy-back --target-dir=/full_alldata
#修改数据文件的属主权限
chown -R mysql:mysql /export/software/mysql/data
systemctl start mysqld
还原的底层规则:
xtrabackup --copy-back 只会把备份里的文件复制到 MySQL 的 data 目录,它不会自动删除 data 里原来的旧文件。如果不清理旧数据,新旧文件混在一起,MySQL 启动时文件冲突、直接崩溃。
