pangolin_exporter

Форк
0
/
pg_stat_user_tables.go 
446 строк · 13.3 Кб
1
// Copyright 2023 The Prometheus Authors
2
// Licensed under the Apache License, Version 2.0 (the "License");
3
// you may not use this file except in compliance with the License.
4
// You may obtain a copy of the License at
5
//
6
// http://www.apache.org/licenses/LICENSE-2.0
7
//
8
// Unless required by applicable law or agreed to in writing, software
9
// distributed under the License is distributed on an "AS IS" BASIS,
10
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11
// See the License for the specific language governing permissions and
12
// limitations under the License.
13

14
package collector
15

16
import (
17
	"context"
18
	"database/sql"
19

20
	"github.com/go-kit/log"
21
	"github.com/prometheus/client_golang/prometheus"
22
)
23

24
const userTableSubsystem = "stat_user_tables"
25

26
func init() {
27
	registerCollector(userTableSubsystem, defaultEnabled, NewPGStatUserTablesCollector)
28
}
29

30
type PGStatUserTablesCollector struct {
31
	log log.Logger
32
}
33

34
func NewPGStatUserTablesCollector(config collectorConfig) (Collector, error) {
35
	return &PGStatUserTablesCollector{log: config.logger}, nil
36
}
37

38
var (
39
	statUserTablesSeqScan = prometheus.NewDesc(
40
		prometheus.BuildFQName(namespace, userTableSubsystem, "seq_scan"),
41
		"Number of sequential scans initiated on this table",
42
		[]string{"datname", "schemaname", "relname"},
43
		prometheus.Labels{},
44
	)
45
	statUserTablesSeqTupRead = prometheus.NewDesc(
46
		prometheus.BuildFQName(namespace, userTableSubsystem, "seq_tup_read"),
47
		"Number of live rows fetched by sequential scans",
48
		[]string{"datname", "schemaname", "relname"},
49
		prometheus.Labels{},
50
	)
51
	statUserTablesIdxScan = prometheus.NewDesc(
52
		prometheus.BuildFQName(namespace, userTableSubsystem, "idx_scan"),
53
		"Number of index scans initiated on this table",
54
		[]string{"datname", "schemaname", "relname"},
55
		prometheus.Labels{},
56
	)
57
	statUserTablesIdxTupFetch = prometheus.NewDesc(
58
		prometheus.BuildFQName(namespace, userTableSubsystem, "idx_tup_fetch"),
59
		"Number of live rows fetched by index scans",
60
		[]string{"datname", "schemaname", "relname"},
61
		prometheus.Labels{},
62
	)
63
	statUserTablesNTupIns = prometheus.NewDesc(
64
		prometheus.BuildFQName(namespace, userTableSubsystem, "n_tup_ins"),
65
		"Number of rows inserted",
66
		[]string{"datname", "schemaname", "relname"},
67
		prometheus.Labels{},
68
	)
69
	statUserTablesNTupUpd = prometheus.NewDesc(
70
		prometheus.BuildFQName(namespace, userTableSubsystem, "n_tup_upd"),
71
		"Number of rows updated",
72
		[]string{"datname", "schemaname", "relname"},
73
		prometheus.Labels{},
74
	)
75
	statUserTablesNTupDel = prometheus.NewDesc(
76
		prometheus.BuildFQName(namespace, userTableSubsystem, "n_tup_del"),
77
		"Number of rows deleted",
78
		[]string{"datname", "schemaname", "relname"},
79
		prometheus.Labels{},
80
	)
81
	statUserTablesNTupHotUpd = prometheus.NewDesc(
82
		prometheus.BuildFQName(namespace, userTableSubsystem, "n_tup_hot_upd"),
83
		"Number of rows HOT updated (i.e., with no separate index update required)",
84
		[]string{"datname", "schemaname", "relname"},
85
		prometheus.Labels{},
86
	)
87
	statUserTablesNLiveTup = prometheus.NewDesc(
88
		prometheus.BuildFQName(namespace, userTableSubsystem, "n_live_tup"),
89
		"Estimated number of live rows",
90
		[]string{"datname", "schemaname", "relname"},
91
		prometheus.Labels{},
92
	)
93
	statUserTablesNDeadTup = prometheus.NewDesc(
94
		prometheus.BuildFQName(namespace, userTableSubsystem, "n_dead_tup"),
95
		"Estimated number of dead rows",
96
		[]string{"datname", "schemaname", "relname"},
97
		prometheus.Labels{},
98
	)
99
	statUserTablesNModSinceAnalyze = prometheus.NewDesc(
100
		prometheus.BuildFQName(namespace, userTableSubsystem, "n_mod_since_analyze"),
101
		"Estimated number of rows changed since last analyze",
102
		[]string{"datname", "schemaname", "relname"},
103
		prometheus.Labels{},
104
	)
105
	statUserTablesLastVacuum = prometheus.NewDesc(
106
		prometheus.BuildFQName(namespace, userTableSubsystem, "last_vacuum"),
107
		"Last time at which this table was manually vacuumed (not counting VACUUM FULL)",
108
		[]string{"datname", "schemaname", "relname"},
109
		prometheus.Labels{},
110
	)
111
	statUserTablesLastAutovacuum = prometheus.NewDesc(
112
		prometheus.BuildFQName(namespace, userTableSubsystem, "last_autovacuum"),
113
		"Last time at which this table was vacuumed by the autovacuum daemon",
114
		[]string{"datname", "schemaname", "relname"},
115
		prometheus.Labels{},
116
	)
117
	statUserTablesLastAnalyze = prometheus.NewDesc(
118
		prometheus.BuildFQName(namespace, userTableSubsystem, "last_analyze"),
119
		"Last time at which this table was manually analyzed",
120
		[]string{"datname", "schemaname", "relname"},
121
		prometheus.Labels{},
122
	)
123
	statUserTablesLastAutoanalyze = prometheus.NewDesc(
124
		prometheus.BuildFQName(namespace, userTableSubsystem, "last_autoanalyze"),
125
		"Last time at which this table was analyzed by the autovacuum daemon",
126
		[]string{"datname", "schemaname", "relname"},
127
		prometheus.Labels{},
128
	)
129
	statUserTablesVacuumCount = prometheus.NewDesc(
130
		prometheus.BuildFQName(namespace, userTableSubsystem, "vacuum_count"),
131
		"Number of times this table has been manually vacuumed (not counting VACUUM FULL)",
132
		[]string{"datname", "schemaname", "relname"},
133
		prometheus.Labels{},
134
	)
135
	statUserTablesAutovacuumCount = prometheus.NewDesc(
136
		prometheus.BuildFQName(namespace, userTableSubsystem, "autovacuum_count"),
137
		"Number of times this table has been vacuumed by the autovacuum daemon",
138
		[]string{"datname", "schemaname", "relname"},
139
		prometheus.Labels{},
140
	)
141
	statUserTablesAnalyzeCount = prometheus.NewDesc(
142
		prometheus.BuildFQName(namespace, userTableSubsystem, "analyze_count"),
143
		"Number of times this table has been manually analyzed",
144
		[]string{"datname", "schemaname", "relname"},
145
		prometheus.Labels{},
146
	)
147
	statUserTablesAutoanalyzeCount = prometheus.NewDesc(
148
		prometheus.BuildFQName(namespace, userTableSubsystem, "autoanalyze_count"),
149
		"Number of times this table has been analyzed by the autovacuum daemon",
150
		[]string{"datname", "schemaname", "relname"},
151
		prometheus.Labels{},
152
	)
153
	statUserTablesTotalSize = prometheus.NewDesc(
154
		prometheus.BuildFQName(namespace, userTableSubsystem, "size_bytes"),
155
		"Total disk space used by this table, in bytes, including all indexes and TOAST data",
156
		[]string{"datname", "schemaname", "relname"},
157
		prometheus.Labels{},
158
	)
159

160
	statUserTablesQuery = `SELECT
161
		current_database() datname,
162
		schemaname,
163
		relname,
164
		seq_scan,
165
		seq_tup_read,
166
		idx_scan,
167
		idx_tup_fetch,
168
		n_tup_ins,
169
		n_tup_upd,
170
		n_tup_del,
171
		n_tup_hot_upd,
172
		n_live_tup,
173
		n_dead_tup,
174
		n_mod_since_analyze,
175
		COALESCE(last_vacuum, '1970-01-01Z') as last_vacuum,
176
		COALESCE(last_autovacuum, '1970-01-01Z') as last_autovacuum,
177
		COALESCE(last_analyze, '1970-01-01Z') as last_analyze,
178
		COALESCE(last_autoanalyze, '1970-01-01Z') as last_autoanalyze,
179
		vacuum_count,
180
		autovacuum_count,
181
		analyze_count,
182
		autoanalyze_count,
183
		pg_total_relation_size(relid) as total_size
184
	FROM
185
		pg_stat_user_tables`
186
)
187

