package com.ningdatech.carapi.archives.manage;

import cn.hutool.core.collection.CollectionUtil;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.ningdatech.basic.exception.BizException;
import com.ningdatech.basic.model.PageVo;
import com.ningdatech.carapi.archives.assembler.QuestionAssembler;
import com.ningdatech.carapi.archives.entity.PaperQuestion;
import com.ningdatech.carapi.archives.enums.PaperQuestionStatusEnum;
import com.ningdatech.carapi.archives.model.JudgmentalQuestionTextContent;
import com.ningdatech.carapi.archives.model.MultipleChoiceQuestionTextContent;
import com.ningdatech.carapi.archives.model.SingleChoiceQuestionTextContent;
import com.ningdatech.carapi.archives.model.po.ReqQuestionListPO;
import com.ningdatech.carapi.archives.model.po.ReqSaveNewQuestionPO;
import com.ningdatech.carapi.archives.model.vo.ResQuestionDetailVO;
import com.ningdatech.carapi.archives.model.vo.ResQuestionListVO;
import com.ningdatech.carapi.archives.service.IPaperQuestionService;
import com.ningdatech.carapi.common.helper.UserInfoHelper;
import com.ningdatech.carapi.driver.constant.QuestionTypeEnum;
import com.ningdatech.carapi.sys.helper.RegionsCacheHelper;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Component;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;

/**
 * @author liuxinxin
 * @date 2022/10/11 下午4:28
 */
@Component
@RequiredArgsConstructor
public class PaperQuestionManage {

    private final IPaperQuestionService iPaperQuestionService;
    private final RegionsCacheHelper regionsCacheHelper;
    private final UserInfoHelper userInfoHelper;

    public PageVo<ResQuestionListVO> questionList(ReqQuestionListPO request) {
        Integer pageNumber = request.getPageNumber();
        Integer pageSize = request.getPageSize();
        LambdaQueryWrapper<PaperQuestion> wrapper = Wrappers.lambdaQuery(PaperQuestion.class);
        buildQuestionQuery(wrapper, request);
        Page<PaperQuestion> page = iPaperQuestionService.page(new Page<>(pageNumber, pageSize),wrapper);
        List<PaperQuestion> records = page.getRecords();
        long total = page.getTotal();

        PageVo<ResQuestionListVO> pageVo = new PageVo<>();
        pageVo.setTotal(total);
        if (total == 0) {
            return pageVo;
        }
        List<ResQuestionListVO> resQuestionListVOList = records.stream().map(r -> {
            ResQuestionListVO resQuestionListVO = new ResQuestionListVO();
            resQuestionListVO.setId(r.getId());
            resQuestionListVO.setQuestion(r.getStem());
            resQuestionListVO.setQuestionType(QuestionTypeEnum.valueOf(r.getQuestionType()));
            resQuestionListVO.setUsageCnt(r.getUsageCnt());
            resQuestionListVO.setFormulationTime(r.getCreateOn());
            return resQuestionListVO;
        }).collect(Collectors.toList());
        pageVo.setRecords(resQuestionListVOList);
        return pageVo;
    }

    //@LambdaDataScope
    private void buildQuestionQuery(LambdaQueryWrapper<PaperQuestion> wrapper, ReqQuestionListPO request) {
        // 获取入参信息
        String question = request.getQuestion();
        QuestionTypeEnum questionType = request.getQuestionType();
        Long regionId = request.getRegionId();
        // 入参转换参数
        String questionTypeStr = Objects.isNull(questionType) ? null : questionType.name();
        List<Long> regionIdList = new ArrayList<>();
        if (Objects.nonNull(regionId)) {
            regionIdList = regionsCacheHelper.listChildRegionId(regionId);
        }
        wrapper.eq(Objects.nonNull(questionType), PaperQuestion::getQuestionType, questionTypeStr)
            .eq(PaperQuestion::getQuestionStatus, PaperQuestionStatusEnum.IN_USE.name())
            .in(CollectionUtil.isNotEmpty(regionIdList), PaperQuestion::getRegionId, regionIdList)
            .like(StringUtils.isNotBlank(question), PaperQuestion::getQuestionTextContent, question);
    }

    public ResQuestionDetailVO questionDetail(Long questionId) {
        PaperQuestion paperQuestion = iPaperQuestionService.getById(questionId);
        if (Objects.isNull(paperQuestion)) {
            return null;
        }
        return QuestionAssembler.buildResQuestionDetailVO(paperQuestion);
    }

