如何使用OpenTelemetry Java API获取当前计数器值?
获取OpenTelemetry Java Counter当前值的方案
方案一:本地同步维护计数器值
由于你完全控制Counter的增减调用,最直接的方式是在调用OpenTelemetry Counter的add方法时,同步更新一个线程安全的本地变量(比如AtomicLong),直接读取这个变量就能拿到当前值。
示例代码:
import io.opentelemetry.api.metrics.Counter; import io.opentelemetry.api.metrics.Meter; import io.opentelemetry.api.OpenTelemetry; import java.util.concurrent.atomic.AtomicLong; public class CustomCounter { private final Counter<Long> otelCounter; private final AtomicLong localCounter = new AtomicLong(0); public CustomCounter(OpenTelemetry openTelemetry) { Meter meter = openTelemetry.meterBuilder("your.meter.name").build(); otelCounter = meter.counterBuilder("your.counter.name") .setDescription("Custom counter") .setUnit("1") .build(); } public void increment(long value) { otelCounter.add(value); localCounter.addAndGet(value); } public long getCurrentValue() { return localCounter.get(); } }
方案二:使用内存导出器(InMemoryMetricExporter)读取指标
OpenTelemetry Java SDK提供了InMemoryMetricExporter,可以将指标数据保存在内存中,无需发送到外部后端,你可以通过MetricReader手动或定期获取聚合后的指标值。
步骤1:添加依赖(Maven)
<dependency> <groupId>io.opentelemetry</groupId> <artifactId>opentelemetry-sdk-metrics</artifactId> <version>your-otel-version</version> </dependency> <dependency> <groupId>io.opentelemetry</groupId> <artifactId>opentelemetry-exporter-metrics-inmemory</artifactId> <version>your-otel-version</version> </dependency>
步骤2:配置并读取Counter值
import io.opentelemetry.api.OpenTelemetry; import io.opentelemetry.api.metrics.Counter; import io.opentelemetry.api.metrics.Meter; import io.opentelemetry.exporter.metrics.inmemory.InMemoryMetricExporter; import io.opentelemetry.sdk.metrics.SdkMeterProvider; import io.opentelemetry.sdk.metrics.export.MetricReader; import io.opentelemetry.sdk.metrics.export.PeriodicMetricReader; import java.util.concurrent.TimeUnit; public class OtelCounterReader { private final Counter<Long> otelCounter; private final InMemoryMetricExporter exporter; private final MetricReader reader; public OtelCounterReader() { exporter = InMemoryMetricExporter.create(); reader = PeriodicMetricReader.builder(exporter) .setInterval(1, TimeUnit.SECONDS) // 定期收集,也可替换为手动读取的ManualMetricReader .build(); SdkMeterProvider meterProvider = SdkMeterProvider.builder() .registerMetricReader(reader) .build(); OpenTelemetry openTelemetry = OpenTelemetry.builder() .setMeterProvider(meterProvider) .build(); Meter meter = openTelemetry.meterBuilder("your.meter.name").build(); otelCounter = meter.counterBuilder("your.counter.name") .setDescription("Counter for testing") .setUnit("1") .build(); } public void increment(long value) { otelCounter.add(value); } public long getCurrentCounterValue() { // 手动触发一次收集(若用PeriodicMetricReader也可等待自动收集) reader.collectAllMetrics().join(); return exporter.getFinishedMetricItems().stream() .filter(item -> item.getName().equals("your.counter.name")) .findFirst() .map(item -> item.getSumData().getPoints().get(0).getValue().longValue()) .orElse(0L); } }
注意事项
- Counter的聚合类型为
Sum,需从SumData中提取数值; - 若需要完全手动控制收集时机,可使用
ManualMetricReader替代PeriodicMetricReader,主动调用collect方法触发指标聚合。
内容的提问来源于stack exchange,提问作者Vasu. Tk
相关产品推荐
相关产品推荐

