我应该备份和恢复`mysql`数据库吗?

在创build备份和恢复整个MySQL服务器的自动化解决scheme的过程中,我遇到了似乎包含用户帐户,权限,元数据等等的mysql数据库。 该数据库应该备份吗? 将备份和尝试恢复它打破了事情?

我有一段时间谷歌search“MySQL备份MySQL数据库”,你可以想象。

这里有一些有趣的事情需要考虑:备份mysql数据库极大地限制了你只能将这样的数据库恢复到你运行备份的同一版本的mysql。 这是为什么:

这里是MySQL 5.0.45的mysql.user

 mysql> desc mysql.user; +-----------------------+-----------------------------------+------+-----+---------+-------+ | Field | Type | Null | Key | Default | Extra | +-----------------------+-----------------------------------+------+-----+---------+-------+ | Host | char(60) | NO | PRI | | | | User | char(16) | NO | PRI | | | | Password | char(41) | NO | | | | | Select_priv | enum('N','Y') | NO | | N | | | Insert_priv | enum('N','Y') | NO | | N | | | Update_priv | enum('N','Y') | NO | | N | | | Delete_priv | enum('N','Y') | NO | | N | | | Create_priv | enum('N','Y') | NO | | N | | | Drop_priv | enum('N','Y') | NO | | N | | | Reload_priv | enum('N','Y') | NO | | N | | | Shutdown_priv | enum('N','Y') | NO | | N | | | Process_priv | enum('N','Y') | NO | | N | | | File_priv | enum('N','Y') | NO | | N | | | Grant_priv | enum('N','Y') | NO | | N | | | References_priv | enum('N','Y') | NO | | N | | | Index_priv | enum('N','Y') | NO | | N | | | Alter_priv | enum('N','Y') | NO | | N | | | Show_db_priv | enum('N','Y') | NO | | N | | | Super_priv | enum('N','Y') | NO | | N | | | Create_tmp_table_priv | enum('N','Y') | NO | | N | | | Lock_tables_priv | enum('N','Y') | NO | | N | | | Execute_priv | enum('N','Y') | NO | | N | | | Repl_slave_priv | enum('N','Y') | NO | | N | | | Repl_client_priv | enum('N','Y') | NO | | N | | | Create_view_priv | enum('N','Y') | NO | | N | | | Show_view_priv | enum('N','Y') | NO | | N | | | Create_routine_priv | enum('N','Y') | NO | | N | | | Alter_routine_priv | enum('N','Y') | NO | | N | | | Create_user_priv | enum('N','Y') | NO | | N | | | ssl_type | enum('','ANY','X509','SPECIFIED') | NO | | | | | ssl_cipher | blob | NO | | | | | x509_issuer | blob | NO | | | | | x509_subject | blob | NO | | | | | max_questions | int(11) unsigned | NO | | 0 | | | max_updates | int(11) unsigned | NO | | 0 | | | max_connections | int(11) unsigned | NO | | 0 | | | max_user_connections | int(11) unsigned | NO | | 0 | | +-----------------------+-----------------------------------+------+-----+---------+-------+ 37 rows in set (0.01 sec) 

