递归触发器 - 一个触发器释放另一个触发器(更新语句)

时间:2014-03-14 23:13:58

标签: triggers sql-update firebird

我在我的小型(2表数据库)中创建了5个触发器。

我添加了最后一个(在INVOICE.SYMBOL更新后更改INVPOS.INVSYMBOL)这些触发器相互激活,我得到了一个

 Too many concurrent executions of the same request.

错误。

你能看看我创造的触发器并帮助我吗?

将来我可以做些什么来避免这些问题?我应该将几个触发器合并为一个吗?

2 个答案:

答案 0 :(得分:2)

你应该避免触发器之间的循环引用。

通常,触发器不适用于复杂的业务逻辑,它们适用于简单的“if-then”业务规则。

对于您描述的情况,您最好实现一个存储过程,您可以为所有表准备数据(执行数据检查,计算必要的值等),然后插入它们。它将导致简单,快速且易于维护的代码。

另外,使用CHECK“阻止0插入AMOUNTPRICENET”,并使用“计算NETVAL”等任务的计算字段。

答案 1 :(得分:1)

一个解决方案可能是检查intresting字段是否已更改,并且仅在真正有效(数据已更改)时才运行触发器操作,即

CREATE TRIGGER Foo FOR T
AS
BEGIN
  -- only execute update statement when the Fld changed
  if(new.Fld is distinct from old.Fld)then begin
     update ...
  end
END

另一种选择可能是检查触发器是否已在此交易中完成了它,即

CREATE TRIGGER Foo FOR T
AS
DECLARE trgrDone VARCHAR(255);
BEGIN
  trgrDone = RDB$GET_CONTEXT('USER_TRANSACTION', 'Foo');
  IF(trgrDone IS NULL)THEN BEGIN
     -- trigger hasn't been executed yet
     -- register the execution
     rdb$set_context('USER_TRANSACTION', 'Foo', 1);
     -- do the work which might cause reentry
     update ...
  END
END