Сохранение базы данных с поставок MySQL на том же сервере, обновленной с производства
-
16-10-2019 - |
Вопрос
Я только что мигрировал свой MySQL 5.5.20 на Amazon RDS из MySQL на EC2. Единственное, с чем мне трудно, - это как держать мою постановную базу данных обновляться из производства. Раньше я только что пробежал ночь mysqlhotcopy
перезаписать постановку из производства, и все было хорошо. Тем не менее, RDS не дает мне доступ к оболочке, поэтому я думаю, что мне нужно чистое решение SQL, чтобы избежать mysqldump
на другой сервер, а затем восстановление обратно на сервер RDS, что кажется ненужным, поскольку я просто хочу скопировать в базу данных в датабазу на том же сервере. Я знаю, что RDS поддерживает Replicas Replicas, но мне нужна реплика для записи, и я не хочу запускать еще один экземпляр для моей базы данных, которая не видит много действий.
Как лучше всего выполнить копию базы данных к датабазе на том же сервере в чистом SQL?
Решение
Я вижу, что MySQldump немного боли в шее из -за трансфортирования данных, а затем в.
Допустим, вы копируете данные из ProdDB в SteargedB. Вот запрос на создание сценария для бокового копирования каждой таблицы:
select
concat
(
'drop table if exists ',db2,'.',tbl,'; ',
'create table ',db2,'.',tbl,' like ',db1,'.',tbl,'; ',
'insert into ',db2,'.',tbl,' select * from ',db1,'.',tbl,';'
)
from (select table_schema db1,table_name tbl
from information_schema.tables where table_schema='stack_dev') tbls,
(select 'stack_test' db2) dbname;
Просто сгенерируйте скрипт в виде текстового файла SQL и импортируйте текстовый файл на целевой сервер:
PROD_IP-10.1.2.20
STAG_IP=10.1.2.40
mysql -h${PROD_IP} -uusername -p --skip-column-names -A -e"select concat('drop table if exists ',db2,'.',tbl,'; ','create table ',db2,'.',tbl,' like ',db1,'.',tbl,'; ','insert into ',db2,'.',tbl,' select * from ',db1,'.',tbl,';') from (select table_schema db1,table_name tbl from information_schema.tables where table_schema='stack_dev') tbls,(select 'stack_test' db2) dbname;" > /root/CopyFromProdToStage.sql
mysql -h${STAG_IP} -uusername -p -A < /root/CopyFromProdToStage.sql
Это должно работать просто для Myisam. Это также должно работать для InnoDB, если нет ограничений. Если есть ограничения, вам, возможно, придется отключить их для сессии импорта:
PROD_IP-10.1.2.20
STAG_IP=10.1.2.40
echo "SET FOREIGN_KEY_CHECKS=0;" > /root/CopyFromProdToStage.sql
mysql -h${PROD_IP} -uusername -p --skip-column-names -A -e"select concat('drop table if exists ',db2,'.',tbl,'; ','create table ',db2,'.',tbl,' like ',db1,'.',tbl,'; ','insert into ',db2,'.',tbl,' select * from ',db1,'.',tbl,';') from (select table_schema db1,table_name tbl from information_schema.tables where table_schema='stack_dev') tbls,(select 'stack_test' db2) dbname;" >> /root/CopyFromProdToStage.sql
mysql -h${STAG_IP} -uusername -p -A < /root/CopyFromProdToStage.sql
Обновление 2012-03-09 17:14 EST
У меня есть хранящаяся процедура, которая выполнит это. Запустите следующее только один раз:
DROP DATABASE IF EXISTS utility;
CREATE DATABASE utility;
DELIMITER $$
DROP PROCEDURE IF EXISTS `utility`.`CopyDB` $$
CREATE PROCEDURE `utility`.`CopyDB` (sourceDB VARCHAR(64),targetDB VARCHAR(64))
TheStoredProcedure:BEGIN
DECLARE found_count,ndx,ndx_last INT;
DECLARE sqlcmd VARCHAR(1024);
SELECT COUNT(1) INTO found_count
FROM information_schema.tables
WHERE table_schema = sourceDB;
IF found_count = 0 THEN
LEAVE TheStoredProcedure;
END IF;
DROP TABLE IF EXISTS DBTablesToCopy;
CREATE TABLE DBTablesToCopy
(
id INT NOT NULL AUTO_INCREMENT,
src VARCHAR(64),
tgt VARCHAR(64),
tbl VARCHAR(64),
PRIMARY KEY (id)
) ENGINE=MyISAM;
DROP TABLE IF EXISTS SQLScriptToCopyTables;
CREATE TABLE SQLScriptToCopyTables
(
id INT NOT NULL AUTO_INCREMENT,
sqltext VARCHAR(1024),
PRIMARY KEY (id)
) ENGINE=MyISAM;
INSERT INTO DBTablesToCopy (src,tgt,tbl)
SELECT sourceDB,targetDB,table_name
FROM information_schema.tables
WHERE table_schema = sourceDB;
INSERT INTO SQLScriptToCopyTables (sqltext) VALUES
(CONCAT('DROP DATABASE IF EXISTS ',targetDB));
INSERT INTO SQLScriptToCopyTables (sqltext) VALUES
(CONCAT('CREATE DATABASE ',targetDB));
SELECT MAX(id) INTO ndx_last FROM DBTablesToCopy;
SET ndx = 0;
WHILE ndx < ndx_last DO
SET ndx = ndx + 1;
INSERT INTO SQLScriptToCopyTables (sqltext)
SELECT CONCAT('CREATE TABLE ',tgt,'.',tbl,' LIKE ',src,'.',tbl)
FROM DBTablesToCopy WHERE id = ndx;
END WHILE;
SET ndx = 0;
WHILE ndx < ndx_last DO
SET ndx = ndx + 1;
INSERT INTO SQLScriptToCopyTables (sqltext)
SELECT CONCAT('INSERT INTO ',tgt,'.',tbl,' SELECT * FROM ',src,'.',tbl)
FROM DBTablesToCopy WHERE id = ndx;
END WHILE;
SELECT MAX(id) INTO ndx_last FROM SQLScriptToCopyTables;
SET ndx = 0;
WHILE ndx < ndx_last DO
SET ndx = ndx + 1;
SELECT sqltext INTO @stmt FROM SQLScriptToCopyTables WHERE id = ndx;
PREPARE s1 FROM @stmt;
EXECUTE s1;
DEALLOCATE PREPARE s1;
END WHILE;
END $$
DELIMITER ;
Тогда в любое время вы хотите копировать stack_dev
к stack_test
, сделай это:
call utility.copydb('stack_dev','stack_test');
и это все.
Попробуй !!!