2017-02-16 10 views
1

У меня есть следующий триггер Microsoft SQL Server для моей таблицы:Как сделать проверку IF в триггере SQL Server

-- Insert statements for trigger here 
DECLARE @AssignmentUID uniqueidentifier; 
DECLARE @ResourceUID uniqueidentifier; 
DECLARE @ResourceName nvarchar(255); 
DECLARE @ResourceClaimsAccount nvarchar(255); 
DECLARE @ProjectUID uniqueidentifier; 
DECLARE @ProjectName nvarchar(255); 
DECLARE @ProjectUrl nvarchar(1000); 
DECLARE @TaskUID uniqueidentifier; 
DECLARE @TaskName nvarchar(255); 
DECLARE @TaskUrl nvarchar(1000); 
DECLARE @UserId nvarchar(255); 
DECLARE @PWAUrl nvarchar(255); 
DECLARE @sql varchar(8000) 

SELECT @AssignmentUID = INSERTED.AssignmentUID 
FROM INSERTED; 

SELECT   
    @TaskUID = MSP_EpmAssignment_UserView.TaskUID, 
    @TaskName = MSP_EpmTask_UserView.TaskName, 
    @ProjectUID = MSP_EpmAssignment_UserView.ProjectUID, 
    @ProjectName = MSP_EpmProject_UserView.ProjectName, 
    @ProjectUrl = MSP_EpmProject_UserView.ProjectWorkspaceInternalHRef, 
    @ResourceUID = MSP_EpmAssignment_UserView.ResourceUID, 
    @ResourceClaimsAccount = MSP_EpmResource_UserView.UserClaimsAccount, 
    @ResourceName = MSP_EpmResource_UserView.ResourceName 
FROM 
    MSP_EpmAssignment_UserView 
LEFT OUTER JOIN 
    MSP_EpmResource_UserView ON MSP_EpmAssignment_UserView.ResourceUID = MSP_EpmResource_UserView.ResourceUID 
LEFT OUTER JOIN 
    MSP_EpmProject_UserView ON MSP_EpmAssignment_UserView.ProjectUID = MSP_EpmProject_UserView.ProjectUID 
LEFT OUTER JOIN 
    MSP_EpmTask_UserView ON MSP_EpmAssignment_UserView.TaskUID = MSP_EpmTask_UserView.TaskUID 
WHERE 
    (MSP_EpmAssignment_UserView.AssignmentUID = @AssignmentUID); 

INSERT INTO tablename 
(ItemTitle, ParentName, ParentUrl, Loginname, SourceId, CreatedAt) 
VALUES (@TaskName, @ProjectName, @ProjectUrl, RIGHT(@ResourceClaimsAccount, CHARINDEX('\', REVERSE('\' + @ResourceClaimsAccount)) - 1), 1, GETDATE()); 

Как я могу проверить, если @AssignmentUID И @TaskUID НЕ NULL перед выполнением INSERT INTO заявление? Есть ли потенциал для оптимизации этого триггера?

+3

У вашего триггера есть ** ОСНОВНАЯ ** ошибка в том, что вы, кажется, считаете, что она будет называться ** один раз за строку ** - это ** не ** случай. Триггер будет срабатывать ** один раз за оператор **, поэтому, если ваши инструкции 'INSERT' влияют на 25 строк, вы получите триггер, запущенный ** один раз **, но тогда' Inserted' будет содержать 25 строк. Какой из этих 25 строк будет выбран ваш код? 'SELECT @AssignmentUID = INSERTED.AssignmentUID FROM INSERTED' - он не детерминирован. Для этого нужно переписать триггер! –

+0

Это триггер INSERT. Может ли это иметь место и для триггера INSERT? – STORM

+0

*** ДА! *** Абсолютно! *** ВСЕ *** триггеры в SQL Server являются ** один раз за оператор ** и обрабатывают возможные несколько строк! (например, если вы вставляете в таблицу на основе «SELECT» из другой таблицы) –

ответ

3

Вам нужно написать триггер в набор на основе моды, чтобы справиться с тем, что Inserted таблица может содержать несколько строк.

Пробуйте этот код - он использует ваше ядро ​​SELECT и делает INNER JOIN таблице Inserted в этой колонке, которую вы пытаетесь захватить в начале. Это будет обрабатывать все строк, которые содержатся в таблице Inserted сразу - нет цикла, нет курсора - нет такого грязного кода!

INSERT INTO tablename (ItemTitle, ParentName, ParentUrl, Loginname, SourceId, CreatedAt) 
SELECT   
    MSP_EpmTask_UserView.TaskName, 
    MSP_EpmProject_UserView.ProjectName, 
    MSP_EpmProject_UserView.ProjectWorkspaceInternalHRef, 
    RIGHT(MSP_EpmResource_UserView.UserClaimsAccount, CHARINDEX('\', REVERSE('\' + MSP_EpmResource_UserView.UserClaimsAccount)) - 1, 
    1, 
    SYSDATETIME() 
FROM 
    MSP_EpmAssignment_UserView 
INNER JOIN 
    Inserted i ON MSP_EpmAssignment_UserView.AssignmentUID = i.AssignmentUID 
LEFT OUTER JOIN 
    MSP_EpmResource_UserView ON MSP_EpmAssignment_UserView.ResourceUID = MSP_EpmResource_UserView.ResourceUID 
LEFT OUTER JOIN 
    MSP_EpmProject_UserView ON MSP_EpmAssignment_UserView.ProjectUID = MSP_EpmProject_UserView.ProjectUID 
LEFT OUTER JOIN 
    MSP_EpmTask_UserView ON MSP_EpmAssignment_UserView.TaskUID = MSP_EpmTask_UserView.TaskUID 
1
IF (@AssignmentUID IS NOT NULL AND @TaskUID IS NOT NULL) 
BEGIN 
    ... 
END