Files
MusicServer/internal/metrics/app.go
SansanandClaude Opus 5.5 f79f51ea4c
CI / integration (push) Failing after 14s
CI / docker (push) Failing after 20s
CI / test (push) Successful in 1m10s
CI / publish (push) Skipped
Expose Prometheus metrics on a separate port
Metrics are served on METRICS_PORT (default 2112, "off" to disable), never on
the public port. Besides the Go runtime and process metrics this adds:

- http_requests_total and http_request_duration_seconds per route pattern,
  from an Echo middleware.
- musicserver_songs_requested_total and musicserver_songs_played_total by
  pick mode (random, low, classic). The mode is now stored with each queued
  song (migration 000006, not released yet).
- Library size, sync duration, last successful sync, broken songs from the
  last full sync, and the database connection pool.

Refs #35, #36, #37

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-11 21:57:58 +02:00

54 lines
2.2 KiB
Go

package metrics
import (
"github.com/prometheus/client_golang/prometheus"
"github.com/prometheus/client_golang/prometheus/promauto"
)
// MusicServer's own metrics. Labels only take values from small fixed sets: never song
// names, IDs, tokens or IPs, since every value creates a new time series.
var (
// SongsRequested counts random songs handed out, by how they were picked.
SongsRequested = promauto.NewCounterVec(prometheus.CounterOpts{
Name: "musicserver_songs_requested_total",
Help: "Random songs handed out, by how they were picked (random, low, classic).",
}, []string{"mode"})
// SongsPlayed counts songs marked as played, by how they were picked.
SongsPlayed = promauto.NewCounterVec(prometheus.CounterOpts{
Name: "musicserver_songs_played_total",
Help: "Songs marked as played, by how they were picked (random, low, classic).",
}, []string{"mode"})
// LibrarySoundtracks is the number of soundtracks in the library.
LibrarySoundtracks = promauto.NewGauge(prometheus.GaugeOpts{
Name: "musicserver_library_soundtracks",
Help: "Soundtracks in the library, counted at startup and after each sync.",
})
// LibrarySongs is the number of songs in the library.
LibrarySongs = promauto.NewGauge(prometheus.GaugeOpts{
Name: "musicserver_library_songs",
Help: "Songs in the library, counted at startup and after each sync.",
})
// SyncDuration is how long syncs take, by type.
SyncDuration = promauto.NewHistogramVec(prometheus.HistogramOpts{
Name: "musicserver_sync_duration_seconds",
Help: "How long a sync took, by type (full, changes).",
Buckets: []float64{1, 5, 10, 30, 60, 120, 300, 600, 1200, 1800, 3600},
}, []string{"type"})
// SyncLastSuccess is when the last sync without errors finished.
SyncLastSuccess = promauto.NewGauge(prometheus.GaugeOpts{
Name: "musicserver_sync_last_success_timestamp_seconds",
Help: "Unix time when the last sync without errors finished.",
})
// BrokenSongs is the number of songs the last full sync found missing and removed.
BrokenSongs = promauto.NewGauge(prometheus.GaugeOpts{
Name: "musicserver_broken_songs",
Help: "Songs whose file was missing in the last full sync. They are removed from the library.",
})
)