Skip to content
Merged
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
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,10 @@ Types of changes:

## [Unreleased]

### Fixed

- Add `identifier_placeholder` parameter to all missing relevant check functions and forward to constructors

## [0.11.1] - 2026-01-22

### Fixed
Expand Down
10 changes: 10 additions & 0 deletions src/koality/checks.py
Original file line number Diff line number Diff line change
Expand Up @@ -811,6 +811,7 @@ def __init__(
*,
filters: dict[str, Any] | None = None,
identifier_format: str = "identifier",
identifier_placeholder: str = "ALL",
date_info: str | None = None,
extra_info: str | None = None,
monitor_only: bool = False,
Expand Down Expand Up @@ -840,6 +841,7 @@ def __init__(
upper_threshold=upper_threshold,
filters=filters,
identifier_format=identifier_format,
identifier_placeholder=identifier_placeholder,
date_info=date_info,
extra_info=extra_info,
monitor_only=monitor_only,
Expand Down Expand Up @@ -1025,6 +1027,7 @@ def __init__(
*,
filters: dict[str, Any] | None = None,
identifier_format: str = "identifier",
identifier_placeholder: str = "ALL",
date_info: str | None = None,
extra_info: str | None = None,
monitor_only: bool = False,
Expand All @@ -1040,6 +1043,7 @@ def __init__(
upper_threshold=upper_threshold,
filters=filters,
identifier_format=identifier_format,
identifier_placeholder=identifier_placeholder,
date_info=date_info,
extra_info=extra_info,
monitor_only=monitor_only,
Expand Down Expand Up @@ -1067,6 +1071,7 @@ def __init__(
*,
filters: dict[str, Any] | None = None,
identifier_format: str = "identifier",
identifier_placeholder: str = "ALL",
date_info: str | None = None,
extra_info: str | None = None,
monitor_only: bool = False,
Expand All @@ -1082,6 +1087,7 @@ def __init__(
upper_threshold=upper_threshold,
filters=filters,
identifier_format=identifier_format,
identifier_placeholder=identifier_placeholder,
date_info=date_info,
extra_info=extra_info,
monitor_only=monitor_only,
Expand Down Expand Up @@ -1109,6 +1115,7 @@ def __init__(
*,
filters: dict[str, Any] | None = None,
identifier_format: str = "identifier",
identifier_placeholder: str = "ALL",
date_info: str | None = None,
extra_info: str | None = None,
monitor_only: bool = False,
Expand All @@ -1124,6 +1131,7 @@ def __init__(
upper_threshold=upper_threshold,
filters=filters,
identifier_format=identifier_format,
identifier_placeholder=identifier_placeholder,
date_info=date_info,
extra_info=extra_info,
monitor_only=monitor_only,
Expand Down Expand Up @@ -1175,6 +1183,7 @@ def __init__(
*,
filters: dict[str, Any] | None = None,
identifier_format: str = "identifier",
identifier_placeholder: str = "ALL",
date_info: str | None = None,
extra_info: str | None = None,
monitor_only: bool = False,
Expand All @@ -1194,6 +1203,7 @@ def __init__(
upper_threshold=upper_threshold,
filters=filters,
identifier_format=identifier_format,
identifier_placeholder=identifier_placeholder,
date_info=date_info,
extra_info=extra_info,
monitor_only=monitor_only,
Expand Down
205 changes: 205 additions & 0 deletions tests/unit/test_identifier_placeholder_checks.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,205 @@
"""Unit tests ensuring identifier_placeholder is respected by checks."""

import datetime as dt

import pytest

from koality.checks import (
AverageCheck,
CountCheck,
DuplicateCheck,
MatchRateCheck,
MaxCheck,
MinCheck,
NullRatioCheck,
OccurrenceCheck,
RegexMatchCheck,
RollingValuesInSetCheck,
)

pytestmark = pytest.mark.unit


def test_average_check_uses_identifier_placeholder() -> None:
"""AverageCheck uses identifier_placeholder for naming-only identifier filters."""
chk = AverageCheck(
database_accessor="",
database_provider=None,
table="t",
check_column="col",
filters={"shop_id": {"type": "identifier"}},
identifier_format="filter_name",
identifier_placeholder="PH",
)
assert chk.identifier == "PH"
assert chk.identifier_column == "SHOP_ID"


def test_max_check_uses_identifier_placeholder() -> None:
"""MaxCheck uses identifier_placeholder for naming-only identifier filters."""
chk = MaxCheck(
database_accessor="",
database_provider=None,
table="t",
check_column="col",
filters={"shop_id": {"type": "identifier"}},
identifier_format="filter_name",
identifier_placeholder="PH2",
)
assert chk.identifier == "PH2"
assert chk.identifier_column == "SHOP_ID"


def test_min_check_uses_identifier_placeholder() -> None:
"""MinCheck uses identifier_placeholder for naming-only identifier filters."""
chk = MinCheck(
database_accessor="",
database_provider=None,
table="t",
check_column="col",
filters={"shop_id": {"type": "identifier"}},
identifier_format="filter_name",
identifier_placeholder="PH3",
)
assert chk.identifier == "PH3"
assert chk.identifier_column == "SHOP_ID"


def test_occurrence_check_uses_identifier_placeholder() -> None:
"""OccurrenceCheck uses identifier_placeholder for naming-only identifier filters."""
chk = OccurrenceCheck(
database_accessor="",
database_provider=None,
max_or_min="max",
table="t",
check_column="col",
filters={"shop_id": {"type": "identifier"}},
identifier_format="filter_name",
identifier_placeholder="PH4",
)
assert chk.identifier == "PH4"
assert chk.identifier_column == "SHOP_ID"


def test_rolling_values_in_set_check_requires_date_and_uses_placeholder() -> None:
"""RollingValuesInSetCheck requires a date filter and uses identifier_placeholder."""
# Provide a date filter to satisfy constructor requirements
today = dt.datetime.now(tz=dt.UTC).date().isoformat()
chk = RollingValuesInSetCheck(
database_accessor="",
database_provider=None,
table="t",
check_column="col",
value_set=["a"],
filters={
"partition_date": {"column": "DATE", "value": today, "type": "date"},
"shop_id": {"type": "identifier"},
},
identifier_format="filter_name",
identifier_placeholder="PH5",
)
assert chk.identifier == "PH5"
assert chk.identifier_column == "SHOP_ID"


def test_values_in_set_check_uses_identifier_placeholder() -> None:
"""ValuesInSetCheck uses identifier_placeholder for naming-only identifier filters."""
chk = RollingValuesInSetCheck(
database_accessor="",
database_provider=None,
table="t",
check_column="col",
value_set=["a"],
filters={
"shop_id": {"type": "identifier"},
"partition_date": {
"column": "DATE",
"value": dt.datetime.now(tz=dt.UTC).date().isoformat(),
"type": "date",
},
},
identifier_format="filter_name",
identifier_placeholder="PH6",
)
assert chk.identifier == "PH6"
assert chk.identifier_column == "SHOP_ID"


def test_regex_check_use_identifier_placeholder() -> None:
"""RegexMatchCheck and MatchRateCheck use identifier_placeholder for naming-only identifier filters."""
regex_chk = RegexMatchCheck(
database_accessor="",
database_provider=None,
table="t",
check_column="col",
regex_to_match="^a",
filters={"shop_id": {"type": "identifier"}},
identifier_format="filter_name",
identifier_placeholder="PH7",
)
assert regex_chk.identifier == "PH7"
assert regex_chk.identifier_column == "SHOP_ID"


def test_matchrate_check_uses_identifier_placeholder() -> None:
"""MatchRateCheck uses identifier_placeholder for naming-only identifier filters."""
# MatchRateCheck
mr_chk = MatchRateCheck(
database_accessor="",
database_provider=None,
left_table="left",
right_table="right",
check_column="col",
join_columns=["id"],
filters={"shop_id": {"type": "identifier"}},
identifier_format="filter_name",
identifier_placeholder="PH8",
)
assert mr_chk.identifier == "PH8"
assert mr_chk.identifier_column == "SHOP_ID"


# CountCheck, DuplicateCheck, NullRatioCheck,
def test_count_check_uses_identifier_placeholder() -> None:
"""CountCheck uses identifier_placeholder for naming-only identifier filters."""
chk = CountCheck(
database_accessor="",
database_provider=None,
table="t",
check_column="col",
filters={"shop_id": {"type": "identifier"}},
identifier_format="filter_name",
identifier_placeholder="PH9",
)
assert chk.identifier == "PH9"
assert chk.identifier_column == "SHOP_ID"


def test_duplicate_check_uses_identifier_placeholder() -> None:
"""DuplicateCheck uses identifier_placeholder for naming-only identifier filters."""
chk = DuplicateCheck(
database_accessor="",
database_provider=None,
table="t",
check_column="col",
filters={"shop_id": {"type": "identifier"}},
identifier_format="filter_name",
identifier_placeholder="PH10",
)
assert chk.identifier == "PH10"
assert chk.identifier_column == "SHOP_ID"


def test_null_ratio_check_uses_identifier_placeholder() -> None:
"""NullRatioCheck uses identifier_placeholder for naming-only identifier filters."""
chk = NullRatioCheck(
database_accessor="",
database_provider=None,
table="t",
check_column="col",
filters={"shop_id": {"type": "identifier"}},
identifier_format="filter_name",
identifier_placeholder="PH11",
)
assert chk.identifier == "PH11"
assert chk.identifier_column == "SHOP_ID"
Loading