diff --git a/appoptics/appoptics.go b/appoptics/appoptics.go index a55951f..8566e7b 100644 --- a/appoptics/appoptics.go +++ b/appoptics/appoptics.go @@ -25,7 +25,6 @@ func translateTimerAttributes(d time.Duration) (attrs map[string]interface{}) { // measurements API. type Reporter struct { Token string - Tags metrics.Labels Interval time.Duration Registry metrics.Registry Percentiles []float64 // percentiles to report on histogram metrics @@ -38,7 +37,7 @@ type Reporter struct { // NewReporter creates a new reporter. func NewReporter(registry metrics.Registry, interval time.Duration, token string, - tags metrics.Labels, percentiles []float64, timeUnits time.Duration, + percentiles []float64, timeUnits time.Duration, prefix string, whitelistedRuntimeMetrics []string, measurementsURI string) *Reporter { @@ -53,7 +52,7 @@ func NewReporter(registry metrics.Registry, interval time.Duration, token string } } - return &Reporter{token, tags, interval, registry, percentiles, prefix, + return &Reporter{token, interval, registry, percentiles, prefix, whitelist, translateTimerAttributes(timeUnits), int64(interval / time.Second), measurementsURI} } @@ -64,9 +63,9 @@ func NewReporter(registry metrics.Registry, interval time.Duration, token string // only a subset of the runtime.* metrics that are gathered by go-metrics. // Passing an empty slice disables uploads for all runtime.* metrics. func AppOptics(registry metrics.Registry, interval time.Duration, token string, - tags metrics.Labels, percentiles []float64, timeUnits time.Duration, + percentiles []float64, timeUnits time.Duration, prefix string, whitelistedRuntimeMetrics []string, measurementsURI string) { - NewReporter(registry, interval, token, tags, percentiles, + NewReporter(registry, interval, token, percentiles, timeUnits, prefix, whitelistedRuntimeMetrics, measurementsURI).Run() } @@ -114,17 +113,6 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc name = rep.Prefix + name measurement := Measurement{} measurement[Period] = rep.Interval.Seconds() - - mergedTags := metrics.Labels{} - copyTags := func(tags metrics.Labels) { - for tagName, tagValue := range tags { - mergedTags[tagName] = tagValue - } - measurement[Tags] = mergedTags - } - // Copy to prevent mutating Reporter's global tags. - copyTags(rep.Tags) - switch m := metric.(type) { case metrics.Counter: if m.Count() <= 0 { @@ -137,17 +125,14 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc DisplayUnitsShort: OperationsShort, DisplayMin: "0", } - copyTags(m.Labels()) batch.Measurements = append(batch.Measurements, measurement) case metrics.Gauge: measurement[Name] = name measurement[Value] = float64(m.Value()) - copyTags(m.Labels()) batch.Measurements = append(batch.Measurements, measurement) case metrics.GaugeFloat64: measurement[Name] = name measurement[Value] = m.Value() - copyTags(m.Labels()) batch.Measurements = append(batch.Measurements, measurement) case metrics.Histogram: s := m.Snapshot().Sample() @@ -168,12 +153,10 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc measurement[Min] = float64(s.Min()) measurement[Sum] = float64(s.Sum()) measurement[StdDev] = float64(s.StdDev()) - copyTags(m.Labels()) measurements[0] = measurement for i, p := range rep.Percentiles { measurements[i+i] = Measurement{ Name: fmt.Sprintf("%s.%.2f", measurement[Name], p), - Tags: mergedTags, Value: s.Percentile(p), Period: measurement[Period], } @@ -183,12 +166,10 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc s := m.Snapshot() measurement[Name] = name measurement[Value] = float64(s.Count()) - copyTags(s.Labels()) batch.Measurements = append(batch.Measurements, measurement) batch.Measurements = append(batch.Measurements, Measurement{ Name: fmt.Sprintf("%s.%s", name, "1min"), - Tags: mergedTags, Value: s.Rate1(), Period: int64(rep.Interval.Seconds()), Attributes: map[string]interface{}{ @@ -199,7 +180,6 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc }, Measurement{ Name: fmt.Sprintf("%s.%s", name, "5min"), - Tags: mergedTags, Value: s.Rate5(), Period: int64(rep.Interval.Seconds()), Attributes: map[string]interface{}{ @@ -210,7 +190,6 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc }, Measurement{ Name: fmt.Sprintf("%s.%s", name, "15min"), - Tags: mergedTags, Value: s.Rate15(), Period: int64(rep.Interval.Seconds()), Attributes: map[string]interface{}{ @@ -224,7 +203,6 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc s := m.Snapshot() measurement[Name] = name measurement[Value] = float64(s.Count()) - copyTags(s.Labels()) batch.Measurements = append(batch.Measurements, measurement) if m.Count() <= 0 { return @@ -233,7 +211,6 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc measurements := make([]Measurement, histogramMeasurementCount) measurements[0] = Measurement{ Name: appOpticsName, - Tags: mergedTags, Count: uint64(s.Count()), Sum: s.Mean() * float64(s.Count()), Max: float64(s.Max()), @@ -245,7 +222,6 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc for i, p := range rep.Percentiles { measurements[i+1] = Measurement{ Name: fmt.Sprintf("%s.timer.%2.0f", name, p*100), - Tags: mergedTags, Value: m.Percentile(p), Period: int64(rep.Interval.Seconds()), Attributes: rep.TimerAttributes, @@ -255,7 +231,6 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc batch.Measurements = append(batch.Measurements, Measurement{ Name: fmt.Sprintf("%s.%s", name, "rate.1min"), - Tags: mergedTags, Value: s.Rate1(), Period: int64(rep.Interval.Seconds()), Attributes: map[string]interface{}{ @@ -266,7 +241,6 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc }, Measurement{ Name: fmt.Sprintf("%s.%s", name, "rate.5min"), - Tags: mergedTags, Value: s.Rate5(), Period: int64(rep.Interval.Seconds()), Attributes: map[string]interface{}{ @@ -277,7 +251,6 @@ func (rep *Reporter) BuildRequest(now time.Time, r metrics.Registry) (batch Batc }, Measurement{ Name: fmt.Sprintf("%s.%s", name, "rate.15min"), - Tags: mergedTags, Value: s.Rate15(), Period: int64(rep.Interval.Seconds()), Attributes: map[string]interface{}{ diff --git a/appoptics/example_test.go b/appoptics/example_test.go index 1b6c1d2..3414a5f 100644 --- a/appoptics/example_test.go +++ b/appoptics/example_test.go @@ -6,10 +6,10 @@ import ( ) func ExampleAppOptics() { - metrics.GetOrRegisterCounter("myCounter", nil, metrics.Labels{"foo": "bar"}) - metrics.GetOrRegisterMeter("myMeter", nil, nil) + metrics.GetOrRegisterCounter("myCounter", nil) + metrics.GetOrRegisterMeter("myMeter", nil) go AppOptics(metrics.DefaultRegistry, time.Second, "token", - metrics.Labels{"hostname": "localhost"}, []float64{0.5, 0.75, 0.95, 0.99}, + []float64{0.5, 0.75, 0.95, 0.99}, time.Millisecond, "myservice.", nil, DefaultMeasurementsURI) } diff --git a/counter.go b/counter.go index e7834a3..608738c 100644 --- a/counter.go +++ b/counter.go @@ -9,43 +9,38 @@ type Counter interface { Dec(int64) Inc(int64) Snapshot() Counter - Labels() Labels - WithLabels(Labels) Counter } // GetOrRegisterCounter returns an existing Counter or constructs and registers // a new StandardCounter. -func GetOrRegisterCounter(name string, r Registry, labels Labels) Counter { +func GetOrRegisterCounter(name string, r Registry) Counter { if nil == r { r = DefaultRegistry } - return r.GetOrRegister(name, func() Counter { - return NewCounter(labels) - }).(Counter) + return r.GetOrRegister(name, NewCounter).(Counter) } // NewRegisteredCounter constructs and registers a new StandardCounter. -func NewRegisteredCounter(name string, r Registry, labels Labels) Counter { +func NewRegisteredCounter(name string, r Registry) Counter { if nil == r { r = DefaultRegistry } - c := NewCounter(labels) + c := NewCounter() r.Register(name, c) return c } // NewCounter constructs a new StandardCounter. -func NewCounter(labels Labels) Counter { +func NewCounter() Counter { if UseNilMetrics { return NilCounter{} } - return &StandardCounter{labels: deepCopyLabels(labels)} + return &StandardCounter{} } // CounterSnapshot is a read-only copy of another Counter. type CounterSnapshot struct { count int64 - labels Labels } // Clear panics. @@ -69,21 +64,6 @@ func (CounterSnapshot) Inc(int64) { // Snapshot returns the snapshot. func (c CounterSnapshot) Snapshot() Counter { return c } -// Labels returns a copy of the snapshot's labels. -func (c CounterSnapshot) Labels() Labels { return deepCopyLabels(c.labels) } - -// WithLabels returns the snapshot with the given labels appended. -func (c CounterSnapshot) WithLabels(labels Labels) Counter { - newLabels := c.labels - for k, v := range labels { - newLabels[k] = v - } - return CounterSnapshot{ - count: c.Count(), - labels: newLabels, - } -} - // NilCounter is a no-op Counter. type NilCounter struct{} @@ -102,17 +82,10 @@ func (NilCounter) Inc(i int64) {} // Snapshot is a no-op. func (NilCounter) Snapshot() Counter { return NilCounter{} } -// Labels is a no-op. -func (NilCounter) Labels() Labels { return Labels{} } - -// WithLabels is a no-op. -func (NilCounter) WithLabels(Labels) Counter { return NilCounter{} } - // StandardCounter is the standard implementation of a Counter and uses the // sync/atomic package to manage a single int64 value. type StandardCounter struct { count atomic.Int64 - labels Labels } // Clear sets the counter to zero. @@ -139,17 +112,5 @@ func (c *StandardCounter) Inc(i int64) { func (c *StandardCounter) Snapshot() Counter { return CounterSnapshot{ count: c.Count(), - labels: c.Labels(), } } - -// Labels returns a deep copy of the counter's labels. -func (c *StandardCounter) Labels() Labels { - return deepCopyLabels(c.labels) -} - -// WithLabels returns a snapshot of the counter with the given labels appended -// to its current list of labels. -func (c *StandardCounter) WithLabels(labels Labels) Counter { - return c.Snapshot().WithLabels(labels) -} diff --git a/counter_test.go b/counter_test.go index 08e5132..af26ef1 100644 --- a/counter_test.go +++ b/counter_test.go @@ -3,7 +3,7 @@ package metrics import "testing" func BenchmarkCounter(b *testing.B) { - c := NewCounter(nil) + c := NewCounter() b.ResetTimer() for i := 0; i < b.N; i++ { c.Inc(1) @@ -11,7 +11,7 @@ func BenchmarkCounter(b *testing.B) { } func TestCounterClear(t *testing.T) { - c := NewCounter(nil) + c := NewCounter() c.Inc(1) c.Clear() if count := c.Count(); count != 0 { @@ -20,7 +20,7 @@ func TestCounterClear(t *testing.T) { } func TestCounterDec1(t *testing.T) { - c := NewCounter(nil) + c := NewCounter() c.Dec(1) if count := c.Count(); count != -1 { t.Errorf("c.Count(): -1 != %v\n", count) @@ -28,7 +28,7 @@ func TestCounterDec1(t *testing.T) { } func TestCounterDec2(t *testing.T) { - c := NewCounter(nil) + c := NewCounter() c.Dec(2) if count := c.Count(); count != -2 { t.Errorf("c.Count(): -2 != %v\n", count) @@ -36,7 +36,7 @@ func TestCounterDec2(t *testing.T) { } func TestCounterInc1(t *testing.T) { - c := NewCounter(nil) + c := NewCounter() c.Inc(1) if count := c.Count(); count != 1 { t.Errorf("c.Count(): 1 != %v\n", count) @@ -44,7 +44,7 @@ func TestCounterInc1(t *testing.T) { } func TestCounterInc2(t *testing.T) { - c := NewCounter(nil) + c := NewCounter() c.Inc(2) if count := c.Count(); count != 2 { t.Errorf("c.Count(): 2 != %v\n", count) @@ -52,7 +52,7 @@ func TestCounterInc2(t *testing.T) { } func TestCounterSnapshot(t *testing.T) { - c := NewCounter(nil) + c := NewCounter() c.Inc(1) snapshot := c.Snapshot() c.Inc(1) @@ -62,7 +62,7 @@ func TestCounterSnapshot(t *testing.T) { } func TestCounterZero(t *testing.T) { - c := NewCounter(nil) + c := NewCounter() if count := c.Count(); count != 0 { t.Errorf("c.Count(): 0 != %v\n", count) } @@ -70,48 +70,8 @@ func TestCounterZero(t *testing.T) { func TestGetOrRegisterCounter(t *testing.T) { r := NewRegistry() - NewRegisteredCounter("foo", r, nil).Inc(47) - if c := GetOrRegisterCounter("foo", r, nil); c.Count() != 47 { + NewRegisteredCounter("foo", r).Inc(47) + if c := GetOrRegisterCounter("foo", r); c.Count() != 47 { t.Fatal(c) } } - -func TestCounterLabels(t *testing.T) { - labels := Labels{"key1": "value1"} - c := NewCounter(labels) - if len(c.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(c.Labels())) - } - if lbls := c.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } - - // Labels passed by value. - labels["key1"] = "valye2" - if lbls := c.Labels()["key1"]; lbls != "value1" { - t.Error("Labels(): labels passed by reference") - } - - // Labels in snapshot. - ss := c.Snapshot() - if len(ss.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(c.Labels())) - } - if lbls := ss.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } -} - -func TestCounterWithLabels(t *testing.T) { - c := NewCounter(Labels{"foo": "bar"}) - new := c.WithLabels(Labels{"bar": "foo"}) - if len(new.Labels()) != 2 { - t.Fatalf("WithLabels() len: %v != 2", len(new.Labels())) - } - if lbls := new.Labels()["foo"]; lbls != "bar" { - t.Errorf("WithLabels(): %v != bar", lbls) - } - if lbls := new.Labels()["bar"]; lbls != "foo" { - t.Errorf("WithLabels(): %v != foo", lbls) - } -} diff --git a/cpu.go b/cpu.go index ed584ee..ab053ff 100644 --- a/cpu.go +++ b/cpu.go @@ -68,9 +68,9 @@ func RegisterCPUStats(r Registry) { r = DefaultRegistry } registerCPUMetricsOnce.Do(func() { - cpuMetrics.GlobalTime = NewGaugeFloat64(nil) - cpuMetrics.GlobalWait = NewGaugeFloat64(nil) - cpuMetrics.LocalTime = NewGaugeFloat64(nil) + cpuMetrics.GlobalTime = NewGaugeFloat64() + cpuMetrics.GlobalWait = NewGaugeFloat64() + cpuMetrics.LocalTime = NewGaugeFloat64() r.Register("cpu.CPUStats.GlobalTime", cpuMetrics.GlobalTime) r.Register("cpu.CPUStats.GlobalWait", cpuMetrics.GlobalWait) r.Register("cpu.CPUStats.LocalTime", cpuMetrics.LocalTime) diff --git a/debug.go b/debug.go index 0285a49..4edc466 100644 --- a/debug.go +++ b/debug.go @@ -61,11 +61,11 @@ func RegisterDebugGCStats(r Registry) { r = DefaultRegistry } registerDebugMetricsOnce.Do(func() { - debugMetrics.GCStats.LastGC = NewGauge(nil) - debugMetrics.GCStats.NumGC = NewGauge(nil) - debugMetrics.GCStats.Pause = NewHistogram(NewExpDecaySample(1028, 0.015), nil) - debugMetrics.GCStats.PauseTotal = NewGauge(nil) - debugMetrics.ReadGCStats = NewTimer(nil) + debugMetrics.GCStats.LastGC = NewGauge() + debugMetrics.GCStats.NumGC = NewGauge() + debugMetrics.GCStats.Pause = NewHistogram(NewExpDecaySample(1028, 0.015)) + debugMetrics.GCStats.PauseTotal = NewGauge() + debugMetrics.ReadGCStats = NewTimer() r.Register("debug.GCStats.LastGC", debugMetrics.GCStats.LastGC) r.Register("debug.GCStats.NumGC", debugMetrics.GCStats.NumGC) diff --git a/disk.go b/disk.go index 224114a..1b93721 100644 --- a/disk.go +++ b/disk.go @@ -70,10 +70,10 @@ func RegisterDiskStats(r Registry) { r = DefaultRegistry } registerDiskMetricsOnce.Do(func() { - diskMetrics.ReadCount = NewGauge(nil) - diskMetrics.ReadBytes = NewGauge(nil) - diskMetrics.WriteCount = NewGauge(nil) - diskMetrics.WriteBytes = NewGauge(nil) + diskMetrics.ReadCount = NewGauge() + diskMetrics.ReadBytes = NewGauge() + diskMetrics.WriteCount = NewGauge() + diskMetrics.WriteBytes = NewGauge() r.Register("disk.DiskStats.ReadCount", diskMetrics.ReadCount) r.Register("disk.DiskStats.ReadBytes", diskMetrics.ReadBytes) r.Register("disk.DiskStats.WriteCount", diskMetrics.WriteCount) diff --git a/gauge.go b/gauge.go index 7f0a36a..2a41d4c 100644 --- a/gauge.go +++ b/gauge.go @@ -7,32 +7,28 @@ type Gauge interface { Snapshot() Gauge Update(int64) Value() int64 - Labels() Labels - WithLabels(Labels) Gauge } // GetOrRegisterGauge returns an existing Gauge or constructs and registers a // new StandardGauge. -func GetOrRegisterGauge(name string, r Registry, labels Labels) Gauge { +func GetOrRegisterGauge(name string, r Registry) Gauge { if nil == r { r = DefaultRegistry } - return r.GetOrRegister(name, func() Gauge { - return NewGauge(labels) - }).(Gauge) + return r.GetOrRegister(name, NewGauge).(Gauge) } // NewGauge constructs a new StandardGauge. -func NewGauge(labels Labels) Gauge { +func NewGauge() Gauge { if UseNilMetrics { return NilGauge{} } - return &StandardGauge{labels: deepCopyLabels(labels)} + return &StandardGauge{} } // NewRegisteredGauge constructs and registers a new StandardGauge. -func NewRegisteredGauge(name string, r Registry, labels Labels) Gauge { - c := NewGauge(labels) +func NewRegisteredGauge(name string, r Registry) Gauge { + c := NewGauge() if nil == r { r = DefaultRegistry } @@ -41,17 +37,16 @@ func NewRegisteredGauge(name string, r Registry, labels Labels) Gauge { } // NewFunctionalGauge constructs a new FunctionalGauge. -func NewFunctionalGauge(f func() int64, labels Labels) Gauge { +func NewFunctionalGauge(f func() int64) Gauge { if UseNilMetrics { return NilGauge{} } - return &FunctionalGauge{value: f, labels: deepCopyLabels(labels)} + return &FunctionalGauge{value: f} } // NewRegisteredFunctionalGauge constructs and registers a new StandardGauge. -func NewRegisteredFunctionalGauge(name string, r Registry, - f func() int64, labels Labels) Gauge { - c := NewFunctionalGauge(f, labels) +func NewRegisteredFunctionalGauge(name string, r Registry, f func() int64) Gauge { + c := NewFunctionalGauge(f) if nil == r { r = DefaultRegistry } @@ -62,7 +57,6 @@ func NewRegisteredFunctionalGauge(name string, r Registry, // GaugeSnapshot is a read-only copy of another Gauge. type GaugeSnapshot struct { value int64 - labels Labels } // Snapshot returns the snapshot. @@ -76,22 +70,6 @@ func (GaugeSnapshot) Update(int64) { // Value returns the value at the time the snapshot was taken. func (g GaugeSnapshot) Value() int64 { return g.value } -// Labels returns a deep copy of the gauge's labels. -func (g GaugeSnapshot) Labels() Labels { return deepCopyLabels(g.labels) } - -// WithLabels returns a copy of the snapshot with the given labels appended to -// the current list of labels. -func (g GaugeSnapshot) WithLabels(labels Labels) Gauge { - newLabels := g.labels - for k, v := range labels { - newLabels[k] = v - } - return GaugeSnapshot{ - value: g.Value(), - labels: newLabels, - } -} - // NilGauge is a no-op Gauge. type NilGauge struct{} @@ -104,24 +82,16 @@ func (NilGauge) Update(v int64) {} // Value is a no-op. func (NilGauge) Value() int64 { return 0 } -// Labels is a no-op. -func (NilGauge) Labels() Labels { return Labels{} } - -// WithLabels is a no-op. -func (NilGauge) WithLabels(Labels) Gauge { return NilGauge{} } - // StandardGauge is the standard implementation of a Gauge and uses the // sync/atomic package to manage a single int64 value. type StandardGauge struct { value atomic.Int64 - labels Labels } // Snapshot returns a read-only copy of the gauge. func (g *StandardGauge) Snapshot() Gauge { return GaugeSnapshot{ value: g.Value(), - labels: g.Labels(), } } @@ -135,19 +105,9 @@ func (g *StandardGauge) Value() int64 { return g.value.Load() } -// Labels returns a copy of the gauge's labels. -func (g *StandardGauge) Labels() Labels { return deepCopyLabels(g.labels) } - -// WithLabels returns a snapshot of the gauge with the given labels appended to -// the current list of labels. -func (g *StandardGauge) WithLabels(labels Labels) Gauge { - return g.Snapshot().WithLabels(labels) -} - // FunctionalGauge returns value from given function type FunctionalGauge struct { value func() int64 - labels Labels } // Value returns the gauge's current value. @@ -159,7 +119,6 @@ func (g FunctionalGauge) Value() int64 { func (g FunctionalGauge) Snapshot() Gauge { return &GaugeSnapshot{ value: g.Value(), - labels: g.Labels(), } } @@ -167,12 +126,3 @@ func (g FunctionalGauge) Snapshot() Gauge { func (FunctionalGauge) Update(int64) { panic("Update called on a FunctionalGauge") } - -// Labels returns a copy of the gauge's labels. -func (g FunctionalGauge) Labels() Labels { return deepCopyLabels(g.labels) } - -// WithLabels returns a snapshot of the gauge with the given labels appended to -// the current list of labels. -func (g FunctionalGauge) WithLabels(labels Labels) Gauge { - return g.Snapshot().WithLabels(labels) -} diff --git a/gauge_float64.go b/gauge_float64.go index 07265aa..35202d0 100644 --- a/gauge_float64.go +++ b/gauge_float64.go @@ -10,30 +10,28 @@ type GaugeFloat64 interface { Snapshot() GaugeFloat64 Update(float64) Value() float64 - Labels() Labels - WithLabels(Labels) GaugeFloat64 } // GetOrRegisterGaugeFloat64 returns an existing GaugeFloat64 or constructs and registers a // new StandardGaugeFloat64. -func GetOrRegisterGaugeFloat64(name string, r Registry, labels Labels) GaugeFloat64 { +func GetOrRegisterGaugeFloat64(name string, r Registry) GaugeFloat64 { if nil == r { r = DefaultRegistry } - return r.GetOrRegister(name, NewGaugeFloat64(labels)).(GaugeFloat64) + return r.GetOrRegister(name, NewGaugeFloat64()).(GaugeFloat64) } // NewGaugeFloat64 constructs a new StandardGaugeFloat64. -func NewGaugeFloat64(labels Labels) GaugeFloat64 { +func NewGaugeFloat64() GaugeFloat64 { if UseNilMetrics { return NilGaugeFloat64{} } - return &StandardGaugeFloat64{labels: deepCopyLabels(labels)} + return &StandardGaugeFloat64{} } // NewRegisteredGaugeFloat64 constructs and registers a new StandardGaugeFloat64. -func NewRegisteredGaugeFloat64(name string, r Registry, labels Labels) GaugeFloat64 { - c := NewGaugeFloat64(labels) +func NewRegisteredGaugeFloat64(name string, r Registry) GaugeFloat64 { + c := NewGaugeFloat64() if nil == r { r = DefaultRegistry } @@ -42,17 +40,16 @@ func NewRegisteredGaugeFloat64(name string, r Registry, labels Labels) GaugeFloa } // NewFunctionalGaugeFloat64 constructs a new FunctionalGauge. -func NewFunctionalGaugeFloat64(f func() float64, labels Labels) GaugeFloat64 { +func NewFunctionalGaugeFloat64(f func() float64) GaugeFloat64 { if UseNilMetrics { return NilGaugeFloat64{} } - return &FunctionalGaugeFloat64{value: f, labels: deepCopyLabels(labels)} + return &FunctionalGaugeFloat64{value: f} } // NewRegisteredFunctionalGaugeFloat64 constructs and registers a new StandardGauge. -func NewRegisteredFunctionalGaugeFloat64(name string, r Registry, - f func() float64, labels Labels) GaugeFloat64 { - c := NewFunctionalGaugeFloat64(f, labels) +func NewRegisteredFunctionalGaugeFloat64(name string, r Registry, f func() float64) GaugeFloat64 { + c := NewFunctionalGaugeFloat64(f) if nil == r { r = DefaultRegistry } @@ -62,8 +59,7 @@ func NewRegisteredFunctionalGaugeFloat64(name string, r Registry, // GaugeFloat64Snapshot is a read-only copy of another GaugeFloat64. type GaugeFloat64Snapshot struct { - value float64 - labels Labels + value float64 } // Snapshot returns the snapshot. @@ -77,22 +73,6 @@ func (GaugeFloat64Snapshot) Update(float64) { // Value returns the value at the time the snapshot was taken. func (g GaugeFloat64Snapshot) Value() float64 { return g.value } -// Labels returns a deep copy of the Snapshot's labels. -func (g GaugeFloat64Snapshot) Labels() Labels { return deepCopyLabels(g.labels) } - -// WithLabels returns a copy of the snapshot with the specified labels appended -// to the current list of labels. -func (g GaugeFloat64Snapshot) WithLabels(labels Labels) GaugeFloat64 { - newLabels := g.labels - for k, v := range labels { - newLabels[k] = v - } - return GaugeFloat64Snapshot{ - value: g.Value(), - labels: newLabels, - } -} - // NilGaugeFloat64 is a no-op Gauge. type NilGaugeFloat64 struct{} @@ -105,26 +85,16 @@ func (NilGaugeFloat64) Update(v float64) {} // Value is a no-op. func (NilGaugeFloat64) Value() float64 { return 0.0 } -// Labels is a no-op. -func (NilGaugeFloat64) Labels() Labels { return Labels{} } - -// WithLabels is a no-op. -func (NilGaugeFloat64) WithLabels(Labels) GaugeFloat64 { - return NilGaugeFloat64{} -} - // StandardGaugeFloat64 is the standard implementation of a GaugeFloat64 and uses // atomic uint64 (holds float bytes) to manage a single float64 value. type StandardGaugeFloat64 struct { - value atomic.Uint64 - labels Labels + value atomic.Uint64 } // Snapshot returns a read-only copy of the gauge. func (g *StandardGaugeFloat64) Snapshot() GaugeFloat64 { return GaugeFloat64Snapshot{ - value: g.Value(), - labels: g.Labels(), + value: g.Value(), } } @@ -138,21 +108,9 @@ func (g *StandardGaugeFloat64) Value() float64 { return math.Float64frombits(g.value.Load()) } -// Labels returns a deep copy of the gauge's labels. -func (g *StandardGaugeFloat64) Labels() Labels { - return deepCopyLabels(g.labels) -} - -// WithLabels returns a snapshot of the Gauge with the given labels appended to -// the current list of labels. -func (g *StandardGaugeFloat64) WithLabels(labels Labels) GaugeFloat64 { - return g.Snapshot().WithLabels(labels) -} - // FunctionalGaugeFloat64 returns value from given function type FunctionalGaugeFloat64 struct { - value func() float64 - labels Labels + value func() float64 } // Value returns the gauge's current value. @@ -163,8 +121,7 @@ func (g FunctionalGaugeFloat64) Value() float64 { // Snapshot returns the snapshot. func (g FunctionalGaugeFloat64) Snapshot() GaugeFloat64 { return GaugeFloat64Snapshot{ - value: g.Value(), - labels: g.Labels(), + value: g.Value(), } } @@ -172,14 +129,3 @@ func (g FunctionalGaugeFloat64) Snapshot() GaugeFloat64 { func (FunctionalGaugeFloat64) Update(float64) { panic("Update called on a FunctionalGaugeFloat64") } - -// Labels returns a deep copy of the gauge's labels. -func (g FunctionalGaugeFloat64) Labels() Labels { - return deepCopyLabels(g.labels) -} - -// WithLabels returns a snapshot of the Gauge with the given labels appended to -// the current list of labels. -func (g FunctionalGaugeFloat64) WithLabels(labels Labels) GaugeFloat64 { - return g.Snapshot().WithLabels(labels) -} diff --git a/gauge_float64_test.go b/gauge_float64_test.go index ed4bfb0..d7d4f85 100644 --- a/gauge_float64_test.go +++ b/gauge_float64_test.go @@ -3,7 +3,7 @@ package metrics import "testing" func BenchmarkGuageFloat64(b *testing.B) { - g := NewGaugeFloat64(nil) + g := NewGaugeFloat64() b.ResetTimer() for i := 0; i < b.N; i++ { g.Update(float64(i)) @@ -11,7 +11,7 @@ func BenchmarkGuageFloat64(b *testing.B) { } func BenchmarkGuageFloat64Parallel(b *testing.B) { - g := NewGaugeFloat64(nil) + g := NewGaugeFloat64() b.ResetTimer() b.RunParallel(func(pb *testing.PB) { for pb.Next() { @@ -21,7 +21,7 @@ func BenchmarkGuageFloat64Parallel(b *testing.B) { } func TestGaugeFloat64(t *testing.T) { - g := NewGaugeFloat64(nil) + g := NewGaugeFloat64() g.Update(float64(47.0)) if v := g.Value(); float64(47.0) != v { t.Errorf("g.Value(): 47.0 != %v\n", v) @@ -29,7 +29,7 @@ func TestGaugeFloat64(t *testing.T) { } func TestGaugeFloat64Snapshot(t *testing.T) { - g := NewGaugeFloat64(nil) + g := NewGaugeFloat64() g.Update(float64(47.0)) snapshot := g.Snapshot() g.Update(float64(0)) @@ -40,9 +40,9 @@ func TestGaugeFloat64Snapshot(t *testing.T) { func TestGetOrRegisterGaugeFloat64(t *testing.T) { r := NewRegistry() - NewRegisteredGaugeFloat64("foo", r, nil).Update(float64(47.0)) + NewRegisteredGaugeFloat64("foo", r).Update(float64(47.0)) t.Logf("registry: %v", r) - if g := GetOrRegisterGaugeFloat64("foo", r, nil); float64(47.0) != g.Value() { + if g := GetOrRegisterGaugeFloat64("foo", r); float64(47.0) != g.Value() { t.Fatal(g) } } @@ -52,7 +52,7 @@ func TestFunctionalGaugeFloat64(t *testing.T) { fg := NewFunctionalGaugeFloat64(func() float64 { counter++ return counter - }, nil) + }) fg.Value() fg.Value() if counter != 2 { @@ -62,48 +62,8 @@ func TestFunctionalGaugeFloat64(t *testing.T) { func TestGetOrRegisterFunctionalGaugeFloat64(t *testing.T) { r := NewRegistry() - NewRegisteredFunctionalGaugeFloat64("foo", r, func() float64 { return 47 }, nil) - if g := GetOrRegisterGaugeFloat64("foo", r, nil); g.Value() != 47 { + NewRegisteredFunctionalGaugeFloat64("foo", r, func() float64 { return 47 }) + if g := GetOrRegisterGaugeFloat64("foo", r); g.Value() != 47 { t.Fatal(g) } } - -func TestGaugeFloat64Labels(t *testing.T) { - labels := Labels{"key1": "value1"} - g := NewGaugeFloat64(labels) - if len(g.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(g.Labels())) - } - if lbls := g.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } - - // Labels passed by value. - labels["key1"] = "value2" - if lbls := g.Labels()["key1"]; lbls != "value1" { - t.Error("Labels(): labels passed by reference") - } - - // Labels in snapshot. - ss := g.Snapshot() - if len(ss.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(g.Labels())) - } - if lbls := ss.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } -} - -func TestGaugeFloat64WithLabels(t *testing.T) { - g := NewGaugeFloat64(Labels{"foo": "bar"}) - new := g.WithLabels(Labels{"bar": "foo"}) - if len(new.Labels()) != 2 { - t.Fatalf("WithLabels() len: %v != 2", len(new.Labels())) - } - if lbls := new.Labels()["foo"]; lbls != "bar" { - t.Errorf("WithLabels(): %v != bar", lbls) - } - if lbls := new.Labels()["bar"]; lbls != "foo" { - t.Errorf("WithLabels(): %v != foo", lbls) - } -} diff --git a/gauge_test.go b/gauge_test.go index 8e9509d..b1bdf75 100644 --- a/gauge_test.go +++ b/gauge_test.go @@ -7,7 +7,7 @@ import ( ) func BenchmarkGuage(b *testing.B) { - g := NewGauge(nil) + g := NewGauge() b.ResetTimer() for i := 0; i < b.N; i++ { g.Update(int64(i)) @@ -16,7 +16,7 @@ func BenchmarkGuage(b *testing.B) { // exercise race detector func TestGaugeConcurrency(t *testing.T) { - g := NewGauge(nil) + g := NewGauge() wg := &sync.WaitGroup{} reps := 100 for i := 0; i < reps; i++ { @@ -30,7 +30,7 @@ func TestGaugeConcurrency(t *testing.T) { } func TestGauge(t *testing.T) { - g := NewGauge(nil) + g := NewGauge() g.Update(int64(47)) if v := g.Value(); v != 47 { t.Errorf("g.Value(): 47 != %v\n", v) @@ -38,7 +38,7 @@ func TestGauge(t *testing.T) { } func TestGaugeSnapshot(t *testing.T) { - g := NewGauge(nil) + g := NewGauge() g.Update(int64(47)) snapshot := g.Snapshot() g.Update(int64(0)) @@ -49,8 +49,8 @@ func TestGaugeSnapshot(t *testing.T) { func TestGetOrRegisterGauge(t *testing.T) { r := NewRegistry() - NewRegisteredGauge("foo", r, nil).Update(47) - if g := GetOrRegisterGauge("foo", r, nil); g.Value() != 47 { + NewRegisteredGauge("foo", r).Update(47) + if g := GetOrRegisterGauge("foo", r); g.Value() != 47 { t.Fatal(g) } } @@ -60,7 +60,7 @@ func TestFunctionalGauge(t *testing.T) { fg := NewFunctionalGauge(func() int64 { counter++ return counter - }, nil) + }) fg.Value() fg.Value() if counter != 2 { @@ -70,48 +70,8 @@ func TestFunctionalGauge(t *testing.T) { func TestGetOrRegisterFunctionalGauge(t *testing.T) { r := NewRegistry() - NewRegisteredFunctionalGauge("foo", r, func() int64 { return 47 }, nil) - if g := GetOrRegisterGauge("foo", r, nil); g.Value() != 47 { + NewRegisteredFunctionalGauge("foo", r, func() int64 { return 47 }) + if g := GetOrRegisterGauge("foo", r); g.Value() != 47 { t.Fatal(g) } } - -func TestGaugeLabels(t *testing.T) { - labels := Labels{"key1": "value1"} - g := NewGauge(labels) - if len(g.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(g.Labels())) - } - if lbls := g.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } - - // Labels passed by value. - labels["key1"] = "value2" - if lbls := g.Labels()["key1"]; lbls != "value1" { - t.Error("Labels(): labels passed by reference") - } - - // Labels in snapshot. - ss := g.Snapshot() - if len(ss.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(g.Labels())) - } - if lbls := ss.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } -} - -func TestGaugeWithLabels(t *testing.T) { - g := NewGauge(Labels{"foo": "bar"}) - new := g.WithLabels(Labels{"bar": "foo"}) - if len(new.Labels()) != 2 { - t.Fatalf("WithLabels() len: %v != 2", len(new.Labels())) - } - if lbls := new.Labels()["foo"]; lbls != "bar" { - t.Errorf("WithLabels(): %v != bar", lbls) - } - if lbls := new.Labels()["bar"]; lbls != "foo" { - t.Errorf("WithLabels(): %v != foo", lbls) - } -} diff --git a/graphite/graphite_test.go b/graphite/graphite_test.go index 9a64194..3b54643 100644 --- a/graphite/graphite_test.go +++ b/graphite/graphite_test.go @@ -46,7 +46,7 @@ func newTestServer(t *testing.T, ctx *atomic.Bool) (map[string]string, r := bufio.NewReader(conn) line, err := r.ReadString('\n') for err == nil { - parts := strings.Split(line, ";") + parts := strings.Split(line, " ") res[parts[0]] = res[parts[0]] + line line, err = r.ReadString('\n') } @@ -72,8 +72,8 @@ func TestWrites(t *testing.T) { res, ln, c, wg := newTestServer(t, &ctx) defer ln.Close() - metrics.GetOrRegisterCounter("foo", nil, metrics.Labels{"key1": "value1"}).Inc(2) - metrics.GetOrRegisterMeter("bar", nil, metrics.Labels{"key2": "value2"}).Mark(1) + metrics.GetOrRegisterCounter("foo", nil).Inc(2) + metrics.GetOrRegisterMeter("bar", nil).Mark(1) ctx.Store(false) wg.Add(1) @@ -84,22 +84,22 @@ func TestWrites(t *testing.T) { } wg.Wait() - expect := "p.bar.count;key2=value2 1" + expect := "p.bar.count 1" if str := res["p.bar.count"]; expect != str[:len(str)-12] { t.Errorf("%s != %s", expect, str[:len(str)-12]) } - expect = "p.bar.rate.15min;key2=value2 1.000000" + expect = "p.bar.rate.15min 1.000000" if str := res["p.bar.rate.15min"]; expect != str[:len(str)-12] { t.Errorf("%s != %s", expect, str[:len(str)-12]) } - expect = "p.bar.rate.1min;key2=value2 1.000000" + expect = "p.bar.rate.1min 1.000000" if str := res["p.bar.rate.1min"]; expect != str[:len(str)-12] { t.Errorf("%s != %s", expect, str[:len(str)-12]) } - expect = "p.bar.rate.5min;key2=value2 1.000000" + expect = "p.bar.rate.5min 1.000000" if str := res["p.bar.rate.5min"]; expect != str[:len(str)-12] { t.Errorf("%s != %s", expect, str[:len(str)-12]) } @@ -107,7 +107,7 @@ func TestWrites(t *testing.T) { // p.bar.rate.mean changes every nanosecond. It is too erratic, // so it is ignored in this test. - expect = "p.foo;key1=value1 2" + expect = "p.foo 2" if str := res["p.foo"]; expect != str[:len(str)-12] { t.Errorf("%s != %s", expect, str[:len(str)-12]) } diff --git a/healthcheck.go b/healthcheck.go index c4e56dd..5348365 100644 --- a/healthcheck.go +++ b/healthcheck.go @@ -6,17 +6,15 @@ type Healthcheck interface { Error() error Healthy() Unhealthy(error) - Labels() Labels - WithLabels(Labels) Healthcheck } // NewHealthcheck constructs a new Healthcheck which will use the given // function to update its status. -func NewHealthcheck(f func(Healthcheck), labels Labels) Healthcheck { +func NewHealthcheck(f func(Healthcheck)) Healthcheck { if UseNilMetrics { return NilHealthcheck{} } - return &StandardHealthcheck{nil, f, deepCopyLabels(labels)} + return &StandardHealthcheck{nil, f} } // NilHealthcheck is a no-op. @@ -34,18 +32,11 @@ func (NilHealthcheck) Healthy() {} // Unhealthy is a no-op. func (NilHealthcheck) Unhealthy(error) {} -// Labels is a no-op. -func (NilHealthcheck) Labels() Labels { return Labels{} } - -// WithLabels is a no-op. -func (NilHealthcheck) WithLabels(Labels) Healthcheck { return NilHealthcheck{} } - // StandardHealthcheck is the standard implementation of a Healthcheck and // stores the pstatus and a function to call to update the status. type StandardHealthcheck struct { - err error - f func(Healthcheck) - labels Labels + err error + f func(Healthcheck) } // Check runs the healthcheck function to update the healthcheck's status. @@ -68,18 +59,3 @@ func (h *StandardHealthcheck) Healthy() { func (h *StandardHealthcheck) Unhealthy(err error) { h.err = err } - -// Labels returns a deep copy of the healthcheck's labels. -func (h *StandardHealthcheck) Labels() Labels { - return deepCopyLabels(h.labels) -} - -// WithLabels returns a copy of the Healthcheck with the given labels appended -// to the current list of labels. -func (h *StandardHealthcheck) WithLabels(labels Labels) Healthcheck { - newLabels := h.labels - for k, v := range labels { - newLabels[k] = v - } - return &StandardHealthcheck{h.err, h.f, newLabels} -} diff --git a/histogram.go b/histogram.go index 85b862e..02e8dc1 100644 --- a/histogram.go +++ b/histogram.go @@ -15,33 +15,31 @@ type Histogram interface { Sum() int64 Update(int64) Variance() float64 - Labels() Labels - WithLabels(Labels) Histogram } // GetOrRegisterHistogram returns an existing Histogram or constructs and // registers a new StandardHistogram. -func GetOrRegisterHistogram(name string, r Registry, s Sample, labels Labels) Histogram { +func GetOrRegisterHistogram(name string, r Registry, s Sample) Histogram { if nil == r { r = DefaultRegistry } return r.GetOrRegister(name, func() Histogram { - return NewHistogram(s, labels) + return NewHistogram(s) }).(Histogram) } // NewHistogram constructs a new StandardHistogram from a Sample. -func NewHistogram(s Sample, labels Labels) Histogram { +func NewHistogram(s Sample) Histogram { if UseNilMetrics { return NilHistogram{} } - return &StandardHistogram{sample: s, labels: deepCopyLabels(labels)} + return &StandardHistogram{sample: s} } // NewRegisteredHistogram constructs and registers a new StandardHistogram from // a Sample. -func NewRegisteredHistogram(name string, r Registry, s Sample, labels Labels) Histogram { - c := NewHistogram(s, labels) +func NewRegisteredHistogram(name string, r Registry, s Sample) Histogram { + c := NewHistogram(s) if nil == r { r = DefaultRegistry } @@ -52,7 +50,6 @@ func NewRegisteredHistogram(name string, r Registry, s Sample, labels Labels) Hi // HistogramSnapshot is a read-only copy of another Histogram. type HistogramSnapshot struct { sample *SampleSnapshot - labels Labels } // Clear panics. @@ -109,19 +106,6 @@ func (*HistogramSnapshot) Update(int64) { // Variance returns the variance of inputs at the time the snapshot was taken. func (h *HistogramSnapshot) Variance() float64 { return h.sample.Variance() } -// Labels returns a deep copy of the snapshot's labels. -func (h *HistogramSnapshot) Labels() Labels { return deepCopyLabels(h.labels) } - -// WithLabels returns a copy of the snapshot with the given labels appended to -// the current list of labels. -func (h *HistogramSnapshot) WithLabels(labels Labels) Histogram { - newLabels := h.labels - for k, v := range labels { - newLabels[k] = v - } - return &HistogramSnapshot{sample: h.sample, labels: newLabels} -} - // NilHistogram is a no-op Histogram. type NilHistogram struct{} @@ -166,17 +150,10 @@ func (NilHistogram) Update(v int64) {} // Variance is a no-op. func (NilHistogram) Variance() float64 { return 0.0 } -// Labels is a no-op. -func (NilHistogram) Labels() Labels { return Labels{} } - -// WithLabels is a no-op. -func (NilHistogram) WithLabels(Labels) Histogram { return NilHistogram{} } - // StandardHistogram is the standard implementation of a Histogram and uses a // Sample to bound its memory use. type StandardHistogram struct { sample Sample - labels Labels } // Clear clears the histogram and its sample. @@ -213,7 +190,6 @@ func (h *StandardHistogram) Sample() Sample { return h.sample } func (h *StandardHistogram) Snapshot() Histogram { return &HistogramSnapshot{ sample: h.sample.Snapshot().(*SampleSnapshot), - labels: h.Labels(), } } @@ -228,12 +204,3 @@ func (h *StandardHistogram) Update(v int64) { h.sample.Update(v) } // Variance returns the variance of the values in the sample. func (h *StandardHistogram) Variance() float64 { return h.sample.Variance() } - -// Labels returns a deep copy of the histogram's labels. -func (h *StandardHistogram) Labels() Labels { return deepCopyLabels(h.labels) } - -// WithLabels returns a snapshot of the Histogram with the given labels appended -// to the current list of labels. -func (h *StandardHistogram) WithLabels(labels Labels) Histogram { - return h.Snapshot().WithLabels(labels) -} diff --git a/histogram_test.go b/histogram_test.go index 4b40187..7c9f42f 100644 --- a/histogram_test.go +++ b/histogram_test.go @@ -3,7 +3,7 @@ package metrics import "testing" func BenchmarkHistogram(b *testing.B) { - h := NewHistogram(NewUniformSample(100), nil) + h := NewHistogram(NewUniformSample(100)) b.ResetTimer() for i := 0; i < b.N; i++ { h.Update(int64(i)) @@ -13,14 +13,14 @@ func BenchmarkHistogram(b *testing.B) { func TestGetOrRegisterHistogram(t *testing.T) { r := NewRegistry() s := NewUniformSample(100) - NewRegisteredHistogram("foo", r, s, nil).Update(47) - if h := GetOrRegisterHistogram("foo", r, s, nil); h.Count() != 1 { + NewRegisteredHistogram("foo", r, s).Update(47) + if h := GetOrRegisterHistogram("foo", r, s); h.Count() != 1 { t.Fatal(h) } } func TestHistogram10000(t *testing.T) { - h := NewHistogram(NewUniformSample(100000), nil) + h := NewHistogram(NewUniformSample(100000)) for i := 1; i <= 10000; i++ { h.Update(int64(i)) } @@ -28,7 +28,7 @@ func TestHistogram10000(t *testing.T) { } func TestHistogramEmpty(t *testing.T) { - h := NewHistogram(NewUniformSample(100), nil) + h := NewHistogram(NewUniformSample(100)) if count := h.Count(); count != 0 { t.Errorf("h.Count(): 0 != %v\n", count) } @@ -57,7 +57,7 @@ func TestHistogramEmpty(t *testing.T) { } func TestHistogramSnapshot(t *testing.T) { - h := NewHistogram(NewUniformSample(100000), nil) + h := NewHistogram(NewUniformSample(100000)) for i := 1; i <= 10000; i++ { h.Update(int64(i)) } @@ -93,43 +93,3 @@ func testHistogram10000(t *testing.T, h Histogram) { t.Errorf("99th percentile: 9900.99 != %v\n", ps[2]) } } - -func TestHistogramLabels(t *testing.T) { - labels := Labels{"key1": "value1"} - h := NewHistogram(NewUniformSample(100), labels) - if len(h.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(h.Labels())) - } - if lbls := h.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } - - // Labels passed by value. - labels["key1"] = "value2" - if lbls := h.Labels()["key1"]; lbls != "value1" { - t.Error("Labels(): labels passed by reference") - } - - // Labels in snapshot. - ss := h.Snapshot() - if len(ss.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(h.Labels())) - } - if lbls := ss.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } -} - -func TestHistogramWithLabels(t *testing.T) { - h := NewHistogram(NewUniformSample(100), Labels{"foo": "bar"}) - new := h.WithLabels(Labels{"bar": "foo"}) - if len(new.Labels()) != 2 { - t.Fatalf("WithLabels() len: %v != 2", len(new.Labels())) - } - if lbls := new.Labels()["foo"]; lbls != "bar" { - t.Errorf("WithLabels(): %v != bar", lbls) - } - if lbls := new.Labels()["bar"]; lbls != "foo" { - t.Errorf("WithLabels(): %v != foo", lbls) - } -} diff --git a/influxdb/v1/influxdb.go b/influxdb/v1/influxdb.go index 58cd47a..ea55f57 100644 --- a/influxdb/v1/influxdb.go +++ b/influxdb/v1/influxdb.go @@ -66,7 +66,6 @@ func influxdb(c *Config) error { m := metric.Snapshot() pts = append(pts, client.Point{ Measurement: prefix + name, - Tags: m.Labels(), Time: now, Fields: map[string]interface{}{ "count": m.Count(), @@ -76,7 +75,6 @@ func influxdb(c *Config) error { m := metric.Snapshot() pts = append(pts, client.Point{ Measurement: prefix + name, - Tags: m.Labels(), Time: now, Fields: map[string]interface{}{ "gauge": m.Value(), @@ -86,7 +84,6 @@ func influxdb(c *Config) error { m := metric.Snapshot() pts = append(pts, client.Point{ Measurement: prefix + name, - Tags: m.Labels(), Time: now, Fields: map[string]interface{}{ "gauge": m.Value(), @@ -96,7 +93,6 @@ func influxdb(c *Config) error { m := metric.Snapshot() pts = append(pts, client.Point{ Measurement: prefix + name, - Tags: m.Labels(), Time: now, Fields: map[string]interface{}{ "count": m.Count(), @@ -111,7 +107,6 @@ func influxdb(c *Config) error { ps := m.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) pts = append(pts, client.Point{ Measurement: prefix + name, - Tags: m.Labels(), Time: now, Fields: map[string]interface{}{ "count": m.Count(), @@ -137,7 +132,6 @@ func influxdb(c *Config) error { ps := m.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) pts = append(pts, client.Point{ Measurement: prefix + name, - Tags: m.Labels(), Time: now, Fields: map[string]interface{}{ "count": m.Count(), diff --git a/influxdb/v1/influxdb_test.go b/influxdb/v1/influxdb_test.go index 002c6de..9d834e0 100644 --- a/influxdb/v1/influxdb_test.go +++ b/influxdb/v1/influxdb_test.go @@ -10,8 +10,8 @@ import ( ) func ExampleInfluxDBV1() { - m := metrics.GetOrRegisterMeter("myMeter", nil, metrics.Labels{"foo": "bar"}) - t := metrics.GetOrRegisterTimer("myTimer", nil, nil) + m := metrics.GetOrRegisterMeter("myMeter", nil) + t := metrics.GetOrRegisterTimer("myTimer", nil) m.Mark(100) t.Update(30 * time.Second) diff --git a/influxdb/v2/influxdb.go b/influxdb/v2/influxdb.go index e15b0cb..a220891 100644 --- a/influxdb/v2/influxdb.go +++ b/influxdb/v2/influxdb.go @@ -62,22 +62,22 @@ func influxdb(c *Config) { switch metric := i.(type) { case metrics.Counter: m := metric.Snapshot() - p := influx.NewPoint(name, m.Labels(), + p := influx.NewPoint(name, nil, map[string]interface{}{"count": m.Count()}, now) api.WritePoint(context.Background(), p) case metrics.Gauge: m := metric.Snapshot() - p := influx.NewPoint(name, m.Labels(), + p := influx.NewPoint(name, nil, map[string]interface{}{"gauge": m.Value()}, now) api.WritePoint(context.Background(), p) case metrics.GaugeFloat64: m := metric.Snapshot() - p := influx.NewPoint(name, m.Labels(), + p := influx.NewPoint(name, nil, map[string]interface{}{"gauge": m.Value()}, now) api.WritePoint(context.Background(), p) case metrics.Meter: m := metric.Snapshot() - p := influx.NewPoint(name, m.Labels(), map[string]interface{}{ + p := influx.NewPoint(name, nil, map[string]interface{}{ "count": m.Count(), "rate.1min": m.Rate1(), "rate.5min": m.Rate5(), @@ -88,7 +88,7 @@ func influxdb(c *Config) { case metrics.Timer: m := metric.Snapshot() ps := m.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) - p := influx.NewPoint(name, m.Labels(), map[string]interface{}{ + p := influx.NewPoint(name, nil, map[string]interface{}{ "count": m.Count(), "min": m.Min(), "max": m.Max(), @@ -110,7 +110,7 @@ func influxdb(c *Config) { case metrics.Histogram: m := metric.Snapshot() ps := m.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) - p := influx.NewPoint(name, m.Labels(), map[string]interface{}{ + p := influx.NewPoint(name, nil, map[string]interface{}{ "count": m.Count(), "min": m.Min(), "max": m.Max(), diff --git a/influxdb/v2/influxdb_test.go b/influxdb/v2/influxdb_test.go index 1a36782..00d0a46 100644 --- a/influxdb/v2/influxdb_test.go +++ b/influxdb/v2/influxdb_test.go @@ -8,8 +8,8 @@ import ( func ExampleInfluxDBV2() { // Register some metrics. - m := metrics.GetOrRegisterMeter("myMeter", nil, metrics.Labels{"foo": "bar"}) - t := metrics.GetOrRegisterTimer("myTimer", nil, nil) + m := metrics.GetOrRegisterMeter("myMeter", nil) + t := metrics.GetOrRegisterTimer("myTimer", nil) m.Mark(100) t.Update(30 * time.Second) diff --git a/json_test.go b/json_test.go index 5ef00db..f91fe8c 100644 --- a/json_test.go +++ b/json_test.go @@ -10,19 +10,19 @@ func TestRegistryMarshallJSON(t *testing.T) { b := &bytes.Buffer{} enc := json.NewEncoder(b) r := NewRegistry() - r.Register("counter", NewCounter(nil)) + r.Register("counter", NewCounter()) enc.Encode(r) - if s := b.String(); s != "{\"counter\":{\"count\":0,\"labels\":{}}}\n" { + if s := b.String(); s != "{\"counter\":{\"count\":0}}\n" { t.Fatalf(s) } } func TestRegistryWriteJSONOnce(t *testing.T) { r := NewRegistry() - r.Register("counter", NewCounter(nil)) + r.Register("counter", NewCounter()) b := &bytes.Buffer{} WriteJSONOnce(r, b) - if s := b.String(); s != "{\"counter\":{\"count\":0,\"labels\":{}}}\n" { + if s := b.String(); s != "{\"counter\":{\"count\":0}}\n" { t.Fail() } } diff --git a/label.go b/label.go deleted file mode 100644 index 1432f10..0000000 --- a/label.go +++ /dev/null @@ -1,12 +0,0 @@ -package metrics - -// Labels is a map of key-values describing a metric. -type Labels map[string]string - -func deepCopyLabels(labels Labels) Labels { - copy := Labels{} - for key, value := range labels { - copy[key] = value - } - return copy -} diff --git a/logging/encode.go b/logging/encode.go index 751524e..d655d26 100644 --- a/logging/encode.go +++ b/logging/encode.go @@ -21,71 +21,51 @@ func Encode(w io.Writer, name, prefix string, i interface{}) { switch metric := i.(type) { case metrics.Counter: - fmt.Fprintf(w, "%s%s %d %v\n", head, EncodeLabels(metric.Labels()), - metric.Count(), ts) + fmt.Fprintf(w, "%s %d %v\n", head, metric.Count(), ts) case metrics.Gauge: - fmt.Fprintf(w, "%s%s %d %v\n", head, EncodeLabels(metric.Labels()), - metric.Value(), ts) + fmt.Fprintf(w, "%s %d %v\n", head, metric.Value(), ts) case metrics.GaugeFloat64: - fmt.Fprintf(w, "%s%s %f %v\n", head, EncodeLabels(metric.Labels()), - metric.Value(), ts) + fmt.Fprintf(w, "%s %f %v\n", head, metric.Value(), ts) case metrics.Meter: m := metric.Snapshot() - labels := EncodeLabels(m.Labels()) - fmt.Fprintf(w, "%s_count%s %d %v\n", head, labels, m.Count(), ts) - fmt.Fprintf(w, "%s_rate_1min%s %f %v\n", head, labels, m.Rate1(), ts) - fmt.Fprintf(w, "%s_rate_5min%s %f %v\n", head, labels, m.Rate5(), ts) - fmt.Fprintf(w, "%s_rate_15min%s %f %v\n", head, labels, m.Rate15(), ts) - fmt.Fprintf(w, "%s_rate_mean%s %f %v\n", head, labels, m.RateMean(), ts) + fmt.Fprintf(w, "%s_count %d %v\n", head, m.Count(), ts) + fmt.Fprintf(w, "%s_rate_1min %f %v\n", head, m.Rate1(), ts) + fmt.Fprintf(w, "%s_rate_5min %f %v\n", head, m.Rate5(), ts) + fmt.Fprintf(w, "%s_rate_15min %f %v\n", head, m.Rate15(), ts) + fmt.Fprintf(w, "%s_rate_mean %f %v\n", head, m.RateMean(), ts) case metrics.Timer: t := metric.Snapshot() - labels := EncodeLabels(t.Labels()) ps := t.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) - fmt.Fprintf(w, "%s_count%s %d %v\n", head, labels, t.Count(), ts) - fmt.Fprintf(w, "%s_min%s %d %v\n", head, labels, t.Min(), ts) - fmt.Fprintf(w, "%s_max%s %d %v\n", head, labels, t.Max(), ts) - fmt.Fprintf(w, "%s_mean%s %f %v\n", head, labels, t.Mean(), ts) - fmt.Fprintf(w, "%s_sum%s %d %v\n", head, labels, t.Sum(), ts) - fmt.Fprintf(w, "%s_stddev%s %f %v\n", head, labels, t.StdDev(), ts) - fmt.Fprintf(w, "%s_variance%s %f %v\n", head, labels, t.Variance(), ts) - fmt.Fprintf(w, "%s_median%s %f %v\n", head, labels, ps[0], ts) - fmt.Fprintf(w, "%s_percentile_75%s %f %v\n", head, labels, ps[1], ts) - fmt.Fprintf(w, "%s_percentile_95%s %f %v\n", head, labels, ps[2], ts) - fmt.Fprintf(w, "%s_percentile_99_0%s %f %v\n", head, labels, ps[3], ts) - fmt.Fprintf(w, "%s_percentile_99_9%s %f %v\n", head, labels, ps[4], ts) - fmt.Fprintf(w, "%s_rate_1min%s %f %v\n", head, labels, t.Rate1(), ts) - fmt.Fprintf(w, "%s_rate_5min%s %f %v\n", head, labels, t.Rate5(), ts) - fmt.Fprintf(w, "%s_rate_15min%s %f %v\n", head, labels, t.Rate15(), ts) - fmt.Fprintf(w, "%s_rate_mean%s %f %v\n", head, labels, t.RateMean(), ts) + fmt.Fprintf(w, "%s_count %d %v\n", head, t.Count(), ts) + fmt.Fprintf(w, "%s_min %d %v\n", head, t.Min(), ts) + fmt.Fprintf(w, "%s_max %d %v\n", head, t.Max(), ts) + fmt.Fprintf(w, "%s_mean %f %v\n", head, t.Mean(), ts) + fmt.Fprintf(w, "%s_sum %d %v\n", head, t.Sum(), ts) + fmt.Fprintf(w, "%s_stddev %f %v\n", head, t.StdDev(), ts) + fmt.Fprintf(w, "%s_variance %f %v\n", head, t.Variance(), ts) + fmt.Fprintf(w, "%s_median %f %v\n", head, ps[0], ts) + fmt.Fprintf(w, "%s_percentile_75 %f %v\n", head, ps[1], ts) + fmt.Fprintf(w, "%s_percentile_95 %f %v\n", head, ps[2], ts) + fmt.Fprintf(w, "%s_percentile_99_0 %f %v\n", head, ps[3], ts) + fmt.Fprintf(w, "%s_percentile_99_9 %f %v\n", head, ps[4], ts) + fmt.Fprintf(w, "%s_rate_1min %f %v\n", head, t.Rate1(), ts) + fmt.Fprintf(w, "%s_rate_5min %f %v\n", head, t.Rate5(), ts) + fmt.Fprintf(w, "%s_rate_15min %f %v\n", head, t.Rate15(), ts) + fmt.Fprintf(w, "%s_rate_mean %f %v\n", head, t.RateMean(), ts) case metrics.Histogram: h := metric.Snapshot() - labels := EncodeLabels(h.Labels()) ps := h.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) - fmt.Fprintf(w, "%s_count%s %d %v\n", head, labels, h.Count(), ts) - fmt.Fprintf(w, "%s_min%s %d %v\n", head, labels, h.Min(), ts) - fmt.Fprintf(w, "%s_max%s %d %v\n", head, labels, h.Max(), ts) - fmt.Fprintf(w, "%s_mean%s %f %v\n", head, labels, h.Mean(), ts) - fmt.Fprintf(w, "%s_sum%s %d %v\n", head, labels, h.Sum(), ts) - fmt.Fprintf(w, "%s_stddev%s %f %v\n", head, labels, h.StdDev(), ts) - fmt.Fprintf(w, "%s_variance%s %f %v\n", head, labels, h.Variance(), ts) - fmt.Fprintf(w, "%s_median%s %f %v\n", head, labels, ps[0], ts) - fmt.Fprintf(w, "%s_percentile_75%s %f %v\n", head, labels, ps[1], ts) - fmt.Fprintf(w, "%s_percentile_95%s %f %v\n", head, labels, ps[2], ts) - fmt.Fprintf(w, "%s_percentile_99_0%s %f %v\n", head, labels, ps[3], ts) - fmt.Fprintf(w, "%s_percentile_99_9%s %f %v\n", head, labels, ps[4], ts) + fmt.Fprintf(w, "%s_count %d %v\n", head, h.Count(), ts) + fmt.Fprintf(w, "%s_min %d %v\n", head, h.Min(), ts) + fmt.Fprintf(w, "%s_max %d %v\n", head, h.Max(), ts) + fmt.Fprintf(w, "%s_mean %f %v\n", head, h.Mean(), ts) + fmt.Fprintf(w, "%s_sum %d %v\n", head, h.Sum(), ts) + fmt.Fprintf(w, "%s_stddev %f %v\n", head, h.StdDev(), ts) + fmt.Fprintf(w, "%s_variance %f %v\n", head, h.Variance(), ts) + fmt.Fprintf(w, "%s_median %f %v\n", head, ps[0], ts) + fmt.Fprintf(w, "%s_percentile_75 %f %v\n", head, ps[1], ts) + fmt.Fprintf(w, "%s_percentile_95 %f %v\n", head, ps[2], ts) + fmt.Fprintf(w, "%s_percentile_99_0 %f %v\n", head, ps[3], ts) + fmt.Fprintf(w, "%s_percentile_99_9 %f %v\n", head, ps[4], ts) } } - -// EncodeLabels encodes labels into JSON format. Returns "" if the -// slice is empty. -func EncodeLabels(labels metrics.Labels) string { - if labels == nil || len(labels) < 1 { - return "" - } - str := "{" - for k, v := range labels { - str += k + ":\"" + v + "\"," - } - // Remove last comma character and add closing brace. - return str[:len(str)-1] + "}" -} diff --git a/logging/encode_test.go b/logging/encode_test.go index 73a4f93..891c65e 100644 --- a/logging/encode_test.go +++ b/logging/encode_test.go @@ -10,7 +10,7 @@ import ( func BenchmarkEncode(b *testing.B) { // Timer is worst-case scenario (most verbose). - timer := metrics.NewTimer(metrics.Labels{"key1": "value1", "key2": "value2"}) + timer := metrics.NewTimer() timer.Update(time.Second) b.ResetTimer() buf := new(bytes.Buffer) @@ -20,11 +20,11 @@ func BenchmarkEncode(b *testing.B) { } func TestEncodeCounter(t *testing.T) { - counter := metrics.NewCounter(metrics.Labels{"key1": "value1"}) + counter := metrics.NewCounter() counter.Inc(500) buf := new(bytes.Buffer) Encode(buf, "foo", "bar", counter) - expect := "bar_foo{key1:\"value1\"} 500" + expect := "bar_foo 500" if str := buf.String(); str[:len(str)-12] != expect { t.Errorf("Encode(): %s != %s", str[:len(str)-12], expect) } @@ -32,13 +32,13 @@ func TestEncodeCounter(t *testing.T) { // Without namespace. buf = new(bytes.Buffer) Encode(buf, "foo", "", counter) - expect = "foo{key1:\"value1\"} 500" + expect = "foo 500" if str := buf.String(); str[:len(str)-12] != expect { t.Errorf("Encode(): %s != %s", str[:len(str)-12], expect) } // Without labels. - counter = metrics.NewCounter(nil) + counter = metrics.NewCounter() buf = new(bytes.Buffer) Encode(buf, "foo", "bar", counter) expect = "bar_foo 0" @@ -48,11 +48,11 @@ func TestEncodeCounter(t *testing.T) { } func TestEncodeGauge(t *testing.T) { - gauge := metrics.NewGauge(metrics.Labels{"foo": "bar"}) + gauge := metrics.NewGauge() gauge.Update(10) buf := new(bytes.Buffer) Encode(buf, "foo", "bar", gauge) - expect := "bar_foo{foo:\"bar\"} 10" + expect := "bar_foo 10" if str := buf.String(); str[:len(str)-12] != expect { t.Errorf("Encode(): %s != %s", str[:len(str)-12], expect) } @@ -60,14 +60,14 @@ func TestEncodeGauge(t *testing.T) { // Without namespace. buf = new(bytes.Buffer) Encode(buf, "foo", "", gauge) - expect = "foo{foo:\"bar\"} 10" + expect = "foo 10" if str := buf.String(); str[:len(str)-12] != expect { t.Errorf("Encode(): %s != %s", str[:len(str)-12], expect) } // Without labels. buf = new(bytes.Buffer) - gauge = metrics.NewGauge(nil) + gauge = metrics.NewGauge() Encode(buf, "foo", "bar", gauge) expect = "bar_foo 0" if str := buf.String(); str[:len(str)-12] != expect { @@ -76,11 +76,11 @@ func TestEncodeGauge(t *testing.T) { } func TestEncodeGaugeFloat64(t *testing.T) { - gauge := metrics.NewGaugeFloat64(metrics.Labels{"foo": "bar"}) + gauge := metrics.NewGaugeFloat64() gauge.Update(10) buf := new(bytes.Buffer) Encode(buf, "foo", "bar", gauge) - expect := "bar_foo{foo:\"bar\"} 10.000000" + expect := "bar_foo 10.000000" if str := buf.String(); str[:len(str)-12] != expect { t.Errorf("Encode(): %s != %s", str[:len(str)-12], expect) } @@ -88,13 +88,13 @@ func TestEncodeGaugeFloat64(t *testing.T) { // Without namespace. buf = new(bytes.Buffer) Encode(buf, "foo", "", gauge) - expect = "foo{foo:\"bar\"} 10.000000" + expect = "foo 10.000000" if str := buf.String(); str[:len(str)-12] != expect { t.Errorf("Encode(): %s != %s", str[:len(str)-12], expect) } // Without labels. - gauge = metrics.NewGaugeFloat64(nil) + gauge = metrics.NewGaugeFloat64() buf = new(bytes.Buffer) Encode(buf, "foo", "bar", gauge) expect = "bar_foo 0.000000" @@ -104,7 +104,7 @@ func TestEncodeGaugeFloat64(t *testing.T) { } func TestEncodeHealthcheck(t *testing.T) { - check := metrics.NewHealthcheck(func(metrics.Healthcheck) {}, nil) + check := metrics.NewHealthcheck(func(metrics.Healthcheck) {}) buf := new(bytes.Buffer) Encode(buf, "foo", "bar", check) if str := buf.String(); str != "" { @@ -113,8 +113,7 @@ func TestEncodeHealthcheck(t *testing.T) { } func TestEncodeHistogram(t *testing.T) { - hist := metrics.NewHistogram(metrics.NewUniformSample(100), - metrics.Labels{"foo": "bar"}) + hist := metrics.NewHistogram(metrics.NewUniformSample(100)) hist.Update(100.0) buf := new(bytes.Buffer) Encode(buf, "foo", "bar", hist) @@ -122,51 +121,51 @@ func TestEncodeHistogram(t *testing.T) { if len(lines) != 13 { t.Fatal("Encode(): Did not produce 13 lines for histogram") } - expect := "bar_foo_count{foo:\"bar\"} 1" + expect := "bar_foo_count 1" if line := lines[0][:len(lines[0])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_min{foo:\"bar\"} 100" + expect = "bar_foo_min 100" if line := lines[1][:len(lines[1])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_max{foo:\"bar\"} 100" + expect = "bar_foo_max 100" if line := lines[2][:len(lines[2])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_mean{foo:\"bar\"} 100.000000" + expect = "bar_foo_mean 100.000000" if line := lines[3][:len(lines[3])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_sum{foo:\"bar\"} 100" + expect = "bar_foo_sum 100" if line := lines[4][:len(lines[4])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_stddev{foo:\"bar\"} 0.000000" + expect = "bar_foo_stddev 0.000000" if line := lines[5][:len(lines[5])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_variance{foo:\"bar\"} 0.000000" + expect = "bar_foo_variance 0.000000" if line := lines[6][:len(lines[6])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_median{foo:\"bar\"} 100.000000" + expect = "bar_foo_median 100.000000" if line := lines[7][:len(lines[7])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_percentile_75{foo:\"bar\"} 100.000000" + expect = "bar_foo_percentile_75 100.000000" if line := lines[8][:len(lines[8])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_percentile_95{foo:\"bar\"} 100.000000" + expect = "bar_foo_percentile_95 100.000000" if line := lines[9][:len(lines[9])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_percentile_99_0{foo:\"bar\"} 100.000000" + expect = "bar_foo_percentile_99_0 100.000000" if line := lines[10][:len(lines[10])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_percentile_99_9{foo:\"bar\"} 100.000000" + expect = "bar_foo_percentile_99_9 100.000000" if line := lines[11][:len(lines[11])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } @@ -178,57 +177,57 @@ func TestEncodeHistogram(t *testing.T) { if len(lines) != 13 { t.Fatal("Encode(): Did not produce 13 lines for histogram") } - expect = "foo_count{foo:\"bar\"} 1" + expect = "foo_count 1" if line := lines[0][:len(lines[0])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_min{foo:\"bar\"} 100" + expect = "foo_min 100" if line := lines[1][:len(lines[1])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_max{foo:\"bar\"} 100" + expect = "foo_max 100" if line := lines[2][:len(lines[2])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_mean{foo:\"bar\"} 100.000000" + expect = "foo_mean 100.000000" if line := lines[3][:len(lines[3])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_sum{foo:\"bar\"} 100" + expect = "foo_sum 100" if line := lines[4][:len(lines[4])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_stddev{foo:\"bar\"} 0.000000" + expect = "foo_stddev 0.000000" if line := lines[5][:len(lines[5])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_variance{foo:\"bar\"} 0.000000" + expect = "foo_variance 0.000000" if line := lines[6][:len(lines[6])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_median{foo:\"bar\"} 100.000000" + expect = "foo_median 100.000000" if line := lines[7][:len(lines[7])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_percentile_75{foo:\"bar\"} 100.000000" + expect = "foo_percentile_75 100.000000" if line := lines[8][:len(lines[8])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_percentile_95{foo:\"bar\"} 100.000000" + expect = "foo_percentile_95 100.000000" if line := lines[9][:len(lines[9])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_percentile_99_0{foo:\"bar\"} 100.000000" + expect = "foo_percentile_99_0 100.000000" if line := lines[10][:len(lines[10])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_percentile_99_9{foo:\"bar\"} 100.000000" + expect = "foo_percentile_99_9 100.000000" if line := lines[11][:len(lines[11])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } // Without labels. - hist = metrics.NewHistogram(metrics.NewUniformSample(100), nil) + hist = metrics.NewHistogram(metrics.NewUniformSample(100)) hist.Update(100) buf = new(bytes.Buffer) Encode(buf, "foo", "bar", hist) @@ -287,7 +286,7 @@ func TestEncodeHistogram(t *testing.T) { } func TestEncodeMeter(t *testing.T) { - meter := metrics.NewMeter(metrics.Labels{"foo": "bar"}) + meter := metrics.NewMeter() meter.Mark(20) buf := new(bytes.Buffer) Encode(buf, "foo", "bar", meter) @@ -295,23 +294,23 @@ func TestEncodeMeter(t *testing.T) { if len(lines) != 6 { t.Fatal("Encode(): Did not produce six lines for meter") } - expect := "bar_foo_count{foo:\"bar\"} 20" + expect := "bar_foo_count 20" if line := lines[0][:len(lines[0])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_rate_1min{foo:\"bar\"} 20.000000" + expect = "bar_foo_rate_1min 20.000000" if line := lines[1][:len(lines[1])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_rate_5min{foo:\"bar\"} 20.000000" + expect = "bar_foo_rate_5min 20.000000" if line := lines[2][:len(lines[2])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_rate_15min{foo:\"bar\"} 20.000000" + expect = "bar_foo_rate_15min 20.000000" if line := lines[3][:len(lines[3])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_rate_mean{foo:\"bar\"}" + expect = "bar_foo_rate_mean" if line := lines[4][:len(expect)]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } @@ -323,29 +322,29 @@ func TestEncodeMeter(t *testing.T) { if len(lines) != 6 { t.Fatal("Encode(): Did not produce six lines for meter") } - expect = "foo_count{foo:\"bar\"} 20" + expect = "foo_count 20" if line := lines[0][:len(lines[0])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_rate_1min{foo:\"bar\"} 20.000000" + expect = "foo_rate_1min 20.000000" if line := lines[1][:len(lines[1])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_rate_5min{foo:\"bar\"} 20.000000" + expect = "foo_rate_5min 20.000000" if line := lines[2][:len(lines[2])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_rate_15min{foo:\"bar\"} 20.000000" + expect = "foo_rate_15min 20.000000" if line := lines[3][:len(lines[3])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_rate_mean{foo:\"bar\"}" + expect = "foo_rate_mean" if line := lines[4][:len(expect)]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } // Without labels. - meter = metrics.NewMeter(nil) + meter = metrics.NewMeter() buf = new(bytes.Buffer) Encode(buf, "foo", "bar", meter) lines = strings.Split(buf.String(), "\n") @@ -376,74 +375,74 @@ func TestEncodeMeter(t *testing.T) { func TestEncodeTimer(t *testing.T) { // Do not timer.Update() without some time.Sleep, results are erratic. - timer := metrics.NewTimer(metrics.Labels{"foo": "bar"}) + timer := metrics.NewTimer() buf := new(bytes.Buffer) Encode(buf, "foo", "bar", timer) lines := strings.Split(buf.String(), "\n") if len(lines) != 17 { t.Fatal("Encode(): Did not produce 17 lines for timer") } - expect := "bar_foo_count{foo:\"bar\"} 0" + expect := "bar_foo_count 0" if line := lines[0][:len(lines[0])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_min{foo:\"bar\"} 0" + expect = "bar_foo_min 0" if line := lines[1][:len(lines[1])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_max{foo:\"bar\"} 0" + expect = "bar_foo_max 0" if line := lines[2][:len(lines[2])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_mean{foo:\"bar\"} 0.000000" + expect = "bar_foo_mean 0.000000" if line := lines[3][:len(lines[3])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_sum{foo:\"bar\"} 0" + expect = "bar_foo_sum 0" if line := lines[4][:len(lines[4])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_stddev{foo:\"bar\"} 0.000000" + expect = "bar_foo_stddev 0.000000" if line := lines[5][:len(lines[5])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_variance{foo:\"bar\"} 0.000000" + expect = "bar_foo_variance 0.000000" if line := lines[6][:len(lines[6])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_median{foo:\"bar\"} 0.000000" + expect = "bar_foo_median 0.000000" if line := lines[7][:len(lines[7])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_percentile_75{foo:\"bar\"} 0.000000" + expect = "bar_foo_percentile_75 0.000000" if line := lines[8][:len(lines[8])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_percentile_95{foo:\"bar\"} 0.000000" + expect = "bar_foo_percentile_95 0.000000" if line := lines[9][:len(lines[9])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_percentile_99_0{foo:\"bar\"} 0.000000" + expect = "bar_foo_percentile_99_0 0.000000" if line := lines[10][:len(lines[10])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_percentile_99_9{foo:\"bar\"} 0.000000" + expect = "bar_foo_percentile_99_9 0.000000" if line := lines[11][:len(lines[11])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_rate_1min{foo:\"bar\"} 0.000000" + expect = "bar_foo_rate_1min 0.000000" if line := lines[12][:len(lines[12])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_rate_5min{foo:\"bar\"} 0.000000" + expect = "bar_foo_rate_5min 0.000000" if line := lines[13][:len(lines[13])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_rate_15min{foo:\"bar\"} 0.000000" + expect = "bar_foo_rate_15min 0.000000" if line := lines[14][:len(lines[14])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "bar_foo_rate_mean{foo:\"bar\"} 0.000000" + expect = "bar_foo_rate_mean 0.000000" if line := lines[15][:len(lines[15])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } @@ -455,73 +454,73 @@ func TestEncodeTimer(t *testing.T) { if len(lines) != 17 { t.Error("Encode(): Did not produce 17 lines for timer") } - expect = "foo_count{foo:\"bar\"} 0" + expect = "foo_count 0" if line := lines[0][:len(lines[0])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_min{foo:\"bar\"} 0" + expect = "foo_min 0" if line := lines[1][:len(lines[1])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_max{foo:\"bar\"} 0" + expect = "foo_max 0" if line := lines[2][:len(lines[2])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_mean{foo:\"bar\"} 0.000000" + expect = "foo_mean 0.000000" if line := lines[3][:len(lines[3])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_sum{foo:\"bar\"} 0" + expect = "foo_sum 0" if line := lines[4][:len(lines[4])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_stddev{foo:\"bar\"} 0.000000" + expect = "foo_stddev 0.000000" if line := lines[5][:len(lines[5])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_variance{foo:\"bar\"} 0.000000" + expect = "foo_variance 0.000000" if line := lines[6][:len(lines[6])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_median{foo:\"bar\"} 0.000000" + expect = "foo_median 0.000000" if line := lines[7][:len(lines[7])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_percentile_75{foo:\"bar\"} 0.000000" + expect = "foo_percentile_75 0.000000" if line := lines[8][:len(lines[8])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_percentile_95{foo:\"bar\"} 0.000000" + expect = "foo_percentile_95 0.000000" if line := lines[9][:len(lines[9])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_percentile_99_0{foo:\"bar\"} 0.000000" + expect = "foo_percentile_99_0 0.000000" if line := lines[10][:len(lines[10])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_percentile_99_9{foo:\"bar\"} 0.000000" + expect = "foo_percentile_99_9 0.000000" if line := lines[11][:len(lines[11])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_rate_1min{foo:\"bar\"} 0.000000" + expect = "foo_rate_1min 0.000000" if line := lines[12][:len(lines[12])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_rate_5min{foo:\"bar\"} 0.000000" + expect = "foo_rate_5min 0.000000" if line := lines[13][:len(lines[13])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_rate_15min{foo:\"bar\"} 0.000000" + expect = "foo_rate_15min 0.000000" if line := lines[14][:len(lines[14])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } - expect = "foo_rate_mean{foo:\"bar\"} 0.000000" + expect = "foo_rate_mean 0.000000" if line := lines[15][:len(lines[15])-11]; line != expect { t.Errorf("Encode(): %s != %s", line, expect) } // Without labels. - timer = metrics.NewTimer(nil) + timer = metrics.NewTimer() buf = new(bytes.Buffer) Encode(buf, "foo", "", timer) lines = strings.Split(buf.String(), "\n") @@ -606,17 +605,3 @@ func TestEncodeUnknown(t *testing.T) { t.Errorf("Encode(): Unknown struct returned non-empty string: %s", str) } } - -func TestEncodeLabels(t *testing.T) { - a := metrics.Labels{"key1": "value1", "key2": "value2"} - - // Empty slice returns empty string. - if str := EncodeLabels(nil); str != "" { - t.Errorf("EncodeLabels(): Empty slice returned %s", str) - } - - expect := "{key1:\"value1\",key2:\"value2\"}" - if str := EncodeLabels(a); str != expect { - t.Errorf("EncodeLabels(): %s != %s", str, expect) - } -} diff --git a/logging/graphite.go b/logging/graphite.go index d028948..65400a4 100644 --- a/logging/graphite.go +++ b/logging/graphite.go @@ -18,71 +18,51 @@ func EncodeGraphite(w io.Writer, name, prefix string, i interface{}) { switch metric := i.(type) { case metrics.Counter: - labels := EncodeGraphiteLabels(metric.Labels()) - fmt.Fprintf(w, "%s%s %d %d\n", head, labels, metric.Count(), ts) + fmt.Fprintf(w, "%s %d %d\n", head, metric.Count(), ts) case metrics.Gauge: - labels := EncodeGraphiteLabels(metric.Labels()) - fmt.Fprintf(w, "%s%s %d %d\n", head, labels, metric.Value(), ts) + fmt.Fprintf(w, "%s %d %d\n", head, metric.Value(), ts) case metrics.GaugeFloat64: - labels := EncodeGraphiteLabels(metric.Labels()) - fmt.Fprintf(w, "%s%s %f %d\n", head, labels, metric.Value(), ts) + fmt.Fprintf(w, "%s %f %d\n", head, metric.Value(), ts) case metrics.Meter: m := metric.Snapshot() - labels := EncodeGraphiteLabels(m.Labels()) - fmt.Fprintf(w, "%s.count%s %d %d\n", head, labels, m.Count(), ts) - fmt.Fprintf(w, "%s.rate.1min%s %f %d\n", head, labels, m.Rate1(), ts) - fmt.Fprintf(w, "%s.rate.5min%s %f %d\n", head, labels, m.Rate5(), ts) - fmt.Fprintf(w, "%s.rate.15min%s %f %d\n", head, labels, m.Rate15(), ts) - fmt.Fprintf(w, "%s.rate.mean%s %f %d\n", head, labels, m.RateMean(), ts) + fmt.Fprintf(w, "%s.count %d %d\n", head, m.Count(), ts) + fmt.Fprintf(w, "%s.rate.1min %f %d\n", head, m.Rate1(), ts) + fmt.Fprintf(w, "%s.rate.5min %f %d\n", head, m.Rate5(), ts) + fmt.Fprintf(w, "%s.rate.15min %f %d\n", head, m.Rate15(), ts) + fmt.Fprintf(w, "%s.rate.mean %f %d\n", head, m.RateMean(), ts) case metrics.Timer: t := metric.Snapshot() - labels := EncodeGraphiteLabels(t.Labels()) ps := t.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) - fmt.Fprintf(w, "%s.count%s %d %d\n", head, labels, t.Count(), ts) - fmt.Fprintf(w, "%s.min%s %d %d\n", head, labels, t.Min(), ts) - fmt.Fprintf(w, "%s.max%s %d %d\n", head, labels, t.Max(), ts) - fmt.Fprintf(w, "%s.mean%s %f %d\n", head, labels, t.Mean(), ts) - fmt.Fprintf(w, "%s.sum%s %d %d\n", head, labels, t.Sum(), ts) - fmt.Fprintf(w, "%s.stddev%s %f %d\n", head, labels, t.StdDev(), ts) - fmt.Fprintf(w, "%s.variance%s %f %d\n", head, labels, t.Variance(), ts) - fmt.Fprintf(w, "%s.median%s %f %d\n", head, labels, ps[0], ts) - fmt.Fprintf(w, "%s.percentile.75%s %f %d\n", head, labels, ps[1], ts) - fmt.Fprintf(w, "%s.percentile.95%s %f %d\n", head, labels, ps[2], ts) - fmt.Fprintf(w, "%s.percentile.99.0%s %f %d\n", head, labels, ps[3], ts) - fmt.Fprintf(w, "%s.percentile.99.9%s %f %d\n", head, labels, ps[4], ts) - fmt.Fprintf(w, "%s.rate.1min%s %f %d\n", head, labels, t.Rate1(), ts) - fmt.Fprintf(w, "%s.rate.5min%s %f %d\n", head, labels, t.Rate5(), ts) - fmt.Fprintf(w, "%s.rate.15min%s %f %d\n", head, labels, t.Rate15(), ts) - fmt.Fprintf(w, "%s.rate.mean%s %f %d\n", head, labels, t.RateMean(), ts) + fmt.Fprintf(w, "%s.count %d %d\n", head, t.Count(), ts) + fmt.Fprintf(w, "%s.min %d %d\n", head, t.Min(), ts) + fmt.Fprintf(w, "%s.max %d %d\n", head, t.Max(), ts) + fmt.Fprintf(w, "%s.mean %f %d\n", head, t.Mean(), ts) + fmt.Fprintf(w, "%s.sum %d %d\n", head, t.Sum(), ts) + fmt.Fprintf(w, "%s.stddev %f %d\n", head, t.StdDev(), ts) + fmt.Fprintf(w, "%s.variance %f %d\n", head, t.Variance(), ts) + fmt.Fprintf(w, "%s.median %f %d\n", head, ps[0], ts) + fmt.Fprintf(w, "%s.percentile.75 %f %d\n", head, ps[1], ts) + fmt.Fprintf(w, "%s.percentile.95 %f %d\n", head, ps[2], ts) + fmt.Fprintf(w, "%s.percentile.99.0 %f %d\n", head, ps[3], ts) + fmt.Fprintf(w, "%s.percentile.99.9 %f %d\n", head, ps[4], ts) + fmt.Fprintf(w, "%s.rate.1min %f %d\n", head, t.Rate1(), ts) + fmt.Fprintf(w, "%s.rate.5min %f %d\n", head, t.Rate5(), ts) + fmt.Fprintf(w, "%s.rate.15min %f %d\n", head, t.Rate15(), ts) + fmt.Fprintf(w, "%s.rate.mean %f %d\n", head, t.RateMean(), ts) case metrics.Histogram: h := metric.Snapshot() - labels := EncodeLabels(h.Labels()) ps := h.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) - fmt.Fprintf(w, "%s.count%s %d %v\n", head, labels, h.Count(), ts) - fmt.Fprintf(w, "%s.min%s %d %v\n", head, labels, h.Min(), ts) - fmt.Fprintf(w, "%s.max%s %d %v\n", head, labels, h.Max(), ts) - fmt.Fprintf(w, "%s.mean%s %f %v\n", head, labels, h.Mean(), ts) - fmt.Fprintf(w, "%s.sum%s %d %d\n", head, labels, h.Sum(), ts) - fmt.Fprintf(w, "%s.stddev%s %f %v\n", head, labels, h.StdDev(), ts) - fmt.Fprintf(w, "%s.variance%s %f %d\n", head, labels, h.Variance(), ts) - fmt.Fprintf(w, "%s.median%s %f %v\n", head, labels, ps[0], ts) - fmt.Fprintf(w, "%s.percentile.75%s %f %v\n", head, labels, ps[1], ts) - fmt.Fprintf(w, "%s.percentile.95%s %f %v\n", head, labels, ps[2], ts) - fmt.Fprintf(w, "%s.percentile.99.0%s %f %v\n", head, labels, ps[3], ts) - fmt.Fprintf(w, "%s.percentile.99.9%s %f %v\n", head, labels, ps[4], ts) + fmt.Fprintf(w, "%s.count %d %v\n", head, h.Count(), ts) + fmt.Fprintf(w, "%s.min %d %v\n", head, h.Min(), ts) + fmt.Fprintf(w, "%s.max %d %v\n", head, h.Max(), ts) + fmt.Fprintf(w, "%s.mean %f %v\n", head, h.Mean(), ts) + fmt.Fprintf(w, "%s.sum %d %d\n", head, h.Sum(), ts) + fmt.Fprintf(w, "%s.stddev %f %v\n", head, h.StdDev(), ts) + fmt.Fprintf(w, "%s.variance %f %d\n", head, h.Variance(), ts) + fmt.Fprintf(w, "%s.median %f %v\n", head, ps[0], ts) + fmt.Fprintf(w, "%s.percentile.75 %f %v\n", head, ps[1], ts) + fmt.Fprintf(w, "%s.percentile.95 %f %v\n", head, ps[2], ts) + fmt.Fprintf(w, "%s.percentile.99.0 %f %v\n", head, ps[3], ts) + fmt.Fprintf(w, "%s.percentile.99.9 %f %v\n", head, ps[4], ts) } } - -// EncodeGraphiteLabels encodes a series of labels into a string label format -// that's recognized by a graphite server. -func EncodeGraphiteLabels(labels metrics.Labels) string { - if labels == nil || len(labels) < 1 { - return "" - } - str := ";" - for k, v := range labels { - str += k + "=" + v + ";" - } - // Remove last semicolon character. - return str[:len(str)-1] -} diff --git a/meter.go b/meter.go index fea8bac..91436dc 100644 --- a/meter.go +++ b/meter.go @@ -15,32 +15,28 @@ type Meter interface { Rate15() float64 RateMean() float64 Snapshot() Meter - Labels() Labels - WithLabels(Labels) Meter } // GetOrRegisterMeter returns an existing Meter or constructs and registers a // new StandardMeter. -func GetOrRegisterMeter(name string, r Registry, labels Labels) Meter { +func GetOrRegisterMeter(name string, r Registry) Meter { if nil == r { r = DefaultRegistry } - return r.GetOrRegister(name, func() Meter { - return NewMeter(labels) - }).(Meter) + return r.GetOrRegister(name, NewMeter).(Meter) } // NewMeter constructs a new StandardMeter. -func NewMeter(labels Labels) Meter { +func NewMeter() Meter { if UseNilMetrics { return NilMeter{} } - return newStandardMeter(labels) + return newStandardMeter() } // NewRegisteredMeter constructs and registers a new StandardMeter. -func NewRegisteredMeter(name string, r Registry, labels Labels) Meter { - c := NewMeter(labels) +func NewRegisteredMeter(name string, r Registry) Meter { + c := NewMeter() if nil == r { r = DefaultRegistry } @@ -52,7 +48,6 @@ func NewRegisteredMeter(name string, r Registry, labels Labels) Meter { type MeterSnapshot struct { count int64 rate1, rate5, rate15, rateMean float64 - labels Labels } // Count returns the count of events at the time the snapshot was taken. @@ -82,26 +77,6 @@ func (m *MeterSnapshot) RateMean() float64 { return m.rateMean } // Snapshot returns the snapshot. func (m *MeterSnapshot) Snapshot() Meter { return m } -// Labels returns the snapshot's labels. -func (m *MeterSnapshot) Labels() Labels { return deepCopyLabels(m.labels) } - -// WithLabels returns a copy of the snapshot with the given labels appended to -// the current list of labels. -func (m *MeterSnapshot) WithLabels(labels Labels) Meter { - newLabels := m.labels - for k, v := range labels { - newLabels[k] = v - } - return &MeterSnapshot{ - count: m.Count(), - rate1: m.Rate1(), - rate5: m.Rate5(), - rate15: m.Rate15(), - rateMean: m.RateMean(), - labels: newLabels, - } -} - // NilMeter is a no-op Meter. type NilMeter struct{} @@ -126,27 +101,19 @@ func (NilMeter) RateMean() float64 { return 0.0 } // Snapshot is a no-op. func (NilMeter) Snapshot() Meter { return NilMeter{} } -// Labels is a no-op. -func (NilMeter) Labels() Labels { return Labels{} } - -// WithLabels is a no-op. -func (NilMeter) WithLabels(Labels) Meter { return NilMeter{} } - // StandardMeter is the standard implementation of a Meter. type StandardMeter struct { count atomic.Int64 a1, a5, a15 EWMA startTime time.Time - labels Labels } -func newStandardMeter(labels Labels) *StandardMeter { +func newStandardMeter() *StandardMeter { return &StandardMeter{ a1: NewEWMA1(), a5: NewEWMA5(), a15: NewEWMA15(), startTime: time.Now(), - labels: deepCopyLabels(labels), } } @@ -191,15 +158,5 @@ func (m *StandardMeter) Snapshot() Meter { rate5: m.Rate5(), rate15: m.Rate15(), rateMean: m.RateMean(), - labels: m.Labels(), } } - -// Labels returns a deep copy of the meter's labels. -func (m *StandardMeter) Labels() Labels { return deepCopyLabels(m.labels) } - -// WithLabels returns a snapshot of the Meter with the given labels appended to -// the current list of labels. -func (m *StandardMeter) WithLabels(labels Labels) Meter { - return m.Snapshot().WithLabels(labels) -} diff --git a/meter_test.go b/meter_test.go index a2b760f..a0ee63a 100644 --- a/meter_test.go +++ b/meter_test.go @@ -8,7 +8,7 @@ import ( ) func BenchmarkMeter(b *testing.B) { - m := NewMeter(nil) + m := NewMeter() b.ResetTimer() for i := 0; i < b.N; i++ { m.Mark(1) @@ -16,7 +16,7 @@ func BenchmarkMeter(b *testing.B) { } func BenchmarkMeterParallel(b *testing.B) { - m := NewMeter(nil) + m := NewMeter() b.ResetTimer() b.RunParallel(func(pb *testing.PB) { for pb.Next() { @@ -27,7 +27,7 @@ func BenchmarkMeterParallel(b *testing.B) { // exercise race detector func TestMeterConcurrency(t *testing.T) { - m := newStandardMeter(nil) + m := newStandardMeter() wg := &sync.WaitGroup{} reps := 100 for i := 0; i < reps; i++ { @@ -49,14 +49,14 @@ func TestMeterConcurrency(t *testing.T) { func TestGetOrRegisterMeter(t *testing.T) { r := NewRegistry() - NewRegisteredMeter("foo", r, nil).Mark(47) - if m := GetOrRegisterMeter("foo", r, nil); m.Count() != 47 { + NewRegisteredMeter("foo", r).Mark(47) + if m := GetOrRegisterMeter("foo", r); m.Count() != 47 { t.Fatal(m) } } func TestMeterDecay(t *testing.T) { - m := newStandardMeter(nil) + m := newStandardMeter() m.Mark(1) rateMean := m.RateMean() time.Sleep(100 * time.Millisecond) @@ -66,7 +66,7 @@ func TestMeterDecay(t *testing.T) { } func TestMeterNonzero(t *testing.T) { - m := NewMeter(nil) + m := NewMeter() m.Mark(3) if count := m.Count(); count != 3 { t.Errorf("m.Count(): 3 != %v\n", count) @@ -75,7 +75,7 @@ func TestMeterNonzero(t *testing.T) { func TestMeterSnapshot(t *testing.T) { r := rand.New(rand.NewSource(time.Now().Unix())) - m := NewMeter(nil) + m := NewMeter() m.Mark(r.Int63()) if snapshot := m.Snapshot(); m.Count() != snapshot.Count() { t.Fatal(snapshot) @@ -83,48 +83,8 @@ func TestMeterSnapshot(t *testing.T) { } func TestMeterZero(t *testing.T) { - m := NewMeter(nil) + m := NewMeter() if count := m.Count(); count != 0 { t.Errorf("m.Count(): 0 != %v\n", count) } } - -func TestMeterLabels(t *testing.T) { - labels := Labels{"key1": "value1"} - m := NewMeter(labels) - if len(m.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(m.Labels())) - } - if lbls := m.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } - - // Labels passed by value. - labels["key1"] = "value3" - if lbls := m.Labels()["key1"]; lbls != "value1" { - t.Error("Labels(): labels passed by reference") - } - - // Labels in snapshot. - ss := m.Snapshot() - if len(ss.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(m.Labels())) - } - if lbls := ss.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } -} - -func TestMeterWithLabels(t *testing.T) { - m := NewMeter(Labels{"foo": "bar"}) - new := m.WithLabels(Labels{"bar": "foo"}) - if len(new.Labels()) != 2 { - t.Fatalf("WithLabels() len: %v != 2", len(new.Labels())) - } - if lbls := new.Labels()["foo"]; lbls != "bar" { - t.Errorf("WithLabels(): %v != bar", lbls) - } - if lbls := new.Labels()["bar"]; lbls != "foo" { - t.Errorf("WithLabels(): %v != foo", lbls) - } -} diff --git a/metrics_test.go b/metrics_test.go index 07a5b13..ce4eefc 100644 --- a/metrics_test.go +++ b/metrics_test.go @@ -18,12 +18,12 @@ var ( func BenchmarkMetrics(b *testing.B) { r := NewRegistry() - c := NewRegisteredCounter("counter", r, nil) - g := NewRegisteredGauge("gauge", r, nil) - gf := NewRegisteredGaugeFloat64("gaugefloat64", r, nil) - h := NewRegisteredHistogram("histogram", r, NewUniformSample(100), nil) - m := NewRegisteredMeter("meter", r, nil) - t := NewRegisteredTimer("timer", r, nil) + c := NewRegisteredCounter("counter", r) + g := NewRegisteredGauge("gauge", r) + gf := NewRegisteredGaugeFloat64("gaugefloat64", r) + h := NewRegisteredHistogram("histogram", r, NewUniformSample(100)) + m := NewRegisteredMeter("meter", r) + t := NewRegisteredTimer("timer", r) RegisterDebugGCStats(r) RegisterRuntimeMemStats(r) b.ResetTimer() @@ -108,12 +108,12 @@ func BenchmarkMetrics(b *testing.B) { } func Example() { - c := NewCounter(nil) + c := NewCounter() Register("money", c) c.Inc(17) // Threadsafe registration - t := GetOrRegisterTimer("db.get.latency", nil, nil) + t := GetOrRegisterTimer("db.get.latency", nil) t.Time(func() {}) t.Update(1) diff --git a/prometheus/prometheus.go b/prometheus/prometheus.go index cb72341..031b5f5 100644 --- a/prometheus/prometheus.go +++ b/prometheus/prometheus.go @@ -58,21 +58,15 @@ func NewWithConfig(c Config, p *pr.Registry) (*Prometheus, error) { // Retrieves or creates a gauge vector for the given name and label set. Not // threadsafe, must be called with a mutex. -func (p *Prometheus) getVector(name string, labels metrics.Labels) *pr.GaugeVec { +func (p *Prometheus) getVector(name string) *pr.GaugeVec { vec, ok := p.vectors[name] if !ok { - // Get label keys. - keys := []string{} - for k := range labels { - keys = append(keys, k) - } vec = pr.NewGaugeVec(pr.GaugeOpts{ Namespace: p.config.Namespace, Subsystem: p.config.Subsystem, Name: name, Help: name, - }, keys) - + }, nil) p.vectors[name] = vec p.reg.MustRegister(vec) } @@ -82,9 +76,9 @@ func (p *Prometheus) getVector(name string, labels metrics.Labels) *pr.GaugeVec // Sets the value of the gauge with name and labels. Prints an error if the // gauge cannot be set or labels dont match predefined schema. Not threadsafe, // must be called with a mutex. -func (p *Prometheus) setValue(name string, val float64, labels metrics.Labels) { - vec := p.getVector(name, labels) - gauge, err := vec.GetMetricWith(pr.Labels(labels)) +func (p *Prometheus) setValue(name string, val float64) { + vec := p.getVector(name) + gauge, err := vec.GetMetricWith(nil) if err != nil { log.Printf("Error: (metrics) ignoring %s due to error: %s", name, err) return @@ -101,57 +95,54 @@ func (p *Prometheus) Once() { switch metric := i.(type) { case metrics.Counter: m := metric.Snapshot() - p.setValue(name+"_count", float64(m.Count()), m.Labels()) + p.setValue(name+"_count", float64(m.Count())) case metrics.Gauge: m := metric.Snapshot() - p.setValue(name+"_gauge", float64(m.Value()), m.Labels()) + p.setValue(name+"_gauge", float64(m.Value())) case metrics.GaugeFloat64: m := metric.Snapshot() - p.setValue(name+"_gauge", m.Value(), m.Labels()) + p.setValue(name+"_gauge", m.Value()) case metrics.Meter: m := metric.Snapshot() - labels := m.Labels() - p.setValue(name+"_count", float64(m.Count()), labels) - p.setValue(name+"_rate_1min", m.Rate1(), labels) - p.setValue(name+"_rate_5min", m.Rate5(), labels) - p.setValue(name+"_rate_15min", m.Rate15(), labels) - p.setValue(name+"_rate_mean", m.RateMean(), labels) + p.setValue(name+"_count", float64(m.Count())) + p.setValue(name+"_rate_1min", m.Rate1()) + p.setValue(name+"_rate_5min", m.Rate5()) + p.setValue(name+"_rate_15min", m.Rate15()) + p.setValue(name+"_rate_mean", m.RateMean()) case metrics.Timer: m := metric.Snapshot() ps := m.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) - labels := m.Labels() - p.setValue(name+"_count", float64(m.Count()), labels) - p.setValue(name+"_min", float64(m.Min()), labels) - p.setValue(name+"_max", float64(m.Max()), labels) - p.setValue(name+"_mean", m.Mean(), labels) - p.setValue(name+"_sum", float64(m.Sum()), labels) - p.setValue(name+"_variance", m.Variance(), labels) - p.setValue(name+"_stddev", m.StdDev(), labels) - p.setValue(name+"_median", ps[0], labels) - p.setValue(name+"_percentile_75", ps[1], labels) - p.setValue(name+"_percentile_95", ps[2], labels) - p.setValue(name+"_percentile_99_0", ps[3], labels) - p.setValue(name+"_percentile_99_9", ps[4], labels) - p.setValue(name+"_rate_1min", m.Rate1(), labels) - p.setValue(name+"_rate_5min", m.Rate5(), labels) - p.setValue(name+"_rate_15min", m.Rate15(), labels) - p.setValue(name+"_rate_mean", m.RateMean(), labels) + p.setValue(name+"_count", float64(m.Count())) + p.setValue(name+"_min", float64(m.Min())) + p.setValue(name+"_max", float64(m.Max())) + p.setValue(name+"_mean", m.Mean()) + p.setValue(name+"_sum", float64(m.Sum())) + p.setValue(name+"_variance", m.Variance()) + p.setValue(name+"_stddev", m.StdDev()) + p.setValue(name+"_median", ps[0]) + p.setValue(name+"_percentile_75", ps[1]) + p.setValue(name+"_percentile_95", ps[2]) + p.setValue(name+"_percentile_99_0", ps[3]) + p.setValue(name+"_percentile_99_9", ps[4]) + p.setValue(name+"_rate_1min", m.Rate1()) + p.setValue(name+"_rate_5min", m.Rate5()) + p.setValue(name+"_rate_15min", m.Rate15()) + p.setValue(name+"_rate_mean", m.RateMean()) case metrics.Histogram: m := metric.Snapshot() ps := m.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) - labels := m.Labels() - p.setValue(name+"_count", float64(m.Count()), labels) - p.setValue(name+"_min", float64(m.Min()), labels) - p.setValue(name+"_max", float64(m.Max()), labels) - p.setValue(name+"_mean", m.Mean(), labels) - p.setValue(name+"_sum", float64(m.Sum()), labels) - p.setValue(name+"_variance", m.Variance(), labels) - p.setValue(name+"_stddev", m.StdDev(), labels) - p.setValue(name+"_median", ps[0], labels) - p.setValue(name+"_percentile_75", ps[1], labels) - p.setValue(name+"_percentile_95", ps[2], labels) - p.setValue(name+"_percentile_99_0", ps[3], labels) - p.setValue(name+"_percentile_99_9", ps[4], labels) + p.setValue(name+"_count", float64(m.Count())) + p.setValue(name+"_min", float64(m.Min())) + p.setValue(name+"_max", float64(m.Max())) + p.setValue(name+"_mean", m.Mean()) + p.setValue(name+"_sum", float64(m.Sum())) + p.setValue(name+"_variance", m.Variance()) + p.setValue(name+"_stddev", m.StdDev()) + p.setValue(name+"_median", ps[0]) + p.setValue(name+"_percentile_75", ps[1]) + p.setValue(name+"_percentile_95", ps[2]) + p.setValue(name+"_percentile_99_0", ps[3]) + p.setValue(name+"_percentile_99_9", ps[4]) } }) } diff --git a/prometheus/prometheus_test.go b/prometheus/prometheus_test.go index 37fb411..6d61b05 100644 --- a/prometheus/prometheus_test.go +++ b/prometheus/prometheus_test.go @@ -14,9 +14,9 @@ import ( func ExamplePrometheus() { // Register some metrics. - metrics.GetOrRegisterTimer("myTimer", nil, nil).Update(time.Second) - metrics.GetOrRegisterCounter("myCounter", nil, nil).Inc(50) - metrics.GetOrRegisterMeter("myMeter", nil, nil).Mark(10) + metrics.GetOrRegisterTimer("myTimer", nil).Update(time.Second) + metrics.GetOrRegisterCounter("myCounter", nil).Inc(50) + metrics.GetOrRegisterMeter("myMeter", nil).Mark(10) // Create prometheus driver. r := prometheus.NewRegistry() @@ -38,8 +38,8 @@ func ExamplePrometheus() { func BenchmarkPrometheus(b *testing.B) { s := metrics.NewUniformSample(100) metricRegistry := metrics.NewRegistry() - metrics.GetOrRegisterMeter("myMeter", metricRegistry, nil).Mark(420) - metrics.GetOrRegisterHistogram("myHist", metricRegistry, s, nil).Update(33) + metrics.GetOrRegisterMeter("myMeter", metricRegistry).Mark(420) + metrics.GetOrRegisterHistogram("myHist", metricRegistry, s).Update(33) r := prometheus.NewRegistry() pr, _ := New(metricRegistry, time.Nanosecond, "ns", "ss", r) @@ -53,8 +53,8 @@ func BenchmarkPrometheus(b *testing.B) { func TestPrometheusConcurrency(t *testing.T) { s := metrics.NewUniformSample(100) metricRegistry := metrics.NewRegistry() - metrics.GetOrRegisterMeter("myMeter", metricRegistry, nil).Mark(420) - metrics.GetOrRegisterHistogram("myHist", metricRegistry, s, nil).Update(33) + metrics.GetOrRegisterMeter("myMeter", metricRegistry).Mark(420) + metrics.GetOrRegisterHistogram("myHist", metricRegistry, s).Update(33) r := prometheus.NewRegistry() pr, err := New(metricRegistry, time.Nanosecond, "ns", "ss", r) @@ -90,9 +90,9 @@ func TestPrometheusCreate(t *testing.T) { } func TestPrometheusOnce(t *testing.T) { - metrics.GetOrRegisterCounter("counter", nil, nil).Inc(45) - metrics.GetOrRegisterGauge("gauge", nil, metrics.Labels{"foo": "bar"}).Update(45) - metrics.GetOrRegisterMeter("meter", nil, nil).Mark(45) + metrics.GetOrRegisterCounter("counter", nil).Inc(45) + metrics.GetOrRegisterGauge("gauge", nil).Update(45) + metrics.GetOrRegisterMeter("meter", nil).Mark(45) r := prometheus.NewRegistry() pr, err := New(metrics.DefaultRegistry, time.Second, "", "", r) @@ -115,7 +115,7 @@ func TestPrometheusOnce(t *testing.T) { // GaugeFloat64 expected = "name:\"gauge_gauge\" help:\"gauge_gauge\" type:GAUGE " + - "metric: gauge: > " + "metric: > " if expected != fmt.Sprint(metrics[1]) { t.Errorf("Once(): %s != %s", expected, metrics[1]) } diff --git a/registry.go b/registry.go index ebaa741..50da2ac 100644 --- a/registry.go +++ b/registry.go @@ -154,16 +154,12 @@ func (r *StandardRegistry) GetAll() map[string]map[string]interface{} { switch metric := i.(type) { case Counter: values["count"] = metric.Count() - values["labels"] = metric.Labels() case Gauge: values["value"] = metric.Value() - values["labels"] = metric.Labels() case GaugeFloat64: values["value"] = metric.Value() - values["labels"] = metric.Labels() case Healthcheck: values["error"] = nil - values["labels"] = metric.Labels() metric.Check() if err := metric.Error(); nil != err { values["error"] = metric.Error().Error() @@ -181,7 +177,6 @@ func (r *StandardRegistry) GetAll() map[string]map[string]interface{} { values["95%"] = ps[2] values["99%"] = ps[3] values["99.9%"] = ps[4] - values["labels"] = metric.Labels() case Meter: m := metric.Snapshot() values["count"] = m.Count() @@ -189,7 +184,6 @@ func (r *StandardRegistry) GetAll() map[string]map[string]interface{} { values["5m.rate"] = m.Rate5() values["15m.rate"] = m.Rate15() values["mean.rate"] = m.RateMean() - values["labels"] = metric.Labels() case Timer: t := metric.Snapshot() ps := t.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999}) @@ -207,7 +201,6 @@ func (r *StandardRegistry) GetAll() map[string]map[string]interface{} { values["5m.rate"] = t.Rate5() values["15m.rate"] = t.Rate15() values["mean.rate"] = t.RateMean() - values["labels"] = metric.Labels() } data[name] = values }) diff --git a/registry_test.go b/registry_test.go index b44063a..67a0e3a 100644 --- a/registry_test.go +++ b/registry_test.go @@ -8,7 +8,7 @@ import ( func BenchmarkRegistry(b *testing.B) { r := NewRegistry() - r.Register("foo", NewCounter(nil)) + r.Register("foo", NewCounter()) b.ResetTimer() for i := 0; i < b.N; i++ { r.Each(func(string, interface{}) {}) @@ -18,7 +18,7 @@ func BenchmarkRegistry(b *testing.B) { func BenchmarkHugeRegistry(b *testing.B) { r := NewRegistry() for i := 0; i < 10000; i++ { - r.Register(fmt.Sprintf("foo%07d", i), NewCounter(nil)) + r.Register(fmt.Sprintf("foo%07d", i), NewCounter()) } v := make([]string, 10000) b.ResetTimer() @@ -35,14 +35,14 @@ func BenchmarkRegistryParallel(b *testing.B) { b.ResetTimer() b.RunParallel(func(pb *testing.PB) { for pb.Next() { - r.GetOrRegister("foo", NewCounter(nil)) + r.GetOrRegister("foo", NewCounter()) } }) } func TestRegistry(t *testing.T) { r := NewRegistry() - r.Register("foo", NewCounter(nil)) + r.Register("foo", NewCounter()) i := 0 r.Each(func(name string, iface interface{}) { i++ @@ -66,10 +66,10 @@ func TestRegistry(t *testing.T) { func TestRegistryDuplicate(t *testing.T) { r := NewRegistry() - if err := r.Register("foo", NewCounter(nil)); nil != err { + if err := r.Register("foo", NewCounter()); nil != err { t.Fatal(err) } - if err := r.Register("foo", NewGauge(nil)); nil == err { + if err := r.Register("foo", NewGauge()); nil == err { t.Fatal(err) } i := 0 @@ -86,7 +86,7 @@ func TestRegistryDuplicate(t *testing.T) { func TestRegistryGet(t *testing.T) { r := NewRegistry() - r.Register("foo", NewCounter(nil)) + r.Register("foo", NewCounter()) if count := r.Get("foo").(Counter).Count(); count != 0 { t.Fatal(count) } @@ -100,8 +100,8 @@ func TestRegistryGetOrRegister(t *testing.T) { r := NewRegistry() // First metric wins with GetOrRegister - _ = r.GetOrRegister("foo", NewCounter(nil)) - m := r.GetOrRegister("foo", NewGauge(nil)) + _ = r.GetOrRegister("foo", NewCounter()) + m := r.GetOrRegister("foo", NewGauge()) if _, ok := m.(Counter); !ok { t.Fatal(m) } @@ -125,8 +125,8 @@ func TestRegistryGetOrRegisterWithLazyInstantiation(t *testing.T) { r := NewRegistry() // First metric wins with GetOrRegister - _ = r.GetOrRegister("foo", func() Counter { return NewCounter(nil) }) - m := r.GetOrRegister("foo", func() Gauge { return NewGauge(nil) }) + _ = r.GetOrRegister("foo", func() Counter { return NewCounter() }) + m := r.GetOrRegister("foo", func() Gauge { return NewGauge() }) if _, ok := m.(Counter); !ok { t.Fatal(m) } @@ -149,9 +149,9 @@ func TestRegistryGetOrRegisterWithLazyInstantiation(t *testing.T) { func TestRegistryUnregister(t *testing.T) { r := NewRegistry() - r.Register("foo", NewCounter(nil)) - r.Register("bar", NewMeter(nil)) - r.Register("baz", NewTimer(nil)) + r.Register("foo", NewCounter()) + r.Register("bar", NewMeter()) + r.Register("baz", NewTimer()) count := 0 counter := func(name string, i interface{}) { count++ @@ -175,7 +175,7 @@ func TestPrefixedChildRegistryGetOrRegister(t *testing.T) { r := NewRegistry() pr := NewPrefixedChildRegistry(r, "prefix.") - _ = pr.GetOrRegister("foo", NewCounter(nil)) + _ = pr.GetOrRegister("foo", NewCounter()) i := 0 r.Each(func(name string, m interface{}) { @@ -192,7 +192,7 @@ func TestPrefixedChildRegistryGetOrRegister(t *testing.T) { func TestPrefixedRegistryGetOrRegister(t *testing.T) { r := NewPrefixedRegistry("prefix.") - _ = r.GetOrRegister("foo", NewCounter(nil)) + _ = r.GetOrRegister("foo", NewCounter()) i := 0 r.Each(func(name string, m interface{}) { @@ -208,8 +208,8 @@ func TestPrefixedRegistryGetOrRegister(t *testing.T) { func TestPrefixedRegistryRegister(t *testing.T) { r := NewPrefixedRegistry("prefix.") - err := r.Register("foo", NewCounter(nil)) - c := NewCounter(nil) + err := r.Register("foo", NewCounter()) + c := NewCounter() Register("bar", c) if err != nil { t.Fatal(err.Error()) @@ -230,7 +230,7 @@ func TestPrefixedRegistryRegister(t *testing.T) { func TestPrefixedRegistryUnregister(t *testing.T) { r := NewPrefixedRegistry("prefix.") - _ = r.Register("foo", NewCounter(nil)) + _ = r.Register("foo", NewCounter()) i := 0 r.Each(func(name string, m interface{}) { @@ -258,7 +258,7 @@ func TestPrefixedRegistryUnregister(t *testing.T) { func TestPrefixedRegistryGet(t *testing.T) { pr := NewPrefixedRegistry("prefix.") name := "foo" - pr.Register(name, NewCounter(nil)) + pr.Register(name, NewCounter()) fooCounter := pr.Get(name) if fooCounter == nil { @@ -270,7 +270,7 @@ func TestPrefixedChildRegistryGet(t *testing.T) { r := NewRegistry() pr := NewPrefixedChildRegistry(r, "prefix.") name := "foo" - pr.Register(name, NewCounter(nil)) + pr.Register(name, NewCounter()) fooCounter := pr.Get(name) if fooCounter == nil { t.Fatal(name) @@ -279,8 +279,8 @@ func TestPrefixedChildRegistryGet(t *testing.T) { func TestChildPrefixedRegistryRegister(t *testing.T) { r := NewPrefixedChildRegistry(DefaultRegistry, "prefix.") - err := r.Register("foo", NewCounter(nil)) - c := NewCounter(nil) + err := r.Register("foo", NewCounter()) + c := NewCounter() Register("bar", c) if err != nil { t.Fatal(err.Error()) @@ -301,15 +301,15 @@ func TestChildPrefixedRegistryRegister(t *testing.T) { func TestChildPrefixedRegistryOfChildRegister(t *testing.T) { r := NewPrefixedChildRegistry(NewRegistry(), "prefix.") r2 := NewPrefixedChildRegistry(r, "prefix2.") - err := r.Register("foo2", NewCounter(nil)) + err := r.Register("foo2", NewCounter()) if err != nil { t.Fatal(err.Error()) } - err = r2.Register("baz", NewCounter(nil)) + err = r2.Register("baz", NewCounter()) if err != nil { t.Fatal(err.Error()) } - c := NewCounter(nil) + c := NewCounter() Register("bars", c) i := 0 @@ -327,15 +327,15 @@ func TestChildPrefixedRegistryOfChildRegister(t *testing.T) { func TestWalkRegistries(t *testing.T) { r := NewPrefixedChildRegistry(NewRegistry(), "prefix.") r2 := NewPrefixedChildRegistry(r, "prefix2.") - err := r.Register("foo2", NewCounter(nil)) + err := r.Register("foo2", NewCounter()) if err != nil { t.Fatal(err.Error()) } - err = r2.Register("baz", NewCounter(nil)) + err = r2.Register("baz", NewCounter()) if err != nil { t.Fatal(err.Error()) } - c := NewCounter(nil) + c := NewCounter() Register("bars", c) _, prefix := findPrefix(r2, "") @@ -347,7 +347,7 @@ func TestWalkRegistries(t *testing.T) { func TestConcurrentRegistryAccess(t *testing.T) { r := NewRegistry() - counter := NewCounter(nil) + counter := NewCounter() signalChan := make(chan struct{}) @@ -404,6 +404,6 @@ func TestRegisterAndRegisteredConcurrency(t *testing.T) { r.Each(func(name string, iface interface{}) { }) }(r, wg) - r.Register("foo", NewCounter(nil)) + r.Register("foo", NewCounter()) wg.Wait() } diff --git a/runtime.go b/runtime.go index cb32483..eb64276 100644 --- a/runtime.go +++ b/runtime.go @@ -152,37 +152,37 @@ func RegisterRuntimeMemStats(r Registry) { r = DefaultRegistry } registerRuntimeMetricsOnce.Do(func() { - runtimeMetrics.MemStats.Alloc = NewGauge(nil) - runtimeMetrics.MemStats.BuckHashSys = NewGauge(nil) - runtimeMetrics.MemStats.DebugGC = NewGauge(nil) - runtimeMetrics.MemStats.EnableGC = NewGauge(nil) - runtimeMetrics.MemStats.Frees = NewGauge(nil) - runtimeMetrics.MemStats.HeapAlloc = NewGauge(nil) - runtimeMetrics.MemStats.HeapIdle = NewGauge(nil) - runtimeMetrics.MemStats.HeapInuse = NewGauge(nil) - runtimeMetrics.MemStats.HeapObjects = NewGauge(nil) - runtimeMetrics.MemStats.HeapReleased = NewGauge(nil) - runtimeMetrics.MemStats.HeapSys = NewGauge(nil) - runtimeMetrics.MemStats.LastGC = NewGauge(nil) - runtimeMetrics.MemStats.Lookups = NewGauge(nil) - runtimeMetrics.MemStats.Mallocs = NewGauge(nil) - runtimeMetrics.MemStats.MCacheInuse = NewGauge(nil) - runtimeMetrics.MemStats.MCacheSys = NewGauge(nil) - runtimeMetrics.MemStats.MSpanInuse = NewGauge(nil) - runtimeMetrics.MemStats.MSpanSys = NewGauge(nil) - runtimeMetrics.MemStats.NextGC = NewGauge(nil) - runtimeMetrics.MemStats.NumGC = NewGauge(nil) - runtimeMetrics.MemStats.GCCPUFraction = NewGaugeFloat64(nil) - runtimeMetrics.MemStats.PauseNs = NewHistogram(NewExpDecaySample(1028, 0.015), nil) - runtimeMetrics.MemStats.PauseTotalNs = NewGauge(nil) - runtimeMetrics.MemStats.StackInuse = NewGauge(nil) - runtimeMetrics.MemStats.StackSys = NewGauge(nil) - runtimeMetrics.MemStats.Sys = NewGauge(nil) - runtimeMetrics.MemStats.TotalAlloc = NewGauge(nil) - runtimeMetrics.NumCgoCall = NewGauge(nil) - runtimeMetrics.NumGoroutine = NewGauge(nil) - runtimeMetrics.NumThread = NewGauge(nil) - runtimeMetrics.ReadMemStats = NewTimer(nil) + runtimeMetrics.MemStats.Alloc = NewGauge() + runtimeMetrics.MemStats.BuckHashSys = NewGauge() + runtimeMetrics.MemStats.DebugGC = NewGauge() + runtimeMetrics.MemStats.EnableGC = NewGauge() + runtimeMetrics.MemStats.Frees = NewGauge() + runtimeMetrics.MemStats.HeapAlloc = NewGauge() + runtimeMetrics.MemStats.HeapIdle = NewGauge() + runtimeMetrics.MemStats.HeapInuse = NewGauge() + runtimeMetrics.MemStats.HeapObjects = NewGauge() + runtimeMetrics.MemStats.HeapReleased = NewGauge() + runtimeMetrics.MemStats.HeapSys = NewGauge() + runtimeMetrics.MemStats.LastGC = NewGauge() + runtimeMetrics.MemStats.Lookups = NewGauge() + runtimeMetrics.MemStats.Mallocs = NewGauge() + runtimeMetrics.MemStats.MCacheInuse = NewGauge() + runtimeMetrics.MemStats.MCacheSys = NewGauge() + runtimeMetrics.MemStats.MSpanInuse = NewGauge() + runtimeMetrics.MemStats.MSpanSys = NewGauge() + runtimeMetrics.MemStats.NextGC = NewGauge() + runtimeMetrics.MemStats.NumGC = NewGauge() + runtimeMetrics.MemStats.GCCPUFraction = NewGaugeFloat64() + runtimeMetrics.MemStats.PauseNs = NewHistogram(NewExpDecaySample(1028, 0.015)) + runtimeMetrics.MemStats.PauseTotalNs = NewGauge() + runtimeMetrics.MemStats.StackInuse = NewGauge() + runtimeMetrics.MemStats.StackSys = NewGauge() + runtimeMetrics.MemStats.Sys = NewGauge() + runtimeMetrics.MemStats.TotalAlloc = NewGauge() + runtimeMetrics.NumCgoCall = NewGauge() + runtimeMetrics.NumGoroutine = NewGauge() + runtimeMetrics.NumThread = NewGauge() + runtimeMetrics.ReadMemStats = NewTimer() r.Register("runtime.MemStats.Alloc", runtimeMetrics.MemStats.Alloc) r.Register("runtime.MemStats.BuckHashSys", runtimeMetrics.MemStats.BuckHashSys) diff --git a/statsd/statsd_test.go b/statsd/statsd_test.go index a0b6177..6586065 100644 --- a/statsd/statsd_test.go +++ b/statsd/statsd_test.go @@ -72,8 +72,8 @@ func TestWrites(t *testing.T) { res, ln, c, wg := newTestServer(t, &ctx) defer ln.Close() - metrics.GetOrRegisterCounter("foo", nil, nil).Inc(2) - metrics.GetOrRegisterMeter("bar", nil, nil).Mark(1) + metrics.GetOrRegisterCounter("foo", nil).Inc(2) + metrics.GetOrRegisterMeter("bar", nil).Mark(1) ctx.Store(false) wg.Add(1) diff --git a/timer.go b/timer.go index 731d49f..534ac9d 100644 --- a/timer.go +++ b/timer.go @@ -24,40 +24,35 @@ type Timer interface { Update(time.Duration) UpdateSince(time.Time) Variance() float64 - Labels() Labels - WithLabels(Labels) Timer } // GetOrRegisterTimer returns an existing Timer or constructs and registers a // new StandardTimer. // Be sure to unregister the meter from the registry once it is of no use to // allow for garbage collection. -func GetOrRegisterTimer(name string, r Registry, labels Labels) Timer { - if nil == r { +func GetOrRegisterTimer(name string, r Registry) Timer { + if r == nil { r = DefaultRegistry } - return r.GetOrRegister(name, func() Timer { - return NewTimer(labels) - }).(Timer) + return r.GetOrRegister(name, NewTimer).(Timer) } // NewCustomTimer constructs a new StandardTimer from a Histogram and a Meter. -func NewCustomTimer(h Histogram, m Meter, labels Labels) Timer { +func NewCustomTimer(h Histogram, m Meter) Timer { if UseNilMetrics { return NilTimer{} } return &StandardTimer{ histogram: h, meter: m, - labels: deepCopyLabels(labels), } } // NewRegisteredTimer constructs and registers a new StandardTimer. // Be sure to unregister the meter from the registry once it is of no use to // allow for garbage collection. -func NewRegisteredTimer(name string, r Registry, labels Labels) Timer { - c := NewTimer(labels) +func NewRegisteredTimer(name string, r Registry) Timer { + c := NewTimer() if nil == r { r = DefaultRegistry } @@ -67,14 +62,13 @@ func NewRegisteredTimer(name string, r Registry, labels Labels) Timer { // NewTimer constructs a new StandardTimer using an exponentially-decaying // sample with the same reservoir size and alpha as UNIX load averages. -func NewTimer(labels Labels) Timer { +func NewTimer() Timer { if UseNilMetrics { return NilTimer{} } return &StandardTimer{ - histogram: NewHistogram(NewExpDecaySample(1028, 0.015), nil), - meter: NewMeter(nil), - labels: deepCopyLabels(labels), + histogram: NewHistogram(NewExpDecaySample(1028, 0.015)), + meter: NewMeter(), } } @@ -134,19 +128,12 @@ func (NilTimer) UpdateSince(time.Time) {} // Variance is a no-op. func (NilTimer) Variance() float64 { return 0.0 } -// Labels is a no-op. -func (NilTimer) Labels() Labels { return Labels{} } - -// WithLabels is a no-op. -func (NilTimer) WithLabels(Labels) Timer { return NilTimer{} } - // StandardTimer is the standard implementation of a Timer and uses a Histogram // and Meter. type StandardTimer struct { histogram Histogram meter Meter mutex sync.Mutex - labels Labels } // Count returns the number of events recorded. @@ -207,7 +194,6 @@ func (t *StandardTimer) Snapshot() Timer { return &TimerSnapshot{ histogram: t.histogram.Snapshot().(*HistogramSnapshot), meter: t.meter.Snapshot().(*MeterSnapshot), - labels: t.Labels(), } } @@ -250,22 +236,10 @@ func (t *StandardTimer) Variance() float64 { return t.histogram.Variance() } -// Labels returns a deep copy of the timer's labels. -func (t *StandardTimer) Labels() Labels { - return deepCopyLabels(t.labels) -} - -// WithLabels returns a snapshot of the Timer with the given labels added to the -// current list of labels. -func (t *StandardTimer) WithLabels(labels Labels) Timer { - return t.Snapshot().WithLabels(labels) -} - // TimerSnapshot is a read-only copy of another Timer. type TimerSnapshot struct { histogram *HistogramSnapshot meter *MeterSnapshot - labels Labels } // Count returns the number of events recorded at the time the snapshot was @@ -337,20 +311,3 @@ func (*TimerSnapshot) UpdateSince(time.Time) { // Variance returns the variance of the values at the time the snapshot was // taken. func (t *TimerSnapshot) Variance() float64 { return t.histogram.Variance() } - -// Labels returns a deep copy of the snapshot's labels. -func (t *TimerSnapshot) Labels() Labels { return deepCopyLabels(t.labels) } - -// WithLabels returns a copy of the snapshot with the given labels added to the -// current list of labels. -func (t *TimerSnapshot) WithLabels(labels Labels) Timer { - newLabels := t.labels - for k, v := range labels { - newLabels[k] = v - } - return &TimerSnapshot{ - histogram: t.histogram, - meter: t.meter, - labels: newLabels, - } -} diff --git a/timer_test.go b/timer_test.go index e192e75..a3b9600 100644 --- a/timer_test.go +++ b/timer_test.go @@ -8,7 +8,7 @@ import ( ) func BenchmarkTimer(b *testing.B) { - tm := NewTimer(nil) + tm := NewTimer() b.ResetTimer() for i := 0; i < b.N; i++ { tm.Update(1) @@ -17,14 +17,14 @@ func BenchmarkTimer(b *testing.B) { func TestGetOrRegisterTimer(t *testing.T) { r := NewRegistry() - NewRegisteredTimer("foo", r, nil).Update(47) - if tm := GetOrRegisterTimer("foo", r, nil); tm.Count() != 1 { + NewRegisteredTimer("foo", r).Update(47) + if tm := GetOrRegisterTimer("foo", r); tm.Count() != 1 { t.Fatal(tm) } } func TestTimerExtremes(t *testing.T) { - tm := NewTimer(nil) + tm := NewTimer() tm.Update(math.MaxInt64) tm.Update(0) if stdDev := tm.StdDev(); stdDev != 4.611686018427388e+18 { @@ -33,7 +33,7 @@ func TestTimerExtremes(t *testing.T) { } func TestTimerFunc(t *testing.T) { - tm := NewTimer(nil) + tm := NewTimer() tm.Time(func() { time.Sleep(50e6) }) if max := tm.Max(); 45e6 > max || max > 55e6 { t.Errorf("tm.Max(): 45e6 > %v || %v > 55e6\n", max, max) @@ -41,7 +41,7 @@ func TestTimerFunc(t *testing.T) { } func TestTimerZero(t *testing.T) { - tm := NewTimer(nil) + tm := NewTimer() if count := tm.Count(); count != 0 { t.Errorf("tm.Count(): 0 != %v\n", count) } @@ -81,49 +81,9 @@ func TestTimerZero(t *testing.T) { } } -func TestTimerLabels(t *testing.T) { - labels := Labels{"key1": "value1"} - c := NewTimer(labels) - if len(c.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(c.Labels())) - } - if lbls := c.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } - - // Labels passed by value. - labels["key1"] = "value2" - if lbls := c.Labels()["key1"]; lbls != "value1" { - t.Error("Labels(): labels passed by reference") - } - - // Labels in snapshot. - ss := c.Snapshot() - if len(ss.Labels()) != 1 { - t.Fatalf("Labels(): %v != 1", len(c.Labels())) - } - if lbls := ss.Labels()["key1"]; lbls != "value1" { - t.Errorf("Labels(): %v != value1", lbls) - } -} - -func TestTimerWithLabels(t *testing.T) { - c := NewTimer(Labels{"foo": "bar"}) - new := c.WithLabels(Labels{"bar": "foo"}) - if len(new.Labels()) != 2 { - t.Fatalf("WithLabels() len: %v != 2", len(new.Labels())) - } - if lbls := new.Labels()["foo"]; lbls != "bar" { - t.Errorf("WithLabels(): %v != bar", lbls) - } - if lbls := new.Labels()["bar"]; lbls != "foo" { - t.Errorf("WithLabels(): %v != foo", lbls) - } -} - func ExampleGetOrRegisterTimer() { m := "account.create.latency" - t := GetOrRegisterTimer(m, nil, nil) + t := GetOrRegisterTimer(m, nil) t.Update(47) fmt.Println(t.Max()) // Output: 47 }