Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

### Added

- `opentelemetry-instrumentation-aio-pika`: Add test to verify tracer uses correct `_instrumentation_name`
([#4178](https://github.com/open-telemetry/opentelemetry-python-contrib/pull/4178))
- `opentelemetry-instrumentation-asgi`: Add exemplars for `http.server.request.duration` and `http.server.duration` metrics
([#3739](https://github.com/open-telemetry/opentelemetry-python-contrib/pull/3739))
- `opentelemetry-instrumentation-wsgi`: Add exemplars for `http.server.request.duration` and `http.server.duration` metrics
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,10 @@
from opentelemetry.instrumentation.aio_pika.callback_decorator import (
CallbackDecorator,
)
from opentelemetry.instrumentation.aio_pika.package import _instruments
from opentelemetry.instrumentation.aio_pika.package import (
_instrumentation_name,
_instruments,
)
from opentelemetry.instrumentation.aio_pika.publish_decorator import (
PublishDecorator,
)
Expand All @@ -30,8 +33,6 @@
from opentelemetry.instrumentation.utils import unwrap
from opentelemetry.trace import Tracer

_INSTRUMENTATION_MODULE_NAME = "opentelemetry.instrumentation.aio_pika"


class AioPikaInstrumentor(BaseInstrumentor):
@staticmethod
Expand Down Expand Up @@ -64,7 +65,7 @@ async def wrapper(wrapped, instance, args, kwargs):
def _instrument(self, **kwargs):
tracer_provider = kwargs.get("tracer_provider", None)
tracer = trace.get_tracer(
_INSTRUMENTATION_MODULE_NAME,
_instrumentation_name,
__version__,
tracer_provider,
schema_url="https://opentelemetry.io/schemas/1.11.0",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
from typing import Collection
from typing import Collection, Final

_instruments: Collection[str] = ("aio_pika >= 7.2.0, < 10.0.0",)

_instrumentation_name: Final[str] = "opentelemetry.instrumentation.aio_pika"
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
CORRELATION_ID = "correlation_id"
MESSAGING_SYSTEM_VALUE = "rabbitmq"
EXCHANGE_NAME = "exchange_name"
INSTRUMENTATION_NAME = "opentelemetry.instrumentation.aio_pika"
QUEUE_NAME = "queue_name"
ROUTING_KEY = "routing_key"
SERVER_HOST = "localhost"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,12 +11,25 @@
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
from unittest import TestCase
import asyncio
from unittest import TestCase, mock

import wrapt
from aio_pika import Exchange, Queue

from opentelemetry.instrumentation.aio_pika import AioPikaInstrumentor
from opentelemetry.test.test_base import TestBase

from .consts import (
AIOPIKA_VERSION_INFO,
CHANNEL_7,
CHANNEL_8,
CONNECTION_7,
EXCHANGE_NAME,
INSTRUMENTATION_NAME,
MESSAGE,
ROUTING_KEY,
)


class TestPika(TestCase):
Expand All @@ -32,3 +45,48 @@ def test_instrument_api(self) -> None:
self.assertFalse(
isinstance(Exchange.publish, wrapt.BoundFunctionWrapper)
)


class TestInstrumentationScopeName(TestBase):
"""Test instrumentation scope via actual span output (not mocking internals)."""

def setUp(self):
super().setUp()
self.loop = asyncio.new_event_loop()
asyncio.set_event_loop(self.loop)

def tearDown(self):
with self.disable_logging():
AioPikaInstrumentor().uninstrument()
self.loop.close()
super().tearDown()

def test_instrumentation_scope_name(self):
"""Verify instrumentation scope via the real instrument() path."""

async def _noop_publish(self, *args, **kwargs):
return None

with mock.patch.object(Exchange, "publish", new=_noop_publish):
AioPikaInstrumentor().instrument(
tracer_provider=self.tracer_provider
)
major = AIOPIKA_VERSION_INFO[0]
if major == 7:
exchange = Exchange(CONNECTION_7, CHANNEL_7, EXCHANGE_NAME)
elif major in (8, 9):
exchange = Exchange(CHANNEL_8, EXCHANGE_NAME)
else:
self.fail(
f"Unsupported aio-pika major version {major} (supported: 7-9, <10)"
)
self.loop.run_until_complete(
exchange.publish(MESSAGE, ROUTING_KEY)
)

spans = self.memory_exporter.get_finished_spans()
self.assertEqual(len(spans), 1)
self.assertEqual(
spans[0].instrumentation_scope.name,
INSTRUMENTATION_NAME,
)