#!/usr/bin/env python
# @Project ：django_base_ai
# @File    : ai_desk_app_manage.py
# @Author  : cx
# @Time    : 11/2/2025
# @Desc    : 员工服务（AI 工作台应用）管理：列表/坐席/认领会话/转人工/关闭会话等。

import logging

from django.core.cache import cache
from rest_framework.decorators import action
from rest_framework.permissions import IsAuthenticated

from django_base_ai.system.models import (
    AIDeskAppManage,
    CoreBaseAuth,
    IMChatRecordForm,
    IMChatToGroup,
    IMChatToGroupMessage,
    IMSession,
)
from django_base_ai.utils.format_core_base_auth import get_auth_user_info
from django_base_ai.utils.json_response import DetailResponse, ErrorResponse
from django_base_ai.utils.serializers import CustomModelSerializer
from django_base_ai.utils.viewset import CustomModelViewSet
from django_base_ai.websocket.websocket_config import websocket_push

logger = logging.getLogger(__name__)


# ---------- Serializer ----------
class AIDeskAppManageSerializer(CustomModelSerializer):
    """列表/详情用。"""
    class Meta:
        model = AIDeskAppManage
        fields = "__all__"
        read_only_fields = ["id"]


class AIDeskAppManageCreateUpdateSerializer(CustomModelSerializer):
    """创建/更新用。"""
    class Meta:
        model = AIDeskAppManage
        fields = "__all__"


