在MySQL中,我可以在提交之前推迟参照完整性检查

Ros*_*ane 50 mysql referential-integrity

正如在这个问题中,我一直在阅读PoEAA,并想知道是否可以推迟参考完整性检查,直到在MySQL中提交.

想要在同一次提交中插入一堆产品和相关产品时,我遇到了这个问题.即使在事务中,当我尝试插入related_products连接表时,我也会遇到约束错误.

如果它有帮助,我正在使用PHP PDO进行数据库连接.

我很感激您提供的任何帮助.

Ros*_*ane 66

看起来我的答案就在这里 ......

与MySQL一样,在插入,删除或更新许多行的SQL语句中,InnoDB逐行检查UNIQUE和FOREIGN KEY约束.执行外键检查时,InnoDB会在必须查看的子记录或父记录上设置共享行级锁.InnoDB立即检查外键约束; 检查不会延迟到事务提交.根据SQL标准,默认行为应该是延迟检查.也就是说,只有在处理完整个SQL语句后才会检查约束.在InnoDB实现延迟约束检查之前,有些事情是不可能的,例如删除使用外键引用自身的记录.

回到绘图板.

  • 如果这对您来说是一个重要的功能,您可以考虑迁移到支持延迟约束的PostgreSQL(包括自9.0以来的延迟唯一约束) - 并且您还可以获得许多其他漂亮的功能(递归查询,窗口函数,检查约束) ,...) (12认同)
  • @rossmcf +1,因为我一直在搜索这句话的文档:D (3认同)

a_h*_*ame 14

如果你问MySQL是否支持DEFERRABLE外键的属性(包括选项INITIALLY DEFERRED),那么答案是明确的.

在MySQL中提交时,您不能推迟约束检查.

并且 - 正如您已经指出的那样 - 它们总是在"行级别"而非"语句级别"进行评估.


Tha*_*ava 10

您可以通过设置服务器变量暂时禁用外键检查来处理innodb引擎的此限制:

set foreign_key_checks=0;
Run Code Online (Sandbox Code Playgroud)

来自MySQL手册:

mysqldump还在转储文件中生成正确的表定义,并且不会忘记外键.

为了更容易为具有外键关系的表重新加载转储文件,mysqldump会自动在转储输出中包含一个语句,以将foreign_key_checks设置为0.这样可以避免在重新加载转储时必须按特定顺序重新加载表的问题.也可以手动设置此变量:

mysql> SET foreign_key_checks = 0;
mysql> SOURCE dump_file_name;
mysql> SET foreign_key_checks = 1;
Run Code Online (Sandbox Code Playgroud)

  • 我不确定这仍然会在更新后检查约束,但这正是我所寻求的. (6认同)
  • @rossmcf它不会 (5认同)