# app/modules/tenancy/schemas/store_domain.py
"""
Pydantic schemas for Store Domain operations.

Schemas include:
- StoreDomainCreate: For adding custom domains
- StoreDomainUpdate: For updating domain settings
- StoreDomainResponse: Standard domain response
- StoreDomainListResponse: Paginated domain list
- DomainVerificationInstructions: DNS verification instructions
"""

import re
from datetime import datetime

from pydantic import BaseModel, ConfigDict, Field, field_validator


class StoreDomainCreate(BaseModel):
    """Schema for adding a custom domain to store."""

    domain: str = Field(
        ...,
        description="Custom domain (e.g., myshop.com or shop.mybrand.com)",
        min_length=3,
        max_length=255,
    )
    is_primary: bool = Field(
        default=False, description="Set as primary domain for the store"
    )
    platform_id: int | None = Field(None, description="Platform this domain belongs to")

    @field_validator("domain")
    @classmethod
    def validate_domain(cls, v: str) -> str:
        """Validate and normalize domain."""
        # Remove protocol if present
        domain = v.replace("https://", "").replace("http://", "")  # noqa: SEC034

        # Remove trailing slash
        domain = domain.rstrip("/")

        # Convert to lowercase
        domain = domain.lower().strip()

        # Basic validation
        if not domain or "/" in domain:
            raise ValueError("Invalid domain format")

        if "." not in domain:
            raise ValueError("Domain must have at least one dot")

        # Check for reserved subdomains
        reserved = ["www", "admin", "api", "mail", "smtp", "ftp", "cpanel", "webmail"]
        first_part = domain.split(".")[0]
        if first_part in reserved:
            raise ValueError(
                f"Domain cannot start with reserved subdomain: {first_part}"
            )

        # Validate domain format (basic regex)
        domain_pattern = r"^[a-z0-9]([a-z0-9-]{0,61}[a-z0-9])?(\.[a-z0-9]([a-z0-9-]{0,61}[a-z0-9])?)*$"
        if not re.match(domain_pattern, domain):
            raise ValueError("Invalid domain format")

        return domain


class StoreDomainUpdate(BaseModel):
    """Schema for updating store domain settings."""

    is_primary: bool | None = Field(None, description="Set as primary domain")
    is_active: bool | None = Field(None, description="Activate or deactivate domain")

    model_config = ConfigDict(from_attributes=True)


class StoreDomainResponse(BaseModel):
    """Standard schema for store domain response."""

    model_config = ConfigDict(from_attributes=True)

    id: int
    store_id: int
    domain: str
    is_primary: bool
    is_active: bool
    is_verified: bool
    ssl_status: str
    platform_id: int | None = None
    verification_token: str | None = None
    verified_at: datetime | None = None
    ssl_verified_at: datetime | None = None
    created_at: datetime
    updated_at: datetime


class StoreDomainListResponse(BaseModel):
    """Schema for paginated store domain list."""

    domains: list[StoreDomainResponse]
    total: int


class DomainVerificationInstructions(BaseModel):
    """DNS verification instructions for domain ownership."""

    domain: str
    verification_token: str
    instructions: dict[str, str]
    txt_record: dict[str, str]
    common_registrars: dict[str, str]

    model_config = ConfigDict(from_attributes=True)


class DomainVerificationResponse(BaseModel):
    """Response after domain verification."""

    message: str
    domain: str
    verified_at: datetime
    is_verified: bool


class DomainDeletionResponse(BaseModel):
    """Response after domain deletion."""

    message: str
    domain: str
    store_id: int
