如何解决多个级联路径?
How to solve multiple cascade paths?
在我的数据库中,我有一个 Person
和 Member
table。 Member
table 有 2 个外键,它们都引用 People
Table 中的同一列。约束如下所示:
CONSTRAINT [FK_Members_People_1]
FOREIGN KEY ([PersonID])
REFERENCES [People].[People]([ID])
ON DELETE CASCADE
ON UPDATE NO ACTION,
CONSTRAINT [FK_Members_People_2]
FOREIGN KEY ([EnquiryTakenBy])
REFERENCES [People].[People]([ID])
ON DELETE SET NULL
ON UPDATE NO ACTION
我得到的错误如下:
Introducing FOREIGN KEY constraint 'FK_Members_People_2' on table 'Members' may cause cycles or multiple cascade paths. Specify ON DELETE NO ACTION or ON UPDATE NO ACTION, or modify other FOREIGN KEY constraints.
我该如何解决这个问题?
基本上这是我想要获得的行为:
- 删除 PersonID 引用的记录时。我需要它来删除其他 table 中的所有 child 记录。 (有 8 child tables)
- 当EnquiryTakenBy 引用的记录被删除时。我需要将 EnquiryTakenBy 设置为 null。
编辑:Table结构如下:
CREATE TABLE [People].[People]
(
[ID] INT NOT NULL IDENTITY,
[PersonType] INT NOT NULL,
[Forename] VARCHAR(16) NOT NULL,
[Surname] VARCHAR(32) NOT NULL,
[Gender] CHAR(1) NOT NULL,
[DateOfBirth] DATE NULL,
[HobbiesAndInterests] VARCHAR(256) NULL,
[AdditionalInformation] VARCHAR(512) NULL,
[LocalCentre] INT NOT NULL DEFAULT 0,
CONSTRAINT [PK_People] PRIMARY KEY ([ID]),
CONSTRAINT [FK_People_PersonType]
FOREIGN KEY ([PersonType])
REFERENCES [Lookups].[PersonTypes]([ID])
ON DELETE CASCADE
ON UPDATE CASCADE,
CONSTRAINT [FK_People_Centres]
FOREIGN KEY ([LocalCentre])
REFERENCES [Lookups].[Centres]([ID])
ON DELETE CASCADE
ON UPDATE CASCADE
)
CREATE TABLE [People].[Members]
(
[PersonID] INT NOT NULL,
[IsActive] BIT NOT NULL DEFAULT 0,
[Issues] VARCHAR(500) NULL,
[InTreatment] BIT NOT NULL DEFAULT 0,
[ProblemSubstance] VARCHAR(64) NOT NULL,
[WantsHelpWith] VARCHAR(128) NULL,
[EnquiryTakenBy] INT NOT NULL,
[IsVolunteer] BIT NOT NULL DEFAULT 0,
CONSTRAINT [PK_Members] PRIMARY KEY ([PersonID]),
CONSTRAINT [FK_Members_People_1]
FOREIGN KEY ([PersonID])
REFERENCES [People].[People]([ID])
ON DELETE CASCADE
ON UPDATE NO ACTION,
CONSTRAINT [FK_Members_People_2]
FOREIGN KEY ([EnquiryTakenBy])
REFERENCES [People].[People]([ID])
ON DELETE SET NULL
ON UPDATE NO ACTION
)
好的,找到解决办法了。显然我的问题与 SQL 服务器不知道哪个约束优先,所以我用这个触发器替换了第二个外键约束:
CREATE TRIGGER Member_UpdateEnquiryID ON People.People
AFTER DELETE
AS
BEGIN
DECLARE @id int = (select id from deleted);
UPDATE People.Members
SET EnquiryTakenBy = NULL
where EnquiryTakenBy = @id
END
在我的数据库中,我有一个 Person
和 Member
table。 Member
table 有 2 个外键,它们都引用 People
Table 中的同一列。约束如下所示:
CONSTRAINT [FK_Members_People_1]
FOREIGN KEY ([PersonID])
REFERENCES [People].[People]([ID])
ON DELETE CASCADE
ON UPDATE NO ACTION,
CONSTRAINT [FK_Members_People_2]
FOREIGN KEY ([EnquiryTakenBy])
REFERENCES [People].[People]([ID])
ON DELETE SET NULL
ON UPDATE NO ACTION
我得到的错误如下:
Introducing FOREIGN KEY constraint 'FK_Members_People_2' on table 'Members' may cause cycles or multiple cascade paths. Specify ON DELETE NO ACTION or ON UPDATE NO ACTION, or modify other FOREIGN KEY constraints.
我该如何解决这个问题?
基本上这是我想要获得的行为:
- 删除 PersonID 引用的记录时。我需要它来删除其他 table 中的所有 child 记录。 (有 8 child tables)
- 当EnquiryTakenBy 引用的记录被删除时。我需要将 EnquiryTakenBy 设置为 null。
编辑:Table结构如下:
CREATE TABLE [People].[People]
(
[ID] INT NOT NULL IDENTITY,
[PersonType] INT NOT NULL,
[Forename] VARCHAR(16) NOT NULL,
[Surname] VARCHAR(32) NOT NULL,
[Gender] CHAR(1) NOT NULL,
[DateOfBirth] DATE NULL,
[HobbiesAndInterests] VARCHAR(256) NULL,
[AdditionalInformation] VARCHAR(512) NULL,
[LocalCentre] INT NOT NULL DEFAULT 0,
CONSTRAINT [PK_People] PRIMARY KEY ([ID]),
CONSTRAINT [FK_People_PersonType]
FOREIGN KEY ([PersonType])
REFERENCES [Lookups].[PersonTypes]([ID])
ON DELETE CASCADE
ON UPDATE CASCADE,
CONSTRAINT [FK_People_Centres]
FOREIGN KEY ([LocalCentre])
REFERENCES [Lookups].[Centres]([ID])
ON DELETE CASCADE
ON UPDATE CASCADE
)
CREATE TABLE [People].[Members]
(
[PersonID] INT NOT NULL,
[IsActive] BIT NOT NULL DEFAULT 0,
[Issues] VARCHAR(500) NULL,
[InTreatment] BIT NOT NULL DEFAULT 0,
[ProblemSubstance] VARCHAR(64) NOT NULL,
[WantsHelpWith] VARCHAR(128) NULL,
[EnquiryTakenBy] INT NOT NULL,
[IsVolunteer] BIT NOT NULL DEFAULT 0,
CONSTRAINT [PK_Members] PRIMARY KEY ([PersonID]),
CONSTRAINT [FK_Members_People_1]
FOREIGN KEY ([PersonID])
REFERENCES [People].[People]([ID])
ON DELETE CASCADE
ON UPDATE NO ACTION,
CONSTRAINT [FK_Members_People_2]
FOREIGN KEY ([EnquiryTakenBy])
REFERENCES [People].[People]([ID])
ON DELETE SET NULL
ON UPDATE NO ACTION
)
好的,找到解决办法了。显然我的问题与 SQL 服务器不知道哪个约束优先,所以我用这个触发器替换了第二个外键约束:
CREATE TRIGGER Member_UpdateEnquiryID ON People.People
AFTER DELETE
AS
BEGIN
DECLARE @id int = (select id from deleted);
UPDATE People.Members
SET EnquiryTakenBy = NULL
where EnquiryTakenBy = @id
END