mysql备份与恢复方法总结与比较

 

这两天把mysql的各种备份方式总结了一下,部分是摘录其余人的内容。mysql

这些一些是综合了许多文章得出的结论,一些是本身试验的结果。正则表达式

多是不十分正确,若是各位发现错误,请指正!sql

 

MYISAM 引擎 的备份与恢复
一、 直接备份文件(cp 、tar)
方法:关闭mysql或者锁顶定表,避免写操做。将数据文件所有复制到备份路径便可。
锁表方法:FLUSH TABLES WITH READ LOCK(锁全部库全部表)

          LOCK TABLES  tbl_name (锁某一表) (此种锁定以前最好执行一下flush tables)shell

解锁方法:unlock tables
恢复:直接将数据复制到mysql数据目录下便可
优势:简单、方便、效率高
缺点:须要锁表或关闭数据库。不具备可移植性!数据易出错
二、 mysqldump 备份
mysqldump客户端可用来转储数据库或搜集数据库进行备份或将数据转移到另外一个SQL服务器(不必定是一个MySQL服务器)。
若是你在服务器上进行备份,而且表均为MyISAM表,应考虑使用 mysqlhotcopy,由于能够更快地进行备份和恢复。
方法:经常使用语句:

shell> mysqldump -uuser -ppass --default-character-set=utf8 --opt --extended-insert=false /数据库

--triggers -R --hex-blob -x db_name > db_name.sql(注意参数顺序)缓存

恢复:shell>mysqldump –uuser –ppass dn_name<db_name.sql
mysqldump 经常使用参数意义见下
优势:备份出来的数据比较小,基本是纯数据,可跨平台
缺点:不支持增量备份。会锁表,若是数据量大,锁表时间会很长。
三、  mysqlhotcopy 备份
mysqlhotcopy是一个Perl脚本,最初由Tim Bunce编写并提供。它使用LOCK TABLES、FLUSH TABLES和cp或scp来快速备份数据库。它是备份数据库或单个表的最快的途径,但它只能运行在数据库目录所在的机器上。 mysqlhotcopy只用于备份MyISAM。它运行在Unix和NetWare中。使用以前,主机需安装perl-DBD-MySQL和perl-DBI rpm包
方法:格式

Shell> mysqlhotcopy –uuser –ppass db_name /path/to/bakdir服务器

经常使用选项:
--addtodest  不重命名目标文件(若是存在),合并它们(增量备份)
--checkpoint=db_name.tbl_name    在指定的db_name.tbl_name插入检查点条目,记录mysqlhotcopy操做记录
--method    备份方法使用cp或者scp,默认使用cp
--allowold  若是目标存在不放弃(加上一个_old后缀从新命名它)。
--noindices 备份中不包括所有索引文件。这样使备份更小、更快。能够在之后用myisamchk -rq从新构建索引。
--regexp= expr   复制全部数据库名匹配给出的正则表达式的数据库。
恢复:将备份出的数据复制(覆盖)到mysql数据目录(注意权限)
优势:支持一次性拷贝多个数据库,同时还支持正则表达。支持增量备份,备份速度快
缺点:只适用myisam引擎;只能在mysql数据目录所在的主机上执行;
四、 sql 语法备份
BACKUP TABLE 语法其实和 mysqlhotcopy 的工做原理差很少,都是锁表,而后拷贝数据文件。它能实如今线备份,可是效果不理想,所以不推荐使用。它只拷贝表结构文件(*.frm)和数据文件(*.myd),不一样时拷贝索引文件,所以恢复时比较慢。只使用myisam引擎

语法:mysq>backup table tbl_name to ‘/path/to/backup/dir/’ (备份目录mysql用户要有写的权限)app

SELECT INTO OUTFILE 则是把数据导出来成为普通的文本文件,能够自定义字段间隔的方式,方便处理这些数据。异步

 SELECT...INTO OUTFILE 'file_name'形式的SELECT能够把被选择的行写入一个文件中。该文件被建立到服务器主机上,所以您必须拥有FILE权限,才能使用此语法。file_name必须是一个新文件,而不能是一个已经存在的文件。

SELECT...INTO OUTFILE语句的主要做用是让您能够很是快速地把一个表转储到服务器机器上。若是您想要在服务器主机以外的部分客户主机上建立结果文件,您不能使用SELECT...INTO OUTFILE。在这种状况下,您应该在客户主机上使用好比“mysql –e "SELECT ..." > file_name”的命令,来生成文件。ide

