Sqlserver标准触发器顺序



我有一个由外部CRM部分创建和编辑的数据库,其中某些表上有多个(最多2个)后触发器。这是由于1个触发器是由CRM自动生成的(我对其控制有限),另一个包含我的代码。

CRM触发器为插入的数据行生成主键。我的触发器需要访问该主键,以便将其作为外键写入另一个表。我使用

Select @id=max(id) from mytable

因为Scope_Identity没有以某种方式产生期望的结果。

这一直有效,直到我让CRM重新创建表和它自己的触发器。触发器选择的该表的最大id似乎总是actual_id-1

当我使用相同的代码更改触发器时,它总是让程序重新运行。

我的问题是:SQL server(我使用的是SQL server 2008)是否按创建时间设置其触发顺序?

以及:是否

sp_settriggerorder @triggername='mycustomtrigger', @order='Last', @stmttype='INSERT'

要永久更改这个,还是每次CRM重新创建其触发器时,我都必须再次调用该过程?(使用DROP和CREATE,而不是ALTER)

希望这个问题的答案能帮助到同样问题的人。

问候

它没有文档,但我相信LAST设置将保留在触发器中,前提是它不被修改。(相反,记录,如果修改触发器,它将丢失此设置)。然而,它似乎奏效了:

create table T (ID int not null)
go
create trigger T_T1 on T
after insert
as
    RAISERROR('T1',10,1) WITH NOWAIT
go
create trigger T_T2 on T
after insert
as
    RAISERROR('T2',10,1) WITH NOWAIT
go
create trigger T_T3 on T
after insert
as
    RAISERROR('T3',10,1) WITH NOWAIT
go
insert into T(ID) values (1)
go
sp_settriggerorder 'T_T2','Last','INSERT'
go
insert into T(ID) values (2)
go
drop trigger T_T1
go
create trigger T_T1 on T
after insert
as
    RAISERROR('T1',10,1) WITH NOWAIT
go
insert into T(ID) values (3)

结果:

T1
T2
T3
(1 row(s) affected)
T1
T3
T2
(1 row(s) affected)
T3
T1
T2
(1 row(s) affected)

然而,关于你的第一个问题:

SQL server(我使用的是SQL server 2008)是否按创建时间设置其触发顺序?

它也出现在,但我不会依赖它。sp_settriggerorder是唯一记录任何订单的地方。

最后,正如我在评论中提到的,我不会依赖您当前的Select @id=max(id) from mytable方法-它可能会因多种原因而被破坏,但最重要的是,每个方法触发一次触发器,并且可能会响应多个行而触发,因此您应该编写触发器来使用inserted伪表(并期望它包含0、1或多行)。

最新更新