日常的数据备份及恢复测试,是DBA工作重中之重的事情,所以要做好备份及测试,日常的备份常见有mysqldump+binlog备份、xtrabackup+binlog备份,无论那一种,几乎都少不了对binlog的备份,说明了binlog在数据恢复中的重要性,下面做个小测试,是工作中不少运维或者新人DBA容易犯的错。

创建一个测试表tb1

  1. <test>(root@localhost) [xuanzhi]> show create table tb1\G
  2. *************************** 1. row ***************************
  3. Table: tb1
  4. Create Table: CREATE TABLE `tb1` (
  5. `id` int(10) NOT NULL AUTO_INCREMENT,
  6. `name` char(10) CHARACTER SET latin1 DEFAULT NULL,
  7. PRIMARY KEY (`id`)
  8. ) ENGINE=InnoDB DEFAULT CHARSET=utf8
  9. 1 row in set (0.00 sec)
  10.  
  11. <test>(root@localhost) [xuanzhi]>

往表里插入两条数据

  1. <test>(root@localhost) [xuanzhi]> insert into tb1 (name) value ('aa'),('bb');
  2. Query OK, 2 rows affected (0.01 sec)
  3. Records: 2 Duplicates: 0 Warnings: 0
  4.  
  5. <test>(root@localhost) [xuanzhi]> show master logs;
  6. +----------------------+-----------+
  7. | Log_name | File_size |
  8. +----------------------+-----------+
  9. | localhost-bin.000001 | 329 |
  10. +----------------------+-----------+
  11. 1 row in set (0.00 sec)
  12.  
  13. <test>(root@localhost) [xuanzhi]>

对数据备份

如果是xtrabackup备份的话,会在有xtrabackup_binlog_info文件中记录此时备份是到那个binlog文件和pos点的,如果是mysqldump备份,则需要带上--master-data=2这个参数,下面我们的数据量少,用mysqldump备份:

  1. [root@localhost ~]# mysqldump -uroot -p123456 -R --events --triggers=true --master-data=2 --single-transaction xuanzhi > xuanzhi.sql
  2. Warning: Using a password on the command line interface can be insecure.
  3. [root@localhost ~]# grep -i "CHANGE MASTER" xuanzhi.sql
  4. -- CHANGE MASTER TO MASTER_LOG_FILE='localhost-bin.000001', MASTER_LOG_POS=329;
  5. [root@localhost ~]#

继续模拟数据库有写入

这个时候是还是写在mysql-bin.000001

  1. <test>(root@localhost) [xuanzhi]> insert into tb1 (name) value ('cc'),('dd');
  2. Query OK, 2 rows affected (0.00 sec)
  3. Records: 2 Duplicates: 0 Warnings: 0
  4.  
  5. <test>(root@localhost) [xuanzhi]> show master logs;
  6. +----------------------+-----------+
  7. | Log_name | File_size |
  8. +----------------------+-----------+
  9. | mysql-bin.000001 | 538 |
  10. +----------------------+-----------+
  11. 1 row in set (0.00 sec)
  12.  
  13. <test>(root@localhost) [xuanzhi]> flush logs;
  14. Query OK, 0 rows affected (0.01 sec)
  15.  
  16. <test>(root@localhost) [xuanzhi]> insert into tb1 (name) value ('ee');
  17. Query OK, 1 row affected (0.00 sec)
  18.  
  19. <test>(root@localhost) [xuanzhi]> show master logs;
  20. +----------------------+-----------+
  21. | Log_name | File_size |
  22. +----------------------+-----------+
  23. | mysql-bin.000001 | 589 |
    | mysql-bin.000002 | 321 |
    +----------------------
    +-----------+
    2 rows in set (0.00 sec) <test>(root@localhost) [xuanzhi]>

上面我们进行flush logs是为了模拟现在已经有多个binlog文件了,恢复时进行多个binlog一起恢复。

模拟误操作

把xunazhi库drop了:

  1. <test>(root@localhost) [xuanzhi]> drop database xuanzhi;
  2. Query OK, 1 row affected (0.02 sec)
  3.  
  4. <test>(root@localhost) [(none)]> show databases;
  5. +--------------------+
  6. | Database |
  7. +--------------------+
  8. | information_schema |
  9. | mysql |
  10. | performance_schema |
  11. | test |
  12. +--------------------+
  13. 4 rows in set (0.00 sec)
  14.  
  15. <test>(root@localhost) [(none)]>

