PG-176 : Extract fully qualified relations name.

pull/73/head
Ibrar Ahmed 2021-02-11 15:51:44 +00:00
parent ce9d503cdb
commit d60f725b4a
9 changed files with 183 additions and 25 deletions

View File

@ -11,7 +11,7 @@ PGFILEDESC = "pg_stat_monitor - execution statistics of SQL statements"
LDFLAGS_SL += $(filter -lm, $(LIBS))
REGRESS_OPTS = --temp-config $(top_srcdir)/contrib/pg_stat_monitor/pg_stat_monitor.conf
REGRESS = guc basic pg_stat_monitor
REGRESS = guc relations basic pg_stat_monitor
# Disabled because these tests require "shared_preload_libraries=pg_stat_statements",
# which typical installcheck users do not have (e.g. buildfarm clients).

35
expected/guc.out Normal file
View File

@ -0,0 +1,35 @@
CREATE EXTENSION pg_stat_monitor;
SELECT pg_stat_monitor_reset();
pg_stat_monitor_reset
-----------------------
(1 row)
select pg_sleep(.5);
pg_sleep
----------
(1 row)
SELECT * FROM pg_stat_monitor_settings;
name | value | default_value | description | minimum | maximum | restart
----------------------------------------+--------+---------------+----------------------------------------------------------------------------------------------------------+---------+------------+---------
pg_stat_monitor.pgsm_max | 100 | 100 | Sets the maximum size of shared memory in (MB) used for statement's metadata tracked by pg_stat_monitor. | 1 | 1000 | 1
pg_stat_monitor.pgsm_query_max_len | 1024 | 1024 | Sets the maximum length of query. | 1024 | 2147483647 | 1
pg_stat_monitor.pgsm_enable | 1 | 1 | Enable/Disable statistics collector. | 0 | 0 | 0
pg_stat_monitor.pgsm_track_utility | 0 | 0 | Selects whether utility commands are tracked. | 0 | 0 | 0
pg_stat_monitor.pgsm_normalized_query | 1 | 1 | Selects whether save query in normalized format. | 0 | 0 | 0
pg_stat_monitor.pgsm_max_buckets | 10 | 10 | Sets the maximum number of buckets. | 1 | 10 | 1
pg_stat_monitor.pgsm_bucket_time | 300 | 60 | Sets the time in seconds per bucket. | 1 | 2147483647 | 1
pg_stat_monitor.pgsm_histogram_min | 0 | 0 | Sets the time in millisecond. | 0 | 2147483647 | 1
pg_stat_monitor.pgsm_histogram_max | 100000 | 10 | Sets the time in millisecond. | 10 | 2147483647 | 1
pg_stat_monitor.pgsm_histogram_buckets | 10 | 10 | Sets the maximum number of histogram buckets | 2 | 2147483647 | 1
(10 rows)
SELECT pg_stat_monitor_reset();
pg_stat_monitor_reset
-----------------------
(1 row)
DROP EXTENSION pg_stat_monitor;

34
expected/relations.out Normal file
View File

@ -0,0 +1,34 @@
CREATE EXTENSION pg_stat_monitor;
SELECT pg_stat_monitor_reset();
pg_stat_monitor_reset
-----------------------
(1 row)
CREATE TABLE foo1(a int);
CREATE TABLE foo2(a int);
CREATE TABLE foo3(a int);
CREATE TABLE foo4(a int);
SELECT * FROM foo1, foo2, foo3, foo4;
a | a | a | a
---+---+---+---
(0 rows)
SELECT query, relations from pg_stat_monitor;
query | relations
--------------------------------------+---------------------------------------------------
SELECT * FROM foo1, foo2, foo3, foo4 | {public.foo1,public.foo2,public.foo3,public.foo4}
SELECT pg_stat_monitor_reset() |
(2 rows)
DROP TABLE foo1;
DROP TABLE foo2;
DROP TABLE foo3;
DROP TABLE foo4;
SELECT pg_stat_monitor_reset();
pg_stat_monitor_reset
-----------------------
(1 row)
DROP EXTENSION pg_stat_monitor;

34
expected/relations_1.out Normal file
View File

