捕获到 SQL 异常。错误是:ORA-04098:触发器无效并且重新验证失败

Posted

技术标签:

【中文标题】捕获到 SQL 异常。错误是:ORA-04098:触发器无效并且重新验证失败【英文标题】:A SQL exception was caught. The error was: ORA-04098: trigger is invalid and failed re-validation 【发布时间】:2016-05-12 16:46:55 【问题描述】:

我用下面的代码创建了一个触发器

create or replace trigger DTE_SAVE_ORIGINAL_VAL
after update
on attrvaldesc
FOR Each row
when (new.field2 is null)
Declare
attrvaloriginal attrval.attrval_id%TYPE;
attrval_id attrval.attrval_id%TYPE;
language_id attrvaldesc.language_id%type;
storeent_id attrval.storeent_id%type;
PRAGMA AUTONOMOUS_TRANSACTION;
Begin
Dbms_Output.Put_Line(:OLD.attrval_id);
select attrval_id into attrvaloriginal from attrval where identifier = (select identifier||'_original' from attrval where attrval_id= :OLD.attrval_id and storeent_id=10051) and storeent_id=10051;
if (attrvaloriginal > 0) then
Dbms_Output.Put_Line(attrvaloriginal);
Dbms_Output.Put_Line(:NEW.value);
delete from attrval where attrval_id = attrvaloriginal and storeent_id=10051;
commit;
END IF;
End;

触发器已编译,当我触发更新 attrvaldesc 表的作业时,我面临以下异常

异常信息:

捕获了一个 SQL 异常。错误是:ORA-04098:触发器 'WCS_ADMIN_HFI.DTE_SAVE_ORIGINAL_VAL' 无效并且重新验证失败

堆栈跟踪: com.ibm.commerce.foundation.dataload.exception.DataLoadSQLException:捕获了 SQL 异常。错误是:ORA-04098:触发器“WCS_ADMIN_HFI.DTE_SAVE_ORIGINAL_VAL”无效并且重新验证失败

为了检查我的触发器中是否有任何错误,我做了一个

SHOW ERRORS TRIGGER DTE_SAVE_ORIGINAL_VAL;

我退回了以下

18/1 PLS-00103:遇到符号“DROP”

【问题讨论】:

您的触发器没有“drop” - 您确定加载了正确的版本吗?啊,它也没有 18 行,所以你是把它作为一个更大的脚本的一部分创建的,而只是省略了/ 来执行create trigger?你需要它,因为它是 PL/SQL。 是的,我没有在最后添加 /。让我试试 它现在可以工作了。谢谢亚历克斯!! 【参考方案1】:

您显示的代码不包含“drop”一词。但错误消息也涉及第 18 行。在触发器中,PLS 错误仅涉及 PL/SQL 部分,以declarebegin 开头。您的 PL/SQL 部分只有 16 行,从 declareend;。这表明问题并不完全在于您显示的内容。

据此我们可以推断您已将触发器创建为脚本的一部分,并且下一条语句正在删除一个对象:

create or replace trigger DTE_SAVE_ORIGINAL_VAL
...
End;

drop ...

因为它是 PL/SQL 触发器创建needs to be submitted with a / character。目前,在您的实际触发器之后的所有内容,直到下一次 / 出现在您的脚本中(或脚本的结尾,可能),都被意外地包含在触发器定义中,这意味着它包含的东西不是有效的 PL/SQL。来自包含drop 的错误,但它也可能包含其他语句,删除、创建或更改任意数量的对象。

所以你需要在脚本中的触发器后添加一个斜杠:

create or replace trigger DTE_SAVE_ORIGINAL_VAL
...
End;
/

drop ...

您可以自行重新运行触发器语句,但请记住,它后面的任何内容(意外视为触发器一部分的所有内容)都没有执行,因此您可能会丢失其他对象,或者让它们以与您期望的方式不同的方式构建(如果脚本应该删除然后重新创建对象)。

可能想要修复然后重新运行整个脚本,只要您没有添加任何会破坏的数据 - 如果您现在正在更新数据,很可能会发生这种情况。如果这样做不安全,请查看还有哪些未完成的操作,并手动执行这些部分,再次注意潜在的数据丢失。

【讨论】:

以上是关于捕获到 SQL 异常。错误是:ORA-04098:触发器无效并且重新验证失败的主要内容,如果未能解决你的问题,请参考以下文章

删除oracle 11g用户删除不掉,报ORA-04098错误!

ORA -04098 触发器无效且未通过重新验证

Oracle:新增用户登录提示“ORA-04098:触发器‘GD.ON_LOGON_TRIGGER’无效且未通过重新验证”

ORA-04098: 简单触发器无效。为啥?

oracle 触发器抛出 ora-04098

ORA-04098 trigger 'DBBJ.DB_EV_ALTER_ST_METADATA' is invalid and failed re-validation