创建数据xuanzhi,把备份导入

  1. <test>(root@localhost) [(none)]> create database xuanzhi;
  2. Query OK, 1 row affected (0.00 sec)
  1. [root@localhost ~]# mysql -uroot -p123456 xuanzhi <./xuanzhi.sql # 这个sql文件可以是绝对路径也可以是相对路径
  2. Warning: Using a password on the command line interface can be insecure.
  3. [root@localhost ~]#

查看数据

  1. <test>(root@localhost) [(none)]> use xuanzhi
  2. Database changed
  3. <test>(root@localhost) [xuanzhi]> select * from tb1;
  4. +----+------+
  5. | id | name |
  6. +----+------+
  7. | 1 | aa |
  8. | 2 | bb |
  9. +----+------+
  10. 2 rows in set (0.00 sec)
  11.  
  12. <test>(root@localhost) [xuanzhi]>

可以看到备份前的数据恢复了

接下来要结合Binlog来恢复

但前提要找出误操作前的pos点,也就是drop database xuanzhi前的pos点:

  1. [root@localhost ~]# mysqlbinlog -v --base64-output=DECODE-ROWS mysql-bin.000002 |grep -C 10 -i "drop database"
  2. ### INSERT INTO `xuanzhi`.`tb1`
  3. ### SET
  4. ### @1=5
  5. ### @2='ee'
  6. # at 290
  7. #170327 21:10:55 server id 1313306 end_log_pos 321 CRC32 0x825a2f99 Xid = 78
  8. COMMIT/*!*/;
  9. # at 321
  10. #170327 21:19:25 server id 1313306 end_log_pos 422 CRC32 0x8c139cac Query thread_id=2 exec_time=0 error_code=0
  11. SET TIMESTAMP=1490620765/*!*/;
  12. drop database xuanzhi
  13. /*!*/;
  14. DELIMITER ;
  15. # End of log file
  16. ROLLBACK /* added by mysqlbinlog */;
  17. /*!50003 SET COMPLETION_TYPE=@OLD_COMPLETION_TYPE*/;
  18. /*!50530 SET @@SESSION.PSEUDO_SLAVE_MODE=0*/;
  19. [root@localhost ~]# mysql -uroot -p123456 xuanzhi <./xuanzhi.sql
  20. Warning: Using a password on the command line interface can be insecure.
  21. [root@localhost ~]#

从上面可以看到,误操作前的pos点是321,那我们现在通过binlog来进行数据恢复:

  1. [root@localhost mysql-5.6]# mysqlbinlog --start-position=329 --stop-position=321 mysql-bin.000001 mysql-bin.000002 |mysql -uroot -p123456 xuanzhi
    # 这里的mysql-bin.000001和mysql-bin.000002等日志文件要从原来的位置拷贝出来,可以是绝对路径也可以是相对路径
  1. Warning: Using a password on the command line interface can be insecure.
    [root@localhost mysql-5.6]#

--start-position是备份后记录下的pos点, --stop-position是误操前的pos点,如果批多个binlog文件,那么start-position是第一个binlog文件的pos点,stop-position是最后一个binlog的pos点,下面我们看下数据是否恢复回来了:

  1. <test>(root@localhost) [xuanzhi]> select * from tb1;
  2. +----+------+
  3. | id | name |
  4. +----+------+
  5. | 1 | aa |
  6. | 2 | bb |
  7. | 3 | cc |
  8. | 4 | dd |
  9. | 5 | ee |
  10. +----+------+
  11. 5 rows in set (0.00 sec)
  12.  
  13. <test>(root@localhost) [xuanzhi]>

这里要提的是进行恢复前,要把需要恢复的binlog备份好,或者移动拷贝一份到另一个目录,因为进行数据导入时也会继续写binlog。假如你没有误操作的情况下,就是想测试一下数据的恢复,很多人的操作是导入备份,再从备份里记录的binlog文件名和pos点进行binlog恢复,发现步骤都很完美,也没报错,恢复后就是只有备份时的数据,没有备份后的数据,下面测试一下给大家看:

  1. <test>(root@localhost) [xuanzhi]> insert into tb1 (name) value ('aa'),('bb');
  2. Query OK, 2 rows affected (0.01 sec)
  3. Records: 2 Duplicates: 0 Warnings: 0
  4.  
  5. <test>(root@localhost) [xuanzhi]> select * from tb1;
  6. +----+------+
  7. | id | name |
  8. +----+------+
  9. | 1 | aa |
  10. | 2 | bb |
  11. +----+------+
  12. 2 rows in set (0.00 sec)
  13. <test>(root@localhost) [xuanzhi]> show master logs;
  14. +----------------------+-----------+
  15. | Log_name | File_size |
  16. +----------------------+-----------+
  17. | localhost-bin.000001 | 329 |
  18. +----------------------+-----------+
  19. 1 row in set (0.00 sec)
  20.  
  21. <test>(root@localhost) [xuanzhi]>

