深入了解使用mysqldump进行备份
恕我直言,如果您知道如何进行备份,那么备份已成为一种艺术形式
你有选择
选项1:mysqldump整个mysql实例
这是最简单的一个,不必理会!!!
mysqldump -h... -u... -p... --hex-blob --routines --triggers --all-databases | gzip > MySQLData.sql.gz
所有内容都写在一个文件中:表结构,索引,触发器,存储过程,用户,加密密码。其他mysqldump选项也可以导出不同样式的INSERT命令,二进制日志中的日志文件和位置坐标,数据库创建选项,部分数据(--where选项)等。
选项2:mysqldump将单独的数据库转储到单独的数据文件中
首先创建数据库列表(执行此操作的两种技术)
技术1
mysql -h... -u... -p... -A --skip-column-names -e"SELECT schema_name FROM information_schema.schemata WHERE schema_name NOT IN ('information_schema','mysql')" > ListOfDatabases.txt
技术2
mysql -h... -u... -p... -A --skip-column-names -e"SELECT DISTINCT table_schema FROM information_schema.tables WHERE table_schema NOT IN ('information_schema','mysql')" > ListOfDatabases.txt
技术1是最快的方法。技术2是最可靠和最安全的。技术2更好,因为有时用户会在/ var / lib / mysql(datadir)中为通用目的创建与数据库无关的文件夹。information_schema会将文件夹注册为information_schema.schemata表中的数据库。技术2将绕过不包含mysql数据的文件夹。
编译数据库列表后,您可以继续遍历该列表并mysqldump它们,即使需要也可以并行进行。
for DB in `cat ListOfDatabases.txt`
do
mysqldump -h... -u... -p... --hex-blob --routines --triggers ${DB} | gzip > ${DB}.sql.gz &
done
wait
如果一次要启动的数据库太多,则一次将其并行转储10个数据库:
COMMIT_COUNT=0
COMMIT_LIMIT=10
for DB in `cat ListOfDatabases.txt`
do
mysqldump -h... -u... -p... --hex-blob --routines --triggers ${DB} | gzip > ${DB}.sql.gz &
(( COMMIT_COUNT++ ))
if [ ${COMMIT_COUNT} -eq ${COMMIT_LIMIT} ]
then
COMMIT_COUNT=0
wait
fi
done
if [ ${COMMIT_COUNT} -gt 0 ]
then
wait
fi
选项3:mysqldump将单独的表转储到单独的数据文件中
首先创建表列表
mysql -h... -u... -p... -A --skip-column-names -e"SELECT CONCAT(table_schema,'.',table_name) FROM information_schema.tables WHERE table_schema NOT IN ('information_schema','mysql')" > ListOfTables.txt
然后将所有表以10为一组转储
COMMIT_COUNT=0
COMMIT_LIMIT=10
for DBTB in `cat ListOfTables.txt`
do
DB=`echo ${DBTB} | sed 's/\./ /g' | awk '{print $1}'`
TB=`echo ${DBTB} | sed 's/\./ /g' | awk '{print $2}'`
mysqldump -h... -u... -p... --hex-blob --triggers ${DB} ${TB} | gzip > ${DB}_${TB}.sql.gz &
(( COMMIT_COUNT++ ))
if [ ${COMMIT_COUNT} -eq ${COMMIT_LIMIT} ]
then
COMMIT_COUNT=0
wait
fi
done
if [ ${COMMIT_COUNT} -gt 0 ]
then
wait
fi
选项4:使用您的想象力
尝试使用上述选项的变体以及干净快照的技术
例子
- 按每个表的大小升序或降序对表列表进行排序。
- 使用单独的过程,在启动mysqldumps之前运行“带读锁的刷新表; SELECT SLEEP(86400)”。mysqldumps完成后,请终止该过程。如果数据库同时包含InnoDB和MyISAM,这将很有帮助
- 将mysqldumps保存在标有日期的文件夹中,并轮换出旧的备份文件夹。
- 将整个实例mysqldumps加载到独立服务器中。
警告
只有选项1才能带来一切。缺点是通过这种方式创建的mysqldumps只能重新加载到生成mysqldump的相同的majot发行版mysql中。换句话说,无法在5.1或5.5中加载来自MySQL 5.0数据库的mysqldump。原因 ?各个主要版本之间的mysql模式完全不同。
选项2和3不包括保存用户名和密码。
这是为用户转储SQL Grants的通用方法,该方法易读且更可移植
mysql -h... -u... -p... --skip-column-names -A -e"SELECT CONCAT('SHOW GRANTS FOR ''',user,'''@''',host,''';') FROM mysql.user WHERE user<>''" | mysql -h... -u... -p... --skip-column-names -A | sed 's/$/;/g' > MySQLGrants.sql
选项3不保存存储过程,因此您可以执行以下操作
mysqldump -h... -u... -p... --no-data --no-create-info --routines > MySQLStoredProcedures.sql &
应该注意的另一点是关于InnoDB。如果您有一个较大的InnoDB缓冲池,则在执行任何备份之前,应尽最大可能对其进行刷新。否则,MySQL将花费时间从缓冲池中清除带有剩余脏页的表。这是我的建议:
在执行备份之前大约1小时,请运行以下SQL命令
SET GLOBAL innodb_max_dirty_pages_pct = 0;
在MySQL 5.5中,默认innodb_max_dirty_pages_pct为75。在MySQL 5.1及更高版本中,默认innodb_max_dirty_pages_pct为90。通过将innodb_max_dirty_pages_pct设置为0,这将加快将脏页刷新到磁盘的速度。这将防止或至少减轻在对任何InnoDB表执行任何mysqldump之前清理InnoDB数据的任何不完整的两阶段提交的影响。
mysqldump上的最后一个字
大多数人都避开mysqldump,转而使用其他工具,而这些工具确实不错。
这些工具包括
- MAATKIT(并行转储 / 还原脚本,来自Percona [不推荐使用,但性能很好])
- XtraBackup(Percona的TopNotch快照备份)
- CDP R1Soft(采用时间点快照的MySQL模块选件)
- MySQL企业备份(以前是InnoDB热备份[商业])
如果您本着真正的MySQL DBA的精神,则可以拥抱mysqldump并完全掌握它。可能您所有的备份都反映出您作为MySQL DBA的技能。