Skip to content

Commit

Permalink
WIP: Mark new PG14 columns nullable
Browse files Browse the repository at this point in the history
TODO: SessionTime, ActiveTime, and IdleInTransactionTime do not work on
PG14; ChecksumLastFailure needs a proper datatype.
  • Loading branch information
df7cb authored and tbe committed Jun 15, 2022
1 parent 36246b5 commit cd1ae8c
Show file tree
Hide file tree
Showing 4 changed files with 112 additions and 106 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,6 @@
bin/
pg-exporter
pid
regression.diffs
regression.out
results/
57 changes: 29 additions & 28 deletions collector/models/pgStatDatabase.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package models

import (
"database/sql"
"time"

"github.com/uptrace/bun"
Expand All @@ -9,32 +10,32 @@ import (
// +metric=slice
type PgStatDatabase struct {
bun.BaseModel `bun:"pg_stat_database"`
DatID int64 `bun:"datid" help:"OID of a database" metric:"database_id,type:label"`
DatName string `bun:"datname" help:"Name of this database" metric:"database,type:label"`
NumBackends int `bun:"numbackends" help:"Number of backends currently connected to this database" metric:"backends,type:gauge"`
XactCommit int64 `bun:"xact_commit" help:"Number of transactions in this database that have been committed" metric:"xact_commited_total"`
XactRollback int64 `bun:"xact_rollback" help:"Number of transactions in this database that have been rolled back" metric:"xact_rolledback_total"`
BlksRead int64 `bun:"blks_read" help:"Number of disk blocks read in this database" metric:"blocks_read_total"`
BlksHit int64 `bun:"blks_hit" help:"Number of times disk blocks were found already in the buffer cache, so that a read was not necessary" metric:"blocks_hit_total"`
TupReturned int64 `bun:"tup_returned" help:"Number of rows returned by queries in this database" metric:"rows_returned_total"`
TupFetched int64 `bun:"tup_fetched" help:"Number of rows fetched by queries in this database" metric:"rows_fetched_total"`
TupInserted int64 `bun:"tup_inserted" help:"Number of rows inserted by queries in this database" metric:"rows_inserted_total"`
TupUpdated int64 `bun:"tup_updated" help:"Number of rows updated by queries in this database" metric:"rows_updated_total"`
TupDeleted int64 `bun:"tup_deleted" help:"Number of rows deleted by queries in this database" metric:"rows_deleted_total"`
Conflicts int64 `bun:"conflicts" help:"Number of queries canceled due to conflicts with recovery in this database" metric:"conflicts_total"`
TempFiles int64 `bun:"temp_files" help:"Number of temporary files created by queries in this database" metric:"temp_files_total"`
TempBytes int64 `bun:"temp_bytes" help:"Total amount of data written to temporary files by queries in this database" metric:"temp_bytes_total"`
Deadlocks int64 `bun:"deadlocks" help:"Number of deadlocks detected in this database" metric:"deadlocks_total"`
ChecksumFailures int64 `bun:"checksum_failures" help:"Number of data page checksum failures detected in this database" metric:"checksum_failures_count"` // new in PG12
ChecksumLastFailure time.Time `bun:"checksum_last_failure" help:"Time at which the last data page checksum failure was detected in this database" metric:"checksum_last_failure"` // new in PG12
BlkReadTime Milliseconds `bun:"blk_read_time" help:"Time spent reading data file blocks by backends in this database" metric:"blk_read_seconds_total"`
BlkWriteTime Milliseconds `bun:"blk_write_time" help:"Time spent writing data file blocks by backends in this database" metric:"blk_write_seconds_total"`
SessionTime Milliseconds `bun:"session_time" help:"Time spent by database sessions in this database, in milliseconds" metric:"session_time_total"` // new in PG14
ActiveTime Milliseconds `bun:"active_time" help:"Time spent executing SQL statements in this database, in milliseconds" metric:"active_time_total"` // new in PG14
IdleInTransactionTime Milliseconds `bun:"idle_in_transaction_time" help:"Time spent idling while in a transaction in this database, in milliseconds" metric:"idle_in_transaction_time_total"` // new in PG14
Sessions int64 `bun:"sessions" help:"Total number of sessions established to this database" metric:"sessions_count"` // new in PG14
SessionsAbandoned int64 `bun:"sessions_abandoned" help:"Number of database sessions to this database that were terminated because connection to the client was lost" metric:"sessions_abandoned_count"` // new in PG14
SessionsFatal int64 `bun:"sessions_fatal" help:"Number of database sessions to this database that were terminated by fatal errors" metric:"sessions_fatal_count"` // new in PG14
SessionsKilled int64 `bun:"sessions_killed" help:"Number of database sessions to this database that were terminated by operator intervention" metric:"sessions_killed_count"` // new in PG14
StatsReset time.Time `bun:"stats_reset" help:"Time at which these statistics were last reset"`
DatID int64 `bun:"datid" help:"OID of a database" metric:"database_id,type:label"`
DatName string `bun:"datname" help:"Name of this database" metric:"database,type:label"`
NumBackends int `bun:"numbackends" help:"Number of backends currently connected to this database" metric:"backends,type:gauge"`
XactCommit int64 `bun:"xact_commit" help:"Number of transactions in this database that have been committed" metric:"xact_commited_total"`
XactRollback int64 `bun:"xact_rollback" help:"Number of transactions in this database that have been rolled back" metric:"xact_rolledback_total"`
BlksRead int64 `bun:"blks_read" help:"Number of disk blocks read in this database" metric:"blocks_read_total"`
BlksHit int64 `bun:"blks_hit" help:"Number of times disk blocks were found already in the buffer cache, so that a read was not necessary" metric:"blocks_hit_total"`
TupReturned int64 `bun:"tup_returned" help:"Number of rows returned by queries in this database" metric:"rows_returned_total"`
TupFetched int64 `bun:"tup_fetched" help:"Number of rows fetched by queries in this database" metric:"rows_fetched_total"`
TupInserted int64 `bun:"tup_inserted" help:"Number of rows inserted by queries in this database" metric:"rows_inserted_total"`
TupUpdated int64 `bun:"tup_updated" help:"Number of rows updated by queries in this database" metric:"rows_updated_total"`
TupDeleted int64 `bun:"tup_deleted" help:"Number of rows deleted by queries in this database" metric:"rows_deleted_total"`
Conflicts int64 `bun:"conflicts" help:"Number of queries canceled due to conflicts with recovery in this database" metric:"conflicts_total"`
TempFiles int64 `bun:"temp_files" help:"Number of temporary files created by queries in this database" metric:"temp_files_total"`
TempBytes int64 `bun:"temp_bytes" help:"Total amount of data written to temporary files by queries in this database" metric:"temp_bytes_total"`
Deadlocks int64 `bun:"deadlocks" help:"Number of deadlocks detected in this database" metric:"deadlocks_total"`
ChecksumFailures sql.NullInt64 `bun:"checksum_failures" help:"Number of data page checksum failures detected in this database" metric:"checksum_failures_count"` // new in PG12
ChecksumLastFailure sql.NullTime `bun:"checksum_last_failure" help:"Time at which the last data page checksum failure was detected in this database" metric:"checksum_last_failure"` // new in PG12
BlkReadTime Milliseconds `bun:"blk_read_time" help:"Time spent reading data file blocks by backends in this database" metric:"blk_read_seconds_total"`
BlkWriteTime Milliseconds `bun:"blk_write_time" help:"Time spent writing data file blocks by backends in this database" metric:"blk_write_seconds_total"`
SessionTime NullMilliseconds `bun:"session_time" help:"Time spent by database sessions in this database, in milliseconds" metric:"session_time_total"` // new in PG14
ActiveTime NullMilliseconds `bun:"active_time" help:"Time spent executing SQL statements in this database, in milliseconds" metric:"active_time_total"` // new in PG14
IdleInTransactionTime NullMilliseconds `bun:"idle_in_transaction_time" help:"Time spent idling while in a transaction in this database, in milliseconds" metric:"idle_in_transaction_time_total"` // new in PG14
Sessions sql.NullInt64 `bun:"sessions" help:"Total number of sessions established to this database" metric:"sessions_count"` // new in PG14
SessionsAbandoned sql.NullInt64 `bun:"sessions_abandoned" help:"Number of database sessions to this database that were terminated because connection to the client was lost" metric:"sessions_abandoned_count"` // new in PG14
SessionsFatal sql.NullInt64 `bun:"sessions_fatal" help:"Number of database sessions to this database that were terminated by fatal errors" metric:"sessions_fatal_count"` // new in PG14
SessionsKilled sql.NullInt64 `bun:"sessions_killed" help:"Number of database sessions to this database that were terminated by operator intervention" metric:"sessions_killed_count"` // new in PG14
StatsReset time.Time `bun:"stats_reset" help:"Time at which these statistics were last reset"`
}
157 changes: 80 additions & 77 deletions collector/models/pgStatDatabase_gen.go
Original file line number Diff line number Diff line change
Expand Up @@ -139,27 +139,6 @@ func (r *PgStatDatabase) ToMetrics(namespace string, subsystem string, ch chan<-
), prometheus.CounterValue, deadlocksTotal,
)

// checksum_failures_count (CounterValue)
checksumFailuresCount := float64(r.ChecksumFailures)
ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `checksum_failures_count`), `Number of data page checksum failures detected in this database`, nil, labels,
), prometheus.CounterValue, checksumFailuresCount,
)