@ -0,0 +1,34 @@
CREATE EXTENSION pg_stat_monitor;
SELECT pg_stat_monitor_reset();
pg_stat_monitor_reset
-----------------------
(1 row)
CREATE TABLE foo1(a int);
CREATE TABLE foo2(a int);
CREATE TABLE foo3(a int);
CREATE TABLE foo4(a int);
SELECT * FROM foo1, foo2, foo3, foo4;
a | a | a | a
---+---+---+---
(0 rows)
SELECT query, relations from pg_stat_monitor;
query | relations
--------------------------------------+---------------------------------------------------
SELECT pg_stat_monitor_reset() |
SELECT * FROM foo1, foo2, foo3, foo4 | {public.foo1,public.foo2,public.foo3,public.foo4}
(2 rows)
DROP TABLE foo1;
DROP TABLE foo2;
DROP TABLE foo3;
DROP TABLE foo4;
SELECT pg_stat_monitor_reset();
pg_stat_monitor_reset
-----------------------
(1 row)
DROP EXTENSION pg_stat_monitor;

View File

@ -127,7 +127,7 @@ CREATE VIEW pg_stat_monitor AS SELECT
queryid,
query,
application_name,
(string_to_array(relations, ','))::oid[]::regclass[] AS relations,
string_to_array(relations, ',') AS relations,
cmd_type,
get_cmd_type(cmd_type) AS cmd_type_text,
elevel,

View File