这里是MySQL 5.1.32的mysql.user

 mysql> desc mysql.user; +-----------------------+-----------------------------------+------+-----+---------+-------+ | Field | Type | Null | Key | Default | Extra | +-----------------------+-----------------------------------+------+-----+---------+-------+ | Host | char(60) | NO | PRI | | | | User | char(16) | NO | PRI | | | | Password | char(41) | NO | | | | | Select_priv | enum('N','Y') | NO | | N | | | Insert_priv | enum('N','Y') | NO | | N | | | Update_priv | enum('N','Y') | NO | | N | | | Delete_priv | enum('N','Y') | NO | | N | | | Create_priv | enum('N','Y') | NO | | N | | | Drop_priv | enum('N','Y') | NO | | N | | | Reload_priv | enum('N','Y') | NO | | N | | | Shutdown_priv | enum('N','Y') | NO | | N | | | Process_priv | enum('N','Y') | NO | | N | | | File_priv | enum('N','Y') | NO | | N | | | Grant_priv | enum('N','Y') | NO | | N | | | References_priv | enum('N','Y') | NO | | N | | | Index_priv | enum('N','Y') | NO | | N | | | Alter_priv | enum('N','Y') | NO | | N | | | Show_db_priv | enum('N','Y') | NO | | N | | | Super_priv | enum('N','Y') | NO | | N | | | Create_tmp_table_priv | enum('N','Y') | NO | | N | | | Lock_tables_priv | enum('N','Y') | NO | | N | | | Execute_priv | enum('N','Y') | NO | | N | | | Repl_slave_priv | enum('N','Y') | NO | | N | | | Repl_client_priv | enum('N','Y') | NO | | N | | | Create_view_priv | enum('N','Y') | NO | | N | | | Show_view_priv | enum('N','Y') | NO | | N | | | Create_routine_priv | enum('N','Y') | NO | | N | | | Alter_routine_priv | enum('N','Y') | NO | | N | | | Create_user_priv | enum('N','Y') | NO | | N | | | Event_priv | enum('N','Y') | NO | | N | | | Trigger_priv | enum('N','Y') | NO | | N | | | ssl_type | enum('','ANY','X509','SPECIFIED') | NO | | | | | ssl_cipher | blob | NO | | NULL | | | x509_issuer | blob | NO | | NULL | | | x509_subject | blob | NO | | NULL | | | max_questions | int(11) unsigned | NO | | 0 | | | max_updates | int(11) unsigned | NO | | 0 | | | max_connections | int(11) unsigned | NO | | 0 | | | max_user_connections | int(11) unsigned | NO | | 0 | | +-----------------------+-----------------------------------+------+-----+---------+-------+ 39 rows in set (0.00 sec) 

这里是MySQL 5.5.12的mysql.user

 mysql> desc mysql.user; +------------------------+-----------------------------------+------+-----+---------+-------+ | Field | Type | Null | Key | Default | Extra | +------------------------+-----------------------------------+------+-----+---------+-------+ | Host | char(60) | NO | PRI | | | | User | char(16) | NO | PRI | | | | Password | char(41) | NO | | | | | Select_priv | enum('N','Y') | NO | | N | | | Insert_priv | enum('N','Y') | NO | | N | | | Update_priv | enum('N','Y') | NO | | N | | | Delete_priv | enum('N','Y') | NO | | N | | | Create_priv | enum('N','Y') | NO | | N | | | Drop_priv | enum('N','Y') | NO | | N | | | Reload_priv | enum('N','Y') | NO | | N | | | Shutdown_priv | enum('N','Y') | NO | | N | | | Process_priv | enum('N','Y') | NO | | N | | | File_priv | enum('N','Y') | NO | | N | | | Grant_priv | enum('N','Y') | NO | | N | | | References_priv | enum('N','Y') | NO | | N | | | Index_priv | enum('N','Y') | NO | | N | | | Alter_priv | enum('N','Y') | NO | | N | | | Show_db_priv | enum('N','Y') | NO | | N | | | Super_priv | enum('N','Y') | NO | | N | | | Create_tmp_table_priv | enum('N','Y') | NO | | N | | | Lock_tables_priv | enum('N','Y') | NO | | N | | | Execute_priv | enum('N','Y') | NO | | N | | | Repl_slave_priv | enum('N','Y') | NO | | N | | | Repl_client_priv | enum('N','Y') | NO | | N | | | Create_view_priv | enum('N','Y') | NO | | N | | | Show_view_priv | enum('N','Y') | NO | | N | | | Create_routine_priv | enum('N','Y') | NO | | N | | | Alter_routine_priv | enum('N','Y') | NO | | N | | | Create_user_priv | enum('N','Y') | NO | | N | | | Event_priv | enum('N','Y') | NO | | N | | | Trigger_priv | enum('N','Y') | NO | | N | | | Create_tablespace_priv | enum('N','Y') | NO | | N | | | ssl_type | enum('','ANY','X509','SPECIFIED') | NO | | | | | ssl_cipher | blob | NO | | NULL | | | x509_issuer | blob | NO | | NULL | | | x509_subject | blob | NO | | NULL | | | max_questions | int(11) unsigned | NO | | 0 | | | max_updates | int(11) unsigned | NO | | 0 | | | max_connections | int(11) unsigned | NO | | 0 | | | max_user_connections | int(11) unsigned | NO | | 0 | | | plugin | char(64) | YES | | | | | authentication_string | text | YES | | NULL | | +------------------------+-----------------------------------+------+-----+---------+-------+ 42 rows in set (0.01 sec) 

