Node.js OpenTelemetry 监控实战:指标采集与导出完整教程

用 OpenTelemetry 为 Node.js 应用建立指标监控:自动 HTTP 指标、Counter/UpDownCounter/Gauge/Histogram 四种仪器用法、指标命名规范,以及通过 OTLP 导出到观测云实现看板与告警。附 Express 完整代码示例。

最佳实践
Node.js OpenTelemetry 监控实战:指标采集与导出完整教程封面

Node.js 的 OpenTelemetry 指标接入以 @opentelemetry/sdk-metrics 为核心,配合自动埋点包即可获得 HTTP 层指标,再用四种仪器补充业务指标——JS 生态的自动埋点覆盖 Express、Fastify、Koa 等主流框架,接入成本极低。

核心要点速览

  • 自动埋点包一行注册,HTTP 请求数、耗时自动产出;
  • 业务指标四种仪器:Counter 计数、UpDownCounter 水位、Gauge 瞬时、Histogram 分布;
  • 指标经 OTLP 周期性导出(默认 60s);
  • 导出后先验证指标名、单位与实例标签,再建立图表和告警。

初始化指标 SDK

const { MeterProvider, PeriodicExportingMetricReader } = require('@opentelemetry/sdk-metrics');
const { OTLPMetricExporter } = require('@opentelemetry/exporter-metrics-otlp-http');
const { Resource } = require('@opentelemetry/resources');

const exporter = new OTLPMetricExporter({
  url: 'http://datakit-host:4318/v1/metrics',
});
const meterProvider = new MeterProvider({
  resource: new Resource({ 'service.name': 'web-frontend' }),
  readers: [new PeriodicExportingMetricReader({ exporter, exportIntervalMillis: 30000 })],
});
const meter = meterProvider.getMeter('web-frontend');

注意 NodeSDK(@opentelemetry/sdk-node)可以一行同时初始化链路+指标,新项目推荐直接使用。

自动 HTTP 指标

const { NodeSDK } = require('@opentelemetry/sdk-node');
const { getNodeAutoInstrumentations } = require('@opentelemetry/auto-instrumentations-node');

const sdk = new NodeSDK({
  metricReader: new PeriodicExportingMetricReader({ exporter }),
  instrumentations: [getNodeAutoInstrumentations()],
});
sdk.start();

Express 的每个路由自动产生请求计数与耗时分布指标,路由参数自动低基数化(/user/:id 而非 /user/12345)。

四种业务指标写法

// Counter:注册总数
const signups = meter.createCounter('user.signups.total');
signups.add(1, { plan: 'pro' });

// UpDownCounter:当前活跃会话
const sessions = meter.createUpDownCounter('sessions.active');
sessions.add(1);            // 登录
sessions.add(-1);           // 登出

// Gauge:当前配置版本之类的瞬时值
const queueDepth = meter.createGauge('jobs.queue.depth');
// 或用 Observable Gauge 回调采集:observableQueue.observe(result => ...)

// Histogram:任务处理耗时分布
const jobDuration = meter.createHistogram('jobs.duration', { unit: 's' });
jobDuration.record(elapsedSeconds, { job_type: 'email' });

命名纪律:点分小写、带单位、属性只放聚合维度(套餐、任务类型),用户 ID 这类高基数值永远不进指标——留给链路与日志。

Node.js 特有的注意点

  • 异步上下文:Promise 链、async/await 由 AsyncLocalStorage 自动跟踪,但事件发射器(EventEmitter)跨边界时需检查上下文是否延续;
  • 进程退出:process.on('SIGTERM', () => sdk.shutdown()) 必须加,否则最后一波指标丢失;
  • 单进程多实例:PM2 集群模式下每个进程独立上报,后端按实例标签区分,聚合时留意。

验证指标导出

使用观测云作为后端时,先启用 DataKit 的 OpenTelemetry 采集器,按实际监听地址配置 exporter;HTTP 指标接收路径通常为 /otel/v1/metrics,不要把 Collector 的默认 4318 端口直接当作 DataKit 默认值。触发一次已知业务操作,检查 Counter 增量和 Histogram 的单位,再按服务与实例建立查询和告警。

常见问题(FAQ)

Q:自动埋点和我手写的指标会冲突吗? 不会,自动指标走框架层,手写指标走业务层,名称空间不同;但注意别对同一件事重复计数。

Q:exportIntervalMillis 设多少? 默认 60s,业务监控够用;告警敏感场景可降到 15-30s,再低收益递减。

Q:可以只导出指标不导出链路吗? 可以,分别配置 reader 与 tracer provider,互不影响。

Q:TypeScript 项目有额外配置吗? 类型定义齐全,直接 import 即可;自动埋点需在应用代码之前加载(--require ./tracing.js 启动参数)。

系列阅读

获取专属方案

联系我们

加入社区

微信扫码
加入官方交流群

立即体验

在线开通,按量计费,真正的云服务!

立即开始

选择观测云版本

代码托管平台