一.用户管理
1.公共用户和本地用户
12c+中的用户分为:公共用户和本地用户
公共用户:可以为CDB管理员创建,公共用户是在所有的PDB中都可以使用的用户,公共用户的信息存在CDB$ROOT中,并且存在于所有的PDB中.公共用户需要连到CDB进行创建和管理.在CDB中创建的用户默认就是公共用户,可以省略container=all.在CDB中只能创建公共用户,不能创建本地用户.
本地用户:本地用户只会存储在对应的PDB中.在PDB中创建的用户默认就是本地用户,可以省略container=current.在PDB中只能创建本地用户,不能创建公共用户.
为了区分公共用和本地用户,引进了新的参数common_user_perfix,表示公共用户的前缀.默认为c##,也就是说如果你想创建了一个公共用户,必须带上前缀.此前缀是可以进行修改的,但是建议不要修改.
SQL> show parameter common_userNAME TYPE VALUE------------------------------------ ----------- ------------------------------common_user_prefix string C##
2.创建用户
1).创建公共用户
公共用户只能在CDB$ROOT进行创建和管理.在CDB中创建的用户,默认就为container=all,在创建公共用户的时候,必须指定前缀,否则报错:
SQL> create user suq identified by suq container=all;create user suq identified by suq container=all*ERROR at line 1:ORA-65096: invalid common user or role nameSQL> create user c##suq identified by suq;User created.
在CDB$ROOT中只能创建公共用户,不能创建本地用户,否则报错:
SQL> create user amy identified by amy container=current;create user amy identified by amy container=current*ERROR at line 1:ORA-65049: Creation of local user or role is not allowed in this container.
创建数据库的时候创建的一些系统用户也是公共用户,例如sys,system等,只是他们没有以c##开头,我想可能是为了和以前版本兼容.
2).创建本地用户
先连接到具体的PDB,再进行创建,则创建的就是本地用户,创建本地用户的语法和12c以前的没什么区别,但是创建的本地用户只有在当前PDB中才存在:
SQL> alter session set container=brent;Session altered.SQL> create user amy identified by amy ;User created.
在PDB中不能创建公共用户:
SQL> create user c##carol identified by carol container=all;create user c##carol identified by carol container=all*ERROR at line 1:ORA-65050: Common DDLs only allowed in root.
3.查询用户
在12c中对dba_的数据字典做了修改.如果你处在CDB$ROOT中,如果查询DBA_视图,那么你只能查询到公共的数据字典.如果你处在PDB中,那么你查询DBA_视图只能查到此PDB的数据字典.
12c中新增了CDB_数据字典,可以查看所有的数据字典.
所以,当你在CDB中查询dba_users,那你只能查询到公共的用户,当你处于PDB中,那么你只能查到PDB中的本地用户.
如果你想查询所有的用户,可以使用下的语句,其中新增oracle_maintained字段提示了此用户是否由oracle管理.
select a.username,a.common,a.con_id,decode(a.CON_ID,1,'CDB$ROOT',b.pdb_name) name from cdb_users a,cdb_pdbs b
where a.con_id=b.con_id(+) and oracle_maintained='N'
order by a.con_id,a.username;
SQL> select a.username,a.common,a.con_id,decode(a.CON_ID,1,'CDB$ROOT',b.pdb_name) name from cdb_users a,cdb_pdbs bwhere a.con_id=b.con_id(+) and oracle_maintained='N'order by a.con_id,a.username; 2 3USERNAME COM CON_ID NAME------------------------------ --- ---------- --------------------------------------------------------------------------------------------------------------------------------C##DSG YES 1 CDB$ROOTC##SUQ YES 1 CDB$ROOTAMY NO 3 BRENTC##DSG YES 3 BRENTC##SUQ YES 3 BRENTSUQ NO 3 BRENTC##DSG YES 4 TESTPDB1C##SUQ YES 4 TESTPDB1SUQ NO 4 TESTPDB1C##DSG YES 5 TESTPDB2C##SUQ YES 5 TESTPDB2SUQ NO 5 TESTPDB2C##DSG YES 7 TESTPDB3C##SUQ YES 7 TESTPDB3SUQ NO 7 TESTPDB3
5.修改用户
修改用户密码和上面创建的思想一样,公共用户只能在CDB$ROOT中进行修改.本地用户只能在PDB中进行修改:
SQL> alter user c##suq identified by suq2;User altered.
6.删除用户
和上面的思想一样:
SQL> drop user c##suq cascade;User dropped.
二.权限管理
1)本地授权
在PDB内部的授权为本地授权.本地授权和以前的授权方法几乎一样.额外的,我们可以在PDB中对公共用户进行授权.也就是说公共用户虽然在所有PDB中都存在这个用户,并不是说你创建了公共用户,他就有权限访问所有PDB,
需要单独赋予create session 权限.
例如我们创建一个公共用户,刚创建玩的用户是没有登录权限的:
SQL> create user c##suq identified by suq;User created.SQL> show pdbs;CON_ID CON_NAME OPEN MODE RESTRICTED---------- ------------------------------ ---------- ----------2 PDB$SEED READ ONLY NO3 BRENT READ WRITE NO4 TESTPDB1 READ WRITE NO5 TESTPDB2 READ WRITE NO7 TESTPDB3 READ WRITE NOSQL>SQL> show con_nameCON_NAME------------------------------CDB$ROOTSQL> conn c##suq/suqERROR:ORA-01045: user C##SUQ lacks CREATE SESSION privilege; logon deniedWarning: You are no longer connected to ORACLE.
如果我们在CDB中赋予了c##suq登录权限,他就可以登录到CDB,(注意,这里如果不添加container子句,则默认为current)
SQL> conn / as sysdbaConnected.SQL> grant create session to c##suq;Grant succeeded.SQL> conn c##suq/suqConnected.
但是我们此时还没有赋予单独的PDB权限给他,所以他尝试连接其他PDB的时候会报错:
SQL> alter session set container=brent;ERROR:ORA-01031: insufficient privileges
此时我们就需要为公共用户授权:
SQL> conn / as sysdbaConnected.SQL> show con_nameCON_NAME------------------------------CDB$ROOTSQL> alter session set container=brent;Session altered.SQL> grant create session to c##suq with admin option container=current;Grant succeeded.
2)公共授权
公共授权的的意思是我们可以在CDB$ROOT中,对公共用户进行公共授权,授权之后的用户就拥有了所有PDB的相关权限:
公共授权添加container=all关键字即可:
SQL> conn / as sysdbaConnected.SQL> show con_nameCON_NAME------------------------------CDB$ROOTSQL> grant create session to c##suq container=all;Grant succeeded.[oracle@ora19c ~]$ sqlplus c##suq/suq@192.168.56.19/brentSQL*Plus: Release 19.0.0.0.0 - Production on Wed Sep 25 23:41:17 2019Version 19.3.0.0.0Copyright (c) 1982, 2019, Oracle. All rights reserved.Last Successful login time: Wed Sep 25 2019 23:40:13 +08:00Connected to:Oracle Database 19c Enterprise Edition Release 19.0.0.0.0 - ProductionVersion 19.3.0.0.0SQL>
那么此时c##suq就拥有的所有PDB的登录权限:
[oracle@ora19c ~]$ sqlplus c##suq/suq@192.168.56.19/testpdb2SQL*Plus: Release 19.0.0.0.0 - Production on Wed Sep 25 23:41:24 2019Version 19.3.0.0.0Copyright (c) 1982, 2019, Oracle. All rights reserved.Last Successful login time: Wed Sep 25 2019 23:41:17 +08:00Connected to:Oracle Database 19c Enterprise Edition Release 19.0.0.0.0 - ProductionVersion 19.3.0.0.0SQL>
常用的一些权限:
grant Create Session to c##Test container=all;
grant Set Container to c##Test container=all;
grant Set Container to c##Test container=all;
3)查看权限
可以通过查看dba_sys_privs查看赋予的权限:
SQL> select * from dba_sys_privs where grantee like 'C##%';GRANTEE PRIVILEGE ADM COM INH-------------------------------------------------------------------------------------------------------------------------------- ---------------------------------------- --- --- ---C##SUQ CREATE SESSION NO NO NOC##SUQ CREATE SESSION NO YES NO
4)修改公共用户的公共访问资源
默认公共用户可以查看CDB的信息,也可以查看v$视图.但是我们可以使用container_data参数控制公共用户访问的粒度.
例如下面我们设置公共用户对v$session只能查询某个PDB上的数据:
SQL> alter user c##suq set container_data=(CDB$ROOT,BRENT) for v_$session container=current;User altered.
可以通过查询dba_container_data字典,查询刚刚的操作:
SQL> select * from dba_container_data;USERNAME D OWNER OBJECT_NAME A CONTAINER_NAME-------------------- - -------------------- ------------------------------ - ------------------------------GSMADMIN_INTERNAL N SYS GV_$ACTIVE_SERVICES YGSMADMIN_INTERNAL N SYS CDB_SERVICES YAPPQOSSYS N SYS V_$WLM_PCMETRIC YAPPQOSSYS N SYS V_$WLM_DB_MODE YAPPQOSSYS N SYS V_$WLM_PCSERVICE YAPPQOSSYS N SYS GV_$WLM_DB_MODE YAPPQOSSYS N SYS V_$CONTAINERS YAPPQOSSYS N SYS DBA_PDBS YC##SUQ N SYS V_$SESSION N CDB$ROOTC##SUQ N SYS V_$SESSION N BRENTSYSTEM Y YDBSFWUSER Y YDBSNMP Y Y
但是注意,这种限制只能限制在CDB中的访问,如果此公共用户拥有PDB的set container权限,那么他就可以先alter session set container,然后再进行查询.
5)用户代理
用户代理可以允许我们以其他用户的身份登录数据库,然后在数据库里看来,和此用户登录数据库一模一样,
SQL> alter user suq grant connect through test;User altered.SQL> connect test[suq]/testConnected.SQL> show user;USER is "SUQ"
三.锁定概要文件(lockdown profile)
我们可以在某个PDB中给某个用户DBA权限,这样此用户就会获取到此PDB的DBA权限,但是没有CDB的DBA权限.但是在12.1中,此用户还是可能潜在存在对CDB或者服务器破坏的权限,
例如生产大量的trc文件.在12.2中引入了锁定概要文件.
1.首先连接到CDB,创建锁定概要文件
SQL> create lockdown profile test_lockdown_profile;Lockdown Profile created.
查看概要文件通过字典:DBA_LOCKDOWN_PROFILES
2.通过概要文件,创建规则
例如数据库中没有分区表,为了确保没有人会创建,禁用分区表的创建:
SQL> alter lockdown profile test_lockdown_profile disable option=('Partitioning');Lockdown Profile altered.
3.将锁定概要文件应用到指定PDB
SQL> alter session set container=testpdb3;Session altered.SQL> alter system set pdb_lockdown=test_lockdown_profile;System altered.
锁定概要文件非常强大,可以对一些特定的选项做启用或者禁止.