Коллеги, всем привет! 👋
На связи Денис.
Последние посты были прям хардкорные: SQL_ID, хэши, трансляторы, кэш скалярных подзапросов. Изнанка и тёмная магия Oracle 🧙♂️
Давайте выдохнем и разберём что-нибудь попроще, но не менее важное. Материал для Junior и Middle, сеньоры-помидоры 🍅 могут кивать и вспоминать свою молодость.
Итак, классика жанра. Видели такое?
create or replace procedure set_salary(p_emp_id number, p_salary number) is
begin
update employees set salary = p_salary where employee_id = p_emp_id;
exception
when others then
null;
end;
Вызываем с кривыми данными:
begin
set_salary(100, -1);
dbms_output.put_line('Зарплата обновлена');
end;
Результат:
Зарплата обновлена
PL/SQL procedure successfully completed.
А в таблице как было 24000, так и осталось. На самом деле update упал на check-констрейнте
ORA-02290, но мы об этом никогда не узнаем. Ни мы, ни вызывающий код, ни пользователь, который через неделю придёт с вопросом "а где мои деньги?" 🤷🏻♂️Почему так пишут?
🔹 "Чтобы не падало". Не падает, да. Просто молча делает не то.
🔹 Скопировали из старого кода, а там так было.
🔹 Поставили на время отладки и забыли.
Как надо
✅ Ловим только те исключения, которые реально умеем обработать:
no_data_found, dup_val_on_index и т.д. Обработать - значит сделать что-то осмысленное, а не "забыть".✅ Если
when others всё-таки нужен (логирование, например), он заканчивается на raise:exception
when others then
log_error(sqlerrm, dbms_utility.format_error_backtrace);
raise;
Ошибка залогирована, вызывающий код про неё знает, транзакция не продолжается как ни в чём не бывало.
✅
dbms_utility.format_error_backtrace - хозяйке на заметку: показывает номер строки, где реально упало. Без него в логе будет только строка обработчика, и ищи потом ветра в поле.Компилятор вам подскажет
Включите предупреждения:
alter session set plsql_warnings = 'ENABLE:ALL';
И на первую версию процедуры Oracle сам скажет. В 11g и 18c:
PLW-06009: procedure "SET_SALARY" OTHERS handler does not end in RAISE or RAISE_APPLICATION_ERROR
В 23ai текст короче, просто
... does not end in RAISE, суть та же.Кстати, прогнал всё на 11g, 18c и 23ai:
when others then null везде одинаково молча глотает ошибку.Подробнее про обработку ошибок - в документации Oracle по PL/SQL.
Итог
Упавшая процедура - это неприятно. Процедура, которая молча не сработала, - это пипец, потому что ищется она неделями. Пусть лучше падает громко.
А у вас в проекте есть
when others then null? Признавайтесь в чатике, сколько штук нашли поиском по коду 😄💬С вами был Денис. Всем хорошего дня 🤝
#oracle #plsql #sql #oracledeveloper #базы_данных #Denis_Kivilev
Канал Oracle Developer | Чатик 💬
Мини-курс Оптимизация: Быстрый старт 🚀
📱 YouTube 📱 ВКонтакте 📱 LinkedIn 📱Threads
RUTUBE
