def _trace_before_publish(self, *args, **kwargs): task = utils.retrieve_task_from_sender(kwargs) task_id = utils.retrieve_task_id_from_message(kwargs) if task is None or task_id is None: return operation_name = f"{_TASK_APPLY_ASYNC}/{task.name}" span = self._tracer.start_span( operation_name, kind=trace.SpanKind.PRODUCER ) # apply some attributes here because most of the data is not available if span.is_recording(): span.set_attribute(_TASK_TAG_KEY, _TASK_APPLY_ASYNC) span.set_attribute(SpanAttributes.MESSAGING_MESSAGE_ID, task_id) span.set_attribute(_TASK_NAME_KEY, task.name) utils.set_attributes_from_context(span, kwargs) activation = trace.use_span(span, end_on_exit=True) activation.__enter__() # pylint: disable=E1101 utils.attach_span(task, task_id, (span, activation), is_publish=True) headers = kwargs.get("headers") if headers: inject(headers)
def test_set_attributes_not_recording(self): # it should extract only relevant keys context = { "correlation_id": "44b7f305", "delivery_info": { "eager": True }, "eta": "soon", "expires": "later", "hostname": "localhost", "id": "44b7f305", "reply_to": "44b7f305", "retries": 4, "timelimit": ("now", "later"), "custom_meta": "custom_value", "routing_key": "celery", } mock_span = mock.Mock() mock_span.is_recording.return_value = False utils.set_attributes_from_context(mock_span, context) self.assertFalse(mock_span.is_recording()) self.assertTrue(mock_span.is_recording.called) self.assertFalse(mock_span.set_attribute.called) self.assertFalse(mock_span.set_status.called)
def _trace_before_publish(self, *args, **kwargs): task = utils.retrieve_task_from_sender(kwargs) task_id = utils.retrieve_task_id_from_message(kwargs) if task is None or task_id is None: return operation_name = "{0}/{1}".format(_TASK_APPLY_ASYNC, task.name) span = self._tracer.start_span( operation_name, kind=trace.SpanKind.PRODUCER ) # apply some attributes here because most of the data is not available if span.is_recording(): span.set_attribute(_TASK_TAG_KEY, _TASK_APPLY_ASYNC) span.set_attribute(_MESSAGE_ID_ATTRIBUTE_NAME, task_id) span.set_attribute(_TASK_NAME_KEY, task.name) utils.set_attributes_from_context(span, kwargs) activation = self._tracer.use_span(span, end_on_exit=True) activation.__enter__() utils.attach_span(task, task_id, (span, activation), is_publish=True) headers = kwargs.get("headers") if headers: propagators.inject(type(headers).__setitem__, headers)
def _trace_before_publish(self, *args, **kwargs): task = utils.retrieve_task_from_sender(kwargs) task_id = utils.retrieve_task_id_from_message(kwargs) if task is None or task_id is None: return span = self._tracer.start_span(task.name, kind=trace.SpanKind.PRODUCER) # apply some attributes here because most of the data is not available span.set_attribute(_TASK_TAG_KEY, _TASK_APPLY_ASYNC) span.set_attribute(_MESSAGE_ID_ATTRIBUTE_NAME, task_id) span.set_attribute(_TASK_NAME_KEY, task.name) utils.set_attributes_from_context(span, kwargs) activation = self._tracer.use_span(span, end_on_exit=True) activation.__enter__() utils.attach_span(task, task_id, (span, activation), is_publish=True)
def test_set_attributes_from_context(self): # it should extract only relevant keys context = { "correlation_id": "44b7f305", "delivery_info": {"eager": True}, "eta": "soon", "expires": "later", "hostname": "localhost", "id": "44b7f305", "reply_to": "44b7f305", "retries": 4, "timelimit": ("now", "later"), "custom_meta": "custom_value", "routing_key": "celery", } span = trace._Span("name", mock.Mock(spec=trace_api.SpanContext)) utils.set_attributes_from_context(span, context) self.assertEqual( span.attributes.get(SpanAttributes.MESSAGING_MESSAGE_ID), "44b7f305", ) self.assertEqual( span.attributes.get(SpanAttributes.MESSAGING_CONVERSATION_ID), "44b7f305", ) self.assertEqual( span.attributes.get(SpanAttributes.MESSAGING_DESTINATION), "celery" ) self.assertEqual( span.attributes["celery.delivery_info"], str({"eager": True}) ) self.assertEqual(span.attributes.get("celery.eta"), "soon") self.assertEqual(span.attributes.get("celery.expires"), "later") self.assertEqual(span.attributes.get("celery.hostname"), "localhost") self.assertEqual(span.attributes.get("celery.reply_to"), "44b7f305") self.assertEqual(span.attributes.get("celery.retries"), 4) self.assertEqual( span.attributes.get("celery.timelimit"), ("now", "later") ) self.assertNotIn("custom_meta", span.attributes)
def test_set_attributes_partial_timelimit_hard_limit(self): # it should extract only relevant keys context = { "correlation_id": "44b7f305", "delivery_info": { "eager": True }, "eta": "soon", "expires": "later", "hostname": "localhost", "id": "44b7f305", "reply_to": "44b7f305", "retries": 4, "timelimit": ("now", None), "custom_meta": "custom_value", "routing_key": "celery", } span = trace._Span("name", mock.Mock(spec=trace_api.SpanContext)) utils.set_attributes_from_context(span, context) self.assertEqual(span.attributes.get("celery.timelimit"), ("now", ""))
def test_set_attributes_from_context_empty_keys(self): # it should not extract empty keys context = { "correlation_id": None, "exchange": "", "timelimit": (None, None), "retries": 0, } span = trace._Span("name", mock.Mock(spec=trace_api.SpanContext)) utils.set_attributes_from_context(span, context) self.assertEqual(len(span.attributes), 0) # edge case: `timelimit` can also be a list of None values context = { "timelimit": [None, None], } utils.set_attributes_from_context(span, context) self.assertEqual(len(span.attributes), 0)
def _trace_postrun(*args, **kwargs): task = utils.retrieve_task(kwargs) task_id = utils.retrieve_task_id(kwargs) if task is None or task_id is None: return logger.debug("postrun signal task_id=%s", task_id) # retrieve and finish the Span span, activation = utils.retrieve_span(task, task_id) if span is None: logger.warning("no existing span found for task_id=%s", task_id) return # request context tags span.set_attribute(_TASK_TAG_KEY, _TASK_RUN) utils.set_attributes_from_context(span, kwargs) utils.set_attributes_from_context(span, task.request) span.set_attribute(_TASK_NAME_KEY, task.name) activation.__exit__(None, None, None) utils.detach_span(task, task_id)