Должен ли я сделать резервную копию и восстановить базу данных `mysql`?


15

В процессе создания автоматизированного решения для резервного копирования и восстановления всего сервера MySQL я натолкнулся на mysqlбазу данных, которая, кажется, содержит учетные записи пользователей, разрешения, метаданные и тому подобное. Нужно ли создавать резервную копию этой базы данных? Будет ли резервное копирование и попытка восстановить это сломать вещи?

У меня было чертовски много времени, когда я гуглял "mysql для резервного копирования базы данных mysql", как вы можете себе представить.


3
Чтобы выполнить полное восстановление, вам нужно сделать резервную копию всего, кроме базы данных «information_schema».
— Джон Гарденье

Ответы:


16

Вот кое-что интересное: резервное копирование mysqlбазы данных сильно ограничивает вас тем, что вы можете восстановить такую ​​базу данных только до той же версии mysql, с которой вы выполняли резервное копирование. Вот почему:

Вот mysql.user из MySQL 5.0.45

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.user из MySQL 5.1.32

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.user из MySQL 5.5.12

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 сгенерирует необходимый SQL-запрос независимо от того, к какому экземпляру mysql вы подключаетесь. (Имейте в виду, что MAATKIT переносится в Percona Toolkit. Этот инструмент, скорее всего, будет называться pt-show-grants).

ВАРИАНТ № 2: Сценарий сброса SQL-грантов

Я написал свою собственную эмуляцию 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

Использование любого из этих параметров создаст более стабильную резервную копию пользовательских грантов.

НА ОТДЕЛЬНОМ ПРИМЕЧАНИЕ

Теперь, если вы используете эту опцию вывода журнала

[mysqld]
log-output=TABLE

база данных mysql заполняет медленный журнал (если он включен) как таблицу mysql в схеме mysql, а не как текстовый файл. Таким образом, создание физических резервных копий будет включать такие журналы на основе таблиц mysql. Поверьте, это не стоит дискового пространства, если общий лог и медленный журнал запросов включены и накапливаются в схеме mysql. Просто придерживайтесь опций дампов MySQL Grants.

ОБНОВЛЕНИЕ 2011-09-19 15:54 ПО ВОСТОЧНОМУ ВРЕМЕНИ

Существует один очень важный фактор в поддержке резервного копирования разрешений MySQL с помощью грантов SQL:

Каждый пользователь выходит со своим паролем в каком-то измененном формате MD5. Для mysql 4.0 и обратно это шестнадцатеричная строка из 16 символов. Для mysql 4.1+ это 41 символ (звездочка, за которой следует шестнадцатеричная строка из 40 символов).

Прежде чем восстанавливать дамп SQL-грантов, проверьте файл дампа SQL-грантов на наличие 16-значных шестнадцатеричных паролей. Если вы видите даже один, вы должны добавить следующее в /etc/my.cnf (или my.ini для Windows) на сервере MySQL, на который вы будете восстанавливать:

[mysqld]
old_password=1

Old_password директива разрешает 16-полукокса и 41 преобразовывались пароли сосуществовать и правильно аутентификации в том же экземпляре Запуск MySQL. Все пароли, созданные в будущем, будут состоять из 16 символов.

Перезапуск MySQL не требуется. Просто запустите это:

SET GLOBAL old_password = 1;

+1 за полный ответ.
— Мирча Вутцовичи

1
Я бы лучше SHOW GRANTSQUOTE()SELECT CONCAT('SHOW GRANTS FOR ',QUOTE(user),'@',QUOTE(host),';') FROM mysql.user WHERE user<>'';
— записал

11

Да, вы определенно хотите сделать резервную копию mysqlбазы данных - это неотъемлемая часть вашего сервиса. Несмотря на то, что вы можете восстановить его содержимое из другой информации, сложность сделать это непомерно высока, если вы пытаетесь быстро вернуться к обслуживанию.


1
+1 Если вы не сделаете резервную копию базы данных mysql, вероятность того, что система будет повреждена после восстановления, очень высока. Был там, сделал это, получил психические шрамы, чтобы доказать это.
— Джон Гарденье

6

Вы можете восстановить базу данных mysql между версиями, по крайней мере, относительно недавних версий. В mysql_upgradeновые версии MySQL включен инструмент , который обновит системные таблицы для вас.

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


Это очень верно. Я видел случаи, когда некоторые используют это и обновляют просто отлично. Я видел, как другие убивали его. С моей точки зрения, как MySQL DBA. Я потерял веру в этот метод. Поскольку ваш ответ отражает твердую веру в его использование, вы должны быть из первой группы. +1 за такую ​​уверенность в mysql_upgrade.
— RolandoMySQLDBA

Когда я импортировал свой 5.6 в версию 8.0, он потерял работу сервера.
— PHPst

5

Пока вы восстанавливаете аналогичную версию mysql, вы можете восстановить базу данных mysql из резервной копии. Если вы сомневаетесь, просто проведите различие между схемами базы данных mysql (из резервной копии и из нового сервера mysql).


+1 за упоминание о восстановлении mysql до той же версии, с которой вы сделали резервную копию.
— RolandoMySQLDBA
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.