我正在尝试构造一个INSTEAD OF UPDATE
触发器,以在执行插入操作之前修改要插入的列之一。如果表的PK在更新期间未更改,则工作正常。
如果表的PK已更新,我不知道如何编写更新语句来更新适当的行。我怎么知道要更新哪些行。
CREATE Table MyTest(ID int NOT NULL PRIMARY KEY,
Name NVARCHAR(40) NOT NULL);
GO
INSERT INTO MyTest VALUES(1,'Joe');
INSERT INTO MyTest VALUES(2,'Scott');
INSERT INTO MyTest VALUES(3,'Dan');
INSERT INTO MyTest VALUES(4,'Becky');
GO
CREATE TRIGGER Update_Please
ON MyTest
INSTEAD OF UPDATE
AS
BEGIN
SET NOCOUNT ON
IF EXISTS (SELECT id
FROM INSERTED
EXCEPT
SELECT id
FROM DELETED)
RAISERROR ('now what?',-1,-1);
/* ======================================================
oh heck! The PK in one or more rows was updated
in the update statement. How do I construct
an update statement w/o joining to inserted on the PK?
====================================================== */
ELSE
BEGIN
-- ALTER A COLUMN
UPDATE M
SET name = CASE WHEN I.NAME = 'Mike' THEN 'The Dude' ELSE I.NAME END
FROM MyTest M
JOIN INSERTED I ON I.id = M.id;
END
END
GO
UPDATE MyTest SET Name = 'Mike' WHERE id > 2; --works great!
UPDATE MyTest SET ID = 9 WHERE Name = 'Joe'; --how do I complete the update?
答案 0 :(得分:2)
正如我在评论中所写,我认为您无法在instead of update
触发器中完成此操作,但是使用for update
做到这一点非常容易。原因是两个触发器之间的差异-在更新基础表之前,在{em> 之前触发了instead of update
触发器,而在之后,触发了for update
触发器。 >那个。这意味着inserted
表中的任何值都与实际表中的值相同-因此只需将触发器从instead of update
更改为for update
:
CREATE TRIGGER Update_Please
ON MyTest
FOR UPDATE
AS
BEGIN
SET NOCOUNT ON
UPDATE M
SET name = CASE WHEN I.NAME = 'Mike' THEN 'The Dude' ELSE I.NAME END
FROM MyTest M
JOIN INSERTED I ON I.id = M.id;
END
GO