20

在 Oracle 数据库中,以下各项有什么区别:

  • 用户()
  • sys_context('USERENV', 'CURRENT_USER')
  • sys_context('USERENV', 'SESSION_USER')

这些是否也可能与“当前用户”相关的值?

  • sys_context('USERENV', 'CURRENT_SCHEMA')
  • sys_context('USERENV', 'AUTHENTICATED_IDENTITY')

我特别感兴趣的是哪些可以更改,哪些可以更改,哪些不能更改值,哪些根据连接类型具有不同的值,哪些始终是用于登录的模式数据库。

在我的大多数测试中,这些值总是相同的。唯一的例外是在运行以下命令来更改“CURRENT_SCHEMA”时:

alter session set current_schema=<SCHEMA>

执行以下操作会导致错误:

alter session set current_user=<USER> --even as sys/system, which is good I suppose

因此,所有这些都存在某种安全/规则。但是,拥有 SESSION_USER 和 CURRENT_USER 背后一定有一些原因。我还认为 user() 可能是 sys_context('USERENV', 'CURRENT_USER') 的快捷方式,但我找不到有关此事的文档。

4

5 回答 5

17

来自手册:http ://docs.oracle.com/cd/E11882_01/server.112/e26088/functions184.htm#SQLRF51825

当前用户

权限当前处于活动状态的数据库用户的名称。这可能会在会话期间发生变化,以反映任何活动定义者权利对象的所有者。当没有定义者的权限对象处于活动状态时,CURRENT_USER 返回与 SESSION_USER 相同的值。当直接在视图定义的主体中使用时,这将返回正在执行正在使用视图的光标的用户;它不尊重游标中使用的视图作为定义者的权利。

SESSION_USER

登录时数据库用户的名称。对于企业用户,返回架构。对于其他用户,返回数据库用户名。该值在整个会话期间保持不变。

因此 SESSION_USER 和 CURRENT_USER 之间存在差异,尤其是当 CURRENT_USER 用于存储过程或函数时。

我不得不承认我不知道“企业用户”这个词是什么意思。

顺便说一句:还有第三个:

SESSION_USERID

登录时数据库用户的标识符。

于 2012-06-12T21:30:41.283 回答
3

sys_context('USERENV', 'CURRENT_SCHEMA')- 当前正在使用的模式以及您已经发现的模式可以更改为alter session

sys_context('USERENV', 'SESSION_USER')- 在创建会话期间用于身份验证的用户,不能更改

sys_context('USERENV', 'CURRENT_USER')-很像“session_user”已弃用(至少根据10g 文档
(根据@a_horse_with_no_name 的回答和他对11g 文档的参考进行编辑)

sys_context('USERENV', 'AUTHENTICATED_IDENTITY')- 用于身份验证的身份取决于“AUTHENTICATION_METHOD”。
来自文档

  • Kerberos 认证的企业用户:kerberos 主体名称
  • Kerberos 认证的外部用户:kerberos 主体名称;与架构名称相同
  • SSL认证企业用户:用户PKI证书中的DN
  • SSL认证的外部用户:用户PKI证书中的DN
  • 密码认证企业用户:昵称;与登录名相同
  • 密码认证的数据库用户:数据库用户名;与架构名称相同
  • OS-authenticated external user:外部操作系统用户名
  • Radius/DCE 认证的外部用户:模式名称
  • 带 DN 的代理:客户端的 Oracle Internet Directory DN
  • 带证书的代理:客户端的证书 DN
  • Proxy with username:如果客户端是本地数据库用户,则为数据库用户名;如果客户端是企业用户,则为昵称。
  • SYSDBA/SYSOPER 使用密码文件:登录名
  • SYSDBA/SYSOPER 使用 OS 认证:操作系统用户名

user pseudo column- 我不确定,根据文件我认为它就像CURRENT_SCHEMA但显然它就像CURRENT_USER

于 2012-06-12T21:01:39.440 回答
3

USER在使用PL/SQL中的函数时需要考虑一个重要的注意事项。正如我在这篇博文中所记录的那样STANDARD.USER()实现如下:

function USER return varchar2 is
c varchar2(255);
begin
    select user into c from sys.dual;
    return c;
end;

因此,它委托给userSQL 引擎中的评估,这会导致隐藏的 PL/SQL 到 SQL 上下文切换。如果您经常这样做,例如在触发器中,那么这在生产系统中可能会非常有害。尽量避免USER()从 PL/SQL 调用,sys_context('USERENV', 'SESSION_USER')而是使用。

于 2019-04-10T07:53:16.900 回答
2

CURRENT_SCHEMA是如果您命名一个对象而不指定其所有者将假定的架构。例如,如果 myCURRENT_SCHEMASCOTT,则SELECT * FROM EMP与 相同SELECT * FROM SCOTT.EMP。默认情况下,当我第一次连接到 Oracle 时,CURRENT_SCHEMA它​​与 CURRENT_USER 相同。

但是,如果我连接为SCOTT,我可以发出ALTER SESSION SET CURRENT_SCHEMA=JOE,然后当我这样做时SELECT * FROM EMP,它被解释为JOE.EMP而不是SCOTT.EMP。当然,如果我没有SELECT权限JOE.EMP,或者JOE没有名为 的对象EMPSELECT则将失败。

于 2017-07-03T15:44:32.120 回答
1

USER 和使用 sys_context 之间也存在性能差异

declare 
  v_result varchar2(100);
begin
  for i in 1..1000000 loop
  v_result := sys_context('userenv','session_user');
  end loop;
end;
/

-- 2.5s

declare 
  v_result varchar2(100);
begin
  for i in 1..1000000 loop
  v_result := user;
  end loop;
end;
/ 

-- 47s

另请参阅 https://svenweller.wordpress.com/2016/02/24/sequence-and-audit-columns-with-apex-5-and-12c/http://www.grassroots-oracle.com/2019 /01/oracle-user-vs-sys-context.html

于 2019-01-22T02:37:02.993 回答