外部认证
如果用户可以直接连接到操作系统,在创建用户时可以指定用户不通过口令,而是通过外部系统认证的方式登录到数据库。
在Windows操作系统中,可以通过修改注册表来实现外部认证。
如果是Oracle 9i版本,需要在HKEY_LOCAL_MACHINE\SOFTWARE\ORACLE\HOME0(根据你的安装命名有可能不同)下面添加字符串键名OSAUTH_PREFIX_DOMAIN,键值设为FALSE;如果是Oracle 10g版本,需要在HKEY_LOCAL_MACHINE\SOFTWARE\ ORACLE\KEY_OraDb10g_home1(根据你的安装命名有可能不同)下面添加字符串键名OSAUTH_PREFIX_DOMAIN,键值设为FALSE。
然后可以通过如下方式创建用户:
SQL> create user ops$eygle identified externally default tablespace users; 用户已创建。 SQL> grant connect to ops$eygle; 授权成功。
这样用户在登录时就不需要显示的输入口令:
SQL> connect / 已连接。 SQL> show user USER 为 "OPS$EYGLE"
这里的OPS$前缀是为了兼容以前版本保留的:
SQL> show parameter os_authent_prefix NAME TYPE VALUE ------------------------------------ ----------- ------------------------------ os_authent_prefix string OPS$
可以将这个前缀设为空值以使用户名更加简单单纯:
SQL> alter system set os_authent_prefix='' scope=spfile; 系统已更改。
在重新启动数据库之后,我们可以创建单纯的外部认证用户:
SQL> create user eygle identified externally default tablespace users; 用户已创建。 SQL> grant connect to eygle; 授权成功。 SQL> select username,password from dba_users where username='EYGLE'; USERNAME PASSWORD ------------------------------ ------------------------------ EYGLE EXTERNAL
此时用新创建的用户连接数据库:
SQL> connect / 已连接。 SQL> show user USER 为 "EYGLE"
如果不再需要使用操作系统认证,可以通过如下命令将用户修改为使用数据库口令认证:
SQL> alter user eygle identified by eygle; 用户已更改。 SQL> connect / ERROR: ORA-01017: invalid username/password; logon denied 警告: 您不再连接到 ORACLE。 SQL> connect eygle/eygle 已连接。
值得注意的是REMOTE_OS_AUTHENT应该被设置为FALSE以防止远程系统认证用户的登录:
SQL> alter system set remote_os_authent=false scope=spfile; 系统已更改。
在Linux/UNIX上由于不存在注册表,设置就更为简单:
SQL> alter system set os_authent_prefix='' scope=spfile; System altered. SQL> startup force; ORACLE instance started. SQL> create user oracle identified externally; User created. SQL> grant connect to oracle; Grant succeeded. SQL> select username,password from dba_users where username='ORACLE'; USERNAME PASSWORD ------------------------------ ------------------------------ ORACLE EXTERNAL SQL> connect / Connected. SQL> show user USER is "ORACLE"
SYS用户行为审计
在很多情况下,可能我们希望审计数据库用户的行为,以便在出现安全问题时能够快速判断,封堵漏洞,保障安全,SYS用户作为一个超级用户,其操作安全尤为重要。
在Oracle 10gR2中,缺省的在audit_file_dest目录会记录SYS用户的登录审计信息,但是并不审计操作内容:
SQL> select * from v$version where rownum <2; BANNER ---------------------------------------------------------------- Oracle Database 10g Enterprise Edition Release 10.2.0.4.0 - 64bi SQL> show parameter audit NAME TYPE VALUE ------------------------------------ ----------- ------------------------------ audit_file_dest string /opt/oracle/admin/rac/adump audit_sys_operations boolean FALSE audit_syslog_level string audit_trail string NONE SQL> select a.spid "Process ID",b.sid "Session ID" from v$process a,v$session b 2 where a.ADDR=b.PADDR 3 and b.SID= (select sid from v$mystat where rownum = 1); Process ID Session ID ------------ ---------- 26549 133 SQL> ! more /opt/oracle/admin/rac/adump/ora_26549.aud Audit file /opt/oracle/admin/rac/adump/ora_26549.aud Oracle Database 10g Enterprise Edition Release 10.2.0.4.0 - 64bit Production With the Partitioning, Real Application Clusters, Data Mining and Real Application Testing options ORACLE_HOME = /opt/oracle/product/10.2.0/db10g System name: SunOS Node name: db210-rac2.eygle.com Release: 5.9 Version: Generic_117171-12 Machine: sun4u Instance name: rac2 Redo thread mounted by this instance: 2 Oracle process number: 31 Unix process pid: 26549, image: oracle@db210-rac2.eygle.com (TNS V1-V3) Sun Nov 21 17:45:51 2010 LENGTH : '137' ACTION :[7] 'CONNECT' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[6] 'oracle' CLIENT TERMINAL:[5] 'pts/1' STATUS:[1] '0'
缺省的审计信息很简略,而audit_sys_operations参数可以帮助实现SYS用户的行为审计,这个参数是静态参数,设置后重启数据库生效:
SQL> alter system set audit_sys_operations=true scope=spfile; System altered. SQL> shutdown immediate; SQL> startup SQL> show parameter audit NAME TYPE VALUE ------------------------------------ ----------- ------------------------------ audit_file_dest string /opt/oracle/admin/rac/adump audit_sys_operations boolean TRUE audit_syslog_level string audit_trail string NONE
现在重新登陆一个SYS会话,看看审计信息会记录哪些内容:
$ sqlplus '/ as sysdba' SQL*Plus: Release 10.2.0.4.0 - Production on Sun Nov 21 17:53:30 2010 Copyright (c) 1982, 2007, Oracle. All Rights Reserved. 首先查询得到进程号信息: SQL> select a.spid "Process ID",b.sid "Session ID" from v$process a,v$session b 2 where a.ADDR=b.PADDR 3 and b.SID= (select sid from v$mystat where rownum = 1); Process ID Session ID ------------ ---------- 605 149 创建测试表,并执行insert/delete等操作 SQL> create table eygle as select * from dba_users; Table created. SQL> insert into eygle select * from dba_users; 13 rows created. SQL> delete from eygle; 26 rows deleted. SQL> commit; Commit complete. 查看审计文件 SQL> ! more /opt/oracle/admin/rac/adump/ora_605.aud Audit file /opt/oracle/admin/rac/adump/ora_605.aud Oracle Database 10g Enterprise Edition Release 10.2.0.4.0 - 64bit Production With the Partitioning, Real Application Clusters, Data Mining and Real Application Testing options ORACLE_HOME = /opt/oracle/product/10.2.0/db10g System name: SunOS Node name: db210-rac2.eygle.com Release: 5.9 Version: Generic_117171-12 Machine: sun4u Instance name: rac2 Redo thread mounted by this instance: 2 Oracle process number: 19 Unix process pid: 605, image: oracle@db210-rac2.eygle.com (TNS V1-V3) 注意,SYS用户现在所有的操作都被详细记录下来 Sun Nov 21 17:53:30 2010 LENGTH : '137' ACTION :[7] 'CONNECT' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[6] 'oracle' CLIENT TERMINAL:[5] 'pts/1' STATUS:[1] '0' Sun Nov 21 17:53:51 2010 LENGTH : '282' ACTION :[150] 'select a.spid "Process ID",b.sid "Session ID" from v$process a,v$session b where a.ADDR=b.PADDR and b.SID= (select sid from v$mystat where rownum = 1)' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[6] 'oracle' CLIENT TERMINAL:[5] 'pts/1' STATUS:[1] '0' Sun Nov 21 17:54:03 2010 LENGTH : '176' ACTION :[45] 'create table eygle as select * from dba_users' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[6] 'oracle' CLIENT TERMINAL:[5] 'pts/1' STATUS:[1] '0' Sun Nov 21 17:54:13 2010 LENGTH : '172' ACTION :[41] 'insert into eygle select * from dba_users' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[6] 'oracle' CLIENT TERMINAL:[5] 'pts/1' STATUS:[1] '0' Sun Nov 21 17:54:16 2010 LENGTH : '148' ACTION :[17] 'delete from eygle' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[6] 'oracle' CLIENT TERMINAL:[5] 'pts/1' STATUS:[1] '0' Sun Nov 21 17:54:18 2010 LENGTH : '136' ACTION :[6] 'commit' DATABASE USER:[1] '/' PRIVILEGE :[6] 'SYSDBA' CLIENT USER:[6] 'oracle' CLIENT TERMINAL:[5] 'pts/1' STATUS:[1] '0'
用户行为审计与FGA
在Oracle 10g中,审计功能是非常易用和强大的,我们可以通过数据库的审计功能灵活的审计数据库中重要的数据信息访问。
审计功能缺省是关闭的,可以通过设置AUDIT_TRAIL来启用,这个参数是静态参数,修改后需要重新启动数据库。
AUDIT_TRAIL支持几个参数是:
AUDIT_TRAIL = { none | os | db | db,extended | xml | xml,extended }
None / false - 禁用审计.
db or true - 启用审计功能,审计信息记录在数据库表SYS.AUD$中。
db,extended - 扩展DB审计功能,SQL_BIND 和 SQL_TEXT 同时被记录.
xml- 启用审计,并使用XML格式记录操作系统级审计文件
xml,extended - 扩展XML审计,记录SQL_BIND 和 SQL_TEXT 信息.
os- 启用审计,审计信息直接记录在操作系统审计文件中
注意,如果使用AUD$存放审计信息,可能会导致SYSTEM表空间使用快速增长,一般建议对空间使用进行控制或者对存储表空间进行分离。
SQL> ALTER SYSTEM SET audit_trail=db SCOPE=SPFILE; System altered. SQL> shutdown immediate; SQL> startup
创建测试用户:
SQL> create user eygle identified by eygle; User created. SQL> grant connect,resource to eygle; Grant succeeded.
设置用户审计,审计SELECT/INSERT/UPDATE/DELETE等操作及其他用户希望审计的内容:
SQL> audit all by eygle by access; Audit succeeded. SQL> audit select table,update table,insert table,delete table by eygle by access; Audit succeeded. SQL> audit execute procedure by eygle by access; Audit succeeded.
接下来使用EYGLE用户执行一系列的操作:
SQL> connect eygle/eygle Connected. SQL> create table eygle as select * from dict; Table created. SQL> insert into eygle select * from dict where rownum <9; 8 rows created. SQL> commit; Commit complete. SQL> delete from eygle where rownum <11; 10 rows deleted. SQL> commit; Commit complete. SQL> drop table eygle purge; Table dropped.
这些操作将被审计记录,查询dba_audit_trail视图可以获得这些审计信息;
SQL> SELECT username,extended_timestamp,owner,obj_name,action_name 2 FROM dba_audit_trail WHERE owner = 'EYGLE' ORDER BY timestamp; USERNAME EXTENDED_TIMESTAMP OWNER OBJ_NAME ACTION_NAME ---------- ----------------------------------- ---------- ------------------------------ ---------------------------- EYGLE 21-NOV-10 08.13.13.409020 PM +08:00 EYGLE EYGLE CREATE TABLE EYGLE 21-NOV-10 08.13.13.410456 PM +08:00 EYGLE from$_subquery$_011 SELECT EYGLE 21-NOV-10 08.13.13.411143 PM +08:00 EYGLE from$_subquery$_004 SELECT EYGLE 21-NOV-10 08.13.26.491018 PM +08:00 EYGLE EYGLE CREATE TABLE EYGLE 21-NOV-10 08.13.40.987887 PM +08:00 EYGLE EYGLE INSERT EYGLE 21-NOV-10 08.13.57.095641 PM +08:00 EYGLE EYGLE DELETE EYGLE 21-NOV-10 08.14.07.876233 PM +08:00 EYGLE EYGLE DROP TABLE
这里值得注意的是,DBA_AUDIT_TRAIL基于底层表AUD$建立,由于AUD$表缺省的建立于SYSTEM表空间,其使用空间可能快速扩展占用大量存储,所以在使用AUDIT特性时,应该考虑将其迁移出SYSTEM表空间,或者定期归档清理审计数据。
在$ORACLE_HOME\rdbms\admin\cataudit.sql中,可以找到创建DBA_AUDIT_TRAIL的详细语句(11g中,AUD$表的创建语法可以在dsec.bsq文件中找到),以下是概要信息:
create or replace view DBA_AUDIT_TRAIL (OS_USERNAME, USERNAME,USERHOST,TERMINAL,TIMESTAMP,OWNER,OBJ_NAME,ACTION,ACTION_NAME, NEW_OWNER,NEW_NAME,OBJ_PRIVILEGE,SYS_PRIVILEGE,ADMIN_OPTION,GRANTEE,AUDIT_OPTION, SES_ACTIONS,LOGOFF_TIME,LOGOFF_LREAD,LOGOFF_PREAD,LOGOFF_LWRITE,LOGOFF_DLOCK, COMMENT_TEXT,SESSIONID,ENTRYID,STATEMENTID,RETURNCODE,PRIV_USED,CLIENT_ID,ECONTEXT_ID, SESSION_CPU,EXTENDED_TIMESTAMP,PROXY_SESSIONID,GLOBAL_UID,INSTANCE_NUMBER,OS_PROCESS, TRANSACTIONID,SCN,SQL_BIND,SQL_TEXT,OBJ_EDITION_NAME,DBID ) as select spare1 /* OS_USERNAME */, userid /* USERNAME */, userhost /* USERHOST */, terminal /* TERMINAL */, cast ( /* TIMESTAMP */ (from_tz(ntimestamp#,'00:00') at local) as date), obj$creator /* OWNER */, obj$name /* OBJECT_NAME */, aud.action# /* ACTION */, act.name /* ACTION_NAME */, new$owner /* NEW_OWNER */, new$name /* NEW_NAME */, decode(aud.action#, 108 /* grant sys_priv */, null, 109 /* revoke sys_priv */, null, 114 /* grant role */, null, 115 /* revoke role */, null, auth$privileges) /* OBJ_PRIVILEGE */, decode(aud.action#, 108 /* grant sys_priv */, spm.name, 109 /* revoke sys_priv */, spm.name, null) /* SYS_PRIVILEGE */, decode(aud.action#, 108 /* grant sys_priv */, substr(auth$privileges,1,1), 109 /* revoke sys_priv */, substr(auth$privileges,1,1), 114 /* grant role */, substr(auth$privileges,1,1), 115 /* revoke role */, substr(auth$privileges,1,1), null) /* ADMIN_OPTION */, auth$grantee /* GRANTEE */, decode(aud.action#, 104 /* audit */, aom.name, 105 /* noaudit */, aom.name, null) /* AUDIT_OPTION */, ses$actions /* SES_ACTIONS */, cast((from_tz(cast(logoff$time as timestamp),'00:00') at local) as date) /* LOGOFF_TIME */, logoff$lread /* LOGOFF_LREAD */, logoff$pread /* LOGOFF_PREAD */, logoff$lwrite /* LOGOFF_LWRITE */, decode(aud.action#, 104 /* audit */, null, 105 /* noaudit */, null, 108 /* grant sys_priv */, null, 109 /* revoke sys_priv */, null, 114 /* grant role */, null, 115 /* revoke role */, null, aud.logoff$dead) /* LOGOFF_DLOCK */, comment$text /* COMMENT_TEXT */, sessionid /* SESSIONID */, entryid /* ENTRYID */, statement /* STATEMENTID */, returncode /* RETURNCODE */, spx.name /* PRIVILEGE */, clientid /* CLIENT_ID */, auditid /* ECONTEXT_ID */, sessioncpu /* SESSION_CPU */, from_tz(ntimestamp#,'00:00') at local, /* EXTENDED_TIMESTAMP */ proxy$sid /* PROXY_SESSIONID */, user$guid /* GLOBAL_UID */, instance# /* INSTANCE_NUMBER */, process# /* OS_PROCESS */, xid /* TRANSACTIONID */, scn /* SCN */, to_nchar(substr(sqlbind,1,2000)) /* SQL_BIND */, to_nchar(substr(sqltext,1,2000)) /* SQL_TEXT */, obj$edition /* OBJ_EDITION_NAME */, dbid /* DBID */ from sys.aud$ aud, system_privilege_map spm, system_privilege_map spx, STMT_AUDIT_OPTION_MAP aom, audit_actions act where aud.action# = act.action (+) and - aud.logoff$dead = spm.privilege (+) and aud.logoff$dead = aom.option# (+) and - aud.priv$used = spx.privilege (+) /
以下是一个产品数据库中的案例情况,缺省的AUD$存储于SYSTEM表空间,经过使用扩展该对象已经占用了2.5G的存储空间:
SQL> select * from v$version; BANNER -------------------------------------------------------------------------------- Oracle Database 11g Enterprise Edition Release 11.2.0.2.0 - 64bit Production PL/SQL Release 11.2.0.2.0 - Production CORE 11.2.0.2.0 Production TNS for Linux: Version 11.2.0.2.0 - Production NLSRTL Version 11.2.0.2.0 - Production SQL> select segment_name,bytes/1024/1024/1024 GB,tablespace_name from dba_segments 2 where segment_name='AUD$'; SEGMENT_NAME GB TABLESPACE_NAME -------------------- ---------- ------------------------------ AUD$ 2.5 SYSTEM SQL> select index_name from dba_indexes where table_name='AUD$'; INDEX_NAME ------------------------------ SYS_IL0000000376C00040$$ SYS_IL0000000376C00041$$
在相关查询中,可以看到AUD$表的全表扫描可能严重影响查询性能:
SQL> select count(*) from dba_audit_trail; COUNT(*) ---------- 13485723 Execution Plan ----------------------------------------------------------------------------------------------------- | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time | ----------------------------------------------------------------------------------------------------- | 0 | SELECT STATEMENT | | 1 | 27 | 90257 (2)| 00:18:04 | | 1 | SORT AGGREGATE | | 1 | 27 | | | |* 2 | HASH JOIN RIGHT OUTER | | 13M| 347M| 90257 (2)| 00:18:04 | | 3 | INDEX FAST FULL SCAN | I_STMT_AUDIT_OPTION_MAP | 249 | 996 | 2 (0)| 00:00:01 | |* 4 | HASH JOIN RIGHT OUTER | | 13M| 295M| 90135 (2)| 00:18:02 | | 5 | INDEX FULL SCAN | I_SYSTEM_PRIVILEGE_MAP | 206 | 1030 | 1 (0)| 00:00:01 | |* 6 | HASH JOIN RIGHT OUTER | | 13M| 231M| 90015 (2)| 00:18:01 | | 7 | INDEX FULL SCAN | I_SYSTEM_PRIVILEGE_MAP | 206 | 1030 | 1 (0)| 00:00:01 | |* 8 | HASH JOIN RIGHT OUTER| | 13M| 167M| 89894 (2)| 00:17:59 | | 9 | INDEX FULL SCAN | I_AUDIT_ACTIONS | 180 | 720 | 1 (0)| 00:00:01 | | 10 | TABLE ACCESS FULL | AUD$ | 13M| 115M| 89774 (2)| 00:17:58 | ----------------------------------------------------------------------------------------------------- Statistics ---------------------------------------------------------- 899 recursive calls 769 db block gets 328252 consistent gets 327603 physical reads 106624 redo size 1 rows processed
AUD$对象的内容可以直接Delete或Truncate来清理,其存储空间转移可以通过类似如下步骤进行,如将其移动至SYSAUX表空间(注意编译因此失效的数据库对象):
create table audx tablespace "SYSAUX" as select * from aud$ where 1 = 2 / rename AUD$ to AUD$$ / rename audx to aud$ /
在Oracle 10g之后,Oracle提供了一个内置的功能,可以用于调整审计日志存储位置,通过DBMS_AUDIT_MGMT.SET_AUDIT_TRAIL_LOCATION可以实现迁移。
SQL> truncate table aud$; --可以根据需要选择是否清理历史数据 Table truncated. SQL> select count(*) from aud$; COUNT(*) ---------- 0 SQL> exec DBMS_AUDIT_MGMT.SET_AUDIT_TRAIL_LOCATION(1,'SYSAUX'); PL/SQL procedure successfully completed. SQL> col segment_name for a30 SQL> select segment_name,bytes,tablespace_name from dba_segments where segment_name='AUD$'; SEGMENT_NAME BYTES TABLESPACE_NAME ------------------------------ ---------- ------------------------------ AUD$ 65536 SYSAUX
该过程有两个参数;
PROCEDURE SET_AUDIT_TRAIL_LOCATION Argument Name Type In/Out Default? ------------------------------ ----------------------- ------ -------- AUDIT_TRAIL_TYPE BINARY_INTEGER IN AUDIT_TRAIL_LOCATION_VALUE VARCHAR2 IN
其中AUDIT_TRAIL_TYPE的选项有如下一些:
可以通过定义常量来设定维护范围,以下语句则是将AUD$和FGA_LOG$一并转移:
SQL> BEGIN 2 DBMS_AUDIT_MGMT.SET_AUDIT_TRAIL_LOCATION( 3 audit_trail_type => DBMS_AUDIT_MGMT.AUDIT_TRAIL_DB_STD, 4 audit_trail_location_value => 'USERS'); 5 END; 6 / PL/SQL procedure successfully completed. SQL> select segment_name,tablespace_name 2 from dba_segments where segment_name in ('AUD$','FGA_LOG$'); SEGMENT_NAME TABLESPACE_NAME -------------------------------------------------------- ------------------------------ FGA_LOG$ USERS AUD$ USERS
在进行对象转移之后,需要检查数据库的失效对象,并且通过运行$ORACLE_HOME\rdbms\admin\utlrp.sql来重新编译失效对象。
这里提到的FGA是指Fine Grained Auditing,通过Oracle FGA特性可以对审计功能进行进一步的扩展,FGA使用FGA_LOG$表记录审计信息。
在测试用户下建立测试表:
SQL> connect eygle/eygle Connected. SQL> create table eygle as select * from dict where 1=0; Table created.
使用SYS用户创建FGA策略:
SQL> connect / as sysdba Connected. SQL> BEGIN 2 DBMS_FGA.add_policy( 3 object_schema => 'EYGLE', 4 object_name => 'EYGLE', 5 policy_name => 'AUDIT_EYGLE', 6 audit_condition => NULL, 7 audit_column => 'TABLE_NAME', --如果设置为NULL,则审计所有COLUMN 8 statement_types => 'SELECT,INSERT,UPDATE,DELETE'); 9 END; 10 / PL/SQL procedure successfully completed.
使用测试用户执行一系列的表操作:
SQL> connect eygle/eygle Connected. SQL> insert into eygle select * from dict where rownum <3; 2 rows created. SQL> commit; Commit complete. SQL> delete from eygle where rownum <2; 1 row deleted. SQL> update eygle set table_name='EYGLE' where rownum <2; 1 row updated. SQL> commit; Commit complete. SQL> select * from eygle; TABLE_NAME COMMENTS ------------------------------------- ------------------------------------------- EYGLE Display password limits of the user
使用SYS用户查询审计信息:
SQL> connect / as sysdba Connected. SQL> select sql_text from dba_fga_audit_trail; SQL_TEXT -------------------------------------------------------------------------------- insert into eygle select * from dict where rownum <3 delete from eygle where rownum <2 update eygle set table_name='EYGLE' where rownum <2 select * from eygle
我们可以注意到,所有针对测试表的操作都被记录了下来。
使用SYS用户删除测试策略:
SQL> BEGIN 2 DBMS_FGA.drop_policy( 3 object_schema => 'EYGLE', 4 object_name => 'EYGLE', 5 policy_name => 'AUDIT_EYGLE'); 6 END; 7 / PL/SQL procedure successfully completed.
如果 audit_trail 设置为OS,则审计信息会直接写入操作系统日志,相应的需要设置audit_syslog_level参数。
如下设置两个参数,重启数据库使参数生效:
SQL> ALTER SYSTEM SET AUDIT_TRAIL=OS SCOPE=SPFILE; System altered. SQL> ALTER SYSTEM SET AUDIT_SYSLOG_LEVEL="local1.warning" SCOPE=SPFILE; System altered. SQL> shutdown immediate; SQL> startup
在操作系统上进行必要的设置(测试用例来自Solaris):
bash-2.05# touch /var/log/audit.log bash-2.05# echo "local1.warning /var/log/audit.log" >> /etc/syslog.conf bash-2.05# /etc/init.d/syslog stop bash-2.05# /etc/init.d/syslog start syslog service starting.
接下来在另外一个进程创建会话,执行查询:
$ sqlplus eygle/eygle SQL*Plus: Release 10.2.0.4.0 - Production on Sun Nov 21 21:17:15 2010 Copyright (c) 1982, 2007, Oracle. All Rights Reserved. Connected to: Oracle Database 10g Enterprise Edition Release 10.2.0.4.0 - 64bit Production With the Partitioning, Real Application Clusters, Data Mining and Real Application Testing options SQL> select count(*) from dict; COUNT(*) ---------- 614
在audit.log日志中将记录详细的审计信息:
Nov 21 21:17:12 db210-rac1 Oracle Audit[6440]: [ID 748625 local1.warning] LENGTH: "156" SESSIONID: "70186" ENTRYID: "1" ACTION: "101" RETURNCODE: "0" LOGOFF$PREAD: "92" LOGOFF$LREAD: "2862" LOGOFF$LWRITE: "8" LOGOFF$DEAD: "0" SESSIONCPU: "41" Nov 21 21:17:15 db210-rac1 Oracle Audit[6957]: [ID 748625 local1.warning] LENGTH: "262" SESSIONID:[5] "70187" ENTRYID:[1] "1" STATEMENT:[1] "1" USERID:[5] "EYGLE" USERHOST:[24] "db210-rac1" TERMINAL:[5] "pts/2" ACTION:[3] "100" RETURNCODE:[1] "0" COMMENT$TEXT:[26] "Authenticated by: DATABASE" OS$USERID:[6] "oracle" PRIV$USED:[1] "5" Nov 21 21:17:33 db210-rac1 Oracle Audit[6957]: [ID 748625 local1.warning] LENGTH: "239" SESSIONID:[5] "70187" ENTRYID:[2] "18" STATEMENT:[1] "8" USERID:[5] "EYGLE" USERHOST:[24] "db210-rac1" TERMINAL:[5] "pts/2" ACTION:[1] "3" RETURNCODE:[1] "0" OBJ$CREATOR:[3] "SYS" OBJ$NAME:[4] "OBJ$" OS$USERID:[6] "oracle"
如何切换用户身份
在DBA管理数据库的过程中,经常需要切换为其他用户进行数据库维护,这就需要我们能够进行用户切换。
在Oracle数据库中,可以通过如下方法进行用户身份切换。
(1)通过DBA用户连接数据库,从dba_users视图中查询得到Oracle用户的口令加密串:
SQL> select username,password from dba_users where username='EYGLE'; USERNAME PASSWORD ------------------------------ ------------------------------ EYGLE B726E09FE21F8E83
注意:在Oracle 11g中,已经不能通过如上查询从DBA_USERS试图获得用户口令。
(2)然后可以修改这个用户的口令并连接到数据库:
SQL> alter user eygle identified by welcome; 用户已更改。 SQL> connect eygle/welcome 已连接。
(3)在另外的session中,用DBA用户迅速将用户口令修改回原来的加密串(防止其他用户登录失败):
SQL> alter user eygle identified by values 'B726E09FE21F8E83'; 用户已更改。
(4)此时口令被变更回原口令,尽量缩短以上过程可以最小化数据库影响时间:
SQL> connect eygle/eygle 已连接。
而已经作为该用户连接的身份则可以执行一系列的相关操作了。
通过代理用户(Proxy)连接数据库
如果试图通过其他用户身份登录,上面的方法必须要修改用户口令,在那一瞬登录的用户仍然可能获得口令错误的提示,所以在Oracle 10gR2中,Oracle提供了一个更好的解决方案企业用户代理:Enterprise User Proxy。
也就是说,我们可以创建一个公有代理用户,这个用户可以被用于代理企业用户或其他用户向目标用户切换,这个代理权限通常通过类似以下语句进行授权:
ALTER USER target_user GRANT CONNECT THROUGH proxy_user;
来看一下以下的测试例子:
SQL> connect / as sysdba 已连接。 SQL> create user proxy identified by pproxy; 用户已创建。 SQL> grant connect to proxy; 授权成功。 SQL> alter user eygle grant connect through proxy; 用户已更改。 SQL> connect proxy[eygle]/pproxy 已连接。 SQL> show user USER 为 "EYGLE" SQL> create table eygle (name varchar2(20)); 表已创建。 SQL> select * from session_privs; PRIVILEGE ---------------------------------------- CREATE SESSION UNLIMITED TABLESPACE CREATE TABLE CREATE CLUSTER CREATE SEQUENCE CREATE PROCEDURE CREATE TRIGGER CREATE TYPE CREATE OPERATOR CREATE INDEXTYPE 已选择10行。 SQL> connect proxy/pproxy 已连接。 SQL> select * from session_privs; PRIVILEGE ---------------------------------------- CREATE SESSION
如果读者熟悉UNIX/Linux的话,可能会经常使用sudo(在不同平台中可能需要独立的软件包安装)的方式进行用户身份的切换,类似如下的方式:
[gqgai@eygle gqgai]$ sudo su - Password: [root@eygle root]#
如果用户被授权使用sudo,那么就可以通过如上方式利用sudo和su命令,输入用户自己的口令(不是root用户的口令)切换为root身份。这样就可以将root的口令变更和用户权限分离开来,具有sudo权限的用户无需再知道root的口令,root口令的变更也就无需通知其他用户。
sudo工具的含义为以其他用户的身份执行某个命令:
NAME sudo - execute a command as another user SYNOPSIS sudo -V | -h | -l | -L | -v | -k | -K | -s | [ -H ] [-P ] [-S ] [ -b ] | [ -p prompt ] [ -c class|- ] [ -a auth_type ] [ -u username|#uid ] command DESCRIPTION sudo allows a permitted user to execute a command as the superuser or another user, as specified in the sudoers file.
利用Oracle的这个功能,可以在SQL*Plus中实现类似操作系统中的sudo功能,为此可以创建一个sudo的公用帐号:
SQL> connect / as sysdba 已连接。 SQL> create user sudo identified by proxy; 用户已创建。 SQL> alter user eygle grant connect through sudo; 用户已更改。 SQL> connect sudo[eygle]/proxy 已连接。 SQL> select * from tab; TNAME TABTYPE CLUSTERID ------------------------------ ------- ---------- EYGLE TABLE SQL> select * from eygle; 未选定行 SQL> insert into eygle values('eygle'); 已创建 1 行。 SQL> commit; 提交完成。 SQL> select * from eygle; NAME -------------------- eygle
这种方式为数据库管理和安全提供了极大的便利。