PL / SQL Триггер не работает - проблема с настройкой переменной - PullRequest
0 голосов
/ 26 февраля 2020

мой триггер не работает, когда я пытаюсь обновить запрос. Есть идеи почему? Я чувствую, что это связано с условиями ГДЕ, когда я пытаюсь установить переменные. Я пытался сделать это без условий WHERE, но это все равно не сработало.

Есть идеи почему? Спасибо!

CREATE OR REPLACE TRIGGER SYSTEM.Product_Price_Check
BEFORE UPDATE ON SYSTEM.product FOR EACH ROW

DECLARE     
min_price NUMBER(19,4); 
new_price NUMBER(19,4);

BEGIN 

    SELECT (StandardCost*1.2)
    INTO min_price
    FROM SYSTEM.product
    WHERE ProductID = :new.ProductID;

    SELECT ListPrice    
    INTO new_price
    FROM SYSTEM.product
    WHERE ProductID = :new.ProductID;

    IF new_price < min_price THEN
        ROLLBACK;
        --DBMS_OUTPUT.PUT_LINE('the price can’t be below '||CAST(min_price as VARCHAR(25)));
        --RAISE VALUE_ERROR;

    --ELSE
       --DBMS_OUTPUT.PUT_LINE('Price was successfully changed');

    END IF;


END;

Ответы [ 3 ]

2 голосов
/ 26 февраля 2020

Полагаю, это домашнее задание, и вам сказали использовать триггер. Долгие годы, проведенные на этом сайте, научили меня, что учителя любят задавать задания, которые требуют неправильного использования триггеров.

В реальной жизни единственный правильный способ применения такого правила - это ограничение проверки:

alter table product add constraint price_check 
    check (standard_cost * 1.2 >= min_price)
1 голос
/ 27 февраля 2020

Как уже отмечали другие, вы не должны создавать объекты, такие как таблицы или триггеры, в схеме SYSTEM. Создайте себе пользователя, предоставьте ему необходимые привилегии (хорошая практика) и используйте этого пользователя и его схему для целей разработки.

Далее - триггеры подряд (один с FOR EACH ROW в нем), к которым у вас нет доступа таблица, для которой определен триггер, в данном случае это таблица PRODUCT. К счастью, вам не нужно. Значения, которые вы хотите, уже находятся в псевдорядах: OLD или: NEW - я предполагаю, что вы действительно хотите использовать: NEW values:

CREATE OR REPLACE TRIGGER PRODUCT_PRICE_CHECK
  BEFORE UPDATE ON PRODUCT
  FOR EACH ROW
DECLARE
  nMin_price NUMBER := :NEW.STANDARD_COST * 1.2;
BEGIN 
    IF :NEW.LISTPRICE < nMin_price THEN
      DBMS_OUTPUT.PUT_LINE('List price can’t be below '|| nMin_price);

      RAISE VALUE_ERROR;
END PRICE_CHECK;

Кроме того, вы не можете выполнить ROLLBACK или COMMIT в триггере - Oracle не позволяет этому произойти.

1 голос
/ 26 февраля 2020

Покажите свою ошибку. Возможно, ваш триггер мутирующий

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

...