【新增】 监控管理导出Excel

This commit is contained in:
dlaren
2025-08-20 14:54:54 +08:00
parent f8055670bd
commit c37b1b54be
14 changed files with 422 additions and 176 deletions

View File

@@ -10,6 +10,7 @@ import io.swagger.v3.oas.annotations.Operation;
import jakarta.validation.*;
import jakarta.servlet.http.*;
import java.math.BigDecimal;
import java.util.*;
import java.io.IOException;
@@ -31,7 +32,9 @@ import pc.exam.pp.module.exam.controller.admin.monitor.vo.*;
import pc.exam.pp.module.exam.dal.dataobject.EducationPaperTask;
import pc.exam.pp.module.exam.dal.dataobject.monitor.MonitorDO;
import pc.exam.pp.module.exam.dal.dataobject.student.StuPaperFileDO;
import pc.exam.pp.module.exam.dal.dataobject.student.StuPaperScoreDO;
import pc.exam.pp.module.exam.service.monitor.MonitorService;
import pc.exam.pp.module.exam.service.stuPaperScore.StuPaperScoreService;
import pc.exam.pp.module.exam.service.stu_paper_file.StuPaperFileService;
import static pc.exam.pp.module.infra.enums.ErrorCodeConstants.DEMO03_MONITOR_SESSION_EXISTS;
@@ -46,6 +49,8 @@ public class MonitorController {
private MonitorService monitorService;
@Resource
StuPaperFileService stuPaperFileService;
@Resource
StuPaperScoreService stuPaperScoreService;
@PostMapping("/create")
@Operation(summary = "创建监控管理")
@@ -89,9 +94,76 @@ public class MonitorController {
public void exportMonitorExcel(@Valid MonitorPageReqVO pageReqVO, HttpServletResponse response) throws IOException {
pageReqVO.setPageSize(PageParam.PAGE_SIZE_NONE);
List<MonitorDO> list = monitorService.getMonitorPage(pageReqVO).getList();
List<List<String>> stuPaperScoreHead = new ArrayList<>();
// 数据
List<List<Object>> stuPaperScoreData = new ArrayList<>();
List<List<String>> stuPaperScoreAllHead = new ArrayList<>();
// 数据
List<List<Object>> stuPaperScoreAllData = new ArrayList<>();
// 获取对应的答卷情况
for (MonitorDO monitor : list) {
// 获取试卷任务
String temporaryId = monitor.getTemporaryId();
String stuId = monitor.getStuId();
List<StuPaperScoreDO> stuPaperScoreDOS = stuPaperScoreService.findByStuIDAndTemporaryId(Long.parseLong(stuId), temporaryId);
if (stuPaperScoreHead.isEmpty()) {
stuPaperScoreHead.add(List.of("考号"));
stuPaperScoreHead.add(List.of("姓名"));
stuPaperScoreHead.add(List.of("学号"));
for (StuPaperScoreDO stuPaperScoreDO : stuPaperScoreDOS) {
String quName = stuPaperScoreDO.getSubjectName() + "(" + stuPaperScoreDO.getSort() + ")";
stuPaperScoreHead.add(List.of(quName));
}
}
// 创建一个空的数组对象 存放已经存在的试题分类
List<String> existingSubjects = new ArrayList<>();
if (stuPaperScoreAllHead.isEmpty()) {
stuPaperScoreAllHead.add(List.of("考号"));
stuPaperScoreAllHead.add(List.of("姓名"));
stuPaperScoreAllHead.add(List.of("学号"));
stuPaperScoreAllHead.add(List.of("成绩"));
for (StuPaperScoreDO stuPaperScoreDO : stuPaperScoreDOS) {
String quName = stuPaperScoreDO.getSubjectName();
if (!existingSubjects.contains(quName)) {
existingSubjects.add(quName);
stuPaperScoreAllHead.add(List.of(quName));
}
}
}
List<Object> row = new ArrayList<>();
row.add(monitor.getUsername()); // 考号
row.add(monitor.getNickname()); // 姓名
row.add(monitor.getStuId()); // 学号
for (StuPaperScoreDO stuPaperScoreDO : stuPaperScoreDOS) {
row.add(stuPaperScoreDO.getScore().toString());
}
stuPaperScoreData.add(row);
List<Object> rowAllData = new ArrayList<>();
rowAllData.add(monitor.getUsername()); // 考号
rowAllData.add(monitor.getNickname()); // 姓名
rowAllData.add(monitor.getStuId()); // 学号
rowAllData.add(monitor.getScore()); // 成绩
// 根据学生ID临时ID题型获取这个题型的总得分
for (String existingSubject : existingSubjects) {
final BigDecimal[] totalScore = {BigDecimal.ZERO};
stuPaperScoreService.findByStuIDAndTemporaryIdAndSubName(Long.parseLong(stuId), temporaryId, existingSubject)
.forEach(stuPaperScoreDO -> {
totalScore[0] = totalScore[0].add(stuPaperScoreDO.getScore());
});
rowAllData.add(totalScore[0]);
}
stuPaperScoreAllData.add(rowAllData);
}
// 导出 Excel
ExcelUtils.write(response, "监控管理.xls", "数据", MonitorRespVO.class,
BeanUtils.toBean(list, MonitorRespVO.class));
List<MonitorRespVO> s1 = BeanUtils.toBean(list, MonitorRespVO.class);
ExcelUtils.writeMulti(response, "考生信息.xls", List.of(
ExcelUtils.SheetSpec.ofBean("学生信息", MonitorRespVO.class, s1),
ExcelUtils.SheetSpec.ofDynamic("试题分数", stuPaperScoreHead, stuPaperScoreData),
ExcelUtils.SheetSpec.ofDynamic("题型分数", stuPaperScoreAllHead, stuPaperScoreAllData)));
// ExcelUtils.write(response, "考生信息.xls", "学生信息", MonitorRespVO.class,
// BeanUtils.toBean(list, MonitorRespVO.class));
}
@PostMapping("/stuMonitor")

View File

@@ -10,6 +10,8 @@ import org.springframework.format.annotation.DateTimeFormat;
import java.time.LocalDateTime;
import com.alibaba.excel.annotation.*;
import pc.exam.pp.module.exam.controller.admin.monitor.vo.converter.ExamStatusConverter;
import pc.exam.pp.module.exam.controller.admin.monitor.vo.converter.SecondsToTimeConverter;
@Schema(description = "管理后台 - 监控管理 Response VO")
@Data
@@ -27,36 +29,26 @@ public class MonitorRespVO {
@ExcelProperty("班级")
private String className;
@ExcelProperty("考试状态")
@ExcelProperty(value = "考试状态", converter = ExamStatusConverter.class)
private String examStatus;
@Schema(description = "成绩")
@ExcelProperty("成绩")
private String score;
@Schema(description = "试卷编号")
@ExcelProperty("试卷编号")
private String paperNum;
@Schema(description = "任务名称")
@ExcelProperty("任务名称")
private String taskName;
@Schema(description = "任务类别")
@ExcelProperty("任务类别")
private String taskType;
@Schema(description = "机器ip")
@ExcelProperty("机器ip")
private String ip;
private String temporaryId;
@Schema(description = "剩余时间")
@ExcelProperty("剩余时间")
@ExcelProperty(value = "剩余时间", converter = SecondsToTimeConverter.class)
private String remainingTime;
@Schema(description = "创建时间")
@ExcelProperty("创建时间")
private LocalDateTime createTime;

View File

@@ -0,0 +1,21 @@
package pc.exam.pp.module.exam.controller.admin.monitor.vo.converter;
import com.alibaba.excel.metadata.GlobalConfiguration;
import com.alibaba.excel.metadata.data.WriteCellData;
import com.alibaba.excel.converters.Converter;
import com.alibaba.excel.metadata.property.ExcelContentProperty;
public class ExamStatusConverter implements Converter<String> {
@Override public Class<String> supportJavaTypeKey() { return String.class; }
@Override
public WriteCellData<?> convertToExcelData(String value, ExcelContentProperty prop, GlobalConfiguration conf) {
if (value == null) return new WriteCellData<>("");
switch (value) {
case "0": return new WriteCellData<>("待考");
case "1": return new WriteCellData<>("考试中");
case "2": return new WriteCellData<>("已结束");
default: return new WriteCellData<>("未知");
}
}
}

View File

@@ -0,0 +1,31 @@
package pc.exam.pp.module.exam.controller.admin.monitor.vo.converter;
import com.alibaba.excel.metadata.GlobalConfiguration;
import com.alibaba.excel.metadata.data.WriteCellData;
import com.alibaba.excel.converters.Converter;
import com.alibaba.excel.metadata.property.ExcelContentProperty;
public class SecondsToTimeConverter implements Converter<String> {
@Override
public Class<?> supportJavaTypeKey() {
return String.class; // 你的字段类型是 String
}
@Override
public WriteCellData<?> convertToExcelData(String value, ExcelContentProperty prop, GlobalConfiguration conf) {
if (value == null || value.isEmpty()) {
return new WriteCellData<>("");
}
try {
int seconds = Integer.parseInt(value);
int h = seconds / 3600;
int m = (seconds % 3600) / 60;
int s = seconds % 60;
String time = String.format("%02d:%02d:%02d", h, m, s);
return new WriteCellData<>(time);
} catch (NumberFormatException e) {
return new WriteCellData<>(value); // 如果不是数字,就原样输出
}
}
}

View File

@@ -19,6 +19,7 @@ import pc.exam.pp.module.exam.service.paper.IEducationPaperPersonService;
import static pc.exam.pp.module.infra.enums.ErrorCodeConstants.DEMO03_PAPER_SESSION_EXISTS;
import static pc.exam.pp.module.infra.enums.ErrorCodeConstants.DEMO03_PAPER_STUDENT_EXISTS;
import java.util.List;
/**
@@ -30,21 +31,20 @@ import java.util.List;
@Tag(name = "管理后台 - 试卷人员分配")
@RestController
@RequestMapping("/exam/person")
public class EducationPaperPersonController
{
public class EducationPaperPersonController {
@Autowired
private IEducationPaperPersonService educationPaperPersonService;
// @Autowired
// @Autowired
// private IExamStuService examStuService;
@Autowired
private IEducationPaperParamService educationPaperParamService;
/**
* 查询试卷人员分配列表
*/
@Operation(summary = "查询试卷人员分配列表")
@GetMapping("/list")
public CommonResult list(EducationPaperPerson educationPaperPerson)
{
public CommonResult list(EducationPaperPerson educationPaperPerson) {
List<EducationPaperPerson> list = educationPaperPersonService.selectEducationPaperPersonList(educationPaperPerson);
return CommonResult.success(list);
}
@@ -61,14 +61,12 @@ public class EducationPaperPersonController
// }
/**
* 新增试卷人员分配
*/
@Operation(summary = "新增试卷人员分配")
@PostMapping
public CommonResult add(@RequestBody EducationPaperPerson educationPaperPerson)
{
public CommonResult add(@RequestBody EducationPaperPerson educationPaperPerson) {
return CommonResult.success(educationPaperPersonService.insertEducationPaperPerson(educationPaperPerson));
}
@@ -77,8 +75,7 @@ public class EducationPaperPersonController
*/
@Operation(summary = "修改试卷人员分配")
@PutMapping
public CommonResult edit(@RequestBody EducationPaperPerson educationPaperPerson)
{
public CommonResult edit(@RequestBody EducationPaperPerson educationPaperPerson) {
return CommonResult.success(educationPaperPersonService.updateEducationPaperPerson(educationPaperPerson));
}
@@ -87,8 +84,7 @@ public class EducationPaperPersonController
*/
@Operation(summary = "删除试卷人员分配")
@DeleteMapping("/{taskIds}")
public CommonResult remove(@PathVariable String[] taskIds)
{
public CommonResult remove(@PathVariable String[] taskIds) {
return CommonResult.success(educationPaperPersonService.deleteEducationPaperPersonByTaskIds(taskIds));
}
@@ -97,12 +93,12 @@ public class EducationPaperPersonController
* 根据试卷任务获取人员分配列表
*/
@Operation(summary = "根据试卷任务获取人员分配列表")
@GetMapping( "/getList")
public CommonResult<PageResult<PersonRepDto>> getInfo(ExamPersonVo examPersonVo)
{
@GetMapping("/getList")
public CommonResult<PageResult<PersonRepDto>> getInfo(ExamPersonVo examPersonVo) {
PageResult<PersonRepDto> list = educationPaperPersonService.selectEducationPaperPersonByTaskId(examPersonVo);
return CommonResult.success(BeanUtils.toBean(list, PersonRepDto.class));
}
/**
* 根据试卷场次获取人员分配列表
*/
@@ -129,14 +125,14 @@ public class EducationPaperPersonController
* 给任务场次分配学生
*
* @param reqVO 包含学生id场次id,试卷任务id
* @return
* @return 成功
*/
@Operation(summary = "给任务场次分配学生")
@RequestMapping("/setSessionStu")
public CommonResult<String> handleStudentSelection(@RequestBody StudentSessionReqVO reqVO) {
if (reqVO.getStudentIds()!=null&&reqVO.getStudentIds().size()>0){
if (reqVO.getStudentIds() != null && !reqVO.getStudentIds().isEmpty()) {
return CommonResult.success(educationPaperPersonService.setStuAndSession(reqVO));
}else {
} else {
return CommonResult.error(DEMO03_PAPER_STUDENT_EXISTS);
}
@@ -144,6 +140,7 @@ public class EducationPaperPersonController
/**
* 删除场次学生
*
* @param reqVO
* @return
*/
@@ -156,6 +153,7 @@ public class EducationPaperPersonController
/**
* 删除任务学生
*
* @param deleteRequestVo
* @return
*/
@@ -167,5 +165,4 @@ public class EducationPaperPersonController
}
}

View File

@@ -59,6 +59,7 @@ public class MonitorDO extends BaseDO {
private String paperNum;
private String taskId;
private String taskName;
private String taskType;
@@ -75,4 +76,9 @@ public class MonitorDO extends BaseDO {
*/
private String temporaryId;
/**
* 开始时间
*/
private String startTime;
}

View File

@@ -18,6 +18,11 @@ public interface StuPaperScoreMapper extends BaseMapperX<StuPaperScoreDO> {
List<StuPaperScoreDO> findByStuIdAndPaperId(@Param("stuId") Long stuId, @Param("paperId") String paperId, @Param("temporaryId") String temporaryId);
List<StuPaperScoreDO> findByStuIdAndTemporaryId(@Param("stuId") Long stuId, @Param("temporaryId") String temporaryId);
List<StuPaperScoreDO> findByStuIdAndTemporaryIdAndSubName(@Param("stuId") Long stuId, @Param("temporaryId") String temporaryId, @Param("subjectName") String subjectName);
List<StuScoreVo> getStuScore(@Param("stuId") Long stuId, @Param("paperId") String paperId, @Param("temporaryId") String temporaryId);
// 通过学生ID试卷ID 试题ID查询数据

View File

@@ -14,7 +14,9 @@ import java.io.IOException;
import java.math.BigDecimal;
import java.nio.charset.StandardCharsets;
import java.sql.Time;
import java.time.Duration;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;
import java.util.*;
import java.util.function.Function;
@@ -121,7 +123,19 @@ public class MonitorServiceImpl implements MonitorService {
@Override
public PageResult<MonitorDO> getMonitorPage(MonitorPageReqVO pageReqVO) {
return monitorMapper.selectPage(pageReqVO);
PageResult<MonitorDO> page = monitorMapper.selectPage(pageReqVO);
page.getList().forEach(monitor -> {
// 获取考试状态
if (!monitor.getExamStatus().equals("0")) {
String startTime = monitor.getStartTime();
LocalDateTime nowTime = LocalDateTime.now();
LocalDateTime endTime = LocalDateTime.parse(startTime, DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
long seconds = Duration.between(endTime, nowTime).getSeconds();
long remainingTime = monitor.getRemainingTime() - seconds;
monitor.setRemainingTime(remainingTime);
}
});
return page;
}
@Override
@@ -243,7 +257,9 @@ public class MonitorServiceImpl implements MonitorService {
}
info.setExamStatus("1");
LocalDateTime nowTime = LocalDateTime.now();
DateTimeFormatter formatter1 = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
info.setStartTime(nowTime.format(formatter1));
info.setIp(stuMonitorPaperVo.getIp());
if (info.getRemainingTime() == null) {
@@ -296,16 +312,12 @@ public class MonitorServiceImpl implements MonitorService {
// 1. 计算剩余时间(秒)
long remainingSeconds = ChronoUnit.SECONDS.between(LocalDateTime.now(), DateUtil.toLocalDateTime(endTime));
remainingSeconds = Math.max(remainingSeconds, 0); // 防止负数
// 2. 获取测评时长examTime 是 java.sql.Time并转换为秒
long examDurationSeconds = examTime.toLocalTime().toSecondOfDay(); // 将 HH:mm:ss 转为秒数
// 3. 规则判断:如果 remainingSeconds > examTime则限制最大值为 examTime
long finalRemaining = Math.min(remainingSeconds, examDurationSeconds);
// 4. 设置和返回
info.setRemainingTime(finalRemaining);
// 判分后更新记录
monitorMapper.updateById(info);
return finalRemaining;
@@ -315,7 +327,6 @@ public class MonitorServiceImpl implements MonitorService {
}
//开启测评时长限制 没开启场次 -直接返回测评时长
if ("1".equals(educationPaperParam.getIsSession()) && "0".equals(educationPaperParam.getIsTime())) {
info.setRemainingTime((long) examTime.toLocalTime().toSecondOfDay());
stringRedisTemplate.opsForValue().set("userCache:" + stuMonitorPaperVo.getTaskId() + ":" + stuMonitorPaperVo.getStuId(), JsonUtils.toJsonString(info));
monitorMapper.updateById(info);
@@ -358,57 +369,80 @@ public class MonitorServiceImpl implements MonitorService {
BigDecimal score = stuScoreVo.getScore();
MonitorDO info = JsonUtils.parseObject(stringRedisTemplate.opsForValue().get(key), MonitorDO.class);
if (info != null) {
long usedTime = info.getRemainingTime();
// 用现在得时间减去开始时间计算剩余时间
String startTime = info.getStartTime();
LocalDateTime endTimeDate = LocalDateTime.now();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
// 转换为 LocalDateTime
LocalDateTime startTimeDate = LocalDateTime.parse(startTime, formatter);
Duration duration = Duration.between(startTimeDate, endTimeDate);
long remainingTime = duration.getSeconds() < 0 ? 0 : duration.getSeconds();
info.setRemainingTime(usedTime - remainingTime);
}
// 重置开始时间
if (info != null) {
info.setStartTime(null);
}
MonitorDO monitorDOs = null;
if (info != null) {
monitorDOs = getMonitor(info.getMonitorId());
}
if (info != null) {
info.setRemainingTime(0L);
}
EducationPaperParam educationPaperParam = educationPaperParamMapper.selectEducationPaperParamByTaskId(taskId);
EducationPaperTask educationPaperTask = educationPaperTaskMapper.selectEducationPaperTaskByTaskId(taskId);
if ("1".equals(educationPaperParam.getSaveGrades())) {
info.setScore(String.valueOf(score));
info.setTemporaryId(stuMonitorPaperEndVo.getTemporaryId());
if (info != null) {
info.setScore(String.valueOf(score));
info.setTemporaryId(stuMonitorPaperEndVo.getTemporaryId());
}
} else {
MonitorDO monitorDO = monitorMapper.selectById(info.getMonitorId());
info.setScore(String.valueOf(score));
if (StringUtils.isNotBlank(monitorDO.getScore())) {
try {
double oldScore = Double.parseDouble(monitorDO.getScore());
if (score.doubleValue() >= oldScore) {
info.setScore(String.valueOf(score));
info.setTemporaryId(stuMonitorPaperEndVo.getTemporaryId());
} else {
// 保留旧的临时ID
if (monitorDOs != null) {
if (monitorDOs.getTemporaryId() != null) {
info.setTemporaryId(monitorDOs.getTemporaryId());
MonitorDO monitorDO = null;
if (info != null) {
monitorDO = monitorMapper.selectById(info.getMonitorId());
info.setScore(String.valueOf(score));
if (StringUtils.isNotBlank(monitorDO.getScore())) {
try {
double oldScore = Double.parseDouble(monitorDO.getScore());
if (score.doubleValue() >= oldScore) {
info.setScore(String.valueOf(score));
info.setTemporaryId(stuMonitorPaperEndVo.getTemporaryId());
} else {
// 保留旧的临时ID
if (monitorDOs != null) {
if (monitorDOs.getTemporaryId() != null) {
info.setTemporaryId(monitorDOs.getTemporaryId());
} else {
info.setTemporaryId(stuMonitorPaperEndVo.getTemporaryId());
}
} else {
// 如果没有旧的临时ID则使用新的
info.setTemporaryId(stuMonitorPaperEndVo.getTemporaryId());
}
} else {
// 如果没有旧的临时ID则使用新的
info.setTemporaryId(stuMonitorPaperEndVo.getTemporaryId());
info.setScore(String.valueOf(oldScore)); // 保留旧成绩
}
info.setScore(String.valueOf(oldScore)); // 保留旧成绩
} catch (NumberFormatException e) {
// 如果旧分数格式错误,则直接设置新分数
info.setScore(String.valueOf(score));
}
} catch (NumberFormatException e) {
// 如果旧分数格式错误,则直接设置新分数
} else {
// 如果没有旧成绩,则直接设置
info.setScore(String.valueOf(score));
}
} else {
// 如果没有旧成绩,则直接设置
info.setScore(String.valueOf(score));
}
}
//考试下的任务 结束改为 结束 其他为待考
if ("1".equals(educationPaperTask.getTaskType())) {
info.setExamStatus("2");
if (info != null) {
info.setExamStatus("2");
}
redisTemplate.delete(key);
} else {
info.setExamStatus("0");
if (info != null) {
info.setExamStatus("0");
}
stringRedisTemplate.opsForValue().set(key, JsonUtils.toJsonString(info));
}
monitorMapper.updateById(info);

View File

@@ -1,4 +1,5 @@
package pc.exam.pp.module.exam.service.paper;
import java.sql.Time;
import java.time.Duration;
import java.time.Instant;
@@ -7,8 +8,6 @@ import java.time.LocalDateTime;
import com.alibaba.excel.util.StringUtils;
import jakarta.annotation.Resource;
import org.apache.poi.hssf.record.DVALRecord;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
@@ -20,7 +19,6 @@ import pc.exam.pp.module.exam.controller.admin.paper.vo.DeleteRequestVo;
import pc.exam.pp.module.exam.controller.admin.paper.vo.ExamPersonVo;
import pc.exam.pp.module.exam.controller.admin.paper.vo.SessionStuPageReqVO;
import pc.exam.pp.module.exam.controller.admin.paper.vo.StudentSessionReqVO;
import pc.exam.pp.module.exam.controller.admin.student.vo.StudentPageReqVO;
import pc.exam.pp.module.exam.dal.dataobject.EducationPaperParam;
import pc.exam.pp.module.exam.dal.dataobject.EducationPaperPerson;
import pc.exam.pp.module.exam.dal.dataobject.EducationPaperSession;
@@ -32,9 +30,7 @@ import pc.exam.pp.module.exam.dal.mysql.paper.EducationPaperParamMapper;
import pc.exam.pp.module.exam.dal.mysql.paper.EducationPaperPersonMapper;
import pc.exam.pp.module.exam.dal.mysql.paper.EducationPaperSessionMapper;
import pc.exam.pp.module.exam.dal.mysql.paper.EducationPaperTaskMapper;
import pc.exam.pp.module.exam.dal.mysql.student.StudentMapper;
import pc.exam.pp.module.exam.utils.uuid.IdUtils;
import pc.exam.pp.module.system.api.user.dto.AdminUserRespDTO;
import java.time.ZoneId;
import java.time.temporal.ChronoUnit;
@@ -50,72 +46,67 @@ import java.util.stream.Collectors;
* @date 2025-04-18
*/
@Service
public class EducationPaperPersonServiceImpl implements IEducationPaperPersonService
{
@Autowired
public class EducationPaperPersonServiceImpl implements IEducationPaperPersonService {
@Resource
private EducationPaperPersonMapper educationPaperPersonMapper;
@Autowired
private EducationPaperTaskMapper educationPaperTaskMapper;
@Resource
private EducationPaperTaskMapper educationPaperTaskMapper;
@Resource
private StringRedisTemplate stringRedisTemplate;
@Autowired
@Resource
private EducationPaperSessionMapper educationPaperSessionMapper;
@Resource
private MonitorMapper monitorMapper;
@Resource
private EducationPaperParamMapper educationPaperParamMapper;
@Autowired
@Resource
private RedisTemplate redisTemplate;
/**
* 查询试卷人员分配
*
* @return 试卷人员分配
*/
@Override
public PageResult<PersonRepDto> selectEducationPaperPersonByTaskId(ExamPersonVo examPersonVo)
{
List<EducationPaperPerson> educationPaperPeoples= educationPaperPersonMapper.selectEducationPaperPersonByTaskId(examPersonVo);
long total= educationPaperPersonMapper.selectEducationPaperPersonByTaskIdTotal(examPersonVo.getTaskId());
List<PersonRepDto> personRepDtos=new ArrayList<>();
if (educationPaperPeoples!=null&&educationPaperPeoples.size()>0){
public PageResult<PersonRepDto> selectEducationPaperPersonByTaskId(ExamPersonVo examPersonVo) {
List<EducationPaperPerson> educationPaperPeoples = educationPaperPersonMapper.selectEducationPaperPersonByTaskId(examPersonVo);
long total = educationPaperPersonMapper.selectEducationPaperPersonByTaskIdTotal(examPersonVo.getTaskId());
List<PersonRepDto> personRepDtos = new ArrayList<>();
if (educationPaperPeoples != null && !educationPaperPeoples.isEmpty()) {
for (EducationPaperPerson educationPaperPerson : educationPaperPeoples) {
PersonRepDto personRepDto = educationPaperPersonMapper.selectUserById(educationPaperPerson.getPersonId());
if ( StringUtils.isNotBlank(personRepDto.getClassId().toString())){
personRepDto.setClassName(educationPaperPersonMapper.selectUserClassName(personRepDto.getClassId())) ;
PersonRepDto personRepDto = educationPaperPersonMapper.selectUserById(educationPaperPerson.getPersonId());
if (StringUtils.isNotBlank(personRepDto.getClassId().toString())) {
personRepDto.setClassName(educationPaperPersonMapper.selectUserClassName(personRepDto.getClassId()));
}
personRepDto.setSessionId(educationPaperPerson.getSessionId());
personRepDto.setBatch(educationPaperPerson.getBatch());
personRepDtos.add(personRepDto);
}
}
PageResult<PersonRepDto> pageResult=new PageResult<>();
}
PageResult<PersonRepDto> pageResult = new PageResult<>();
pageResult.setList(personRepDtos);
pageResult.setTotal(total);
return pageResult;
}
}
@Override
public PageResult<PersonRepDto> selectEducationPaperPersonBySessionId(ExamPersonVo examPersonVo) {
examPersonVo.setOffset(examPersonVo.getOffset());
List<EducationPaperPerson> educationPaperPeoples= educationPaperPersonMapper.selectEducationPaperPersonBySessionId(examPersonVo);
long total= educationPaperPersonMapper.selectEducationPaperPersonBySessionIdTotal(examPersonVo.getSessionId());
List<PersonRepDto> personRepDtos=new ArrayList<>();
if (educationPaperPeoples!=null&&educationPaperPeoples.size()>0){
List<EducationPaperPerson> educationPaperPeoples = educationPaperPersonMapper.selectEducationPaperPersonBySessionId(examPersonVo);
long total = educationPaperPersonMapper.selectEducationPaperPersonBySessionIdTotal(examPersonVo.getSessionId());
List<PersonRepDto> personRepDtos = new ArrayList<>();
if (educationPaperPeoples != null && !educationPaperPeoples.isEmpty()) {
for (EducationPaperPerson educationPaperPerson : educationPaperPeoples) {
PersonRepDto personRepDto = educationPaperPersonMapper.selectUserById(educationPaperPerson.getPersonId());
if ( StringUtils.isNotBlank(personRepDto.getClassId().toString())){
personRepDto.setClassName(educationPaperPersonMapper.selectUserClassName(personRepDto.getClassId())) ;
PersonRepDto personRepDto = educationPaperPersonMapper.selectUserById(educationPaperPerson.getPersonId());
if (StringUtils.isNotBlank(personRepDto.getClassId().toString())) {
personRepDto.setClassName(educationPaperPersonMapper.selectUserClassName(personRepDto.getClassId()));
}
personRepDto.setSessionId(educationPaperPerson.getSessionId());
personRepDto.setBatch(educationPaperPerson.getBatch());
personRepDtos.add(personRepDto);
}
}
PageResult<PersonRepDto> pageResult=new PageResult<>();
PageResult<PersonRepDto> pageResult = new PageResult<>();
pageResult.setList(personRepDtos);
pageResult.setTotal(total);
return pageResult;
@@ -126,29 +117,28 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
public PageResult<PersonRepDto> selectEducationPaperPersonBySearch(SessionStuPageReqVO sessionStuPageReqVO) {
String className = sessionStuPageReqVO.getClassName();
if (StringUtils.isNotBlank(className)) {
Long classId=educationPaperPersonMapper.selectUserClassIdByName(className);
Long classId = educationPaperPersonMapper.selectUserClassIdByName(className);
sessionStuPageReqVO.setClassId(classId);
}
List<PersonRepDto> personRepDtos;
long total;
String sessionId = sessionStuPageReqVO.getSessionId();
if (StringUtils.isNotBlank(sessionId)){
if (StringUtils.isNotBlank(sessionId)) {
sessionStuPageReqVO.setOffset(sessionStuPageReqVO.getOffset());
personRepDtos = educationPaperPersonMapper.selectEducationPaperPersonByNotInSessionId(sessionStuPageReqVO);
total=educationPaperPersonMapper.selectEducationPaperPersonByNotInSessionIdTotal(sessionStuPageReqVO);
}
else {
personRepDtos = educationPaperPersonMapper.selectEducationPaperPersonByNotInSessionId(sessionStuPageReqVO);
total = educationPaperPersonMapper.selectEducationPaperPersonByNotInSessionIdTotal(sessionStuPageReqVO);
} else {
sessionStuPageReqVO.setOffset(sessionStuPageReqVO.getOffset());
personRepDtos = educationPaperPersonMapper.selectEducationPaperPersonBySessionIdNotIn(sessionStuPageReqVO);
total=educationPaperPersonMapper.selectEducationPaperPersonBySessionIdNotInTotal(sessionStuPageReqVO);
personRepDtos = educationPaperPersonMapper.selectEducationPaperPersonBySessionIdNotIn(sessionStuPageReqVO);
total = educationPaperPersonMapper.selectEducationPaperPersonBySessionIdNotInTotal(sessionStuPageReqVO);
}
if (personRepDtos!=null&&personRepDtos.size()>0){
if (personRepDtos != null && !personRepDtos.isEmpty()) {
for (PersonRepDto personRepDto : personRepDtos) {
personRepDto.setClassName(educationPaperPersonMapper.selectUserClassName(personRepDto.getClassId())) ;
personRepDto.setClassName(educationPaperPersonMapper.selectUserClassName(personRepDto.getClassId()));
}
}
PageResult<PersonRepDto> pageResult=new PageResult<>();
PageResult<PersonRepDto> pageResult = new PageResult<>();
pageResult.setList(personRepDtos);
pageResult.setTotal(total);
return pageResult;
@@ -165,16 +155,10 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
String taskId = reqVO.getTaskId();
//考场批次
String batch = reqVO.getBatch();
//这里要taskId和studentIds去判断表里是否有 符合这两个条件的数据因为会有学生在此考场不设置sessionid的
//这里要taskId和studentIds去判断表里是否有 符合这两个条件的数据因为会有学生在此考场不设置sessionid的
//根据taskId和studentIds获得EducationPaperPerson在判断它的sessionid是否为空为空把sessionId和batch赋值再插入
List<EducationPaperPerson> educationPaperPeople=new ArrayList<>();
if (studentIds!=null&&studentIds.size()>0){
List<EducationPaperPerson> educationPaperPeople = new ArrayList<>();
if (studentIds != null && !studentIds.isEmpty()) {
for (String studentId : studentIds) {
// 查询是否存在该 taskId + studentId 的记录,且 sessionId 为 null
EducationPaperPerson existing = educationPaperPersonMapper.selectByTaskIdAndPersonId(taskId, studentId);
@@ -186,9 +170,9 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
educationPaperPersonMapper.updateByTaskIdAndStuId(existing);
// 本来没有设置考场的,这里要更新缓存的 剩余时间
EducationPaperSession educationPaperSession = educationPaperSessionMapper.selectEducationPaperSessionBySessionId(sessionId);
String key = "userCache:" + taskId+":"+studentId;
MonitorDO info = JsonUtils.parseObject(stringRedisTemplate.opsForValue().get(key),MonitorDO.class);
if (info!=null){
String key = "userCache:" + taskId + ":" + studentId;
MonitorDO info = JsonUtils.parseObject(stringRedisTemplate.opsForValue().get(key), MonitorDO.class);
if (info != null) {
Date startTime = educationPaperSession.getStartTime();
Date endTime = educationPaperSession.getEndTime();
@@ -199,28 +183,22 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
LocalDateTime end = Instant.ofEpochMilli(endTime.getTime())
.atZone(ZoneId.systemDefault())
.toLocalDateTime();
long remainingSeconds = ChronoUnit.SECONDS.between(start, end);
info.setRemainingTime(remainingSeconds);
}
// 更新缓存
redisTemplate.opsForValue().set(key, info);
monitorMapper.updateById(info);
}
//把学生加到试卷任务里
if (existing == null) {
EducationPaperTask educationPaperTask = educationPaperTaskMapper.selectEducationPaperTaskByTaskId(taskId);
String name= educationPaperTaskMapper.selectEducationPaperTaskNameByid(taskId);
String name = educationPaperTaskMapper.selectEducationPaperTaskNameByid(taskId);
EducationPaperParam educationPaperParam = educationPaperParamMapper.selectEducationPaperParamByTaskId(taskId);
EducationPaperPerson educationPaperPerson=new EducationPaperPerson();
String key = "userCache:" + taskId+":"+studentId;
PersonRepDto personRepDto = educationPaperPersonMapper.selectUserById(studentId);
EducationPaperPerson educationPaperPerson = new EducationPaperPerson();
String key = "userCache:" + taskId + ":" + studentId;
PersonRepDto personRepDto = educationPaperPersonMapper.selectUserById(studentId);
String uuid = IdUtils.simpleUUID();
MonitorDO info = new MonitorDO();
info.setMonitorId(uuid);
@@ -231,13 +209,12 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
//判断是否开启测评时长限制
Time examTime = educationPaperParam.getExamTime();
//开启测评时长限制
if ("0".equals(educationPaperParam.getIsTime())){
if ("0".equals(educationPaperParam.getIsTime())) {
info.setRemainingTime((long) examTime.toLocalTime().toSecondOfDay());
}
//设置学生班级
if (StringUtils.isNotBlank(personRepDto.getClassId().toString())){
String className=educationPaperTaskMapper.selectStuClassNameByClassId(personRepDto.getClassId());
if (StringUtils.isNotBlank(personRepDto.getClassId().toString())) {
String className = educationPaperTaskMapper.selectStuClassNameByClassId(personRepDto.getClassId());
info.setClassName(className);
}
info.setExamStatus("0");
@@ -255,17 +232,11 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
educationPaperPeople.add(educationPaperPerson);
}
// 如果存在但 sessionId 已有值,则跳过
}
if (educationPaperPeople!=null&&educationPaperPeople.size()>0){
if (!educationPaperPeople.isEmpty()) {
educationPaperPersonMapper.insertEducationPaperPersonList(educationPaperPeople);
}
}
return "0";
}
@@ -277,8 +248,6 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
if (studentIds == null || studentIds.isEmpty()) {
return "请选择删除的学生!"; // 无操作
}
List<String> proxyStuIds = monitorMapper.selectStuIdByTaskId(reqVO.getTaskId());
//筛选出当前任务中状态为"代考"的学生ID只允许删除这些学生
List<String> intersection = studentIds.stream()
@@ -294,7 +263,7 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
return "选择的所有学生的状态都为待考,不能删除!"; // 无符合条件的学生
}
//删除监控管理学生
DeleteRequestVo deleteRequestVo=new DeleteRequestVo();
DeleteRequestVo deleteRequestVo = new DeleteRequestVo();
deleteRequestVo.setStudentIds(intersection);
deleteRequestVo.setTaskId(reqVO.getTaskId());
monitorMapper.removeMonitorByStuIdAndTaskId(deleteRequestVo);
@@ -308,8 +277,8 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
reqVO.setStudentIds(intersection);
educationPaperPersonMapper.removeSessionStu(reqVO);
if (!notToDeleteIds.isEmpty()) {
List<String> names= educationPaperPersonMapper.selectNameByids(notToDeleteIds);
return "以下选择学生的状态为待考:"+names+",不能删除!"; // 无符合条件的学生
List<String> names = educationPaperPersonMapper.selectNameByids(notToDeleteIds);
return "以下选择学生的状态为待考:" + names + ",不能删除!"; // 无符合条件的学生
}
return "删除成功";
}
@@ -339,17 +308,16 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
.collect(Collectors.toList());
deleteRequestVo.setStudentIds(intersection);
monitorMapper.removeMonitorByStuIdAndTaskId(deleteRequestVo);
for (String studentId : intersection) {
String key = "userCache:" + deleteRequestVo.getTaskId()+":"+studentId;
String key = "userCache:" + deleteRequestVo.getTaskId() + ":" + studentId;
redisTemplate.delete(key);
}
educationPaperPersonMapper.removeTaskStu(deleteRequestVo);
if (!notToDeleteIds.isEmpty()) {
List<String> names= educationPaperPersonMapper.selectNameByids(notToDeleteIds);
return "以下选择学生的状态为待考:"+names+",不能删除!"; // 无符合条件的学生
List<String> names = educationPaperPersonMapper.selectNameByids(notToDeleteIds);
return "以下选择学生的状态为待考:" + names + ",不能删除!"; // 无符合条件的学生
}
return "删除成功";
}
@@ -367,8 +335,7 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
* @return 试卷人员分配
*/
@Override
public List<EducationPaperPerson> selectEducationPaperPersonList(EducationPaperPerson educationPaperPerson)
{
public List<EducationPaperPerson> selectEducationPaperPersonList(EducationPaperPerson educationPaperPerson) {
return educationPaperPersonMapper.selectEducationPaperPersonList(educationPaperPerson);
}
@@ -379,8 +346,7 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
* @return 结果
*/
@Override
public int insertEducationPaperPerson(EducationPaperPerson educationPaperPerson)
{
public int insertEducationPaperPerson(EducationPaperPerson educationPaperPerson) {
return educationPaperPersonMapper.insertEducationPaperPerson(educationPaperPerson);
}
@@ -391,8 +357,7 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
* @return 结果
*/
@Override
public int updateEducationPaperPerson(EducationPaperPerson educationPaperPerson)
{
public int updateEducationPaperPerson(EducationPaperPerson educationPaperPerson) {
return educationPaperPersonMapper.updateEducationPaperPerson(educationPaperPerson);
}
@@ -403,8 +368,7 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
* @return 结果
*/
@Override
public int deleteEducationPaperPersonByTaskIds(String[] taskIds)
{
public int deleteEducationPaperPersonByTaskIds(String[] taskIds) {
return educationPaperPersonMapper.deleteEducationPaperPersonByTaskIds(taskIds);
}
@@ -415,8 +379,7 @@ public class EducationPaperPersonServiceImpl implements IEducationPaperPersonSer
* @return 结果
*/
@Override
public int deleteEducationPaperPersonByTaskId(String taskId)
{
public int deleteEducationPaperPersonByTaskId(String taskId) {
return educationPaperPersonMapper.deleteEducationPaperPersonByTaskId(taskId);
}

View File

@@ -18,8 +18,7 @@ import java.util.List;
* @author pengchen
* @date 2025-04-18
*/
public interface IEducationPaperPersonService
{
public interface IEducationPaperPersonService {
/**
* 查询试卷人员分配
*
@@ -71,6 +70,11 @@ public interface IEducationPaperPersonService
PageResult<PersonRepDto> selectEducationPaperPersonBySearch(SessionStuPageReqVO sessionStuPageReqVO);
/**
* 给任务场次分配学生
* @param reqVO 包含学生id场次id,试卷任务id
* @return 成功
*/
String setStuAndSession(StudentSessionReqVO reqVO);
String removeSessionStu(StudentSessionReqVO reqVO);
@@ -80,7 +84,6 @@ public interface IEducationPaperPersonService
List<String> selectStuIdByTaskId(String taskid);
// PageResult<PersonRepDto> selectExamStuList(StudentPageReqVO examStu);
}

View File

@@ -15,6 +15,10 @@ public interface StuPaperScoreService {
List<StuPaperScoreDO> findByStuIDAndPaperId(Long stuId, String paperId, String temporaryId);
List<StuPaperScoreDO> findByStuIDAndTemporaryId(Long stuId, String temporaryId);
List<StuPaperScoreDO> findByStuIDAndTemporaryIdAndSubName(Long stuId, String temporaryId, String subjectName);
void insertStuPaperScore(StuPaperScoreDO stuPaperScoreDO);
void updateStuPaperScore(StuPaperScoreDO stuPaperScoreDO);

View File

@@ -35,6 +35,16 @@ public class StuPaperScoreServiceImpl implements StuPaperScoreService {
return stuPaperScoreMapper.findByStuIdAndPaperId(stuId, paperId, temporaryId);
}
@Override
public List<StuPaperScoreDO> findByStuIDAndTemporaryId(Long stuId, String temporaryId) {
return stuPaperScoreMapper.findByStuIdAndTemporaryId(stuId, temporaryId);
}
@Override
public List<StuPaperScoreDO> findByStuIDAndTemporaryIdAndSubName(Long stuId, String temporaryId, String subjectName) {
return stuPaperScoreMapper.findByStuIdAndTemporaryIdAndSubName(stuId, temporaryId, subjectName);
}
@Override
public void insertStuPaperScore(StuPaperScoreDO stuPaperScoreDO) {
stuPaperScoreMapper.insert(stuPaperScoreDO);

View File

@@ -9,7 +9,30 @@
文档可见https://www.iocoder.cn/MyBatis/x-plugins/
-->
<select id="findByStuIdAndPaperId" resultType="pc.exam.pp.module.exam.dal.dataobject.student.StuPaperScoreDO">
SELECT * FROM exam_stu_paper_score WHERE stu_id = #{stuId} AND paper_id = #{paperId} AND temporary_id = #{temporaryId} order by sort ASC
SELECT *
FROM exam_stu_paper_score
WHERE stu_id = #{stuId}
AND paper_id = #{paperId}
AND temporary_id = #{temporaryId}
order by sort ASC
</select>
<select id="findByStuIdAndTemporaryId" resultType="pc.exam.pp.module.exam.dal.dataobject.student.StuPaperScoreDO">
SELECT *
FROM exam_stu_paper_score
WHERE stu_id = #{stuId}
AND temporary_id = #{temporaryId}
order by sort ASC
</select>
<select id="findByStuIdAndTemporaryIdAndSubName"
resultType="pc.exam.pp.module.exam.dal.dataobject.student.StuPaperScoreDO">
SELECT *
FROM exam_stu_paper_score
WHERE stu_id = #{stuId}
AND temporary_id = #{temporaryId}
AND subject_name = #{subjectName}
order by sort ASC
</select>
@@ -27,11 +50,19 @@
AND esps.paper_id = #{paperId}
AND esps.temporary_id = #{temporaryId}
</select>
<select id="findByStuIdAndPaperIdAndQuestionId" resultType="pc.exam.pp.module.exam.dal.dataobject.student.StuPaperScoreDO">
SELECT * FROM exam_stu_paper_score WHERE stu_id = #{stuId} AND paper_id = #{paperId} AND qu_id = #{quId}
<select id="findByStuIdAndPaperIdAndQuestionId"
resultType="pc.exam.pp.module.exam.dal.dataobject.student.StuPaperScoreDO">
SELECT *
FROM exam_stu_paper_score
WHERE stu_id = #{stuId}
AND paper_id = #{paperId}
AND qu_id = #{quId}
</select>
<delete id="deleteByStuIdAndPaperId">
DELETE FROM exam_stu_paper_score WHERE stu_id = #{stuId} AND paper_id = #{paperId}
DELETE
FROM exam_stu_paper_score
WHERE stu_id = #{stuId}
AND paper_id = #{paperId}
</delete>