在SQL Server 2005中,有没有办法让触发器找出哪个对象负责触发触发器?我想用它来禁用一个存储的prodecure的触发器.
有没有其他方法只为当前事务禁用触发器?我可以使用以下代码,但如果我没有弄错,它也会影响并发事务 - 这将是一件坏事.
DISABLE TRIGGER { [ schema_name . ] trigger_name [ ,...n ] | ALL } ON { object_name | DATABASE | ALL SERVER } [ ; ] ENABLE TRIGGER { [ schema_name . ] trigger_name [ ,...n ] | ALL } ON { object_name | DATABASE | ALL SERVER } [ ; ]
如果可能的话,我想避免在我的表中使用"NoTrigger"字段并执行a的技术NoTrigger = null
,因为我希望保持表尽可能小.
我想避免触发器的原因是因为它包含对表的手动更新很重要的逻辑,但我的存储过程将处理这个逻辑.因为这将是一个高度使用的程序,我希望它快.
触发器会在服务器上产生额外的开销,因为它们会启动隐式事务.一旦执行了触发器,就会启动一个新的隐式事务,并且事务中的任何数据检索都将保留受影响表的锁定.
来自:http://searchsqlserver.techtarget.com/tip/1,289483,sid87_gci1170220,00.html#trigger
我刚刚看到这篇文章最近在SQL Server Central新闻简报中突出显示,它似乎提供了一种方法,您可以使用连接上的Context_Info找到有用的方法:
http://www.mssqltips.com/tip.asp?tip=1591
由Terrapin编辑:
以上链接包括以下代码:
USE AdventureWorks; GO -- creating the table in AdventureWorks database IF OBJECT_ID('dbo.Table1') IS NOT NULL DROP TABLE dbo.Table1 GO CREATE TABLE dbo.Table1(ID INT) GO -- Creating a trigger CREATE TRIGGER TR_Test ON dbo.Table1 FOR INSERT,UPDATE,DELETE AS DECLARE @Cinfo VARBINARY(128) SELECT @Cinfo = Context_Info() IF @Cinfo = 0x55555 RETURN PRINT 'Trigger Executed' -- Actual code goes here -- For simplicity, I did not include any code GO
如果要阻止执行触发器,可以执行以下操作:
SET Context_Info 0x55555 INSERT dbo.Table1 VALUES(100)
如果您的触发器在应用程序中导致性能问题,那么最好的方法是删除对表的所有手动更新,并要求所有更新都通过包含正确更新逻辑的插入/更新存储过程.然后你可以完全移除扳机.
如果没有别的办法,我建议拒绝表更新权限.
这也解决了重复代码的问题.在更新SP和触发器中复制代码违反了良好的软件工程原则,这将是一个维护问题.