2016-06-04 2 views
1

Я получаю сообщение об ошибке ORA-04091 (перепишите триггер (или функцию), чтобы он не читал эту таблицу.) Каждый раз, когда я запускаю триггер.Oracle - переписать триггер

Вот триггер:

create or replace TRIGGER comment_date_trigger 
BEFORE INSERT OR UPDATE 
ON "comment" 
FOR EACH ROW 
DECLARE 
    date_article TIMESTAMP; 
    date_parent TIMESTAMP; 
BEGIN 
    IF :NEW."comment_parent_id" IS NOT NULL THEN 
     SELECT "comment_date" INTO date_parent FROM "comment_view" WHERE "comment_id" = :NEW."comment_parent_id"; 
    END IF; 
    SELECT "article_date" INTO date_article FROM "article" WHERE "article_id" = :NEW."comment_article_id"; 
    IF :NEW."comment_date" > SYSTIMESTAMP THEN 
     RAISE_APPLICATION_ERROR(-20003, '...'); 
    ELSIF :NEW."comment_date" < date_article THEN 
     RAISE_APPLICATION_ERROR(-20005, '...'); 
    ELSIF :NEW."comment_date" < date_parent THEN 
     RAISE_APPLICATION_ERROR(-20006, '...'); 
    END IF; 
END; 

Что самое простое решение, чтобы решить эту проблему, пожалуйста? Как вы могли видеть, я попытался использовать представление, но проблема остается.

Спасибо.

+0

Работает ли она, если вы меняете * перед вставкой или обновлением * до * после вставки или обновления *? Это должен быть тот же эффект, поскольку вы не намерены изменять какие-либо новые. значения, и в итоге вы откажетесь от транзакции, если она не пройдет проверку. –

+0

Это все равно. – KRiSTiN

ответ

1

Вы не можете выполнить запрос в той же таблице триггера, потому что таблица изменяется.

Только обходной путь я знаю, чтобы объявить триггер с PRAGMA AUTONOMOUS_TRANSACTION: это будет отвязать транзакцию, которая срабатывает триггер из запросов, выполняемых триггером:

create or replace TRIGGER comment_date_trigger 
BEFORE INSERT OR UPDATE ON comment 
FOR EACH ROW 
DECLARE 

    PRAGMA AUTONOMOUS_TRANSACTION; 

    date_article TIMESTAMP; 
    date_parent TIMESTAMP; 

BEGIN 

    IF :NEW.comment_parent_id IS NOT NULL THEN 
     SELECT comment_date INTO date_parent FROM comment_view WHERE comment_id = :NEW.comment_parent_id; 
    END IF; 

    SELECT article_date INTO date_article FROM article WHERE article_id = :NEW.comment_article_id; 

    IF :NEW.comment_date > SYSTIMESTAMP THEN 
     RAISE_APPLICATION_ERROR(-20003, '...'); 
    ELSIF :NEW.comment_date < date_article THEN 
     RAISE_APPLICATION_ERROR(-20005, '...'); 
    ELSIF :NEW.comment_date < date_parent THEN 
     RAISE_APPLICATION_ERROR(-20006, '...'); 
    END IF; 

END; 

Пожалуйста, обратите внимание в любом случае, что такого рода программирование считается Неправильная практика: взгляните на Fix Oracle mutating trigger table errors

+1

Да, я уже нашел точно такое же решение, может быть, около 5 минут назад. Кажется, он работает. Спасибо. – KRiSTiN

Смежные вопросы