msyql的备份是为了防止mysql服务器故障导致数据丢失,或者人为误操作导致的数据丢失,总之就是为了保证的安全性和可恢复性。
mysql的备份类型有很多种,我们针对不同的场合当然会有不同的选择了。
根据备份时,数据库服务器是否在线:
冷备:cold backup:在关闭sql服务之后进行的备份是最简单最安全的,而且损坏或者不一致的风险最小,但是关闭sql识别会让公司的业务停止一段时间,而且对于高负载和高数据量下的关闭和重启mysql也可能是要花很长一段时间的。
温备:warm backup:给sql加上读锁,意味着,加锁之后的事务请求只能读不能写,而且在用FLUSH TABLES WITH READ LOK加锁式,或者全局的读锁之后,才可以进行备份,当然这会花去很长一段时间。
热备:hot backup:顾名思义就是在sql服务运行的情况下,进行备份,当然线上肯定还有很多的用户请求以及各种操作都在进行,这样的备份数据完全有可能产生损坏。
根据备份的数据集:
完全备份:full backup:也就是说,备份这个数据库。
部分备份: partial backup:部分备份,在备份的时候有可能我们只是对部分数据库或者部分数据库里面的表进行备份而已。
根据备份时的接口(直接备份数据文件还是通过mysql服务器导出数据):
物理备份:直接复制(归档)数据文件的备份方式;physical backup
物理备份,就是简单的文件复制了,至需要将需要的文件复制到其他地方即可完成备份。而且物理备份的恢复可能就更简单,对应InnoDB则需要停止数据库服务。
逻辑备份:把数据从库中提出出来保存为文本文件;logical backup
逻辑备份,它只是将我们事务执行的所有操作,用SQL;语句或者文本文件保存起来,恢复的时候就需要将这些SQL语句再一次在服务器上运行一遍。
根据备份时是备份整个数据还是仅备份变化的数据:
完全备份:full backup:对于完全备份就是把整个数据库做一个备份
增量备份:incremental backup:在完全备份或者上次增量备份的基础上做备份
差异备份:differential backup:从上次完全备份的基础上到当然的备份
备份策略:
选择备份方式选择备份时间考虑到恢复成本恢复时长
备份成本:
锁时间备份时长备份负载
备份工具:
mysqldump:逻辑备份工具
InnoDB热备、MyISAM温备、Aria温备
备份和恢复过程较慢
mysqldumper: 多线程的mysqldump
很难实现差异或增量备份;
lvm-snapshot:
接近于热备的工具:因为要先请求全局锁,而后创建快照,并在创建快照完成后释放全局锁;
使用cp、tar等工具进行物理备份;
备份和恢复速度较快;
很难实现增量备份,并且请求全局需要等待一段时间,在繁忙的服务器上尤其如此;
本文中会讲诉三种备份方式:
1、Mysqldump
2、LVM-snapshot
3、Xtarbackup
恢复:
我们用完全备份+(增量备份/差异备份)+二进制日志文件(FLUSH LOGS),可以实现数据的完整恢复。
一、Mysqldump
注意:
1、备份的时候要加锁;--lock-all-tables:加锁是温备。
2、滚动日志;--flush-logs
3、--single-transaction: 加此选项指定是热备能够对InnoDB存储引擎实现热备
热备不需要加锁;
4、指定导出的库 --databases tb_name 备份指定库
--all-databases 备份所有库
5、记录二进制日志文件及位置: --master-data=[0|1|2]
[root@station112 ~]# mysqldump --databases tb_name --flush-logs --master-data=[0 |1|2] > /tmp/tb_name.sql
恢复:
完全备份+二进日志文件
Set session sql_log_bin=0; 先关掉日志文件
下面进行实验:本次是用热备。
1、先查看下我们所有的库。
mysql> SHOW DATABASES; +--------------------+ | Database | +--------------------+ | information_schema | | hellodb | | mydb | | mysql | | performance_schema | | test | +--------------------+ 6 rows in set (0.00 sec)
2、我们备份所以的数据库到/tmp/all.sql
[root@station112 tmp]# mysqldump --all-databases --flush-logs --single-transaction --master-data=2 > /tmp/all.sql
3、我们为了恢复完全备份之后产生的二进制日志文件,我们来插入点数据,之后再进行删除
mysql> CREATE DATABASE xie; Query OK, 1 row affected (0.00 sec) mysql> USE xie; Database changed mysql> CREATE TABLE t1(Name char(20),ID tinyint); Query OK, 0 rows affected (0.12 sec) mysql> INSERT INTO xie.t1 VALUE('tb1','123'); Query OK, 1 row affected (0.01 sec) mysql> SELECT * FROM t1; +------+------+ | Name | ID | +------+------+ | tb1 | 123 | +------+------+ 1 row in set (0.00 sec)
我们进行了完全备份之后,进行了上面才操作,之后我们其他人一不小心删除掉了我们刚才建立的那个数据库
mysql> DROP DATABASE xie; Query OK, 1 row affected (0.06 sec)
我们的二进制日志文件就派上用场了
我们先来查看下系统生成的二进制日志文件
[root@station112 tmp]# mysqlbinlog /mydata/binlogs/master-bin.000007 查看生成的二进制文件,将刚才所做操作的position之前的内容备份到一个文件中,一会用来恢复 SET @@session.collation_database=DEFAULT/*!*/; CREATE DATABASE xie /*!*/; # at 188 #140412 8:51:04 server id 1 end_log_pos 291 Query thread_id=14 exec_time=0 error_code=0 end_log_pos 291这个是建立数据库时的位置记录点 use `xie`/*!*/; SET TIMESTAMP=1397263864/*!*/; CREATE TABLE t1(Name char(20),ID tinyint) /*!*/; # at 291 #140412 8:52:00 server id 1 end_log_pos 358 Query thread_id=14 exec_time=0 error_code=0 SET TIMESTAMP=1397263920/*!*/; BEGIN /*!*/; # at 358 #140412 8:52:00 server id 1 end_log_pos 457 Query thread_id=14 exec_time=0 error_code=0 SET TIMESTAMP=1397263920/*!*/; INSERT INTO xie.t1 VALUE('tb1','123') /*!*/; # at 457 #140412 8:52:00 server id 1 end_log_pos 484 Xid = 1363 COMMIT/*!*/; # at 484 #140412 9:05:36 server id 1 end_log_pos 563 Query thread_id=14 exec_time=0 error_code=0 end_log_pos 563 这个是删除数据库的那一条。我们要取这个中间的内容。 SET TIMESTAMP=1397264736/*!*/; DROP DATABASE xie /*!*/; DELIMITER ; # End of log file ROLLBACK /* added by mysqlbinlog */; /*!50003 SET COMPLETION_TYPE=@OLD_COMPLETION_TYPE*/; /*!50530 SET @@SESSION.PSEUDO_SLAVE_MODE=0*/;
DELIMITER /*!*/; # at 4 #140412 8:47:35 server id 1 end_log_pos 107 Start: binlog v 4, server v 5.5.33-log created 140412 8:47:35 #总这个地方开始 BINLOG ' J41IUw8BAAAAZwAAAGsAAAAAAAQANS41LjMzLWxvZwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA AAAAAAAAAAAAAAAAAAAAAAAAEzgNAAgAEgAEBAQEEgAAVAAEGggAAAAICAgCAA== '/*!*/; # at 107 #140412 8:50:17 server id 1 end_log_pos 188 Query thread_id=14 exec_time=0 error_code=0 SET TIMESTAMP=1397263817/*!*/; SET @@session.pseudo_thread_id=14/*!*/; SET @@session.foreign_key_checks=1, @@session.sql_auto_is_null=0, @@session.unique_checks=1, @@session.autocommit=1/*!*/; SET @@session.sql_mode=0/*!*/; SET @@session.auto_increment_increment=1, @@session.auto_increment_offset=1/*!*/; /*!\C utf8 *//*!*/; SET @@session.character_set_client=33,@@session.collation_connection=33,@@session.collation_server=33/*!*/; SET @@session.lc_time_names=0/*!*/; SET @@session.collation_database=DEFAULT/*!*/; CREATE DATABASE xie /*!*/; # at 188 #140412 8:51:04 server id 1 end_log_pos 291 Query thread_id=14 exec_time=0 error_code=0 use `xie`/*!*/; SET TIMESTAMP=1397263864/*!*/; CREATE TABLE t1(Name char(20),ID tinyint) /*!*/; # at 291 #140412 8:52:00 server id 1 end_log_pos 358 Query thread_id=14 exec_time=0 error_code=0 SET TIMESTAMP=1397263920/*!*/; BEGIN /*!*/; # at 358 #140412 8:52:00 server id 1 end_log_pos 457 Query thread_id=14 exec_time=0 error_code=0 SET TIMESTAMP=1397263920/*!*/; INSERT INTO xie.t1 VALUE('tb1','123') /*!*/; # at 457 #140412 8:52:00 server id 1 end_log_pos 484 Xid = 1363 COMMIT/*!*/; #到这个地方结束,导出二进制日志 # at 484 #140412 9:05:36 server id 1 end_log_pos 563 Query thread_id=14 exec_time=0 error_code=0 SET TIMESTAMP=1397264736/*!*/; DROP DATABASE xie /*!*/; # at 563 #140412 9:42:11 server id 1 end_log_pos 607 Rotate to master-bin.000008 pos: 4 DELIMITER ; # End of log file ROLLBACK /* added by mysqlbinlog */; /*!50003 SET COMPLETION_TYPE=@OLD_COMPLETION_TYPE*/; /*!50530 SET @@SESSION.PSEUDO_SLAVE_MODE=0*/;
查询完之后我们就要导出这个二进制日志文件了,一会用来恢复数据库
[root@station112 tmp]# mysqlbinlog --start-position=107 --stop-position=484 /mydata/binlogs/master-bin.000007 > /tmp/binlog.sql
接下来我们来恢复试试;
此刻不要让其他人连入数据库做任何的读写操作;
先来查看下那个删除掉的数据库是不是不存在
我们之前创建的那个 xie 库 不在了!!!!
mysql> SHOW DATABASES; +--------------------+ | Database | +--------------------+ | information_schema | | hellodb | | mydb | | mysql | | performance_schema | | test | +--------------------+ 6 rows in set (0.00 sec)
1、我们停掉二进制日志文件记录。
mysql> FLUSH LOGS; Query OK, 0 rows affected (0.11 sec) mysql> SHOW MASTER STATUS; +-------------------+----------+--------------+------------------+ | File | Position | Binlog_Do_DB | Binlog_Ignore_DB | +-------------------+----------+--------------+------------------+ | master-bin.000008 | 107 | | | +-------------------+----------+--------------+------------------+ 1 row in set (0.00 sec) mysql> SET session sql_log_bin=0; Query OK, 0 rows affected (0.00 sec)
2、再导入数据,然后查看;
mysql> set session sql_log_bin=0; Query OK, 0 rows affected (0.00 sec) mysql> SOURCE /tmp/binlog.sql Query OK, 0 rows affected (0.00 sec) Query OK, 0 rows affected (0.00 sec) Query OK, 0 rows affected (0.00 sec)
查看
mysql> SHOW DATABASES; +--------------------+ | Database | +--------------------+ | information_schema | | hellodb | | mydb | | mysql | | performance_schema | | test | | xie | +--------------------+ 7 rows in set (0.00 sec)
哈哈,已导入了,是不是二进制日志文件有点强大?????
二、LVM-snapshot
用快照来进行备份恢复,这个就很简单了。
具体步骤:
创建