"""Proxy CRUD domain — sync and async mixins."""

from __future__ import annotations

from typing import Any

from ...exceptions import api_error_handler, async_api_error_handler
from ..._api.generated.proxies.proxies__api__proxies.models import (
    Proxy,
    PaginatedProxyList,
    ProxyRequest,
    PatchedProxyRequest,
)
from ._utils import coerce_proxy_type, coerce_proxy_mode, coerce_proxy_status


class _ProxiesMixin:
    """Sync proxy CRUD methods."""

    _api: Any

    @api_error_handler
    def list(
        self,
        *,
        page: int = 1,
        page_size: int = 20,
        search: str | None = None,
        ordering: str | None = None,
    ) -> PaginatedProxyList:
        """List proxies."""
        return self._api.proxies_list(page=page, page_size=page_size, search=search, ordering=ordering)

    @api_error_handler
    def get(self, proxy_id: str) -> Proxy:
        """Get proxy details."""
        return self._api.proxies_retrieve(proxy_id)

    @api_error_handler
    def create(
        self,
        *,
        host: str,
        port: int,
        proxy_type: str | None = None,
        proxy_mode: str | None = None,
        username: str | None = None,
        password: str | None = None,
        provider: str | None = None,
        country: str | None = None,
        region: str | None = None,
        city: str | None = None,
        status: str | None = None,
        is_active: bool | None = None,
        expires_at: str | None = None,
        max_concurrent_requests: int | None = None,
        requests_per_minute: int | None = None,
        cost_per_gb: str | None = None,
        monthly_cost: str | None = None,
        metadata: dict[str, Any] | None = None,
        config: dict[str, Any] | None = None,
    ) -> Proxy:
        """Create a new proxy."""
        request = ProxyRequest(
            host=host,
            port=port,
            proxy_type=coerce_proxy_type(proxy_type),
            proxy_mode=coerce_proxy_mode(proxy_mode),
            username=username,
            password=password,
            provider=provider,
            country=country,
            region=region,
            city=city,
            status=coerce_proxy_status(status),
            is_active=is_active,
            expires_at=expires_at,
            max_concurrent_requests=max_concurrent_requests,
            requests_per_minute=requests_per_minute,
            cost_per_gb=cost_per_gb,
            monthly_cost=monthly_cost,
            metadata=metadata,
            config=config,
        )
        return self._api.proxies_create(request)

    @api_error_handler
    def update(
        self,
        proxy_id: str,
        *,
        host: str | None = None,
        port: int | None = None,
        proxy_type: str | None = None,
        proxy_mode: str | None = None,
        username: str | None = None,
        password: str | None = None,
        provider: str | None = None,
        country: str | None = None,
        region: str | None = None,
        city: str | None = None,
        status: str | None = None,
        is_active: bool | None = None,
        expires_at: str | None = None,
        max_concurrent_requests: int | None = None,
        requests_per_minute: int | None = None,
        cost_per_gb: str | None = None,
        monthly_cost: str | None = None,
        metadata: dict[str, Any] | None = None,
        config: dict[str, Any] | None = None,
    ) -> Proxy:
        """Update a proxy (partial update)."""
        request = PatchedProxyRequest(
            host=host,
            port=port,
            proxy_type=coerce_proxy_type(proxy_type),
            proxy_mode=coerce_proxy_mode(proxy_mode),
            username=username,
            password=password,
            provider=provider,
            country=country,
            region=region,
            city=city,
            status=coerce_proxy_status(status),
            is_active=is_active,
            expires_at=expires_at,
            max_concurrent_requests=max_concurrent_requests,
            requests_per_minute=requests_per_minute,
            cost_per_gb=cost_per_gb,
            monthly_cost=monthly_cost,
            metadata=metadata,
            config=config,
        )
        return self._api.proxies_partial_update(proxy_id, request)

    @api_error_handler
    def delete(self, proxy_id: str) -> bool:
        """Delete a proxy."""
        self._api.proxies_destroy(proxy_id)
        return True

    @api_error_handler
    def get_healthy(self) -> list[Proxy]:
        """Get healthy proxies."""
        return self._api.proxies_healthy_retrieve()

    @api_error_handler
    def get_korean(self) -> list[Proxy]:
        """Get Korean proxies."""
        return self._api.proxies_korean_retrieve()

    @api_error_handler
    def get_by_country(self, country: str | None = None) -> list[Proxy]:
        """Get proxies by country."""
        return self._api.proxies_by_country_retrieve()

    @api_error_handler
    def get_performance_stats(self) -> dict[str, Any]:
        """Get overall performance statistics."""
        return self._api.proxies_performance_stats_retrieve()


