package com.qmth.themis.task.quartz;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.qmth.themis.business.bean.admin.ExamListBean;
import com.qmth.themis.business.cache.bean.ExamActivityCacheBean;
import com.qmth.themis.business.cache.bean.ExamCacheBean;
import com.qmth.themis.business.cache.bean.ExamStudentCacheBean;
import com.qmth.themis.business.constant.SystemConstant;
import com.qmth.themis.business.entity.TEExam;
import com.qmth.themis.business.entity.TEExamActivity;
import com.qmth.themis.business.entity.TOeExamRecord;
import com.qmth.themis.business.enums.ExamRecordStatusEnum;
import com.qmth.themis.business.enums.FinishTypeEnum;
import com.qmth.themis.business.enums.WebsocketStatusEnum;
import com.qmth.themis.business.service.*;
import com.qmth.themis.business.util.RedisUtil;
import org.quartz.JobExecutionContext;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.scheduling.quartz.QuartzJobBean;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @Description: 非强制交卷activity任务
 * @Param:
 * @return:
 * @Author: wangliang
 * @Date: 2020/9/22
 */
public class MqActivityJob extends QuartzJobBean {
    private final static Logger log = LoggerFactory.getLogger(MqActivityJob.class);

    @Resource
    TEExamService teExamService;

    @Resource
    TEExamActivityService teExamActivityService;

    @Resource
    TEExamStudentService teExamStudentService;

    @Resource
    TOeExamRecordService tOeExamRecordService;

    @Resource
    CommonService commonService;

    @Resource
    ThemisCacheService themisCacheService;

    @Resource
    RedisUtil redisUtil;