五、 binlog 日志备份
二进制日志记录了全部的 DDL 和 DML 的语句, 但不包括查询语句, 语句以事件方式保存。若是MySQL服务器启用了二进制日志,你可使用mysqlbinlog工具来恢复从指定的时间点开始 (例如,从你最后一次备份)直到如今或另外一个指定的时间点的数据。而坏处是日志文件增加速度快,很快占会占满磁盘空间,并且二进制日志会使服务器性能大约慢1%.
以下状况时,二进制日志会更换到新的文件:
           (1)服务器重启
           (2)服务器被更新
           (3)日志达到最大日志长度 max_binlog_size
           (4)在 MySQL 命令终端 FLUSH LOGS
开启方法:修改my.cnf,在[mysqld]下开启binkog日志

log-bin=mysql-bin
binlog-do-db=db_test(指定开启binlog的数据库,如不知道,默认是所有数据库)
binlog-do-db=db_test2

expire_logs_day=3(设置日志的过时天数,过了指定的天数,会自动删除,如不设置,默认永久保存)    
从新启动数据库
恢复方法:

(1)、mysqlbinlog -stop-date=“2012-08-24 9:59:59” /var/log/mysql/mysql-bin.[0-9]* | mysql -u root –ppass                   (读取日志最开始至2012-08-24的全部日志并恢复)

(2)、mysqlbinlog -stop-date=“2012-08-24 9:59:59” /var/log/mysql/mysql-bin.[0-9]* | mysql -u root –ppass --one-database db_name (只按时间恢复某一数据库得信息)

(3)、mysqlbinlog -stop-date=“2012-08-24 9:59:59” /var/log/mysql/mysql-bin.[0-9]*>file.sql

