OpenTelemetry Test Utilities
The `opentelemetry-test-utils` library provides common utilities and base classes designed to simplify unit testing of OpenTelemetry Python components. This includes helpers for capturing and asserting telemetry data (traces, metrics, logs) within a test environment. It is part of the larger OpenTelemetry Python project, currently at version 0.62b0, with new beta releases typically accompanying major `opentelemetry-python` releases.
Warnings
- gotcha The `opentelemetry-test-utils` library often has a `0.x.x.bY` versioning scheme (e.g., 0.62b0) that is distinct from the main `opentelemetry-python` package's `1.x.x` version. Ensure you are installing the correct beta version that aligns with your `opentelemetry-sdk` version, as APIs can change rapidly in beta releases.
- gotcha This library is primarily intended for internal testing of OpenTelemetry components or custom instrumentations. For simpler application-level testing of whether spans are being generated, it might be sufficient to use `InMemorySpanExporter` directly from `opentelemetry.sdk.trace.export` without `opentelemetry-test-utils`, which might offer a more stable API.
- breaking In `opentelemetry-python` v1.40.0 (corresponding to `opentelemetry-test-utils` 0.61b0), the behavior of `start_span` and `start_as_current_span` in `NoOpTracer` was fixed to propagate span contexts even without an SDK installed. Tests that relied on `NoOpTracer` *always* returning an `INVALID_SPAN` regardless of context might be affected.
- deprecated As of `opentelemetry-python` v1.40.0 (corresponding to `opentelemetry-test-utils` 0.61b0), `opentelemetry-sdk`'s `LoggingHandler` has been deprecated. Any test setups that rely on directly configuring `LoggingHandler` should migrate.
Install
-
pip install opentelemetry-test-utils -
pip install opentelemetry-test-utils==0.62b0
Imports
- OTELTestBase
from opentelemetry.test_utils import OTELTestBase
- get_finished_spans
from opentelemetry.sdk.testing.helpers import get_finished_spans
Quickstart
import unittest
from opentelemetry import trace
from opentelemetry.sdk.resources import Resource
from opentelemetry.sdk.trace import TracerProvider
from opentelemetry.sdk.trace.export import SimpleSpanProcessor, InMemorySpanExporter
from opentelemetry.test_utils import OTELTestBase
class MyInstrumentationTest(OTELTestBase):
def setUp(self):
super().setUp()
# Configure a tracer provider with an in-memory exporter for testing
self.exporter = InMemorySpanExporter()
self.span_processor = SimpleSpanProcessor(self.exporter)
self.tracer_provider = TracerProvider(resource=Resource.create({"service.name": "test-service"}))
self.tracer_provider.add_span_processor(self.span_processor)
trace.set_tracer_provider(self.tracer_provider)
self.tracer = trace.get_tracer(__name__)
def tearDown(self):
trace.set_tracer_provider(TracerProvider()) # Reset to default NoOpTracerProvider
self.span_processor.shutdown()
super().tearDown()
def test_basic_span_creation(self):
with self.tracer.start_as_current_span("test-span") as span:
span.set_attribute("key", "value")
span.add_event("my-event")
# Assert that one span was exported
spans = self.exporter.get_finished_spans()
self.assertEqual(len(spans), 1)
# Assert properties of the exported span
exported_span = spans[0]
self.assertEqual(exported_span.name, "test-span")
self.assertEqual(exported_span.attributes["key"], "value")
self.assertEqual(len(exported_span.events), 1)
self.assertEqual(exported_span.events[0].name, "my-event")
if __name__ == '__main__':
unittest.main()