しない顧客の名前がPeter
の場合に顧客を削除するトリガーを作成したい。どうやってやるの?
CREATE TRIGGER trgCUSTOMER ON customer
FOR DELETE
AS
BEGIN
IF (SELECT name FROM deleted) not like 'Peter'
BEGIN
delete from customer where name = (select name from deleted);
END
END;
次の2つのオプションがあります。
1)行「Peter」を削除する場合に備えて、DELETEをロールバックします。これはAFTERトリガーで行います。そのうちの1つが「Peter」である複数の行を削除する場合、トランザクション全体がロールバックされることに注意してください。
CREATE TRIGGER TR_CUSTOMER_DEL ON customer
FOR DELETE
AS
BEGIN
SET NOCOUNT ON;
IF EXISTS (
SELECT *
FROM deleted
WHERE name = 'Peter'
)
BEGIN
ROLLBACK;
THROW 50001, 'Cannot delete Peter', 1;
END
END;
2)INSTEAD OFトリガーを使用して、SQL ServerがテーブルでDELETEを実行する方法をオーバーライドします。この場合、「Peter」行のDELETEは暗黙的に無視されます。
CREATE TRIGGER TR_CUSTOMER_IO_DEL ON customer
INSTEAD OF DELETE
AS
BEGIN
SET NOCOUNT ON;
DELETE c
FROM customer AS c
INNER JOIN deleted AS d
ON c.customer_id = d.customer_id
WHERE d.name <> 'Peter';
END;
どちらが最適かは、ビジネスロジックによって大きく異なります。
そのトリガーは機能しました。
CREATE TRIGGER trgCustomer ON customer
INSTEAD OF DELETE
AS
BEGIN
SET NOCOUNT ON
DELETE
FROM customer
WHERE customer.ID IN (Select ID from deleted where name != 'Peter')
END;
レコードを削除しない(監査目的で、OPの投稿に従って)が、削除されたレコードにフラグを付け、これを反映するようにビューを変更するには、次のようにします。
上記のようにトリガーを作成しますが、UPDATEステートメントに変更します...
USE [yourdatabase];
GO
SET ANSI_NULLS ON;
GO
SET QUOTED_IDENTIFIER ON;
GO
CREATE TRIGGER declencheur_suppression
ON synt_examen
INSTEAD OF DELETE
AS
UPDATE t
SET t.Status = 0
FROM Etudiant AS t
INNER JOIN deleted d ON t.ID = d.ID
GO
もちろん、「Status
」という別の列を追加して、ACTIVE(または削除されていない)の場合はデフォルトで1にする必要があります。 0の場合、削除されたことを意味します。
これを反映するには、WHERE Etudiant = 1
などのWHERE
句を使用するようにビューを変更します。
レコードを物理的に削除するは、DBAの慣習として可能な限り回避する必要があるため、この方法を使用します。