(将日志转换成sql文件,可直接导入到mysql内)
Mysqlbinlog 经常使用参数:
--start-position=N     从二进制日志中第1个位置等于N参量时的事件开始读
--stop-position=N      从二进制日志中第1个位置等于和大于N参量时的事件起中止读。
--start-datetime=datetime       从二进制日志中第1个日期时间等于或晚于 datetime参量的事件开始读取。 datetime值相对于运行mysqlbinlog的机器上的本地时区
---database=db_name,-d db_name       只列出该数据库的条目(只用本地日志)。
-h host_name   获取给定主机上的MySQL服务器的二进制日志。
--to-last-logs,-t       在MySQL服务器中请求的二进制日志的结尾处不中止,而是继续打印直到最后一个二进制日志的结尾。若是将输出发送给同一台MySQL服务器,会致使无限循环。该选项要求--read-from-remote-server。
--disable-logs-bin,-D       禁用二进制日志。若是使用--to-last-logs选项将输出发送给同一台MySQL服务器,能够避免无限循环。该选项在崩溃恢复时也颇有用,能够避免复制已经记录的语句。注释:该选项要求有SUPER权限。
六、 mysql 主从复制
MySQL支持单向、异步复制,复制过程当中一个服务器充当主服务器,而一个或多个其它服务器充当从服务器。(这与 同步复制能够进行对比, 同步复制是MySQL簇的一个特征)。主服务器将更新写入二进制日志文件,并维护文件的一个索引以跟踪日志循环。这些日志能够记录发送到从服务器的更新。当一个从服务器链接主服务器时,它通知主服务器从服务器在日志中读取的最后一次成功更新的位置。从服务器接收从那时起发生的任何更新,而后封锁并等待主服务器通知新的更新。
主从复制严格来讲不算一种备份方式,它只是将主mysql上全部的写操做在从的从新执行了一遍。这样写操做在主库上,在从库上能够读数据库,从而实现读写分离,下降了主库的压力,提升了查询速度。而在从库上执行上面的备份方法,能够大胆的锁表或关闭数据库,提升mysql的高可用性。
[具体配置方法见附录]
七、 软件备份XtarBackup (innobackupex
Xtrabackup下的innobackupex 支持myisam的备份。备份时也会锁表(不支持增量备份)
备份

shell>innobackupex –defaults-file=/etc/my.cnf –user=username –password=passwd --databases=”databases1 databases2” /bak/path/to/dir

恢复:

Shell>innobackupex –apply-log –defaults-file=/etc/my.cnf –user=username –password=passwd /path/to/bak/dir/data

由于innobackupex存在bug,因此执行完上面的命令后,须要手动将备份出的(.frm .MYD .MYI)文件覆盖的mysql的数据目录!
 
Innodb 引擎 的备份与恢复
一、 Mysqldump

Shell> mysqldump -uuser -ppass --default-character-set=utf8 --opt --extended-insert=false /

--triggers -R --hex-blob --single-transaction db_name > db_name.sql

恢复:shell>mysqldump –uuser –ppass dn_name<db_name.sql
二、  软件备份XtarBackup(xtrabackup)
xtrabackup

优势:支持热备,支持增量备份。
xtrabackup缺点:备份是物理拷贝+逻辑备份的方式备份数据库,会发生物理磁盘的读操做,可是物理备份的速度会比较快。
总的来看xtrabackup会比mysqldump优秀不少,由于他支持热备和增量备份。可是这个也是根据数据库状况而定,若是是在slave上作备份,不用太多的考虑表锁问题,mysqldump也是很不错的。还有就是若是数据量不大,小于5G,数据基本都是update语句较多的状况下,不太适合使用xtrabackup作全备和增量备份策略,由于xtrabackup增量备份的原理是经过lsn(日志序号)来操做的,若是你的数据库更新太频繁,天天新的lsn太多,那增量备份尚未全备来的快,还有就是xtrabackup全备的时候会备份ib_logfile*和ibdata*,就算你使用的独享表空间也会备份这些文件,因此每次全备的size会比较大,磁盘空间和系统资源的占用也比较多。

Xtrabackup中包含两个工具:
xtrabackup 只能备份InnoDB和XtraDB两种数据表,支持在线热备份,能够在不加锁的状况下备份Innodb数据表,不过此工具不能操做Myisam引擎表
innobackupex  是一个脚本封装,封装了xtrabackup,能同时处理Innodb和Myisam,但在处理Myisam时须要加一个读锁。
方法:

(1)   普通备份(全量备份) 

Xtrabackup –defaulets-file=/etc/my.cnf –backup –target-dir=/path/to/backdir/

注意:xtrabackup只备份数据文件,并不备份数据表结构(.frm),因此这里要手动备份一下,以便xtrabackup恢复的时候使用。 

(2)     增量备份 xtrabackup –default-file=/etc/my.cnf –backup –target-dir=/path/to/backdir –incremental-basedir=/path/to/base/backdir

补充:
myisamchk
myisamchk能够得到有关数据库表的信息或检查、修复、优化他们。
myisamchk适用MyISAM表。
当你运行 myisamchk时,必须确保其它程序不使用表。

使用以前先执行“FLUSH TABLES” 强制清空仍然在内存中的任何表修改,同时确保myisamchk执行过程当中其余程序不使用表。不然会报错“warning: clients are using or haven't closed the table properly”

避免此问题出现的最简单方法是用check table命令来检查表,用法“sql>check table dbname.tabname”
 
mysqldump
mysqldump支持下面的选项:

--add-drop--database 在每一个CREATE DATABASE语句前添加DROP DATABASE语句。

---database,-B 转储几个数据库。一般状况,mysqldump将命令行中的第1个名字参量看做数据库名,后面的名看做表名。使用该选项,它将全部名字参量看做数据库名。CREATE DATABASE IF NOT EXISTS db_name和USE db_name语句包含在每一个新数据库前的输出中。
--tables 覆盖---database或-B选项。选项后面的全部参量被看做表名。

--default-character-set=charset 使用charsetas默认字符集。若是没有指定,mysqldump使用utf8。若是数据表不是采用默认的 latin1 字符集的话,那么导出时必须指定该选项,不然再次导入数据后将产生乱码问题。

--delayed-insert 使用INSERT DELAYED语句插入行。

--delete-master-logs 在主复制服务器上,完成转储操做后删除二进制日志。该选项自动启用--master-data。

--disable-keys,-K   对于每一个表,用/*!40000 ALTER TABLE tbl_name DISABLE KEYS */;和/*!40000 ALTER TABLE tbl_name ENABLE KEYS */;语句引用INSERT语句。这样能够更快地装载转储文件,由于在插入全部行后建立索引。该选项只适合MyISAM表。

--extended-insert,-e 使用包括几个VALUES列表的多行INSERT语法。这样使转储文件更小,重载文件时能够加速插入。

--flush-logs,-F   开始转储前刷新MySQL服务器日志文件。该选项要求RELOAD权限。请注意若是结合--all--database(或-A)选项使用该选项,根据每一个转储的数据库刷新日志。例外状况是当使用--lock-all-tables或--master-data的时候:在这种状况下,日志只刷新一次,在全部 表被锁定后刷新。若是你想要同时转储和刷新日志,应使用--flush-logs连同--lock-all-tables或--master-data。

--force,-f  在表转储过程当中,即便出现SQL错误也继续。

--host=host_name,-h host_name   从给定主机的MySQL服务器转储数据。默认主机是localhost。

--hex-blob 使用十六进制格式导出二进制字符串字段。若是有二进制数据就必须使用本选项。影响到的字段类型有 BINARY、VARBINARY、BLOB。
--lock-all-tables,-x    全部数据库中的全部表加锁。在总体转储过程当中经过全局读锁定来实现。该选项自动关闭--single-transaction和--lock-tables。
--lock-tables,-l 开始转储前锁定全部表。用READ LOCAL锁定表以容许并行插入MyISAM表。对于事务表例如InnoDB和BDB,--single-transaction是一个更好的选项,由于它不根本须要锁定表。请注意当转储多个数据库时,--lock-tables分别为每一个数据库锁定表。所以,该选项不能保证转储文件中的表在数据库之间的逻辑一致性。不一样数据库表的转储状态能够彻底不一样。
--master-data[=value] 该选项将二进制日志的位置和文件名写入到输出中。该选项要求有RELOAD权限,而且必须启用二进制日志。若是该选项值等于1,位置和文件名被写入CHANGE MASTER语句形式的转储输出,若是你使用该SQL转储主服务器以设置从服务器,从服务器从主服务器二进制日志的正确位置开始。若是选项值等于2,CHANGE MASTER语句被写成SQL注释。若是value被省略,这是默认动做。
--master-data 选项启用--lock-all-tables,除非还指定--single-transaction(在这种状况下,只在刚开始转储时短期得到全局读锁定。又见--single-transaction。)在任何一种状况下,日志相关动做发生在转储时。该选项自动关闭--lock-tables。

--single-transaction 该选项从服务器转储数据以前发出一个BEGIN SQL语句。它只适用于事务表,例如InnoDB和BDB,由于而后它将在发出BEGIN而没有阻塞任何应用程序时转储一致的数据库状态。当使用该选项时,应记住只有InnoDB表能以一致的状态被转储。例如,使用该选项时任何转储的MyISAM或HEAP表仍然能够更改状态。--single-transaction选项和--lock-tables选项是互斥的,由于LOCK TABLES会使任何挂起的事务隐含提交。要想转储大的表,应结合--quick使用该选项。

--no-data,-d 不写表的任何行信息。若是你只想转储表的结构这颇有用。

--opt          该选项是速记;等同于指定 --add-drop-tables--add-locking --create-option --disable-keys--extended-insert --lock-tables --quick --set-charset。它能够给出很快的转储操做并产生一个能够很快装入MySQL服务器的转储文件。该选项默认开启,但能够用--skip-opt禁用。要想只禁用确信用-opt启用的选项,使用--skip形式;例如,--skip-add-drop-tables或--skip-quick。

--quick,-q 该选项用于转储大的表。它强制mysqldump从服务器一次一行地检索表中的行而不是检索全部行并在输出前将它缓存到内存中。
--routines,-R 在转储的数据库中转储存储程序(函数和程序)。使用---routines产生的输出包含CREATE PROCEDURE和CREATE FUNCTION语句以从新建立子程序。可是,这些语句不包括属性,例如子程序定义者或建立和修改时间戳。这说明当重载子程序时,对它们进行建立时定义者应设置为重载用户,时间戳等于重载时间。若是你须要建立的子程序使用原来的定义者和时间戳属性,不使用--routines。相反,使用一个具备mysql数据库相应权限的MySQL帐户直接转储和重载mysql.proc表的内容。
--triggers 为每一个转储的表转储触发器。该选项默认启用;用--skip-triggers禁用它。

MySQL表级锁的锁模式
MySQL的表级锁有两种模式:表共享读锁(Table Read Lock)和表独占写锁(Table Write
Lock)。MyISAM在执行查询语句(SELECT)前,会自动给涉及的全部表加读锁,在执行更新操做(UPDATE、DELETE、INSERT等)前,会自动给涉及的表加写锁。
因此对MyISAM表进行操做,会有如下状况:
a、对MyISAM表的读操做(加读锁),不会阻塞其余进程对同一表的读请求,但会阻塞对同一表的写请求。只有当读锁释放后,才会执行其它进程的写操做。
b、对MyISAM表的写操做(加写锁),会阻塞其余进程对同一表的读和写操做,只有当写锁释放后,才会执行其它进程的读写操做。

锁表方法
FLUSH TABLES WITH READ LOCK;
这个命令是全局读锁定,执行了命令以后全部库全部表都被锁定只读。通常都是用在数据库联机备份,这个时候数据库的写操做将被阻塞,读操做顺利进行。

解锁的语句也是unlock tables。 LOCK TABLES tab_name

相关文章
相关标签/搜索