from __future__ import annotations

"""OpenAI LLM client implementation.

This module provides a production-ready OpenAI client that integrates with
the neuraparse LLM abstraction layer.
"""

import os
from dataclasses import dataclass, field
from typing import Any

try:
    import openai  # type: ignore[import-not-found]
except ImportError:  # pragma: no cover
    openai = None  # type: ignore[assignment]


@dataclass
class OpenAILLMClient:
    """OpenAI-based LLM client.

    Uses the OpenAI Python SDK to generate completions. API key is read from
    environment variable ``OPENAI_API_KEY`` by default.

    Args:
        model: OpenAI model name (e.g., "gpt-4", "gpt-3.5-turbo").
        api_key: Optional API key. If None, reads from OPENAI_API_KEY env var.
        temperature: Sampling temperature (0.0 to 2.0).
        max_tokens: Maximum tokens in the completion.
    """

    model: str = "gpt-3.5-turbo"
    api_key: str | None = None
    temperature: float = 0.7
    max_tokens: int = 1024
    _client: Any = field(init=False, repr=False, default=None)

    def __post_init__(self) -> None:
        """Initialize OpenAI client after dataclass initialization."""
        if openai is None:  # pragma: no cover
            raise RuntimeError(
                "OpenAI provider requires 'openai' package. "
                "Install it with: pip install openai"
            )

        api_key = self.api_key or os.getenv("OPENAI_API_KEY")
        if not api_key:
            raise ValueError(
                "OpenAI API key not provided. Set OPENAI_API_KEY environment "
                "variable or pass api_key parameter."
            )

        self._client = openai.OpenAI(api_key=api_key)

    def generate(self, prompt: str, **kwargs: Any) -> str:
        """Generate a completion for the given prompt.

        Args:
            prompt: Input prompt text.
            **kwargs: Optional overrides for temperature, max_tokens, etc.

        Returns:
            Generated completion text.
        """
        temperature = kwargs.get("temperature", self.temperature)
        max_tokens = kwargs.get("max_tokens", self.max_tokens)

        response = self._client.chat.completions.create(
            model=self.model,
            messages=[{"role": "user", "content": prompt}],
            temperature=temperature,
            max_tokens=max_tokens,
        )

        return response.choices[0].message.content or ""