// checksum_last_failure (CounterValue)
var checksumLastFailure float64
if r.ChecksumLastFailure.IsZero() {
checksumLastFailure = float64(0)
} else {
checksumLastFailure = float64(r.ChecksumLastFailure.Unix())
}
ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `checksum_last_failure`), `Time at which the last data page checksum failure was detected in this database`, nil, labels,
), prometheus.CounterValue, checksumLastFailure,
)

// blk_read_seconds_total (CounterValue)
blkReadSecondsTotal := r.BlkReadTime.Seconds()
ch <- prometheus.MustNewConstMetric(
Expand All @@ -176,62 +155,6 @@ func (r *PgStatDatabase) ToMetrics(namespace string, subsystem string, ch chan<-
), prometheus.CounterValue, blkWriteSecondsTotal,
)

// session_time_total (CounterValue)
sessionTimeTotal := r.SessionTime.Seconds()
ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `session_time_total`), `Time spent by database sessions in this database, in milliseconds`, nil, labels,
), prometheus.CounterValue, sessionTimeTotal,
)

// active_time_total (CounterValue)
activeTimeTotal := r.ActiveTime.Seconds()
ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `active_time_total`), `Time spent executing SQL statements in this database, in milliseconds`, nil, labels,
), prometheus.CounterValue, activeTimeTotal,
)

