Skip to content

fix(eap): fix coalesced attribute handling for deprecated keys#7886

Merged
buenaflor merged 5 commits intomasterfrom
gibuenaf/fix-coalesce-null-replacement
Apr 24, 2026
Merged

fix(eap): fix coalesced attribute handling for deprecated keys#7886
buenaflor merged 5 commits intomasterfrom
gibuenaf/fix-coalesce-null-replacement

Conversation

@buenaflor
Copy link
Copy Markdown
Contributor

@buenaflor buenaflor commented Apr 20, 2026

Two related fixes for coalesced attribute handling:

1. Skip deprecations without a replacement when building coalesce map

The _build_deprecated_attributes loop assumed every deprecation has a replacement, but replacement is optional. For deprecations without a successor, replacement=None created a None key in ATTRIBUTES_TO_COALESCE and grouped unrelated deprecated attributes together. Now only deprecated attributes that define a replacement are included.

Refs #7884

2. Handle coalesced attributes in exists_filter

exists_filter (has: syntax) on coalesced attributes only checked the canonical key, missing v1 spans stored under deprecated keys. In get_field_existence_expression, when attribute_key_to_expression returns a coalesce(...) for attributes with deprecated mappings, the helper get_subscriptable_field extracted only the first parameter (canonical key) and generated mapContains for just that key — all deprecated alternatives were silently ignored.

Added a handler that detects coalesce function calls and recursively generates per-parameter existence checks combined with OR.

Fixes #7879

`_build_deprecated_attributes` in `snuba/protos/common.py` treats
`metadata.deprecation.replacement` as a `str`, but it's `Optional[str]`.
Attributes deprecated without a successor have `replacement=None`, so
they all collapse under a `None` key in `ATTRIBUTES_TO_COALESCE`,
grouping unrelated deprecated names together.

Only include deprecations that specify a replacement, and drop the
misleading `cast`.

Made-with: Cursor
Add a focused assertion that `ATTRIBUTES_TO_COALESCE` never contains a
`None` key. This guards against reintroducing the bug where deprecated
attributes without a replacement were grouped under `None`.

Made-with: Cursor
Copilot AI review requested due to automatic review settings April 20, 2026 16:04
@buenaflor buenaflor requested a review from a team as a code owner April 20, 2026 16:04
Copy link
Copy Markdown

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Fixes a bug in the EAP attribute coalescing map construction where deprecated attributes without a replacement were incorrectly included, creating a None key and causing unrelated deprecated attributes to be grouped together. This aligns Snuba’s attribute resolution behavior with the sentry-conventions metadata model where replacement is optional.

Changes:

  • Skip deprecation entries that do not define a replacement when building ATTRIBUTES_TO_COALESCE.
  • Add a regression test ensuring the coalesce map does not contain a None key.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated no comments.

File Description
snuba/protos/common.py Fixes coalesce-map construction by filtering out deprecations lacking a replacement.
tests/protos/test_protos_common.py Adds regression test to prevent None from appearing as a coalesce-map key.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

`get_field_existence_expression` now decomposes `coalesce(...)` expressions
into OR-combined per-key existence checks, so `has:<canonical_key>` matches
spans that only store the value under a deprecated key.

Fixes #7879

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@buenaflor buenaflor requested a review from a team as a code owner April 21, 2026 08:35
@buenaflor buenaflor changed the title fix(eap): skip deprecations without a replacement when building coalesce map fix(eap): fix coalesced attribute handling for deprecated keys Apr 21, 2026
Assert exact key coverage for coalesced exists_filter expressions so the test catches accidental extra mapContains keys as well as missing deprecated aliases.

Made-with: Cursor
@buenaflor buenaflor merged commit cdd3614 into master Apr 24, 2026
70 of 72 checks passed
@buenaflor buenaflor deleted the gibuenaf/fix-coalesce-null-replacement branch April 24, 2026 09:08
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

exists_filter on coalesced attributes misses v1 spans stored under deprecated keys

3 participants