首页 文章

如何截断外键约束表?

提问于
浏览
523

mygroup 上的 TRUNCATE 为什么不起作用?即使我有 ON DELETE CASCADE SET 我得到:

ERROR 1701(42000):无法截断外键约束中引用的表(mytest.instance,CONSTRAINT instance_ibfk_1 FOREIGN KEY(GroupID)REFERENCES mytest.mygroup(ID))

drop database mytest;
create database mytest;
use mytest;

CREATE TABLE mygroup (
   ID    INT NOT NULL AUTO_INCREMENT PRIMARY KEY
) ENGINE=InnoDB;

CREATE TABLE instance (
   ID           INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
   GroupID      INT NOT NULL,
   DateTime     DATETIME DEFAULT NULL,

   FOREIGN KEY  (GroupID) REFERENCES mygroup(ID) ON DELETE CASCADE,
   UNIQUE(GroupID)
) ENGINE=InnoDB;

10 回答

  • 10

    我只想这样做:

    DELETE FROM mytest.instance;
    ALTER TABLE mytest.instance AUTO_INCREMENT = 1;
    
  • 6

    虽然这个问题是在5年前提出的,但我不知道当时MySql中存在此工具,但现在如果使用 phpmyadmin ,您只需打开数据库,然后选择要截断的表 . 在底部有一个下拉列表,其中列出了许多选项 . 打开它并在 Headers Delete data or table 下选择 Empty 选项 . 它会自动转到下一页,其中复选框中有一个选项,称为启用外键检查 . 只需取消选择它并按是按钮,所选表格将被截断 . 可以在内部运行user447951的答案中建议的查询 . 但是从phpmyadmin界面使用非常方便 .

  • 1140

    如果表的数据库引擎不同,您将收到此错误,因此将它们更改为InnoDB

    ALTER TABLE my_table ENGINE = InnoDB;
    
  • 126

    根据mysql documentation,TRUNCATE不能用于具有外键关系的表 . 没有完整的替代AFAIK .

    删除约束仍然不会调用ON DELETE和ON UPDATE . 我能想到的唯一解决方案是:

    • 删除所有行,删除外键,截断,重新创建键

    • 删除所有行,重置auto_increment(如果使用)

    在MySQL中似乎TRUNCATE还不是一个完整的功能(它也不会调用触发器) . 见评论

  • 753

    你可以做

    DELETE FROM `mytable` WHERE `id` > 0
    
  • 3

    获取旧的外键检查状态和sql模式是在将模型同步到数据库时将Mysql Workbench截断/删除表的最佳方法 .

    SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0;
    SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0;`
    SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='TRADITIONAL,ALLOW_INVALID_DATES';
    
    DROP TABLE TABLE_NAME;
    TRUNCATE TABLE_NAME;
    
    SET SQL_MODE=@OLD_SQL_MODE;
    SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS;
    SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS;
    
  • 0

    是的你可以:

    SET FOREIGN_KEY_CHECKS = 0;
    
    TRUNCATE table1;
    TRUNCATE table2;
    
    SET FOREIGN_KEY_CHECKS = 1;
    

    使用这些语句,您可能会冒险将行放入不符合 FOREIGN KEY 约束的表中 .

  • 10

    答案确实是the one provided by zerkms,如 Option 1 所述:

    选项1:不会有损坏数据完整性的风险:删除约束执行TRUNCATE手动删除现在引用无处的行创建约束

    棘手的部分是 Removing constraints ,所以我想告诉你如何,以防有人需要知道如何做到这一点:

    • 运行 SHOW CREATE TABLE <Table Name> 查询以查看 FOREIGN KEY 的名称是什么(下图中的红框):

    enter image description here

    • 运行 ALTER TABLE <Table Name> DROP FOREIGN KEY <Foreign Key Name> . 这将删除外键约束 .

    • 删除关联的 Index (通过表结构页面),您就完成了 .

    重新创建外键:

    ALTER TABLE <Table Name>
    ADD FOREIGN KEY (<Field Name>) REFERENCES <Foreign Table Name>(<Field Name>);
    
  • 0

    如果你使用phpMyAdmin很容易 .

    只需取消选中 SQL 标签下的 Enable foreign key checks 选项并运行 TRUNCATE <TABLE_NAME>

    enter image description here

  • 1

    您不能 TRUNCATE 上应用了FK约束的表( TRUNCATEDELETE 不同) .

    要解决此问题,请使用以下任一解决方案 . 两者都存在损害数据完整性的风险 .

    Option 1:

    • 删除约束

    • 执行 TRUNCATE

    • 手动删除现在引用 nowhere 的行

    • 创建约束

    Option 2:user447951 建议their answer

    SET FOREIGN_KEY_CHECKS = 0; 
    TRUNCATE table $table_name; 
    SET FOREIGN_KEY_CHECKS = 1;
    

相关问题