1

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

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)

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

问候

4

1 回答 1

2

它没有记录,但我相信该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 或多行)。

于 2012-09-07T08:36:28.217 回答