使用execute immediate运行sql时访问内部错误代码
我正在从脚本运行下面的PL/SQL块。如您所见,它添加了一个列,并且应该捕获任何异常——其中,将在列中抛出的异常已经存在 现在,如果我运行此操作,并且该列已经存在,我会得到一个错误: 错误代码:-1735 错误消息:ORA-01735:ALTER TABLE选项无效 这很好,但是如果我运行内部SQL;这是紧随其后的SQL自身执行立即命令,我得到的是以下消息,更准确地说: ORA-01430:表中已存在正在添加的列 第一个错误的错误代码是-1735,我能够理解下面代码中注释掉的when子句;如果未注释掉,结果将改为: 发生了其他一些错误 我无法捕捉到-1430异常,尽管这似乎是异常的根本原因 所以我的问题是:在这种情况下,有没有办法访问这个内部异常?在这种情况下,这是一个有效的术语吗?换言之,是否可以对其进行修改以提供更具体的错误消息使用execute immediate运行sql时访问内部错误代码,sql,oracle,exception,plsql,dynamic-sql,Sql,Oracle,Exception,Plsql,Dynamic Sql,我正在从脚本运行下面的PL/SQL块。如您所见,它添加了一个列,并且应该捕获任何异常——其中,将在列中抛出的异常已经存在 现在,如果我运行此操作,并且该列已经存在,我会得到一个错误: 错误代码:-1735 错误消息:ORA-01735:ALTER TABLE选项无效 这很好,但是如果我运行内部SQL;这是紧随其后的SQL自身执行立即命令,我得到的是以下消息,更准确地说: ORA-01430:表中已存在正在添加的列 第一个错误的错误代码是-1735,我能够理解下面代码中注释掉的when子句;如果未
DECLARE
column_exists exception;
pragma exception_init (column_exists , -1430);
general_error exception;
pragma exception_init (general_error , -1735);
BEGIN
execute immediate 'ALTER TABLE my_table
ADD (some_column VARCHAR2(10 CHAR));';
EXCEPTION
-- I expected / wanted this to catch my error in order
-- to let me output a more specific message:
WHEN column_exists THEN
DBMS_OUTPUT.PUT_LINE('The column or index already exists');
-- Note: Commented out, but would otherwise catch the general error.
-- (I tested it here just to confirm that I can catch exceptions this way)
-- WHEN general_error THEN
-- DBMS_OUTPUT.PUT_LINE('Some other error occurred');
-- General catch: Generates the first message quoted above:
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('Error code: ' || SQLCODE);
DBMS_OUTPUT.PUT_LINE('Error message: ' || SQLERRM);
END;
/
这是我在稍微修改您的代码后得到的结果: 在第9行中,有一个分号应该删除,因为EXECUTE IMMEDIATE不允许这样做,如下所示:
ADD (some_column VARCHAR2(10 CHAR));';
^
|
remove it
样本表:
SQL> CREATE TABLE test
2 AS
3 SELECT * FROM dept;
Table created.
您的代码:
SQL> DECLARE
2 column_exists EXCEPTION;
3 PRAGMA EXCEPTION_INIT (column_exists, -1430);
4
5 general_error EXCEPTION;
6 PRAGMA EXCEPTION_INIT (general_error, -1735);
7 BEGIN
8 EXECUTE IMMEDIATE 'ALTER TABLE test
9 ADD (loc VARCHAR2(10 CHAR))'; --> remove ; here
10 EXCEPTION
11 -- I expected / wanted this to catch my error in order
12 -- to let me output a more specific message:
13 WHEN column_exists
14 THEN
15 DBMS_OUTPUT.PUT_LINE ('The column or index already exists');
16 -- Note: Commented out, but would otherwise catch the general error.
17 -- (I tested it here just to confirm that I can catch exceptions this way)
18 -- WHEN general_error THEN
19 -- DBMS_OUTPUT.PUT_LINE('Some other error occurred');
20
21 -- General catch: Generates the first message quoted above:
22 WHEN OTHERS
23 THEN
24 DBMS_OUTPUT.PUT_LINE ('Error code: ' || SQLCODE);
25 DBMS_OUTPUT.PUT_LINE ('Error message: ' || SQLERRM);
26 END;
27 /
The column or index already exists
PL/SQL procedure successfully completed.
SQL>
现在,我不确定是否是多余分号的情况。如果有必要,请删除它并重新表述问题。这是我在稍微修改代码后得到的结果: 在第9行中,有一个分号应该删除,因为EXECUTE IMMEDIATE不允许这样做,如下所示:
ADD (some_column VARCHAR2(10 CHAR));';
^
|
remove it
样本表:
SQL> CREATE TABLE test
2 AS
3 SELECT * FROM dept;
Table created.
您的代码:
SQL> DECLARE
2 column_exists EXCEPTION;
3 PRAGMA EXCEPTION_INIT (column_exists, -1430);
4
5 general_error EXCEPTION;
6 PRAGMA EXCEPTION_INIT (general_error, -1735);
7 BEGIN
8 EXECUTE IMMEDIATE 'ALTER TABLE test
9 ADD (loc VARCHAR2(10 CHAR))'; --> remove ; here
10 EXCEPTION
11 -- I expected / wanted this to catch my error in order
12 -- to let me output a more specific message:
13 WHEN column_exists
14 THEN
15 DBMS_OUTPUT.PUT_LINE ('The column or index already exists');
16 -- Note: Commented out, but would otherwise catch the general error.
17 -- (I tested it here just to confirm that I can catch exceptions this way)
18 -- WHEN general_error THEN
19 -- DBMS_OUTPUT.PUT_LINE('Some other error occurred');
20
21 -- General catch: Generates the first message quoted above:
22 WHEN OTHERS
23 THEN
24 DBMS_OUTPUT.PUT_LINE ('Error code: ' || SQLCODE);
25 DBMS_OUTPUT.PUT_LINE ('Error message: ' || SQLERRM);
26 END;
27 /
The column or index already exists
PL/SQL procedure successfully completed.
SQL>
现在,我不确定是否是多余分号的情况。如有必要,将其删除并重新表述问题。删除;在“。。。。。VARCHAR210 CHAR;'然后再试一次。您还可以从用户选项卡中选中view SELECT*,其中table_name='MY_table';查看是否已添加列。删除;在“。。。。。VARCHAR210 CHAR;'然后再试一次。您还可以从用户选项卡中选中view SELECT*,其中table_name='MY_table';查看是否已经添加了列。谢谢,看起来这实际上是个错误。我无法检测到它,因为单独运行SQL(包括分号)效果很好。谢谢你的意见!谢谢,看来这实际上是个错误。我无法检测到它,因为单独运行SQL(包括分号)效果很好。谢谢你的意见!