为什么使用增量备份?
完全备份有两种方式,一种是使用tar打包数据文件,另一种是使用mysqldump进行完全备份。完全备份存在的问题很容易看到,每次都是把所有的数据内容进行备份,备份数据中有大量的重复数据,并且完全备份的时间和恢复的时间很长。解决完全备份存在的问题就是使用增量备份的方式,增量备份就是备份自上一次备份之后增加或改变的文件或者内容。
增量备份的特点:
增量备份的优点是没有重复数据,备份量不大,时间短。缺点也很明显,需要上次完全备份及完全备份之后所有的增量备份才能恢复,而且对所有增量备份进行逐个反推恢复,操作较为繁琐。
MySQL没有提供直接的增量备份方法,但是可以通过MySQL的二进制日志(binary logs)简介间接实现增量备份。二进制日志对备份的意义如下:
- (1) 二进制日志保存了所有更新或者可能更新数据库的操作。
- (2) 二进制日志在启动MySQL服务器后开始记录,并在文件达到max_binlog_size所设置的大小或者接收到flush-logs命令后重新创建新的日志文件。
- (3) 只需要定时执行flush-logs方法重新创建新的日志,生成二进制文件序列,并及时把这些日志保存到安全的地方就完成了一个时间段的增量备份。
实验环境:
CentOS7.3上的MySQL-5.7.17
一、 增量备份恢复
1. 创建数据库、数据表并添加数据
#systemctl stop firewalld.service //关闭防火墙
#setenforce 0 //关闭增强安全功能
#systemctl restart mysqld.service //重启mysql
#mysql –u root –p //登录进入mysql
>create database school; //创建数据库school
>use school; //进入school
>create table info (name varchar(10),score decimal(5,2)); //创建数据表info
>insert into info (name,score) values (‘zhangsan’,88); //向info中插入数据
>insert into info (name,score) values (‘lisi’,88);
>select * from info; //查看数据表info中数据
>exit
2.修改mysql配置文件,开启二进制日志功能,并重启mysql服务
#vim /etc/my.cnf
[mysqld]
user = mysql
basedir = /usr/local/mysql
datadir = /usr/local/mysql/data
port = 3306
character_set_server=utf8
pid-file = /usr/local/mysql/mysqld.pid
socket = /usr/local/mysql/mysql.sock
server-id = 1
log-bin=mysql-bin //添加二进制日志功能
#systemctl restart mysql.service //重启mysql服务
3.使用mysqldump备份school数据库
#mysqldump –u root –p school > /opt/school.sql
4.执行flush-logs生成新的二进制文件
#mysqladmin –u root –p flush-logs
#ls /usr/local/mysql/data //生成了新的二进制文件mysql-bin.000002
5.添加test01数据并执行flush-logs生成新的二进制文件
#mysql –u root –p
>use school;
>insert into info (name,score) values (‘test01’,60);
>exit
#mysqladmin –u root –p flush-logs
#ls
6.添加test02数据并执行flush-logs生成新的二进制文件
#mysql –u root –p
>use school;
>insert into info (name,score) values (‘test02’,60);
>exit
#mysqladmin –u root –p flush-logs
#ls
7.模拟误操作删除test01、test02
#mysql –u root –p
>use school;
>delete from info where name=’test01’;
>delete from info where name=’test02’;
>exit
8.使用二进制文件进行恢复操作,需要注意的是恢复的顺序,要先恢复最先生成的二进制文件,然后依次执行。
#mysqlbinlog --no-defaults mysql-bin.000002 | mysql –u root –p
#mysql –u root –p
>use school;
>select * from info; //test01已经恢复,可知test01删除记录保存在mysql-bin.000002中
>exit
#mysqlbinlog –no-defaults mysql-bin.000003 | mysql –u root –p
#mysql -u root –p
>use school;
>select * from info; //test02已恢复,test02的删除记录保存在mysql-bin.000003中
>exit
9.查看二进制变更文件内容所用命令为
#mysqlbinlog --no-defaults --base64-output=decode-rows –v mysql-bin.000002
二.mysql基于时间点的恢复
1.先创建好school数据库,info表,在表中增加数据name=’tom’,score=88;name=’jerry’,score=88
2.修改mysql配置文件,开启二进制日志功能,并重启mysql服务
#vim /etc/my.cnf
[mysqld]
user = mysql
basedir = /usr/local/mysql
datadir = /usr/local/mysql/data
port = 3306
character_set_server=utf8
pid-file = /usr/local/mysql/mysqld.pid
socket = /usr/local/mysql/mysql.sock
server-id = 1
log-bin=mysql-bin
#systemctl restart mysql.service
3.进行完全备份及增量备份
#mysqldump –u root –p school > /opt/school.sql //进行完全备份
#mysqladmin –u root –p flush-logs //进行增量备份生成mysql-bin.000002
4.模拟误操作,添加test01,删除tom,添加test02
>insert into info(name,score) values (‘test01’,88);
>delete from info where name=’tom’;
>insert into info(name,score) values (‘test02’,88);
5.添加增量备份
#mysqladmin –u root –p flush-logs //生成增量备份mysql-bin.000003
6.利用二进制变更文件查看具体操作,并导入新建文本文档方便管理
#mysqlbinlog --no-defaults --base64-output=decode-rows –v mysql-bin.000002 > /opt/info.txt
#vim /opt/info.txt
7.找到对应操作的时间标记和位置标记
- 180705 9:55:42 错误操作时间 --stop-datetime
- 180705 9:55:49 正确操作时间 --start-datetime
- at 563 上一次正确操作节点 --stop-position
- at 660 下一次正确操作节点 --start-position
8.先利用完全备份恢复tom和jerry的数据
>drop table info;
#mysql –u root –p school < /opt/school.sql
>mysql –u root –p
>use school;
>show tables;
>select * from info;
>exit
9.基于时间点的恢复
#mysqlbinlog –no-defaults –stop-datetime=’2018-07-05 9:55:42’ /usr/local/mysql/data/mysql-bin.000002 | mysql –u root –p //注意时间格式需要用-连接
进入info后可以发现test01已恢复
##mysqlbinlog –no-defaults –start-datetime=’2018-07-05 9:55:49’ /usr/local/mysql/data/mysql-bin.000002 | mysql –u root –p
进入info可发现test02已恢复,从而基于时间点的恢复完成
三.基于位置的恢复
1.先准备好误操作环境,将test01,test02环境
>delete from info where name=’test01’;
>delete from info where name=’test02’;
2.基于位置的恢复
#mysqlbinlog –no-defaults –stop-position =’563’ /usr/local/mysql/data/mysql-bin.000002 | mysql –u root –p //上一次正确操作节点
#mysqlbinlog –no-defaults –start-position=’660’ /usr/local/mysql/data/mysql-bin.000002 | mysql –u root –p //下一次正确操作节点
进入school的info中再次查看,可以发现test01和test02已经恢复。