Самоучитель по SQL-сервер в Linux



Обработка ошибок и исключений

Команда RAISE предназначена для инициирования ошибок и исключений в функциях PL/pgSQL. Она передает заданную информацию механизму PostgreSQL elog (стандартное средство ведения протокола ошибок — данные обычно направляются в файл /var/log/messages или $PGDATA/serverlog с одновременным выводом в поток stderr).

В команде RAISE также указывается уровень ошибки и строка, передаваемая PostgreSQL. Кроме того, в команду можно включить переменные и выражения, значения которых будут содержаться в выходных данных. Соответствующие позиции строки помечаются знаками процента (%). Синтаксис команды RAISE: RAISE уровень ''сообщение'' [. идентификатор [...] ]:

В табл. 11.1 приведены три допустимые значения уровня ошибки с краткими описаниями.

Таблица 11.1. Допустимые значения уровня ошибки

Значение

Описание

DEBUG

Команда уровня DEBUG направляет заданный текст в виде сообщения DEBUG: в журнал PostgreSQL и клиентской программе, если клиент подключен к кластеру базы данных, работающему в отладочном режиме. Команды RAISE уровня DEBUG игнорируются базами данных, работающими в режиме реальной эксплуатации

NOTICE

Команда уровня NOTICE направляет заданный текст в виде сообщения NOTICE: в журнал PostgreSQL и клиентской программе. Сообщение передается в любом режиме работы PostgreSQL

EXCEPTION

Команда уровня EXCEPTION направляет заданный текст в виде сообщения ERROR: в журнал PostgreSQL и клиентской программе. Ошибка уровня EXCEPTION также вызывает откат текущей транзакции

В листинге 11.48 первая команда RAISE выводит отладочное сообщение, а вторая и третья команды выводят сообщение для пользователя. Обратите внимание на знак % в третьей команде — он отмечает позицию, в которой выводится значение an_i nteger. Наконец, четвертая команда RAISE выводит сообщение об ошибке и инициирует исключение, приводящее к отмене транзакции.

Листинг 11.48. Команда RAISE

CREATE FUNCTION raise_test () RETURNS integer AS '

DECLARE

-- Объявление целочисленной переменной для тестового вывода.

an_integer integer = 1;

BEGIN

- Вывести отладочное сообщение уровня

DEBUG. RAISE DEBUG "The raise_test() function began.":

an_integer = an_integer * 1;

-- Вывести сообщение об изменении переменной an_integer,

-- а затем вывести другое сообщение с ее новым значением.

RAISE NOTICE "Variable anjnteger was cnanged.";

RAISE NOTICE "Variable anjnteger's value is now £." anjnteger;

-- Инициировать исключение.

RAISE EXCEPTION "Variable % cnanged.

Transaction aborted. ",anjnteger:

RETURN 1:

END;

' LANGUAGE 'plpgsql':

В листинге 11.49 приведены результаты, полученные при вызове функции raise_test() из базы данных booktown. Отладочное сообщение DEBUG отсутствует, поскольку база данных работает не в отладочном режиме.

Листинг 11.49. Результаты вызова raise_test()

booktown=# SELECT raise_test();

NOTICE: Variable anjnteger was changed.

NOTICE: Variable anjnteger's value is now 2.

ERROR: Variable 2 changed. Aborting transaction.

Вызов функций

При вызове функции PL/pgSQL из кода PL/pgSQL имя функции обычно включается в команду SQL SELECT или в команду присваивания. Примеры:

SELECT функция (аргументы):

переменндя := функция(аргументы):

Подобный способ вызова функций при выборке и присваивании стал стандартным, поскольку любая функция PostgreSQL должна возвращать значение некоторого типа. Ключевое слово PERFORM позволяет вызвать функцию и проигнорировать возвращаемое значение. Синтаксис вызова функции с ключевым словом PERFORM: PERFORM функция (аргументы'):

В листинге 11.50 приведены примеры вызова функции PL/pgSQL с ключевым словом PERFORM и вызова другой функции PL/pgSQL посредством присваивания (в команде SELECT INTO). Функция ship_item() является удобной «оболочкой» для вызова функции add_sh1pment(). Она получает исходные данные, убеждается в существовании покупателя и книги, а затем передает данные add_shipment().

Листинг 11.50. Использование ключевого слова PERFORM

CREATE FUNCTION shipjtem (text.text.text) RETURNS integer AS '

DECLARE

-- Объявление псевдонимов для аргументов функции.

l_name ALIAS FOR $1: f_name ALIAS FOR $2;

bookjsbn ALIAS FOR $3:

-- Объявление переменной для хранения кода книги.

-- Переменная используется для проверки переданного кода ISBN.

book_id Integer:

-- Объявление переменной для хранения кода покупателя.

-- Переменная используется для проверки переданных данных покупателя.

customeMd integer;

BEGIN

-- Получить код покупателя при помощи ранее определенной функции.

SELECT INTO customer_id get_customer_id(l_name.f_name);

-- Если покупатель не найден, функция get_customerjd

-- возвращает -1. В этом случае вернуть -1 и выйти из функции.

IF customerjd = -1 THEN

RETURN -1:

END IF:

-- Получить код книги с заданным кодом ISBN.

SELECT INTO book id book id FROM editions WHERE isbn = book isbn:

-- Если данные книги отсутствуют в базе, вернуть -1.

IF NOT FOUND THEN

RETURN -1;

END IF;

-- Если книга и покупатель существуют.

-- сохранить информацию о поставке в базе.

PERFORM add_shipment(customer_id.bookjsbn);

-- Вернуть 1 - признак успешного выполнения функции.

RETURN 1:

END;

' LANGUAGE 'plpgsql':




Книжный магазин