将Update触发后添加到数据库中的所有表

时间:2013-11-20 13:33:27

标签: sql-server-2008 triggers

我目前正在使用此脚本向数据库中的所有表添加触发器:

exec sp_MSForEachTable 'CREATE TRIGGER [?_Update] ON ? FOR UPDATE AS 
BEGIN SET NOCOUNT ON update ? set ModifiedOn = GETDATE() END'

我需要更改触发器,以便它只更新已更改的行,因此它需要如下所示:

exec sp_MSForEachTable 'CREATE TRIGGER [?_Update] ON ? FOR UPDATE AS 
BEGIN SET NOCOUNT ON update ? set ModifiedOn = GETDATE() 
from ? updatedTable inner join inserted i 
on i.[the tables primary key] = updatedTable.[the tables primary key]
END'

但是我不知道如何获得[表格主键]值。第一个脚本创建的触发器如下所示:

update [dim].[company] set ModifiedOn = GETDATE()

并假设我可以使第二个脚本工作,它将创建此触发器:

update [dim].[company] set ModifiedOn = GETDATE() 
from [Dim].[Company] updatedTable
inner join inserted i on i.CompanyKey = updatedTable.CompanyKey

是否有人知道如何执行此操作,或者是否有可能将所需触发器添加到数据库中的所有表的替代方法?

最终目标是知道记录何时被更改,最好是人类可读或可以转换为人类可读的内容。我不知道更新的时间和地点,因此使用sprocs进行更新。

1 个答案:

答案 0 :(得分:0)

如果所有主要密钥都是标识列,那么您可以欺骗并使用IDENTITYCOL“列”名称:

create table T (ID int IDENTITY(1,1) not null primary key,Col1 varchar(10) not null,Changed datetime null)
go

create trigger T_T
on T
after insert,update
as
    update t set Changed = GETDATE()
    from inserted i
        inner join
        T t on i.IDENTITYCOL = t.IDENTITYCOL

IDENTITYCOL实际上是该表中标识列的任何列的自动别名。


实际上,$ identity可能是首选:

update t set Changed = GETDATE()
from inserted i
    inner join
    T t on i.$identity = t.$identity

IDENTITYCOL似乎是deprecated。并不是说我实际上可以找到其中任何一个的实际文档页面。