ORA-06519的根本原因

时间:2018-11-23 18:14:36

标签: oracle plsql error-handling transactions

Fehler beim Start in Zeile : 1 in Befehl -
DECLARE 
  retval NUMBER;
BEGIN
    MONITORING.PERFORM_CHECK(1000705, retval);
END;
Fehlerbericht -
ORA-06519: Aktive lokale Transaktion erkannt und Rollback durchgeführt
ORA-06512: in "RR_MONITORING.MONITORING_ACTIVITY_LOG", Zeile 13
ORA-06512: in "RR_MONITORING.MONITORING", Zeile 43
ORA-06502: PL/SQL: numerischer oder Wertefehler: character string buffer too small
ORA-06512: in "RR_MONITORING.MONITORING_ACTIVITY_LOG", Zeile 10
ORA-06512: in "RR_MONITORING.MONITORING", Zeile 259
ORA-06519: Aktive lokale Transaktion erkannt und Rollback durchgeführt
ORA-06512: in "RR_MONITORING.MONITORING_ACTIVITY_LOG", Zeile 13
ORA-06512: in "RR_MONITORING.MONITORING", Zeile 1129
ORA-01422: Exakter Abruf gibt mehr als die angeforderte Zeilenzahl zurück
ORA-06512: in Zeile 4
06519. 00000 -  "active autonomous transaction detected and rolled back"
*Cause:    Before returning from an autonomous PL/SQL block, all autonomous
           transactions started within the block must be completed (either
           committed or rolled back). If not, the active autonomous
           transaction is implicitly rolled back and this error is raised.
*Action:   Ensure that before returning from an autonomous PL/SQL block,
           any active autonomous transactions are explicitly committed
           or rolled back.

哪些错误消息行包含根本原因错误? 先前的操作是否可能导致错误,或者该错误必须在代码中? “字符串缓冲区太小”-ACTIVITY_LOG或其他地方错误吗?

create or replace PROCEDURE "MONITORING_ACTIVITY_LOG" (IN_KPI_DEF_ID_VAL IN VARCHAR DEFAULT 0,IN_OBJECT IN VARCHAR) AS
  PRAGMA AUTONOMOUS_TRANSACTION;

err_code VARCHAR(100);
err_msg VARCHAR(200);

BEGIN

    err_code :=SUBSTR(SQLCODE, 1, 100);
    err_msg := SUBSTR(SQLERRM, 1, 200);
    Insert into ACTIVITY_LOG(KPI_DEF_ID,EXCEPTION_IN,OBJECT,SQL_ERROR_CODE,SQL_ERROR_MESSAGE,TIMESTAMP) VALUES (IN_KPI_DEF_ID_VAL,'MONITORING',IN_OBJECT,err_code,err_msg,SYSDATE);

END;    

2 个答案:

答案 0 :(得分:2)

ORA-06519是其本身的根本原因。在您的跟踪中,您有来自应用程序其他部分的不相关错误消息,这些错误消息触发了对#if defined(I_NEED_A_BAD_HACK) || defined(GLOBAL_STATE_STORE) # define USE_FULL_FUNCTION #endif #ifdef USE_FULL_FUNCTION std::vector< std::string >& GetGlobalStrings() { static std::vector< std::string > g; return g; } #else std::vector< std::string >& GetGlobalStrings(); #endif 的调用,以记录错误消息。

因此,ORA-06519。您的过程声明了AUTONOMOUS_TRANSACTION MONITORING_ACTIVITY_LOG。此类事务的范围是声明它的过程。因此,您需要在过程结束之前通过发出pragma来关闭自主事务。

commit

答案 1 :(得分:1)

在我看来,它始于MONITORING.PERFORM_CHECK第1129行(也许是select into“ ORA-01422:精确获取返回的行数超过了请求的行数” ),从而触发了对错误记录器的调用,该错误记录器本身由于缺少commit的自治事务而失败,并失败了ORA-06519。

err_msg := SUBSTR(SQLERRM, 1, 200);处似乎还出现“ ORA-06502:数字或值错误:字符串缓冲区太小” ,尽管由于定义为{ {1}}(顺便说一下,应为varchar(200))。我不确定您为什么要截断它,因为您可能会丢失有用的信息。我个人将直接使用varchar2并确保该列具有适当的大小。 (请注意,您实际的错误堆栈的长度为681个字节,将其截断为200个会删除您要查找的大多数详细信息。)

我从不知道sqlerrm是捕获有用的东西,我更喜欢存储包,过程,行号,调用堆栈,模块,操作,客户端信息,用户,OS用户等。< / p>