单表快速恢复!XtraBackup 隐藏技巧揭秘

DBA 团队-刘臻 360云计算

背景介绍

数据库工作者对下面这个场景肯定不会陌生:某次操作失误导致误删了某个表,需要立即进行数据恢复。如果是普通的全量备份,发现这个实例有好几百G甚至上T的数据,然后苦逼的拷贝数据库、追同步、等待数据恢复,估计好几个小时已经过去了~~~

本文主要介绍利用 XtraBackup 备份工具来实现单表快速恢复,在紧急数据恢复场景下,用最短的时间来恢复数据,最大程度降低损失。

涉及两种备份模式:

  1. 本地全量备份
  2. 远程流式备份

注:只适应于独立表空间的场景,即 innodbfileper_table = ON

本地全量备份恢复

正常使用 XtraBackup 备份到本地,并执行 apply-log ,但是在打包上传存储的时候,对每个表文件单独打包压缩。

重点 :对每个表文件单独打包,例如 dbname.tablename.tar

备份命令简单示例:


## 备份数据
innobackupex --user=users --password=xxxxxxx --socket=/xxx/mysql.sock --defaults-file=/xxxxx/my.cnf   /data/backup_dir/mysql  2>> /var/log/mysqlbackup.log
## 应用 apply log
innobackupex -apply-log  /data/backup/mysql 
## 分表单独打包(可以根据实际情况加入压缩和加密)
for tablename in $tables; do tar -cvf dbname.tablename.tar dbname/tablename ; done

注:一定不要忘记执行 apply-log

在数据恢复的时候,只需要拷贝必须的基础文件和需要恢复的表文件包,解压启动,并在数据库配置文件中添加replicate-wild-do-table=dbname.tablename ,只需要追对应表的数据同步即可。这样可以省去大量传输数据、解压和追同步的时间,以最少的时间恢复数据。

单表快速数据恢复步骤:

  • 拷贝 mysql 库相关文件
  • 拷贝 ibdata* 文件
  • 拷贝 ib_logfile* 文件
  • 拷贝 my.cnf 配置文件
  • 拷贝 XtraBackup 相关日志文件
  • 拷贝需要恢复的数据表相关文件以及目录结构
  • 配置文件中添加配置:replicate-wild-do-table=dbname.tablename
  • 配置文件中添加配置:skip-slave-start
  • 如果有压缩加密则解压解密相关文件,启动
  • change 到指定点位或者 gtid

注:恢复时配置文件一定要加 skip-slave-start 参数,避免直接启动同步导致数据追过头

远程流式备份恢复

在数据库容量逐渐变大,本地备份和传输磁盘容量有瓶颈的时候我们引入了远程流式备份。XtraBackup 有个 –stream 的参数,支持两种流式备份:tar 和 xbstream ,为了单表快速恢复,我们选择了 xbstream 。

备份命令简单示例:


## 直接利用 xbstream 将数据备份到远程存储
innobackupex --user=users --password=xxxxxxx --socket=/xxx/mysql.sock --defaults-file=/xxxxx/my.cnf --stream=xbstream --compress   /data/backup_dir/mysql  2>> /var/log/mysqlbackup.log  |  ssh users@10.10.10.10 "xbstream -x -C  /data/backup_dir1/mysql/"

数据恢复与之前本地备份单表快速恢复类同,拷贝必须的基础文件和需要恢复的数据表表相关文件,大致操作步骤与命令如下:

  • 拷贝 mysql 库相关文件
  • 拷贝 ibdata* 文件
  • 拷贝 ib_logfile* 文件
  • 拷贝 my.cnf 配置文件
  • 拷贝 XtraBackup 相关日志文件
  • 拷贝需要恢复的数据表相关文件以及目录结构
  • 配置文件中添加配置:replicate-wild-do-table=dbname.tablename
  • 配置文件中添加配置:skip-slave-start
  • 解压相关文件,命令:

innobackupex   --decompress   --parallel=8   /data/backup_dir/mysql
  • 执行 apply-log:

innobackupex -apply-log  /data/backup/mysql  
  • change 到指定点位或者 gtid

注:执行 apply-log 时出现如下报错不要紧张,直接忽略就行,因为只拷贝了部分表数据文件用来恢复,其他表的信息仍然在存在于 InnoDB 的内部数据字典中,所以会有报错。 InnoDB: Table xxxx/xxxxx in the InnoDB data dictionary has tablespace id xxx, but tablespace with that id or name does not exist. Have you deleted or moved .ibd files? This may also be a table created with CREATE TEMPORARY TABLE whose .ibd and .frm files MySQL automatically removed, but the table still exists in the InnoDB internal data dictionary.

总结

单表快速恢复能帮我们最短时间恢复线上数据,同时此方法也适用于多表恢复。不过想要快速恢复数据前期准备也必不可少,怎么能快速获取备份信息、需要恢复到的 binlog 点位、gtid 等都需要下一番功夫。只有诸事具备才能无往不利。