misunderstanding
A reader, October 01, 2001 - 9:49 pm UTC
Tom
We were under the impression that invokers rights allow you to compile and execute a procedure even though the schema creating the procedure or function has privileges over the underlying objects through roles, but not directly.
But your explanation tells us that this is not so.
So this means, if the schema doesnt have direct privileges over say table T, there is no way you can use that object in creating your sub program subprogram.
That is final.
Is it so?
October 02, 2001 - 7:17 am UTC
Invokers rights are compiled
no differently then a definers rights routine, the owner needs to have access to the underlying objects via a direct grant. In this respect, at compile time, invokers and definers rights routines are no different.(i go into this in great detail, with tons of examples and recommandations on how to and how not to use this feature in my book if you are interested. Some 40 pages on this topic alone)
It is only at RUNTIME that the behavior is different. At runtime, an invokers rights routine runs under the invokers rights -- much like an anonymous plsql block (with differences, its not exactly the same).
There is no way using STATIC SQL to create that object, this is true. But if you look at:
</code>
http://asktom.oracle.com/pls/asktom/f?p=100:11:::::P11_QUESTION_ID:1035431863958 <code>
You'll see that you can create a procedure that can access any object the invoker can access. This is what invokers rights routines excell at. Writing generic, reusable utilities that work on unknown sets of data using dynamic sql (either via dbms_sql or using native dynamic sql).
A query on Invoker rights
Anil Pant, January 09, 2005 - 3:27 am UTC
Hello,
In your book Effective Oracle by Desgin on page 586, you say "You flood the Oracle shared pool".
What I understand from this is, similar procedure when invoked by N different users then each will parsed differently (even though the sql statements are same) and each will have their own sql area rather than sharing.
Am I correct ?
January 09, 2005 - 11:46 am UTC
in invokers rights -- the SAME procedure (not similar) is used by many people, but it is AS IF each person had their own copy of the procedure as the SQL is not parsed as the "owner" (as is normal) but rather as "user" or "invoker".
Meaning, a procedure with:
for x in ( select * from emp )
loop
can in fact be accessing totally different EMP tables when you run it versus me running it, or with different security privs or whatever. so you end up with a parsed sql plan PER INVOKER instead of one nice plan to be used by all.
SESSION_USER and CURRENT_USER query
Adrian, January 24, 2005 - 7:21 am UTC
Tom,
I was seeing some strange behaviour with SESSION_USER and CURRENT_USER earlier, so returned to your chapter on Invokers Rights in your first book. I'm seeing no difference between invokers or definers with respect to CURRENT_USER, SESSION_USER or CURRENT_SCHEMA. Could you please comment - it's the bit where I change users that is confusing me.
SQL*Plus: Release 10.1.0.2.0 - Production on Mon Jan 24 12:15:24 2005
Copyright (c) 1982, 2004, Oracle. All rights reserved.
Connected to:
Oracle Database 10g Enterprise Edition Release 10.1.0.2.0 - 64bit Production
With the Partitioning, OLAP and Data Mining options
ABB>
ABB> CREATE OR REPLACE PROCEDURE definer_proc IS
2 BEGIN
3 DBMS_OUTPUT.PUT_LINE( 'Current user=' || sys_context('userenv','current_user') );
4 DBMS_OUTPUT.PUT_LINE( 'Session user=' || sys_context('userenv','session_user') );
5 DBMS_OUTPUT.PUT_LINE( 'Current schema=' || sys_context('userenv','current_schema') );
6 END definer_proc;
7 /
Procedure created.
ABB>
ABB> CREATE OR REPLACE PROCEDURE invoker_proc AUTHID CURRENT_USER IS
2 BEGIN
3 DBMS_OUTPUT.PUT_LINE( 'Current user=' || sys_context('userenv','current_user') );
4 DBMS_OUTPUT.PUT_LINE( 'Session user=' || sys_context('userenv','session_user') );
5 DBMS_OUTPUT.PUT_LINE( 'Current schema=' || sys_context('userenv','current_schema') );
6 END invoker_proc;
7 /
Procedure created.
ABB>
ABB> SELECT object_name, authid
2 FROM user_procedures
3 WHERE object_name LIKE '%PROC';
OBJECT_NAME AUTHID
------------------------------ ------------
INVOKER_PROC CURRENT_USER
DEFINER_PROC DEFINER
ABB>
ABB> exec definer_proc;
Current user=ABB
Session user=ABB
Current schema=ABB
PL/SQL procedure successfully completed.
ABB> exec invoker_proc;
Current user=ABB
Session user=ABB
Current schema=ABB
PL/SQL procedure successfully completed.
ABB>
ABB> GRANT EXECUTE ON definer_proc TO ac;
Grant succeeded.
ABB> GRANT EXECUTE ON invoker_proc TO ac;
Grant succeeded.
ABB>
ABB> conn ac/ac
Connected.
AC>
AC> exec abb.definer_proc;
Current user=AC
Session user=AC
Current schema=AC
PL/SQL procedure successfully completed.
AC> exec abb.invoker_proc;
Current user=AC
Session user=AC
Current schema=AC
PL/SQL procedure successfully completed.
Regards
Adrian
January 24, 2005 - 8:43 am UTC
you should select them from dual
But...
Adrian, January 24, 2005 - 10:01 am UTC
>> you should select them from dual
But surely the advantage of application contexts is that SQL and PL/SQL can use them. Selecting from dual to get the "correct" answer hides an implementation that just wouldn't be obvious to people. For example, I just came along and used the SYS_CONTEXT function in PL/SQL and assumed it should give me the correct answer. Surely many more developers will have made the same "mistake".
Is there a good reason why we would need to select this from dual to have it respond correctly ?
Regards
Adrian
January 24, 2005 - 11:18 am UTC
please take this one up with support - the only way to get behaviour changed is via the mechanism. (eg: i agree with you)
...case sensitive
Adrian, February 21, 2005 - 9:27 am UTC
Tom,
In case you were interested, there is already a bug with this and to get the correct behaviour in PL/SQL, you must use SYS_CONTEXT( 'USERENV', 'CURRENT_USER' ) i.e. capitals. Strange but true.
Regards
Adrian
Ravi, June 08, 2005 - 6:29 pm UTC
Tom I'm schema A and I need to run a procedure in schema B with all roles enabled. How do I do that?
That means I can call an invoker rights procedure in Schema B because I'll have roles disabled.
Should I call a definer rights procedure in Schema B, which in turn calls an invoker rights procedure in Schema B to do this?
June 08, 2005 - 10:18 pm UTC
You cannot.
If you are schema A, you can either:
a) run an invoker rights procedure as you "A" with all of "A"'s roles or
b) run a definer rights preocedure as "B" with "B"'s base privileges
that is all. as soon as you hit that definer rights procedure, the roles are "gone" and you cannot set them on once you hit the Definer Rights procedure.
Ravi, June 08, 2005 - 6:30 pm UTC
To add one bit, my code in procedure that I want to execute is a NDS using execute immediate.
Ravi, June 09, 2005 - 9:46 am UTC
Tom, I should rephrase the Question,
When I have logged on as Schema A and then call a Definer procedure in Schema B. But in Schema B, I want SCHEMA B's roles enabled, because one of its roles gives me a special DCL privliege.
So if this procedure now calls ANOTHER procedure in Schema B which is running as invoker (Authid current_user), while this second procedures run, would I have Schema B's roles enabled.
Important that I dont want Schema A's roles enabled, but Schema B's.
So instead of directly calling a Invoker rights procedure in Schema B (which means I'd have A's roles enabled), I am calling a definer rights first so that my current_user becomes SCHEMAB. Then I call another invoker procedure in Schema B to have Schema B's roles enabled?
June 09, 2005 - 11:21 am UTC
No, i understood what you *want*
I can only say "you cannot get that to happen"
It will not work - once you call the D.R. routine, roles are gone and you are not getting them back.
B needs to have this privilege granted directly to them, not via a role.
Getting the right USER
A reader, June 09, 2005 - 11:36 am UTC
I have a standard definer right stored procedure owned by FOO that references the builtin USER keyword.
If I grant execute to A and A runs it, the USER in the code will return A. If I grant execute to B and B runs it, USER will return B.
How can I refer to the value of the "owner" (definer) of the procedure in the stored procedure code?
Thanks
June 09, 2005 - 6:07 pm UTC
a@ORA9IR2W> create procedure p
2 as
3 begin
4 for x in ( select user u, sys_context('userenv', 'current_schema' ) cs from dual )
5 loop
6 dbms_output.put_line( x.u || ', ' || x.cs );
7 end loop;
8 end;
9 /
Procedure created.
a@ORA9IR2W>
a@ORA9IR2W> grant execute on p to b;
Grant succeeded.
a@ORA9IR2W>
a@ORA9IR2W> @connect b/b
a@ORA9IR2W> set termout off
b@ORA9IR2W> set termout on
b@ORA9IR2W>
b@ORA9IR2W> exec a.p
B, A
PL/SQL procedure successfully completed.
sadf
dfd, September 19, 2010 - 3:47 am UTC
sdaf