ROLLBACK сделать данные в таблице INSERTED удалены в ПОСЛЕ INSERT TRIGGER - PullRequest
0 голосов
/ 10 апреля 2020

Я привожу пример, чтобы показать мою проблему. Я создал таблицу следующим образом:

CREATE TABLE a
(
    id INT
)

Затем я создал триггер AFTER INSERT, чтобы запретить вставку id = 1 в таблицу a:

CREATE TRIGGER [dbo].[insert_a]
ON [dbo].[a] AFTER INSERT 
AS
BEGIN
    DECLARE @id INT
    SELECT @id = id FROM inserted

    IF @id = 1
    BEGIN
        RAISERROR('1', 12, 1)
        ROLLBACK;
    END

    SELECT * FROM inserted
END

Затем я вставляю id = 1 в таблицу a:

INSERT INTO a VALUES(1)

Я ничего не получаю из таблицы INSERTED.

Я понимаю, что когда я выполняю ROLLBACK, то + данные в таблице a откатываются (Я знаю) и данные в INSERTED таблице тоже удаляются. Почему это так?

Если я изменю триггер AFTER INSERT на триггер INSTEAD OF INSERT:

ALTER TRIGGER [dbo].[insert_a]
ON [dbo].[a] INSTEAD OF INSERT 
AS
BEGIN
    DECLARE @id INT
    SELECT @id = id FROM inserted

    IF @id = 1
    BEGIN
        RAISERROR('1', 12, 1)
        ROLLBACK
    END

    SELECT * FROM inserted
END

INSERT INTO a VALUES(1)

Тогда я получу результат:

id
1

То означает, что данные в таблице INSERTED не удалены, хотя они были выполнены в режиме ROLLBACK.

Помогите мне глубоко объяснить, что происходит внутри триггера?

1 Ответ

0 голосов
/ 10 апреля 2020

Насколько я знаю, это предполагаемое поведение. Просто AFTER может вводить в заблуждение в зависимости от того, как вы на это смотрите.

"Триггер и оператор, который его запускает, обрабатываются как одна транзакция, которую можно откатить изнутри триггера. Если обнаружена серьезная ошибка, вся транзакция автоматически откатывается. ".

https://msdn.microsoft.com/en-us/library/ms178110.aspx

...