正在调用Oracle触发器,但没有任何反应

时间:2016-03-14 08:55:49

标签: oracle stored-procedures oracle11g exception-handling triggers

我有后插入触发器,后者又调用了一个程序。触发器和过程正确地记录到表DEVLOGS,似乎没有异常发生。

我的 TRIGGER

CREATE OR REPLACE TRIGGER MYSCHEMA.MYTRIGGER
AFTER INSERT ON MYSCHEMA.MYTABLE
REFERENCING NEW AS NEW OLD AS OLD
FOR EACH ROW
DECLARE err_msg varchar(1000);
BEGIN

-- Log start trigger
    INSERT INTO DEVLOGS (TIMESTAMP, MSG  ) values ( CURRENT_TIMESTAMP, 'Now starting TRIGGER MYTRIGGER' );

-- CALL Procedure:
    MYSCHEMA.MYPROC(
            :NEW.MNPDID, 
            NVL(:NEW.CTCAETERM,'NULL'), 
            NVL(:NEW.SO_NARRATIVE || :NEW.SO_NARRATIVE1 || :NEW.SO_NARRATIVE2,'NULL'), 
            NVL(:NEW.SO_TRUE,1),
            NVL(:NEW.ADDINFO,'NULL'), 
            NVL(:NEW.SO_REL1,0), 
            NVL(:NEW.SO_REL2,0), 
            NVL(:NEW.SO_SOC1,'NULL')
         );

-- Log end trigger
    INSERT INTO DEVLOGS (TIMESTAMP, MNPDID, MSG  ) values ( CURRENT_TIMESTAMP, :NEW.MNPDID, 'OK TRIGGER MYTRIGGER(' || 
            :NEW.MNPDID                     || ', ' || 
            NVL(:NEW.CTCAETERM,'NULL')      || ', ' ||
            NVL(:NEW.SO_NARRATIVE || :NEW.SO_NARRATIVE1 || :NEW.SO_NARRATIVE2,'NULL')   || ', ' ||
            NVL(:NEW.SO_TRUE,1)         || ', ' ||
            NVL(:NEW.ADDINFO,'NULL')      || ', ' ||
            NVL(:NEW.SO_REL1,0)         || ', ' ||
            NVL(:NEW.SO_REL2,0)         || ', ' ||
            NVL(:NEW.SO_SOC1,'NULL')      || '). Terminated, no exception' );

EXCEPTION
    WHEN OTHERS THEN
    err_msg := SUBSTR(SQLERRM, 1, 1000);
    INSERT INTO DEVLOGS (TIMESTAMP, MSG  ) values ( CURRENT_TIMESTAMP, 'ERROR IN TRIGGER MYTRIGGER:' || err_msg );
END;
/

我的程序

CREATE OR REPLACE PACKAGE BODY MYSCHEMA.MYPACKAGE AS
PROCEDURE MYPROC(
    ID DEVSAES.MNPDID%TYPE,
    CTCAETERM DEVSAES.CTCAETERM%TYPE , 
    SO_NARRATIVE DEVSAES.SO_NARRATIVE%TYPE, 
    SO_TRUE DEVSAES.TRUESAE%TYPE,
    ADDINFO DEVSAES.ADDINFO%TYPE, 
    SO_REL1 DEVSAES.SO_REL1%TYPE, 
    SO_REL2 DEVSAES.SO_REL2%TYPE, 
    SO_SOC1 DEVSAES.SO_SOC1%TYPE)
IS
err_msg varchar2(1000);
BEGIN

INSERT INTO DEVLOGS (TIMESTAMP, MSG  ) values ( current_timestamp, 'In PROCEDURE MYPROC: Now calling procedure with params: ' || ID || ', ' || CTCAETERM || ', ' || SO_NARRATIVE || ', ' || SO_TRUE || ', ' || ADDINFO || ', ' || SO_REL1 || ', ' || SO_REL2 || ', ' || SO_SOC1 );
INSERT INTO DEVSAES
SELECT
   CN.PID
  ,AE.AEDATE
  ,AE.AEID
  ,ID
...
FROM TABLE1 CN
INNER JOIN TABLE2 AE
   ON CN.CNID = AE.CNID

...
WHERE AE.MNPDID = ID;

