Oracle触发器 同一事件激活两个触发器

5.11 同一事件激活两个触发器

问题

现在需要创建一个触发器,把SYSDATE的值插入LOCATIONS表的HIRE_DATE字段。但是这个表已经有一个BEFORE INSERT触发器,而你又不希望这两个触发器产生冲突。

解决方案

使用FOLLOWS子句可以保证触发器按顺序执行。下面的例子创建了两个触发器,它们会在employees表的before insert事件发生时同时执行。
首先创建的触发器会验证雇员的工资是否处于某个范围内:

CREATE OR REPLACE TRIGGER verify_emp_salary
BEFORE INSERT ON employees
FOR EACH ROW
DECLARE
  v_min_sal jobs.min_salary%TYPE;
  v_max_sal     jobs.max_salary%TYPE;
BEGIN
  SELECT min_salary, max_salary
  INTO v_min_sal, v_max_sal
  FROM JOBS
  WHERE JOB_ID = :new.JOB_ID;

  IF :new.salary > v_max_sal THEN
    RAISE_APPLICATION_ERROR(-20901,
       'You cannot give a salary greater than the max in this category');
  ELSIF :new.salary < v_min_sal THEN
    RAISE_APPLICATION_ERROR(-20902,
       'You cannot give a salary less than the min in this category');
  END IF;
END;

/

接下来创建的触发器会强行将雇用日期修改为当前日期:

CREATE or REPLACE TRIGGER populate_hire_date
BEFORE INSERT
ON employees    
FOR EACH ROW

FOLLOWS verify_emp_salary
DECLARE
BEGIN
:new.hire_date := sysdate;
END;
/

因为记录没有插入数据库时,修改雇佣日期没有任何意义,所以你想先触发verify_emp_salary触发器。这里只需要在populate_hire_date触发器中添加一个follows子句就可以达到这个效果。

原理分析

Oracle 11g为ORACLE触发器引入了FOLLOWS子句,它用于指定触发器的执行顺序。FOLLOWS子句会指定在激活当前触发器之前,先执行哪个触发器。换句话说,如果创建触发器时指定了FOLLOWS子句,那么FOLLOWS子句的触发器就会在当前触发器执行之前先触发。因此,如果你在FOLLOWS子句中指定了一个不存在的触发器,就会收到一个编译错误。

注意 PRECEDES子句同样是Oracle 11g中引入。可以用这个子句指定与FOLLOWS子句对立的情况。如果指定PRECEDES而非FOLLOWS子句,那么当前的触发器就会优先于PRECEDES子句中指定的触发器先被触发。

默认情况下Oracle触发器的执行是无序的。过去没办法保证触发器的执行顺序。现在新引入的FOLLOWS子句可以帮助指定触发器的执行顺序。但是,一定要确保触发器之间不要互相依赖。因为这样做可能导致其中的一个触发器被丢弃。如果一个触发器依赖于另外一个触发器的成功执行,那么这个设计可以说相当糟糕,所以FOLLOWS子句只应该在没有依赖的情况下使用。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值