圆形外键.我该如何处理它们?

2 .net sql sql-server foreign-keys

我的大部分sql代码都是生成的(来自POD).现在我有问题,表user_data有一个FK到ref_status,它指向两个不同的user_data.我的代码执行以下操作

  1. 开始交易
  2. 查看user_data(并将其添加到列表中)
  3. 看到ref_status然后用它重复#2
  4. 执行create table ref_status代码

然后我得到了例外

Foreign key 'FK__...__0F975522' references invalid table 'user_data'.
Run Code Online (Sandbox Code Playgroud)

如果他们使用彼此的两个作为参考,我如何创建两个表?我认为,因为它是在同一个交易中,它会起作用.我还要注意这个代码在sqlite中工作正常,启用了FK支持(自上个月发布的System.Data.SQLite以来一直支持).那么我期望如何创建这两个表呢?

Dan*_*haw 6

SQL Server中实际上不支持循环外键.如果你真的想要它可以做到,但它没有用,因为你无法插入任何数据 - 你不能插入表A,因为表B中所需的引用不存在,反之亦然.唯一的方法是创建一个没有FK的表,然后在创建第二个表后添加它.然后,要插入数据,您需要禁用其中一个FK,然后重新启用它,但如果您有大量数据,这是一个非常耗费资源的操作,因为在FK时都需要重新检查重新启用.

基本上,您要么必须使用不完整的声明性引用完整性,要么更明智地考虑重新构建您的数据,如@munisor建议的那样.

警告:以下代码说明了如何创建圆形FK,但这对您的健康非常不利!我相信从长远来看,你不会想要这样做.例如,在运行之后简单地尝试删除这些表中的任何一个是非常困难的,你不能简单DROP TABLE!

CREATE TABLE [A]
(
    [AId] int
        NOT NULL
        PRIMARY KEY,
    [BId] int
        NULL
        -- You can't create the reference to B here since it doesn't yet exist!
)

CREATE TABLE [B]
(
    [BId] int
        NOT NULL
        PRIMARY KEY,
    [AId] int
        NOT NULL
        FOREIGN KEY
            REFERENCES [A]
)

-- Now that B is created, add the FK to A
ALTER TABLE [A]
    ADD
        FOREIGN KEY ( [BId] )
        REFERENCES [B]

ALTER TABLE [A]
    ALTER COLUMN [BId]
        int
        NOT NULL
Run Code Online (Sandbox Code Playgroud)