Ver código fonte

Graphite: Enable configuring conversion units

Tomás Senart 12 anos atrás
pai
commit
d7ab897500
2 arquivos alterados com 86 adições e 37 exclusões
  1. 64 37
      graphite.go
  2. 22 0
      graphite_test.go

+ 64 - 37
graphite.go

@@ -8,63 +8,90 @@ import (
 	"time"
 )
 
+// GraphiteConfig provides a container with configuration parameters for
+// the Graphite exporter
+type GraphiteConfig struct {
+	Addr          *net.TCPAddr  // Network address to connect to
+	Registry      Registry      // Registry to be exported
+	FlushInterval time.Duration // Flush interval
+	DurationUnit  time.Duration // Time conversion unit for durations
+	RateUnit      time.Duration // Time conversion unit for rates
+	Prefix        string        // Prefix to be prepended to metric names
+}
+
+// Graphite is a blocking exporter function which reports metrics in r
+// to a graphite server located at addr, flushing them every d duration
+// and prepending metric names with prefix.
 func Graphite(r Registry, d time.Duration, prefix string, addr *net.TCPAddr) {
-	for {
-		if err := graphite(r, prefix, addr); nil != err {
+	GraphiteWithConfig(GraphiteConfig{
+		Addr:          addr,
+		Registry:      r,
+		FlushInterval: d,
+		DurationUnit:  time.Nanosecond,
+		RateUnit:      time.Nanosecond,
+		Prefix:        prefix,
+	})
+}
+
+// GraphiteWithConfig is a blocking exporter function just like Graphite,
+// but it takes a GraphiteConfig instead.
+func GraphiteWithConfig(c GraphiteConfig) {
+	for _ = range time.Tick(c.FlushInterval) {
+		if err := graphite(&c); nil != err {
 			log.Println(err)
 		}
-		time.Sleep(d)
 	}
 }
 
-func graphite(r Registry, prefix string, addr *net.TCPAddr) error {
+func graphite(c *GraphiteConfig) error {
 	now := time.Now().Unix()
-	conn, err := net.DialTCP("tcp", nil, addr)
+	du, ru := float64(c.DurationUnit), float64(c.RateUnit)
+	conn, err := net.DialTCP("tcp", nil, c.Addr)
 	if nil != err {
 		return err
 	}
 	defer conn.Close()
 	w := bufio.NewWriter(conn)
-	r.Each(func(name string, i interface{}) {
+	c.Registry.Each(func(name string, i interface{}) {
 		switch m := i.(type) {
 		case Counter:
-			fmt.Fprintf(w, "%s.%s.count %d %d\n", prefix, name, m.Count(), now)
+			fmt.Fprintf(w, "%s.%s.count %d %d\n", c.Prefix, name, m.Count(), now)
 		case Gauge:
-			fmt.Fprintf(w, "%s.%s.value %d %d\n", prefix, name, m.Value(), now)
+			fmt.Fprintf(w, "%s.%s.value %d %d\n", c.Prefix, name, m.Value(), now)
 		case Histogram:
 			ps := m.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999})
-			fmt.Fprintf(w, "%s.%s.count %d %d\n", prefix, name, m.Count(), now)
-			fmt.Fprintf(w, "%s.%s.min %d %d\n", prefix, name, m.Min(), now)
-			fmt.Fprintf(w, "%s.%s.max %d %d\n", prefix, name, m.Max(), now)
-			fmt.Fprintf(w, "%s.%s.mean %.2f %d\n", prefix, name, m.Mean(), now)
-			fmt.Fprintf(w, "%s.%s.std-dev %.2f %d\n", prefix, name, m.StdDev(), now)
-			fmt.Fprintf(w, "%s.%s.50-percentile %.2f %d\n", prefix, name, ps[0], now)
-			fmt.Fprintf(w, "%s.%s.75-percentile %.2f %d\n", prefix, name, ps[1], now)
-			fmt.Fprintf(w, "%s.%s.95-percentile %.2f %d\n", prefix, name, ps[2], now)
-			fmt.Fprintf(w, "%s.%s.99-percentile %.2f %d\n", prefix, name, ps[3], now)
-			fmt.Fprintf(w, "%s.%s.999-percentile %.2f %d\n", prefix, name, ps[4], now)
+			fmt.Fprintf(w, "%s.%s.count %d %d\n", c.Prefix, name, m.Count(), now)
+			fmt.Fprintf(w, "%s.%s.min %d %d\n", c.Prefix, name, m.Min(), now)
+			fmt.Fprintf(w, "%s.%s.max %d %d\n", c.Prefix, name, m.Max(), now)
+			fmt.Fprintf(w, "%s.%s.mean %.2f %d\n", c.Prefix, name, m.Mean(), now)
+			fmt.Fprintf(w, "%s.%s.std-dev %.2f %d\n", c.Prefix, name, m.StdDev(), now)
+			fmt.Fprintf(w, "%s.%s.50-percentile %.2f %d\n", c.Prefix, name, ps[0], now)
+			fmt.Fprintf(w, "%s.%s.75-percentile %.2f %d\n", c.Prefix, name, ps[1], now)
+			fmt.Fprintf(w, "%s.%s.95-percentile %.2f %d\n", c.Prefix, name, ps[2], now)
+			fmt.Fprintf(w, "%s.%s.99-percentile %.2f %d\n", c.Prefix, name, ps[3], now)
+			fmt.Fprintf(w, "%s.%s.999-percentile %.2f %d\n", c.Prefix, name, ps[4], now)
 		case Meter:
-			fmt.Fprintf(w, "%s.%s.count %d %d\n", prefix, name, m.Count(), now)
-			fmt.Fprintf(w, "%s.%s.one-minute %.2f %d\n", prefix, name, m.Rate1(), now)
-			fmt.Fprintf(w, "%s.%s.five-minute %.2f %d\n", prefix, name, m.Rate5(), now)
-			fmt.Fprintf(w, "%s.%s.fifteen-minute %.2f %d\n", prefix, name, m.Rate15(), now)
-			fmt.Fprintf(w, "%s.%s.mean %.2f %d\n", prefix, name, m.RateMean(), now)
+			fmt.Fprintf(w, "%s.%s.count %d %d\n", c.Prefix, name, m.Count(), now)
+			fmt.Fprintf(w, "%s.%s.one-minute %.2f %d\n", c.Prefix, name, ru*m.Rate1(), now)
+			fmt.Fprintf(w, "%s.%s.five-minute %.2f %d\n", c.Prefix, name, ru*m.Rate5(), now)
+			fmt.Fprintf(w, "%s.%s.fifteen-minute %.2f %d\n", c.Prefix, name, ru*m.Rate15(), now)
+			fmt.Fprintf(w, "%s.%s.mean %.2f %d\n", c.Prefix, name, ru*m.RateMean(), now)
 		case Timer:
 			ps := m.Percentiles([]float64{0.5, 0.75, 0.95, 0.99, 0.999})
-			fmt.Fprintf(w, "%s.%s.count %d %d\n", prefix, name, m.Count(), now)
-			fmt.Fprintf(w, "%s.%s.min %d %d\n", prefix, name, m.Min(), now)
-			fmt.Fprintf(w, "%s.%s.max %d %d\n", prefix, name, m.Max(), now)
-			fmt.Fprintf(w, "%s.%s.mean %.2f %d\n", prefix, name, m.Mean(), now)
-			fmt.Fprintf(w, "%s.%s.std-dev %.2f %d\n", prefix, name, m.StdDev(), now)
-			fmt.Fprintf(w, "%s.%s.50-percentile %.2f %d\n", prefix, name, ps[0], now)
-			fmt.Fprintf(w, "%s.%s.75-percentile %.2f %d\n", prefix, name, ps[1], now)
-			fmt.Fprintf(w, "%s.%s.95-percentile %.2f %d\n", prefix, name, ps[2], now)
-			fmt.Fprintf(w, "%s.%s.99-percentile %.2f %d\n", prefix, name, ps[3], now)
-			fmt.Fprintf(w, "%s.%s.999-percentile %.2f %d\n", prefix, name, ps[4], now)
-			fmt.Fprintf(w, "%s.%s.one-minute %.2f %d\n", prefix, name, m.Rate1(), now)
-			fmt.Fprintf(w, "%s.%s.five-minute %.2f %d\n", prefix, name, m.Rate5(), now)
-			fmt.Fprintf(w, "%s.%s.fifteen-minute %.2f %d\n", prefix, name, m.Rate15(), now)
-			fmt.Fprintf(w, "%s.%s.mean-rate %.2f %d\n", prefix, name, m.RateMean(), now)
+			fmt.Fprintf(w, "%s.%s.count %d %d\n", c.Prefix, name, m.Count(), now)
+			fmt.Fprintf(w, "%s.%s.min %d %d\n", c.Prefix, name, int64(du)*m.Min(), now)
+			fmt.Fprintf(w, "%s.%s.max %d %d\n", c.Prefix, name, int64(du)*m.Max(), now)
+			fmt.Fprintf(w, "%s.%s.mean %.2f %d\n", c.Prefix, name, du*m.Mean(), now)
+			fmt.Fprintf(w, "%s.%s.std-dev %.2f %d\n", c.Prefix, name, du*m.StdDev(), now)
+			fmt.Fprintf(w, "%s.%s.50-percentile %.2f %d\n", c.Prefix, name, du*ps[0], now)
+			fmt.Fprintf(w, "%s.%s.75-percentile %.2f %d\n", c.Prefix, name, du*ps[1], now)
+			fmt.Fprintf(w, "%s.%s.95-percentile %.2f %d\n", c.Prefix, name, du*ps[2], now)
+			fmt.Fprintf(w, "%s.%s.99-percentile %.2f %d\n", c.Prefix, name, du*ps[3], now)
+			fmt.Fprintf(w, "%s.%s.999-percentile %.2f %d\n", c.Prefix, name, du*ps[4], now)
+			fmt.Fprintf(w, "%s.%s.one-minute %.2f %d\n", c.Prefix, name, ru*m.Rate1(), now)
+			fmt.Fprintf(w, "%s.%s.five-minute %.2f %d\n", c.Prefix, name, ru*m.Rate5(), now)
+			fmt.Fprintf(w, "%s.%s.fifteen-minute %.2f %d\n", c.Prefix, name, ru*m.Rate15(), now)
+			fmt.Fprintf(w, "%s.%s.mean-rate %.2f %d\n", c.Prefix, name, ru*m.RateMean(), now)
 		}
 		w.Flush()
 	})

+ 22 - 0
graphite_test.go

@@ -0,0 +1,22 @@
+package metrics
+
+import (
+	"net"
+	"time"
+)
+
+func ExampleGraphite() {
+	addr, _ := net.ResolveTCPAddr("net", ":2003")
+	go Graphite(DefaultRegistry, 1*time.Second, "some.prefix", addr)
+}
+
+func ExampleGraphiteWithConfig() {
+	addr, _ := net.ResolveTCPAddr("net", ":2003")
+	go GraphiteWithConfig(GraphiteConfig{
+		Addr:          addr,
+		Registry:      DefaultRegistry,
+		FlushInterval: 1 * time.Second,
+		DurationUnit:  time.Millisecond,
+		RateUnit:      time.Second,
+	})
+}