package com.emoon.tongue.service.impl;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.json.JSONUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.emoon.common.core.utils.StringUtils;
import com.emoon.tongue.domain.entity.TongueDiagnosis;
import com.emoon.tongue.domain.vo.*;
import com.emoon.tongue.mapper.TongueDiagnosisMapper;
import com.emoon.tongue.service.ITongueDiagnosisService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import java.time.LocalDateTime;
import java.util.Date;
import java.util.List;
import java.time.ZoneId;

/**
 * 舌诊任务Service业务层实现
 *
 * @author destiny
 * @date 2025-12-09
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class TongueDiagnosisServiceImpl implements ITongueDiagnosisService {

    private final TongueDiagnosisMapper baseMapper;

    /**
     * 根据患者ID和医院编码查询舌诊任务详情
     *
     * @param patientId 患者ID
     * @param projectId 医院编码
     * @return 舌诊任务详情
     */
    @Override
    public TongueDiagnosisDetailVo getDiagnosisDetail(String patientId, String projectId) {
        // 构造查询条件
        LambdaQueryWrapper<TongueDiagnosis> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(TongueDiagnosis::getPatientId, patientId);
        wrapper.eq(TongueDiagnosis::getProjectId, projectId);
        wrapper.eq(TongueDiagnosis::getDelFlag, "0"); // 未删除的数据

        // 查询数据
        TongueDiagnosis entity = baseMapper.selectOne(wrapper);

        // 如果没有找到数据，返回空对象
        if (entity == null) {
            TongueDiagnosisDetailVo detailVo = new TongueDiagnosisDetailVo();
            detailVo.setUploadStatus(0); // 未上传状态

            // 初始化患者信息
            PatientCoreInfo patientInfo = new PatientCoreInfo();
            patientInfo.setPatientId(patientId);
            detailVo.setPatientInfo(patientInfo);

            return detailVo;
        }

        // 转换为VO对象
        return convertToDetailVo(entity);
    }

    /**
     * 处理舌象上传
     *
     * @param imageUrl              图片URL
     * @param patientId             患者ID
     * @param projectId             医院编码
     * @param patientAge            患者年龄
     * @param patientGender         患者性别
     * @param patientChiefComplaint 患者主诉
     * @return 是否上传成功
     */
    @Override
    public boolean handleTongueImageUpload(String imageUrl, String imagePath, String patientId, String projectId,
                                           Integer patientAge, Integer patientGender, String patientChiefComplaint) {
        try {
            // 查询或创建舌诊任务记录
            LambdaQueryWrapper<TongueDiagnosis> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(TongueDiagnosis::getPatientId, patientId)
                .eq(TongueDiagnosis::getProjectId, projectId)
                .eq(TongueDiagnosis::getDelFlag, "0");

            List<TongueDiagnosis> tongueDiagnoses = baseMapper.selectList(queryWrapper);
            if (CollectionUtil.isEmpty(tongueDiagnoses)) {
                TongueDiagnosis tongueDiagnosis = TongueDiagnosis.builder()
                    .patientId(patientId)
                    .projectId(projectId)
                    .uploadStatus(1) // 已上传待推理
                    .imageUrl(imageUrl)
                    .imagePath(imagePath)
                    .uploadTime(LocalDateTime.now())
                    .patientAge(patientAge)
                    .patientGender(patientGender)
                    .patientChiefComplaint(patientChiefComplaint)
                    .build();
                // 设置父类字段，避免null值
                Date now = new Date();
                tongueDiagnosis.setCreateDept(-1L);
                tongueDiagnosis.setCreateBy(-1L);
                tongueDiagnosis.setCreateTime(now);
                tongueDiagnosis.setUpdateBy(-1L);
                tongueDiagnosis.setUpdateTime(now);
                baseMapper.insert(tongueDiagnosis);
            } else {
                // 更新舌诊任务状态
                TongueDiagnosis tongueDiagnosis = tongueDiagnoses.get(0);
                tongueDiagnosis.setUploadStatus(1); // 已上传待推理
                tongueDiagnosis.setImageUrl(imageUrl);
                tongueDiagnosis.setImagePath(imagePath);
                tongueDiagnosis.setUploadTime(LocalDateTime.now());
                tongueDiagnosis.setPatientAge(patientAge);
                tongueDiagnosis.setPatientGender(patientGender);
                tongueDiagnosis.setPatientChiefComplaint(patientChiefComplaint);
                baseMapper.updateById(tongueDiagnosis);
            }

            return true;
        } catch (Exception e) {
            log.error("处理舌象上传失败", e);
            return false;
        }
    }

    /**
     * 根据患者ID和医院编码获取记录主键ID
     *
     * @param patientId 患者ID
     * @param projectId 医院编码
     * @return 记录主键ID
     */
    @Override
    public Long getDiagnosisId(String patientId, String projectId) {
        LambdaQueryWrapper<TongueDiagnosis> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(TongueDiagnosis::getPatientId, patientId);
        wrapper.eq(TongueDiagnosis::getProjectId, projectId);
        wrapper.eq(TongueDiagnosis::getDelFlag, "0");

        TongueDiagnosis entity = baseMapper.selectOne(wrapper);
        return entity != null ? entity.getId() : null;
    }

    /**
     * 更新舌诊AI诊断结果
     *
     * @param id              记录主键ID
     * @param diagnosisResult 诊断结果JSON字符串
     * @return 是否成功
     */
    @Override
    public boolean updateAiDiagnosisResult(Long id, String diagnosisResult) {
        try {
            TongueDiagnosis entity = baseMapper.selectById(id);
            if (entity == null) {
                log.error("未找到舌诊记录，ID: {}", id);
                return false;
            }

            // 解析传入的诊断结果JSON
            TongueDiagnosisInfo diagnosisInfo;
            try {
                diagnosisInfo = JSONUtil.toBean(diagnosisResult, TongueDiagnosisInfo.class);
                log.info("成功解析AI诊断结果: {}", diagnosisInfo.getTongueGeneralDesc());
            } catch (Exception e) {
                log.error("解析AI诊断结果JSON失败，使用mock结果作为fallback: {}", diagnosisResult, e);
                diagnosisInfo = TongueDiagnosisInfo.generateMockResult();
            }

            // 更新诊断结果和状态
            entity.setUploadStatus(2); // 推理完成
            entity.setTongueDiagnosisInfo(diagnosisInfo);
            entity.setInferFinishTime(LocalDateTime.now());

            int result = baseMapper.updateById(entity);
            log.info("舌诊诊断结果已更新，任务ID: {}", id);
            return result > 0;
        } catch (Exception e) {
            log.error("更新AI诊断结果失败，ID: {}", id, e);
            return false;
        }
    }

    /**
     * 将实体对象转换为详情VO对象
     *
     * @param entity 实体对象
     * @return 详情VO对象
     */
    private TongueDiagnosisDetailVo convertToDetailVo(TongueDiagnosis entity) {
        TongueDiagnosisDetailVo detailVo = new TongueDiagnosisDetailVo();

        // 设置上传状态
        detailVo.setUploadStatus(entity.getUploadStatus());

        // 设置推理完成时间
        detailVo.setInferFinishTime(entity.getInferFinishTime());

        // 设置患者信息
        PatientCoreInfo patientInfo = new PatientCoreInfo();
        patientInfo.setPatientId(entity.getPatientId());
        patientInfo.setPatientAge(entity.getPatientAge());
        patientInfo.setPatientGender(entity.getPatientGender());
        patientInfo.setPatientChiefComplaint(entity.getPatientChiefComplaint());
        detailVo.setPatientInfo(patientInfo);

        // 如果已上传，则设置舌象照片信息
        if (entity.getUploadStatus() >= 1
            && (StringUtils.isNotEmpty(entity.getImageUrl()) || StringUtils.isNotEmpty(entity.getImagePath()))) {
            TongueImageInfo tongueImage = new TongueImageInfo();
            tongueImage.setUrl(entity.getImageUrl());
            tongueImage.setPath(entity.getImagePath());
            tongueImage.setUploadTime(entity.getUploadTime());
            detailVo.setTongueImage(tongueImage);
        }

        // 如果诊断完成，则设置诊断结果
        if (entity.getUploadStatus() == 2 && entity.getTongueDiagnosisInfo() != null) {
            detailVo.setDiagnosisInfo(entity.getTongueDiagnosisInfo());
        }

        return detailVo;
    }
}
