为了账号安全,请及时绑定邮箱和手机立即绑定

Prometheus计数器:如何使用golang客户端获取当前值?

Prometheus计数器:如何使用golang客户端获取当前值?

Go
qq_笑_17 2023-07-26 13:17:03
我正在使用计数器来计算请求数。有没有办法获取普罗米修斯计数器的当前值?我的目标是重用现有计数器而不分配另一个变量。Golang prometheus客户端版本为1.1.0。
查看完整描述

4 回答

?
桃花长相依

TA贡献1860条经验 获得超8个赞

很简单,有一个获取 Prometheus 计数器值的函数



import (

    "github.com/prometheus/client_golang/prometheus"

    dto "github.com/prometheus/client_model/go"

    "github.com/prometheus/common/log"

)


func GetCounterValue(metric *prometheus.CounterVec) float64 {

    var m = &dto.Metric{}

    if err := metric.WithLabelValues("label1", "label2").Write(m); err != nil {

        log.Error(err)

        return 0

    }

    return m.Counter.GetValue()

}


查看完整回答
反对 回复 2023-07-26
?
慕无忌1623718

TA贡献1744条经验 获得超4个赞

目前 Golang 官方实现中还没有办法获取计数器的值。

您还可以通过增加自己的计数器并使用CounterFunc来收集它来避免重复计数。

注意:使用整型并atomic避免并发访问问题

// declare the counter as unsigned int

var requestsCounter uint64 = 0


// register counter in Prometheus collector

prometheus.MustRegister(prometheus.NewCounterFunc(

    prometheus.CounterOpts{

        Name: "requests_total",

        Help: "Counts number of requests",

    },

    func() float64 {

        return float64(atomic.LoadUint64(&requestsCounter))

    }))


// somewhere in your code

atomic.AddUint64(&requestsCounter, 1)


查看完整回答
反对 回复 2023-07-26
?
慕后森

TA贡献1802条经验 获得超5个赞

可以在官方 Golang 实现中读取计数器(或任何指标)的值。我不确定它是什么时候添加的。


这对我来说适用于没有向量的简单度量:


func getMetricValue(col prometheus.Collector) float64 {

    c := make(chan prometheus.Metric, 1) // 1 for metric with no vector

    col.Collect(c)      // collect current metric value into the channel

    m := dto.Metric{}

    _ = (<-c).Write(&m) // read metric value from the channel

    return *m.Counter.Value

}

更新:这是一个更通用的版本,适用于向量和直方图......


// GetMetricValue returns the sum of the Counter metrics associated with the Collector

// e.g. the metric for a non-vector, or the sum of the metrics for vector labels.

// If the metric is a Histogram then number of samples is used.

func GetMetricValue(col prometheus.Collector) float64 {

    var total float64

    collect(col, func(m dto.Metric) {

        if h := m.GetHistogram(); h != nil {

                total += float64(h.GetSampleCount())

        } else {

                total += m.GetCounter().GetValue()

        }

    })

    return total

}


// collect calls the function for each metric associated with the Collector

func collect(col prometheus.Collector, do func(dto.Metric)) {

    c := make(chan prometheus.Metric)

    go func(c chan prometheus.Metric) {

        col.Collect(c)

        close(c)

    }(c)

    for x := range c { // eg range across distinct label vector values

            m := dto.Metric{}

            _ = x.Write(&m)

            do(m)

    }

}


查看完整回答
反对 回复 2023-07-26
?
拉丁的传说

TA贡献1789条经验 获得超8个赞

import (

  "github.com/VictoriaMetrics/metrics"

)


var requestsTotal = metrics.NewCounter(`http_requests_total`)

//...


func getRequestsTotal() uint64 {

  return requestsTotal.Get()

}

例如,只需在所需的计数器上调用Get()函数即可。


查看完整回答
反对 回复 2023-07-26
  • 4 回答
  • 0 关注
  • 260 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信