import json
import threading
import uuid
from typing import Dict, Any, List

import requests

import dwai
from dwai.bailian.model_api.models import ChatQaMessage
_thread_context = threading.local()


class CompletionsRequestError(Exception):
    def __init__(self,
                 message=None,
                 status_code=None,
                 response_body=None
                 ):
        super(CompletionsRequestError, self).__init__(message)

        self.message = message
        self.status_code = status_code
        self.response_body = response_body

    def __str__(self):
        return "%s: status_code=%s, response_body=%s" % (
            self.message,
            self.status_code,
            self.response_body
        )

    def __repr__(self):
        return "(message=%r, status_code=%r, response_body=%r)" % (
            self.message,
            self.status_code,
            self.response_body
        )


class BaseCompletions:
    """ 调用百联进行文本生成 """

    @classmethod
    def call(cls, *args, **kwargs) -> Any:
        raise NotImplementedError()

    def reqeust(self, app_id: str,
                prompt: str,
                request_id: str = None,
                session_id: str = None,
                history: List[ChatQaMessage] = None,
                top_p: float = 0.0,
                biz_params: Dict = None,
                has_thoughts: bool = False,
                stream: bool = False,
                doc_reference_type: str = None):

        headers = dict()
        headers["Content-Type"] = "application/json;charset=UTF-8"
        headers["Authorization"] = "Bearer %s" % dwai.api_key

        if stream:
            headers["Accept"] = "text/event-stream"

        self.validate(app_id=app_id, prompt=prompt)

        if request_id is None:
            uuid_obj = uuid.uuid4()
            request_id = str(uuid_obj).replace('-', '')

        h = None
        if history is not None:
            h = []
            for v in history:
                h.append(v.to_dict())

        data = {
            "model": "qwen-plus-v1",
            "input": {
                "prompt": prompt,
                "history": []
            },
            "parameters": {
            }
        }

        url = "%s%s" % (dwai.api_base, "/bailian/services/aigc/text-generation/generation")
        session = self.__get_session()
        resp = session.request("POST",
                               url=url,
                               headers=headers,
                               data=json.dumps(data),
                               stream=stream)

        if not resp.ok:
            raise CompletionsRequestError("completion request error", resp.status_code, resp.text)

        return resp

    @staticmethod
    def __get_session() -> requests.Session:
        if not hasattr(_thread_context, "session"):
            _thread_context.session = requests.Session()

        return _thread_context.session

    @staticmethod
    def validate(app_id: str,
                 prompt: str):
        if dwai.api_base is None:
            dwai.api_base = "https://bailian.aliyuncs.com"

        if dwai.api_key is None:
            raise ValueError("you need to set DW_API_KEY before calling api")

        if app_id is None or app_id == '':
            raise ValueError("app id is required")

        if prompt is None or prompt == '':
            raise ValueError("prompt is required")



