SQL Server触发器 - SET变量= column.value

时间:2012-05-30 07:05:18

标签: sql sql-server-2008

我正在尝试创建一个触发器,该触发器在表component上运行,并将UPDATEDELETEINSERT操作记录到表component_history < / p>

CREATE TRIGGER component_hist
ON component
AFTER INSERT, UPDATE, DELETE
AS

DECLARE
   @tr_action varchar(8),
   @tr_id_compoment int,
   @tr_name varchar(max),
   @tr_value int

IF COLUMNS_UPDATED() <> 0 -- delete or update?
BEGIN     
  SET @tr_action = 'UPDATE'
ELSE -- delete     
BEGIN
  SET @tr_action = 'DELETE'
END

INSERT INTO component_history VALUES (@tr_id_component, @tr_name, @tr_value, @tr_action);

如何将表格id, name, value中的信息(component)发送到component_history

我试过了:

SET 
@tr_id_component = component.id,
@tr_name = component.name,
@tr_value = component.value

但它报告说:

  

Msg 4104,Level 16,State 1,Procedure component_hist,Line 22
  无法绑定多部分标识符“component.id”。

1 个答案:

答案 0 :(得分:2)

这样的事情应该足够了:

CREATE TRIGGER component_hist
ON component
AFTER INSERT, UPDATE, DELETE
AS

INSERT INTO component_history /* I'd prefer to see a column list here */
select id,name,value,CASE WHEN EXISTS(select * from deleted) THEN 'UPDATE' ELSE 'INSERT' END
from inserted
UNION ALL
select id,name,value,'DELETE'
from deleted
where not exists(select * from inserted)

优化(如果您有大量大型更新)将EXISTS (select * from deleted)评估移出SELECT(从那时起)目前每行评估一次。)

另请注意,在UPDATE情况下,我们只是存储新值,而不是旧值。


inserted and deleted pseudo-tables是特殊的 - 它们包含受导致触发器触发的语句影响的行。 inserted表包含任何新行,deleted表包含任何旧行。这导致了这样的逻辑:在insert期间,deleted将为空(没有旧行受插入影响)。在delete期间,inserted将为空(未创建新行)。在update期间,将填充两个表。

这就是select的顶部适用于insertupdate操作的原因,因为我们使用的是inserted表。但我们检查deleted中是否有任何行,以区分这两个操作。在底部selectunion all下方),我们查询deleted表 - 但我们使用where子句来阻止返回任何行,如果这实际上是{ {1}}操作。