247 lines
7.8 KiB
Go
247 lines
7.8 KiB
Go
package tsm1
|
|
|
|
import (
|
|
"sort"
|
|
"sync"
|
|
|
|
"github.com/prometheus/client_golang/prometheus"
|
|
)
|
|
|
|
// The following package variables act as singletons, to be shared by all Engine
|
|
// instantiations. This allows multiple Engines to be instantiated within the
|
|
// same process.
|
|
var (
|
|
bms *blockMetrics
|
|
mmu sync.RWMutex
|
|
)
|
|
|
|
// PrometheusCollectors returns all prometheus metrics for the tsm1 package.
|
|
func PrometheusCollectors() []prometheus.Collector {
|
|
mmu.RLock()
|
|
defer mmu.RUnlock()
|
|
|
|
var collectors []prometheus.Collector
|
|
if bms != nil {
|
|
collectors = append(collectors, bms.compactionMetrics.PrometheusCollectors()...)
|
|
collectors = append(collectors, bms.fileMetrics.PrometheusCollectors()...)
|
|
collectors = append(collectors, bms.cacheMetrics.PrometheusCollectors()...)
|
|
}
|
|
return collectors
|
|
}
|
|
|
|
// namespace is the leading part of all published metrics for the Storage service.
|
|
const namespace = "storage"
|
|
|
|
const compactionSubsystem = "compactions" // sub-system associated with metrics for compactions.
|
|
const fileStoreSubsystem = "tsm_files" // sub-system associated with metrics for TSM files.
|
|
const cacheSubsystem = "cache" // sub-system associated with metrics for the cache.
|
|
|
|
// blockMetrics are a set of metrics concerned with tracking data about block storage.
|
|
type blockMetrics struct {
|
|
labels prometheus.Labels
|
|
*compactionMetrics
|
|
*fileMetrics
|
|
*cacheMetrics
|
|
}
|
|
|
|
// newBlockMetrics initialises the prometheus metrics for the block subsystem.
|
|
func newBlockMetrics(labels prometheus.Labels) *blockMetrics {
|
|
return &blockMetrics{
|
|
labels: labels,
|
|
compactionMetrics: newCompactionMetrics(labels),
|
|
fileMetrics: newFileMetrics(labels),
|
|
cacheMetrics: newCacheMetrics(labels),
|
|
}
|
|
}
|
|
|
|
// PrometheusCollectors satisfies the prom.PrometheusCollector interface.
|
|
func (m *blockMetrics) PrometheusCollectors() []prometheus.Collector {
|
|
var metrics []prometheus.Collector
|
|
metrics = append(metrics, m.compactionMetrics.PrometheusCollectors()...)
|
|
metrics = append(metrics, m.fileMetrics.PrometheusCollectors()...)
|
|
metrics = append(metrics, m.cacheMetrics.PrometheusCollectors()...)
|
|
return metrics
|
|
}
|
|
|
|
// compactionMetrics are a set of metrics concerned with tracking data about compactions.
|
|
type compactionMetrics struct {
|
|
CompactionsActive *prometheus.GaugeVec
|
|
CompactionDuration *prometheus.HistogramVec
|
|
CompactionQueue *prometheus.GaugeVec
|
|
|
|
// The following metrics include a ``"status" = {ok, error}` label
|
|
Compactions *prometheus.CounterVec
|
|
}
|
|
|
|
// newCompactionMetrics initialises the prometheus metrics for compactions.
|
|
func newCompactionMetrics(labels prometheus.Labels) *compactionMetrics {
|
|
names := []string{"level"} // All compaction metrics have a `level` label.
|
|
for k := range labels {
|
|
names = append(names, k)
|
|
}
|
|
sort.Strings(names)
|
|
|
|
totalCompactionsNames := append(append([]string(nil), names...), []string{"reason", "status"}...)
|
|
sort.Strings(totalCompactionsNames)
|
|
|
|
return &compactionMetrics{
|
|
Compactions: prometheus.NewCounterVec(prometheus.CounterOpts{
|
|
Namespace: namespace,
|
|
Subsystem: compactionSubsystem,
|
|
Name: "total",
|
|
Help: "Number of times cache snapshotted or TSM compaction attempted.",
|
|
}, totalCompactionsNames),
|
|
CompactionsActive: prometheus.NewGaugeVec(prometheus.GaugeOpts{
|
|
Namespace: namespace,
|
|
Subsystem: compactionSubsystem,
|
|
Name: "active",
|
|
Help: "Number of active compactions.",
|
|
}, names),
|
|
CompactionDuration: prometheus.NewHistogramVec(prometheus.HistogramOpts{
|
|
Namespace: namespace,
|
|
Subsystem: compactionSubsystem,
|
|
Name: "duration_seconds",
|
|
Help: "Time taken for a successful compaction or snapshot.",
|
|
// 30 buckets spaced exponentially between 5s and ~53 minutes.
|
|
Buckets: prometheus.ExponentialBuckets(5.0, 1.25, 30),
|
|
}, names),
|
|
CompactionQueue: prometheus.NewGaugeVec(prometheus.GaugeOpts{
|
|
Namespace: namespace,
|
|
Subsystem: compactionSubsystem,
|
|
Name: "queued",
|
|
Help: "Number of queued compactions.",
|
|
}, names),
|
|
}
|
|
}
|
|
|
|
// PrometheusCollectors satisfies the prom.PrometheusCollector interface.
|
|
func (m *compactionMetrics) PrometheusCollectors() []prometheus.Collector {
|
|
return []prometheus.Collector{
|
|
m.Compactions,
|
|
m.CompactionsActive,
|
|
m.CompactionDuration,
|
|
m.CompactionQueue,
|
|
}
|
|
}
|
|
|
|
// fileMetrics are a set of metrics concerned with tracking data about compactions.
|
|
type fileMetrics struct {
|
|
DiskSize *prometheus.GaugeVec
|
|
Files *prometheus.GaugeVec
|
|
}
|
|
|
|
// newFileMetrics initialises the prometheus metrics for tracking files on disk.
|
|
func newFileMetrics(labels prometheus.Labels) *fileMetrics {
|
|
var names []string
|
|
for k := range labels {
|
|
names = append(names, k)
|
|
}
|
|
sort.Strings(names)
|
|
|
|
return &fileMetrics{
|
|
DiskSize: prometheus.NewGaugeVec(prometheus.GaugeOpts{
|
|
Namespace: namespace,
|
|
Subsystem: fileStoreSubsystem,
|
|
Name: "disk_bytes",
|
|
Help: "Number of bytes TSM files using on disk.",
|
|
}, names),
|
|
Files: prometheus.NewGaugeVec(prometheus.GaugeOpts{
|
|
Namespace: namespace,
|
|
Subsystem: fileStoreSubsystem,
|
|
Name: "total",
|
|
Help: "Number of files.",
|
|
}, names),
|
|
}
|
|
}
|
|
|
|
// PrometheusCollectors satisfies the prom.PrometheusCollector interface.
|
|
func (m *fileMetrics) PrometheusCollectors() []prometheus.Collector {
|
|
return []prometheus.Collector{
|
|
m.DiskSize,
|
|
m.Files,
|
|
}
|
|
}
|
|
|
|
// cacheMetrics are a set of metrics concerned with tracking data about the TSM Cache.
|
|
type cacheMetrics struct {
|
|
MemSize *prometheus.GaugeVec
|
|
DiskSize *prometheus.GaugeVec
|
|
SnapshotsActive *prometheus.GaugeVec
|
|
Age *prometheus.GaugeVec
|
|
SnapshottedBytes *prometheus.CounterVec
|
|
|
|
// The following metrics include a ``"status" = {ok, error, dropped}` label
|
|
WrittenBytes *prometheus.CounterVec
|
|
Writes *prometheus.CounterVec
|
|
}
|
|
|
|
// newCacheMetrics initialises the prometheus metrics for compactions.
|
|
func newCacheMetrics(labels prometheus.Labels) *cacheMetrics {
|
|
var names []string
|
|
for k := range labels {
|
|
names = append(names, k)
|
|
}
|
|
sort.Strings(names)
|
|
|
|
writeNames := append(append([]string(nil), names...), "status")
|
|
sort.Strings(writeNames)
|
|
|
|
return &cacheMetrics{
|
|
MemSize: prometheus.NewGaugeVec(prometheus.GaugeOpts{
|
|
Namespace: namespace,
|
|
Subsystem: cacheSubsystem,
|
|
Name: "inuse_bytes",
|
|
Help: "In-memory size of cache.",
|
|
}, names),
|
|
DiskSize: prometheus.NewGaugeVec(prometheus.GaugeOpts{
|
|
Namespace: namespace,
|
|
Subsystem: cacheSubsystem,
|
|
Name: "disk_bytes",
|
|
Help: "Number of bytes on disk used by snapshot data.",
|
|
}, names),
|
|
SnapshotsActive: prometheus.NewGaugeVec(prometheus.GaugeOpts{
|
|
Namespace: namespace,
|
|
Subsystem: cacheSubsystem,
|
|
Name: "snapshots_active",
|
|
Help: "Number of active concurrent snapshots (>1 when splitting the cache).",
|
|
}, names),
|
|
Age: prometheus.NewGaugeVec(prometheus.GaugeOpts{
|
|
Namespace: namespace,
|
|
Subsystem: cacheSubsystem,
|
|
Name: "age_seconds",
|
|
Help: "Age in seconds of the current cache (time since last snapshot or initialisation).",
|
|
}, names),
|
|
SnapshottedBytes: prometheus.NewCounterVec(prometheus.CounterOpts{
|
|
Namespace: namespace,
|
|
Subsystem: cacheSubsystem,
|
|
Name: "snapshot_bytes",
|
|
Help: "Number of bytes snapshotted.",
|
|
}, names),
|
|
WrittenBytes: prometheus.NewCounterVec(prometheus.CounterOpts{
|
|
Namespace: namespace,
|
|
Subsystem: cacheSubsystem,
|
|
Name: "written_bytes",
|
|
Help: "Number of bytes successfully written to the Cache.",
|
|
}, writeNames),
|
|
Writes: prometheus.NewCounterVec(prometheus.CounterOpts{
|
|
Namespace: namespace,
|
|
Subsystem: cacheSubsystem,
|
|
Name: "writes_total",
|
|
Help: "Number of writes to the Cache.",
|
|
}, writeNames),
|
|
}
|
|
}
|
|
|
|
// PrometheusCollectors satisfies the prom.PrometheusCollector interface.
|
|
func (m *cacheMetrics) PrometheusCollectors() []prometheus.Collector {
|
|
return []prometheus.Collector{
|
|
m.MemSize,
|
|
m.DiskSize,
|
|
m.SnapshotsActive,
|
|
m.Age,
|
|
m.SnapshottedBytes,
|
|
m.WrittenBytes,
|
|
m.Writes,
|
|
}
|
|
}
|