package cn.iocoder.yudao.module.llm.service.dataset;

import cn.iocoder.yudao.module.llm.controller.admin.dataset.vo.*;
import cn.iocoder.yudao.module.llm.dal.dataobject.dataset.DatasetAnswerDO;
import cn.iocoder.yudao.module.llm.dal.dataobject.dataset.DatasetQuestionDO;
import cn.iocoder.yudao.module.llm.dal.mysql.dataset.DatasetAnswerMapper;
import cn.iocoder.yudao.module.llm.dal.mysql.dataset.DatasetMapper;
import cn.iocoder.yudao.module.llm.dal.mysql.dataset.DatasetQuestionMapper;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import jodd.util.StringUtil;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import org.springframework.validation.annotation.Validated;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;
import java.util.stream.Collectors;

import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.pojo.PageParam;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;


import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
import static cn.iocoder.yudao.module.llm.enums.ErrorCodeConstants.*;

/**
 * 数据集数据问题 Service 实现类
 *
 * @author 华大大模型
 */
@Service
@Validated
public class DatasetQuestionServiceImpl implements DatasetQuestionService {

    @Resource
    private DatasetQuestionMapper datasetQuestionMapper;
    @Resource
    private DatasetAnswerMapper datasetAnswerMapper;
    @Resource
    private DatasetMapper datasetMapper;

    @Override
    public Long createDatasetQuestion(DatasetQuestionSaveReqVO createReqVO) {
        // 插入
        DatasetQuestionDO datasetQuestion = BeanUtils.toBean(createReqVO, DatasetQuestionDO.class);
        datasetQuestionMapper.insert(datasetQuestion);
        // 返回
        return datasetQuestion.getId();
    }

    @Override
    public void updateDatasetQuestion(DatasetQuestionSaveReqVO updateReqVO) {
        // 校验存在
        validateDatasetQuestionExists(updateReqVO.getId());
        // 更新
        DatasetQuestionDO updateObj = BeanUtils.toBean(updateReqVO, DatasetQuestionDO.class);
        datasetQuestionMapper.updateById(updateObj);
    }

    @Override
    public void deleteDatasetQuestion(Long id) {
        // 校验存在
        validateDatasetQuestionExists(id);
        // 删除
        datasetQuestionMapper.deleteById(id);
    }

    private void validateDatasetQuestionExists(Long id) {
        if (datasetQuestionMapper.selectById(id) == null) {
            throw exception(DATASET_QUESTION_NOT_EXISTS);
        }
    }

    @Override
    public DatasetQuestionDO getDatasetQuestion(Long id) {
        return datasetQuestionMapper.selectById(id);
    }

    @Override
    public PageResult<DatasetQuestionRespVO> getDatasetQuestionPage(DatasetQuestionPageReqVO pageReqVO) {
        PageResult<DatasetQuestionDO> datasetQuestionDOPageResult = datasetQuestionMapper.selectPage(pageReqVO);
        PageResult<DatasetQuestionRespVO> result = BeanUtils.toBean(datasetQuestionDOPageResult, DatasetQuestionRespVO.class);
        if (CollectionUtils.isNotEmpty(result.getList())){
            result.getList().forEach(item -> {
                List<DatasetAnswerDO> datasetAnswerDOS = datasetAnswerMapper.selectList(new LambdaQueryWrapper<>(DatasetAnswerDO.class)
                        .eq(DatasetAnswerDO::getQuestionId, item.getId()));
                item.setDatasetAnswerRespVO(BeanUtils.toBean(datasetAnswerDOS, DatasetAnswerRespVO.class));

            });
        }
        return result;
    }