// idle_in_transaction_time_total (CounterValue)
idleInTransactionTimeTotal := r.IdleInTransactionTime.Seconds()
ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `idle_in_transaction_time_total`), `Time spent idling while in a transaction in this database, in milliseconds`, nil, labels,
), prometheus.CounterValue, idleInTransactionTimeTotal,
)

// sessions_count (CounterValue)
sessionsCount := float64(r.Sessions)
ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `sessions_count`), `Total number of sessions established to this database`, nil, labels,
), prometheus.CounterValue, sessionsCount,
)

// sessions_abandoned_count (CounterValue)
sessionsAbandonedCount := float64(r.SessionsAbandoned)
ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `sessions_abandoned_count`), `Number of database sessions to this database that were terminated because connection to the client was lost`, nil, labels,
), prometheus.CounterValue, sessionsAbandonedCount,
)

// sessions_fatal_count (CounterValue)
sessionsFatalCount := float64(r.SessionsFatal)
ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `sessions_fatal_count`), `Number of database sessions to this database that were terminated by fatal errors`, nil, labels,
), prometheus.CounterValue, sessionsFatalCount,
)

// sessions_killed_count (CounterValue)
sessionsKilledCount := float64(r.SessionsKilled)
ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `sessions_killed_count`), `Number of database sessions to this database that were terminated by operator intervention`, nil, labels,
), prometheus.CounterValue, sessionsKilledCount,
)