188
func (c *PGStatUserTablesCollector) Update(ctx context.Context, instance *instance, ch chan<- prometheus.Metric) error {
189
	db := instance.getDB()
190
	rows, err := db.QueryContext(ctx,
191
		statUserTablesQuery)
192

193
	if err != nil {
194
		return err
195
	}
196
	defer rows.Close()
197

198
	for rows.Next() {
199
		var datname, schemaname, relname sql.NullString
200
		var seqScan, seqTupRead, idxScan, idxTupFetch, nTupIns, nTupUpd, nTupDel, nTupHotUpd, nLiveTup, nDeadTup,
201
			nModSinceAnalyze, vacuumCount, autovacuumCount, analyzeCount, autoanalyzeCount, totalSize sql.NullInt64
202
		var lastVacuum, lastAutovacuum, lastAnalyze, lastAutoanalyze sql.NullTime
203

204
		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 {
205
			return err
206
		}
207

208
		datnameLabel := "unknown"
209
		if datname.Valid {
210
			datnameLabel = datname.String
211
		}
212
		schemanameLabel := "unknown"
213
		if schemaname.Valid {
214
			schemanameLabel = schemaname.String
215
		}
216
		relnameLabel := "unknown"
217
		if relname.Valid {
218
			relnameLabel = relname.String
219
		}
220

221
		seqScanMetric := 0.0
222
		if seqScan.Valid {
223
			seqScanMetric = float64(seqScan.Int64)
224
		}
225
		ch <- prometheus.MustNewConstMetric(
226
			statUserTablesSeqScan,
227
			prometheus.CounterValue,
228
			seqScanMetric,
229
			datnameLabel, schemanameLabel, relnameLabel,
230
		)
231

232
		seqTupReadMetric := 0.0
233
		if seqTupRead.Valid {
234
			seqTupReadMetric = float64(seqTupRead.Int64)
235
		}
236
		ch <- prometheus.MustNewConstMetric(
237
			statUserTablesSeqTupRead,
238
			prometheus.CounterValue,
239
			seqTupReadMetric,
240
			datnameLabel, schemanameLabel, relnameLabel,
241
		)
242

243
		idxScanMetric := 0.0
244
		if idxScan.Valid {
245
			idxScanMetric = float64(idxScan.Int64)
246
		}
247
		ch <- prometheus.MustNewConstMetric(
248
			statUserTablesIdxScan,
249
			prometheus.CounterValue,
250
			idxScanMetric,
251
			datnameLabel, schemanameLabel, relnameLabel,
252
		)
253

254
		idxTupFetchMetric := 0.0
255
		if idxTupFetch.Valid {
256
			idxTupFetchMetric = float64(idxTupFetch.Int64)
257
		}
258
		ch <- prometheus.MustNewConstMetric(
259
			statUserTablesIdxTupFetch,
260
			prometheus.CounterValue,
261
			idxTupFetchMetric,
262
			datnameLabel, schemanameLabel, relnameLabel,
263
		)
264

265
		nTupInsMetric := 0.0
266
		if nTupIns.Valid {
267
			nTupInsMetric = float64(nTupIns.Int64)
268
		}
269
		ch <- prometheus.MustNewConstMetric(
270
			statUserTablesNTupIns,
271
			prometheus.CounterValue,
272
			nTupInsMetric,
273
			datnameLabel, schemanameLabel, relnameLabel,
274
		)
275

276
		nTupUpdMetric := 0.0
277
		if nTupUpd.Valid {
278
			nTupUpdMetric = float64(nTupUpd.Int64)
279
		}
280
		ch <- prometheus.MustNewConstMetric(
281
			statUserTablesNTupUpd,
282
			prometheus.CounterValue,
283
			nTupUpdMetric,
284
			datnameLabel, schemanameLabel, relnameLabel,
285
		)
286

287
		nTupDelMetric := 0.0
288
		if nTupDel.Valid {
289
			nTupDelMetric = float64(nTupDel.Int64)
290
		}
291
		ch <- prometheus.MustNewConstMetric(
292
			statUserTablesNTupDel,
293
			prometheus.CounterValue,
294
			nTupDelMetric,
295
			datnameLabel, schemanameLabel, relnameLabel,
296
		)
297

298
		nTupHotUpdMetric := 0.0
299
		if nTupHotUpd.Valid {
300
			nTupHotUpdMetric = float64(nTupHotUpd.Int64)
301
		}
302
		ch <- prometheus.MustNewConstMetric(
303
			statUserTablesNTupHotUpd,
304
			prometheus.CounterValue,
305
			nTupHotUpdMetric,
306
			datnameLabel, schemanameLabel, relnameLabel,
307
		)
308

309
		nLiveTupMetric := 0.0
310
		if nLiveTup.Valid {
311
			nLiveTupMetric = float64(nLiveTup.Int64)
312
		}
313
		ch <- prometheus.MustNewConstMetric(
314
			statUserTablesNLiveTup,
315
			prometheus.GaugeValue,
316
			nLiveTupMetric,
317
			datnameLabel, schemanameLabel, relnameLabel,
318
		)
319

320
		nDeadTupMetric := 0.0
321
		if nDeadTup.Valid {
322
			nDeadTupMetric = float64(nDeadTup.Int64)
323
		}
324
		ch <- prometheus.MustNewConstMetric(
325
			statUserTablesNDeadTup,
326
			prometheus.GaugeValue,
327
			nDeadTupMetric,
328
			datnameLabel, schemanameLabel, relnameLabel,
329
		)
330

331
		nModSinceAnalyzeMetric := 0.0
332
		if nModSinceAnalyze.Valid {
333
			nModSinceAnalyzeMetric = float64(nModSinceAnalyze.Int64)
334
		}
335
		ch <- prometheus.MustNewConstMetric(
336
			statUserTablesNModSinceAnalyze,
337
			prometheus.GaugeValue,
338
			nModSinceAnalyzeMetric,
339
			datnameLabel, schemanameLabel, relnameLabel,
340
		)
341

342
		lastVacuumMetric := 0.0
343
		if lastVacuum.Valid {
344
			lastVacuumMetric = float64(lastVacuum.Time.Unix())
345
		}
346
		ch <- prometheus.MustNewConstMetric(
347
			statUserTablesLastVacuum,
348
			prometheus.GaugeValue,
349
			lastVacuumMetric,
350
			datnameLabel, schemanameLabel, relnameLabel,
351
		)
352

353
		lastAutovacuumMetric := 0.0
354
		if lastAutovacuum.Valid {
355
			lastAutovacuumMetric = float64(lastAutovacuum.Time.Unix())
356
		}
357
		ch <- prometheus.MustNewConstMetric(
358
			statUserTablesLastAutovacuum,
359
			prometheus.GaugeValue,
360
			lastAutovacuumMetric,
361
			datnameLabel, schemanameLabel, relnameLabel,
362
		)
363

364
		lastAnalyzeMetric := 0.0
365
		if lastAnalyze.Valid {
366
			lastAnalyzeMetric = float64(lastAnalyze.Time.Unix())
367
		}
368
		ch <- prometheus.MustNewConstMetric(
369
			statUserTablesLastAnalyze,
370
			prometheus.GaugeValue,
371
			lastAnalyzeMetric,
372
			datnameLabel, schemanameLabel, relnameLabel,
373
		)
374

375
		lastAutoanalyzeMetric := 0.0
376
		if lastAutoanalyze.Valid {
377
			lastAutoanalyzeMetric = float64(lastAutoanalyze.Time.Unix())
378
		}
379
		ch <- prometheus.MustNewConstMetric(
380
			statUserTablesLastAutoanalyze,
381
			prometheus.GaugeValue,
382
			lastAutoanalyzeMetric,
383
			datnameLabel, schemanameLabel, relnameLabel,
384
		)
385

386
		vacuumCountMetric := 0.0
387
		if vacuumCount.Valid {
388
			vacuumCountMetric = float64(vacuumCount.Int64)
389
		}
390
		ch <- prometheus.MustNewConstMetric(
391
			statUserTablesVacuumCount,
392
			prometheus.CounterValue,
393
			vacuumCountMetric,
394
			datnameLabel, schemanameLabel, relnameLabel,
395
		)
396

397
		autovacuumCountMetric := 0.0
398
		if autovacuumCount.Valid {
399
			autovacuumCountMetric = float64(autovacuumCount.Int64)
400
		}
401
		ch <- prometheus.MustNewConstMetric(
402
			statUserTablesAutovacuumCount,
403
			prometheus.CounterValue,
404
			autovacuumCountMetric,
405
			datnameLabel, schemanameLabel, relnameLabel,
406
		)
407

408
		analyzeCountMetric := 0.0
409
		if analyzeCount.Valid {
410
			analyzeCountMetric = float64(analyzeCount.Int64)
411
		}
412
		ch <- prometheus.MustNewConstMetric(
413
			statUserTablesAnalyzeCount,
414
			prometheus.CounterValue,
415
			analyzeCountMetric,
416
			datnameLabel, schemanameLabel, relnameLabel,
417
		)
418

419
		autoanalyzeCountMetric := 0.0
420
		if autoanalyzeCount.Valid {
421
			autoanalyzeCountMetric = float64(autoanalyzeCount.Int64)
422
		}
423
		ch <- prometheus.MustNewConstMetric(
424
			statUserTablesAutoanalyzeCount,
425
			prometheus.CounterValue,
426
			autoanalyzeCountMetric,
427
			datnameLabel, schemanameLabel, relnameLabel,
428
		)
429

430
		totalSizeMetric := 0.0
431
		if totalSize.Valid {
432
			totalSizeMetric = float64(totalSize.Int64)
433
		}
434
		ch <- prometheus.MustNewConstMetric(
435
			statUserTablesTotalSize,
436
			prometheus.GaugeValue,
437
			totalSizeMetric,
438
			datnameLabel, schemanameLabel, relnameLabel,
439
		)
440
	}
441

442
	if err := rows.Err(); err != nil {
443
		return err
444
	}
445
	return nil
446
}
447

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.