    /**
     * 获得 数据集数据问题 列表
     *
     * @param datasetId 数据集ID
     * @return 数据集数据问题 列表
     */
    @Override
    public List<DatasetQuestionRespVO> getDatasetQuestionList(Long datasetId) {
        List<DatasetQuestionDO> datasetQuestionDOS = datasetQuestionMapper.selectList(new LambdaQueryWrapper<>(DatasetQuestionDO.class)
                .eq(DatasetQuestionDO::getDatasetId, datasetId));
        List<DatasetQuestionRespVO> result = BeanUtils.toBean(datasetQuestionDOS, DatasetQuestionRespVO.class);
        if (CollectionUtils.isNotEmpty(result)) {
            result.forEach(item -> {
                List<DatasetAnswerDO> datasetAnswerDOS = datasetAnswerMapper.selectList(new LambdaQueryWrapper<>(DatasetAnswerDO.class)
                        .eq(DatasetAnswerDO::getQuestionId, item.getId()));
                item.setDatasetAnswerRespVO(BeanUtils.toBean(datasetAnswerDOS, DatasetAnswerRespVO.class));
            });
        }
        return result;
    }

    @Override
    public void updateDatasetQuestionDataAnno(List<DatasetQuestionSaveReqVO> updateReqVOS) {
        List<Long> ids = new ArrayList<>();
        Long datasetId = null;
        for (DatasetQuestionSaveReqVO updateReqVO : updateReqVOS){
            if (datasetId == null){
                datasetId = updateReqVO.getDatasetId();
            }
            DatasetQuestionDO datasetQuestionDO =  BeanUtils.toBean(updateReqVO, DatasetQuestionDO.class);

            List<DatasetAnswerSaveReqVO> datasetAnswerSaveReqVO = updateReqVO.getDatasetAnswerRespVO();
            List<DatasetAnswerDO> datasetAnswerDOS = BeanUtils.toBean(datasetAnswerSaveReqVO, DatasetAnswerDO.class);
            if (CollectionUtils.isNotEmpty(datasetAnswerDOS)){
                for (DatasetAnswerDO datasetAnswerDO : datasetAnswerDOS){
                    if (StringUtil.isNotBlank(datasetAnswerDO.getAnswer())){
                        datasetQuestionDO.setStatus(2);
                    }
                    if (datasetAnswerDO.getId() == null){
                        datasetAnswerMapper.insert(datasetAnswerDO);
                        ids.add(datasetAnswerDO.getId());
                    }else {
                        ids.add(datasetAnswerDO.getId());
                        datasetAnswerMapper.updateById(datasetAnswerDO);
                    }
                }
//                datasetAnswerMapper.insertOrUpdate(datasetAnswerDOS);
            }
            datasetQuestionMapper.updateById(datasetQuestionDO);
        }
        List<Long> collect1 = updateReqVOS.stream().map(DatasetQuestionSaveReqVO::getId).collect(Collectors.toList());
        LambdaQueryWrapper<DatasetAnswerDO> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.in(collect1!= null,DatasetAnswerDO::getQuestionId, collect1);
        List<DatasetAnswerDO> datasetAnswerDOS = datasetAnswerMapper.selectList(queryWrapper);
        List<Long> collect = datasetAnswerDOS.stream().map(DatasetAnswerDO::getId).collect(Collectors.toList());
        List<Long> diff1 = new ArrayList<>();
        if (CollectionUtils.isNotEmpty(collect)){
            HashSet<Long> set1 = new HashSet<>(ids);
            HashSet<Long> set2 = new HashSet<>(collect);
            // 获取 set2 中有但 set1 中没有的元素
            set2.removeAll(set1);
            diff1 = new ArrayList<>(set2);
        }
        if (CollectionUtils.isNotEmpty(diff1)){
            datasetAnswerMapper.deleteBatchIds(diff1);
        }
        // 标注进度修改
        LambdaQueryWrapper<DatasetQuestionDO> wrapper =  new LambdaQueryWrapper<DatasetQuestionDO>()
                .eq(DatasetQuestionDO::getDatasetId, updateReqVOS.get(0).getDatasetId());
        Long sumCount = datasetQuestionMapper.selectCount(wrapper);
        wrapper.eq(DatasetQuestionDO::getStatus,2);
        Long annoCount = datasetQuestionMapper.selectCount(wrapper);
        double ratio = sumCount == 0 ? 0 : ((double) annoCount / sumCount) *100;
        Integer formattedRatio = ratio == 0 ? 0 : (int) ratio;
        Integer status = formattedRatio == 100 ? 2 : 1;
        datasetMapper.updateProcess(formattedRatio, updateReqVOS.get(0).getDatasetId(),status);
    }

}
