metrics.go 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186
  1. package stats
  2. import (
  3. "fmt"
  4. "log"
  5. "net/http"
  6. "os"
  7. "strings"
  8. "time"
  9. "github.com/prometheus/client_golang/prometheus"
  10. "github.com/prometheus/client_golang/prometheus/promhttp"
  11. "github.com/prometheus/client_golang/prometheus/push"
  12. "github.com/chrislusf/seaweedfs/weed/glog"
  13. )
  14. var (
  15. Gather = prometheus.NewRegistry()
  16. FilerRequestCounter = prometheus.NewCounterVec(
  17. prometheus.CounterOpts{
  18. Namespace: "SeaweedFS",
  19. Subsystem: "filer",
  20. Name: "request_total",
  21. Help: "Counter of filer requests.",
  22. }, []string{"type"})
  23. FilerRequestHistogram = prometheus.NewHistogramVec(
  24. prometheus.HistogramOpts{
  25. Namespace: "SeaweedFS",
  26. Subsystem: "filer",
  27. Name: "request_seconds",
  28. Help: "Bucketed histogram of filer request processing time.",
  29. Buckets: prometheus.ExponentialBuckets(0.0001, 2, 24),
  30. }, []string{"type"})
  31. FilerStoreCounter = prometheus.NewCounterVec(
  32. prometheus.CounterOpts{
  33. Namespace: "SeaweedFS",
  34. Subsystem: "filerStore",
  35. Name: "request_total",
  36. Help: "Counter of filer store requests.",
  37. }, []string{"store", "type"})
  38. FilerStoreHistogram = prometheus.NewHistogramVec(
  39. prometheus.HistogramOpts{
  40. Namespace: "SeaweedFS",
  41. Subsystem: "filerStore",
  42. Name: "request_seconds",
  43. Help: "Bucketed histogram of filer store request processing time.",
  44. Buckets: prometheus.ExponentialBuckets(0.0001, 2, 24),
  45. }, []string{"store", "type"})
  46. VolumeServerRequestCounter = prometheus.NewCounterVec(
  47. prometheus.CounterOpts{
  48. Namespace: "SeaweedFS",
  49. Subsystem: "volumeServer",
  50. Name: "request_total",
  51. Help: "Counter of volume server requests.",
  52. }, []string{"type"})
  53. VolumeServerRequestHistogram = prometheus.NewHistogramVec(
  54. prometheus.HistogramOpts{
  55. Namespace: "SeaweedFS",
  56. Subsystem: "volumeServer",
  57. Name: "request_seconds",
  58. Help: "Bucketed histogram of volume server request processing time.",
  59. Buckets: prometheus.ExponentialBuckets(0.0001, 2, 24),
  60. }, []string{"type"})
  61. VolumeServerVolumeCounter = prometheus.NewGaugeVec(
  62. prometheus.GaugeOpts{
  63. Namespace: "SeaweedFS",
  64. Subsystem: "volumeServer",
  65. Name: "volumes",
  66. Help: "Number of volumes or shards.",
  67. }, []string{"collection", "type"})
  68. VolumeServerReadOnlyVolumeGauge = prometheus.NewGaugeVec(
  69. prometheus.GaugeOpts{
  70. Namespace: "SeaweedFS",
  71. Subsystem: "volumeServer",
  72. Name: "read_only_volumes",
  73. Help: "Number of read only volumes.",
  74. }, []string{"collection", "type"})
  75. VolumeServerMaxVolumeCounter = prometheus.NewGauge(
  76. prometheus.GaugeOpts{
  77. Namespace: "SeaweedFS",
  78. Subsystem: "volumeServer",
  79. Name: "max_volumes",
  80. Help: "Maximum number of volumes.",
  81. })
  82. VolumeServerDiskSizeGauge = prometheus.NewGaugeVec(
  83. prometheus.GaugeOpts{
  84. Namespace: "SeaweedFS",
  85. Subsystem: "volumeServer",
  86. Name: "total_disk_size",
  87. Help: "Actual disk size used by volumes.",
  88. }, []string{"collection", "type"})
  89. VolumeServerResourceGauge = prometheus.NewGaugeVec(
  90. prometheus.GaugeOpts{
  91. Namespace: "SeaweedFS",
  92. Subsystem: "volumeServer",
  93. Name: "resource",
  94. Help: "Resource usage",
  95. }, []string{"name", "type"})
  96. S3RequestCounter = prometheus.NewCounterVec(
  97. prometheus.CounterOpts{
  98. Namespace: "SeaweedFS",
  99. Subsystem: "s3",
  100. Name: "request_total",
  101. Help: "Counter of s3 requests.",
  102. }, []string{"type", "code"})
  103. S3RequestHistogram = prometheus.NewHistogramVec(
  104. prometheus.HistogramOpts{
  105. Namespace: "SeaweedFS",
  106. Subsystem: "s3",
  107. Name: "request_seconds",
  108. Help: "Bucketed histogram of s3 request processing time.",
  109. Buckets: prometheus.ExponentialBuckets(0.0001, 2, 24),
  110. }, []string{"type"})
  111. )
  112. func init() {
  113. Gather.MustRegister(FilerRequestCounter)
  114. Gather.MustRegister(FilerRequestHistogram)
  115. Gather.MustRegister(FilerStoreCounter)
  116. Gather.MustRegister(FilerStoreHistogram)
  117. Gather.MustRegister(prometheus.NewGoCollector())
  118. Gather.MustRegister(VolumeServerRequestCounter)
  119. Gather.MustRegister(VolumeServerRequestHistogram)
  120. Gather.MustRegister(VolumeServerVolumeCounter)
  121. Gather.MustRegister(VolumeServerMaxVolumeCounter)
  122. Gather.MustRegister(VolumeServerReadOnlyVolumeGauge)
  123. Gather.MustRegister(VolumeServerDiskSizeGauge)
  124. Gather.MustRegister(VolumeServerResourceGauge)
  125. Gather.MustRegister(S3RequestCounter)
  126. Gather.MustRegister(S3RequestHistogram)
  127. }
  128. func LoopPushingMetric(name, instance, addr string, intervalSeconds int) {
  129. if addr == "" || intervalSeconds == 0 {
  130. return
  131. }
  132. glog.V(0).Infof("%s server sends metrics to %s every %d seconds", name, addr, intervalSeconds)
  133. pusher := push.New(addr, name).Gatherer(Gather).Grouping("instance", instance)
  134. for {
  135. err := pusher.Push()
  136. if err != nil && !strings.HasPrefix(err.Error(), "unexpected status code 200") {
  137. glog.V(0).Infof("could not push metrics to prometheus push gateway %s: %v", addr, err)
  138. }
  139. if intervalSeconds <= 0 {
  140. intervalSeconds = 15
  141. }
  142. time.Sleep(time.Duration(intervalSeconds) * time.Second)
  143. }
  144. }
  145. func StartMetricsServer(port int) {
  146. if port == 0 {
  147. return
  148. }
  149. http.Handle("/metrics", promhttp.HandlerFor(Gather, promhttp.HandlerOpts{}))
  150. log.Fatal(http.ListenAndServe(fmt.Sprintf(":%d", port), nil))
  151. }
  152. func SourceName(port uint32) string {
  153. hostname, err := os.Hostname()
  154. if err != nil {
  155. return "unknown"
  156. }
  157. return fmt.Sprintf("%s:%d", hostname, port)
  158. }