feat: add backup collector (pve_not_backed_up_total, pve_not_backed_up_info)
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
a62264edf8
commit
5e61f224c4
3 changed files with 107 additions and 0 deletions
69
collector/backup.go
Normal file
69
collector/backup.go
Normal file
|
|
@ -0,0 +1,69 @@
|
|||
package collector
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"log/slog"
|
||||
"strconv"
|
||||
|
||||
"github.com/prometheus/client_golang/prometheus"
|
||||
)
|
||||
|
||||
func init() {
|
||||
registerCollector("backup", func(logger *slog.Logger) Collector {
|
||||
return newBackupCollector(logger)
|
||||
})
|
||||
}
|
||||
|
||||
type backupCollector struct {
|
||||
logger *slog.Logger
|
||||
}
|
||||
|
||||
func newBackupCollector(logger *slog.Logger) *backupCollector {
|
||||
return &backupCollector{logger: logger}
|
||||
}
|
||||
|
||||
type backupNotBackedUpResponse struct {
|
||||
Data []backupNotBackedUpEntry `json:"data"`
|
||||
}
|
||||
|
||||
type backupNotBackedUpEntry struct {
|
||||
VMID int `json:"vmid"`
|
||||
Name string `json:"name"`
|
||||
Type string `json:"type"`
|
||||
}
|
||||
|
||||
var (
|
||||
notBackedUpTotalDesc = prometheus.NewDesc(
|
||||
prometheus.BuildFQName(namespace, "", "not_backed_up_total"),
|
||||
"Whether a guest is not backed up (1 = not backed up).",
|
||||
[]string{"id"},
|
||||
nil,
|
||||
)
|
||||
notBackedUpInfoDesc = prometheus.NewDesc(
|
||||
prometheus.BuildFQName(namespace, "", "not_backed_up_info"),
|
||||
"Information about a guest that is not backed up.",
|
||||
[]string{"id"},
|
||||
nil,
|
||||
)
|
||||
)
|
||||
|
||||
func (c *backupCollector) Update(client *Client, ch chan<- prometheus.Metric) error {
|
||||
body, err := client.Get("/cluster/backup-info/not-backed-up")
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to get /cluster/backup-info/not-backed-up: %w", err)
|
||||
}
|
||||
|
||||
var resp backupNotBackedUpResponse
|
||||
if err := json.Unmarshal(body, &resp); err != nil {
|
||||
return fmt.Errorf("failed to parse backup-info response: %w", err)
|
||||
}
|
||||
|
||||
for _, entry := range resp.Data {
|
||||
id := entry.Type + "/" + strconv.Itoa(entry.VMID)
|
||||
ch <- prometheus.MustNewConstMetric(notBackedUpTotalDesc, prometheus.GaugeValue, 1, id)
|
||||
ch <- prometheus.MustNewConstMetric(notBackedUpInfoDesc, prometheus.GaugeValue, 1, id)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
37
collector/backup_test.go
Normal file
37
collector/backup_test.go
Normal file
|
|
@ -0,0 +1,37 @@
|
|||
package collector
|
||||
|
||||
import (
|
||||
"log/slog"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
"github.com/prometheus/client_golang/prometheus"
|
||||
"github.com/prometheus/client_golang/prometheus/testutil"
|
||||
)
|
||||
|
||||
func TestBackupCollector(t *testing.T) {
|
||||
client := newTestClient(t, map[string]string{
|
||||
"/cluster/backup-info/not-backed-up": "backup_not_backed_up.json",
|
||||
})
|
||||
|
||||
collector := newBackupCollector(slog.Default())
|
||||
adapter := &testCollectorAdapter{client: client, collector: collector}
|
||||
|
||||
reg := prometheus.NewRegistry()
|
||||
reg.MustRegister(adapter)
|
||||
|
||||
expected := `
|
||||
# HELP pve_not_backed_up_info Information about a guest that is not backed up.
|
||||
# TYPE pve_not_backed_up_info gauge
|
||||
pve_not_backed_up_info{id="qemu/100"} 1
|
||||
# HELP pve_not_backed_up_total Whether a guest is not backed up (1 = not backed up).
|
||||
# TYPE pve_not_backed_up_total gauge
|
||||
pve_not_backed_up_total{id="qemu/100"} 1
|
||||
`
|
||||
|
||||
if err := testutil.GatherAndCompare(reg, strings.NewReader(expected),
|
||||
"pve_not_backed_up_total", "pve_not_backed_up_info",
|
||||
); err != nil {
|
||||
t.Errorf("unexpected metrics: %s", err)
|
||||
}
|
||||
}
|
||||
1
collector/fixtures/backup_not_backed_up.json
Normal file
1
collector/fixtures/backup_not_backed_up.json
Normal file
|
|
@ -0,0 +1 @@
|
|||
{"data":[{"vmid":100,"name":"pve-backup.freyja.sip.is","type":"qemu"}]}
|
||||
Loading…
Add table
Add a link
Reference in a new issue