prom-client使用

本文介绍了如何在Node.js项目中使用prom-client库来创建和上报各种类型的监控指标(Counter、Histogram、Gauge和Summary),包括数据收集、处理和通过Pushgateway向平台发送。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

prom-client

metric.ts

import {
  Counter,
  Histogram,
  Gauge,
  Summary,
  Pushgateway,
  Registry,
} from 'prom-client';

type MetricData = {
  name: string;
  labels: Record<string, string>;
  labelNames: string[];
  type: string;
  help: string;
  value?: number;
  buckets?: number[];
  percentiles?: number[];
};

export enum MetricType {
  CounterType = 'counter',
  HistogramType = 'histogram',
  GaugeType = 'gauge',
  SummaryType = 'summary',
}

const register = new Registry();

// 上报到平台
export async function pushGateway() {
  try {
    const gateway = new Pushgateway(
      'https://xxx',
      [],
      register
    );

    const { resp, body } = await gateway.push({ jobName: 'pipeline test' });
    console.log(
      `push gateway successfully, status code is ${
        (resp as any).statusCode
      }, body is ${body}`
    );
  } catch (err) {
    console.log('push gateway failed:', err);
  }
}

// 创建指标类别
function createCounter(metricData: MetricData) {
  const { name, help, labelNames } = metricData;
  let counter = register.getSingleMetric(name) as Counter<string>;
  if (!counter) {
    counter = new Counter({
      name,
      help,
      labelNames,
      registers: [register],
    });
  }
  return counter;
}

function createHistogram(metricData: MetricData) {
  const { name, help, labelNames, buckets } = metricData;
  let histogram = register.getSingleMetric(name) as Histogram<string>;
  if (!histogram) {
    histogram = new Histogram({
      name,
      help,
      labelNames,
      buckets,
      registers: [register],
    });
  }
  return histogram;
}

function createSummary(metricData: MetricData) {
  const { name, help, labelNames, percentiles } = metricData;
  let summary = register.getSingleMetric(name) as Summary<string>;
  if (!summary) {
    summary = new Summary({
      name,
      help,
      labelNames,
      percentiles,
      registers: [register],
    });
  }
  return summary;
}

function createGauge(metricData: MetricData) {
  const { name, help, labelNames } = metricData;
  let gauge = register.getSingleMetric(name) as Gauge<string>;
  if (!gauge) {
    gauge = new Gauge({
      name,
      help,
      labelNames,
      registers: [register],
    });
  }
  return gauge;
}

export function handleMetric(metricData: MetricData) {
  const { type: metricType, value, labels } = metricData;
  const newValue = value || 1;
  if (metricType === MetricType.CounterType) {
    const counter = createCounter(metricData);
    register.registerMetric(counter);
    counter.inc(labels, newValue);
  } else if (metricType === MetricType.HistogramType) {
    const histogram = createHistogram(metricData);
    register.registerMetric(histogram);
    histogram.observe(labels, newValue);
  } else if (metricType === MetricType.SummaryType) {
    const summary = createSummary(metricData);
    register.registerMetric(summary);
    summary.observe(labels, newValue);
  } else if (metricType === MetricType.GaugeType) {
    const gauge = createGauge(metricData);
    register.registerMetric(gauge);
    gauge.set(labels, newValue);
  }
}

使用:

async function collectMetrics(name: string) {
  try {
     // 先获取指标原始数据
     // 比如需要掉接口拉取
     // await getList()...
      const labels = {
        labels: {
          name,
          env
        },
        labelNames: [
          'name',
          'env',
        ],
      };

      const counterMetric = {
        name: 'pipeline_run_total',
        help: 'pipeline run total',
        type: MetricType.CounterType,
        ...labels,
      };
      const histogramMetric = {
        name: 'pipeline_run_duration',
        help: 'pipeline run finished',
        value: duration,
        buckets: [
          30000, 60000, 75000, 90000, 105000, 120000, 135000, 150000, 165000,
          180000, 195000, 210000, 225000, 240000, 270000, 300000, 330000,
          360000,
        ],
        type: MetricType.HistogramType,
        ...labels,
      };

      // 处理指标
      [counterMetric, histogramMetric].forEach((metric) =>
        handleMetric(metric)
      );
    }
  } catch (err) {
    // err
  }
}

(async () => {
  // collect metrics
  const testNames=['test1','test2']
  await Promise.all(testNames.map((name) => collectMetrics(name)));
  // export to metric store
  await pushGateway();
})()
  .catch((e) => console.log(e.message || e))
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值