出于调试目的,我需要根据给定的标志引发应用程序级别的消息。这是异常代码
EXCEPTION
WHEN dml_errors THEN
l_errors := SQL%BULK_EXCEPTIONS.COUNT;
S_Publish('I', 'Number of statements that failed: ' || l_errors);
FOR i IN 1..l_errors LOOP
S_Publish('I', 'Error #' || TO_CHAR(i) || ' occurred during '|| 'iteration #' || SQL%BULK_EXCEPTIONS(i).ERROR_INDEX);
S_Publish('I', 'Error message is ' || SQLERRM(-SQL%BULK_EXCEPTIONS(i).ERROR_CODE));
S_Publish('I', 'Failing Record ID is ' || sap_tbl_ins(SQL%BULK_EXCEPTIONS(i).ERROR_INDEX).DEVICE_PIN);
END LOOP;
IF g_app_error_flag THEN
raise_application_error(-20707, 'Fatal Error: Replication script exceptions', TRUE);
END IF;
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('Error on record:' || l_zzman);
S_Publish('I', 'SAP_EQUI Update: Failure processing record ' || l_zzman);
S_Publish ('F');
IF g_app_error_flag THEN
raise_application_error(-20708, 'Fatal Error: Replication script exceptions', TRUE);
END IF;
现在给出这个代码,只要** g_app_error_flag为真, raise_application_error 就会引发一个。但是,在所有情况下(我的意思是测试环境,我通过在表格上添加一些约束来故意使脚本失败),我所看到的只是DML错误,即
ORA-01403: no data found
ORA-06512: at "DBNAME.PRODUCT_COPY_PACKAGE", line 1808
ORA-24381: error(s) in array DML
ORA-06512: at "DBNAME.PRODUCT_COPY_PACKAGE", line 84
ORA-06512: at line 3
你们可以建议一下吗?
P.S:
这是S_Publish的定义。 S_Publish中没有“加注”。
PROCEDURE S_Publish (i_type IN VARCHAR2,
i_msg IN VARCHAR2 DEFAULT NULL) IS
BEGIN
CASE
WHEN i_type = 'G' THEN
IF g_debug_flag
THEN
INSERT INTO logtable (tstamp,line) values (SYSDATE, i_msg);
COMMIT;
g_counter := 0;
END IF;
WHEN i_type = 'F' THEN
g_err_code := SQLCODE;
g_err_msg := TO_CHAR(g_err_code)||' '||SUBSTR(SQLERRM, 1, 100);
INSERT INTO logtable (tstamp,line) values (SYSDATE, g_err_msg);
COMMIT;
WHEN i_type = 'I' THEN
INSERT INTO logtable (tstamp,line) values (SYSDATE, i_msg);
COMMIT;
g_counter := 0;
END CASE;
END S_Publish;
经过一些调试后,到目前为止我已经想到了什么。我不知道它背后是什么呢?
所以问题是程序在结束打印错误即FOR i IN 1..l_errors LOOP
之后就会退出。该程序退出END LOOP
。为什么之后的任何事情都没有被执行?
答案 0 :(得分:2)
所以问题发生在S_Publish
。它所指的表格,即sap_tbl_ins
是基于0
的。 SQL%BULK_EXCEPTIONS(i).ERROR_INDEX
基本上是失败时的迭代次数。因此,引用一个基于0的索引和一个数字会引发数组超出范围"例外。我只想出来并将公式改为
S_Publish('I', 'Failing Record ID is ' || sap_tbl_ins((SQL%BULK_EXCEPTIONS(i).ERROR_INDEX)-1).DEVICE_PIN);
并且工作正常。
答案 1 :(得分:0)
由于我们没有看到所有代码,我们必须依赖于您,当您通过在表上添加一些约束来故意执行脚本失败时,您发布的此异常块就是活性。因此,如果此块正在生效,您没有看到“raise_application_error(-20707,.....”或带有-20708的第二个)的原因可能是“S_Publish”过程本身引发异常除非你用额外的一个来包围它们,否则不会在它们运行的同一个异常块中捕获。为了测试这个理论,尝试暂时删除对它的调用,看看你是否得到了引发的错误。
答案 2 :(得分:0)
好的,问题:
1)PRODUCT_COPY_PKG中第1808行/周围的代码是什么。这是第一个错误发生的地方。
2)插入到logtable是否正在发生? (即 - 这个异常块是否真的在执行?)
3)那个错误堆栈输出是否来自dbms_output语句?或者是Oracle在运行时的堆栈转储?
样式注释:我希望用PRAGMA AUTONOMOUS_TRANSACTION定义S_PUBLISH,否则你的COMMIT可以提交一个部分完成的事务,如果你的代码在出错的时候正在做的事情......