上次解说了定义者权限(默认状态)。
总结一下:定义者权限的程序在定义者的权限和模式中执行的。
上次的例子,用户ALLEN执行用户SCOTT的过程(PROC1)时,在那个过程中参照的EMP表不是作为执行者的ALLEN的EMP表,而是定义者的SCOTT的EMP表。
如果想要让用户ALLEN执行户SCOTT的过程(PROC1),参照的是执行者ALLEN的EMP表的话,可以将那个程序设为“执行者权限”。以下就是队一行的方法:(决定执行者权限的方法)。
首先,PROC1过程的定义者和上次一样都是SCOTT,所以在SCOTT中重新定义该过程,但是定义的时候需要指定的是“执行者权限”。请看下面的例子:
–例子开始–
SQL> show user
用户是“SCOTT”。
SQL> CREATE OR REPLACE PROCEDURE PROC1
2 AUTHID CURRENT USER-- ←指定的是执行者权限
3 IS
4 V_ENAME VARCHAR2(20);
5 BEGIN
6 SELECT ENAME INTO V_ENAME FROM EMP WHERE EMPNO = 7934;
7 DBMS_OUTPUT.PUT_LINE(V_ENAME);
8 END;
9 /
程序已创建。
–例子结束–
在上述例子中,第2行制定了改存储过程是执行者权限,用的是“AUTHID CURRENT USER”指定的。
用ALLEN执行一下看看结果:
–执行开始–
SQL>connect ALLEN/allen --用用户ALLEN连接。
SQL>set serveroutput on- -允许显示画面
SQL> EXEC SCOTT.PROC1 – 运行SCOTT.PROC1过程
miller --小写字母“miler” 和上次不同
PL/SQL过程成功完成。
–执行结束
从上边执行的结果可以看出,查询用的是ALLEN的EMP表。
这个存储过程就是“执行权限”。
所以,执行者权限的存储过程最大的好处就是:不同模式(用户)中有结构和表名都相同的表,不同模式(用户)想对该表进行相同的处理的时候,可以用执行者权限。
如果是定义者权限的程序,即使是相同的处理,也需要用各自的模式定义各自的过程。
但是,如果是执行者权限的程序,只需要用一个模式来定义即可,只需要给出执行权限的就可以了,不需要每个模式都有相同内容的过程,这样就简化了管理。
但是,需要注意一个很细的细节:
如果在执行权限的过程中调用子程序(过程、函数等),则该子程序默认为定义者权限的模式。
也就是说,程序和主程序的表是执行者的模式,主程序调用的子程序是定义者的模式。
例子如下:假设SCOTT用户和ALLEN用户分别创建了PROC2程序。
SCOTT的PROC2程序显示SCOTT的消息,ALLEN的PROC2程序显示ALLEN的消息。
SCOTT.PROC1是执行者权限,该过程中调用了“PROC2”过程。
用户ALLEN执行SCOTT.PROC1过程,该过程调用的PROC2过程是ALLEN的PROC2过程还是SCOTT的过程PROC2呢?
根据上边描述,答案是SCOTT的PROC2程序。
因此,应该会显示SCOTT的信息。
马上试试看:
首先,SCOTT用户创建上述PROC2程序。
–例子开始–
SQL> CONNECT SCOTT/tiger
已连接。
SQL> CREATE OR REPLACE PROCEDURE PROC2
2 IS
3 BEGIN
4 DBMS_OUTPUT.PUT_LINE(‘我是SCOTT模式的PROC2程序’);
5 END;
6 /
–例子结束
接下来ALLEN用户也创建PROC2程序。
–例子开始–
SQL> CONNECT Allen/allen
已连接。
SQL> CREATE OR REPLACE PROCEDURE PROC2
2 IS
3 BEGIN
4 DBMS_OUTPUT.PUT_LINE(‘我是ALLEN模式的PROC2程序’);
5 END;
6 /
程序已创建。
–例子结束–
然后,在SCOTT的PROC1过程中追加调用PROC2过程。
–例子开始–
SQL> CONNECT SCOTT/tiger
已连接。
SQL> CREATE OR REPLACE PROCEDURE PROC1
2 AUTHID CURRENT USER --←指定执行者权限
3 IS
4 V_ENAME VARCHAR2(20);
5 BEGIN
6 SELECT ENAME INTO V_ENAME FROM EMP WHERE EMPNO = 7934;
7 DBMS_OUTPUT.PUT_LINE(V_ENAME);
8 PROC2; --←添加呼出子程序的代码
9 END;
10 /
程序已创建。
–例子结束–
我们用用户ALLEN去执行SCOTT.PROC1
–例子开始–
SQL> CONNECT ALLEN/allen
已连接。
SQL> set serveroutput on
SQL> CONNECT ALLEN/allen
已连接。
SQL> SET SERVEROUTPUT ON
SQL> EXECUTE SCOTT.PROC1
miler --小写字母“miler”,EMP表是ALLEN的模式的表
我是SCOTT模式的PROC2程序 --PROC2程序是SCOTT的模式
PL/SQL过程成功完成。
–例子结束–
从上边例子的执行结果来看,主程序是执行者模式,子程序是定义者者模式。
所以结论:子程序没有指定模式时候,默认是定义者的模式,及时主程序制定了执行者模式,子程序也是定义者模式。
本次就是针对执行者权限进行了解释。下一节继续针对执行者权限进行进一步说明。