Skip to content
Draft
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
1 change: 0 additions & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -384,7 +384,6 @@ ignore_missing_imports = true
# - python3 -m tools.mypy_helpers.find_easiest_modules
[[tool.mypy.overrides]]
module = [
"sentry.snuba.metrics.query_builder",
"sentry.testutils.cases",
]
disable_error_code = [
Expand Down
85 changes: 38 additions & 47 deletions src/sentry/snuba/metrics/query_builder.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
from collections.abc import Mapping, Sequence
from datetime import datetime, timedelta
from enum import Enum
from typing import Any, TypedDict, overload
from typing import Any, TypedDict

import sentry_sdk
from snuba_sdk import (
Expand Down Expand Up @@ -137,7 +137,9 @@ def parse_public_field(field: str) -> MetricField:
return MetricField(operation, get_mri(metric_name))


def transform_null_transaction_to_unparameterized(use_case_id, org_id, alias=None):
def transform_null_transaction_to_unparameterized(
use_case_id: UseCaseID, org_id: int, alias: str | None = None
) -> Function:
"""
This function transforms any null tag.transaction to '<< unparameterized >>' so that it can be handled
as such in any query using that tag value.
Expand Down Expand Up @@ -508,11 +510,11 @@ class QueryDefinition:

def __init__(
self,
projects,
query_params,
projects: Sequence[Project],
query_params: Any,
allow_mri: bool = False,
paginator_kwargs: dict | None = None,
):
paginator_kwargs: dict[str, int] | None = None,
) -> None:
self._projects = projects
paginator_kwargs = paginator_kwargs or {}

Expand Down Expand Up @@ -561,7 +563,9 @@ def to_metrics_query(self) -> DeprecatingMetricsQuery:
)

@staticmethod
def _parse_orderby(query_params, allow_mri: bool = False):
def _parse_orderby(
query_params: Any, allow_mri: bool = False
) -> list[MetricsOrderBy] | None:
orderbys = query_params.getlist("orderBy", [])
if not orderbys:
return None
Expand All @@ -579,19 +583,19 @@ def _parse_orderby(query_params, allow_mri: bool = False):
return orderby_list

@staticmethod
def _parse_limit(paginator_kwargs) -> Limit | None:
def _parse_limit(paginator_kwargs: Mapping[str, int]) -> Limit | None:
if "limit" not in paginator_kwargs:
return None
return Limit(paginator_kwargs["limit"])

@staticmethod
def _parse_offset(paginator_kwargs) -> Offset | None:
def _parse_offset(paginator_kwargs: Mapping[str, int]) -> Offset | None:
if "offset" not in paginator_kwargs:
return None
return Offset(paginator_kwargs["offset"])


def get_date_range(params: Mapping) -> tuple[datetime, datetime, int]:
def get_date_range(params: Mapping[str, Any]) -> tuple[datetime, datetime, int]:
"""Get start, end, rollup for the given parameters.

Apply a similar logic as `sessions_v2.get_constrained_date_range`,
Expand Down Expand Up @@ -787,26 +791,6 @@ def __init__(
field.alias: field for field in self._metrics_query.select if field.alias is not None
}

@overload
@staticmethod
def generate_snql_for_action_by_fields(
metric_action_by_field: MetricOrderByField,
use_case_id: UseCaseID,
org_id: int,
projects: Sequence[Project],
is_column: bool = False,
) -> list[OrderBy]: ...

@overload
@staticmethod
def generate_snql_for_action_by_fields(
metric_action_by_field: MetricActionByField,
use_case_id: UseCaseID,
org_id: int,
projects: Sequence[Project],
is_column: bool = False,
) -> Column | AliasedExpression | Function: ...

@staticmethod
def generate_snql_for_action_by_fields(
metric_action_by_field: MetricActionByField,
Expand Down Expand Up @@ -1033,17 +1017,17 @@ def _build_having(self) -> list[BooleanCondition | Condition]:

def __build_totals_and_series_queries(
self,
entity,
select,
where,
having,
groupby,
orderby,
limit,
offset,
rollup,
intervals_len,
):
entity: MetricEntity,
select: list[Any],
where: list[BooleanCondition | Condition],
having: list[BooleanCondition | Condition],
groupby: list[Column] | None,
orderby: list[OrderBy] | None,
limit: Any,
offset: Offset | None,
rollup: Granularity,
intervals_len: int,
) -> dict[str, Query]:
rv = {}
totals_query = Query(
match=Entity(entity),
Expand Down Expand Up @@ -1099,7 +1083,7 @@ def __update_query_dicts_with_component_entities(
component_entities: dict[MetricEntity, Sequence[str]],
metric_mri_to_obj_dict: dict[tuple[str | None, str, str], MetricExpressionBase],
fields_in_entities: dict[MetricEntity, list[tuple[str | None, str, str]]],
parent_alias,
parent_alias: str,
) -> dict[tuple[str | None, str, str], MetricExpressionBase]:
# At this point in time, we are only supporting raw metrics in the metrics attribute of
# any instance of DerivedMetric, and so in this case the op will always be None
Expand All @@ -1124,7 +1108,12 @@ def __update_query_dicts_with_component_entities(
fields_in_entities.setdefault(entity, []).append(metric_key)
return metric_mri_to_obj_dict

def get_snuba_queries(self):
def get_snuba_queries(
self,
) -> tuple[
dict[MetricEntity, dict[str, Query]],
dict[MetricEntity, list[tuple[str | None, str, str]]],
]:
metric_mri_to_obj_dict: dict[tuple[str | None, str, str], MetricExpressionBase] = {}
fields_in_entities: dict[MetricEntity, list[tuple[str | None, str, str]]] = {}

Expand Down Expand Up @@ -1254,9 +1243,9 @@ def __init__(
metrics_query: DeprecatingMetricsQuery,
fields_in_entities: dict[MetricEntity, list[tuple[str | None, str, str]]],
intervals: list[datetime],
results,
results: Mapping[str, Mapping[str, Mapping[str, list[dict[str, Any]]]]],
use_case_id: UseCaseID,
):
) -> None:
self._organization_id = organization_id
self._intervals = intervals
self._results = results
Expand Down Expand Up @@ -1294,7 +1283,9 @@ def __init__(

self._timestamp_index = {timestamp: index for index, timestamp in enumerate(intervals)}

def _extract_data(self, data, groups: dict[tuple[tuple[str, str], ...], _SeriesTotals]) -> None:
def _extract_data(
self, data: dict[str, Any], groups: dict[tuple[tuple[str, str], ...], _SeriesTotals]
) -> None:
group_key_aliases = (
{metric_groupby_obj.alias for metric_groupby_obj in self._metrics_query.groupby}
if self._metrics_query.groupby
Expand Down Expand Up @@ -1354,7 +1345,7 @@ def _extract_data(self, data, groups: dict[tuple[tuple[str, str], ...], _SeriesT
if series[series_index] == default_null_value:
series[series_index] = cleaned_value

def translate_result_groups(self):
def translate_result_groups(self) -> list[_BySeriesTotals]:
groups_d: dict[tuple[tuple[str, str], ...], _SeriesTotals] = {}
for _, subresults in self._results.items():
for k in "totals", "series":
Expand Down
Loading