OtelMetrics
OpenTelemetry support for Effect metrics.
This module exposes Effect metrics as an OpenTelemetry MetricProducer.
makeProducer creates the producer, registerProducer attaches it to one
or more SDK MetricReaders, and layer manages that setup in a scoped
layer. The TemporalityPreference type lets callers choose cumulative or
delta metric values.
Constructors
makeProducer
Creates an OpenTelemetry metric producer from Effect metrics.
When to use
Use when you need a MetricProducer for manually wiring Effect metrics into
OpenTelemetry instead of using the scoped layer helper.
Details
Requires the current OpenTelemetry Resource, captures the current Effect
context, and uses cumulative temporality by default. Pass "delta" for
interval-based values.
See
- registerProducer for attaching a producer to metric readers
- layer for creating and registering a producer in a scoped layer
Signature
declare function makeProducer(temporality?: TemporalityPreference): Effect<MetricProducer, never, Resource>Layers
Creates a Layer that registers a metric producer with metric readers.
Signature
declare function layer(evaluate: LazyArg<any>, options?: { readonly shutdownTimeout?: Input; readonly temporality?: TemporalityPreference;}): Layer<never, never, Resource>Example
(Exporting delta metrics)
import { OtelMetrics, Resource } from "@effect/opentelemetry"import { AggregationTemporality, InMemoryMetricExporter, PeriodicExportingMetricReader} from "@opentelemetry/sdk-metrics"import { Effect, Layer, Metric } from "effect"
const exporter = new InMemoryMetricExporter(AggregationTemporality.DELTA)const reader = new PeriodicExportingMetricReader({ exporter, exportIntervalMillis: 60_000})const metricsLayer = OtelMetrics.layer(() => reader, { temporality: "delta" }).pipe( Layer.provide(Resource.layerEmpty))
const program = Effect.gen(function*() { yield* Metric.update(Metric.counter("docs.requests", { incremental: true }), 2) yield* Effect.promise(() => reader.forceFlush())
const metric = exporter.getMetrics()[0]?.scopeMetrics[0]?.metrics.find( (metric) => metric.descriptor.name === "docs.requests" ) return [metric?.descriptor.name, metric?.aggregationTemporality, metric?.dataPoints[0]?.value] as const}).pipe( Effect.provide(metricsLayer), Effect.provideService(Metric.MetricRegistry, new Map()))
await Effect.runPromise(program) // => ["docs.requests", AggregationTemporality.DELTA, 2]Models
TemporalityPreference type
Determines how metric values relate to the time interval over which they are aggregated.
Details
cumulative reports total since a fixed start time. Each data point depends
on all previous measurements. This is the default behavior. delta reports
changes since the last export. Each interval is independent with no
dependency on previous measurements.
Signature
type TemporalityPreference = "cumulative" | "delta"Resource Management
registerProducer
Registers a metric producer with one or more metric readers.
Signature
declare function registerProducer(self: MetricProducer, metricReader: LazyArg<any>, options?: { readonly shutdownTimeout?: Input;}): Effect<Array<any>, never, Scope>