Skip to content

Commit

Permalink
Merge pull request #10156 from gyuho/metrics-health
Browse files Browse the repository at this point in the history
etcdserver: add "etcd_server_health_success/failures"
  • Loading branch information
gyuho authored Oct 9, 2018
2 parents ac47540 + 7524cc6 commit ba606bf
Show file tree
Hide file tree
Showing 2 changed files with 59 additions and 6 deletions.
32 changes: 27 additions & 5 deletions etcdserver/api/etcdhttp/metrics.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ import (
"go.etcd.io/etcd/etcdserver/etcdserverpb"
"go.etcd.io/etcd/raft"

"github.com/prometheus/client_golang/prometheus"
"github.com/prometheus/client_golang/prometheus/promhttp"
)

Expand All @@ -43,11 +44,6 @@ func HandlePrometheus(mux *http.ServeMux) {
mux.Handle(pathMetrics, promhttp.Handler())
}

// HandleHealth registers health handler on '/health'.
func HandleHealth(mux *http.ServeMux, srv etcdserver.ServerV2) {
mux.Handle(PathHealth, NewHealthHandler(func() Health { return checkHealth(srv) }))
}

// NewHealthHandler handles '/health' requests.
func NewHealthHandler(hfunc func() Health) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
Expand All @@ -67,6 +63,26 @@ func NewHealthHandler(hfunc func() Health) http.HandlerFunc {
}
}

var (
healthSuccess = prometheus.NewCounter(prometheus.CounterOpts{
Namespace: "etcd",
Subsystem: "server",
Name: "health_success",
Help: "The total number of successful health checks",
})
healthFailed = prometheus.NewCounter(prometheus.CounterOpts{
Namespace: "etcd",
Subsystem: "server",
Name: "health_failures",
Help: "The total number of failed health checks",
})
)

func init() {
prometheus.MustRegister(healthSuccess)
prometheus.MustRegister(healthFailed)
}

// Health defines etcd server health status.
// TODO: remove manual parsing in etcdctl cluster-health
type Health struct {
Expand Down Expand Up @@ -97,5 +113,11 @@ func checkHealth(srv etcdserver.ServerV2) Health {
h.Health = "false"
}
}

if h.Health == "true" {
healthSuccess.Inc()
} else {
healthFailed.Inc()
}
return h
}
33 changes: 32 additions & 1 deletion integration/metrics_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,14 +16,15 @@ package integration

import (
"context"
"net/http"
"strconv"
"testing"
"time"

"go.etcd.io/etcd/etcdserver"

pb "go.etcd.io/etcd/etcdserver/etcdserverpb"
"go.etcd.io/etcd/pkg/testutil"
"go.etcd.io/etcd/pkg/transport"
)

// TestMetricDbSizeBoot checks that the db size metric is set on boot.
Expand Down Expand Up @@ -165,3 +166,33 @@ func TestMetricQuotaBackendBytes(t *testing.T) {
t.Fatalf("expected %d, got %f", etcdserver.DefaultQuotaBytes, qv)
}
}

func TestMetricsHealth(t *testing.T) {
defer testutil.AfterTest(t)
clus := NewClusterV3(t, &ClusterConfig{Size: 1})
defer clus.Terminate(t)

tr, err := transport.NewTransport(transport.TLSInfo{}, 5*time.Second)
if err != nil {
t.Fatal(err)
}
u := clus.Members[0].ClientURLs[0]
u.Path = "/health"
resp, err := tr.RoundTrip(&http.Request{
Header: make(http.Header),
Method: http.MethodGet,
URL: &u,
})
resp.Body.Close()
if err != nil {
t.Fatal(err)
}

hv, err := clus.Members[0].Metric("etcd_server_health_success")
if err != nil {
t.Fatal(err)
}
if hv != "1" {
t.Fatalf("expected '1' from /health, got %q", hv)
}
}

0 comments on commit ba606bf

Please sign in to comment.