class AIDeskAppManageViewSet(CustomModelViewSet):
    """
    员工服务管理（AI 工作台应用）。
    list/retrieve: 查询；create/update/destroy: 增删改。
    action: desks=获取当前用户可见的员工服务列表；seat_info=坐席信息；claim=认领会话；transfer_to_service=转人工；close_claim=关闭会话。
    """

    queryset = AIDeskAppManage.objects.all()
    serializer_class = AIDeskAppManageSerializer
    create_serializer_class = AIDeskAppManageCreateUpdateSerializer
    update_serializer_class = AIDeskAppManageCreateUpdateSerializer
    search_fields = ["name"]

    @action(methods=["GET"], detail=False, permission_classes=[IsAuthenticated])
    def desks(self, request, *args, **kwargs):
        """当前用户可见的员工服务列表，含未读消息数、最近一条消息缓存等。"""
        current_user = request.user
        # 可选：按部门/标签做可见性过滤，当前为全部
        list(current_user.tags_set.all().values_list("id", flat=True))
        ai_desk_app_manage_result = AIDeskAppManage.objects.filter().all()
        result = []
        logger.debug("desks 用户 %s 可见应用数 %d", current_user.username, ai_desk_app_manage_result.count())
        for item in ai_desk_app_manage_result:
            im_session = (
                IMSession.objects.filter(ai_desk_app_manage=item, creator=current_user.id, is_colse=False)
                .order_by("-id")
                .first()
            )
            im_session_id = im_session.parent.session_id if im_session and im_session.parent else None
            un_msg_count = IMChatToGroupMessage.objects.filter(
                im_chat_to_group__im_session__session_id=im_session_id, from_to_user=self.request.user, is_read=True
            ).count()
            result.append(
                {
                    "id": item.id,
                    "name": item.name,
                    "alias": item.alias,
                    "email": item.email,
                    "mobile": item.mobile,
                    "landline": item.landline,
                    "avatar": item.avatar,
                    "welcome_essage": item.welcome_message,
                    "recommended_questions": item.recommended_questions,
                    "human_services": item.human_services,
                    "im_session": im_session_id,
                    "last_message": cache.get(f"{im_session_id}_{current_user.id}", {}) if im_session else {},
                    "un_read_count": un_msg_count,
                }
            )
        return DetailResponse(data=result, msg="成功")

    @action(methods=["get"], detail=False, permission_classes=[IsAuthenticated])
    def seat_info(self, request, *args, **kwargs):
        """根据应用 id(nid) 返回该员工服务配置的坐席信息（CoreBaseAuth.target_data）。"""
        nid = request.GET.get("nid", 0)
        if not nid:
            return ErrorResponse(msg="参数不合法")
        ai_desk_app_manage = AIDeskAppManage.objects.filter(id=nid).first()
        if not ai_desk_app_manage:
            logger.warning("seat_info 应用不存在 nid=%s", nid)
            return ErrorResponse(msg="应用不存在")
        if not ai_desk_app_manage.seats:
            return DetailResponse(msg="未设置人工坐席")
        seats_id = ai_desk_app_manage.seats.get("nid", 0)
        django_base_ai_auth = CoreBaseAuth.objects.filter(id=seats_id).first()
        if not django_base_ai_auth:
            return DetailResponse(data=[])
        return DetailResponse(django_base_ai_auth.target_data)

    @action(methods=["post"], detail=False)
    def claim(self, request, *args, **kwargs):
        """坐席认领会话：将未认领的会话标记为当前坐席已认领（is_claim=2）。"""
        im_session = request.data.get("im_session", 0)
        if not im_session:
            return ErrorResponse(msg="参数不合法")
        request.data.get("tid", 0)
        session = IMSession.objects.filter(session_id=im_session).first()
        if not session:
            return ErrorResponse(msg="认领失败")
        user_ids = get_auth_user_info(session.ai_desk_app_manage.seats.get("nid", 0))
        IMSession.objects.filter(session_id=im_session).exclude(from_user__id__in=user_ids).update(is_claim=2)
        logger.info("认领会话 im_session=%s 坐席数=%d", im_session, len(user_ids))
        return DetailResponse(msg="认领成功")

    @action(methods=["post"], detail=False, permission_classes=[IsAuthenticated])
    def transfer_to_service(self, request, *args, **kwargs):
        """转人工：用户从某员工服务(tid)发起，创建或复用 IMSession，并拉取坐席到群组。"""
        tid = request.data.get("tid", 0)
        nid = request.data.get("nid", 0)
        if not tid:
            return ErrorResponse(msg="参数不合法")
        ai_desk_app_manage = AIDeskAppManage.objects.filter(id=tid).first()
        if not ai_desk_app_manage:
            return ErrorResponse(msg="您无权限查看,或应用不存在")
        current_user = request.user
        im_session = IMSession.objects.filter(
            from_user=current_user,
            ai_desk_app_manage_id=tid,
            session_type=True,
            creator=current_user.id,
            is_colse=False,
        ).first()
        if not im_session:
            im_session = IMSession.objects.create(
                from_user=current_user,
                ai_desk_app_manage_id=tid,
                session_type=True,
                creator=current_user.id,
                modifier=current_user.id,
            )
            im_chat_to_group = IMChatToGroup.objects.create(
                im_session=im_session, name=current_user.name, group_ext_info={current_user.id: nid}
            )
            im_chat_to_group.group_admins.add(current_user.id)
            user_ids = get_auth_user_info(ai_desk_app_manage.seats.get("nid", 0))
            im_session_list = []
            for user_id in user_ids:
                im_session_list.append(
                    IMSession(
                        parent=im_session,
                        from_user_id=user_id,
                        ai_desk_app_manage_id=tid,
                        session_type=True,
                        creator=user_id,
                        modifier=user_id,
                    )
                )
            IMSession.objects.bulk_create(im_session_list)
            im_chat_to_group.from_many_to_user.set(user_ids)
            im_chat_to_group.save()
            logger.info("转人工创建新会话 tid=%s user=%s im_session_id=%s", tid, current_user.username, im_session.session_id)
        im_session_id = im_session.parent.session_id if im_session and im_session.parent else im_session.session_id
        return DetailResponse(msg="创建成功", data=im_session_id)

    @action(methods=["post"], detail=False)
    def close_claim(self, request, *args, **kwargs):
        """关闭会话：标记会话及子会话已关闭，可选推送满意度问卷（WebSocket）。"""
        current_user = request.user
        im_session = request.data.get("im_session", 0)
        if not im_session:
            return ErrorResponse(msg="参数不合法")
        im_session_obj = IMSession.objects.filter(session_id=im_session).first()
        if not im_session_obj:
            return ErrorResponse(msg="您无权访问")
        IMSession.objects.filter(parent=im_session_obj).update(is_colse=True)
        im_session_obj.is_colse = True
        im_session_obj.save()
        logger.info("关闭会话 im_session=%s user=%s", im_session, current_user.username)
        ai_desk_app_manage = im_session_obj.ai_desk_app_manage
        room_name = f"{im_session_obj.creator}_{cache.get(im_session_obj.creator, 0)}"
        im_chat_to_group = IMChatToGroup.objects.filter(im_session=im_session_obj).first()
        if ai_desk_app_manage and ai_desk_app_manage.dissatisfied_switch:
            close_info = {
                "title": "您对本次服务是否满意?",
                "im_session": im_session,
                "info": [
                    {
                        "title": "满意",
                        "type": 1,
                        "icon": "/media/assets/satisfied.png",
                        "sub_title": [{"sort": 0, "label": "满意"}],
                    },
                    {
                        "title": "一般",
                        "type": 2,
                        "icon": "/media/assets/average.png",
                        "sub_title": [{"sort": 0, "label": "一般"}],
                    },
                    {
                        "title": "不满意",
                        "type": 3,
                        "icon": "/media/assets/dissatisfied.png",
                        "sub_title": ai_desk_app_manage.dissatisfied if ai_desk_app_manage else None,
                    },
                ],
            }
            IMChatToGroupMessage.objects.create(
                im_chat_to_group=im_chat_to_group,
                from_user_id=im_session_obj.creator,
                is_read=False,
                from_to_user_id=im_session_obj.creator,
                content={"data": close_info, "type": "close_claim"},
                creator=current_user.id,
                modifier=current_user.id,
            )
            websocket_push(
                room_name,
                message={
                    "create_datetime": im_session_obj.create_datetime.strftime("%Y-%m-%d %H:%M:%S"),
                    "content": {"data": {"nid": 1, "data": close_info, "type": "close_claim"}},
                },
            )
        IMChatRecordForm.objects.update_or_create(
            defaults={"im_session": im_session_obj, "creator": current_user.id, "modifier": current_user.id},
            im_session=im_session_obj,
        )
        return DetailResponse(msg="已结束")
