diff --git a/metrics/cloudwatch/cloudwatch.go b/metrics/cloudwatch/cloudwatch.go index b9baa75..ca0c2bd 100644 --- a/metrics/cloudwatch/cloudwatch.go +++ b/metrics/cloudwatch/cloudwatch.go @@ -1,15 +1,14 @@ package cloudwatch import ( + "fmt" "sync" - "time" - - "fmt" "github.com/aws/aws-sdk-go/aws" "github.com/aws/aws-sdk-go/service/cloudwatch" "github.com/aws/aws-sdk-go/service/cloudwatch/cloudwatchiface" + "github.com/go-kit/kit/log" "github.com/go-kit/kit/metrics" "github.com/go-kit/kit/metrics/generic" @@ -24,54 +23,54 @@ mtx sync.RWMutex namespace string svc cloudwatchiface.CloudWatchAPI - counters map[string]*Counter - gauges map[string]*Gauge - histograms map[string]*Histogram + counters map[string]*counter + gauges map[string]*gauge + histograms map[string]*histogram logger log.Logger } // New returns a CloudWatch object that may be used to create metrics. Namespace is // applied to all created metrics and maps to the CloudWatch namespace. // Callers must ensure that regular calls to Send are performed, either manually or with one of the helper methods. -func New(namespace string, logger log.Logger, svc cloudwatchiface.CloudWatchAPI) *CloudWatch { +func New(namespace string, svc cloudwatchiface.CloudWatchAPI, logger log.Logger) *CloudWatch { return &CloudWatch{ namespace: namespace, svc: svc, - counters: map[string]*Counter{}, - gauges: map[string]*Gauge{}, - histograms: map[string]*Histogram{}, + counters: map[string]*counter{}, + gauges: map[string]*gauge{}, + histograms: map[string]*histogram{}, logger: logger, } } // NewCounter returns a counter. Observations are aggregated and emitted once // per write invocation. -func (cw *CloudWatch) NewCounter(name string) *Counter { - c := NewCounter(name) +func (cw *CloudWatch) NewCounter(name string) metrics.Counter { cw.mtx.Lock() + defer cw.mtx.Unlock() + c := &counter{c: generic.NewCounter(name)} cw.counters[name] = c - cw.mtx.Unlock() return c } // NewGauge returns a gauge. Observations are aggregated and emitted once per // write invocation. -func (cw *CloudWatch) NewGauge(name string) *Gauge { - g := NewGauge(name) +func (cw *CloudWatch) NewGauge(name string) metrics.Gauge { cw.mtx.Lock() + defer cw.mtx.Unlock() + g := &gauge{g: generic.NewGauge(name)} cw.gauges[name] = g - cw.mtx.Unlock() return g } // NewHistogram returns a histogram. Observations are aggregated and emitted as // per-quantile gauges, once per write invocation. 50 is a good default value // for buckets. -func (cw *CloudWatch) NewHistogram(name string, buckets int) *Histogram { - h := NewHistogram(name, buckets) +func (cw *CloudWatch) NewHistogram(name string, buckets int) metrics.Histogram { cw.mtx.Lock() + defer cw.mtx.Unlock() + h := &histogram{h: generic.NewHistogram(name, buckets)} cw.histograms[name] = h - cw.mtx.Unlock() return h } @@ -87,14 +86,14 @@ } } -// Send will fire an api request to CloudWatch with the latest stats for -// all metrics. +// Send will fire an API request to CloudWatch with the latest stats for +// all metrics. It is preferred that the WriteLoop method is used. func (cw *CloudWatch) Send() error { cw.mtx.RLock() defer cw.mtx.RUnlock() now := time.Now() - datums := []*cloudwatch.MetricDatum{} + var datums []*cloudwatch.MetricDatum for name, c := range cw.counters { datums = append(datums, &cloudwatch.MetricDatum{ @@ -140,77 +139,56 @@ return err } -// Counter is a CloudWatch counter metric. -type Counter struct { +// counter is a CloudWatch counter metric. +type counter struct { c *generic.Counter } -// NewCounter returns a new usable counter metric. -func NewCounter(name string) *Counter { - return &Counter{ - c: generic.NewCounter(name), - } -} - // With implements counter -func (c *Counter) With(labelValues ...string) metrics.Counter { +func (c *counter) With(labelValues ...string) metrics.Counter { c.c = c.c.With(labelValues...).(*generic.Counter) return c } // Add implements counter. -func (c *Counter) Add(delta float64) { +func (c *counter) Add(delta float64) { c.c.Add(delta) } -// Gauge is a CloudWatch gauge metric. -type Gauge struct { +// gauge is a CloudWatch gauge metric. +type gauge struct { g *generic.Gauge } -// NewGauge returns a new usable gauge metric -func NewGauge(name string) *Gauge { - return &Gauge{ - g: generic.NewGauge(name), - } -} - // With implements gauge -func (g *Gauge) With(labelValues ...string) metrics.Gauge { +func (g *gauge) With(labelValues ...string) metrics.Gauge { g.g = g.g.With(labelValues...).(*generic.Gauge) return g } // Set implements gauge -func (g *Gauge) Set(value float64) { +func (g *gauge) Set(value float64) { g.g.Set(value) } // Add implements gauge -func (g *Gauge) Add(delta float64) { +func (g *gauge) Add(delta float64) { g.g.Add(delta) } -// Histogram is a CloudWatch histogram metric -type Histogram struct { +// histogram is a CloudWatch histogram metric +type histogram struct { h *generic.Histogram } -// NewHistogram returns a new usable histogram metric -func NewHistogram(name string, buckets int) *Histogram { - return &Histogram{ - h: generic.NewHistogram(name, buckets), - } -} - // With implements histogram -func (h *Histogram) With(labelValues ...string) metrics.Histogram { +func (h *histogram) With(labelValues ...string) metrics.Histogram { h.h = h.h.With(labelValues...).(*generic.Histogram) return h } // Observe implements histogram -func (h *Histogram) Observe(value float64) { +func (h *histogram) Observe(value float64) { h.h.Observe(value) } diff --git a/metrics/cloudwatch/cloudwatch_test.go b/metrics/cloudwatch/cloudwatch_test.go index db68c38..c0cf1d0 100644 --- a/metrics/cloudwatch/cloudwatch_test.go +++ b/metrics/cloudwatch/cloudwatch_test.go @@ -2,14 +2,13 @@ import ( "errors" + "fmt" + "sync" "testing" - - "sync" - - "fmt" "github.com/aws/aws-sdk-go/service/cloudwatch" "github.com/aws/aws-sdk-go/service/cloudwatch/cloudwatchiface" + "github.com/go-kit/kit/log" "github.com/go-kit/kit/metrics/teststat" ) @@ -65,7 +64,7 @@ namespace, name := "abc", "def" label, value := "label", "value" svc := newMockCloudWatch() - cw := New(namespace, log.NewNopLogger(), svc) + cw := New(namespace, svc, log.NewNopLogger()) counter := cw.NewCounter(name).With(label, value) valuef := func() float64 { err := cw.Send() @@ -88,7 +87,7 @@ namespace, name := "abc", "def" label, value := "label", "value" svc := newMockCloudWatch() - cw := New(namespace, log.NewNopLogger(), svc) + cw := New(namespace, svc, log.NewNopLogger()) gauge := cw.NewGauge(name).With(label, value) valuef := func() float64 { err := cw.Send() @@ -111,7 +110,7 @@ namespace, name := "abc", "def" label, value := "label", "value" svc := newMockCloudWatch() - cw := New(namespace, log.NewNopLogger(), svc) + cw := New(namespace, svc, log.NewNopLogger()) histogram := cw.NewHistogram(name, 50).With(label, value) n50 := fmt.Sprintf("%s_50", name) n90 := fmt.Sprintf("%s_90", name)