"""LM Studio LLM provider for Local Deep Research."""

from loguru import logger

from ...llm_registry import register_llm
from ..openai_base import OpenAICompatibleProvider


class LMStudioProvider(OpenAICompatibleProvider):
    """LM Studio provider using OpenAI-compatible endpoint.

    LM Studio provides a local OpenAI-compatible API for running models.
    """

    provider_name = "LM Studio"
    api_key_setting = None  # LM Studio doesn't need a real API key
    url_setting = "llm.lmstudio.url"  # Settings key for URL
    default_base_url = "http://localhost:1234/v1"
    default_model = "local-model"  # User should specify their loaded model

    # Metadata for auto-discovery
    provider_key = "LMSTUDIO"
    company_name = "LM Studio"
    region = "Local"
    country = "Local"
    data_location = "Local"
    is_cloud = False  # Local provider

    @classmethod
    def create_llm(cls, model_name=None, temperature=0.7, **kwargs):
        """Override to handle LM Studio specifics."""
        from ....config.thread_settings import get_setting_from_snapshot

        settings_snapshot = kwargs.get("settings_snapshot")

        # Get LM Studio URL from settings
        lmstudio_url = get_setting_from_snapshot(
            "llm.lmstudio.url",
            "http://localhost:1234",
            settings_snapshot=settings_snapshot,
        )

        # LM Studio uses /v1 endpoint
        kwargs["base_url"] = f"{lmstudio_url}/v1"

        # LM Studio doesn't require a real API key, just use a clearly fake placeholder
        kwargs["api_key"] = "not-required"  # pragma: allowlist secret

        # Use parent's create_llm but bypass API key check
        return super()._create_llm_instance(model_name, temperature, **kwargs)

    @classmethod
    def is_available(cls, settings_snapshot=None):
        """Check if LM Studio is available."""
        try:
            from ....config.thread_settings import get_setting_from_snapshot
            from ....security import safe_get

            lmstudio_url = get_setting_from_snapshot(
                "llm.lmstudio.url",
                "http://localhost:1234",
                settings_snapshot=settings_snapshot,
            )
            # LM Studio typically uses OpenAI-compatible endpoints
            response = safe_get(
                f"{lmstudio_url}/v1/models",
                timeout=1.0,
                allow_localhost=True,
                allow_private_ips=True,
            )
            return response.status_code == 200
        except Exception:
            return False

    @classmethod
    def requires_auth_for_models(cls):
        """LM Studio doesn't require authentication for listing models."""
        return False


# Keep the standalone functions for backward compatibility and registration
def create_lmstudio_llm(model_name=None, temperature=0.7, **kwargs):
    """Factory function for LM Studio LLMs.

    Args:
        model_name: Name of the model to use
        temperature: Model temperature (0.0-1.0)
        **kwargs: Additional arguments including settings_snapshot

    Returns:
        A configured ChatOpenAI instance pointing to LM Studio

    Raises:
        ValueError: If LM Studio is not available
    """
    return LMStudioProvider.create_llm(model_name, temperature, **kwargs)


def is_lmstudio_available(settings_snapshot=None):
    """Check if LM Studio is available.

    Args:
        settings_snapshot: Optional settings snapshot to use

    Returns:
        True if LM Studio is running, False otherwise
    """
    return LMStudioProvider.is_available(settings_snapshot)


def register_lmstudio_provider():
    """Register the LM Studio provider with the LLM registry."""
    register_llm("lmstudio", create_lmstudio_llm)
    logger.info("Registered LM Studio LLM provider")
