autocert: add metrics for renewal count, total and next expiration (#2019)

This commit is contained in:
Caleb Doxsey 2021-03-25 08:03:04 -06:00 committed by GitHub
parent 7eac4283ed
commit 4cc697ace4
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 102 additions and 0 deletions

View file

@ -17,6 +17,7 @@ import (
"github.com/pomerium/pomerium/config"
"github.com/pomerium/pomerium/internal/httputil"
"github.com/pomerium/pomerium/internal/log"
"github.com/pomerium/pomerium/internal/telemetry/metrics"
)
var (
@ -177,6 +178,7 @@ func (mgr *Manager) obtainCert(domain string, cm *certmagic.Config) (certmagic.C
log.Error().Err(err).Msg("autocert failed to obtain client certificate")
return certmagic.Certificate{}, errObtainCertFailed
}
metrics.RecordAutocertRenewal()
cert, err = cm.CacheManagedCertificate(domain)
}
return cert, err
@ -226,6 +228,8 @@ func (mgr *Manager) updateAutocert(cfg *config.Config) error {
cfg.AutoCertificates = append(cfg.AutoCertificates, cert.Certificate)
}
metrics.RecordAutocertCertificates(cfg.AutoCertificates)
return nil
}

View file

@ -0,0 +1,90 @@
package metrics
import (
"crypto/tls"
"crypto/x509"
"sync/atomic"
"time"
"go.opencensus.io/metric"
"github.com/pomerium/pomerium/pkg/metrics"
)
var (
autocertRenewalsTotal int64
autocertCertificatesTotal int64
autocertCertificateNextExpiresSeconds int64
)
func registerAutocertMetrics(registry *metric.Registry) error {
gaugeMetrics := []struct {
name string
desc string
ptr *int64
}{
{metrics.AutocertCertificatesTotal, "Number of certificates tracked by autocert.", &autocertCertificatesTotal},
{metrics.AutocertCertificateNextExpiresSeconds, "The next expiration timestamp in seconds.", &autocertCertificateNextExpiresSeconds},
}
for _, gm := range gaugeMetrics {
m, err := registry.AddInt64DerivedGauge(gm.name, metric.WithDescription(gm.desc))
if err != nil {
return err
}
err = m.UpsertEntry(func() int64 {
return atomic.LoadInt64(gm.ptr)
})
if err != nil {
return err
}
}
cumulativeMetrics := []struct {
name string
desc string
ptr *int64
}{
{metrics.AutocertRenewalsTotal, "Number of autocert renewals.", &autocertRenewalsTotal},
}
for _, cm := range cumulativeMetrics {
m, err := registry.AddInt64DerivedCumulative(cm.name, metric.WithDescription(cm.desc))
if err != nil {
return err
}
err = m.UpsertEntry(func() int64 {
return atomic.LoadInt64(cm.ptr)
})
if err != nil {
return err
}
}
return nil
}
// RecordAutocertRenewal records an autocert renewal.
func RecordAutocertRenewal() {
atomic.AddInt64(&autocertRenewalsTotal, 1)
}
// RecordAutocertCertificates records the next timestamp an autocert certificate will expire.
func RecordAutocertCertificates(certs []tls.Certificate) {
var expiresAt time.Time
for _, cert := range certs {
if len(cert.Certificate) == 0 {
continue
}
c, err := x509.ParseCertificate(cert.Certificate[0])
if err != nil {
continue
}
if expiresAt.IsZero() || c.NotAfter.Before(expiresAt) {
expiresAt = c.NotAfter
}
}
if !expiresAt.IsZero() {
atomic.StoreInt64(&autocertCertificateNextExpiresSeconds, expiresAt.Unix())
}
atomic.StoreInt64(&autocertCertificatesTotal, int64(len(certs)))
}

View file

@ -67,6 +67,11 @@ func (r *metricRegistry) init() {
if err != nil {
log.Error().Err(err).Msg("telemetry/metrics: failed to register policy count metric")
}
err = registerAutocertMetrics(r.registry)
if err != nil {
log.Error().Err(err).Msg("telemetry/metrics: failed to register autocert metrics")
}
})
}

View file

@ -4,6 +4,9 @@ package metrics
// metrics
const (
AutocertRenewalsTotal = "autocert_renewals_total"
AutocertCertificatesTotal = "autocert_certificates_total"
AutocertCertificateNextExpiresSeconds = "autocert_certificate_next_expires_seconds"
// ConfigLastReloadTimestampSeconds is unix timestamp when configuration was last reloaded
ConfigLastReloadTimestampSeconds = "config_last_reload_success_timestamp"
// ConfigLastReloadSuccess is set to 1 if last configuration was successfully reloaded