From 84fa15f574b58c3dbe9accbdd3cdf1947b992cef Mon Sep 17 00:00:00 2001 From: Nar Saynorath Date: Fri, 3 Jan 2025 10:17:58 -0500 Subject: [PATCH] fix(frames-delay): Update meta resolver frames delay units (#82209) Fixes parsing the units for span metrics. This ensures that aggregates over the span metrics will have the right units. Fixes https://github.com/getsentry/sentry/issues/81560 --------- Co-authored-by: Markus Hintersteiner --- .../search/events/builder/spans_metrics.py | 7 +++ .../test_organization_events_span_metrics.py | 56 +++++++++++++++++++ 2 files changed, 63 insertions(+) diff --git a/src/sentry/search/events/builder/spans_metrics.py b/src/sentry/search/events/builder/spans_metrics.py index 4dac161cc851cf..5ab6ea363afb26 100644 --- a/src/sentry/search/events/builder/spans_metrics.py +++ b/src/sentry/search/events/builder/spans_metrics.py @@ -8,6 +8,7 @@ ) from sentry.search.events.datasets.spans_metrics import SpansMetricsDatasetConfig from sentry.search.events.types import SelectType +from sentry.snuba.metrics.naming_layer.mri import parse_mri SIZE_FIELDS = { "http.decoded_response_content_length": "byte", @@ -43,6 +44,12 @@ def get_field_type(self, field: str) -> str | None: if unit := self.size_fields.get(field): return unit + mri = constants.SPAN_METRICS_MAP.get(field) + if mri is not None: + parsed_mri = parse_mri(mri) + if parsed_mri is not None and parsed_mri.unit in constants.RESULT_TYPES: + return parsed_mri.unit + return None def resolve_select( diff --git a/tests/snuba/api/endpoints/test_organization_events_span_metrics.py b/tests/snuba/api/endpoints/test_organization_events_span_metrics.py index 1b191bfd4670db..a4c4606319551d 100644 --- a/tests/snuba/api/endpoints/test_organization_events_span_metrics.py +++ b/tests/snuba/api/endpoints/test_organization_events_span_metrics.py @@ -1775,6 +1775,62 @@ def test_slow_frames_gauge_metric(self): } ] + def test_frames_delay_gauge_metric(self): + self.store_span_metric( + { + "min": 5, + "max": 5, + "sum": 5, + "count": 1, + "last": 5, + }, + entity="metrics_gauges", + metric="mobile.frames_delay", + timestamp=self.six_min_ago, + tags={"release": "foo"}, + ) + self.store_span_metric( + { + "min": 10, + "max": 10, + "sum": 10, + "count": 1, + "last": 10, + }, + entity="metrics_gauges", + metric="mobile.frames_delay", + timestamp=self.six_min_ago, + tags={"release": "bar"}, + ) + + response = self.do_request( + { + "field": [ + "avg_if(mobile.frames_delay,release,foo)", + "avg_if(mobile.frames_delay,release,bar)", + "avg_compare(mobile.frames_delay,release,foo,bar)", + ], + "query": "", + "project": self.project.id, + "dataset": "spansMetrics", + "statsPeriod": "1h", + } + ) + + assert response.status_code == 200, response.content + data = response.data["data"] + meta = response.data["meta"] + assert data == [ + { + "avg_compare(mobile.frames_delay,release,foo,bar)": 1.0, + "avg_if(mobile.frames_delay,release,foo)": 5.0, + "avg_if(mobile.frames_delay,release,bar)": 10.0, + } + ] + assert meta["units"]["avg_if(mobile.frames_delay,release,foo)"] == "second" + assert meta["units"]["avg_if(mobile.frames_delay,release,bar)"] == "second" + assert meta["units"]["avg_compare(mobile.frames_delay,release,foo,bar)"] is None + def test_resolve_messaging_message_receive_latency_gauge(self): self.store_span_metric( {