"""Pydantic schemas for the universal Fetch Data Toggle system."""
from __future__ import annotations

from datetime import datetime
from typing import List, Optional

from pydantic import BaseModel, Field


class ModuleSyncSettingsOut(BaseModel):
    """Full settings + live counters for one module."""

    module_name: str
    module_label: str

    fetch_clients_enabled: bool
    fetch_accounts_enabled: bool
    fetch_domains_enabled: bool

    last_clients_sync: Optional[datetime] = None
    last_accounts_sync: Optional[datetime] = None
    last_domains_sync: Optional[datetime] = None

    clients_sync_status: str
    accounts_sync_status: str
    domains_sync_status: str

    clients_count: int
    accounts_count: int
    domains_count: int
    domains_linked_count: int
    domains_unlinked_count: int

    last_error: Optional[str] = None


class ModuleSyncToggleUpdate(BaseModel):
    """PATCH body for toggling a module's fetch flags.

    Each field is optional so the UI can toggle only one at a time.
    """

    fetch_clients_enabled: Optional[bool] = None
    fetch_accounts_enabled: Optional[bool] = None
    fetch_domains_enabled: Optional[bool] = None


class ModuleSyncRunResult(BaseModel):
    """Result envelope returned by manual fetch endpoints."""

    module_name: str
    sync_type: str
    status: str
    items_fetched: int = 0
    error_message: Optional[str] = None
    started_at: datetime
    finished_at: Optional[datetime] = None
    duration_ms: int = 0


class ModuleSyncRunAllResult(BaseModel):
    """Result envelope for "Fetch All Now" (runs the three types)."""

    module_name: str
    runs: List[ModuleSyncRunResult]


class ModuleSyncLogItem(BaseModel):
    id: int
    module_name: str
    sync_type: str
    status: str
    items_fetched: int
    error_message: Optional[str] = None
    triggered_by: str
    actor_email: Optional[str] = None
    duration_ms: int
    started_at: datetime
    finished_at: Optional[datetime] = None


class ModuleSyncLogDetail(ModuleSyncLogItem):
    raw_response: Optional[str] = None


class ModuleSyncLogList(BaseModel):
    items: List[ModuleSyncLogItem]
    total: int


class ModuleDiagnosticStep(BaseModel):
    step: str
    ok: bool
    detail: Optional[str] = None


class ModuleDiagnosticsResult(BaseModel):
    module_name: str
    ok: bool
    steps: List[ModuleDiagnosticStep] = Field(default_factory=list)
    message: Optional[str] = None