class _AsyncProxiesMixin:
    """Async proxy CRUD methods."""

    _api: Any

    @async_api_error_handler
    async def list(
        self,
        *,
        page: int = 1,
        page_size: int = 20,
        search: str | None = None,
        ordering: str | None = None,
    ) -> PaginatedProxyList:
        """List proxies."""
        return await self._api.proxies_list(page=page, page_size=page_size, search=search, ordering=ordering)

    @async_api_error_handler
    async def get(self, proxy_id: str) -> Proxy:
        """Get proxy details."""
        return await self._api.proxies_retrieve(proxy_id)

    @async_api_error_handler
    async def create(
        self,
        *,
        host: str,
        port: int,
        proxy_type: str | None = None,
        proxy_mode: str | None = None,
        username: str | None = None,
        password: str | None = None,
        provider: str | None = None,
        country: str | None = None,
        region: str | None = None,
        city: str | None = None,
        status: str | None = None,
        is_active: bool | None = None,
        expires_at: str | None = None,
        max_concurrent_requests: int | None = None,
        requests_per_minute: int | None = None,
        cost_per_gb: str | None = None,
        monthly_cost: str | None = None,
        metadata: dict[str, Any] | None = None,
        config: dict[str, Any] | None = None,
    ) -> Proxy:
        """Create a new proxy."""
        request = ProxyRequest(
            host=host,
            port=port,
            proxy_type=coerce_proxy_type(proxy_type),
            proxy_mode=coerce_proxy_mode(proxy_mode),
            username=username,
            password=password,
            provider=provider,
            country=country,
            region=region,
            city=city,
            status=coerce_proxy_status(status),
            is_active=is_active,
            expires_at=expires_at,
            max_concurrent_requests=max_concurrent_requests,
            requests_per_minute=requests_per_minute,
            cost_per_gb=cost_per_gb,
            monthly_cost=monthly_cost,
            metadata=metadata,
            config=config,
        )
        return await self._api.proxies_create(request)

    @async_api_error_handler
    async def update(
        self,
        proxy_id: str,
        *,
        host: str | None = None,
        port: int | None = None,
        proxy_type: str | None = None,
        proxy_mode: str | None = None,
        username: str | None = None,
        password: str | None = None,
        provider: str | None = None,
        country: str | None = None,
        region: str | None = None,
        city: str | None = None,
        status: str | None = None,
        is_active: bool | None = None,
        expires_at: str | None = None,
        max_concurrent_requests: int | None = None,
        requests_per_minute: int | None = None,
        cost_per_gb: str | None = None,
        monthly_cost: str | None = None,
        metadata: dict[str, Any] | None = None,
        config: dict[str, Any] | None = None,
    ) -> Proxy:
        """Update a proxy (partial update)."""
        request = PatchedProxyRequest(
            host=host,
            port=port,
            proxy_type=coerce_proxy_type(proxy_type),
            proxy_mode=coerce_proxy_mode(proxy_mode),
            username=username,
            password=password,
            provider=provider,
            country=country,
            region=region,
            city=city,
            status=coerce_proxy_status(status),
            is_active=is_active,
            expires_at=expires_at,
            max_concurrent_requests=max_concurrent_requests,
            requests_per_minute=requests_per_minute,
            cost_per_gb=cost_per_gb,
            monthly_cost=monthly_cost,
            metadata=metadata,
            config=config,
        )
        return await self._api.proxies_partial_update(proxy_id, request)

    @async_api_error_handler
    async def delete(self, proxy_id: str) -> bool:
        """Delete a proxy."""
        await self._api.proxies_destroy(proxy_id)
        return True

    @async_api_error_handler
    async def get_healthy(self) -> list[Proxy]:
        """Get healthy proxies."""
        return await self._api.proxies_healthy_retrieve()

    @async_api_error_handler
    async def get_korean(self) -> list[Proxy]:
        """Get Korean proxies."""
        return await self._api.proxies_korean_retrieve()

    @async_api_error_handler
    async def get_by_country(self, country: str | None = None) -> list[Proxy]:
        """Get proxies by country."""
        return await self._api.proxies_by_country_retrieve()

    @async_api_error_handler
    async def get_performance_stats(self) -> dict[str, Any]:
        """Get overall performance statistics."""
        return await self._api.proxies_performance_stats_retrieve()
