表更改后 Oracle SQL 过程变得无效
Posted
技术标签:
【中文标题】表更改后 Oracle SQL 过程变得无效【英文标题】:Oracle SQL procedure getting invalid after table alter 【发布时间】:2021-08-25 05:55:28 【问题描述】:当试图改变一个表时,只有选择语句的过程之一变得无效。 表格脚本:
create table t1(a number,b number);
create or replace procedure p1
is
x number;
y number;
begin
select a,b into x,y from t1;
end;
/
create or replace procedure p2(i number)
is
x number;
y number;
begin
select a,b into x,y from t1 where i=1;
end;
/
alter table t1 add (d number);
select object_name,status from dba_objects where object_name in ('T','P1','P2');
T VALID
P1 VALID
P2 INVALID
观察到,当过程接受参数时,如果我们在 select 语句中使用它,对象就会变得无效,否则它不会变得无效。
是否可以在程序无效的情况下更改表?
【问题讨论】:
this 有帮助吗? 【参考方案1】:实际上,您的对象并非真的无效。当您的第二个过程包含一个 where 子句,该子句根据规则在字典中产生无效时,就会出现此问题。
如果您运行该程序,它将自动生效。
演示
甲骨文 19c
SQL> alter session set current_schema=test1 ;
Session altered.
SQL> create table t1(a number,b number);
Table created.
SQL> create or replace procedure p1
is
x number;
y number;
begin
select a,b into x,y from t1;
end;
/ 2 3 4 5 6 7 8
Procedure created.
SQL> create or replace procedure p2(i number)
is
x number;
y number;
begin
select a,b into x,y from t1 where i=1;
end;
/
2 3 4 5 6 7 8
Procedure created.
SQL> alter table t1 add (d number);
Table altered.
SQL> select object_name,status from dba_objects where object_name in ('T1','P1','P2') and owner='TEST1' ;
OBJECT_NAME STATUS
------------------------- --------------------
P1 VALID
P2 INVALID
T1 VALID
现在,如果程序确实无效,您将无法执行它。让我们在您的表中插入一行并尝试运行它。
SQL> insert into t1 values ( 1 ,1 ,1) ;
1 row created.
SQL> commit ;
Commit complete.
SQL> set serveroutput on
SQL> exec p2 ( i=>1 ) ;
PL/SQL procedure successfully completed.
SQL> select object_name,status from dba_objects where object_name in ('T','P1','P2') and owner='TEST1' ;
OBJECT_NAME STATUS
------------------------- --------------------
P1 VALID
P2 VALID
T1 VALID
有一些内部规则定义了字典中对象的失效,例如过程、函数或包,当它们所依赖的对象发生某些更改时。
在这种特定情况下,并没有真正的失效,因为对象只是在执行 DDL 后在字典中被标记为无效。
第一个不是无效的原因是因为它不包含任何where子句,而只是检索两个现有的列。第二个变得无效,因为它包含 PLSQL 变量的 where 子句。见下文
https://docs.oracle.com/cd/E24693_01/appdev.11203/e17125/adfns_dependencies.htm#CHDJIIFC
【讨论】:
感谢 roberto 的清晰解释但我们被卡住了,因为我们的对象被高度访问,并且可能在部署期间导致库缓存锁定library cache lock
是什么意思?那些不是真的无效的对象,一旦你执行它们就会变得有效。,以上是关于表更改后 Oracle SQL 过程变得无效的主要内容,如果未能解决你的问题,请参考以下文章