import time
import threading
import json
from urllib.request import Request, urlopen
from openai import OpenAI
from .pricing import PRICING


def _compute_cost(model, prompt_tokens, completion_tokens):
    if model not in PRICING:
        return 0.0, True
    prices = PRICING[model]
    cost = (prompt_tokens * prices["input"] / 1_000_000) + (completion_tokens * prices["output"] / 1_000_000)
    return round(cost, 6), False


def _send_event(api_url, api_key, payload):
    try:
        data = json.dumps(payload).encode("utf-8")
        req = Request(
            f"{api_url}/api/v1/ingest",
            data=data,
            headers={
                "Authorization": f"Bearer {api_key}",
                "Content-Type": "application/json",
            },
            method="POST",
        )
        urlopen(req, timeout=5)
    except Exception as e:
        print(f"[spendlens] Warning: failed to send event: {e}")


class SpendLensClient:
    def __init__(self, api_key, api_url="https://spendlensdev-product-production.up.railway.app", **openai_kwargs):
        self._api_key = api_key
        self._api_url = api_url
        self._openai = OpenAI(**openai_kwargs)
        self.chat = _ChatNamespace(self)


class _ChatNamespace:
    def __init__(self, client):
        self._client = client
        self.completions = _CompletionsNamespace(client)


class _CompletionsNamespace:
    def __init__(self, client):
        self._client = client

    def create(self, **kwargs):
        tags = kwargs.pop("tags", kwargs.pop("costlens_tags", {}))
        start_time = time.time()

        response = self._client._openai.chat.completions.create(**kwargs)

        latency_ms = int((time.time() - start_time) * 1000)
        model = response.model
        prompt_tokens = response.usage.prompt_tokens
        completion_tokens = response.usage.completion_tokens
        total_tokens = response.usage.total_tokens
        cost_usd, unknown_model = _compute_cost(model, prompt_tokens, completion_tokens)

        payload = {
            "timestamp": time.strftime("%Y-%m-%dT%H:%M:%S.000Z", time.gmtime()),
            "model": model,
            "prompt_tokens": prompt_tokens,
            "completion_tokens": completion_tokens,
            "total_tokens": total_tokens,
            "cost_usd": cost_usd,
            "latency_ms": latency_ms,
            "status": "success",
            "tags": {
                "user_id": tags.get("user_id"),
                "feature": tags.get("feature"),
                "endpoint": tags.get("endpoint"),
            },
        }

        threading.Thread(
            target=_send_event,
            args=(self._client._api_url, self._client._api_key, payload),
            daemon=True,
        ).start()

        return response