// stats_reset (CounterValue)
var statsReset float64
if r.StatsReset.IsZero() {
Expand All @@ -246,6 +169,86 @@ func (r *PgStatDatabase) ToMetrics(namespace string, subsystem string, ch chan<-
)

// optional metrics
// checksum_failures_count (CounterValue)
if r.ChecksumFailures.Valid {
checksumFailuresCount := float64(r.ChecksumFailures.Int64)

ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `checksum_failures_count`), `Number of data page checksum failures detected in this database`, nil, labels,
), prometheus.CounterValue, checksumFailuresCount,
)
}
// session_time_total (CounterValue)
if r.SessionTime.Valid {
sessionTimeTotal := r.SessionTime.Seconds()

ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `session_time_total`), `Time spent by database sessions in this database, in milliseconds`, nil, labels,
), prometheus.CounterValue, sessionTimeTotal,
)
}
// active_time_total (CounterValue)
if r.ActiveTime.Valid {
activeTimeTotal := r.ActiveTime.Seconds()

ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `active_time_total`), `Time spent executing SQL statements in this database, in milliseconds`, nil, labels,
), prometheus.CounterValue, activeTimeTotal,
)
}
// idle_in_transaction_time_total (CounterValue)
if r.IdleInTransactionTime.Valid {
idleInTransactionTimeTotal := r.IdleInTransactionTime.Seconds()

ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `idle_in_transaction_time_total`), `Time spent idling while in a transaction in this database, in milliseconds`, nil, labels,
), prometheus.CounterValue, idleInTransactionTimeTotal,
)
}
// sessions_count (CounterValue)
if r.Sessions.Valid {
sessionsCount := float64(r.Sessions.Int64)

ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `sessions_count`), `Total number of sessions established to this database`, nil, labels,
), prometheus.CounterValue, sessionsCount,
)
}
// sessions_abandoned_count (CounterValue)
if r.SessionsAbandoned.Valid {
sessionsAbandonedCount := float64(r.SessionsAbandoned.Int64)

ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `sessions_abandoned_count`), `Number of database sessions to this database that were terminated because connection to the client was lost`, nil, labels,
), prometheus.CounterValue, sessionsAbandonedCount,
)
}
// sessions_fatal_count (CounterValue)
if r.SessionsFatal.Valid {
sessionsFatalCount := float64(r.SessionsFatal.Int64)

ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `sessions_fatal_count`), `Number of database sessions to this database that were terminated by fatal errors`, nil, labels,
), prometheus.CounterValue, sessionsFatalCount,
)
}
// sessions_killed_count (CounterValue)
if r.SessionsKilled.Valid {
sessionsKilledCount := float64(r.SessionsKilled.Int64)

ch <- prometheus.MustNewConstMetric(
prometheus.NewDesc(
prometheus.BuildFQName(namespace, subsystem, `sessions_killed_count`), `Number of database sessions to this database that were terminated by operator intervention`, nil, labels,
), prometheus.CounterValue, sessionsKilledCount,
)
}

return nil
}
2 changes: 1 addition & 1 deletion gen/generator/parser.go
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ func parseModel(t *types.Type) *modelDescription {
case "int64", "int", "time.Time", "float64",
"./collector/models.Milliseconds", "github.com/1and1/pg-exporter/collector/models.Milliseconds":
desc.metrics = append(desc.metrics, field)
case "database/sql.NullInt64", "database/sql.NullFloat64",
case "database/sql.NullInt64", "database/sql.NullFloat64", "database/sql.NullTime",
"./collector/models.NullMilliseconds", "github.com/1and1/pg-exporter/collector/models.NullMilliseconds":
desc.optionalMetrics = append(desc.optionalMetrics, field)
default:
Expand Down

0 comments on commit cd1ae8c

Please sign in to comment.