Skip to content

Commit 7b82ca6

Browse files
Fix filters being applied to wrong evaluables (#124)
To check whether a rule should be evaluated, we executed all model filters even when the type of the evaluable filter did not match the evaluable. To fix this; check the type first before executing the filters.
1 parent 5a70c40 commit 7b82ca6

File tree

3 files changed

+31
-6
lines changed

3 files changed

+31
-6
lines changed

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@ and this project adheres to
88

99
## [Unreleased]
1010

11+
- Fix filters being applied to wrong evaluables (#124)
12+
1113
## [0.13.0] - 2025-07-07
1214

1315
- Support linting of exposures (#112)

src/dbt_score/rule.py

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -166,12 +166,13 @@ def should_evaluate(cls, evaluable: Evaluable) -> bool:
166166
"""
167167
resource_types_match = cls.resource_type is type(evaluable)
168168

169+
if not resource_types_match:
170+
return False
171+
169172
if cls.rule_filters:
170-
return (
171-
all(f.evaluate(evaluable) for f in cls.rule_filters)
172-
and resource_types_match
173-
)
174-
return resource_types_match
173+
return all(f.evaluate(evaluable) for f in cls.rule_filters)
174+
175+
return True
175176

176177
@classmethod
177178
def set_severity(cls, severity: Severity) -> None:

tests/test_rule.py

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -145,7 +145,11 @@ def evaluate(self, source: Source) -> bool: # type: ignore[override]
145145

146146
@pytest.mark.parametrize(
147147
"rule_filter_fixture",
148-
["source_filter_no_parens", "source_filter_parens", "source_filter_class"],
148+
[
149+
"source_filter_no_parens",
150+
"source_filter_parens",
151+
"source_filter_class",
152+
],
149153
)
150154
def test_rule_filter_must_match_resource_type_as_rule(
151155
self, request, rule_filter_fixture
@@ -174,3 +178,21 @@ def evaluate(self, model: Model) -> RuleViolation | None: # type: ignore[overri
174178

175179
assert "Mismatched resource_type on filter" in str(excinfo.value)
176180
assert "Expected Model, but got Source" in str(excinfo.value)
181+
182+
183+
def test_should_evaluate(model1, source1):
184+
"""Test that should_evaluate does not execute filter on mismatched resource type."""
185+
186+
@rule_filter
187+
def model_filter(model: Model) -> bool:
188+
"""Filter on empty constraints."""
189+
return model.constraints == [] # constraints does not exist for Source
190+
191+
@rule(rule_filters={model_filter()})
192+
def model_rule(model: Model) -> RuleViolation | None:
193+
"""Rule that always returns None."""
194+
return None
195+
196+
rule1 = model_rule()
197+
assert rule1.should_evaluate(model1) is True
198+
assert rule1.should_evaluate(source1) is False

0 commit comments

Comments
 (0)