繁体   English   中英

Oracle:使用SQL或PL / SQL在动态SQL中查找错误的位置

[英]Oracle: Find the position of an error in dynamic SQL using SQL or PL/SQL

如何在PL / SQL或SQL中的动态SQL语句中找到错误的位置?

从SQL * Plus我看到错误的位置,例如,无效的SQL DML语句:

SYS@orcl> SELECT
       2    X
       3  FROM
       4    TABLEX
       5  /
  TABLEX
  *
ERROR at line 4:
ORA-00942: table or view does not exist

SQL * Plus使用行号显示错误,并打印和标记与发现错误的星号对齐。

转换为动态SQL,我可以得到错误代码(SQLCODE)和错误消息(SQLERRM):

SYS@orcl> SET SERVEROUTPUT ON
SYS@orcl> BEGIN
       2    EXECUTE IMMEDIATE 'SELECT X FROM TABLEX';
       3  EXCEPTION
       4    WHEN OTHERS THEN
       5      DBMS_OUTPUT.PUT_LINE('SQLCODE:' || SQLCODE);
       6      DBMS_OUTPUT.PUT_LINE('SQLERRM:' || SQLERRM);
       7  END;
       8  /
SQLCODE:-942
SQLERRM:ORA-00942: table or view does not exist

但是如何在动态SQL字符串中获取错误的位置?

我看到Oracle提供了一个SQL通信区域(SQLCA),其中包含有关错误的有趣信息。 尤其是:

  • SQLCODE和SQLERRM字段(可能是使用相应PL / SQL函数检索的数据的源),
  • SQLERRD字段,其中SQLERRD(5)元素给出'解析错误偏移'。

是否可以从PL / SQL或SQL访问SQLERRD? 如果是这样,怎么样? 如果没有,还有哪种技术可以从PL / SQL或SQL中提供错误的位置?

(此处http://docs.oracle.com/cd/B28359_01/appdev.111/b31231/chapter8.htm#BABIGBFF记录了SQLCA并使用Pro * C进行访问。)

(这里的答案如何声明SQLCA.SQLERRD?似乎表明SQLERRD没有在PL / SQL中定义,因此无法访问。)

(这里的讨论为什么Oracle没有告诉你WHICH表或视图不存在?给出了一些建议,用于显示使用跟踪文件的错误SQL并在一些开发工具中显示错误的位置。)

你有一个用于在dbms_utility中提取错误消息的

begin 
    .. generate error
exception when others then 
    dbms_output.put_line(
        dbms_utility.format_call_stack()      || chr(10) || 
        dbms_utility.format_error_backtrace() || chr(10) || 
        dbms_utility.format_error_stack())
end;

通过动态PL / SQL运行语句会将相关行号存储在错误堆栈中。

例如,此语句在第4行有错误:

declare
    v_count number;
    v_bad_sql varchar2(32767) := 
        'SELECT
            X
          FROM
            TABLEX';
begin
    execute immediate v_bad_sql into v_count;
exception when others then
    begin
        execute immediate
            'begin for i in ( '||v_bad_sql||') loop null; end loop; end;';
    exception when others then
        dbms_output.put_line(sqlerrm);
    end;
end;
/

ORA-06550: line 4, column 4:
PL/SQL: ORA-00942: table or view does not exist
ORA-00942: table or view does not exist
ORA-06550: line 1, column 18:
PL/SQL: SQL Statement ignored
ORA-00942: table or view does not exist

这种方法有一些缺点:

  1. 它需要一些额外的,丑陋的代码来捕获异常并重新尝试SQL。
  2. 该示例仅适用于选择。 您需要调整它以进行插入,更新,删除,合并,动态PL / SQL等。通常,您应该知道它是什么类型的SQL语句。 如果你运气不好,你需要解析声明,这可能非常困难。
  3. 如果整个PL / SQL语句在一行上,则列号错误。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM