暂无图片
暂无图片
暂无图片
暂无图片
暂无图片

PostgreSQL授权普通用户kill会话权限

原创 黄舒琪 2021-08-12
684

作者:吴聪

作为DBA,可能经常回听到开发人员说“我有个SQL执行太久了,帮我kill下”“我有张表好像锁住了,帮我kill下”。时间久了确实挺烦的,此时我们肯定想的是让他们自己去kill,但是又不能直接给开发或者用户超级用户的权限,那么怎么只授权普通用户kill会话的权限呢?

—方法1:

PostgreSQL9.6开始,新增了默认角色pgsignalbackend,这个角色具有 cancel query、terminate 其它会话的权限。

例子:

bill@bill=>create user user01 login;

CREATE ROLE

bill@bill=>create user user02 login;

CREATE ROLE

会话1:

bill@bill=>\c - user01

You are now connected to database ‘bill’ as user ‘user01’.

user01@bill=>select pgbackendpid();

pgbackendpid


18238

(1 row)

会话2:

bill@bill=>\c - user02

You are now connected to database ‘bill’ as user ‘user02’.

user02@bill=>select pgcancelbackend(18238);

ERROR: must be a member of the role whose query is being canceled or member of pgsignalbackend

可以看到,普通用户是没法kill会话的。当然这里的提示也很明显了,普通用户要么只能kill自己的会话,要么属于pgsignalbackend组中。

授权:

这下可以kill会话了。

bill@bill=>grant pgsignalbackend to user02;

GRANT ROLE

bill@bill=>\c - user02

You are now connected to database ‘bill’ as user ‘user02’.

user02@bill=>select pgcancelbackend(18238);

pgcancelbackend


t

(1 row)

但是需要注意,不能去kill超级用户的会话,只有超级用户才能kill超级用户的会话。

user02@bill=>select pgcancelbackend(10852);

ERROR: must be a superuser to cancel superuser query

那如果用的是9.6之前的版本呢?虽然现在应该很少有人用9.6之前的版本了,但是任然还是会有的,比如我自己这边就有套GP6的库,内核版本就是PG9.4,那么该怎么办呢?

这种情况我们可以通过UDF来实现。

—方法2:

创建UDF函数:

bill@bill=>CREATE SCHEMA queryadmin;

CREATE SCHEMA

bill@bill=>CREATE OR REPLACE FUNCTION queryadmin.killprocess(userpid integer)

bill-# RETURNS boolean AS bodybody

bill$# DECLARE

bill$# qry boolean;

bill$# BEGIN

bill$# qry :=(SELECT pgcatalog.pgcancelbackend(pid)

bill$# FROM pgstatactivity

bill$# WHERE usename=(select sessionuser)

bill$# AND pid=userpid);

bill$# RETURN qry;

bill$# END;

bill#body$

bill-# LANGUAGE plpgsql

bill-# SECURITY DEFINER

bill-# VOLATILE

bill-# RETURNS NULL ON NULL INPUT;

CREATE FUNCTION

授权:

bill@bill=>GRANT USAGE ON SCHEMA queryadmin TO user02;

GRANT

bill@bill=>GRANT EXECUTE ON FUNCTION queryadmin.killprocess(pid integer) TO user02;

GRANT

使用普通用户去调用该函数就可以kill会话了:

user02@bill=>SELECT *FROM queryadmin.killprocess(22734);

killprocess


(1 row)

总结:

对于给普通用户授权kill会话权限,建议:

版本>=9.6:授权普通用户pgsignalbackend角色;版本<9.6:使用自定义函数。

来源:百度

「喜欢这篇文章,您的关注和赞赏是给作者最好的鼓励」
关注作者
【版权声明】本文为墨天轮用户原创内容,转载时必须标注文章的来源(墨天轮),文章链接,文章作者等基本信息,否则作者和墨天轮有权追究责任。如果您发现墨天轮中有涉嫌抄袭或者侵权的内容,欢迎发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论