mirror of
https://github.com/safing/portbase
synced 2025-09-01 10:09:50 +00:00
Add config options for metrics
This commit is contained in:
parent
4a05c26339
commit
aef3f26ad3
4 changed files with 89 additions and 16 deletions
|
@ -90,7 +90,7 @@ func writeMetricsTo(ctx context.Context, url string) error {
|
|||
}
|
||||
|
||||
// Create request
|
||||
req, err := http.NewRequestWithContext(ctx, http.MethodPut, url, buf)
|
||||
req, err := http.NewRequestWithContext(ctx, http.MethodPost, url, buf)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to create request: %w", err)
|
||||
}
|
||||
|
@ -118,6 +118,7 @@ func writeMetricsTo(ctx context.Context, url string) error {
|
|||
}
|
||||
|
||||
func metricsWriter(ctx context.Context) error {
|
||||
pushURL := pushOption()
|
||||
ticker := time.NewTicker(10 * time.Second)
|
||||
defer ticker.Stop()
|
||||
|
||||
|
|
69
metrics/config.go
Normal file
69
metrics/config.go
Normal file
|
@ -0,0 +1,69 @@
|
|||
package metrics
|
||||
|
||||
import (
|
||||
"flag"
|
||||
|
||||
"github.com/safing/portbase/config"
|
||||
)
|
||||
|
||||
// Configuration Keys
|
||||
var (
|
||||
CfgOptionInstanceKey = "core/metrics/instance"
|
||||
instanceOption config.StringOption
|
||||
cfgOptionInstanceOrder = 0
|
||||
|
||||
CfgOptionPushKey = "core/metrics/push"
|
||||
pushOption config.StringOption
|
||||
cfgOptionPushOrder = 0
|
||||
|
||||
pushFlag string
|
||||
instanceFlag string
|
||||
)
|
||||
|
||||
func init() {
|
||||
flag.StringVar(&pushFlag, "push-metrics", "", "Set default URL to push prometheus metrics to.")
|
||||
flag.StringVar(&instanceFlag, "metrics-instance", "", "Set the default global instance label.")
|
||||
}
|
||||
|
||||
func prepConfig() error {
|
||||
err := config.Register(&config.Option{
|
||||
Name: "Metrics Instance Name",
|
||||
Key: CfgOptionInstanceKey,
|
||||
Description: "Define the prometheus instance label for exported metrics. Please note that changing the instance name will reset persisted metrics.",
|
||||
OptType: config.OptTypeString,
|
||||
ExpertiseLevel: config.ExpertiseLevelExpert,
|
||||
ReleaseLevel: config.ReleaseLevelStable,
|
||||
DefaultValue: instanceFlag,
|
||||
RequiresRestart: true,
|
||||
Annotations: config.Annotations{
|
||||
config.DisplayOrderAnnotation: cfgOptionInstanceOrder,
|
||||
config.CategoryAnnotation: "Metrics",
|
||||
},
|
||||
ValidationRegex: "^(" + prometheusBaseFormt + ")?$",
|
||||
})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
instanceOption = config.Concurrent.GetAsString(CfgOptionInstanceKey, instanceFlag)
|
||||
|
||||
err = config.Register(&config.Option{
|
||||
Name: "Push Metrics",
|
||||
Key: CfgOptionPushKey,
|
||||
Description: "Push metrics to this URL in the prometheus format.",
|
||||
OptType: config.OptTypeString,
|
||||
ExpertiseLevel: config.ExpertiseLevelExpert,
|
||||
ReleaseLevel: config.ReleaseLevelStable,
|
||||
DefaultValue: pushFlag,
|
||||
RequiresRestart: true,
|
||||
Annotations: config.Annotations{
|
||||
config.DisplayOrderAnnotation: cfgOptionPushOrder,
|
||||
config.CategoryAnnotation: "Metrics",
|
||||
},
|
||||
})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
pushOption = config.Concurrent.GetAsString(CfgOptionPushKey, pushFlag)
|
||||
|
||||
return nil
|
||||
}
|
|
@ -15,7 +15,8 @@ import (
|
|||
|
||||
// PrometheusFormatRequirement is required format defined by prometheus for
|
||||
// metric and label names.
|
||||
const PrometheusFormatRequirement = "[a-zA-Z_][a-zA-Z0-9_]*"
|
||||
const prometheusBaseFormt = "[a-zA-Z_][a-zA-Z0-9_]*"
|
||||
const PrometheusFormatRequirement = "^" + prometheusBaseFormt + "$"
|
||||
|
||||
var prometheusFormat = regexp.MustCompile(PrometheusFormatRequirement)
|
||||
|
||||
|
@ -60,7 +61,7 @@ type Options struct {
|
|||
|
||||
func newMetricBase(id string, labels map[string]string, opts Options) (*metricBase, error) {
|
||||
// Check formats.
|
||||
if !prometheusFormat.MatchString(id) {
|
||||
if !prometheusFormat.MatchString(strings.ReplaceAll(id, "/", "_")) {
|
||||
return nil, fmt.Errorf("metric name %q must match %s", id, PrometheusFormatRequirement)
|
||||
}
|
||||
for labelName := range labels {
|
||||
|
@ -75,6 +76,11 @@ func newMetricBase(id string, labels map[string]string, opts Options) (*metricBa
|
|||
opts.Permission = api.PermitUser
|
||||
}
|
||||
|
||||
// Ensure that labels is a map.
|
||||
if labels == nil {
|
||||
labels = make(map[string]string)
|
||||
}
|
||||
|
||||
// Create metric base.
|
||||
base := &metricBase{
|
||||
Identifier: id,
|
||||
|
|
|
@ -2,7 +2,6 @@ package metrics
|
|||
|
||||
import (
|
||||
"errors"
|
||||
"flag"
|
||||
"fmt"
|
||||
"sort"
|
||||
"sync"
|
||||
|
@ -20,9 +19,6 @@ var (
|
|||
metricNamespace string
|
||||
globalLabels = make(map[string]string)
|
||||
|
||||
pushURL string
|
||||
metricInstance string
|
||||
|
||||
// ErrAlreadyStarted is returned when an operation is only valid before the
|
||||
// first metric is registered, and is called after.
|
||||
ErrAlreadyStarted = errors.New("can only be changed before first metric is registered")
|
||||
|
@ -36,29 +32,30 @@ var (
|
|||
)
|
||||
|
||||
func init() {
|
||||
flag.StringVar(&pushURL, "push-metrics", "", "URL to push prometheus metrics to")
|
||||
flag.StringVar(&metricInstance, "metrics-instance", "", "Set the global instance label")
|
||||
|
||||
module = modules.Register("metrics", prep, start, stop, "database", "api")
|
||||
}
|
||||
|
||||
func prep() error {
|
||||
return prepConfig()
|
||||
}
|
||||
|
||||
func start() error {
|
||||
// Add metric instance name as global variable if set.
|
||||
if metricInstance != "" {
|
||||
if err := AddGlobalLabel("instance", metricInstance); err != nil {
|
||||
if instanceOption() != "" {
|
||||
if err := AddGlobalLabel("instance", instanceOption()); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return registerInfoMetric()
|
||||
}
|
||||
if err := registerInfoMetric(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
func start() error {
|
||||
if err := registerAPI(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if pushURL != "" {
|
||||
if pushOption() != "" {
|
||||
module.StartServiceWorker("metric pusher", 0, metricsWriter)
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue