|
@@ -1,14 +1,49 @@
|
|
package com.qmth.themis.business.service.impl;
|
|
package com.qmth.themis.business.service.impl;
|
|
|
|
|
|
|
|
+import java.io.File;
|
|
|
|
+import java.math.BigDecimal;
|
|
|
|
+import java.text.SimpleDateFormat;
|
|
|
|
+import java.time.LocalDateTime;
|
|
|
|
+import java.time.ZoneOffset;
|
|
|
|
+import java.util.Date;
|
|
|
|
+import java.util.HashMap;
|
|
|
|
+import java.util.List;
|
|
|
|
+import java.util.Map;
|
|
|
|
+import java.util.Objects;
|
|
|
|
+import java.util.UUID;
|
|
|
|
+
|
|
|
|
+import javax.annotation.Resource;
|
|
|
|
+
|
|
|
|
+import org.apache.commons.lang3.StringUtils;
|
|
|
|
+import org.slf4j.Logger;
|
|
|
|
+import org.slf4j.LoggerFactory;
|
|
|
|
+import org.springframework.beans.BeanUtils;
|
|
|
|
+import org.springframework.stereotype.Service;
|
|
|
|
+import org.springframework.transaction.annotation.Transactional;
|
|
|
|
+
|
|
import com.alibaba.fastjson.JSONArray;
|
|
import com.alibaba.fastjson.JSONArray;
|
|
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
|
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
|
import com.baomidou.mybatisplus.core.metadata.IPage;
|
|
import com.baomidou.mybatisplus.core.metadata.IPage;
|
|
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
|
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
|
-import com.qmth.themis.business.bean.backend.*;
|
|
|
|
|
|
+import com.qmth.themis.business.bean.backend.InvigilateListBean;
|
|
|
|
+import com.qmth.themis.business.bean.backend.InvigilateListHistoryBean;
|
|
|
|
+import com.qmth.themis.business.bean.backend.InvigilateListPatrolBean;
|
|
|
|
+import com.qmth.themis.business.bean.backend.InvigilateListProgressBean;
|
|
|
|
+import com.qmth.themis.business.bean.backend.InvigilateListProgressExcelBean;
|
|
|
|
+import com.qmth.themis.business.bean.backend.InvigilateListVideoBean;
|
|
|
|
+import com.qmth.themis.business.bean.backend.InvigilateListWarningBean;
|
|
|
|
+import com.qmth.themis.business.bean.backend.OpenRecordNeedMarkBean;
|
|
import com.qmth.themis.business.cache.ExamActivityRecordCacheUtil;
|
|
import com.qmth.themis.business.cache.ExamActivityRecordCacheUtil;
|
|
import com.qmth.themis.business.cache.ExamRecordCacheUtil;
|
|
import com.qmth.themis.business.cache.ExamRecordCacheUtil;
|
|
import com.qmth.themis.business.cache.RedisKeyHelper;
|
|
import com.qmth.themis.business.cache.RedisKeyHelper;
|
|
-import com.qmth.themis.business.cache.bean.*;
|
|
|
|
|
|
+import com.qmth.themis.business.cache.bean.ExamActivityCacheBean;
|
|
|
|
+import com.qmth.themis.business.cache.bean.ExamActivityRecordCacheBean;
|
|
|
|
+import com.qmth.themis.business.cache.bean.ExamCacheBean;
|
|
|
|
+import com.qmth.themis.business.cache.bean.ExamPaperCacheBean;
|
|
|
|
+import com.qmth.themis.business.cache.bean.ExamStudentAnswerCacheBean;
|
|
|
|
+import com.qmth.themis.business.cache.bean.ExamStudentCacheBean;
|
|
|
|
+import com.qmth.themis.business.cache.bean.ExamStudentPaperStructCacheBean;
|
|
|
|
+import com.qmth.themis.business.cache.bean.ObjectiveAnswerCacheBean;
|
|
import com.qmth.themis.business.config.SystemConfig;
|
|
import com.qmth.themis.business.config.SystemConfig;
|
|
import com.qmth.themis.business.constant.SpringContextHolder;
|
|
import com.qmth.themis.business.constant.SpringContextHolder;
|
|
import com.qmth.themis.business.constant.SystemConstant;
|
|
import com.qmth.themis.business.constant.SystemConstant;
|
|
@@ -18,25 +53,29 @@ import com.qmth.themis.business.dto.response.MarkResultDto;
|
|
import com.qmth.themis.business.dto.response.TEExamUnFinishDto;
|
|
import com.qmth.themis.business.dto.response.TEExamUnFinishDto;
|
|
import com.qmth.themis.business.entity.TOeExamAnswer;
|
|
import com.qmth.themis.business.entity.TOeExamAnswer;
|
|
import com.qmth.themis.business.entity.TOeExamRecord;
|
|
import com.qmth.themis.business.entity.TOeExamRecord;
|
|
-import com.qmth.themis.business.enums.*;
|
|
|
|
-import com.qmth.themis.business.service.*;
|
|
|
|
|
|
+import com.qmth.themis.business.enums.ExamRecordFieldEnum;
|
|
|
|
+import com.qmth.themis.business.enums.ExamRecordStatusEnum;
|
|
|
|
+import com.qmth.themis.business.enums.ExamTypeEnum;
|
|
|
|
+import com.qmth.themis.business.enums.ExceptionEnum;
|
|
|
|
+import com.qmth.themis.business.enums.FinishTypeEnum;
|
|
|
|
+import com.qmth.themis.business.enums.LivenessTypeEnum;
|
|
|
|
+import com.qmth.themis.business.enums.MqTagEnum;
|
|
|
|
+import com.qmth.themis.business.enums.MqTopicEnum;
|
|
|
|
+import com.qmth.themis.business.enums.ObjectiveScorePolicyEnum;
|
|
|
|
+import com.qmth.themis.business.enums.RecordSelectStrategyEnum;
|
|
|
|
+import com.qmth.themis.business.enums.VerifyExceptionEnum;
|
|
|
|
+import com.qmth.themis.business.service.MqDtoService;
|
|
|
|
+import com.qmth.themis.business.service.TEExamActivityService;
|
|
|
|
+import com.qmth.themis.business.service.TEExamPaperService;
|
|
|
|
+import com.qmth.themis.business.service.TEExamService;
|
|
|
|
+import com.qmth.themis.business.service.TEExamStudentService;
|
|
|
|
+import com.qmth.themis.business.service.TOeExamAnswerService;
|
|
|
|
+import com.qmth.themis.business.service.TOeExamRecordService;
|
|
import com.qmth.themis.business.util.OssUtil;
|
|
import com.qmth.themis.business.util.OssUtil;
|
|
import com.qmth.themis.business.util.RedisUtil;
|
|
import com.qmth.themis.business.util.RedisUtil;
|
|
import com.qmth.themis.common.contanst.Constants;
|
|
import com.qmth.themis.common.contanst.Constants;
|
|
import com.qmth.themis.common.util.FileUtil;
|
|
import com.qmth.themis.common.util.FileUtil;
|
|
import com.qmth.themis.common.util.SimpleBeanUtil;
|
|
import com.qmth.themis.common.util.SimpleBeanUtil;
|
|
-import org.apache.commons.lang3.StringUtils;
|
|
|
|
-import org.slf4j.Logger;
|
|
|
|
-import org.slf4j.LoggerFactory;
|
|
|
|
-import org.springframework.beans.BeanUtils;
|
|
|
|
-import org.springframework.stereotype.Service;
|
|
|
|
-import org.springframework.transaction.annotation.Transactional;
|
|
|
|
-
|
|
|
|
-import javax.annotation.Resource;
|
|
|
|
-import java.io.File;
|
|
|
|
-import java.math.BigDecimal;
|
|
|
|
-import java.text.SimpleDateFormat;
|
|
|
|
-import java.util.*;
|
|
|
|
|
|
|
|
/**
|
|
/**
|
|
* @Description: 考试记录 服务实现类
|
|
* @Description: 考试记录 服务实现类
|
|
@@ -177,34 +216,34 @@ public class TOeExamRecordServiceImpl extends ServiceImpl<TOeExamRecordMapper, T
|
|
ExamStudentAnswerCacheBean answer = (ExamStudentAnswerCacheBean) redisUtil.get(
|
|
ExamStudentAnswerCacheBean answer = (ExamStudentAnswerCacheBean) redisUtil.get(
|
|
RedisKeyHelper.examAnswerKey(recordId), key);
|
|
RedisKeyHelper.examAnswerKey(recordId), key);
|
|
if (answer == null) {
|
|
if (answer == null) {
|
|
- log.error("no ExamStudentAnswerCacheBean for calculateObjectiveScore key:" + key);
|
|
|
|
|
|
+ log.error("no ExamStudentAnswerCacheBean for calculateObjectiveScore recordId:"+recordId+" key:" + key);
|
|
|
|
|
|
// 计算客观分总分
|
|
// 计算客观分总分
|
|
- calculateTotalObjectiveScore(recordId);
|
|
|
|
|
|
+ calculateTotalObjectiveScore(param);
|
|
return;
|
|
return;
|
|
}
|
|
}
|
|
//整卷客观题标答缓存集合
|
|
//整卷客观题标答缓存集合
|
|
Map<String, ObjectiveAnswerCacheBean> map = examPaperService.getObjectiveAnswerCacheBean(paperId);
|
|
Map<String, ObjectiveAnswerCacheBean> map = examPaperService.getObjectiveAnswerCacheBean(paperId);
|
|
if (map == null || map.size() == 0) {
|
|
if (map == null || map.size() == 0) {
|
|
- log.debug("no ObjectiveAnswerCacheBean map for calculateObjectiveScore paperId:" + paperId);
|
|
|
|
|
|
+ log.info("no ObjectiveAnswerCacheBean map for calculateObjectiveScore recordId:"+recordId+" paperId:" + paperId);
|
|
// 更新分数
|
|
// 更新分数
|
|
answer.setScore(0.0);
|
|
answer.setScore(0.0);
|
|
redisUtil.set(RedisKeyHelper.examAnswerKey(recordId), key, answer);
|
|
redisUtil.set(RedisKeyHelper.examAnswerKey(recordId), key, answer);
|
|
|
|
|
|
// 计算客观分总分
|
|
// 计算客观分总分
|
|
- calculateTotalObjectiveScore(recordId);
|
|
|
|
|
|
+ calculateTotalObjectiveScore(param);
|
|
return;
|
|
return;
|
|
}
|
|
}
|
|
//客观题标答缓存
|
|
//客观题标答缓存
|
|
ObjectiveAnswerCacheBean cb = map.get(key);
|
|
ObjectiveAnswerCacheBean cb = map.get(key);
|
|
if (cb == null) {
|
|
if (cb == null) {
|
|
- log.debug("no ObjectiveAnswerCacheBean for calculateObjectiveScore key:" + key);
|
|
|
|
|
|
+ log.info("no ObjectiveAnswerCacheBean for calculateObjectiveScore recordId:"+recordId+" key:" + key);
|
|
// 更新分数
|
|
// 更新分数
|
|
answer.setScore(0.0);
|
|
answer.setScore(0.0);
|
|
redisUtil.set(RedisKeyHelper.examAnswerKey(recordId), key, answer);
|
|
redisUtil.set(RedisKeyHelper.examAnswerKey(recordId), key, answer);
|
|
|
|
|
|
// 计算客观分总分
|
|
// 计算客观分总分
|
|
- calculateTotalObjectiveScore(recordId);
|
|
|
|
|
|
+ calculateTotalObjectiveScore(param);
|
|
return;
|
|
return;
|
|
}
|
|
}
|
|
|
|
|
|
@@ -251,18 +290,22 @@ public class TOeExamRecordServiceImpl extends ServiceImpl<TOeExamRecordMapper, T
|
|
}
|
|
}
|
|
|
|
|
|
if (answer.getScore() == null) {
|
|
if (answer.getScore() == null) {
|
|
- log.debug("小题分数为空,得分置为0," + "recordId:" + recordId + " questionKey:" + key);
|
|
|
|
|
|
+ log.info("小题分数为空,得分置为0," + "recordId:" + recordId + " questionKey:" + key);
|
|
answer.setScore(0.0);
|
|
answer.setScore(0.0);
|
|
}
|
|
}
|
|
// 更新分数
|
|
// 更新分数
|
|
redisUtil.set(RedisKeyHelper.examAnswerKey(recordId), key, answer);
|
|
redisUtil.set(RedisKeyHelper.examAnswerKey(recordId), key, answer);
|
|
|
|
|
|
// 计算客观分总分
|
|
// 计算客观分总分
|
|
- calculateTotalObjectiveScore(recordId);
|
|
|
|
|
|
+ calculateTotalObjectiveScore(param);
|
|
}
|
|
}
|
|
|
|
|
|
@SuppressWarnings("unchecked")
|
|
@SuppressWarnings("unchecked")
|
|
- private void calculateTotalObjectiveScore(Long recordId) {
|
|
|
|
|
|
+ private void calculateTotalObjectiveScore(Map<String, Object> param) {
|
|
|
|
+ Long recordId = (Long) param.get("recordId");
|
|
|
|
+ Integer mainNumber = (Integer) param.get("mainNumber");
|
|
|
|
+ Integer subNumber = (Integer) param.get("subNumber");
|
|
|
|
+ Integer subIndex = (Integer) param.get("subIndex");
|
|
String lockKey = SystemConstant.REDIS_LOCK_TOTAL_OBJECTIVE_SCORE_PREFIX + recordId;
|
|
String lockKey = SystemConstant.REDIS_LOCK_TOTAL_OBJECTIVE_SCORE_PREFIX + recordId;
|
|
try {
|
|
try {
|
|
Boolean lock = redisUtil.lock(lockKey, SystemConstant.REDIS_CACHE_TIME_OUT);
|
|
Boolean lock = redisUtil.lock(lockKey, SystemConstant.REDIS_CACHE_TIME_OUT);
|
|
@@ -284,11 +327,34 @@ public class TOeExamRecordServiceImpl extends ServiceImpl<TOeExamRecordMapper, T
|
|
ExamRecordCacheUtil.setObjectiveScore(recordId, total, true);
|
|
ExamRecordCacheUtil.setObjectiveScore(recordId, total, true);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
+ }else {
|
|
|
|
+ calculateObjectiveScoreMsg(recordId, mainNumber, subNumber, subIndex);
|
|
}
|
|
}
|
|
} finally {
|
|
} finally {
|
|
redisUtil.releaseLock(lockKey);
|
|
redisUtil.releaseLock(lockKey);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
+
|
|
|
|
+ //考试中计算客观分消息
|
|
|
|
+ private void calculateObjectiveScoreMsg(Long recordId, Integer mainNumber, Integer subNumber, Integer subIndex) {
|
|
|
|
+ Map<String, Object> transMap = new HashMap<String, Object>();
|
|
|
|
+ transMap.put("recordId", recordId);
|
|
|
|
+ transMap.put("mainNumber", mainNumber);
|
|
|
|
+ transMap.put("subNumber", subNumber);
|
|
|
|
+ transMap.put("subIndex", subIndex);
|
|
|
|
+
|
|
|
|
+ String level = "1s";
|
|
|
|
+ Integer time = SystemConstant.mqDelayLevel.get(level);
|
|
|
|
+ LocalDateTime dt = LocalDateTime.now();
|
|
|
|
+ dt = dt.plusSeconds(Long.parseLong(level.replace("s", "")));
|
|
|
|
+ Map<String, Object> propMap = new HashMap<String, Object>();
|
|
|
|
+ propMap.put("timeOut", time);
|
|
|
|
+ propMap.put("mqExecTime", dt.toInstant(ZoneOffset.of("+8")).toEpochMilli());
|
|
|
|
+ MqDto mqDto = new MqDto(MqTopicEnum.THEMIS_TOPIC.getCode(), MqTagEnum.CALCULATE_OBJECTIVE_SCORE.name(),
|
|
|
|
+ transMap, MqTagEnum.CALCULATE_OBJECTIVE_SCORE, recordId.toString(), propMap, recordId.toString());
|
|
|
|
+
|
|
|
|
+ mqDtoService.assembleSendAsyncDelayMsg(mqDto);
|
|
|
|
+ }
|
|
|
|
|
|
private boolean checkSingleChoice(String answerArray, JSONArray ar) {
|
|
private boolean checkSingleChoice(String answerArray, JSONArray ar) {
|
|
JSONArray an = JSONArray.parseArray(answerArray);
|
|
JSONArray an = JSONArray.parseArray(answerArray);
|
|
@@ -718,14 +784,14 @@ public class TOeExamRecordServiceImpl extends ServiceImpl<TOeExamRecordMapper, T
|
|
|
|
|
|
Map<String, ObjectiveAnswerCacheBean> map = examPaperService.getObjectiveAnswerCacheBean(rec.getPaperId());
|
|
Map<String, ObjectiveAnswerCacheBean> map = examPaperService.getObjectiveAnswerCacheBean(rec.getPaperId());
|
|
if (map == null || map.size() == 0) {
|
|
if (map == null || map.size() == 0) {
|
|
- log.debug("no ObjectiveAnswerCacheBean for calculateObjectiveScore recordId:" + recordId);
|
|
|
|
|
|
+ log.info("no ObjectiveAnswerCacheBean for calculateObjectiveScore recordId:" + recordId);
|
|
return;
|
|
return;
|
|
}
|
|
}
|
|
QueryWrapper<TOeExamAnswer> wp = new QueryWrapper<>();
|
|
QueryWrapper<TOeExamAnswer> wp = new QueryWrapper<>();
|
|
wp.lambda().eq(TOeExamAnswer::getExamRecordId, recordId);
|
|
wp.lambda().eq(TOeExamAnswer::getExamRecordId, recordId);
|
|
List<TOeExamAnswer> answers = examAnswerService.list(wp);
|
|
List<TOeExamAnswer> answers = examAnswerService.list(wp);
|
|
if (answers == null || answers.size() == 0) {
|
|
if (answers == null || answers.size() == 0) {
|
|
- log.debug("no ObjectiveAnswer for calculateObjectiveScore recordId:" + recordId);
|
|
|
|
|
|
+ log.info("no ObjectiveAnswer for calculateObjectiveScore recordId:" + recordId);
|
|
return;
|
|
return;
|
|
}
|
|
}
|
|
BigDecimal tatolscore = new BigDecimal(0.0);
|
|
BigDecimal tatolscore = new BigDecimal(0.0);
|
|
@@ -748,7 +814,7 @@ public class TOeExamRecordServiceImpl extends ServiceImpl<TOeExamRecordMapper, T
|
|
String key = RedisKeyHelper.examAnswerHashKey(mainNumber, subNumber, subIndex);
|
|
String key = RedisKeyHelper.examAnswerHashKey(mainNumber, subNumber, subIndex);
|
|
ObjectiveAnswerCacheBean cb = map.get(key);
|
|
ObjectiveAnswerCacheBean cb = map.get(key);
|
|
if (cb == null) {
|
|
if (cb == null) {
|
|
- log.debug("not a objective question recordId:" + answer.getExamRecordId() + " key:" + key);
|
|
|
|
|
|
+ log.info("not a objective question recordId:" + answer.getExamRecordId() + " key:" + key);
|
|
return null;
|
|
return null;
|
|
}
|
|
}
|
|
|
|
|