3

我试图在 SQLite 中使用外键支持来维护具有自反连接的单表数据库的引用完整性。

例如

PRAGMA foreign_keys = ON;

create table tree (
  objectId text unique not null,
  parentObjectID text,
  foreign key (parentObjectID) references tree(parentObjectID) on delete cascade
)

我希望的行为是,当父行被删除时,其子行及其子行也将被删除。

但是,当我尝试删除根行时(预期的行为是数据库中的所有其他行也被删除),我收到此错误:

sqlite> delete from tree where objectid = '0';
Error: foreign key mismatch

SQLite外键支持(和删除行为)可以提供我的期望吗?

4

1 回答 1

2

您的问题很简单,您的 FKparentObjectId引用parentObjectId而不是objectIdSQLite 在您尝试使用该表之前不会检测到这一点混乱。如果您的 FK 定义如下:

foreign key (parentObjectID) references tree(objectID) on delete cascade

来自精美手册

因此,换句话说,需要同时查看子项和父项的错误配置的外键约束是 DML 错误。外键 DML 错误的英文错误消息通常是“外键不匹配”,但如果父表不存在,也可能是“没有这样的表”。如果出现以下情况,可能会报告外键 DML 错误:

  • 父表不存在,或
  • 外键约束中命名的父键列不存在,或者
  • 外键约束中命名的父键列不是父表的主键,并且不受使用 CREATE TABLE 中指定的整理顺序的唯一约束,或
  • 子表引用了父表的主键,没有指定主键列,并且父表中的主键列数与子键列数不匹配。

第三点似乎适用于此,因为parentObjectId它既不是 PK 也不是被限制为唯一的,所以这就是为什么在您尝试修改表的内容(即使用 DML 语句而不是 DDL 语句)之前不会看到错误的原因。

于 2013-01-12T20:50:57.600 回答