1

假设您有下表,旨在表示分层数据:

+--------+-------------+
| Field  | Type        |
+--------+-------------+
| id     | int(10)     |
| parent | int(10)     |
| name   | varchar(45) |
+--------+-------------+

该表是自引用的,因为parent_id引用id.

所以你可能有以下数据:

+----+--------+---------------+
| id | parent | name          |
+----+--------+---------------+
|  1 |      0 | fruit         |
|  2 |      0 | vegetable     |
|  3 |      1 | apple         |
|  4 |      1 | orange        |
|  5 |      3 | red delicious |
|  6 |      3 | granny smith  |
|  7 |      3 | gala          |
+----+--------+---------------+

使用 MySQL,我试图对数据施加(自引用)外键约束,以便在更新时级联并防止删除记录(如果它有任何“子项”)。

所以我使用了以下内容:

CREATE TABLE `test`.`fruit` (
  `id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
  `parent` INT(10) UNSIGNED,
  `name` VARCHAR(45) NOT NULL,
  PRIMARY KEY (`id`),
  CONSTRAINT `fk_parent`
    FOREIGN KEY (`parent`)
    REFERENCES `fruit` (`id`)
    ON UPDATE CASCADE
    ON DELETE RESTRICT
)
ENGINE = InnoDB;

据我了解,这应该符合我的要求。(并且parent必须默认为 null 才能允许插入,对吗?)

问题是,如果我更改id记录,它不会级联:

Cannot delete or update a parent row: a foreign key constraint fails (`test`.`fruit`, CONSTRAINT `fk_parent` FOREIGN KEY (`parent`) REFERENCES `fruit` (`id`) ON UPDATE CASCADE)

我错过了什么?

如果我的术语搞砸了,请随时纠正我......我是新来的约束。

4

1 回答 1

2

偏离 SQL 标准:如果 ON UPDATE CASCADE 或 ON UPDATE SET NULL 递归更新它先前在级联期间更新的同一个表,它的行为类似于 RESTRICT。这意味着您不能使用自引用 ON UPDATE CASCADE 或 ON UPDATE SET NULL 操作。这是为了防止级联更新导致的无限循环。另一方面,自引用 ON DELETE SET NULL 是可能的,自引用 ON DELETE CASCADE 也是如此。级联操作的嵌套深度不得超过 15 层。

于 2010-06-01T20:16:29.967 回答