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
10 changes: 8 additions & 2 deletions sentry_sdk/integrations/aiohttp.py
Original file line number Diff line number Diff line change
Expand Up @@ -233,6 +233,7 @@
},
parent_span=None,
)
scope.get_current_scope()._server_segment_span = span_ctx
else:
transaction = continue_trace(
headers,
Expand Down Expand Up @@ -323,14 +324,19 @@
if integration is None:
return rv

route_info = rv.get_info()
pattern = route_info.get("path") or route_info.get("formatter")

Check failure on line 328 in sentry_sdk/integrations/aiohttp.py

View check run for this annotation

@sentry/warden / warden: find-bugs

Unprotected route_info extraction can break aiohttp request resolution

Keep `rv.get_info()` and pattern extraction inside the existing try/except (or wrap with capture_internal_exceptions); an exception here now escapes sentry_urldispatcher_resolve and can fail the request instead of only skipping transaction naming.

server_span = sentry_sdk.get_current_scope()._server_segment_span
if server_span is not None and pattern is not None:
server_span.set_attribute(SPANDATA.HTTP_ROUTE, pattern)

Check warning on line 332 in sentry_sdk/integrations/aiohttp.py

View check run for this annotation

@sentry/warden / warden: code-review

rv.get_info() no longer guarded by try/except

Moving `rv.get_info()` outside the try/except means any failure there now aborts URL resolution and the request; keep the lookup inside a `capture_internal_exceptions`/`try` block so http.route is best-effort.
Comment thread
alexander-alderman-webb marked this conversation as resolved.
Comment thread
alexander-alderman-webb marked this conversation as resolved.

name = None

try:
if integration.transaction_style == "handler_name":
name = transaction_from_function(rv.handler)
elif integration.transaction_style == "method_and_path_pattern":
route_info = rv.get_info()
pattern = route_info.get("path") or route_info.get("formatter")
name = "{} {}".format(request.method, pattern)
except Exception:
pass
Expand Down
36 changes: 36 additions & 0 deletions tests/integrations/aiohttp/test_aiohttp.py
Original file line number Diff line number Diff line change
Expand Up @@ -1882,6 +1882,42 @@ async def hello(request):
assert server_segment["attributes"]["sentry.segment.name.source"] == expected_source


@pytest.mark.asyncio
@pytest.mark.parametrize(
"url,expected_route",
[
("/message", "/{var}"),
],
)
async def test_http_route(
sentry_init,
aiohttp_client,
capture_items,
url,
expected_route,
):
sentry_init(
integrations=[AioHttpIntegration()],
traces_sample_rate=1.0,
trace_lifecycle="stream",
)

async def hello(request):
return web.Response(text="hello")

app = web.Application()
app.router.add_get(r"/{var}", hello)

items = capture_items("span")

client = await aiohttp_client(app)
await client.get(url)

sentry_sdk.flush()
(segment,) = (item.payload for item in items if item.payload.get("is_segment"))
assert segment["attributes"]["http.route"] == expected_route


@pytest.mark.asyncio
async def test_server_error_span_streaming(sentry_init, aiohttp_client, capture_items):
sentry_init(
Expand Down
Loading