2009-10-19 58 views
12

Im trabajando en un script pl-sql, en el que tengo alrededor de 10 conversiones TO_CHAR.¿Hay alguna forma de obtener el número de línea donde se lanzó una excepción?

Uno de ellos es una excepción

ORA-06502: PL/SQL: numeric or value error: character string buffer too small 

.

Actualmente, im registrar el mensaje con esta pieza de código

EXCEPTION 
    WHEN OTHERS THEN 
    DBMS_OUTPUT.put_line('Exception message is '||SQLERRM(sqlcode)); 
    ROLLBACK; 

me gustaría añadir (en su mayoría para fines de depuración) de la línea donde se produce la excepción, con el fin de recibir un mensaje en el forma de

ORA-06502: PL/SQL: numeric or value error: character string buffer too small (at line x) 

¿Hay una manera fácil de hacer esto?

Respuesta

0

Puede colocar su manejador de excepciones en cada instrucción.

9

Las respuestas han mencionado ambos, $$PLSQL_LINE & DBMS_UTILITY.FORMAT_ERROR_BACKTRACE. Pero me gustaría añadir un poco acerca de la diferencia entre ellos:

  1. Predefined Inquiry Directives$$PLSQL_LINE & $$PLSQL_UNIT
    PLSQL_LINE Directiva consulta predefinida es un valor literal PLS_INTEGER que indica el número de línea de referencia para $$ PLSQL_LINE en la unidad de programa actual.
    Según su definición, PLSQL_LINE no es adecuado para el registro de excepciones porque proporcionará el número de línea de la excepción, en lugar de que el número de línea del error se haya producido. Esto hace que sea difícil detectar la ubicación del error, especialmente con las unidades de programa grandes, a menos que envuelva cada declaración con el manejador de excepciones como se indica en la respuesta de Jeffrey.
    Sin embargo, lo bueno de PLSQL_LINE, proporciona el número sin la necesidad de ninguna extracción o análisis sintáctico de cadenas. Por lo tanto, podría ser más adecuado para otros fines de registro.
  2. DBMS_UTILITY.FORMAT_ERROR_BACKTRACE
    Este procedimiento muestra la pila de llamadas en el punto donde se produjo una excepción, incluso si el procedimiento es invocado desde un controlador de excepción en un ámbito externo.
    La ventaja de utilizar este procedimiento es que proporciona el número de línea exacto en el programa donde se produce el error , y no donde aparece la llamada al procedimiento Sin embargo, el procedimiento devuelve una cadena como ORA-XXXXX: at "<program_unit_name>", line xx.Entonces, si está interesado en extraer el número de línea en sí, para cualquier propósito de registro que desee, necesitará analizar la cadena.

Finalmente, para dejar la diferencia clara, a continuación se presentan dos procedimientos, con el mismo contenido. Puede ejecutar ellos y notar la diferencia de salida

CREATE OR REPLACE PROCEDURE proc_plsql_line 
    IS 
    BEGIN 
     RAISE VALUE_ERROR; 
    EXCEPTION 
     WHEN VALUE_ERROR 
     THEN 
      DBMS_OUTPUT.put_line ('Error raised in: '|| $$plsql_unit ||' at line ' || $$plsql_line || ' - '||sqlerrm); 
    END; 
/

Y

CREATE OR REPLACE PROCEDURE proc_backtrace 
    IS 
    BEGIN 
     RAISE VALUE_ERROR; 
    EXCEPTION 
     WHEN VALUE_ERROR 
     THEN 
      DBMS_OUTPUT.put_line ('Error raised: '|| DBMS_UTILITY.FORMAT_ERROR_BACKTRACE || ' - '||sqlerrm); 
    END; 
/

Ejecución:

exec proc_plsql_line; 

Error raised in: PROC_PLSQL_LINE at line 8 - ORA-06502: PL/SQL: numeric or value error 


exec proc_backtrace; 

Error raised: ORA-06512: at "PROC_BACKTRACE", line 4 - ORA-06502: PL/SQL: numeric or value error 
+2

¡esta debería ser la respuesta "ACEPTABLE"! –

0

La declaración DBMS_UTILITY.format_error_backtrace le dará el número de línea

begin 
select 1/0 from dual; 
exception 
    when others then 
    dbms_output.put_line('ERROR_STACK: ' || DBMS_UTILITY.FORMAT_ERROR_STACK); 
    dbms_output.put_line('ERROR_BACKTRACE: ' || DBMS_UTILITY.FORMAT_ERROR_BACKTRACE); 
end; 
Cuestiones relacionadas