from rest_framework import serializers


class TenantSerializer(serializers.Serializer):
    id_imobiliaria = serializers.IntegerField(required=False)
    nome = serializers.CharField(required=False, allow_blank=False, max_length=255)


class ActorSerializer(serializers.Serializer):
    id_usuario = serializers.IntegerField(required=False)
    tipo = serializers.CharField(required=False, allow_blank=False, max_length=64)
    nome = serializers.CharField(required=False, allow_blank=False, max_length=255)


class BusinessContextSerializer(serializers.Serializer):
    modulo = serializers.CharField(required=False, allow_blank=False, max_length=64)
    registro_id = serializers.IntegerField(required=False)
    codigo_externo = serializers.CharField(required=False, allow_blank=False, max_length=128)
    etapa = serializers.CharField(required=False, allow_blank=False, max_length=64)
    status = serializers.CharField(required=False, allow_blank=False, max_length=128)


class ConversationHistoryItemSerializer(serializers.Serializer):
    role = serializers.ChoiceField(choices=["user", "assistant", "system"])
    text = serializers.CharField(allow_blank=False, trim_whitespace=True)
    timestamp = serializers.DateTimeField(required=False)


class ConversationSerializer(serializers.Serializer):
    conversation_id = serializers.CharField(required=False, allow_blank=False, max_length=128)
    message_id = serializers.CharField(required=False, allow_blank=False, max_length=128)
    message = serializers.CharField(required=False, allow_blank=False, trim_whitespace=True)
    history = ConversationHistoryItemSerializer(required=False, many=True)


class OptionsSerializer(serializers.Serializer):
    stream = serializers.BooleanField(required=False)
    temperature = serializers.FloatField(required=False, min_value=0, max_value=2)
    max_tokens = serializers.IntegerField(required=False, min_value=1, max_value=4000)


class ChatMessageRequestSerializer(serializers.Serializer):
    request_id = serializers.CharField(required=False, allow_blank=False, max_length=128)
    source = serializers.CharField(required=False, allow_blank=False, max_length=64)
    tenant = TenantSerializer(required=False)
    actor = ActorSerializer(required=False)
    context = BusinessContextSerializer(required=False)
    conversation = ConversationSerializer(required=False)
    case_data = serializers.DictField(required=False)
    options = OptionsSerializer(required=False)
    message = serializers.CharField(required=False, allow_blank=False, trim_whitespace=True)
    conversation_id = serializers.CharField(required=False, allow_blank=False, max_length=128)

    def validate(self, attrs):
        message = attrs.get("message")
        conversation = attrs.get("conversation") or {}
        conversation_message = conversation.get("message")

        resolved_message = conversation_message or message
        if not resolved_message:
            raise serializers.ValidationError(
                {"message": "Either 'message' or 'conversation.message' must be provided."}
            )

        max_length = self.context["max_question_length"]
        if len(resolved_message) > max_length:
            raise serializers.ValidationError(
                f"Message exceeds maximum length of {max_length} characters."
            )

        attrs["message"] = resolved_message

        if "conversation_id" not in attrs and conversation.get("conversation_id"):
            attrs["conversation_id"] = conversation["conversation_id"]

        return attrs


class AnswerSerializer(serializers.Serializer):
    text = serializers.CharField()
    role = serializers.CharField()


class UsageSerializer(serializers.Serializer):
    input_tokens = serializers.IntegerField(required=False)
    output_tokens = serializers.IntegerField(required=False)


class ChatMessageResponseSerializer(serializers.Serializer):
    request_id = serializers.CharField()
    conversation_id = serializers.CharField()
    answer = serializers.SerializerMethodField()
    status = serializers.CharField()
    error = serializers.JSONField(allow_null=True)
    usage = serializers.SerializerMethodField()
    model = serializers.CharField()

    def get_answer(self, obj):
        return {"text": obj.answer_text, "role": "assistant"}

    def get_usage(self, obj):
        usage = getattr(obj, "usage", None)
        if not usage:
            return None

        return {key: value for key, value in usage.items() if value is not None}
