SQLite 长臂检查约束?
SQLite long-arm check constraint?
我在 SQLite 中有两个表,建模一对多关系:
CREATE TABLE parent (
id INTEGER PRIMARY KEY,
payload TEXT
);
CREATE TABLE child (
id INTEGER PRIMARY KEY,
flag BOOLEAN,
parent_id INTEGER,
FOREIGN KEY(parent_id) REFERENCES parent (id) ON DELETE CASCADE ON UPDATE CASCADE,
);
有没有办法在child.flag
上放一个CHECK CONSTRAINT
,这样对于任何[=15],在所有child
中总是只有一个True
=]?
我的研究表明,没有办法让本地检查约束知道它的兄弟状态。我建议将检查逻辑放在应用层。
"Although this is solved by putting application-level logic, I still would like to see if there is any creative solution in pure database, not involving apps and triggers."
是的,可以通过 partial unique index:
实现所需的约束
CREATE UNIQUE INDEX idx ON child (flag, parent_id) WHERE flag = 1;
INSERT INTO parent(id, payload) VALUES(1, 'Parent1');
INSERT INTO child(id, flag, parent_id) VALUES (1, 1, 1);
INSERT INTO child(id, flag, parent_id) VALUES (2, 0, 1);
INSERT INTO child(id, flag, parent_id) VALUES (3, 0, 1);
SELECT * FROM child;
-- trying to insert second active child will cause unique index violation
INSERT INTO child(id, flag, parent_id) VALUES (4, 1, 1)
-- UNIQUE constraint failed: child.flag, child.parent_id
我在 SQLite 中有两个表,建模一对多关系:
CREATE TABLE parent (
id INTEGER PRIMARY KEY,
payload TEXT
);
CREATE TABLE child (
id INTEGER PRIMARY KEY,
flag BOOLEAN,
parent_id INTEGER,
FOREIGN KEY(parent_id) REFERENCES parent (id) ON DELETE CASCADE ON UPDATE CASCADE,
);
有没有办法在child.flag
上放一个CHECK CONSTRAINT
,这样对于任何[=15],在所有child
中总是只有一个True
=]?
我的研究表明,没有办法让本地检查约束知道它的兄弟状态。我建议将检查逻辑放在应用层。
"Although this is solved by putting application-level logic, I still would like to see if there is any creative solution in pure database, not involving apps and triggers."
是的,可以通过 partial unique index:
实现所需的约束CREATE UNIQUE INDEX idx ON child (flag, parent_id) WHERE flag = 1;
INSERT INTO parent(id, payload) VALUES(1, 'Parent1');
INSERT INTO child(id, flag, parent_id) VALUES (1, 1, 1);
INSERT INTO child(id, flag, parent_id) VALUES (2, 0, 1);
INSERT INTO child(id, flag, parent_id) VALUES (3, 0, 1);
SELECT * FROM child;
-- trying to insert second active child will cause unique index violation
INSERT INTO child(id, flag, parent_id) VALUES (4, 1, 1)
-- UNIQUE constraint failed: child.flag, child.parent_id