Ну є 2 методи:
Спосіб 1. Відомий спосіб перейменування схеми бази даних - це скидання схеми за допомогою Mysqldump та відновлення її в іншій схемі, а потім скидання старої схеми (за потреби).
Від Шелла
mysqldump emp > emp.out
mysql -e "CREATE DATABASE employees;"
mysql employees < emp.out
mysql -e "DROP DATABASE emp;"
Хоча вищезазначений метод простий, він займає багато часу та часу. Що робити, якщо схема більше 100 Гб? Є методи, за допомогою яких ви можете з'єднати вищезазначені команди, щоб заощадити на просторі, однак це не заощадить час.
Для виправлення подібних ситуацій існує ще один швидкий метод перейменування схем, однак, потрібно робити певну обережність, роблячи це.
Спосіб 2: MySQL має дуже гарну функцію для перейменування таблиць, яка працює навіть у різних схемах. Ця операція перейменування є атомною, і ніхто більше не може отримати доступ до таблиці під час її перейменування. Це потребує короткого часу, оскільки зміна імені таблиці або її схеми є лише зміною метаданих. Ось процедурний підхід при виконанні перейменування:
Створіть нову схему бази даних з потрібним іменем. Перейменуйте таблиці зі старої схеми на нову схему, використовуючи команду «ОЗНАЙТИ ТАБЛИЦЯ» MySQL. Відкиньте стару схему бази даних.
If there are views, triggers, functions, stored procedures in the schema, those will need to be recreated too
. "RENAME TABLE" MySQL виходить з ладу, якщо на таблицях є тригери. Щоб виправити це, ми можемо зробити наступне:
1) Dump the triggers, events and stored routines in a separate file.
Це робиться за допомогою прапорців -E, -R (крім -t -d, що скидає тригери) до команди mysqldump. Щойно тригери скидаються, нам потрібно буде скинути їх із схеми, щоб команда RENAME TABLE працювала.
$ mysqldump <old_schema_name> -d -t -R -E > stored_routines_triggers_events.out
2) Створіть список лише таблиць "BASE". Їх можна знайти за допомогою запиту на information_schema.TABLES
столі.
mysql> select TABLE_NAME from information_schema.tables where
table_schema='<old_schema_name>' and TABLE_TYPE='BASE TABLE';
3) Вивантажте перегляди у вихідний файл. Перегляди можна знайти за допомогою запиту в одній information_schema.TABLES
таблиці.
mysql> select TABLE_NAME from information_schema.tables where
table_schema='<old_schema_name>' and TABLE_TYPE='VIEW';
$ mysqldump <database> <view1> <view2> … > views.out
4) Опустіть тригери на поточні таблиці в old_schema.
mysql> DROP TRIGGER <trigger_name>;
...
5) Відновіть вищезазначені файли дамп після того, як всі таблиці «База», знайдені на кроці №2, будуть перейменовані.
mysql> RENAME TABLE <old_schema>.table_name TO <new_schema>.table_name;
...
$ mysql <new_schema> < views.out
$ mysql <new_schema> < stored_routines_triggers_events.out
Складності з вищезазначеними методами: нам може знадобитися оновити ГРАНТИ для користувачів таким чином, щоб вони відповідали правильній схемі_назви. Вони можуть бути виправлені за допомогою простого ОНОВЛЕННЯ на таблицях mysql.column_priv, mysql.procs_priv, mysql.tables_priv, mysql.db, оновлення імені old_schema до new_schema та виклик "Flush privileges;". Хоча "метод 2" здається дещо складнішим, ніж "метод 1", це абсолютно можливо. Простий скрипт bash для виконання вищезазначених кроків у належній послідовності може допомогти вам заощадити місце та час під час перейменування схем бази даних наступного разу.
Команда Perbana Remote DBA написала сценарій під назвою "rename_db", який працює наступним чином:
[root@dba~]# /tmp/rename_db
rename_db <server> <database> <new_database>
Щоб продемонструвати використання цього сценарію, використовували зразок схеми “emp”, створювали тестові тригери, зберігали підпрограми на цій схемі. Постараємося перейменувати схему бази даних за допомогою скрипту, який займає кілька секунд, а не час, який вимагає методу скидання / відновлення.
mysql> show databases;
+--------------------+
| Database |
+--------------------+
| information_schema |
| emp |
| mysql |
| performance_schema |
| test |
+--------------------+
[root@dba ~]# time /tmp/rename_db localhost emp emp_test
create database emp_test DEFAULT CHARACTER SET latin1
drop trigger salary_trigger
rename table emp.__emp_new to emp_test.__emp_new
rename table emp._emp_new to emp_test._emp_new
rename table emp.departments to emp_test.departments
rename table emp.dept to emp_test.dept
rename table emp.dept_emp to emp_test.dept_emp
rename table emp.dept_manager to emp_test.dept_manager
rename table emp.emp to emp_test.emp
rename table emp.employees to emp_test.employees
rename table emp.salaries_temp to emp_test.salaries_temp
rename table emp.titles to emp_test.titles
loading views
loading triggers, routines and events
Dropping database emp
real 0m0.643s
user 0m0.053s
sys 0m0.131s
mysql> show databases;
+--------------------+
| Database |
+--------------------+
| information_schema |
| emp_test |
| mysql |
| performance_schema |
| test |
+--------------------+
Як видно з вищенаведеного результату, схема бази даних "emp" була перейменована на "emp_test" менш ніж за секунду. Нарешті, це сценарій від Percona, який використовується вище для "методу 2".
#!/bin/bash
# Copyright 2013 Percona LLC and/or its affiliates
set -e
if [ -z "$3" ]; then
echo "rename_db <server> <database> <new_database>"
exit 1
fi
db_exists=`mysql -h $1 -e "show databases like '$3'" -sss`
if [ -n "$db_exists" ]; then
echo "ERROR: New database already exists $3"
exit 1
fi
TIMESTAMP=`date +%s`
character_set=`mysql -h $1 -e "show create database $2\G" -sss | grep ^Create | awk -F'CHARACTER SET ' '{print $2}' | awk '{print $1}'`
TABLES=`mysql -h $1 -e "select TABLE_NAME from information_schema.tables where table_schema='$2' and TABLE_TYPE='BASE TABLE'" -sss`
STATUS=$?
if [ "$STATUS" != 0 ] || [ -z "$TABLES" ]; then
echo "Error retrieving tables from $2"
exit 1
fi
echo "create database $3 DEFAULT CHARACTER SET $character_set"
mysql -h $1 -e "create database $3 DEFAULT CHARACTER SET $character_set"
TRIGGERS=`mysql -h $1 $2 -e "show triggers\G" | grep Trigger: | awk '{print $2}'`
VIEWS=`mysql -h $1 -e "select TABLE_NAME from information_schema.tables where table_schema='$2' and TABLE_TYPE='VIEW'" -sss`
if [ -n "$VIEWS" ]; then
mysqldump -h $1 $2 $VIEWS > /tmp/${2}_views${TIMESTAMP}.dump
fi
mysqldump -h $1 $2 -d -t -R -E > /tmp/${2}_triggers${TIMESTAMP}.dump
for TRIGGER in $TRIGGERS; do
echo "drop trigger $TRIGGER"
mysql -h $1 $2 -e "drop trigger $TRIGGER"
done
for TABLE in $TABLES; do
echo "rename table $2.$TABLE to $3.$TABLE"
mysql -h $1 $2 -e "SET FOREIGN_KEY_CHECKS=0; rename table $2.$TABLE to $3.$TABLE"
done
if [ -n "$VIEWS" ]; then
echo "loading views"
mysql -h $1 $3 < /tmp/${2}_views${TIMESTAMP}.dump
fi
echo "loading triggers, routines and events"
mysql -h $1 $3 < /tmp/${2}_triggers${TIMESTAMP}.dump
TABLES=`mysql -h $1 -e "select TABLE_NAME from information_schema.tables where table_schema='$2' and TABLE_TYPE='BASE TABLE'" -sss`
if [ -z "$TABLES" ]; then
echo "Dropping database $2"
mysql -h $1 $2 -e "drop database $2"
fi
if [ `mysql -h $1 -e "select count(*) from mysql.columns_priv where db='$2'" -sss` -gt 0 ]; then
COLUMNS_PRIV=" UPDATE mysql.columns_priv set db='$3' WHERE db='$2';"
fi
if [ `mysql -h $1 -e "select count(*) from mysql.procs_priv where db='$2'" -sss` -gt 0 ]; then
PROCS_PRIV=" UPDATE mysql.procs_priv set db='$3' WHERE db='$2';"
fi
if [ `mysql -h $1 -e "select count(*) from mysql.tables_priv where db='$2'" -sss` -gt 0 ]; then
TABLES_PRIV=" UPDATE mysql.tables_priv set db='$3' WHERE db='$2';"
fi
if [ `mysql -h $1 -e "select count(*) from mysql.db where db='$2'" -sss` -gt 0 ]; then
DB_PRIV=" UPDATE mysql.db set db='$3' WHERE db='$2';"
fi
if [ -n "$COLUMNS_PRIV" ] || [ -n "$PROCS_PRIV" ] || [ -n "$TABLES_PRIV" ] || [ -n "$DB_PRIV" ]; then
echo "IF YOU WANT TO RENAME the GRANTS YOU NEED TO RUN ALL OUTPUT BELOW:"
if [ -n "$COLUMNS_PRIV" ]; then echo "$COLUMNS_PRIV"; fi
if [ -n "$PROCS_PRIV" ]; then echo "$PROCS_PRIV"; fi
if [ -n "$TABLES_PRIV" ]; then echo "$TABLES_PRIV"; fi
if [ -n "$DB_PRIV" ]; then echo "$DB_PRIV"; fi
echo " flush privileges;"
fi