行级触发器中的变异表错误

时间:2015-03-11 11:11:57

标签: plsql plsqldeveloper

将数据库触发器写入

  1. 在表格
  2. 下午6点至10点之间停止交易
  3. 如果记录超过10
  4. ,请提供相应的消息
  5. 从周一至周六删除超过2个月的数据,日期不应该是该月的第1天。 (即离开星期日和月份数据的第一个月大于2个月)
  6. 我试过这段代码,

    CREATE OR REPLACE TRIGGER EMP_INFO_BFT BEFORE
      INSERT OR DELETE OR UPDATE ON EMP_INFO
      FOR EACH ROW 
      DECLARE l_TIME NUMBER(10);
      l_RECORD NUMBER;
      BEGIN
       l_TIME:=TO_CHAR(SYSDATE,'HH24');
        IF l_TIME NOT BETWEEN 18 AND 10 THEN
        RAISE_APPLICATION_ERROR(-20003,'TIME ALREADY OVER.....TRANSACTION NOT ALLOWED NOW');
       END IF;
        DELETE
        FROM EMP_INFO
        WHERE TRUNC (HIRE_DATE )                < ADD_MONTHS (TRUNC (SYSDATE), -2)
        AND TO_CHAR (TRUNC (HIRE_DATE ), 'DY') != 'SUN'
        AND TO_CHAR (TRUNC (HIRE_DATE ), 'DD') != '01';
        SELECT COUNT(*) INTO l_RECORD FROM EMP_INFO;
        IF l_RECORD>=10 THEN
          RAISE_APPLICATION_ERROR(-20005,'10 RECORD ALLOWED IN EMP_INFO TABLE');
        END IF;
      END;
    

    插入时出现变异错误。

2 个答案:

答案 0 :(得分:0)

变异错误

Check this link基本上说:

&#34;如果触发器确实导致变异表错误,唯一真正的选择是将触发器重写为语句级触发器。

变异表错误仅影响行级触发器。&#34;

您的代码没有引用:NEW:OLD,因此将其更改为语句级别触发器应该很简单,只需删除FOR EACH ROW

<强> PS

我认为你的BETWEEN不会起作用。

更改

IF l_TIME NOT BETWEEN 18 AND 10 THEN

IF l_TIME BETWEEN 10 AND 18 THEN
    NULL;
ELSE

会解决它。

答案 1 :(得分:0)

将此触发器设为自动触发器,请检查以下代码:

CREATE OR REPLACE TRIGGER EMP_INFO_BFT BEFORE
  INSERT OR DELETE OR UPDATE ON EMP_INFO
  FOR EACH ROW 
  DECLARE l_TIME NUMBER(10);
  l_RECORD NUMBER;
pragma autonomous_transaction;
  BEGIN
   l_TIME:=TO_CHAR(SYSDATE,'HH24');
    IF l_TIME NOT BETWEEN 18 AND 10 THEN
    RAISE_APPLICATION_ERROR(-20003,'TIME ALREADY OVER.....TRANSACTION NOT ALLOWED NOW');
   END IF;
    DELETE
    FROM EMP_INFO
    WHERE TRUNC (HIRE_DATE )                < ADD_MONTHS (TRUNC (SYSDATE), -2)
    AND TO_CHAR (TRUNC (HIRE_DATE ), 'DY') != 'SUN'
    AND TO_CHAR (TRUNC (HIRE_DATE ), 'DD') != '01';
    commit;
    SELECT COUNT(*) INTO l_RECORD FROM EMP_INFO;
    IF l_RECORD>=10 THEN
      RAISE_APPLICATION_ERROR(-20005,'10 RECORD ALLOWED IN EMP_INFO TABLE');
    END IF;
  END;