From 66dd77c0ff6e4aaeeaf1f6a718ac81de51710faf Mon Sep 17 00:00:00 2001 From: Courtney Holcomb Date: Wed, 10 Jul 2024 18:12:20 -0700 Subject: [PATCH 1/4] Use SetDefaultGranularityRule in CLI rule set --- .../metricflow_semantics/model/dbt_manifest_parser.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/metricflow-semantics/metricflow_semantics/model/dbt_manifest_parser.py b/metricflow-semantics/metricflow_semantics/model/dbt_manifest_parser.py index 638da5283f..903ac85fb5 100644 --- a/metricflow-semantics/metricflow_semantics/model/dbt_manifest_parser.py +++ b/metricflow-semantics/metricflow_semantics/model/dbt_manifest_parser.py @@ -11,6 +11,7 @@ ConvertMedianToPercentileRule, ) from dbt_semantic_interfaces.transformations.cumulative_type_params import SetCumulativeTypeParamsRule +from dbt_semantic_interfaces.transformations.default_granularity import SetDefaultGranularityRule from dbt_semantic_interfaces.transformations.names import LowerCaseNamesRule from dbt_semantic_interfaces.transformations.proxy_measure import CreateProxyMeasureRule from dbt_semantic_interfaces.transformations.semantic_manifest_transformer import ( @@ -38,6 +39,7 @@ def parse_manifest_from_dbt_generated_manifest(manifest_json_string: str) -> Pyd ConvertMedianToPercentileRule(), DedupeMetricInputMeasuresRule(), # Remove once fix is in core SetCumulativeTypeParamsRule(), + SetDefaultGranularityRule(), ), ) model = PydanticSemanticManifestTransformer.transform(raw_model, rules) From 6e68ad6214616092c5cd1deef95dbbedb9694dec Mon Sep 17 00:00:00 2001 From: Courtney Holcomb Date: Wed, 10 Jul 2024 18:13:12 -0700 Subject: [PATCH 2/4] Add default_granularity to MetricSpec --- .../metricflow_semantics/specs/spec_classes.py | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/metricflow-semantics/metricflow_semantics/specs/spec_classes.py b/metricflow-semantics/metricflow_semantics/specs/spec_classes.py index 546f07f58d..ebfdeb7c1c 100644 --- a/metricflow-semantics/metricflow_semantics/specs/spec_classes.py +++ b/metricflow-semantics/metricflow_semantics/specs/spec_classes.py @@ -570,6 +570,7 @@ class MetricSpec(InstanceSpec): # noqa: D101 alias: Optional[str] = None offset_window: Optional[PydanticMetricTimeWindow] = None offset_to_grain: Optional[TimeGranularity] = None + default_granularity: Optional[TimeGranularity] = None @staticmethod def from_element_name(element_name: str) -> MetricSpec: # noqa: D102 @@ -598,7 +599,12 @@ def has_time_offset(self) -> bool: # noqa: D102 def without_offset(self) -> MetricSpec: """Represents the metric spec with any time offsets removed.""" - return MetricSpec(element_name=self.element_name, filter_specs=self.filter_specs, alias=self.alias) + return MetricSpec( + element_name=self.element_name, + filter_specs=self.filter_specs, + alias=self.alias, + default_granularity=self.default_granularity, + ) @dataclass(frozen=True) From fd57e01957e664c594625d8d15796fc3f6c1f8cf Mon Sep 17 00:00:00 2001 From: Courtney Holcomb Date: Wed, 10 Jul 2024 18:16:28 -0700 Subject: [PATCH 3/4] Add MetricLookup method to get_default_granularity_for_metrics --- .../model/semantics/metric_lookup.py | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/metricflow-semantics/metricflow_semantics/model/semantics/metric_lookup.py b/metricflow-semantics/metricflow_semantics/model/semantics/metric_lookup.py index 21e5fb8ac1..5b5f153595 100644 --- a/metricflow-semantics/metricflow_semantics/model/semantics/metric_lookup.py +++ b/metricflow-semantics/metricflow_semantics/model/semantics/metric_lookup.py @@ -210,3 +210,18 @@ def get_min_queryable_time_granularity(self, metric_reference: MetricReference) minimum_queryable_granularity = defined_time_granularity return minimum_queryable_granularity + + def get_default_granularity_for_metrics( + self, metric_references: Sequence[MetricReference] + ) -> Optional[TimeGranularity]: + """When querying a group of metrics, the default granularity will be the largest of the metrics' default granularities.""" + max_default_granularity: Optional[TimeGranularity] = None + for metric_reference in metric_references: + default_granularity = self.get_metric(metric_reference).default_granularity + assert ( + default_granularity + ), f"No default_granularity set for {metric_reference}. Something has been misconfigured." + if not max_default_granularity or default_granularity.to_int() > max_default_granularity.to_int(): + max_default_granularity = default_granularity + + return max_default_granularity From 7435beed08c4ea683f91293f56ed40d694f1afe2 Mon Sep 17 00:00:00 2001 From: Courtney Holcomb Date: Thu, 11 Jul 2024 17:15:26 -0700 Subject: [PATCH 4/4] Remove default_granularity from MetricSpec --- metricflow-semantics/metricflow_semantics/specs/spec_classes.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/metricflow-semantics/metricflow_semantics/specs/spec_classes.py b/metricflow-semantics/metricflow_semantics/specs/spec_classes.py index ebfdeb7c1c..f899a79c5c 100644 --- a/metricflow-semantics/metricflow_semantics/specs/spec_classes.py +++ b/metricflow-semantics/metricflow_semantics/specs/spec_classes.py @@ -570,7 +570,6 @@ class MetricSpec(InstanceSpec): # noqa: D101 alias: Optional[str] = None offset_window: Optional[PydanticMetricTimeWindow] = None offset_to_grain: Optional[TimeGranularity] = None - default_granularity: Optional[TimeGranularity] = None @staticmethod def from_element_name(element_name: str) -> MetricSpec: # noqa: D102 @@ -603,7 +602,6 @@ def without_offset(self) -> MetricSpec: element_name=self.element_name, filter_specs=self.filter_specs, alias=self.alias, - default_granularity=self.default_granularity, )