1

我想问一下为什么(try catch)不能正确工作,因为人 2 触发器的错误何时出现问题。不要问餐桌人和餐桌人2之间的区别,这只是说明问题的例子。

CREATE TRIGGER Example
ON Person
after INSERT
AS

BEGIN TRY
    INSERT INTO [Person2]
    SELECT 
        inserted.Name,
        inserted.Surname,
        inserted.Age,
        inserted.Street
    FROM   inserted
END TRY
BEGIN CATCH
END CATCH

如果触发器延迟,则插入工作正常

INSERT INTO Person
Values
('Jhon', 'Kowalsky', '12', null)

错误

(0 行受影响)

消息 3616,级别 16,状态 1,第 1 行触发器执行期间引发错误。批处理已中止,并且用户事务(如果有)已回滚。

table Person - 在这里您可以看到 person 和 person 2 Street 之间的一个区别允许空值

在此处输入图像描述

表 Person 2 - 在这里您可以看到 person 和 person 2 Street 之间的一个区别不允许空值

在此处输入图像描述

4

1 回答 1

1

试试这个——

CREATE TRIGGER dbo.Example 

    ON dbo.Person
    AFTER INSERT

AS 
BEGIN
    SET NOCOUNT ON
    SET XACT_ABORT ON

    DECLARE @OwnTran BIT

    SET @OwnTran = 0

    IF @@TRANCOUNT = 0 
        BEGIN 
            SET @OwnTran = 1
            BEGIN TRAN
        END

    BEGIN TRY

        INSERT INTO dbo.Person2 (Name, Surname, Age, Street)
        SELECT  
              i.Name 
            , i.Surname 
            , i.Age 
            , i.Street
        FROM INSERTED i

    END TRY
    BEGIN CATCH

        DECLARE @em NVARCHAR(MAX), @sev INT, @st INT

        SELECT  @em = ERROR_MESSAGE(),
                @sev = ERROR_SEVERITY(),
                @st = ERROR_STATE()

        RAISERROR(@em, @sev, @st)

        IF @@TRANCOUNT > 0 
            ROLLBACK TRAN

    END CATCH

    IF @OwnTran = 1 AND @@TRANCOUNT > 0 
    BEGIN
        COMMIT TRAN
    END

END
于 2013-06-03T07:57:09.517 回答