jla*_*rcy 4 sql postgresql privileges dependencies sql-revoke
我正在使用 PostgreSQL 10.4,我发现了一个奇怪的行为。
如果我们创建一个角色并将其授予CONNECT数据库:
CREATE ROLE dummy;
GRANT CONNECT ON DATABASE test TO dummy;
Run Code Online (Sandbox Code Playgroud)
然后我们不能删除这个角色,即使它根本不拥有任何对象,这个命令:
DROP ROLE dummy;
Run Code Online (Sandbox Code Playgroud)
提高:
ERROR: role "dummy" cannot be dropped because some objects depend on it
SQL state: 2BP01
Detail: privileges for database test
Run Code Online (Sandbox Code Playgroud)
文档有点误导:
2B 类 — 依赖特权描述符仍然存在
2B000dependent_privilege_descriptors_still_exist
2BP01dependent_objects_still_exist
它说依赖对象仍然存在,但似乎没有依赖于这个特定角色的对象,它在数据库上没有任何东西。
无论如何,如果我们撤销CONNECT特权,那么角色可以被删除:
REVOKE CONNECT ON DATABASE test FROM dummy;
DROP ROLE dummy;
Run Code Online (Sandbox Code Playgroud)
我刚刚检查了 PostgreSQL 9.5 上也存在该行为。我觉得有点奇怪,我不明白为什么这个特定的特权会导致删除角色失败。
其他观察
这真的是阻塞,因为我们既不能重新分配这个对象:
REASSIGN OWNED BY dummy TO postgres;
Run Code Online (Sandbox Code Playgroud)
也不丢弃对象:
DROP OWNED BY dummy;
Run Code Online (Sandbox Code Playgroud)
两者都引发相关错误:
ERROR: permission denied to reassign objects
SQL state: 42501
ERROR: permission denied to drop objects
SQL state: 42501
Run Code Online (Sandbox Code Playgroud)
正如@RaymondNijland 指出的那样,这一定是因为CONNECT权限被视为角色相关对象。以下查询:
WITH
R AS (SELECT * FROM pg_roles WHERE rolname = 'dummy')
SELECT
D.*
FROM
R, pg_shdepend AS D
WHERE
refobjid = R.oid;
Run Code Online (Sandbox Code Playgroud)
CONNECT授予时返回单行:
"dbid";"classid";"objid";"objsubid";"refclassid";"refobjid";"deptype"
0;1262;27961;0;1260;27966;"a"
Run Code Online (Sandbox Code Playgroud)
当特权被撤销时,根本没有行。这至少解释了为什么我们不能重新分配对象。
关于依赖类型,文档说明:
SHARED_DEPENDENCY_ACL(一种)被引用的对象(必须是角色)在依赖对象的ACL(访问控制列表,即权限列表)中有提到。(
A SHARED_DEPENDENCY_ACL不会为对象的所有者创建SHARED_DEPENDENCY_OWNER条目,因为无论如何所有者都会有条目。)
但我没有足够的洞察力来清楚地理解它。
我的问题是:
使用REASSIGN.
我发现当超级用户帐户不可用时(如 RDS 或 Cloud SQL),我必须将目标角色授予我当前的角色,以便从目标角色重新分配或删除拥有的对象。例如,如果我的活跃用户是postsgres,而我正在尝试删除user_a:
> DROP OWNED BY user_a
ERROR: permission denied to drop objects
> GRANT user_a TO postgres;
GRANT ROLE
> DROP OWNED BY user_a;
DROP OWNED
Run Code Online (Sandbox Code Playgroud)
现在,如果user_a碰巧是 的成员,这会变得有点棘手postgres,尤其是如果它碰巧通过其他角色继承了该成员身份,让我们称其为schema_admin...
> DROP OWNED BY user_a
ERROR: permission denied to drop objects
> GRANT user_a TO postgres;
ERROR: role "user_a" is a member of role "postgres"
-- Alright, let's try to revoke it...
> REVOKE postgres FROM user_a;
REVOKE ROLE
> GRANT user_a TO postgres;
ERROR: role "user_a" is a member of role "postgres"
-- It's still a member through the inherited grant - trying to revoke again doesn't work:
> REVOKE postgres FROM user_a;
WARNING: role "user_a" is not a member of role "postgres"
REVOKE ROLE
-- So you have to identify the role it's inheriting from, and revoke that:
> REVOKE schema_admin FROM user_a;
REVOKE ROLE
> GRANT user_a TO postgres;
GRANT ROLE
-- Now just to be safe, I'll reassign owned objects before actually dropping everything:
> REASSIGN OWNED BY user_a TO postgres;
REASSIGN OWNED
> DROP OWNED BY user_a;
DROP OWNED
> DROP ROLE user_a;
DROP ROLE;
Run Code Online (Sandbox Code Playgroud)
瞧!
注意:这里还有另一个广泛引用且有效的答案:https : //sysadmintips.com/services/databases/postgresql-error-permission-denied-to-reassign-objects/只要您能够创建并以新的临时用户身份登录。然而,在某些情况下,这本身就是一个问题(然后你还有额外的清理工作来处理完成后删除该临时角色),所以我试图在这里避免这种情况。
| 归档时间: |
|
| 查看次数: |
3162 次 |
| 最近记录: |