【问题标题】:Best way to update foreign keys to point to different table?更新外键以指向不同表的最佳方法?
【发布时间】:2018-01-09 21:36:50
【问题描述】:

我正在清理一个随着时间的推移变得混乱的 mysql 数据库。清理是增量的(也就是说我不想一次迁移所有表)。

我的偏好是尽可能避免对旧表进行破坏性编辑。例如,我将表文件夹重命名为 decomissioned_folders,然后创建一个新的 folders 表,可以将适当的记录迁移到该表中,而不会影响旧表。

这个数据库中有很多表,其中一个是表users。数据库中的许多其他表都有指向表users的外键。

我想知道:

如果我将表 users 重命名为 decomissioned_users 然后创建一个新的 users 表并填充它,最好的处理方法是什么用外键?对于数据库中现在包含指向旧 decomissioned_users 表的外键的每个表,是否有一种(简单)方法来更新这些外键以指向新 users代替表?

(注意,ids的值在表之间不会改变,所以外键的值在表之间保持有效。)

【问题讨论】:

    标签: mysql foreign-keys


    【解决方案1】:

    有一个简单的方法,但它涉及删除旧外键并创建新外键。

    这是一个演示:

    mysql> create table foo (id serial primary key);
    
    mysql> create table bar (foo_id bigint unsigned, foreign key (foo_id) references foo(id));
    

    重命名表后,外键引用会自动更新以跟随重命名的表:

    mysql> rename table foo to old_foo;
    
    mysql> show create table bar\G
    *************************** 1. row ***************************
           Table: bar
    Create Table: CREATE TABLE `bar` (
      `foo_id` bigint(20) unsigned DEFAULT NULL,
      KEY `foo_id` (`foo_id`),
      CONSTRAINT `bar_ibfk_1` FOREIGN KEY (`foo_id`) REFERENCES `old_foo` (`id`)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4
    

    创建新表后:

    mysql> create table foo like old_foo;
    

    我们可以通过以下方式重新定义外键:

    mysql> alter table bar 
           drop foreign key bar_ibfk_1, 
           add foreign key (foo_id) references foo(id);
    

    现在表引用了新表:

    mysql> show create table bar\G
    *************************** 1. row ***************************
           Table: bar
    Create Table: CREATE TABLE `bar` (
      `foo_id` bigint(20) unsigned DEFAULT NULL,
      KEY `foo_id` (`foo_id`),
      CONSTRAINT `bar_ibfk_2` FOREIGN KEY (`foo_id`) REFERENCES `foo` (`id`)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4
    

    如果您有很多外键,您可以通过查询 INFORMATION_SCHEMA、表 TABLE_CONSTRAINTS 和 KEY_COLUMN_USAGE 来发现它们的列表。从此元数据中,您可以构建 ALTER TABLE 语句来更改外键。

    【讨论】:

    • 谢谢比尔,这是一个很好的解释!
    猜你喜欢
    • 2016-11-20
    • 2011-10-09
    • 2020-11-26
    • 1970-01-01
    • 1970-01-01
    • 2021-03-24
    • 1970-01-01
    • 1970-01-01
    • 2015-12-21
    相关资源
    最近更新 更多