You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

查询n秒内重复InspectionNotes及处理外键约束删除问题

解决删除重复InspectionNotes记录时的外键约束问题

嘿,这个外键约束的问题我之前也碰到过,刚好能给你几个实用的解决方案,你可以根据自己的业务场景来选:

方案一:先把关联记录指向保留的主记录,再删除重复项

如果那些关联的InspectionHoldDurations记录应该属于你要保留的那条InspectionNote(比如最早创建的那条),可以先更新关联表的引用,再删除重复的主表记录:

第一步:更新关联表,转移引用

WITH DuplicateNotes AS (
    SELECT 
        InspectionNoteID,
        -- 获取同组内要保留的记录ID(这里按创建时间最早的保留,你可以调整ORDER BY逻辑)
        FIRST_VALUE(InspectionNoteID) OVER (
            PARTITION BY InspectionID, Notes, UserRoleID  -- 这里是你判断重复的字段,按需调整
            ORDER BY CreateDate ASC
        ) AS KeepNoteID,
        ROW_NUMBER() OVER (
            PARTITION BY InspectionID, Notes, UserRoleID 
            ORDER BY CreateDate ASC
        ) AS rn
    FROM InspectionNotes
    WHERE CreateDate >= DATEADD(SECOND, -n, GETDATE()) -- 替换成你的n秒范围
)
UPDATE ihd
SET ihd.PutOnHoldNoteID = dn.KeepNoteID
FROM InspectionHoldDurations ihd
JOIN DuplicateNotes dn ON ihd.PutOnHoldNoteID = dn.InspectionNoteID
WHERE dn.rn > 1;

第二步:删除主表的重复记录

WITH DuplicateNotes AS (
    SELECT 
        InspectionNoteID,
        ROW_NUMBER() OVER (
            PARTITION BY InspectionID, Notes, UserRoleID 
            ORDER BY CreateDate ASC
        ) AS rn
    FROM InspectionNotes
    WHERE CreateDate >= DATEADD(SECOND, -n, GETDATE())
)
DELETE FROM DuplicateNotes WHERE rn > 1;

方案二:修改外键为级联删除(谨慎使用)

如果业务逻辑允许删除InspectionNotes记录时自动删除关联的InspectionHoldDurations记录,可以修改外键约束添加级联删除:

先查看当前外键约束名称

SELECT name 
FROM sys.foreign_keys 
WHERE referenced_object_id = OBJECT_ID('InspectionNotes')
AND parent_object_id = OBJECT_ID('InspectionHoldDurations');

删除原外键并重新创建(替换成你的外键名称)

-- 删除原外键
ALTER TABLE InspectionHoldDurations
DROP CONSTRAINT [FK_你的外键名称];

-- 重新创建带级联删除的外键
ALTER TABLE InspectionHoldDurations
ADD CONSTRAINT [FK_你的外键名称]
FOREIGN KEY (PutOnHoldNoteID)
REFERENCES InspectionNotes(InspectionNoteID)
ON DELETE CASCADE;

之后你再删除重复的InspectionNotes记录时,关联的InspectionHoldDurations记录会被自动删除。⚠️ 注意:这个操作会永久删除关联数据,一定要确认业务允许再执行!

方案三:先删除关联表的冗余记录,再删主表

如果那些关联的InspectionHoldDurations记录本身也是冗余的,不需要保留,可以先删关联表的对应行,再删主表重复项:

WITH DuplicateNotes AS (
    SELECT 
        InspectionNoteID,
        ROW_NUMBER() OVER (
            PARTITION BY InspectionID, Notes, UserRoleID 
            ORDER BY CreateDate ASC
        ) AS rn
    FROM InspectionNotes
    WHERE CreateDate >= DATEADD(SECOND, -n, GETDATE())
)
-- 先删除关联表中引用重复记录的行
DELETE ihd
FROM InspectionHoldDurations ihd
JOIN DuplicateNotes dn ON ihd.PutOnHoldNoteID = dn.InspectionNoteID
WHERE dn.rn > 1;

-- 再删除主表的重复记录
DELETE FROM DuplicateNotes WHERE rn > 1;

重要提醒

  • 操作前一定要备份数据,或者在测试环境先验证所有逻辑!
  • 确认你判断重复的规则(PARTITION BY的字段、n秒的范围)完全符合业务需求,避免误删正确的记录。

内容的提问来源于stack exchange,提问作者nerdperson

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 03:29:12