diff --git a/CHANGELOG.md b/CHANGELOG.md index 6e26036875..58c9c75d01 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -8,6 +8,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased](https://github.com/open-telemetry/opentelemetry-python/compare/v1.13.0-0.34b0...HEAD) - Add metric instrumentation for tornado ([#1252](https://github.com/open-telemetry/opentelemetry-python-contrib/pull/1252)) +- Fix bug in Falcon instrumentation + ([#1377](https://github.com/open-telemetry/opentelemetry-python-contrib/pull/1377)) ### Added diff --git a/instrumentation/opentelemetry-instrumentation-falcon/src/opentelemetry/instrumentation/falcon/__init__.py b/instrumentation/opentelemetry-instrumentation-falcon/src/opentelemetry/instrumentation/falcon/__init__.py index 7a3e8aebb2..e94c0659f0 100644 --- a/instrumentation/opentelemetry-instrumentation-falcon/src/opentelemetry/instrumentation/falcon/__init__.py +++ b/instrumentation/opentelemetry-instrumentation-falcon/src/opentelemetry/instrumentation/falcon/__init__.py @@ -277,6 +277,7 @@ def _handle_exception( def __call__(self, env, start_response): # pylint: disable=E1101 # pylint: disable=too-many-locals + # pylint: disable=too-many-branches if self._otel_excluded_urls.url_disabled(env.get("PATH_INFO", "/")): return super().__call__(env, start_response) @@ -313,35 +314,38 @@ def __call__(self, env, start_response): activation.__enter__() env[_ENVIRON_SPAN_KEY] = span env[_ENVIRON_ACTIVATION_KEY] = activation + exception = None def _start_response(status, response_headers, *args, **kwargs): response = start_response( status, response_headers, *args, **kwargs ) - activation.__exit__(None, None, None) - if token is not None: - context.detach(token) return response start = default_timer() try: return super().__call__(env, _start_response) except Exception as exc: - activation.__exit__( - type(exc), - exc, - getattr(exc, "__traceback__", None), - ) - if token is not None: - context.detach(token) + exception = exc raise finally: - duration_attrs[ - SpanAttributes.HTTP_STATUS_CODE - ] = span.attributes.get(SpanAttributes.HTTP_STATUS_CODE) + if span.is_recording(): + duration_attrs[ + SpanAttributes.HTTP_STATUS_CODE + ] = span.attributes.get(SpanAttributes.HTTP_STATUS_CODE) duration = max(round((default_timer() - start) * 1000), 0) self.duration_histogram.record(duration, duration_attrs) self.active_requests_counter.add(-1, active_requests_count_attrs) + if exception is None: + activation.__exit__(None, None, None) + else: + activation.__exit__( + type(exception), + exception, + getattr(exception, "__traceback__", None), + ) + if token is not None: + context.detach(token) class _TraceMiddleware: