from __future__ import annotations from datetime import datetime, timezone from typing import Literal from sqlalchemy.orm import Session from .models import ExternalObservation, ModerationStatus SourceCheckStatus = Literal["available", "missing", "temporary_error", "blocked"] def record_source_check( session: Session, observation: ExternalObservation, status: SourceCheckStatus, *, checked_at: datetime | None = None, ) -> ExternalObservation: """Persist a check performed during an already scheduled source request. Only an authoritative 404/410-style ``missing`` result withdraws published data. Transient errors and access blocks remain diagnostic and never remove an observation from activity. """ current = checked_at or datetime.now(timezone.utc) observation.source_check_status = status observation.source_checked_at = current if status == "missing" and observation.status != "withdrawn": if observation.catch_report is not None: observation.catch_report.moderation_status = ModerationStatus.pending observation.status = "withdrawn" observation.review_note = "Source record missing; withdrawn pending moderator review" observation.reviewed_at = current observation.moderation_version += 1 session.commit() return observation