    public void createNewQuestion(ReqSaveNewQuestionPO po) {
        QuestionTypeEnum questionType = po.getQuestionType();
        PaperQuestion paperQuestion = new PaperQuestion();

        String stem = po.getStem();
        String questionTextContent = null;
        String correctJsonStr = null;
        switch (questionType) {
            case JUDGMENTAL:
                JudgmentalQuestionTextContent judgmentalQuestionTextContent = new JudgmentalQuestionTextContent();
                judgmentalQuestionTextContent.setStem(stem);
                judgmentalQuestionTextContent.setAnswer(po.getJudgmentalQuestionCorrectAnswer());
                questionTextContent = JSONObject.toJSONString(judgmentalQuestionTextContent);
                correctJsonStr = JSONObject.toJSONString(po.getJudgmentalQuestionCorrectAnswer());
                break;
            case SINGLE_CHOICE:
                SingleChoiceQuestionTextContent singleChoiceQuestionTextContent = new SingleChoiceQuestionTextContent();
                singleChoiceQuestionTextContent.setStem(stem);
                singleChoiceQuestionTextContent.setOptions(po.getOptions());
                singleChoiceQuestionTextContent.setAnswer(po.getChoiceQuestionCorrectAnswer().get(0));
                questionTextContent = JSONObject.toJSONString(singleChoiceQuestionTextContent);
                correctJsonStr = JSONObject.toJSONString(po.getChoiceQuestionCorrectAnswer().get(0));

                break;
            case MULTIPLE_CHOICE:
                MultipleChoiceQuestionTextContent multipleChoiceQuestionTextContent = new MultipleChoiceQuestionTextContent();
                multipleChoiceQuestionTextContent.setStem(stem);
                multipleChoiceQuestionTextContent.setOptions(po.getOptions());
                multipleChoiceQuestionTextContent.setAnswer(po.getChoiceQuestionCorrectAnswer());
                questionTextContent = JSONObject.toJSONString(multipleChoiceQuestionTextContent);
                correctJsonStr = JSONObject.toJSONString(po.getChoiceQuestionCorrectAnswer());
                break;
            default:
                break;
        }

        paperQuestion.setCreateOn(LocalDateTime.now());
        paperQuestion.setUpdateOn(LocalDateTime.now());
        paperQuestion.setStem(stem);
        paperQuestion.setCorrect(correctJsonStr);
        paperQuestion.setQuestionStatus(PaperQuestionStatusEnum.IN_USE.name());
        paperQuestion.setQuestionTextContent(questionTextContent);
        paperQuestion.setQuestionType(questionType.name());
        paperQuestion.setUsageCnt(0L);
        paperQuestion.setRegionId(userInfoHelper.getUserRegionId());
        iPaperQuestionService.save(paperQuestion);
    }

    public void saveQuestion(ReqSaveNewQuestionPO request) {
        Long id = request.getId();
        if (Objects.nonNull(id)) {
            PaperQuestion currentPaperQuestion = iPaperQuestionService.getById(id);
            if (Objects.isNull(currentPaperQuestion)) {
                throw new BizException("试题不存在");
            }
            assemblerQuestionSaveRecord(currentPaperQuestion, request);
            iPaperQuestionService.updateById(currentPaperQuestion);

        } else {
            PaperQuestion paperQuestion = new PaperQuestion();
            assemblerQuestionSaveRecord(paperQuestion, request);
            paperQuestion.setCreateOn(LocalDateTime.now());
            paperQuestion.setQuestionStatus(PaperQuestionStatusEnum.IN_USE.name());
            paperQuestion.setUsageCnt(0L);
            paperQuestion.setRegionId(userInfoHelper.getUserRegionId());
            iPaperQuestionService.save(paperQuestion);
        }
    }

    private void assemblerQuestionSaveRecord(PaperQuestion saveRecord, ReqSaveNewQuestionPO request) {
        QuestionTypeEnum questionType = request.getQuestionType();
        String stem = request.getStem();
        String questionTextContent = null;
        String correctJsonStr = null;
        switch (questionType) {
            case JUDGMENTAL:
                JudgmentalQuestionTextContent judgmentalQuestionTextContent = new JudgmentalQuestionTextContent();
                judgmentalQuestionTextContent.setStem(stem);
                judgmentalQuestionTextContent.setAnswer(request.getJudgmentalQuestionCorrectAnswer());
                questionTextContent = JSONObject.toJSONString(judgmentalQuestionTextContent);
                correctJsonStr = JSONObject.toJSONString(request.getJudgmentalQuestionCorrectAnswer());
                break;
            case SINGLE_CHOICE:
                SingleChoiceQuestionTextContent singleChoiceQuestionTextContent = new SingleChoiceQuestionTextContent();
                singleChoiceQuestionTextContent.setStem(stem);
                singleChoiceQuestionTextContent.setOptions(request.getOptions());
                singleChoiceQuestionTextContent.setAnswer(request.getChoiceQuestionCorrectAnswer().get(0));
                questionTextContent = JSONObject.toJSONString(singleChoiceQuestionTextContent);
                correctJsonStr = JSONObject.toJSONString(request.getChoiceQuestionCorrectAnswer().get(0));

                break;
            case MULTIPLE_CHOICE:
                MultipleChoiceQuestionTextContent multipleChoiceQuestionTextContent = new MultipleChoiceQuestionTextContent();
                multipleChoiceQuestionTextContent.setStem(stem);
                multipleChoiceQuestionTextContent.setOptions(request.getOptions());
                multipleChoiceQuestionTextContent.setAnswer(request.getChoiceQuestionCorrectAnswer());
                questionTextContent = JSONObject.toJSONString(multipleChoiceQuestionTextContent);
                correctJsonStr = JSONObject.toJSONString(request.getChoiceQuestionCorrectAnswer());
                break;
            default:
                break;
        }
        saveRecord.setUpdateOn(LocalDateTime.now());
        saveRecord.setStem(stem);
        saveRecord.setCorrect(correctJsonStr);
        saveRecord.setQuestionTextContent(questionTextContent);
        saveRecord.setQuestionType(questionType.name());
    }

    public void deleteQuestion(Long id) {
        PaperQuestion paperQuestion = iPaperQuestionService.getById(id);
        if (paperQuestion.getUsageCnt() > 0) {
            throw new BizException("试题已被使用无法删除");
        }
        iPaperQuestionService.removeById(id);
    }
}
