我们正在合理化我们的数据库用户权限,为此,我们要撤消授予所有用户(但不是特定角色)的架构中所有表的所有选择权限。
通过一些正则表达式,我尝试为每个表创建一个通用的revoke
,类似于:
从USER1,USER2,USER3 ...;
撤销TABLE1上的select从USER1,USER2,USER3 ...;
撤销TABLE2上的select
但是,并非所有用户都被授予对所有表的权限,这会导致oracle错误:
01927. 00000 - "cannot REVOKE privileges you did not grant"
哪个有意义,但没有帮助。
我还尝试使用All_Tab_Privs
获取所有表的列表,其中包含要撤消的必要授权,这样可行,但我看不出如何轻松地从中实现撤销权限。< / p>
SELECT * From All_Tab_Privs where grantor = 'GRANTING_USER' and grantee != 'READROLE' and grantee != 'PUBLIC' and grantee != 'SYS';
如果没有在电子表格中花费数小时,如何做到这一点的任何建议?我猜一些PL / SQL?感谢。
答案 0 :(得分:4)
这种工作的一般模式是使用隐式游标返回所需的数据,然后构建DDL并执行它们。
begin
for x in (select attribute_1, attribute_2 ... from ... where ...)
loop
execute immediate 'REVOKE ...'||x.attribute1||' etc';
end loop;
end;
/
一个不错的选择是在SELECT中构建要执行的SQL,然后执行它。它更容易测试,但SQL看起来有点笨拙。
答案 1 :(得分:3)
一些PL / SQL和动态SQL:
begin
for r in (SELECT * From All_Tab_Privs
where grantor = 'GRANTING_USER'
and grantee != 'READROLE'
and grantee != 'PUBLIC'
and grantee != 'SYS')
loop
execute immediate 'revoke '||r.privilege||' from '||r.grantee;
end loop;
end;
答案 2 :(得分:3)
-- Revoke Privs Granted to Users
BEGIN
FOR r IN (SELECT * FROM all_tab_privs WHERE grantee IN ('USER_1', 'USER_2'))
LOOP
EXECUTE IMMEDIATE 'REVOKE '||r.privilege||' ON '||r.table_name||' FROM '||r.grantee;
END LOOP;
END;
/
答案 3 :(得分:2)
我的数据库有一个非常有趣的情况。 Oracles拥有SQL Developer仍然列出了每个表的现有授权,尽管它们已从all_tab_privs
表中删除( SELECT 没有为搜索到的受助者带来任何结果)。
我已经通过使用以下构造解决了这个问题:
BEGIN
FOR r IN (SELECT owner, table_name FROM dba_tables WHERE owner IN ('owner1', 'owner2'))
LOOP
EXECUTE IMMEDIATE 'REVOKE ALL ON '||r.owner||'.'||r.table_name||' FROM grantee1, grantee2';
END LOOP;
END;
/
首先从某些所有者的每个表中选择所有所有者和表名。然后它撤销某些受助人的所有拨款。
好消息是,如果没有为所选表中的一个列出的受让人提供任何授权,那么这不会失败。
请注意,这应该从管理员帐户执行,例如 system ,因此当前用户有权撤销对其他用户的表的授权。