Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

WIP - expose queryable granularities on MFEngine #1393

Draft
wants to merge 1 commit into
base: main
Choose a base branch
from
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
Original file line number Diff line number Diff line change
Expand Up @@ -188,7 +188,7 @@ def get_valid_agg_time_dimensions_for_metric(
)
return valid_agg_time_dimension_specs

def get_min_queryable_time_granularity(self, metric_reference: MetricReference) -> TimeGranularity:
def get_min_queryable_base_time_granularity(self, metric_reference: MetricReference) -> TimeGranularity:
"""The minimum grain that can be queried with this metric.

Maps to the largest granularity defined for any of the metric's agg_time_dimensions.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -394,7 +394,7 @@ def visit_metric_node(self, node: MetricGroupByItemResolutionNode) -> PushDownRe
# Note: ignores any granularity set on input metrics.
metric_default_time_granularity = metric_to_use_for_time_granularity_resolution.time_granularity or max(
TimeGranularity.DAY,
self._semantic_manifest_lookup.metric_lookup.get_min_queryable_time_granularity(
self._semantic_manifest_lookup.metric_lookup.get_min_queryable_base_time_granularity(
MetricReference(metric_to_use_for_time_granularity_resolution.name)
),
)
Expand Down
14 changes: 7 additions & 7 deletions metricflow/dataflow/builder/dataflow_plan_builder.py
Original file line number Diff line number Diff line change
Expand Up @@ -443,7 +443,7 @@ def _build_cumulative_metric_output_node(
) -> DataflowPlanNode:
# TODO: [custom granularity] Figure out how to support custom granularities as defaults
default_granularity = ExpandedTimeGranularity.from_time_granularity(
self._metric_lookup.get_min_queryable_time_granularity(metric_spec.reference)
self._metric_lookup.get_min_queryable_base_time_granularity(metric_spec.reference)
)

queried_agg_time_dimensions = queried_linkable_specs.included_agg_time_dimension_specs_for_metric(
Expand Down Expand Up @@ -1562,12 +1562,12 @@ def _build_aggregated_measure_from_measure_source_node(
non_additive_dimension_grain = self._semantic_model_lookup.get_defined_time_granularity(
TimeDimensionReference(non_additive_dimension_spec.name)
)
queried_time_dimension_spec: Optional[
TimeDimensionSpec
] = self._find_non_additive_dimension_in_linkable_specs(
agg_time_dimension=agg_time_dimension,
linkable_specs=queried_linkable_specs.as_tuple,
non_additive_dimension_spec=non_additive_dimension_spec,
queried_time_dimension_spec: Optional[TimeDimensionSpec] = (
self._find_non_additive_dimension_in_linkable_specs(
agg_time_dimension=agg_time_dimension,
linkable_specs=queried_linkable_specs.as_tuple,
non_additive_dimension_spec=non_additive_dimension_spec,
)
)
time_dimension_spec = TimeDimensionSpec(
# The NonAdditiveDimensionSpec name property is a plain element name
Expand Down
30 changes: 29 additions & 1 deletion metricflow/engine/metricflow_engine.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,12 @@

from dbt_semantic_interfaces.implementations.elements.dimension import PydanticDimensionTypeParams
from dbt_semantic_interfaces.implementations.filters.where_filter import PydanticWhereFilter
from dbt_semantic_interfaces.references import EntityReference, MeasureReference, MetricReference
from dbt_semantic_interfaces.references import (
EntityReference,
MeasureReference,
MetricReference,
TimeDimensionReference,
)
from dbt_semantic_interfaces.type_enums import DimensionType
from metricflow_semantics.dag.sequential_id import SequentialIdGenerator
from metricflow_semantics.errors.error_classes import ExecutionException
Expand All @@ -33,6 +38,7 @@
from metricflow_semantics.sql.sql_table import SqlTable
from metricflow_semantics.time.time_source import TimeSource
from metricflow_semantics.time.time_spine_source import TimeSpineSource
from dbt_semantic_interfaces.type_enums.time_granularity import TimeGranularity

from metricflow.data_table.mf_table import MetricFlowDataTable
from metricflow.dataflow.builder.dataflow_plan_builder import DataflowPlanBuilder
Expand Down Expand Up @@ -552,6 +558,28 @@ def get_measures_for_metrics(self, metric_names: List[str]) -> List[Measure]: #
)
return list(measures)

def get_min_queryable_base_granularity_for_metrics(
self, metric_references: Sequence[MetricReference]
) -> Optional[TimeGranularity]:
"""Get the minimum queryable standard granularity that can be queried with all selected metrics."""
min_granularity_per_metric = {
self._semantic_manifest_lookup.metric_lookup.get_min_queryable_base_time_granularity(metric_reference)
for metric_reference in metric_references
}
# TODO: test that MAX works on enum values
return max(min_granularity_per_metric) if min_granularity_per_metric else None

def get_min_queryable_base_granularity_for_dimensions(
self, time_dimension_references: Sequence[TimeDimensionReference]
) -> Optional[TimeGranularity]:
"""Get the minimum queryable standard granularity that can be queried with all selected time dimensions."""
min_granularity_per_dimension = {
self._semantic_manifest_lookup.semantic_model_lookup.get_defined_time_granularity(time_dimension_reference)
for time_dimension_reference in time_dimension_references
}
# TODO: test that MAX works on enum values
return max(min_granularity_per_metric) if min_granularity_per_metric else None

def simple_dimensions_for_metrics( # noqa: D102
self,
metric_names: List[str],
Expand Down
Loading