Oracle ORA-04068中经常出现错误:已丢弃现有的包状态

时间:2009-11-19 07:49:26

标签: sql oracle oracle10g

我们每天在每两个小时运行一次的脚本上收到此错误,但是在一天的不同时间。

ERROR at line 1:
ORA-04068: existing state of packages has been discarded
ORA-04061: existing state of package body "PACKAGE.NAME" has been
invalidated
ORA-06508: PL/SQL: could not find program unit being called:
"PACKAGE.NAME"
ORA-06512: at line 1

有人列出可能导致此错误的条件,以便我们进行调查吗?

感谢。

更新:  执行'ALTER SESSION CLOSE DATABASE LINK DBLINK'会使包的状态无效吗?

5 个答案:

答案 0 :(得分:14)

包中包含公共或私有变量。 (对吗?)这个变量构成了包的状态。如果您在第3个会话中编译包。下一次访问此包将抛出ORA-04068。

程序包的构建时间戳必须早于程序包会话状态。

如果脚本运行不需要包状态,则在脚本开头调用DBMS_SESSION.RESET_PACKAGE。这会清除会话的所有包状态。

答案 1 :(得分:13)

这一个班轮实际上解决了所有问题:

PRAGMA SERIALLY_REUSABLE;

确保您的全局变量无状态以避免任何问题。

答案 2 :(得分:4)

您还可以查看dba_dependenciesuser_dependencies

select *
from dba_dependencies
where name = 'YOUR_PACKAGE'
and type = 'PACKAGE' --- or 'PACKAGE_BODY'
and owner = USER --- or USERNAME

这将为您提供包依赖的对象。检查那里发生的事情。

答案 3 :(得分:1)

我们曾多次遇到过这个问题,我们正在编译架构以暂时解决此问题。过了几天我们一直在寻找永久性的解决方案。

我们在下面的查询中发现了同义词中的时间戳差异。我们重新编译同义词,它工作!已经快一周了,到目前为止我们没有任何问题。以下是在我们的案例中有帮助的查询。

**

select do.obj# d_obj,do.name d_name, do.type# d_type, po.obj# p_obj,po.name p_name,
to_char(p_timestamp,'DD-MON-YYYY HH24:MI:SS') "P_Timestamp",
to_char(po.stime ,'DD-MON-YYYY HH24:MI:SS') "STIME", 
decode(sign(po.stime-p_timestamp),0,'SAME','*DIFFER*') X 
from sys.obj$ do, sys.dependency$ d, sys.obj$ po
where P_OBJ#=po.obj#(+) and D_OBJ#=do.obj# 
and do.status=1 /*dependent is valid*/ 
and po.status=1 /*parent is valid*/ 
and po.stime!=p_timestamp /*parent timestamp not match*/ 
order by 2,1;

**

我希望这可以帮助那些可能遇到此问题的人。

答案 4 :(得分:0)

您似乎正在对对象进行更改,导致其他对象无效。例如,删除索引可能会将所有依赖于该表的包置于无效状态。它可以具有级联效应。如果程序包无效,则依赖于程序包的函数和使用该函数的视图可能会变为无效。尝试在每次DDL查询后重新编译所有对象。