Доступ к внутреннему коду ошибки при запуске sql с использованием команды «немедленное выполнение» - PullRequest
0 голосов
/ 14 октября 2019

Я запускаю блок PL / SQL ниже из скрипта. Как вы можете видеть, он добавляет столбец и должен перехватывать любые исключения - среди них уже существует тот, который будет добавлен в столбец.

Теперь, если я запускаю этот файл и столбец уже существует, я получаю сообщение об ошибке:

Код ошибки: -1735

Сообщение об ошибке: ORA-01735: недействительноОпция ALTER TABLE

Это все хорошо, но если вместо этого я запусту внутренний SQL;это SQL, который следует за execute immediate сам по себе, вместо этого я получаю это сообщение, которое является более точным:

ORA-01430: добавляемый столбец уже существует в таблице

Первая ошибка имеет код ошибки -1735 , и я могу перехватить ее с помощью when, которое закомментировано в приведенном ниже коде;если это не закомментировано, вместо этого будет результат:

Произошла какая-то другая ошибка

Я не смог поймать -1430 исключение, хотя, хотя это, кажется, является основной причиной исключения.

Итак, мой вопрос: есть ли способ получить доступ к этому «внутреннему» исключению в этом случае? (это даже допустимый термин в этом случае?) Другими словами, может ли это бытьизменены, чтобы предоставить более конкретное сообщение об ошибке?

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;
/

1 Ответ

2 голосов
/ 14 октября 2019

Это то, что я получаю после небольшого изменения вашего кода:

В строке # 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>

Теперь я не уверен, было ли это с лишней точкой с запятой илине. Удалите его и перефразируйте вопрос, если необходимо.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...