进行备份操作:

  1. [root@localhost ~]# mysqldump -uroot -p123456 -R --events --triggers=true --master-data=2 --single-transaction xuanzhi > xuanzhi.sql
  2. Warning: Using a password on the command line interface can be insecure.
  3. [root@localhost ~]# grep -i "change master" xuanzhi.sql
  4. -- CHANGE MASTER TO MASTER_LOG_FILE='localhost-bin.000001', MASTER_LOG_POS=329;
  5. [root@localhost ~]#

继续写localhost-bin.000001后进行flush logs生成新的binlog再继续写数据,这里只是想模拟localhost-bin.000001写满了切localhost-bin.000002,结合多个binlog一起恢复

  1. <test>(root@localhost) [xuanzhi]> insert into tb1 (name) value ('cc'),('dd');
  2. Query OK, 2 rows affected (0.00 sec)
  3. Records: 2 Duplicates: 0 Warnings: 0
  4.  
  5. <test>(root@localhost) [xuanzhi]> flush logs;
  6. Query OK, 0 rows affected (0.00 sec)
  7.  
  8. <test>(root@localhost) [xuanzhi]> insert into tb1 (name) value ('dd');
  9. Query OK, 1 row affected (0.01 sec)
  10.  
  11. <test>(root@localhost) [xuanzhi]> show master logs;
  12. +----------------------+-----------+
  13. | Log_name | File_size |
  14. +----------------------+-----------+
  15. | localhost-bin.000001 | 589 |
  16. | localhost-bin.000002 | 321 |
  17. +----------------------+-----------+
  18. 2 rows in set (0.00 sec)
  19.  
  20. <test>(root@localhost) [xuanzhi]>

下面进行恢复测试,正常来说先把备份导入:

  1. [root@localhost ~]# mysql -uroot -p123456 xuanzhi <./xuanzhi.sql
  2. Warning: Using a password on the command line interface can be insecure.
  3. [root@localhost ~]#

查看数据,只有备份的那两条记录:

  1. <test>(root@localhost) [xuanzhi]> select * from tb1;
  2. +----+------+
  3. | id | name |
  4. +----+------+
  5. | 1 | aa |
  6. | 2 | bb |
  7. +----+------+
  8. 2 rows in set (0.00 sec)
  9.  
  10. <test>(root@localhost) [xuanzhi]>

那现在通过localhost-bin.000001,localhost-bin.000002来恢复后面那3条数据,那么起始pos是那个呢,就是上面备份完后备份文件里的那个pos,我们进到binlog的存放路径:

可以看到备份后的数据是没有恢复回来的。为什么呢?因为导入备份的时候,又开始写binlog了,而你恢复时用的binlog也就是现在导入备份时正在写的binlog。大体过程是这样的:

1、导入备份后,备份的所有操作都写进最后一个binlog了,也就是上面的localhost-bin.000002

2、进行binlog恢复,从备份文件里的pos点开始,按理来说是可以恢复到最新数据的,但是上面导入了备份,导入时的所有操作都会记录到localhost-bin.000002

3、备份导入时会有DROP TABLE和CREATE TABLE的动作写进binlog里,所以最终得到的数据,还是备份时的数据。

总结:

一、在恢复全备数据之前必须将该binlog文件移出,否则恢复过程中,会继续写入语句到binlog,最终导致增量恢复数据部分变得比较混乱

二、做好数据文件及binlog的备份至关重要,但不是备份完就算了,要定期进行数据恢复测试或演练

三、恢复时建议对外停止更新,即禁止更新数据库

