Skip to content

Add OpenTelemetry metrics monitor (faust[opentelemetry])#746

Open
wbarnha wants to merge 2 commits into
masterfrom
claude/new-session-abcs0g
Open

Add OpenTelemetry metrics monitor (faust[opentelemetry])#746
wbarnha wants to merge 2 commits into
masterfrom
claude/new-session-abcs0g

Conversation

@wbarnha

@wbarnha wbarnha commented Jul 22, 2026

Copy link
Copy Markdown
Member

Description

Adds OpenTelemetryMonitor, a sensor that reports the same metric set as the built-in Statsd and Datadog monitors, but through the OpenTelemetry metrics API — so Faust metrics can be exported to any OpenTelemetry-compatible backend (OTLP, Prometheus, the console, ...).

This is the metrics counterpart to the OpenTelemetry tracing discussions in #688 / #689, and is intentionally standalone: it depends on neither of those PRs.

How it works

  • Faust depends only on opentelemetry-api, via the new optional faust[opentelemetry] extra. Every instrument is a cheap no-op until your application configures a global MeterProvider with the exporter of its choice — the library never picks an SDK or exporter for you.
  • Following OpenTelemetry conventions, each instrument is dimensioned by attributes (topic, partition, stream, table, status_code, ...) rather than baking those into the metric name the way Statsd does (read_offset.{topic}.{partition}).
  • Modeled on the existing DatadogMonitor (same Monitor hooks, same metric coverage), so it stays consistent with the other backends and calls super() first to preserve the in-memory Monitor stats.

Usage:

from opentelemetry import metrics
from opentelemetry.sdk.metrics import MeterProvider
from opentelemetry.sdk.metrics.export import (
    ConsoleMetricExporter, PeriodicExportingMetricReader,
)
from faust.sensors.otel import OpenTelemetryMonitor

reader = PeriodicExportingMetricReader(ConsoleMetricExporter())
metrics.set_meter_provider(MeterProvider(metric_readers=[reader]))

app = faust.App('example', broker='kafka://localhost:9092')
app.monitor = OpenTelemetryMonitor()

Instruments

  • Counters: faust.messages.received, faust.events.total, faust.messages.sent, faust.messages.send_errors, faust.table.operations, faust.assignments, faust.http.requests, faust.custom.count.
  • UpDownCounters (in-flight work): faust.messages.active, faust.events.active, faust.rebalances.active, faust.rebalances.recovering.
  • Histograms (unit ms): faust.events.runtime, faust.commit.latency, faust.send.latency, faust.send.error_latency, faust.assignment.latency, faust.rebalance.return_latency, faust.rebalance.end_latency, faust.http.latency.
  • Gauges (last-known value per topic/partition): faust.offset.read, faust.offset.committed, faust.offset.end, faust.producer.buffer.

Changes

  • faust/sensors/otel.pyOTelMetrics instrument container + OpenTelemetryMonitor.
  • requirements/extras/opentelemetry.txt (opentelemetry-api/-sdk >=1.23.0, for the synchronous Gauge), the opentelemetry bundle in setup.py, and the extra added to requirements/test.txt.
  • tests/unit/sensors/test_otel.py — 17 tests driving the Monitor hooks against an in-memory SDK metric reader (counter/up-down/histogram/gauge points + attributes), plus the no-OpenTelemetry ImproperlyConfigured path.
  • Docs — user-guide section in docs/userguide/sensors.rst, a bundle entry in docs/includes/installation.txt, and a reference autodoc page.

Verification

  • pytest tests/unit/sensors/ — 156 passed (17 new), the full sensors suite green.
  • black / isort / flake8 (repo pins) clean on the new files.

🤖 Generated with Claude Code


Generated by Claude Code

Add OpenTelemetryMonitor, a sensor that reports the same metric set as the
Statsd and Datadog monitors through the OpenTelemetry metrics API, so Faust
metrics can be exported to any OpenTelemetry-compatible backend (OTLP,
Prometheus, console, ...).

Faust depends only on opentelemetry-api via the new optional
faust[opentelemetry] extra; every instrument is a cheap no-op until the
application configures a global MeterProvider. Following OpenTelemetry
conventions, each instrument is dimensioned by attributes (topic, partition,
stream, table, ...) rather than baking those into the metric name as Statsd
does.

- faust/sensors/otel.py: OTelMetrics instrument container + OpenTelemetryMonitor.
- requirements/extras/opentelemetry.txt + setup.py bundle + test requirements.
- tests/unit/sensors/test_otel.py: 17 tests driving the hooks against an
  in-memory SDK metric reader.
- docs: user-guide section, installation bundle entry, reference autodoc page.

Assisted-by: Claude Opus 4.8

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01LJ1voGxC8Nqs3AUPKnFVzZ
@codecov

codecov Bot commented Jul 22, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 96.06%. Comparing base (706b502) to head (20e563e).

Additional details and impacted files
@@            Coverage Diff             @@
##           master     #746      +/-   ##
==========================================
+ Coverage   95.98%   96.06%   +0.07%     
==========================================
  Files         103      104       +1     
  Lines       11069    11249     +180     
  Branches     1191     1202      +11     
==========================================
+ Hits        10625    10806     +181     
+ Misses        350      349       -1     
  Partials       94       94              

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

Adds a test that passes a pre-built OTelMetrics container via the
`metrics=` kwarg, covering the last uncovered line/branch in
OpenTelemetryMonitor.metrics (patch coverage 98.9% -> 100%).

Assisted-by: Claude Opus 4.8

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01LJ1voGxC8Nqs3AUPKnFVzZ
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants