范围和正确使用SQLERRM? (处理异常PL / SQL,ORACLE)

时间:2018-03-17 02:34:19

标签: sql oracle exception stored-procedures plsql

我对在oracle存储过程中处理异常有一些疑问,特别是关于sqlerrm的使用。让我解释一下。

根据oracle官方文档,sqlerrm是一个函数:

“..返回与最近引发的错误异常相关的错误消息。此函数只能在代码的异常处理部分中使用。”

oracle异常语法是:

EXCEPTION
WHEN exception_name1 THEN
      [statements]
   WHEN exception_name_n THEN
      [statements]
   WHEN OTHERS THEN
      [statements] --Here use SQLERRM and do a trace
END;

通常,在发生不受控制的异常时使用SQLERRM。

现在,当您将一些暴露于异常的函数调用到存储过程中时,异常处理会发生什么?

让我用一个例子来解释:

--Create a packague
CREATE OR REPLACE PACKAGE BODY MY_PACKAGE AS

FUNCTION F1() RETURN NUMBER IS
BEGIN
    --do querys and return a value
END F1;

FUNCTION F2() RETURN NUMBER IS 
BEGIN
    --do querys and return a value
END F2;

FUNCTION F3() RETURN NUMBER IS
BEGIN
    --do querys and return a value
END F3;

PROCEDURE MY_PROCEDURE(v_mssg_err OUT VARCHAR2) IS
    v1 NUMBER; v2 NUMBER; v3 VARCHAR2(10);
BEGIN
    v1 := FUNCTION1();
    v2 := FUNCTION2();
    v3 := FUNCTION3();
    v_mssg_err := 'OK';

    EXCEPTION WHEN OTHERS THEN
        --If an error happens in F1(),F2() or F3()
        v_mssg_err := sqlerrm; 
        -- I think this is a correct way to handle exceptions
END MY_PROCEDURE;
END MY_PACKAGE;

我认为SQlERRM返回F1(),F2()或F3()中出现的错误消息。

但是,我收到了一个包,其中正在处理包中声明的每个函数的异常。这样。

FUNCTION F4() RETURN VARCHAR2 IS
    response VARCHAR2(1000); --511 is the max length possible for SQLERRM
BEGIN
    --do querys and return a string value
    RETURN response;
    EXCEPTION WHEN OTHERS THEN
        response := TO_CHAR(-1)||sqlerrm;       
END F4;

我不确定这是处理异常的有效方法。因为对于调用该函数的每个存储过程,它是必要的拆分并检查值返回。

回到我的问题

调用多个函数的存储过程中的范围和正确的异常处理是什么?非常感谢你的帮助!

来源:

  1. Oracle:https://www.techonthenet.com/oracle/exceptions/sqlerrm.php
  2. SQLERRM长度:http://matt.gizma.com/2006/08/a_varchar2_511_to_hold_sqlerrm.html

1 个答案:

答案 0 :(得分:0)

这取决于错误的类型以及您希望如何管理它。您的异常将被最近的封闭块(或块本身)捕获,该块具有该异常的异常处理程序。

如果要将异常捕获到F1()中,则意味着您要从那里处理异常。然后,您的主程序将能够继续执行F2,F3等。如果从主程序中捕获F1()的异常,则执行将在那里停止,因此它将无法调用其他函数。

另请注意,您需要将return语句放入函数的异常处理中,否则在执行时会抛出异常(ORA-06503)。