mysqldump全量备份+mysqlbinlog二进制日志增量备份的更多相关文章

  1. mysql备份脚本,每天执行一次全量备份,三次增量备份

    线上一个小业务的mysql备份 全量备份 #!/bin/bash #crete by hexm at -- #scripte name : full_backup.sh #descriptioni : ...

  2. MySQL二进制日志的备份和恢复

    二进制日志:记录数据库修改的相关操作,作用是即时点回复,主从复制 可以按时间滚动,也可以按大小滚动 server-id:服务器身份标识 一.二进制文件的删除方法,千万不要手动删除 PURGE BINA ...

  3. mysql备份与还原,增量备份;使用ibd和frm文件恢复数据

    主要用的:binlog.mysqldump.mysqlbinlog 参考: https://www.cnblogs.com/Cherie/p/3309456.html https://blog.csd ...

  4. Mysql备份系列(2)--mysqldump备份(全量+增量)方案操作记录

    在日常运维工作中,对mysql数据库的备份是万分重要的,以防在数据库表丢失或损坏情况出现,可以及时恢复数据. 线上数据库备份场景:每周日执行一次全量备份,然后每天下午1点执行MySQLdump增量备份 ...

  5. mysql全量和增量备份详解(带脚本)

    在日常运维工作中,对mysql数据库的备份是万分重要的,以防在数据库表丢失或损坏情况出现,可以及时恢复数据. 下面对这种备份方案详细说明下:1.MySQLdump增量备份配置执行增量备份的前提条件是M ...

  6. mysql数据库的增量备份和全备

    还有一种简单的方法 参考 https://blog.csdn.net/u010098331/article/details/50932064 (注意:5.6版本以上新加了gtid 功能,gtid开启之 ...

  7. 阿里云 如何减少备份使用量? mysql数据库的完整备份、差异备份、增量备份

    RDS for MySQL备份.SQL审计容量相关问题_MYSQL使用_技术运维问题_云数据库 RDS 版-阿里云 https://help.aliyun.com/knowledge_detail/4 ...

  8. MySQL定时备份(全量备份+增量备份)

    MySQL 定时备份 参考 zone7_ 的 实战-MySQL定时备份系列文章 参考 zmcyu 的 mysql数据库的完整备份.差异备份.增量备份 更多binlog的学习参考马丁传奇的 MySQL的 ...

  9. SVN完全备份,增量备份,库同步

    svn备份一般采用三种方式:1)svnadmin dump 2)svnadmin hotcopy 3)svnsync. 优缺点分析: ============== 第一种svnadmin hotcop ...

随机推荐

  1. ice地址

    http://www.zeroc.com/download/eclipse

  2. Code First 数据库的表中属性的配置

      数据类型的约定配置 默认规则 列的数据类型是由数据库决定的,SqlServer的默认规则如下 String: nvarchar(MAX) Int:int Bool:bit Decimal:deci ...

  3. chromium的安装程序

    转自:http://www.xue163.com/182/6/1822338.html#pinglun 这篇文章主要简单讲解chromium的安装程序mini_installer 在编译mini_in ...

  4. html端编码规范

    理想的方式是让HTML只用于定义内容呈现的结构,让CSS控制内容呈现的样式,而所有功能的实现定义在JavaScript中

  5. 从头開始写项目Makefile(十):make内嵌函数及make命令显示

    [版权声明:转载请保留出处:blog.csdn.net/gentleliu.Mail:shallnew at 163 dot com]     这一节我们讲一下make的函数,在之前的章节已经讲到了几 ...

  6. .aspx(或.asp)文件与.html(.htm)文件的区别与联系

    由于都是用于描述网页文档的文件,自学asp.net起就对两者之间的关系很好奇 主要的区别在于,当用户请求页面时,它们在服务器的端的处理不同 下图解释客户端请求页面时,服务器端的处理流程: .html文 ...

  7. Node.js:常用工具、路由

    一.常用工具util util 是一个Node.js 核心模块,提供常用函数的集合,用于弥补核心JavaScript 的功能 过于精简的不足. 1.util.inherits util.inherit ...

  8. [Python爬虫] 之八:Selenium +phantomjs抓取微博数据

    基本思路:在登录状态下,打开首页,利用高级搜索框输入需要查询的条件,点击搜索链接进行搜索.如果数据有多页,每页数据是20条件,读取页数 然后循环页数,对每页数据进行抓取数据. 在实践过程中发现一个问题 ...

  9. OpenGL进阶(十四) - UVN Camera实现

    提要 3D游戏中最基本的一个功能就是3D漫游了,玩家可以通过键盘或者鼠标控制自己的视角. 之前我们也学习过一个相关的函数,glLookAt,用来制定摄像机的位置,摄像机观察目标位置,还有摄像机的放置方 ...

  10. mac远程桌面Microsoft Remote Desktop for Mac的安装与使用

    mac远程桌面Microsoft Remote Desktop for Mac的安装与使用 学习了:https://blog.csdn.net/ytangdigl/article/details/78 ...