Default monitoring roles
Three nologin roles with non-overlapping privs are created by default * pg_read_all_settings - read all GUCs. * pg_read_all_stats - pg_stat_*, pg_database_size(), pg_tablespace_size() * pg_stat_scan_tables - may lock/scan tables Top level role - pg_monitor includes all of the above by default, plus others Author: Dave Page Reviewed-by: Stephen Frost, Robert Haas, Peter Eisentraut, Simon Riggs
This commit is contained in:
parent
e984ef5861
commit
25fff40798
@ -4,8 +4,9 @@ MODULE_big = pg_buffercache
|
||||
OBJS = pg_buffercache_pages.o $(WIN32RES)
|
||||
|
||||
EXTENSION = pg_buffercache
|
||||
DATA = pg_buffercache--1.2.sql pg_buffercache--1.1--1.2.sql \
|
||||
pg_buffercache--1.0--1.1.sql pg_buffercache--unpackaged--1.0.sql
|
||||
DATA = pg_buffercache--1.2.sql pg_buffercache--1.2--1.3.sql \
|
||||
pg_buffercache--1.1--1.2.sql pg_buffercache--1.0--1.1.sql \
|
||||
pg_buffercache--unpackaged--1.0.sql
|
||||
PGFILEDESC = "pg_buffercache - monitoring of shared buffer cache in real-time"
|
||||
|
||||
ifdef USE_PGXS
|
||||
|
7
contrib/pg_buffercache/pg_buffercache--1.2--1.3.sql
Normal file
7
contrib/pg_buffercache/pg_buffercache--1.2--1.3.sql
Normal file
@ -0,0 +1,7 @@
|
||||
/* contrib/pg_buffercache/pg_buffercache--1.2--1.3.sql */
|
||||
|
||||
-- complain if script is sourced in psql, rather than via ALTER EXTENSION
|
||||
\echo Use "ALTER EXTENSION pg_buffercache UPDATE TO '1.3'" to load this file. \quit
|
||||
|
||||
GRANT EXECUTE ON FUNCTION pg_buffercache_pages() TO pg_monitor;
|
||||
GRANT SELECT ON pg_buffercache TO pg_monitor;
|
@ -1,5 +1,5 @@
|
||||
# pg_buffercache extension
|
||||
comment = 'examine the shared buffer cache'
|
||||
default_version = '1.2'
|
||||
default_version = '1.3'
|
||||
module_pathname = '$libdir/pg_buffercache'
|
||||
relocatable = true
|
||||
|
@ -4,8 +4,8 @@ MODULE_big = pg_freespacemap
|
||||
OBJS = pg_freespacemap.o $(WIN32RES)
|
||||
|
||||
EXTENSION = pg_freespacemap
|
||||
DATA = pg_freespacemap--1.1.sql pg_freespacemap--1.0--1.1.sql \
|
||||
pg_freespacemap--unpackaged--1.0.sql
|
||||
DATA = pg_freespacemap--1.1.sql pg_freespacemap--1.1--1.2.sql \
|
||||
pg_freespacemap--1.0--1.1.sql pg_freespacemap--unpackaged--1.0.sql
|
||||
PGFILEDESC = "pg_freespacemap - monitoring of free space map"
|
||||
|
||||
ifdef USE_PGXS
|
||||
|
7
contrib/pg_freespacemap/pg_freespacemap--1.1--1.2.sql
Normal file
7
contrib/pg_freespacemap/pg_freespacemap--1.1--1.2.sql
Normal file
@ -0,0 +1,7 @@
|
||||
/* contrib/pg_freespacemap/pg_freespacemap--1.1--1.2.sql */
|
||||
|
||||
-- complain if script is sourced in psql, rather than via ALTER EXTENSION
|
||||
\echo Use "ALTER EXTENSION pg_freespacemap UPDATE TO '1.2'" to load this file. \quit
|
||||
|
||||
GRANT EXECUTE ON FUNCTION pg_freespace(regclass, bigint) TO pg_stat_scan_tables;
|
||||
GRANT EXECUTE ON FUNCTION pg_freespace(regclass) TO pg_stat_scan_tables;
|
@ -1,5 +1,5 @@
|
||||
# pg_freespacemap extension
|
||||
comment = 'examine the free space map (FSM)'
|
||||
default_version = '1.1'
|
||||
default_version = '1.2'
|
||||
module_pathname = '$libdir/pg_freespacemap'
|
||||
relocatable = true
|
||||
|
@ -4,9 +4,10 @@ MODULE_big = pg_stat_statements
|
||||
OBJS = pg_stat_statements.o $(WIN32RES)
|
||||
|
||||
EXTENSION = pg_stat_statements
|
||||
DATA = pg_stat_statements--1.4.sql pg_stat_statements--1.3--1.4.sql \
|
||||
pg_stat_statements--1.2--1.3.sql pg_stat_statements--1.1--1.2.sql \
|
||||
pg_stat_statements--1.0--1.1.sql pg_stat_statements--unpackaged--1.0.sql
|
||||
DATA = pg_stat_statements--1.4.sql pg_stat_statements--1.4--1.5.sql \
|
||||
pg_stat_statements--1.3--1.4.sql pg_stat_statements--1.2--1.3.sql \
|
||||
pg_stat_statements--1.1--1.2.sql pg_stat_statements--1.0--1.1.sql \
|
||||
pg_stat_statements--unpackaged--1.0.sql
|
||||
PGFILEDESC = "pg_stat_statements - execution statistics of SQL statements"
|
||||
|
||||
LDFLAGS_SL += $(filter -lm, $(LIBS))
|
||||
|
@ -0,0 +1,6 @@
|
||||
/* contrib/pg_stat_statements/pg_stat_statements--1.4--1.5.sql */
|
||||
|
||||
-- complain if script is sourced in psql, rather than via ALTER EXTENSION
|
||||
\echo Use "ALTER EXTENSION pg_stat_statements UPDATE TO '1.5'" to load this file. \quit
|
||||
|
||||
GRANT EXECUTE ON FUNCTION pg_stat_statements_reset() TO pg_read_all_stats;
|
@ -62,6 +62,7 @@
|
||||
#include <unistd.h>
|
||||
|
||||
#include "access/hash.h"
|
||||
#include "catalog/pg_authid.h"
|
||||
#include "executor/instrument.h"
|
||||
#include "funcapi.h"
|
||||
#include "mb/pg_wchar.h"
|
||||
@ -1391,7 +1392,7 @@ pg_stat_statements_internal(FunctionCallInfo fcinfo,
|
||||
MemoryContext per_query_ctx;
|
||||
MemoryContext oldcontext;
|
||||
Oid userid = GetUserId();
|
||||
bool is_superuser = superuser();
|
||||
bool is_allowed_role = false;
|
||||
char *qbuffer = NULL;
|
||||
Size qbuffer_size = 0;
|
||||
Size extent = 0;
|
||||
@ -1399,6 +1400,9 @@ pg_stat_statements_internal(FunctionCallInfo fcinfo,
|
||||
HASH_SEQ_STATUS hash_seq;
|
||||
pgssEntry *entry;
|
||||
|
||||
/* Superusers or members of pg_read_all_stats members are allowed */
|
||||
is_allowed_role = is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_STATS);
|
||||
|
||||
/* hash table must exist already */
|
||||
if (!pgss || !pgss_hash)
|
||||
ereport(ERROR,
|
||||
@ -1541,7 +1545,7 @@ pg_stat_statements_internal(FunctionCallInfo fcinfo,
|
||||
values[i++] = ObjectIdGetDatum(entry->key.userid);
|
||||
values[i++] = ObjectIdGetDatum(entry->key.dbid);
|
||||
|
||||
if (is_superuser || entry->key.userid == userid)
|
||||
if (is_allowed_role || entry->key.userid == userid)
|
||||
{
|
||||
if (api_version >= PGSS_V1_2)
|
||||
values[i++] = Int64GetDatumFast(queryid);
|
||||
|
@ -1,5 +1,5 @@
|
||||
# pg_stat_statements extension
|
||||
comment = 'track execution statistics of all SQL statements executed'
|
||||
default_version = '1.4'
|
||||
default_version = '1.5'
|
||||
module_pathname = '$libdir/pg_stat_statements'
|
||||
relocatable = true
|
||||
|
@ -4,7 +4,8 @@ MODULE_big = pg_visibility
|
||||
OBJS = pg_visibility.o $(WIN32RES)
|
||||
|
||||
EXTENSION = pg_visibility
|
||||
DATA = pg_visibility--1.1.sql pg_visibility--1.0--1.1.sql
|
||||
DATA = pg_visibility--1.1.sql pg_visibility--1.1--1.2.sql \
|
||||
pg_visibility--1.0--1.1.sql
|
||||
PGFILEDESC = "pg_visibility - page visibility information"
|
||||
|
||||
REGRESS = pg_visibility
|
||||
|
13
contrib/pg_visibility/pg_visibility--1.1--1.2.sql
Normal file
13
contrib/pg_visibility/pg_visibility--1.1--1.2.sql
Normal file
@ -0,0 +1,13 @@
|
||||
/* contrib/pg_visibility/pg_visibility--1.1--1.2.sql */
|
||||
|
||||
-- complain if script is sourced in psql, rather than via ALTER EXTENSION
|
||||
\echo Use "ALTER EXTENSION pg_visibility UPDATE TO '1.2'" to load this file. \quit
|
||||
|
||||
-- Allow use of monitoring functions by pg_monitor members
|
||||
GRANT EXECUTE ON FUNCTION pg_visibility_map(regclass, bigint) TO pg_stat_scan_tables;
|
||||
GRANT EXECUTE ON FUNCTION pg_visibility(regclass, bigint) TO pg_stat_scan_tables;
|
||||
GRANT EXECUTE ON FUNCTION pg_visibility_map(regclass) TO pg_stat_scan_tables;
|
||||
GRANT EXECUTE ON FUNCTION pg_visibility(regclass) TO pg_stat_scan_tables;
|
||||
GRANT EXECUTE ON FUNCTION pg_visibility_map_summary(regclass) TO pg_stat_scan_tables;
|
||||
GRANT EXECUTE ON FUNCTION pg_check_frozen(regclass) TO pg_stat_scan_tables;
|
||||
GRANT EXECUTE ON FUNCTION pg_check_visible(regclass) TO pg_stat_scan_tables;
|
@ -1,5 +1,5 @@
|
||||
# pg_visibility extension
|
||||
comment = 'examine the visibility map (VM) and page-level visibility info'
|
||||
default_version = '1.1'
|
||||
default_version = '1.2'
|
||||
module_pathname = '$libdir/pg_visibility'
|
||||
relocatable = true
|
||||
|
@ -28,6 +28,7 @@
|
||||
#include "access/relscan.h"
|
||||
#include "access/xact.h"
|
||||
#include "catalog/namespace.h"
|
||||
#include "catalog/pg_authid.h"
|
||||
#include "funcapi.h"
|
||||
#include "miscadmin.h"
|
||||
#include "storage/bufmgr.h"
|
||||
@ -98,9 +99,11 @@ pgrowlocks(PG_FUNCTION_ARGS)
|
||||
relrv = makeRangeVarFromNameList(textToQualifiedNameList(relname));
|
||||
rel = heap_openrv(relrv, AccessShareLock);
|
||||
|
||||
/* check permissions: must have SELECT on table */
|
||||
aclresult = pg_class_aclcheck(RelationGetRelid(rel), GetUserId(),
|
||||
ACL_SELECT);
|
||||
/* check permissions: must have SELECT on table or be in pg_stat_scan_tables */
|
||||
aclresult = (pg_class_aclcheck(RelationGetRelid(rel), GetUserId(),
|
||||
ACL_SELECT) ||
|
||||
is_member_of_role(GetUserId(), DEFAULT_ROLE_STAT_SCAN_TABLES);
|
||||
|
||||
if (aclresult != ACLCHECK_OK)
|
||||
aclcheck_error(aclresult, ACL_KIND_CLASS,
|
||||
RelationGetRelationName(rel));
|
||||
|
@ -17,6 +17,7 @@ AS 'MODULE_PATHNAME', 'pgstattuple_v1_5'
|
||||
LANGUAGE C STRICT PARALLEL SAFE;
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pgstattuple(text) FROM PUBLIC;
|
||||
GRANT EXECUTE ON FUNCTION pgstattuple(text) TO pg_stat_scan_tables;
|
||||
|
||||
CREATE OR REPLACE FUNCTION pgstatindex(IN relname text,
|
||||
OUT version INT,
|
||||
@ -33,6 +34,7 @@ AS 'MODULE_PATHNAME', 'pgstatindex_v1_5'
|
||||
LANGUAGE C STRICT PARALLEL SAFE;
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pgstatindex(text) FROM PUBLIC;
|
||||
GRANT EXECUTE ON FUNCTION pgstatindex(text) TO pg_stat_scan_tables;
|
||||
|
||||
CREATE OR REPLACE FUNCTION pg_relpages(IN relname text)
|
||||
RETURNS BIGINT
|
||||
@ -40,6 +42,7 @@ AS 'MODULE_PATHNAME', 'pg_relpages_v1_5'
|
||||
LANGUAGE C STRICT PARALLEL SAFE;
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pg_relpages(text) FROM PUBLIC;
|
||||
GRANT EXECUTE ON FUNCTION pg_relpages(text) TO pg_stat_scan_tables;
|
||||
|
||||
/* New stuff in 1.1 begins here */
|
||||
|
||||
@ -51,6 +54,7 @@ AS 'MODULE_PATHNAME', 'pgstatginindex_v1_5'
|
||||
LANGUAGE C STRICT PARALLEL SAFE;
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pgstatginindex(regclass) FROM PUBLIC;
|
||||
GRANT EXECUTE ON FUNCTION pgstatginindex(regclass) TO pg_stat_scan_tables;
|
||||
|
||||
/* New stuff in 1.2 begins here */
|
||||
|
||||
@ -68,6 +72,7 @@ AS 'MODULE_PATHNAME', 'pgstattuplebyid_v1_5'
|
||||
LANGUAGE C STRICT PARALLEL SAFE;
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pgstattuple(regclass) FROM PUBLIC;
|
||||
GRANT EXECUTE ON FUNCTION pgstattuple(regclass) TO pg_stat_scan_tables;
|
||||
|
||||
CREATE OR REPLACE FUNCTION pgstatindex(IN relname regclass,
|
||||
OUT version INT,
|
||||
@ -84,6 +89,7 @@ AS 'MODULE_PATHNAME', 'pgstatindexbyid_v1_5'
|
||||
LANGUAGE C STRICT PARALLEL SAFE;
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pgstatindex(regclass) FROM PUBLIC;
|
||||
GRANT EXECUTE ON FUNCTION pgstatindex(regclass) TO pg_stat_scan_tables;
|
||||
|
||||
CREATE OR REPLACE FUNCTION pg_relpages(IN relname regclass)
|
||||
RETURNS BIGINT
|
||||
@ -91,6 +97,7 @@ AS 'MODULE_PATHNAME', 'pg_relpagesbyid_v1_5'
|
||||
LANGUAGE C STRICT PARALLEL SAFE;
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pg_relpages(regclass) FROM PUBLIC;
|
||||
GRANT EXECUTE ON FUNCTION pg_relpages(regclass) TO pg_stat_scan_tables;
|
||||
|
||||
/* New stuff in 1.3 begins here */
|
||||
|
||||
@ -109,6 +116,7 @@ AS 'MODULE_PATHNAME', 'pgstattuple_approx_v1_5'
|
||||
LANGUAGE C STRICT PARALLEL SAFE;
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pgstattuple_approx(regclass) FROM PUBLIC;
|
||||
GRANT EXECUTE ON FUNCTION pgstattuple_approx(regclass) TO pg_stat_scan_tables;
|
||||
|
||||
/* New stuff in 1.5 begins here */
|
||||
|
||||
@ -125,3 +133,4 @@ AS 'MODULE_PATHNAME', 'pgstathashindex'
|
||||
LANGUAGE C STRICT PARALLEL SAFE;
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pgstathashindex(regclass) FROM PUBLIC;
|
||||
GRANT EXECUTE ON FUNCTION pgstathashindex(regclass) TO pg_stat_scan_tables;
|
||||
|
@ -10221,15 +10221,17 @@ SELECT * FROM pg_locks pl LEFT JOIN pg_prepared_xacts ppx
|
||||
<entry><type>text</type></entry>
|
||||
<entry>Configuration file the current value was set in (null for
|
||||
values set from sources other than configuration files, or when
|
||||
examined by a non-superuser);
|
||||
helpful when using <literal>include</> directives in configuration files</entry>
|
||||
examined by a user who is neither a superuser or a member of
|
||||
<literal>pg_read_all_settings</literal>); helpful when using
|
||||
<literal>include</> directives in configuration files</entry>
|
||||
</row>
|
||||
<row>
|
||||
<entry><structfield>sourceline</structfield></entry>
|
||||
<entry><type>integer</type></entry>
|
||||
<entry>Line number within the configuration file the current value was
|
||||
set at (null for values set from sources other than configuration files,
|
||||
or when examined by a non-superuser)
|
||||
or when examined by a user who is neither a superuser or a member of
|
||||
<literal>pg_read_all_settings</literal>).
|
||||
</entry>
|
||||
</row>
|
||||
<row>
|
||||
|
@ -19408,9 +19408,11 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup());
|
||||
accept the OID or name of a database or tablespace, and return the total
|
||||
disk space used therein. To use <function>pg_database_size</function>,
|
||||
you must have <literal>CONNECT</> permission on the specified database
|
||||
(which is granted by default). To use <function>pg_tablespace_size</>,
|
||||
you must have <literal>CREATE</> permission on the specified tablespace,
|
||||
unless it is the default tablespace for the current database.
|
||||
(which is granted by default), or be a member of the <literal>pg_read_all_stats</>
|
||||
role. To use <function>pg_tablespace_size</>, you must have
|
||||
<literal>CREATE</> permission on the specified tablespace, or be a member
|
||||
of the <literal>pg_read_all_stats</> role unless it is the default tablespace for
|
||||
the current database.
|
||||
</para>
|
||||
|
||||
<para>
|
||||
@ -19736,7 +19738,8 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup());
|
||||
<entry><type>setof record</type></entry>
|
||||
<entry>
|
||||
List the name, size, and last modification time of files in the log
|
||||
directory. Access may be granted to non-superuser roles.
|
||||
directory. Access is granted to members of the <literal>pg_monitor</>
|
||||
role and may be granted to other non-superuser roles.
|
||||
</entry>
|
||||
</row>
|
||||
<row>
|
||||
@ -19746,7 +19749,8 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup());
|
||||
<entry><type>setof record</type></entry>
|
||||
<entry>
|
||||
List the name, size, and last modification time of files in the WAL
|
||||
directory. Access may be granted to non-superuser roles.
|
||||
directory. Access is granted to members of the <literal>pg_monitor</>
|
||||
role and may be granted to other non-superuser roles.
|
||||
</entry>
|
||||
</row>
|
||||
<row>
|
||||
@ -19807,8 +19811,8 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup());
|
||||
<para>
|
||||
<function>pg_ls_logdir</> returns the name, size, and last modified time
|
||||
(mtime) of each file in the log directory. By default, only superusers
|
||||
can use this function, but access may be granted to others using
|
||||
<command>GRANT</command>.
|
||||
and members of the <literal>pg_monitor</> role can use this function.
|
||||
Access may be granted to others using <command>GRANT</command>.
|
||||
</para>
|
||||
|
||||
<indexterm>
|
||||
@ -19817,8 +19821,9 @@ postgres=# SELECT * FROM pg_walfile_name_offset(pg_stop_backup());
|
||||
<para>
|
||||
<function>pg_ls_waldir</> returns the name, size, and last modified time
|
||||
(mtime) of each file in the write ahead log (WAL) directory. By
|
||||
default only superusers can use this function, but access may be granted
|
||||
to others using <command>GRANT</command>.
|
||||
default only superusers and members of the <literal>pg_monitor</> role
|
||||
can use this function. Access may be granted to others using
|
||||
<command>GRANT</command>.
|
||||
</para>
|
||||
|
||||
<indexterm>
|
||||
|
@ -24,8 +24,9 @@
|
||||
</para>
|
||||
|
||||
<para>
|
||||
By default public access is revoked from both of these, just in case there
|
||||
are security issues lurking.
|
||||
By default use is restricted to superusers and members of the
|
||||
<literal>pg_read_all_stats</literal> role. Access may be granted to others
|
||||
using <command>GRANT</command>.
|
||||
</para>
|
||||
|
||||
<sect2>
|
||||
|
@ -16,8 +16,9 @@
|
||||
</para>
|
||||
|
||||
<para>
|
||||
By default public access is revoked from the functions, just in case
|
||||
there are security issues lurking.
|
||||
By default use is restricted to superusers and members of the
|
||||
<literal>pg_stat_scan_tables</literal> role. Access may be granted to others
|
||||
using <command>GRANT</command>.
|
||||
</para>
|
||||
|
||||
<sect2>
|
||||
|
@ -12,6 +12,13 @@
|
||||
locking information for a specified table.
|
||||
</para>
|
||||
|
||||
<para>
|
||||
By default use is restricted to superusers, members of the
|
||||
<literal>pg_stat_scan_tables</literal> role, and users with
|
||||
<literal>SELECT</literal> permissions on the table.
|
||||
</para>
|
||||
|
||||
|
||||
<sect2>
|
||||
<title>Overview</title>
|
||||
|
||||
|
@ -226,10 +226,11 @@
|
||||
</table>
|
||||
|
||||
<para>
|
||||
For security reasons, non-superusers are not allowed to see the SQL
|
||||
text or <structfield>queryid</structfield> of queries executed by other users.
|
||||
They can see the statistics, however, if the view has been installed in their
|
||||
database.
|
||||
For security reasons, only superusers and members of the
|
||||
<literal>pg_read_all_stats<literal> role are allowed to see the SQL text and
|
||||
<structfield>queryid</structfield> of queries executed by other users.
|
||||
Other users can see the statistics, however, if the view has been installed
|
||||
in their database.
|
||||
</para>
|
||||
|
||||
<para>
|
||||
|
@ -16,7 +16,8 @@
|
||||
As these functions return detailed page-level information, only the superuser
|
||||
has EXECUTE privileges on them upon installation. After the functions have
|
||||
been installed, users may issue <command>GRANT</command> commands to change
|
||||
the privileges on the functions to allow non-superusers to execute them. See
|
||||
the privileges on the functions to allow non-superusers to execute them. Members
|
||||
of the <literal>pg_stat_scan_tables</literal> role are granted access by default. See
|
||||
the description of the <xref linkend="sql-grant"> command for specifics.
|
||||
</para>
|
||||
|
||||
|
@ -140,7 +140,10 @@
|
||||
</variablelist>
|
||||
|
||||
<para>
|
||||
By default, these functions are executable only by superusers.
|
||||
By default, these functions are executable only by superusers and members of the
|
||||
<literal>pg_stat_scan_tables</literal> role, with the exception of
|
||||
<function>pg_truncate_visibility_map(relation regclass)</function> which can only
|
||||
be executed by superusers.
|
||||
</para>
|
||||
</sect2>
|
||||
|
||||
|
@ -515,14 +515,50 @@ DROP ROLE doomed_role;
|
||||
</row>
|
||||
</thead>
|
||||
<tbody>
|
||||
<row>
|
||||
<entry>pg_read_all_settings</entry>
|
||||
<entry>Read all configuration variables, even those normally visible only to
|
||||
superusers.</entry>
|
||||
</row>
|
||||
<row>
|
||||
<entry>pg_read_all_stats</entry>
|
||||
<entry>Read all pg_stat_* views and use various statistics related extensions,
|
||||
even those normally visible only to superusers.</entry>
|
||||
</row>
|
||||
<row>
|
||||
<entry>pg_stat_scan_tables</entry>
|
||||
<entry>Execute monitoring functions that may take AccessShareLocks on tables,
|
||||
potentially for a long time.</entry>
|
||||
</row>
|
||||
<row>
|
||||
<entry>pg_signal_backend</entry>
|
||||
<entry>Send signals to other backends (eg: cancel query, terminate).</entry>
|
||||
</row>
|
||||
<row>
|
||||
<entry>pg_monitor</entry>
|
||||
<entry>Read/execute various monitoring views and functions.
|
||||
This role is a member of <literal>pg_read_all_settings</literal>,
|
||||
<literal>pg_read_all_stats</literal> and
|
||||
<literal>pg_stat_scan_tables</literal>.</entry>
|
||||
</row>
|
||||
</tbody>
|
||||
</tgroup>
|
||||
</table>
|
||||
|
||||
<para>
|
||||
The <literal>pg_monitor</literal>, <literal>pg_read_all_settings</literal>,
|
||||
<literal>pg_read_all_stats</literal> and <literal>pg_stat_scan_tables</literal>
|
||||
roles are intended to allow administrators to easily configure a role for the
|
||||
purpose of monitoring the database server. They grant a set of common privileges
|
||||
allowing the role to read various useful configuration settings, statistics and
|
||||
other system information normally restricted to superusers.
|
||||
</para>
|
||||
|
||||
<para>
|
||||
Care should be taken when granting these roles to ensure they are only used where
|
||||
needed to perform the desired monitoring.
|
||||
</para>
|
||||
|
||||
<para>
|
||||
Administrators can grant access to these roles to users using the GRANT
|
||||
command:
|
||||
|
@ -1148,3 +1148,9 @@ REVOKE EXECUTE ON FUNCTION pg_stat_reset_single_function_counters(oid) FROM publ
|
||||
|
||||
REVOKE EXECUTE ON FUNCTION pg_ls_logdir() FROM public;
|
||||
REVOKE EXECUTE ON FUNCTION pg_ls_waldir() FROM public;
|
||||
GRANT EXECUTE ON FUNCTION pg_ls_logdir() TO pg_monitor;
|
||||
GRANT EXECUTE ON FUNCTION pg_ls_waldir() TO pg_monitor;
|
||||
|
||||
GRANT pg_read_all_settings TO pg_monitor;
|
||||
GRANT pg_read_all_stats TO pg_monitor;
|
||||
GRANT pg_stat_scan_tables TO pg_monitor;
|
||||
|
@ -50,6 +50,7 @@
|
||||
#include "access/timeline.h"
|
||||
#include "access/transam.h"
|
||||
#include "access/xlog_internal.h"
|
||||
#include "catalog/pg_authid.h"
|
||||
#include "catalog/pg_type.h"
|
||||
#include "funcapi.h"
|
||||
#include "libpq/pqformat.h"
|
||||
@ -1421,7 +1422,7 @@ pg_stat_get_wal_receiver(PG_FUNCTION_ARGS)
|
||||
/* Fetch values */
|
||||
values[0] = Int32GetDatum(walrcv->pid);
|
||||
|
||||
if (!superuser())
|
||||
if (!is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_STATS))
|
||||
{
|
||||
/*
|
||||
* Only superusers can see details. Other users only get the pid value
|
||||
|
@ -17,6 +17,7 @@
|
||||
#include "access/htup_details.h"
|
||||
#include "catalog/catalog.h"
|
||||
#include "catalog/namespace.h"
|
||||
#include "catalog/pg_authid.h"
|
||||
#include "catalog/pg_tablespace.h"
|
||||
#include "commands/dbcommands.h"
|
||||
#include "commands/tablespace.h"
|
||||
@ -88,11 +89,17 @@ calculate_database_size(Oid dbOid)
|
||||
char pathname[MAXPGPATH];
|
||||
AclResult aclresult;
|
||||
|
||||
/* User must have connect privilege for target database */
|
||||
/*
|
||||
* User must have connect privilege for target database
|
||||
* or be a member of pg_read_all_stats
|
||||
*/
|
||||
aclresult = pg_database_aclcheck(dbOid, GetUserId(), ACL_CONNECT);
|
||||
if (aclresult != ACLCHECK_OK)
|
||||
if (aclresult != ACLCHECK_OK &&
|
||||
!is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_STATS))
|
||||
{
|
||||
aclcheck_error(aclresult, ACL_KIND_DATABASE,
|
||||
get_database_name(dbOid));
|
||||
}
|
||||
|
||||
/* Shared storage in pg_global is not counted */
|
||||
|
||||
@ -172,11 +179,12 @@ calculate_tablespace_size(Oid tblspcOid)
|
||||
AclResult aclresult;
|
||||
|
||||
/*
|
||||
* User must have CREATE privilege for target tablespace, either
|
||||
* explicitly granted or implicitly because it is default for current
|
||||
* database.
|
||||
* User must be a member of pg_read_all_stats or have CREATE privilege for
|
||||
* target tablespace, either explicitly granted or implicitly because
|
||||
* it is default for current database.
|
||||
*/
|
||||
if (tblspcOid != MyDatabaseTableSpace)
|
||||
if (tblspcOid != MyDatabaseTableSpace &&
|
||||
!is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_STATS))
|
||||
{
|
||||
aclresult = pg_tablespace_aclcheck(tblspcOid, GetUserId(), ACL_CREATE);
|
||||
if (aclresult != ACLCHECK_OK)
|
||||
|
@ -15,6 +15,7 @@
|
||||
#include "postgres.h"
|
||||
|
||||
#include "access/htup_details.h"
|
||||
#include "catalog/pg_authid.h"
|
||||
#include "catalog/pg_type.h"
|
||||
#include "common/ip.h"
|
||||
#include "funcapi.h"
|
||||
@ -658,8 +659,9 @@ pg_stat_get_activity(PG_FUNCTION_ARGS)
|
||||
nulls[19] = nulls[20] = nulls[21] = nulls[22] = nulls[23] = true;
|
||||
}
|
||||
|
||||
/* Values only available to role member */
|
||||
if (has_privs_of_role(GetUserId(), beentry->st_userid))
|
||||
/* Values only available to role member or pg_read_all_stats */
|
||||
if (has_privs_of_role(GetUserId(), beentry->st_userid) ||
|
||||
is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_STATS))
|
||||
{
|
||||
SockAddr zero_clientaddr;
|
||||
|
||||
|
@ -34,6 +34,7 @@
|
||||
#include "access/xact.h"
|
||||
#include "access/xlog_internal.h"
|
||||
#include "catalog/namespace.h"
|
||||
#include "catalog/pg_authid.h"
|
||||
#include "commands/async.h"
|
||||
#include "commands/prepare.h"
|
||||
#include "commands/user.h"
|
||||
@ -6689,10 +6690,11 @@ GetConfigOption(const char *name, bool missing_ok, bool restrict_superuser)
|
||||
}
|
||||
if (restrict_superuser &&
|
||||
(record->flags & GUC_SUPERUSER_ONLY) &&
|
||||
!superuser())
|
||||
!is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_SETTINGS))
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
|
||||
errmsg("must be superuser to examine \"%s\"", name)));
|
||||
errmsg("must be superuser or a member of pg_read_all_settings to examine \"%s\"",
|
||||
name)));
|
||||
|
||||
switch (record->vartype)
|
||||
{
|
||||
@ -6737,10 +6739,12 @@ GetConfigOptionResetString(const char *name)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_UNDEFINED_OBJECT),
|
||||
errmsg("unrecognized configuration parameter \"%s\"", name)));
|
||||
if ((record->flags & GUC_SUPERUSER_ONLY) && !superuser())
|
||||
if ((record->flags & GUC_SUPERUSER_ONLY) &&
|
||||
!is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_SETTINGS))
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
|
||||
errmsg("must be superuser to examine \"%s\"", name)));
|
||||
errmsg("must be superuser or a member of pg_read_all_settings to examine \"%s\"",
|
||||
name)));
|
||||
|
||||
switch (record->vartype)
|
||||
{
|
||||
@ -8027,10 +8031,12 @@ GetConfigOptionByName(const char *name, const char **varname, bool missing_ok)
|
||||
errmsg("unrecognized configuration parameter \"%s\"", name)));
|
||||
}
|
||||
|
||||
if ((record->flags & GUC_SUPERUSER_ONLY) && !superuser())
|
||||
if ((record->flags & GUC_SUPERUSER_ONLY) &&
|
||||
!is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_SETTINGS))
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
|
||||
errmsg("must be superuser to examine \"%s\"", name)));
|
||||
errmsg("must be superuser or a member of pg_read_all_settings to examine \"%s\"",
|
||||
name)));
|
||||
|
||||
if (varname)
|
||||
*varname = record->name;
|
||||
@ -8056,7 +8062,8 @@ GetConfigOptionByNum(int varnum, const char **values, bool *noshow)
|
||||
if (noshow)
|
||||
{
|
||||
if ((conf->flags & GUC_NO_SHOW_ALL) ||
|
||||
((conf->flags & GUC_SUPERUSER_ONLY) && !superuser()))
|
||||
((conf->flags & GUC_SUPERUSER_ONLY) &&
|
||||
!is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_SETTINGS)))
|
||||
*noshow = true;
|
||||
else
|
||||
*noshow = false;
|
||||
|
@ -99,10 +99,18 @@ typedef FormData_pg_authid *Form_pg_authid;
|
||||
* ----------------
|
||||
*/
|
||||
DATA(insert OID = 10 ( "POSTGRES" t t t t t t t -1 _null_ _null_));
|
||||
DATA(insert OID = 3373 ( "pg_monitor" f t f f f f f -1 _null_ _null_));
|
||||
DATA(insert OID = 3374 ( "pg_read_all_settings" f t f f f f f -1 _null_ _null_));
|
||||
DATA(insert OID = 3375 ( "pg_read_all_stats" f t f f f f f -1 _null_ _null_));
|
||||
DATA(insert OID = 3377 ( "pg_stat_scan_tables" f t f f f f f -1 _null_ _null_));
|
||||
DATA(insert OID = 4200 ( "pg_signal_backend" f t f f f f f -1 _null_ _null_));
|
||||
|
||||
#define BOOTSTRAP_SUPERUSERID 10
|
||||
|
||||
#define DEFAULT_ROLE_MONITOR 3373
|
||||
#define DEFAULT_ROLE_READ_ALL_SETTINGS 3374
|
||||
#define DEFAULT_ROLE_READ_ALL_STATS 3375
|
||||
#define DEFAULT_ROLE_STAT_SCAN_TABLES 3377
|
||||
#define DEFAULT_ROLE_SIGNAL_BACKENDID 4200
|
||||
|
||||
#endif /* PG_AUTHID_H */
|
||||
|
Loading…
Reference in New Issue
Block a user