-
Notifications
You must be signed in to change notification settings - Fork 97
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Use pushdown params to disable time range constraint pushdown
The predicate pushdown operations for time range constriants currently rely on None/not-None state to determine whether or not to push the ConstrainTimeRange filter node to the source. With the switch to pushdown params this None/not-None state gets tenuous, as future updates will need to do things like manage time range constraints, other time dimension filters, and categorical dimension (and entity) filters, and relying on externalizing None/not-None combinations for these various filter types will be challenging. This change encapsulates the enabling and disabling of time range constraints inside of PredicatePushdownParams. At the moment, in order to maintain the existing behavior, we simply internalize the None/not-None behavior for time range constraints. This will also allow us to easily retain pushdown processing for categorical dimensions even when time constraint filters should not be applied, and gradually centralize those controls as we streamline the callsites. There is added complexity to this change because of two things. 1. Time constraint updating is scattered around in the DataflowPlanBuilder 2. Conversion metrics currently do predicate pushdown for time constraints The first of these will be addressed later. Since we cannot reliably support general predicate pushdown for conversion metrics, we need to allow for a time-range-only pushdown operation. Today this is equivalent to pushdown enabled, but that will change shortly.
- Loading branch information
Showing
3 changed files
with
189 additions
and
19 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
54 changes: 54 additions & 0 deletions
54
tests_metricflow/dataflow/builder/test_predicate_pushdown.py
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,54 @@ | ||
from __future__ import annotations | ||
|
||
import dataclasses | ||
|
||
import pytest | ||
from metricflow_semantics.filters.time_constraint import TimeRangeConstraint | ||
|
||
from metricflow.plan_conversion.node_processor import PredicatePushdownParameters, PredicatePushdownState | ||
|
||
|
||
@pytest.fixture | ||
def all_pushdown_params() -> PredicatePushdownParameters: | ||
"""Tests a valid configuration with all predicate properties set and pushdown fully enabled.""" | ||
params = PredicatePushdownParameters( | ||
time_range_constraint=TimeRangeConstraint.all_time(), pushdown_state=PredicatePushdownState.FULLY_ENABLED | ||
) | ||
predicate_property_names = { | ||
field.name for field in dataclasses.fields(params) if field.metadata.get(params._PREDICATE_METADATA_KEY) | ||
} | ||
predicate_properties = { | ||
name: value for name, value in dataclasses.asdict(params).items() if name in predicate_property_names | ||
} | ||
assert all(value is not None for value in predicate_properties.values()), ( | ||
"All predicate properties in this pushdown param instance should be set to something other than None. Found " | ||
f"one or more None values in property map: {predicate_properties}" | ||
) | ||
return params | ||
|
||
|
||
def test_time_range_pushdown_enabled_states(all_pushdown_params: PredicatePushdownParameters) -> None: | ||
"""Tests pushdown enabled check for time range pushdown operations.""" | ||
time_range_only_params = PredicatePushdownParameters( | ||
time_range_constraint=TimeRangeConstraint.all_time(), | ||
pushdown_state=PredicatePushdownState.ENABLED_FOR_TIME_RANGE_ONLY, | ||
) | ||
|
||
enabled_states = { | ||
"fully enabled": all_pushdown_params.is_pushdown_enabled, | ||
"enabled for time range only": time_range_only_params.is_pushdown_enabled, | ||
} | ||
|
||
assert all(list(enabled_states.values())), ( | ||
"Expected pushdown to be enabled for pushdown params with time range constraint and global pushdown enabled, " | ||
f"but some params returned False for is_pushdown_enabled.\nPushdown enabled states: {enabled_states}\n" | ||
f"All params: {all_pushdown_params}\nTime range only params: {time_range_only_params}" | ||
) | ||
|
||
|
||
def test_invalid_disabled_pushdown_params() -> None: | ||
"""Tests checks for invalid param configuration on disabled pushdown parameters.""" | ||
with pytest.raises(AssertionError, match="Disabled pushdown parameters cannot have properties set"): | ||
PredicatePushdownParameters( | ||
pushdown_state=PredicatePushdownState.DISABLED, time_range_constraint=TimeRangeConstraint.all_time() | ||
) |