feat(asgi): Migrate away from event processor in span first #5920
6 issues
High
Test parameterization duplicates same values, never tests span_streaming=True code path - `tests/integrations/asgi/test_asgi.py:170`
The @pytest.mark.parametrize decorator specifies [[False, True], [False, True]] - two identical test cases. This means span_streaming is always False, so the entire if span_streaming: branch (lines 198-222) that validates the new span streaming functionality is never executed. The PR's stated purpose is to migrate away from event processors in span-first mode, but this test doesn't actually test that functionality.
Test parameterization has duplicate values - span_streaming path never tested - `tests/integrations/asgi/test_asgi.py:170`
The parametrize decorator on line 170 uses [[False, True], [False, True]] which creates two identical test cases with span_streaming=False, send_default_pii=True. This means the new span streaming code path (lines 198-222) will never be executed. The intended parameterization should test all combinations: [[False, False], [False, True], [True, False], [True, True]] or at least include span_streaming=True cases.
Medium
envelopes_to_spans raises KeyError when span has no attributes - `tests/conftest.py:1230-1232`
The function directly accesses span_json["attributes"] which will raise a KeyError if the span has no attributes. Looking at _span_batcher.py:116-119, the attributes field is only serialized when item._attributes is truthy - spans without attributes won't have this key in the JSON. This will cause test failures if any span being parsed lacks attributes.
AnnotatedValue objects from _filter_headers are not properly handled in attributes - `sentry_sdk/integrations/_asgi_common.py:123-124`
_get_request_attributes iterates over headers from _filter_headers and directly assigns values to attributes. When should_send_default_pii() returns False, _filter_headers returns AnnotatedValue objects for sensitive headers (cookies, authorization, etc.). These objects are passed to set_attribute(), which calls format_attribute() -> safe_repr(), resulting in unhelpful string representations like '<AnnotatedValue object>' instead of proper redaction handling. While no actual PII is leaked (AnnotatedValue.value is empty), the behavior is inconsistent with _get_request_data and produces meaningless attribute values.
Attribute name mismatch between code and test - `sentry_sdk/integrations/asgi.py:244`
The code sets network.protocol.name as the attribute key, but the test test_capture_transaction in tests/integrations/asgi/test_asgi.py line 217 expects the attribute to be http.request.protocol.name. This will cause the test to fail when span streaming is enabled, as the test assertion span["attributes"]["http.request.protocol.name"] == "http" will not find the expected key.
KeyError when span has no attributes - `tests/conftest.py:1230-1232`
The envelopes_to_spans function directly accesses span_json["attributes"] without checking if the key exists. In _span_batcher.py line 116, the attributes field is only included in the transport format when item._attributes is truthy (non-empty). If a span has no attributes set, span_json["attributes"] will not exist, causing a KeyError when the function tries to iterate over it.
4 skills analyzed
| Skill | Findings | Duration | Cost |
|---|---|---|---|
| code-review | 2 | 3m 34s | $1.72 |
| find-bugs | 4 | 5m 14s | $4.21 |
| skill-scanner | 0 | 3m 25s | $0.74 |
| security-review | 0 | 4m 31s | $0.94 |
Duration: 16m 43s · Tokens: 5.7M in / 49.2k out · Cost: $7.64 (+extraction: $0.01, +merge: $0.00, +fix_gate: $0.02, +dedup: $0.01)