2013-08-07 4 views
0

저는 이것을 조금 보았습니다. 삽입이 발생한 후 커밋이 시작되기 전에 트리거를 실행할 수있는 방법을 찾을 수 없습니다. 삽입 된 정보에 문제가있는 경우 역할을 다시 수행 할 수있는 기능이 필요하므로 삽입 된 정보를 확인하여 삽입이 완료된 후에 필요합니다.SQL Server : 게시 삽입 사전 커밋 트리거

이와 동일한 기능을 재생할 수있는 방법이 있습니까?

답변

1

트리거는 커밋이 시작되기 전에 활성화됩니다.

CREATE TABLE dbo.Product(
    Id INT NOT NULL PRIMARY KEY, 
    Name NVARCHAR(100) NOT NULL, 
    UnitPrice NUMERIC(9,2) NOT NULL -- CHECK (UnitPrice > 0) 
); 
GO 
CREATE TRIGGER trgIU_Product_VerifyUnitPrice 
ON dbo.Product 
AFTER INSERT, UPDATE 
AS 
BEGIN 
    IF UPDATE(UnitPrice) 
    BEGIN 
     -- For simple checks you could use CHECK constraints 
     -- inserted and deleted are virtual tables store the new and the old rows (values) 
     IF EXISTS(SELECT * FROM inserted WHERE UnitPrice <= 0) 
     BEGIN 
      ROLLBACK; -- It "cancels" current transaction 
      RAISERROR('Wrong UnitPrice.',16,1); -- It notifies the caller that there is an error 
     END 
    END 
END; 
GO 

SET NOCOUNT ON; 
PRINT 'Test #1'; 
INSERT INTO dbo.Product (Id,Name,UnitPrice) 
SELECT 1 , 'PCs  ', 1200; 

PRINT 'Test #2'; 
INSERT INTO dbo.Product (Id,Name,UnitPrice) 
SELECT 2 , 'MACs  ', 2200; 

PRINT 'Test #3'; 
INSERT INTO dbo.Product (Id,Name,UnitPrice) 
SELECT 3 , 'Keyboard ', 0; 

PRINT 'Test #4'; 
INSERT INTO dbo.Product (Id,Name,UnitPrice) 
SELECT 4 , 'AAA', 111 
UNION ALL 
SELECT 5 , 'BBB', 0; 
GO 

PRINT 'Test #5'; 
BEGIN TRANSACTION; 
INSERT INTO dbo.Product (Id,Name,UnitPrice) 
SELECT 6 , 'CCC', 222 
UNION ALL 
SELECT 7 , 'DDD', 0; 
COMMIT TRANSACTION; 
GO 
SELECT @@TRANCOUNT AS [Active transactions count]; 
GO 

PRINT 'Test #6'; 
SELECT * FROM dbo.Product; 

결과 :

/* 
Test #1 

Test #2 

Test #3 
Msg 50000, Level 16, State 1, Procedure trgIU_Product_VerifyUnitPrice, Line 11 
Wrong UnitPrice. 
Msg 3609, Level 16, State 1, Line 11 
The transaction ended in the trigger. The batch has been aborted. 

Test #4 
Msg 50000, Level 16, State 1, Procedure trgIU_Product_VerifyUnitPrice, Line 11 
Wrong UnitPrice. 
Msg 3609, Level 16, State 1, Line 2 
The transaction ended in the trigger. The batch has been aborted. 

Test #5 
Msg 50000, Level 16, State 1, Procedure trgIU_Product_VerifyUnitPrice, Line 11 
Wrong UnitPrice. 
Msg 3609, Level 16, State 1, Line 3 
The transaction ended in the trigger. The batch has been aborted. 
Active transactions count 
------------------------- 
0 

Test #6 
Id Name UnitPrice 
-- ---- --------- 
1 PCs 1200.00 
2 MACs 2200.00 
*/ 

참고 : http://technet.microsoft.com/en-us/library/ms189799.aspx

일부 검사가 실패 할 경우 트리거 내에서 당신은 ROLLBACK을 사용할 수 있습니다
1

documentation의 AFTER TRIGGER에 대한 설명을 확인하십시오.

AFTER는 트리거링 SQL 문에 지정된 모든 작업 이 성공적으로 실행 된 경우에만 DML 트리거가 시작되도록 지정합니다.

AFTER 트리거는 쉽게 작성할 수 있지만 트랜잭션을 커밋하기 직전의 상황을 제어하는 ​​데는 사용할 수 없습니다. 다음과 같은 경우까지 열려있는 명시적인 거래가있을 수 있습니다. '수동으로'롤백되거나 커밋되었습니다.