sql-server - SQL Server 引入 FOREIGN KEY 约束可能导致循环或多个级联路径
问题描述
我有两张桌子:T_User and T_Order
T_User
--------
ID
Name
T_Order
必须要外键T_User
T_Order
--------
ID
FK_UserActionOwnerID
FK_UserActionReceiverID
然后我在我的图表上建立了两个关系,从T_User ID
两个 FK 到T_Order
. 我还将这两种关系设置为delete and update rules
,cascade
因为我想如果T_User
记录将被删除,因此记录T_Order
应该被删除,或者如果T_User
ID
会改变然后也更新它T_Order.
但是我得到以下错误:
'T_User' 表已成功保存 'T_Order' 表 - 无法创建关系 'FK_T_Order_T_Users1'。在表“T_Order”上引入 FOREIGN KEY 约束“FK_T_Order_T_Users1”可能会导致循环或多个级联路径。指定 ON DELETE NO ACTION 或 ON UPDATE NO ACTION,或修改其他 FOREIGN KEY 约束。无法创建约束或索引。请参阅以前的错误。
实物图: 点这里
解决方案
外键约束可能导致循环或多个级联路径?@Martin-Brown 链接的问题建议使用触发器而不是级联外键。这是一个使用INSTEAD OF DELETE
触发器来做(我认为)你想做的事情的例子。
-- Create tables
create table dbo.T_User (
ID int identity not null primary key,
Name varchar(100) not null
)
create table dbo.T_Order (
ID int identity not null primary key,
FK_UserActionOwnerID int not null,
FK_UserActionReceiverID int not null
)
go
-- Create foreign keys
alter table dbo.T_Order add constraint FK_T_Order_T_Users1 FOREIGN KEY (FK_UserActionOwnerID) REFERENCES dbo.T_User (ID)
alter table dbo.T_Order add constraint FK_T_Order_T_Users2 FOREIGN KEY (FK_UserActionReceiverID) REFERENCES dbo.T_User (ID)
go
-- Create trigger
create trigger tr_T_User_Delete on dbo.T_User instead of delete as
begin
if (@@rowcount = 0) return
delete o from dbo.T_Order o inner join deleted d on d.ID = o.FK_UserActionOwnerID
delete o from dbo.T_Order o inner join deleted d on d.ID = o.FK_UserActionReceiverID
delete u from dbo.T_User u inner join deleted d on d.ID = u.ID
end
go
-- Demo
insert dbo.T_User (Name) values ('Peter'), ('Paul') -- Assume identity ID 1 and 2
insert dbo.T_Order (FK_UserActionOwnerID, FK_UserActionReceiverID) values (1, 1), (1, 2), (2, 2)
select * from dbo.T_Order
delete from dbo.T_User where ID = 1
select * from dbo.T_Order
您可以INSTEAD OF UPDATE
以相同的方式使用触发器,但您可能想考虑更新 ID 是否有意义 - 我通常不会想到这一点。
推荐阅读
- ruby-on-rails - 自定义表单的 POST 路由问题
- nginx - 为什么我从 Nginx 收到只读文件系统错误?
- r - lapply() 的各种转换 - R
- json - 无法从 Swish QR 代码 API 理解此 JSON 模式
- javascript - 无法读取上下文提供程序中的 useReducer 挂钩更新的状态
- node.js - 我如何使用 nodejs (puppeteer) 监控网络活动
- r - 如何从 R 中的 sqldf 输出中获取列的总和?
- javascript - Angular - 如何使用 InnerHtml 执行存储在字符串中的脚本
- vue.js - 如何使用多个选择按钮过滤 Vue.js 中的数组?
- c++ - 将函数 SetKeys 添加到 MFRC522 库