@ -32,7 +32,20 @@ do \
{ \
int i; \
for(i = 0; i < _len && i < _max_len; i++) \
{\
_str_dst[i] = _str_src[i]; \
}\
}while(0)
#define _snprintf2(_str_dst, _str_src, _len1, _len2)\
do \
{ \
int i,j; \
for(i = 0; i < _len1; i++) \
for(j = 0; j < _len2; j++) \
{ \
_str_dst[i][j] = _str_src[i][j]; \
} \
}while(0)
/*---- Initicalization Function Declarations ----*/
@ -40,6 +53,11 @@ void _PG_init(void);
void _PG_fini(void);
int64 v = 5631;
/*---- Initicalization Function Declarations ----*/
void _PG_init(void);
void _PG_fini(void);
/*---- Local variables ----*/
/* Current nesting depth of ExecutorRun+ProcessUtility calls */
@ -459,7 +477,7 @@ pgss_ExecutorEnd(QueryDesc *queryDesc)
prev_ExecutorEnd(queryDesc);
else
standard_ExecutorEnd(queryDesc);
memset(pgss->relations, 0x0, sizeof(pgss->relations));
pgss->num_relations = 0;
}
static bool
@ -469,9 +487,10 @@ pgss_ExecutorCheckPerms(List *rt, bool abort)
pgssSharedState *pgss = pgsm_get_ss();
int i = 0;
int j = 0;
Oid list_oid[20];
LWLockAcquire(pgss->lock, LW_EXCLUSIVE);
memset(pgss->relations, 0x0, sizeof(pgss->relations));
pgss->num_relations = 0;
foreach(lr, rt)
{
@ -484,13 +503,22 @@ pgss_ExecutorCheckPerms(List *rt, bool abort)
bool found = false;
for(j = 0; j < i; j++)
{
if (pgss->relations[j] == rte->relid)
if (list_oid[j] == rte->relid)
found = true;
}
if (!found)
pgss->relations[i++] = rte->relid;
{
char *namespace_name;
char *relation_name;
list_oid[j] = rte->relid;
namespace_name = get_namespace_name(get_rel_namespace(rte->relid));
relation_name = get_rel_name(rte->relid);
snprintf(pgss->relations[i++], REL_LEN, "%s.%s", namespace_name, relation_name);
}
}
}
pgss->num_relations = i;
LWLockRelease(pgss->lock);
if (prev_ExecutorCheckPerms_hook)
@ -783,8 +811,6 @@ static void pgss_store(uint64 queryId,
char *norm_query = NULL;
int encoding = GetDatabaseEncoding();
bool reset = false;
bool found = false;
int i;
pgssSharedState *pgss = pgsm_get_ss();
HTAB *pgss_hash = pgsm_get_hash();
int message_len = message ? strlen(message) : 0;
@ -951,13 +977,8 @@ static void pgss_store(uint64 queryId,
}
_snprintf(e->counters.info.application_name, application_name, application_name_len, APPLICATIONNAME_LEN);
found = false;
for (i = 0; i < REL_LST; i++)
if (e->counters.info.relations[i] != 0)
found = true;
if (!found)
_snprintf(e->counters.info.relations, pgss->relations, REL_LST, REL_LST);
e->counters.info.num_relations = pgss->num_relations;
_snprintf2(e->counters.info.relations, pgss->relations, pgss->num_relations, REL_LEN);
e->counters.info.cmd_type = cmd_type;
e->counters.error.elevel = elevel;
@ -1103,7 +1124,6 @@ pg_stat_monitor_internal(FunctionCallInfo fcinfo,
Datum values[PG_STAT_STATEMENTS_COLS];
bool nulls[PG_STAT_STATEMENTS_COLS];
int i = 0;
int j = 0;
int len = 0;
int kind;
Counters tmp;
@ -1200,15 +1220,27 @@ pg_stat_monitor_internal(FunctionCallInfo fcinfo,
else
values[i++] = CStringGetTextDatum(tmp.info.application_name);
len = 0;
for (j = 0; j < REL_LST; j++)
if (tmp.info.relations[j] != 0)
len++;
if (tmp.info.num_relations > 0)
{
int j;
char *text_str = palloc0(1024);
bool first = true;
if (len == 0)
nulls[i++] = true;
/* Need to calculate the actual size, and avoid unnessary memory usage */
for (j = 0; j < tmp.info.num_relations; j++)
{
if (first)
{
snprintf(text_str, 1024, "%s", tmp.info.relations[j]);
first = false;
continue;
}
snprintf(text_str, 1024, "%s,%s", text_str, tmp.info.relations[j]);
}
values[i++] = CStringGetTextDatum(text_str);
}
else
values[i++] = IntArrayGetTextDatum(tmp.info.relations, len);
nulls[i++] = true;
values[i++] = Int64GetDatumFast(tmp.info.cmd_type);
values[i++] = Int64GetDatumFast(tmp.error.elevel);

View File

@ -75,6 +75,7 @@
#define TEXT_LEN 255
#define ERROR_MESSAGE_LEN 100
#define REL_LST 10
#define REL_LEN 1000
#define CMD_LST 10
#define CMD_LEN 20
#define APPLICATIONNAME_LEN 100
@ -163,7 +164,8 @@ typedef struct QueryInfo
uint host; /* client IP */
int64 type; /* type of query, options are query, info, warning, error, fatal */
char application_name[APPLICATIONNAME_LEN];
int32 relations[REL_LST]; /* List of relation involved in the query */
char relations[REL_LST][REL_LEN]; /* List of relation involved in the query */
int num_relations; /* Number of relation in the query */
CmdType cmd_type; /* query command type SELECT/UPDATE/DELETE/INSERT */
} QueryInfo;
@ -262,7 +264,8 @@ typedef struct pgssSharedState
uint64 prev_bucket_usec;
uint64 bucket_entry[MAX_BUCKETS];
int64 query_buf_size_bucket;
int32 relations[REL_LST];
char relations[REL_LST][REL_LEN];
int num_relations; /* Number of relation in the query */
char bucket_start_time[MAX_BUCKETS][60]; /* start time of the bucket */
} pgssSharedState;

6
sql/guc.sql Normal file
View File

@ -0,0 +1,6 @@
CREATE EXTENSION pg_stat_monitor;
SELECT pg_stat_monitor_reset();
select pg_sleep(.5);
SELECT * FROM pg_stat_monitor_settings;
SELECT pg_stat_monitor_reset();
DROP EXTENSION pg_stat_monitor;

14
sql/relations.sql Normal file
View File

@ -0,0 +1,14 @@
CREATE EXTENSION pg_stat_monitor;
SELECT pg_stat_monitor_reset();
CREATE TABLE foo1(a int);
CREATE TABLE foo2(a int);
CREATE TABLE foo3(a int);
CREATE TABLE foo4(a int);
SELECT * FROM foo1, foo2, foo3, foo4;
SELECT query, relations from pg_stat_monitor;
DROP TABLE foo1;
DROP TABLE foo2;
DROP TABLE foo3;
DROP TABLE foo4;
SELECT pg_stat_monitor_reset();
DROP EXTENSION pg_stat_monitor;