Record table only size bytes as well in addition to the total size bytes (#1149)

* Record table only size bytes as well in addition to the total size bytes

Signed-off-by: Felix Yuan <felix.yuan@reddit.com>

* Update collector/pg_stat_user_tables.go

Co-authored-by: Ben Kochie <superq@gmail.com>
Signed-off-by: Felix Yuan <felix.yuan@reddit.com>

* Update collector/pg_stat_user_tables.go

Co-authored-by: Ben Kochie <superq@gmail.com>
Signed-off-by: Felix Yuan <felix.yuan@reddit.com>

* Finish renaming elements to index and table size

Signed-off-by: Felix Yuan <felix.yuan@reddit.com>

---------

Signed-off-by: Felix Yuan <felix.yuan@reddit.com>
Co-authored-by: Ben Kochie <superq@gmail.com>
This commit is contained in:
Felix Yuan 2025-04-18 07:14:25 -07:00 committed by GitHub
parent f8b7139174
commit 5edc331876
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 40 additions and 14 deletions

View File

@ -150,9 +150,15 @@ var (
[]string{"datname", "schemaname", "relname"}, []string{"datname", "schemaname", "relname"},
prometheus.Labels{}, prometheus.Labels{},
) )
statUserTablesTotalSize = prometheus.NewDesc( statUserIndexSize = prometheus.NewDesc(
prometheus.BuildFQName(namespace, userTableSubsystem, "size_bytes"), prometheus.BuildFQName(namespace, userTableSubsystem, "index_size_bytes"),
"Total disk space used by this table, in bytes, including all indexes and TOAST data", "Total disk space used by this index, in bytes",
[]string{"datname", "schemaname", "relname"},
prometheus.Labels{},
)
statUserTableSize = prometheus.NewDesc(
prometheus.BuildFQName(namespace, userTableSubsystem, "table_size_bytes"),
"Total disk space used by this table, in bytes",
[]string{"datname", "schemaname", "relname"}, []string{"datname", "schemaname", "relname"},
prometheus.Labels{}, prometheus.Labels{},
) )
@ -180,7 +186,8 @@ var (
autovacuum_count, autovacuum_count,
analyze_count, analyze_count,
autoanalyze_count, autoanalyze_count,
pg_total_relation_size(relid) as total_size pg_indexes_size(relid) as indexes_size,
pg_table_size(relid) as table_size
FROM FROM
pg_stat_user_tables` pg_stat_user_tables`
) )
@ -198,10 +205,10 @@ func (c *PGStatUserTablesCollector) Update(ctx context.Context, instance *instan
for rows.Next() { for rows.Next() {
var datname, schemaname, relname sql.NullString var datname, schemaname, relname sql.NullString
var seqScan, seqTupRead, idxScan, idxTupFetch, nTupIns, nTupUpd, nTupDel, nTupHotUpd, nLiveTup, nDeadTup, var seqScan, seqTupRead, idxScan, idxTupFetch, nTupIns, nTupUpd, nTupDel, nTupHotUpd, nLiveTup, nDeadTup,
nModSinceAnalyze, vacuumCount, autovacuumCount, analyzeCount, autoanalyzeCount, totalSize sql.NullInt64 nModSinceAnalyze, vacuumCount, autovacuumCount, analyzeCount, autoanalyzeCount, indexSize, tableSize sql.NullInt64
var lastVacuum, lastAutovacuum, lastAnalyze, lastAutoanalyze sql.NullTime var lastVacuum, lastAutovacuum, lastAnalyze, lastAutoanalyze sql.NullTime
if err := rows.Scan(&datname, &schemaname, &relname, &seqScan, &seqTupRead, &idxScan, &idxTupFetch, &nTupIns, &nTupUpd, &nTupDel, &nTupHotUpd, &nLiveTup, &nDeadTup, &nModSinceAnalyze, &lastVacuum, &lastAutovacuum, &lastAnalyze, &lastAutoanalyze, &vacuumCount, &autovacuumCount, &analyzeCount, &autoanalyzeCount, &totalSize); err != nil { if err := rows.Scan(&datname, &schemaname, &relname, &seqScan, &seqTupRead, &idxScan, &idxTupFetch, &nTupIns, &nTupUpd, &nTupDel, &nTupHotUpd, &nLiveTup, &nDeadTup, &nModSinceAnalyze, &lastVacuum, &lastAutovacuum, &lastAnalyze, &lastAutoanalyze, &vacuumCount, &autovacuumCount, &analyzeCount, &autoanalyzeCount, &indexSize, &tableSize); err != nil {
return err return err
} }
@ -427,14 +434,25 @@ func (c *PGStatUserTablesCollector) Update(ctx context.Context, instance *instan
datnameLabel, schemanameLabel, relnameLabel, datnameLabel, schemanameLabel, relnameLabel,
) )
totalSizeMetric := 0.0 indexSizeMetric := 0.0
if totalSize.Valid { if indexSize.Valid {
totalSizeMetric = float64(totalSize.Int64) indexSizeMetric = float64(indexSize.Int64)
} }
ch <- prometheus.MustNewConstMetric( ch <- prometheus.MustNewConstMetric(
statUserTablesTotalSize, statUserIndexSize,
prometheus.GaugeValue, prometheus.GaugeValue,
totalSizeMetric, indexSizeMetric,
datnameLabel, schemanameLabel, relnameLabel,
)
tableSizeMetric := 0.0
if tableSize.Valid {
tableSizeMetric = float64(tableSize.Int64)
}
ch <- prometheus.MustNewConstMetric(
statUserTableSize,
prometheus.GaugeValue,
tableSizeMetric,
datnameLabel, schemanameLabel, relnameLabel, datnameLabel, schemanameLabel, relnameLabel,
) )
} }