    /**
     * 每天凌晨定时任务
     *
     * @param context
     */
    @Override
    protected void executeInternal(JobExecutionContext context) {
        log.info("mq_activity_job进来了,context:{}", context);
//        //每天凌晨清理考试缓存数据
//        Map<String, List<ExamListBean>> examListMap = themisCacheService.getCurrentExamListCache();
//        if (!CollectionUtils.isEmpty(examListMap)) {
//            for (Map.Entry<String, List<ExamListBean>> entry : examListMap.entrySet()) {
//                Long examId = Long.parseLong(entry.getKey());
//                ExamCacheBean examCacheBean = teExamService.getExamCacheBean(examId);
//                if (examCacheBean.getEnable().intValue() == 0 || examCacheBean.getEndTime().longValue() <= System.currentTimeMillis()) {
//                    themisCacheService.removeCurrentExamListCache(entry.getKey());
//                    continue;
//                }
//                List<ExamListBean> examListBeanList = themisCacheService.getCurrentExamListCache(entry.getKey());
//                if (!CollectionUtils.isEmpty(examListBeanList)) {
//                    for (ExamListBean e : examListBeanList) {
//                        ExamActivityCacheBean examActivityCacheBean = teExamActivityService.getExamActivityCacheBean(e.getExamActivityId());
//                        if (examActivityCacheBean.getEnable().intValue() == 0 || examActivityCacheBean.getFinishTime().longValue() <= System.currentTimeMillis()) {
//                            themisCacheService.removeCurrentExamListCache(entry.getKey(), e.getExamActivityId());
//                        }
//                    }
//                } else {
//                    themisCacheService.removeCurrentExamListCache(entry.getKey());
//                }
//            }
//        }
        Long finishTime = System.currentTimeMillis();
        QueryWrapper<TEExam> teExamQueryWrapper = new QueryWrapper<>();
        teExamQueryWrapper.lambda().eq(TEExam::getEnable, 1)
                .le(TEExam::getEndTime, finishTime)
                .isNull(TEExam::getScanTime);
        List<TEExam> teExamList = teExamService.list(teExamQueryWrapper);
        if (Objects.nonNull(teExamList) && teExamList.size() > 0) {
            for (TEExam exam : teExamList) {
                QueryWrapper<TEExamActivity> teExamActivityQueryWrapper = new QueryWrapper<>();
                teExamActivityQueryWrapper.lambda().eq(TEExamActivity::getEnable, 1)
                        .eq(TEExamActivity::getExamId, exam.getId())
                        .le(TEExamActivity::getFinishTime, finishTime);
                List<TEExamActivity> teExamActivityList = teExamActivityService.list(teExamActivityQueryWrapper);
                if (Objects.nonNull(teExamActivityList) && teExamActivityList.size() > 0) {
                    Set<Long> examActivityIdSet = teExamActivityList.stream().map(s -> s.getId()).collect(Collectors.toSet());
                    QueryWrapper<TOeExamRecord> tOeExamRecordQueryWrapper = new QueryWrapper<>();
                    tOeExamRecordQueryWrapper.lambda().in(TOeExamRecord::getExamActivityId, examActivityIdSet);
                    List<TOeExamRecord> examRecordList = tOeExamRecordService.list(tOeExamRecordQueryWrapper);
                    Integer forceFinish = exam.getForceFinish();
                    if (Objects.nonNull(forceFinish) && forceFinish.intValue() == 1) {//强制收卷
                        if (!CollectionUtils.isEmpty(examRecordList)) {
                            List<TOeExamRecord> updateExamRecordList = new ArrayList<>(examRecordList.size() / 2);
                            examRecordList.forEach(s -> {
                                ExamRecordStatusEnum examRecordStatusEnum = s.getStatus();
                                //获取该考试批次下所有未交卷的考生的考试记录
                                if (Objects.nonNull(examRecordStatusEnum)
                                        && !Objects.equals(ExamRecordStatusEnum.FINISHED, examRecordStatusEnum)
                                        && !Objects.equals(ExamRecordStatusEnum.PERSISTED, examRecordStatusEnum)
                                        && !Objects.equals(ExamRecordStatusEnum.JUNK, examRecordStatusEnum)) {
                                    Integer durationSeconds = s.getDurationSeconds();
                                    Long examStudentId = s.getExamStudentId();
                                    ExamStudentCacheBean examStudentCacheBean = teExamStudentService.getExamStudentCacheBean(examStudentId);
                                    //候考阶段且没有进入考试则不交卷
                                    try {
                                        if (examRecordStatusEnum == ExamRecordStatusEnum.FIRST_PREPARE && Objects.isNull(s.getFirstStartTime())) {
                                            commonService.deleteExamStudentCache(s.getId(), examStudentCacheBean.getStudentId());
                                            s.setStatus(ExamRecordStatusEnum.JUNK);
                                            s.setUpdateTime(System.currentTimeMillis());
                                            if (Objects.nonNull(s.getClientWebsocketStatus()) && s.getClientWebsocketStatus() == WebsocketStatusEnum.ON_LINE) {
                                                s.setClientWebsocketStatus(WebsocketStatusEnum.OFF_LINE);
                                            }
                                            updateExamRecordList.add(s);
                                            commonService.dismissRoomByStrRoomId(s.getId());
                                        } else {//交卷
                                            teExamService.finish(examStudentCacheBean.getStudentId(), s.getId(), FinishTypeEnum.AUTO.name(), durationSeconds);
                                        }
                                        themisCacheService.removeExamSummaryAllCache(s.getExamId(), s.getExamActivityId(), examStudentCacheBean.getRoomCode());
                                    } catch (Exception e) {
                                        log.error(SystemConstant.LOG_ERROR, e);
                                    }
                                }
                            });
                            if (!CollectionUtils.isEmpty(updateExamRecordList)) {
                                tOeExamRecordService.updateBatchById(updateExamRecordList);
                            }
                        }
                    } else {
                        if (!CollectionUtils.isEmpty(examRecordList)) {
                            List<TOeExamRecord> updateExamRecordList = new ArrayList<>(examRecordList.size() / 2);
                            examRecordList.forEach(s -> {
                                ExamRecordStatusEnum examRecordStatusEnum = s.getStatus();
                                //获取该考试批次下所有未交卷的考生的考试记录
                                if (Objects.nonNull(examRecordStatusEnum)
                                        && !Objects.equals(ExamRecordStatusEnum.FINISHED, examRecordStatusEnum)
                                        && !Objects.equals(ExamRecordStatusEnum.PERSISTED, examRecordStatusEnum)
                                        && !Objects.equals(ExamRecordStatusEnum.ANSWERING, examRecordStatusEnum)
                                        && !Objects.equals(ExamRecordStatusEnum.JUNK, examRecordStatusEnum)) {
                                    Integer durationSeconds = s.getDurationSeconds();
                                    Long examStudentId = s.getExamStudentId();
                                    ExamStudentCacheBean examStudentCacheBean = teExamStudentService.getExamStudentCacheBean(examStudentId);
                                    //候考阶段且没有进入考试则不交卷
                                    try {
                                        if (examRecordStatusEnum == ExamRecordStatusEnum.FIRST_PREPARE && Objects.isNull(s.getFirstStartTime())) {
                                            commonService.deleteExamStudentCache(s.getId(), examStudentCacheBean.getStudentId());
                                            s.setStatus(ExamRecordStatusEnum.JUNK);
                                            s.setUpdateTime(System.currentTimeMillis());
                                            if (Objects.nonNull(s.getClientWebsocketStatus()) && s.getClientWebsocketStatus() == WebsocketStatusEnum.ON_LINE) {
                                                s.setClientWebsocketStatus(WebsocketStatusEnum.OFF_LINE);
                                            }
                                            updateExamRecordList.add(s);
                                            commonService.dismissRoomByStrRoomId(s.getId());
                                        } else {//交卷
                                            teExamService.finish(examStudentCacheBean.getStudentId(), s.getId(), FinishTypeEnum.AUTO.name(), durationSeconds);
                                        }
                                        themisCacheService.removeExamSummaryAllCache(s.getExamId(), s.getExamActivityId(), examStudentCacheBean.getRoomCode());
                                    } catch (Exception e) {
                                        log.error(SystemConstant.LOG_ERROR, e);
                                    }
                                }
                            });
                            if (!CollectionUtils.isEmpty(updateExamRecordList)) {
                                tOeExamRecordService.updateBatchById(updateExamRecordList);
                            }
                        }
                    }
                }
                exam.setScanTime(finishTime);
            }
            teExamService.saveOrUpdateBatch(teExamList);
        }
    }
}