From 88f187a056bd12ed856af8e7a3c2b27bba02f958 Mon Sep 17 00:00:00 2001 From: "DESKTOP-691E36A\\Administrator" Date: Mon, 20 Jul 2026 00:23:09 -0600 Subject: [PATCH] Fix CI smoke test freshness failure Add a --reference-time CLI flag and use a fixed timestamp in the CI smoke test so sample data freshness checks stay deterministic. --- .github/workflows/ci.yml | 1 + src/dqo/cli.py | 16 ++++++++++++++++ tests/test_cli.py | 24 ++++++++++++++++++++++++ 3 files changed, 41 insertions(+) create mode 100644 tests/test_cli.py diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 3f6b764..674619b 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -61,4 +61,5 @@ jobs: --contract contracts/orders.yml \ --data data/samples/orders.csv \ --references data/samples \ + --reference-time 2026-07-14T12:00:00Z \ --history-db "$DQO_DATABASE_URL" diff --git a/src/dqo/cli.py b/src/dqo/cli.py index aa38dd1..a61c2b2 100644 --- a/src/dqo/cli.py +++ b/src/dqo/cli.py @@ -4,6 +4,7 @@ import argparse import sys +from datetime import datetime, timezone from pathlib import Path from src.dqo.alerts import AlertRouter, ConsoleAlertChannel, FileAlertChannel, WebhookAlertChannel @@ -11,6 +12,14 @@ from src.dqo.runner import run_contract_file +def _parse_reference_time(value: str) -> datetime: + normalized = value.replace("Z", "+00:00") + parsed = datetime.fromisoformat(normalized) + if parsed.tzinfo is None: + return parsed.replace(tzinfo=timezone.utc) + return parsed + + def build_parser() -> argparse.ArgumentParser: parser = argparse.ArgumentParser(description="Run data-quality checks against contracts") subparsers = parser.add_subparsers(dest="command", required=True) @@ -23,6 +32,12 @@ def build_parser() -> argparse.ArgumentParser: run_parser.add_argument("--alert-file", type=Path, default=Path(".dqo/alerts.jsonl")) run_parser.add_argument("--webhook-url", type=str, default=None) run_parser.add_argument("--no-console-alerts", action="store_true") + run_parser.add_argument( + "--reference-time", + type=_parse_reference_time, + default=None, + help="Evaluate freshness relative to this ISO-8601 timestamp (default: current UTC time)", + ) history_parser = subparsers.add_parser("history", help="Show recent runs") history_parser.add_argument("--contract", required=True) @@ -41,6 +56,7 @@ def main(argv: list[str] | None = None) -> int: args.contract, args.data, reference_dir=args.references, + now=args.reference_time, ) store = HistoryStore(database_url=args.history_db) diff --git a/tests/test_cli.py b/tests/test_cli.py new file mode 100644 index 0000000..5a3f788 --- /dev/null +++ b/tests/test_cli.py @@ -0,0 +1,24 @@ +from pathlib import Path + +from src.dqo.cli import main + + +def test_cli_run_passes_with_reference_time(tmp_path: Path) -> None: + exit_code = main( + [ + "run", + "--contract", + "contracts/orders.yml", + "--data", + "data/samples/orders.csv", + "--references", + "data/samples", + "--reference-time", + "2026-07-14T12:00:00Z", + "--no-console-alerts", + "--history-db", + f"sqlite:///{tmp_path / 'history.db'}", + ] + ) + + assert exit_code == 0