View File

@ -72,7 +72,8 @@ func TestPGStatUserTablesCollector(t *testing.T) {
"autovacuum_count", "autovacuum_count",
"analyze_count", "analyze_count",
"autoanalyze_count", "autoanalyze_count",
"total_size"} "index_size",
"table_size"}
rows := sqlmock.NewRows(columns). rows := sqlmock.NewRows(columns).
AddRow("postgres", AddRow("postgres",
"public", "public",
@ -96,7 +97,8 @@ func TestPGStatUserTablesCollector(t *testing.T) {
12, 12,
13, 13,
14, 14,
15) 15,
16)
mock.ExpectQuery(sanitizeQuery(statUserTablesQuery)).WillReturnRows(rows) mock.ExpectQuery(sanitizeQuery(statUserTablesQuery)).WillReturnRows(rows)
ch := make(chan prometheus.Metric) ch := make(chan prometheus.Metric)
go func() { go func() {
@ -128,6 +130,8 @@ func TestPGStatUserTablesCollector(t *testing.T) {
{labels: labelMap{"datname": "postgres", "schemaname": "public", "relname": "a_table"}, metricType: dto.MetricType_COUNTER, value: 12}, {labels: labelMap{"datname": "postgres", "schemaname": "public", "relname": "a_table"}, metricType: dto.MetricType_COUNTER, value: 12},
{labels: labelMap{"datname": "postgres", "schemaname": "public", "relname": "a_table"}, metricType: dto.MetricType_COUNTER, value: 13}, {labels: labelMap{"datname": "postgres", "schemaname": "public", "relname": "a_table"}, metricType: dto.MetricType_COUNTER, value: 13},
{labels: labelMap{"datname": "postgres", "schemaname": "public", "relname": "a_table"}, metricType: dto.MetricType_COUNTER, value: 14}, {labels: labelMap{"datname": "postgres", "schemaname": "public", "relname": "a_table"}, metricType: dto.MetricType_COUNTER, value: 14},
{labels: labelMap{"datname": "postgres", "schemaname": "public", "relname": "a_table"}, metricType: dto.MetricType_GAUGE, value: 15},
{labels: labelMap{"datname": "postgres", "schemaname": "public", "relname": "a_table"}, metricType: dto.MetricType_GAUGE, value: 16},
} }
convey.Convey("Metrics comparison", t, func() { convey.Convey("Metrics comparison", t, func() {
@ -173,7 +177,8 @@ func TestPGStatUserTablesCollectorNullValues(t *testing.T) {
"autovacuum_count", "autovacuum_count",
"analyze_count", "analyze_count",
"autoanalyze_count", "autoanalyze_count",
"total_size"} "index_size",
"table_size"}
rows := sqlmock.NewRows(columns). rows := sqlmock.NewRows(columns).
AddRow("postgres", AddRow("postgres",
nil, nil,
@ -197,6 +202,7 @@ func TestPGStatUserTablesCollectorNullValues(t *testing.T) {
nil, nil,
nil, nil,
nil, nil,
nil,
nil) nil)
mock.ExpectQuery(sanitizeQuery(statUserTablesQuery)).WillReturnRows(rows) mock.ExpectQuery(sanitizeQuery(statUserTablesQuery)).WillReturnRows(rows)
ch := make(chan prometheus.Metric) ch := make(chan prometheus.Metric)
@ -229,6 +235,8 @@ func TestPGStatUserTablesCollectorNullValues(t *testing.T) {
{labels: labelMap{"datname": "postgres", "schemaname": "unknown", "relname": "unknown"}, metricType: dto.MetricType_COUNTER, value: 0}, {labels: labelMap{"datname": "postgres", "schemaname": "unknown", "relname": "unknown"}, metricType: dto.MetricType_COUNTER, value: 0},
{labels: labelMap{"datname": "postgres", "schemaname": "unknown", "relname": "unknown"}, metricType: dto.MetricType_COUNTER, value: 0}, {labels: labelMap{"datname": "postgres", "schemaname": "unknown", "relname": "unknown"}, metricType: dto.MetricType_COUNTER, value: 0},
{labels: labelMap{"datname": "postgres", "schemaname": "unknown", "relname": "unknown"}, metricType: dto.MetricType_COUNTER, value: 0}, {labels: labelMap{"datname": "postgres", "schemaname": "unknown", "relname": "unknown"}, metricType: dto.MetricType_COUNTER, value: 0},
{labels: labelMap{"datname": "postgres", "schemaname": "unknown", "relname": "unknown"}, metricType: dto.MetricType_GAUGE, value: 0},
{labels: labelMap{"datname": "postgres", "schemaname": "unknown", "relname": "unknown"}, metricType: dto.MetricType_GAUGE, value: 0},
} }
convey.Convey("Metrics comparison", t, func() { convey.Convey("Metrics comparison", t, func() {