package metrics import ( "net/http" "github.com/prometheus/client_golang/prometheus" "github.com/prometheus/client_golang/prometheus/promhttp" ) // Registry 持有 NixMsg 指标与独立注册表(避免污染默认全局注册表)。 type Registry struct { reg *prometheus.Registry Connections *prometheus.GaugeVec EndpointsTotal prometheus.Gauge DeliveriesPending prometheus.Gauge MessagesScheduled prometheus.Gauge DispatchToPushSeconds prometheus.Observer AckSeconds prometheus.Observer WriteQueueLength prometheus.Gauge WriteCommitSeconds prometheus.Observer PasswordHashQueue prometheus.Gauge ErrorsTotal *prometheus.CounterVec } // New 按 DEVELOPMENT 4.3 注册指标。 func New() *Registry { reg := prometheus.NewRegistry() r := &Registry{reg: reg} r.Connections = prometheus.NewGaugeVec(prometheus.GaugeOpts{ Name: "nixmsg_connections", Help: "Current online connections by transport (ws or tcp).", }, []string{"transport"}) r.EndpointsTotal = prometheus.NewGauge(prometheus.GaugeOpts{ Name: "nixmsg_endpoints", Help: "Total number of endpoints.", }) r.DeliveriesPending = prometheus.NewGauge(prometheus.GaugeOpts{ Name: "nixmsg_deliveries_pending", Help: "Number of pending deliveries.", }) r.MessagesScheduled = prometheus.NewGauge(prometheus.GaugeOpts{ Name: "nixmsg_messages_scheduled", Help: "Number of scheduled messages not yet dispatched.", }) dispatchHist := prometheus.NewHistogram(prometheus.HistogramOpts{ Name: "nixmsg_dispatch_to_push_duration_seconds", Help: "Latency from message due time to push.", Buckets: prometheus.DefBuckets, }) r.DispatchToPushSeconds = dispatchHist ackHist := prometheus.NewHistogram(prometheus.HistogramOpts{ Name: "nixmsg_ack_duration_seconds", Help: "Latency from push to ack.", Buckets: prometheus.DefBuckets, }) r.AckSeconds = ackHist r.WriteQueueLength = prometheus.NewGauge(prometheus.GaugeOpts{ Name: "nixmsg_write_queue_length", Help: "Number of write operations waiting or in the current batch.", }) commitHist := prometheus.NewHistogram(prometheus.HistogramOpts{ Name: "nixmsg_write_batch_commit_duration_seconds", Help: "Duration of each merged write-queue commit.", Buckets: prometheus.DefBuckets, }) r.WriteCommitSeconds = commitHist r.PasswordHashQueue = prometheus.NewGauge(prometheus.GaugeOpts{ Name: "nixmsg_password_hash_queue_length", Help: "Number of password hash jobs waiting for a pool slot.", }) r.ErrorsTotal = prometheus.NewCounterVec(prometheus.CounterOpts{ Name: "nixmsg_errors_total", Help: "Count of application error codes.", }, []string{"code"}) reg.MustRegister( r.Connections, r.EndpointsTotal, r.DeliveriesPending, r.MessagesScheduled, dispatchHist, ackHist, r.WriteQueueLength, commitHist, r.PasswordHashQueue, r.ErrorsTotal, ) // 初始化 transport 标签,便于空载抓取也能看到序列。 r.Connections.WithLabelValues("ws").Set(0) r.Connections.WithLabelValues("tcp").Set(0) return r } // Handler 返回 Prometheus 文本格式的 /metrics 处理函数(访问规则由 A 线加)。 func (r *Registry) Handler() http.Handler { return promhttp.HandlerFor(r.reg, promhttp.HandlerOpts{}) } // Gatherer 暴露底层 Gatherer(测试用)。 func (r *Registry) Gatherer() prometheus.Gatherer { return r.reg }