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

创建CHECK约束要求INKOOPBEDRAG大于PRIJS_PER_D时报错如何解决

问题原因

标准SQL规定,CHECK约束仅可引用当前表的字段,无法直接查询引用其他关联表的字段,这是你编写的约束执行报错的根本原因。

解决实现方案

下面提供两种主流的跨表字段校验实现方式:

  • 方案1:触发器实现(兼容性最高,全主流数据库支持)
    在INKOOPOVEREENKOMST表的INSERT、UPDATE事件上创建触发器,每次数据写入/更新时关联ARTIKEL表做字段校验,不符合规则则拦截操作。
    以SQL Server为例,示例代码如下:
CREATE TRIGGER TRG_Check_Inkoopbedrag
ON INKOOPOVEREENKOMST
FOR INSERT, UPDATE
AS
BEGIN
    SET NOCOUNT ON;
    -- 校验是否存在不符合规则的数据
    IF EXISTS (
        SELECT 1 
        FROM inserted i
        INNER JOIN ARTIKEL a 
            ON i.BARCODE = a.BARCODE
        WHERE i.INKOOPBEDRAG <= a.PRIJS_PER_D
    )
    BEGIN
        RAISERROR('INKOOPBEDRAG字段值必须大于对应商品的PRIJS_PER_D值', 16, 1);
        ROLLBACK TRANSACTION;
    END
END
  • 方案2:用户定义函数+CHECK约束(部分数据库支持,如SQL Server)
    先创建自定义函数根据BARCODE查询对应ARTIKEL表的PRIJS_PER_D值,再在CHECK约束中调用该函数完成校验。该方案语法更简洁,但仅支持兼容UDF在CHECK中调用的数据库,且性能低于触发器方案。
    示例代码如下:
-- 自定义查询PRIJS_PER_D的函数
CREATE FUNCTION dbo.Func_Get_Prijs_Per_D(@InputBarcode VARCHAR(100))
RETURNS DECIMAL(12,2)
AS
BEGIN
    DECLARE @ResultPrijs DECIMAL(12,2);
    SELECT @ResultPrijs = PRIJS_PER_D 
    FROM ARTIKEL 
    WHERE BARCODE = @InputBarcode;
    RETURN @ResultPrijs;
END
GO

-- 创建CHECK约束
ALTER TABLE INKOOPOVEREENKOMST
ADD CONSTRAINT CK_inkoopbedraghogerdprijs
CHECK (INKOOPBEDRAG > dbo.Func_Get_Prijs_Per_D(BARCODE));

补充说明:上述两种方案默认仅在INKOOPOVEREENKOMST表数据变更时做校验,如果你需要在ARTIKEL表的PRIJS_PER_D字段修改时也校验历史关联数据是否符合规则,需要额外在ARTIKEL表的UPDATE事件上增加对应触发器。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.23 17:06:02