mysql:复制包含外键的表结构
我知道如何使用mysql:复制包含外键的表结构,mysql,Mysql,我知道如何使用像创建旧表那样创建新表来复制表,但这也不能复制外键约束。我还可以对来自show create table old_table的结果执行字符串操作(使用正则表达式替换表名和外键约束名),但这似乎很容易出错。是否有更好的方法来复制表的结构,包括外键?您可能可以编写一个过程,在创建表之后,根据以下信息准备ALTER table…语句: SELECT * FROM INFORMATION_SCHEMA.KEY_COLUMN_USAGE WHERE TABLE_NAME LIKE '&l
像创建旧表那样创建新表来复制表,但这也不能复制外键约束。我还可以对来自show create table old_table
的结果执行字符串操作(使用正则表达式替换表名和外键约束名),但这似乎很容易出错。是否有更好的方法来复制表的结构,包括外键?您可能可以编写一个过程,在创建表之后,根据以下信息准备ALTER table…
语句:
SELECT *
FROM INFORMATION_SCHEMA.KEY_COLUMN_USAGE
WHERE TABLE_NAME LIKE '<table_name>'
AND TABLE_SCHEMA = '<db_name>'
AND REFERENCED_TABLE_NAME IS NOT NULL;
选择*
来自信息\u SCHEMA.KEY\u列\u用法
其中表名称类似于“”
和表_SCHEMA=''
且引用的_表_名称不为空;
如果只需编写一点脚本就可以了,您可以利用SHOW CREATE TABLE
这样的几行代码(PHP,但该概念适用于任何语言):
//获取create语句
$retrieve=“SHOW CREATE TABLE”;
$create=
//隔离“创建表”索引
$create=$create['create Table'];
//到处用新表名替换旧表名
$create=preg_replace(“/”$newname.“/”,$oldname,$create);
//您可能需要重命名外键以防止名称重复使用错误。
//看http://stackoverflow.com/questions/12623651/
$create=preg_replace(“/FK_/”,“FK_TEMP_”,$create);
//创建新表
不是很优雅,但到目前为止还可以用。我是在一个测试环境中做这件事的,所以我把它放在我的setUp()
方法中 Wrikken的回答启发了我。让我扩展一下
嗯,事情更复杂。请参阅:。它说,临时
表和其他东西也会有问题。Wrikken提到的解决方案是一个很好的方法,但是,您需要至少再进行一次查找,以获取有关UPDATE
和DELETE
规则的信息:
SELECT *
FROM INFORMATION_SCHEMA.REFERENTIAL_CONSTRAINTS
WHERE TABLE_NAME LIKE '<table_name>'
AND CONSTRAINT_SCHEMA = '<db_name>';
选择*
来自信息\u模式。参考\u约束
其中表名称类似于“”
和约束_模式=“”;
因此,获得一个简化任务的工具可能是一个好主意。我个人使用Adminer()。它附带了一个导出整个数据库的选项(包括所有表、触发器、外键等等)。一旦导出它(在SQL语法中),就可以轻松地更改DB名称并将其重新导入。我在项目的bugs部分写到了这一点(见票证380)
也许你已经有了你最喜欢的数据库管理器,而不想要另一个。然后,您可以按照以下步骤操作:
使用mysqldump
->转储数据库,您将获得file.sql
创建一个新的数据库
在新数据库中执行file.sql
Adminer
和mysqldump
都有一个选项,可以只选择特定的表,这样就不必导出整个数据库。如果您只需要结构而不需要数据,请为mysqldump
使用一个选项-d
,或者在Adminer
中单击该选项。如果您有phpMyAdmin,则可以只导出表的结构,然后在.sql文件中将旧表名更改为新表名并将其导入回
这是一种相当快速的方法如果您只想清理表,可以将所有相关数据复制到复制表中。而不是截断并复制回来。结果是,您保留了FK
CREATE TABLE IF NOT EXISTS t_copy LIKE t_origin;
INSERT INTO t_copy
SELECT t_origin.*
FROM t_origin;
SET FOREIGN_KEY_CHECKS = 0;
TRUNCATE t_origin;
INSERT INTO t_origin
SELECT t_copy.*
FROM t_copy;
DROP TABLE t_copy;
SET FOREIGN_KEY_CHECKS = 1;
我创建了一个bash脚本,将一个表复制到另一个数据库中,通过向其中添加“_1”来修改键和约束:
mysqldump -h ${host_ip} -u root -p${some_password} ${some_database} ${some_table} > some_filename
sed -i -r -e 's@KEY `([a-zA-Z0-9_]*)`@KEY `\1_1`@g' -e 's@CONSTRAINT `([a-zA-Z0-9_]*)`@CONSTRAINT `\1_1`@g' some_filename
mysql -h ${host_ip} -u root -p${some_password} ${some_new_database} < some_filename
mysqldump-h${host\u ip}-u root-p${some\u password}${some\u database}${some\u table}>some\u文件名
sed-i-r-e's@KEY`([a-zA-Z0-9\]*)`@KEY`\1\`1`@g'-e's@CONSTRAINT`([a-zA-Z0-9\]*)`@CONSTRAINT`\1\'1`@g'某些文件名
mysql-h${host\u ip}-u root-p${some\u password}${some\u new\u database}
这也适用于新的数据库实例,但不需要使用“sed”命令。只有当源数据库和目标数据库位于同一实例中时,才需要执行此操作。您是否曾经尝试过这样做?我现在正试图弄明白这一点,但无法真正让它工作。令人遗憾的是,创建表类创建了95%的输出表。。。我,如果这对任何人都有用的话。我把几个相关的问题粘在一起,就像这个问题中提到的那样。如果你处理的是脚本操作,这是最好的方法。令人遗憾的是,创建TABLE-LIKE完成了95%。我,如果这对任何人都有用的话。我把几个相关的问题粘在一起,就像这个问题中提到的那样。这实际上是一个很好的替代解决方案。我不明白那些反对票+从我这里得到1。
mysqldump -h ${host_ip} -u root -p${some_password} ${some_database} ${some_table} > some_filename
sed -i -r -e 's@KEY `([a-zA-Z0-9_]*)`@KEY `\1_1`@g' -e 's@CONSTRAINT `([a-zA-Z0-9_]*)`@CONSTRAINT `\1_1`@g' some_filename
mysql -h ${host_ip} -u root -p${some_password} ${some_new_database} < some_filename