-
Notifications
You must be signed in to change notification settings - Fork 1k
opentelemetry-instrumentation-boto3sqs: migrate to current messaging semantic conventions #4920
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| `opentelemetry-instrumentation-boto3sqs`: migrate to current messaging semantic conventions |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -20,6 +20,7 @@ | |
|
|
||
| import logging | ||
| from typing import Any, Collection, Dict, Generator, List, Mapping, Optional | ||
| from urllib.parse import urlparse | ||
|
|
||
| import boto3.session | ||
| import botocore.client | ||
|
|
@@ -32,11 +33,20 @@ | |
| unwrap, | ||
| ) | ||
| from opentelemetry.propagators.textmap import CarrierT, Getter, Setter | ||
| from opentelemetry.semconv.trace import ( | ||
| MessagingDestinationKindValues, | ||
| MessagingOperationValues, | ||
| SpanAttributes, | ||
| from opentelemetry.semconv._incubating.attributes.messaging_attributes import ( | ||
| MESSAGING_DESTINATION_NAME, | ||
| MESSAGING_MESSAGE_ID, | ||
| MESSAGING_OPERATION_NAME, | ||
| MESSAGING_OPERATION_TYPE, | ||
| MESSAGING_SYSTEM, | ||
| MessagingOperationTypeValues, | ||
| MessagingSystemValues, | ||
| ) | ||
| from opentelemetry.semconv.attributes.server_attributes import ( | ||
| SERVER_ADDRESS, | ||
| SERVER_PORT, | ||
| ) | ||
| from opentelemetry.semconv.schemas import Schemas | ||
| from opentelemetry.trace import Link, Span, SpanKind, Tracer, TracerProvider | ||
|
|
||
| from .package import _instruments | ||
|
|
@@ -133,30 +143,27 @@ def _enrich_span( | |
| span: Span, | ||
| queue_name: str, | ||
| queue_url: str, | ||
| conversation_id: Optional[str] = None, | ||
| operation: Optional[MessagingOperationValues] = None, | ||
| operation_name: str, | ||
| operation_type: MessagingOperationTypeValues, | ||
| message_id: Optional[str] = None, | ||
| ) -> None: | ||
| if not span.is_recording(): | ||
| return | ||
| span.set_attribute(SpanAttributes.MESSAGING_SYSTEM, "aws.sqs") | ||
| span.set_attribute(SpanAttributes.MESSAGING_DESTINATION, queue_name) | ||
| span.set_attribute( | ||
| SpanAttributes.MESSAGING_DESTINATION_KIND, | ||
| MessagingDestinationKindValues.QUEUE.value, | ||
| MESSAGING_SYSTEM, MessagingSystemValues.AWS_SQS.value | ||
| ) | ||
| span.set_attribute(SpanAttributes.MESSAGING_URL, queue_url) | ||
| span.set_attribute(MESSAGING_DESTINATION_NAME, queue_name) | ||
| span.set_attribute(MESSAGING_OPERATION_NAME, operation_name) | ||
| span.set_attribute(MESSAGING_OPERATION_TYPE, operation_type.value) | ||
|
|
||
| parsed_url = urlparse(queue_url) | ||
| if parsed_url.hostname: | ||
| span.set_attribute(SERVER_ADDRESS, parsed_url.hostname) | ||
| if parsed_url.port: | ||
| span.set_attribute(SERVER_PORT, parsed_url.port) | ||
|
Comment on lines
+162
to
+163
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
When a custom AGENTS.md reference: AGENTS.md:L80-L82 Useful? React with 👍 / 👎.
Comment on lines
+162
to
+163
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
When a valid queue URL explicitly includes its scheme's default port, such as Useful? React with 👍 / 👎. |
||
|
|
||
| if operation: | ||
| span.set_attribute( | ||
| SpanAttributes.MESSAGING_OPERATION, operation.value | ||
| ) | ||
| if conversation_id: | ||
| span.set_attribute( | ||
| SpanAttributes.MESSAGING_CONVERSATION_ID, conversation_id | ||
| ) | ||
| if message_id: | ||
| span.set_attribute(SpanAttributes.MESSAGING_MESSAGE_ID, message_id) | ||
| span.set_attribute(MESSAGING_MESSAGE_ID, message_id) | ||
|
|
||
| @staticmethod | ||
| def _safe_end_processing_span(receipt_handle: str) -> None: | ||
|
|
@@ -202,8 +209,9 @@ def _create_processing_span( | |
| span, | ||
| queue_name, | ||
| queue_url, | ||
| "process", | ||
| MessagingOperationTypeValues.PROCESS, | ||
| message_id=message_id, | ||
| operation=MessagingOperationValues.PROCESS, | ||
| ) | ||
|
|
||
| def _wrap_send_message(self, sqs_class: type) -> None: | ||
|
|
@@ -221,16 +229,20 @@ def send_wrapper(wrapped, instance, args, kwargs): | |
| kind=SpanKind.PRODUCER, | ||
| end_on_exit=True, | ||
| ) as span: | ||
| Boto3SQSInstrumentor._enrich_span(span, queue_name, queue_url) | ||
| Boto3SQSInstrumentor._enrich_span( | ||
| span, | ||
| queue_name, | ||
| queue_url, | ||
| "send", | ||
| MessagingOperationTypeValues.PUBLISH, | ||
| ) | ||
| attributes = kwargs.pop("MessageAttributes", {}) | ||
| propagate.inject(attributes, setter=boto3sqs_setter) | ||
| retval = wrapped(*args, MessageAttributes=attributes, **kwargs) | ||
| message_id = retval.get("MessageId") | ||
| if message_id: | ||
| if span.is_recording(): | ||
| span.set_attribute( | ||
| SpanAttributes.MESSAGING_MESSAGE_ID, message_id | ||
| ) | ||
| span.set_attribute(MESSAGING_MESSAGE_ID, message_id) | ||
| return retval | ||
|
|
||
| wrap_function_wrapper(sqs_class, "send_message", send_wrapper) | ||
|
|
@@ -258,7 +270,11 @@ def send_batch_wrapper(wrapped, instance, args, kwargs): | |
| ) | ||
| ids_to_spans[entry_id] = span | ||
| Boto3SQSInstrumentor._enrich_span( | ||
| span, queue_name, queue_url, conversation_id=entry_id | ||
| span, | ||
| queue_name, | ||
| queue_url, | ||
| "send", | ||
| MessagingOperationTypeValues.PUBLISH, | ||
| ) | ||
| with trace.use_span(span): | ||
| if "MessageAttributes" not in entry: | ||
|
|
@@ -273,7 +289,7 @@ def send_batch_wrapper(wrapped, instance, args, kwargs): | |
| if message_span: | ||
| if message_span.is_recording(): | ||
| message_span.set_attribute( | ||
| SpanAttributes.MESSAGING_MESSAGE_ID, | ||
| MESSAGING_MESSAGE_ID, | ||
| successful_messages.get("MessageId"), | ||
| ) | ||
| for span in ids_to_spans.values(): | ||
|
|
@@ -303,7 +319,8 @@ def receive_message_wrapper(wrapped, instance, args, kwargs): | |
| span, | ||
| queue_name, | ||
| queue_url, | ||
| operation=MessagingOperationValues.RECEIVE, | ||
| "receive", | ||
| MessagingOperationTypeValues.RECEIVE, | ||
| ) | ||
| retval = wrapped( | ||
| *args, | ||
|
|
@@ -415,7 +432,7 @@ def _instrument(self, **kwargs: Dict[str, Any]) -> None: | |
| __name__, | ||
| __version__, | ||
| self._tracer_provider, | ||
| schema_url="https://opentelemetry.io/schemas/1.11.0", | ||
| schema_url=Schemas.V1_27_0.value, | ||
| ) | ||
| self._wrap_client_creation() | ||
|
|
||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Removing
queue_urlfrom_enrich_spandrops the previous endpoint information without replacing it with the current convention'sserver.address(andserver.portfor non-default ports), even though every instrumented call already supplies the queue URL. As a result, spans for AWS endpoints and especially LocalStack/custom endpoints can no longer identify the server that handled the operation, and the declared v1.27 messaging telemetry is incomplete; retain and parse the URL using the generated server attribute constants.AGENTS.md reference: AGENTS.md:L84-L87
Useful? React with 👍 / 👎.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good catch — added
server.address(andserver.portwhen the URL carries an explicit port, e.g. LocalStack) parsed from the queue URL in_enrich_span, replacing the endpoint info the oldmessaging.urlattribute provided. Covered by the updated default-attrs assertions plus a new custom-endpoint test. 5804e8c