count.go 1.5 KB
Newer Older
Y
Your Name 已提交
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82
package graphite

import (
	"strconv"
	"sync"
	"time"

	"github.com/eolinker/goku-api-gateway/diting"
	"github.com/marpaia/graphite-golang"
)

//Count count
type Count struct {
	metricKey          MetricKey
	metricsValuesCount *MetricsValuesCount
}

//Add add
func (c *Count) Add(value float64, labels diting.Labels) {

	key := c.metricKey.Key(labels, "count")
	c.metricsValuesCount.Add(key, value)
}

//Metrics metrics
func (c *Count) Metrics() []graphite.Metric {
	values := c.metricsValuesCount.Collapse()
	if len(values) == 0 {
		return nil
	}
	ms := make([]graphite.Metric, 0, len(values))
	t := time.Now().Unix()

	for k, v := range values {
		ms = append(ms, graphite.NewMetric(k, strconv.FormatInt(v, 10), t))
	}

	return ms

}

//NewCounter new counter
func NewCounter(metricKey MetricKey) *Count {
	return &Count{
		metricKey:          metricKey,
		metricsValuesCount: NewMetricsValuesCount(),
	}
}

//MetricsValuesCount metricsValuesCount
type MetricsValuesCount struct {
	values map[string]int64
	locker sync.Mutex
}

//NewMetricsValuesCount new metricsValuesCount
func NewMetricsValuesCount() *MetricsValuesCount {
	return &MetricsValuesCount{
		values: make(map[string]int64),
		locker: sync.Mutex{},
	}
}

//Add add
func (m *MetricsValuesCount) Add(key string, value float64) {
	m.locker.Lock()
	v := int64(value)
	m.values[key] += v
	m.locker.Unlock()
}

//Collapse collapse
func (m *MetricsValuesCount) Collapse() map[string]int64 {
	n := make(map[string]int64)

	m.locker.Lock()
	v := m.values
	m.values = n
	m.locker.Unlock()

	return v
}