如果您尝试将mysql.user恢复到某个版本的MySQL,那么这不会造成随意的权限问题。 以与版本无关的方式备份mysql用户权限的方法是在SQL中转储用户权限。 这样,用户授权是完全便携的。 有两种方法可以实现这一点:

选项1:使用MAATKIT

mk-show-grants将会生成你需要连接的任何mysql实例所需要的SQL。 (请记住,MAATKIT正在被迁移到Percona工具包,这个工具很可能被称为pt-show-grants)。

选项2:编写SQL GRANTS的转储脚本

我写了自己的mk-show-grants的模拟。 它将离开匿名用户。 它看起来像这样:

 mysql -hhostaddr -umyuserid -pmypassword --skip-column-names -A -e"SELECT CONCAT('SHOW GRANTS FOR ''',user,'''@''',host,''';') FROM mysql.user WHERE user<>''" | mysql -hhostaddr -umyuserid -pmypassword --skip-column-names -A | sed 's/$/;/g' > MySQLUserGrants.sql 

使用这些选项中的任何一个都可以创build用户授权的更稳定的备份。

在一个单独的笔记

现在,如果你正在使用这个日志输出选项

 [mysqld] log-output=TABLE 

mysql数据库将在mysql模式中将慢日志(如果启用)填充为mysql表格,而不是文本文件。 因此,做物理备份将包括这样的基于表的日志。 相信我,如果通用日志和慢速查询日志已启用并在mysql模式中堆积起来,则不值得磁盘空间。 只需坚持MySQL授予转储选项。

美国东部时间2011-09-19 15:54

通过SQL Grants维护MySQL权限的备份有一个非常重要的因素:

每个用户都以一些修改过的MD5格式输出密码。 对于MySQL 4.0和后面,它是一个16个字符的hexstring。 对于mysql 4.1+,它是41个字符(星号后跟一个40个字符的hexstring)。

在还原SQL Grants转储之前,请检查SQL Grants转储文件是否有任何16个字符的hex密码。 如果你看到一个,你必须在你要恢复的mysql服务器上添加以下内容到/etc/my.cnf(或Windows的my.ini):

 [mysqld] old_password=1 

old_password指令允许在同一个正在运行的mysql实例中共存16个字符和41个字符的密码并正确进行身份validation。 任何创build的密码将是16个字符。

MySQL重新启动不是必需的。 只要运行这个:

 SET GLOBAL old_password = 1; 

是的,你一定要备份mysql数据库 – 这是你服务的一个组成部分。 虽然你可以从其他信息中重build它的内容,但是如果你想尽快恢复服务,那么这样做的难度就会很大。

您可以在不同版本之间恢复mysql数据库,至less相当新的版本。 在新版本的MySQL中有一个名为mysql_upgrade的工具,可以为你升级系统表。

http://dev.mysql.com/doc/refman/5.0/en/mysql-upgrade.html

只要你恢复到一个类似的mysql版本,你可以从备份恢复mysql数据库。 如果您有疑问,只需在mysql数据库模式(来自备份和新的mysql服务器之一)之间进行区分。