INSERT INTO DEVLOGS (TIMESTAMP, MSG  ) values ( current_timestamp, 'In PROCEDURE MYPROC: Procedure terminated.');
EXCEPTION
    WHEN OTHERS THEN
    err_msg := SUBSTR(SQLERRM, 1, 1000);
    INSERT INTO DEVLOGS (TIMESTAMP, MSG  ) values ( current_timestamp, 'In PROCEDURE MYPROC:' || err_msg );
END;
END MYPACKAGE;
/

现在,在查看日志时,没有异常被提出:

14/03/2016 08:15:45.367522        Now startting TRIGGER MYTRIGGER
14/03/2016 08:15:45.673051              In PROCEDURE MYPROC: Now calling procedure with params: 998, Cataract, NULL, 1, NULL, 2, 4, Eye disorders
14/03/2016 08:15:46.910680              In PROCEDURE MYPROC: Procedure terminated.
14/03/2016 08:15:46.915188  998     OK TRIGGER MYTRIGGER(998, Cataract, NULL, 1, NULL, 2, 4, Eye disorders). Terminated, no exception

在程序 DEVSAES 中没有找到数据,程序实际上应该写入该程序,此外,当我手动调用程序' (即之前没有触发),然后正确插入值

更新

我现在已将程序加入触发器。进一步改进:

  • PRAGMA AUTONOMOUS TRANSACTION已添加
  • 最后添加
  • COMMIT
  • SQL%Rowcount记录到DEVLOGS中。它确实说0 rows inserted

当我调用查询的SELECT部分​​并用固定值替换:NEW变量(模拟插入的参数)时,它返回一行,正好是我想自动插入DEVSAES表的那一行。

我修改后的查询如下:

CREATE OR REPLACE TRIGGER MYSCHEMA.MYTRIGGER
AFTER INSERT
ON MYSCHEMA.MYTABLE
REFERENCING NEW AS NEW OLD AS OLD
FOR EACH ROW
DECLARE 
    err_msg varchar(1000);
    v_count integer;
PRAGMA AUTONOMOUS_TRANSACTION;
BEGIN
INSERT INTO DEVLOGS (TIMESTAMP, MSG) values ( current_timestamp,
    'In Trigger MYTRIGGER: Now calling INSERT with params: ' || :NEW.MNPDID || ', ' || :NEW.CTCAETERM );
INSERT INTO DEVSAES
SELECT
   CN.PID
  ,AE.AEDATE
  ,AE.AEID
  ,:NEW.ID
  ,:NEW.CTCAETERM

...

FROM MYSCHEMA.CASENODE CN
  INNER JOIN MYSCHEMA.ADVERSEEVENT AE
     ON CN.CNID = AE.CNID
...
WHERE D2.MNPDID = :NEW.MNPDID;
v_count := SQL%ROWCOUNT;
INSERT INTO DEVLOGS (TIMESTAMP, MSG  ) VALUES ( CURRENT_TIMESTAMP, 'Trigger MYSCHEMA.MYTRIGGER terminated. No exceptions catched. ' || v_count ||' rows inserted. Now comitting.');
COMMIT;
EXCEPTION
    WHEN OTHERS THEN
    err_msg := SUBSTR(SQLERRM, 1, 1000);
    INSERT INTO DEVLOGS (TIMESTAMP, MSG  ) VALUES ( CURRENT_TIMESTAMP, 'ERROR IN TRIGGER MYTRIGGER:' || err_msg );
END;
/

日志:

17/03/2016 14:05:51.664756              Trigger MYSCHEMA.MYTRIGGER terminated. No exceptions catched. 0 rows inserted. Now comitting.
17/03/2016 14:05:51.664153              In TRIGGER MYTRIGGER: Now calling INSERT with params: 1056, Cushingoid, , , , 2, 3, Endocrine disorders

1 个答案:

答案 0 :(得分:0)

找到解决方案:在我的程序中,缺少一个在目标表中设置 NOT NULL 的列。 我做了什么:

  • 我将这个缺失的列添加到INSERT语句
  • 然后我不得不 删除insert into DEVLOGSAUTONOMOUS TRANSACTION为 以及我在上面的UPDATE部分插入的COMMIT语句。

但是,我不知道为什么我的异常处理程序没有在过程/触发器中捕获到非NULL约束违规。

oracle对我来说仍然没有预测性......