from typing import Literal from pydantic_settings import BaseSettings, SettingsConfigDict class Settings(BaseSettings): model_config = SettingsConfigDict( env_file=".env", env_file_encoding="utf-8", extra="ignore", ) database_url: str = "postgresql+asyncpg://custodian:changeme@127.0.0.1:5432/custodian" api_base: str = "http://127.0.0.1:8000" # What this instance claims to be. Deliberately defaults to "unknown": # an instance that has not declared itself is not the primary, and callers # that need the authoritative hub must be able to tell the difference. # Answering on a port is not evidence of authority — that assumption cost # seven weeks of onboarding (CUST-WP-0067-T03, ADR-010). state_hub_instance_role: Literal["primary", "cache", "unknown"] = "unknown" # Env vars are STATE_HUB_INSTANCE_ROLE / STATE_HUB_INSTANCE_LABEL — the # field name *is* the binding, so renaming either breaks the deployment # silently. Covered by tests/test_instance_identity.py. # Free-form label to name *which* instance answered, e.g. "railiance01". state_hub_instance_label: str | None = None debug: bool = False state_hub_report_dir: str = "reports/recently-on-scope" state_hub_markitect_cli_path: str | None = None activity_core_url: str | None = None activity_core_worker_token: str | None = None ops_run_projection_ttl_seconds: float = 15.0 ops_run_sla_hours: float = 1.0 sbom_nexus_url: str | None = None sbom_nexus_read_mode: Literal["legacy", "nexus"] = "legacy" sbom_nexus_write_mode: Literal["legacy", "nexus"] = "legacy" sbom_nexus_timeout_seconds: float = 5.0 settings = Settings()