from __future__ import annotations from datetime import datetime, timedelta, timezone from typing import Any from sqlalchemy import select, text from sqlalchemy.orm import Session from .models import CommunityImportRun, ImportStatus, OfficialRecordImport def readiness_report( session: Session, s3: Any, *, import_required: bool, import_interval_seconds: int, community_import_interval_seconds: int = 1800, now: datetime | None = None, ) -> tuple[bool, dict[str, dict[str, object]]]: current = now or datetime.now(timezone.utc) components: dict[str, dict[str, object]] = {} ready = True try: session.execute(text("SELECT 1")) components["postgresql"] = {"status": "ready"} except Exception: components["postgresql"] = {"status": "unavailable"} ready = False try: s3.list_buckets() components["minio"] = {"status": "ready"} except Exception: components["minio"] = {"status": "unavailable"} ready = False try: latest = session.scalar(select(OfficialRecordImport).order_by( OfficialRecordImport.started_at.desc(), OfficialRecordImport.id.desc(), ).limit(1)) if not import_required: components["official_import"] = { "status": "optional", "last_run_status": latest.status.value if latest else None, } elif latest is None: components["official_import"] = {"status": "not_run"} ready = False else: started = latest.started_at if latest.started_at.tzinfo else latest.started_at.replace(tzinfo=timezone.utc) stale = started < current - timedelta(seconds=import_interval_seconds * 2) healthy = latest.status == ImportStatus.success and not stale components["official_import"] = { "status": "ready" if healthy else ("stale" if stale else latest.status.value), "last_run_status": latest.status.value, "last_started_at": started.isoformat(), } ready = ready and healthy except Exception: components["official_import"] = {"status": "unknown"} if import_required: ready = False # Check community scheduler: look for recent import runs try: latest_community = session.scalar( select(CommunityImportRun) .order_by(CommunityImportRun.started_at.desc()) .limit(1) ) if latest_community is None: components["community_scheduler"] = {"status": "not_started"} else: started = latest_community.started_at if started.tzinfo is None: started = started.replace(tzinfo=timezone.utc) stale = started < current - timedelta(seconds=community_import_interval_seconds * 2) healthy = latest_community.status == "success" and not stale components["community_scheduler"] = { "status": "ready" if healthy else ("stale" if stale else latest_community.status), "last_started_at": started.isoformat(), } except Exception: components["community_scheduler"] = {"status": "unknown"} return ready, components