триггер mysql к триггеру оракула - PullRequest
1 голос
/ 18 ноября 2010

Я написал триггер в mysql, который проверяет, может ли человек проверить другой элемент библиотеки.Я установил лимит проверки 3. Мне нужно преобразовать его в триггер Oracle, но у меня много проблем.

Вот мой код MySQL:

DELIMITER //
DROP TRIGGER IF EXISTS library.CheckBorrowsTable//
CREATE TRIGGER CheckBorrowsTable
BEFORE INSERT ON library.Borrows
FOR EACH ROW
BEGIN
IF ((SELECT COUNT(*) FROM library.Borrows WHERE libraryID = new.libraryID) >= 3)THEN
SET new = NULL;
END IF;
END//
DELIMITER ;

Вот мой Oraclecode:

IF((SELECT COUNT(libraryID) FROM Borrows WHERE libraryID = :NEW.libraryID) >= 3) THEN
:NEW = NULL;
END IF;

В моем коде Oracle есть и другие части, но Oracle Express Edition добавляет эти части (Begin, End и т. д.) ...

1 Ответ

3 голосов
/ 18 ноября 2010

Триггер уровня строки в таблице A (т. Е. Library.borrows) не может запросить таблицу A. Если вы это сделаете, вы получите исключение мутирующей таблицы (если только вы не можете гарантировать, что вы когда-либо будете выполнять вставку только одной строки спункт ЗНАЧЕНИЯ).Так что это не будет считаться хорошей практикой разработки в Oracle.

Наиболее логичным способом реализации такого рода требований не является использование триггера.Вместо этого, если ваше приложение вызывает API хранимых процедур, у вас будет хранимая процедура (например, CHECK_OUT), которая сначала запрашивает таблицу, чтобы определить, сколько книг было извлечено отдельным человеком, и вставляет строку в таблицу BORROWS, только если посетитель находится нижеего или ее предел.

Второй подход заключается в сохранении количества пунктов, извлеченных в отдельной таблице.Если у вас была таблица PATRONS со столбцом NUM_CHECKED_OUT, а в таблице BORROWS был PATRON_ID, указывающий, кто заимствовал книгу, ваш триггер может сделать что-то вроде

CREATE OR REPLACE TRIGGER CheckBorrowsTable
  BEFORE INSERT ON library.borrows
  FOR EACH ROW
BEGIN
  UPDATE patrons p
     SET p.num_checked_out = p.num_checked_out + 1
   WHERE p.patron_id = :new.patron_id
END;

вместе с ограничением CHECK для таблицы PATRONS, чтобыубедитесь, что NUM_CHECKED_OUT никогда не превышает 3.

За исключением того, что возможно, хотя и довольно обременительно, обойти ошибку таблицы мутаций с помощью "решения трех триггеров".

  1. A ДОТриггер уровня инструкции INSERT очищает коллекцию, созданную в пакете.
  2. ПЕРЕД триггером уровня строки INSERT записывается первичный ключ (или ROWID) изменяемой строки в коллекцию.
  3. Триггер уровня оператора AFTER INSERT считывает данные из коллекции, запрашивает таблицу и определяет, нарушает ли какая-либо из вставок бизнес-правило.Если они это сделали, выведите исключение.

Как вы можете себе представить, однако, триггерное решение включает в себя достаточное количество движущихся фигур, поэтому это не особенно рекомендуется.

Вы также можетереализовать такие вещи с помощью быстро обновляемого материализованного представления, но я не верю, что это вариант в экспресс-редакции базы данных (хотя я могу ошибаться в этом).

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