zhangf
2024-09-11 1a316551c8e46b793904090cfa84781bf77fef2a
增加科目类别
已修改33个文件
已添加21个文件
1160 ■■■■■ 文件已修改
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/config/ExecutorConfig.java 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/controller/ThStudyRecordManagerController.java 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/controller/ThSubjectTypeController.java 44 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/controller/ThstatisticController.java 21 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/controller/TripartiteInterfaceController.java 31 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/entity/ThBatch.java 5 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/entity/ThStudyDetail.java 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/entity/ThSubjectType.java 17 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/enums/StudentFinishStatus.java 41 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/mapper/ThExamRecordMapper.java 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/mapper/ThStudentBatchMapper.java 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/mapper/ThSubjectTypeMapper.java 11 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/query/ThBatchQuery.java 7 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/query/ThExamRecordQuery.java 5 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/query/ThStatisticQuery.java 23 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/query/ThStudyDetailQuery.java 6 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/req/ThBatchReqDTO.java 6 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/req/ThStudyDetailReqDTO.java 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/resp/ThPlatformStudentRespDTO.java 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/resp/ThStatisticRespDTO.java 15 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/vo/ThBatchVO.java 6 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/vo/ThSubjectTypeVO.java 14 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/vo/ThTrainVO.java 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThExamRecordService.java 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThStudentBatchService.java 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThStudyRecordManagerService.java 3 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThSubjectTypeService.java 14 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThstatisticService.java 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/TripartiteInterfaceService.java 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThBatchManagerServiceImpl.java 46 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThExamRecordServiceImpl.java 7 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThStudentBatchServiceImpl.java 16 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThStudyRecordManagerServiceImpl.java 71 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThSubjectTypeServiceImpl.java 80 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThstatisticServiceImpl.java 77 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/TripartiteInterfaceServiceImpl.java 74 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/resources/mapper/institutionaccess/ThBatchMapper.xml 42 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/resources/mapper/institutionaccess/ThExamRecordMapper.xml 26 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/resources/mapper/institutionaccess/ThStudentBatchMapper.xml 55 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/resources/mapper/institutionaccess/ThStudyDetailMapper.xml 13 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-admin/src/main/resources/application.yml 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-common/src/main/java/com/ruoyi/common/constant/CacheConstants.java 5 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-common/src/main/java/com/ruoyi/common/core/domain/model/ResultVO.java 16 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-common/src/main/java/com/ruoyi/common/utils/HttpClientUtil.java 150 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/domain/InstitutionalManager.java 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/domain/ThAccessAddress.java 15 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/domain/enums/AccessAddressType.java 40 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/domain/req/InstitutionModStatusReqDTO.java 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/domain/vo/InstitutionVo.java 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/mapper/ThAccessAddressMapper.java 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/service/InstitutionalManagerService.java 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/service/ThAccessAddressService.java 8 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/service/impl/InstitutionalManagerServiceImpl.java 40 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
ruoyi-system/src/main/java/com/ruoyi/system/service/impl/ThAccessAddressServiceImpl.java 17 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/config/ExecutorConfig.java
@@ -15,8 +15,8 @@
import java.util.concurrent.Executor;
import java.util.concurrent.ThreadPoolExecutor;
@Configuration
@EnableAsync
/*@Configuration
@EnableAsync*/
public class ExecutorConfig implements AsyncConfigurer {
    private Logger logger = LoggerFactory.getLogger(ExecutorConfig.class);
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/controller/ThStudyRecordManagerController.java
@@ -20,6 +20,10 @@
        startPage();
        return getDataTable(thStudyRecordManagerService.listByPage(query));
    }
    @GetMapping("/idcard")
    public AjaxResult getStudyRecordByIdcard(ThStudyDetailQuery query) {
        return success(thStudyRecordManagerService.getStudyRecordByIdcard(query));
    }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/controller/ThSubjectTypeController.java
对比新文件
@@ -0,0 +1,44 @@
package com.gkhy.exam.institutionalaccess.controller;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.service.ThSubjectTypeService;
import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.redis.RedisCache;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import javax.annotation.PostConstruct;
@RestController
@RequestMapping("/th/subject/type")
public class ThSubjectTypeController extends BaseController {
    private static final Logger log = LoggerFactory.getLogger(ThSubjectTypeController.class);
    @Autowired
    private ThSubjectTypeService thSubjectTypeService;
    @Autowired
    private RedisCache redisCache;
    //缓存科目信息
    @PostConstruct
    private void initThSubjectType() {
        //清除redis缓存
        String key = CacheConstants.THREE_SUBJECT_TYPE;
        if (redisCache.hasKey(key)) {
            redisCache.deleteObject(key);
        }
        thSubjectTypeService.subjectTypeCache();
        log.info("【组织架构信息】已加入缓存");
    }
    @GetMapping("/tree")
    private AjaxResult getTree() {
        return AjaxResult.success(thSubjectTypeService.getTree());
    }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/controller/ThstatisticController.java
对比新文件
@@ -0,0 +1,21 @@
package com.gkhy.exam.institutionalaccess.controller;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.service.ThstatisticService;
import com.ruoyi.common.core.domain.AjaxResult;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping("/th/statistic")
public class ThstatisticController {
    @Autowired
    private ThstatisticService thstatisticService;
    @GetMapping("/count")
    private AjaxResult getStatistic(ThStatisticQuery thStatisticQuery) {
        return AjaxResult.success(thstatisticService.getStatistic(thStatisticQuery));
    }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/controller/TripartiteInterfaceController.java
@@ -1,17 +1,26 @@
package com.gkhy.exam.institutionalaccess.controller;
import com.alibaba.fastjson2.JSONObject;
import com.alibaba.fastjson2.TypeReference;
import com.gkhy.exam.institutionalaccess.enums.*;
import com.gkhy.exam.institutionalaccess.model.req.*;
import com.gkhy.exam.institutionalaccess.model.resp.ThPlatformStudentRespDTO;
import com.gkhy.exam.institutionalaccess.service.TripartiteInterfaceService;
import com.ruoyi.common.annotation.RepeatedClick;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.signature.AESUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;
@RequestMapping("/gov-server/receive")
@@ -96,7 +105,7 @@
     * 课程
     * @param args
     */
    /*public static void main(String[] args) {
   /* public static void main(String[] args) {
        List<ThCourseReqDTO> list = new ArrayList<>();
        ThCourseReqDTO thCourseReqDTO = new ThCourseReqDTO();
        thCourseReqDTO.setUuid("20bded7f-660c-4380-b7f9-00f3976e1875");
@@ -189,7 +198,12 @@
        thBatchReqDTO.setBatchName("第一期2024");
        thBatchReqDTO.setTrainOrgName("测试机构");
        thBatchReqDTO.setHaveExam(HaveExam.YES.getStatus());
        thBatchReqDTO.setStatus(OpenStatus.NO.getStatus());
        thBatchReqDTO.setStatus(OpenStatus.START.getStatus());
        thBatchReqDTO.setActualEndTime(LocalDateTime.now());
        thBatchReqDTO.setActualStartTime(null);
        thBatchReqDTO.setExpectEndTime(LocalDateTime.now());
        thBatchReqDTO.setExpectStartTime(LocalDateTime.now());
        thBatchReqDTO.setSubjectCode("201");
        thBatchReqDTO.setDelFlag((byte)0);
        thBatchReqDTO.setBatchLessonNum(new BigDecimal(40));
        List<ThBatchCourseReqDTO> courseList = new ArrayList<>();
@@ -233,7 +247,7 @@
    /**
     * 学生信息上报
     */
  /*  public static void main(String[] args) {
   /* public static void main(String[] args) {
        ThStudentReqDTO thStudentReqDTO = new ThStudentReqDTO();
        thStudentReqDTO.setUuid("5096d539-9ec4-499e-a7ef-3fc1c688ba51");
        thStudentReqDTO.setName("李四fafas");
@@ -306,7 +320,7 @@
    /**
     *
     */
    /*public static void main(String[] args) {
    public static void main(String[] args) {
        List<ThStudyDetailReqDTO> list = new ArrayList<>();
        ThStudyDetailReqDTO thStudyDetailReqDTO = new ThStudyDetailReqDTO();
        thStudyDetailReqDTO.setUuid("8c061cb1-8560-43b8-abe4-04ae8e763f59");
@@ -319,6 +333,7 @@
        thStudyDetailReqDTO.setChapterUuid("d5cd3b26-be11-4ffe-8a34-283c49c85253");
        thStudyDetailReqDTO.setDuration(4567l);
        thStudyDetailReqDTO.setTrainOrgName("测试");
        thStudyDetailReqDTO.setCompleteStatus(StudentFinishStatus.YES.getStatus());
        thStudyDetailReqDTO.setStartTime(LocalDateTime.now());
        thStudyDetailReqDTO.setFinishTime(LocalDateTime.now());
        thStudyDetailReqDTO.setVideoUrl("hhtht");
@@ -345,10 +360,12 @@
        String encrypt = AESUtils.encrypt(jsonString);
        System.out.println(encrypt);
    }*/
    }
   /* public static void main(String[] args) {
        String decrypt = AESUtils.decrypt("");
        String decrypt = AESUtils.decrypt("BhSazFtvofCRelDGgefpPEYzIR9eUed3RV52ThGuzib1FyirNEW8Dri7WBJBKDKAn8+bNbL2HydRalakvoNA6oP/AM/sYpxDvO4pwaJPvYkow8crP8qPcB+vnDoJRCpvChl6RIBc4+oMONh6gsX6FA==");
        ThPlatformStudentRespDTO studentRespDTO = JSONObject.parseObject(decrypt, new TypeReference<ThPlatformStudentRespDTO>() {});
        System.out.println(decrypt);
        System.out.println(studentRespDTO);
    }*/
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/entity/ThBatch.java
@@ -30,6 +30,11 @@
    // private Byte finishStatus;
    //删除标志(0代表存在 2代表删除)
    private Byte delFlag;
    private LocalDateTime actualStartTime;
    private LocalDateTime actualEndTime;
    private LocalDateTime expectStartTime;
    private LocalDateTime expectEndTime;
    private String subjectCode;
    /** 创建者 */
    private String createBy;
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/entity/ThStudyDetail.java
@@ -38,6 +38,8 @@
    private String videoUrl;
    private String lessonReportUrl;
    private Byte completeStatus;
    //删除标志(0代表存在 2代表删除)
    private Byte delFlag;
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/entity/ThSubjectType.java
对比新文件
@@ -0,0 +1,17 @@
package com.gkhy.exam.institutionalaccess.entity;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
@TableName("th_subject_type")
@Data
public class ThSubjectType {
    @TableId(type = IdType.AUTO)
    private Long id;
    private String name;
    private String code;
    private String parentCode;
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/enums/StudentFinishStatus.java
对比新文件
@@ -0,0 +1,41 @@
package com.gkhy.exam.institutionalaccess.enums;
public enum StudentFinishStatus {
    //完成(0否,1是)
    NO((byte)0,"未结束"),
    YES((byte)1,"结束"),
    ;
    private Byte status;
    private String desc;
    StudentFinishStatus(Byte status, String desc) {
        this.status = status;
        this.desc = desc;
    }
    public Byte getStatus() {
        return status;
    }
    public void setStatus(Byte status) {
        this.status = status;
    }
    public String getDesc() {
        return desc;
    }
    public void setDesc(String desc) {
        this.desc = desc;
    }
    public static StudentFinishStatus get(Byte status) {
        for (StudentFinishStatus finishStatus : StudentFinishStatus.values()) {
            if (finishStatus.getStatus() == status) {
                return finishStatus;
            }
        }
        return null;
    }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/mapper/ThExamRecordMapper.java
@@ -4,7 +4,9 @@
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.gkhy.exam.institutionalaccess.entity.ThExamRecord;
import com.gkhy.exam.institutionalaccess.model.query.ThExamRecordQuery;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.model.vo.ThExamRecordVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThTrainVO;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import org.springframework.stereotype.Repository;
@@ -18,4 +20,6 @@
    List<ThExamRecord> getByUuids(@Param("examUuids") List<String> examUuids);
    Integer insertBatch(@Param("list") List<ThExamRecord> list);
    List<ThTrainVO> getStatistic(@Param("query") ThStatisticQuery thStatisticQuery);
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/mapper/ThStudentBatchMapper.java
@@ -2,10 +2,8 @@
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.gkhy.exam.institutionalaccess.entity.ThStudentBatch;
import com.gkhy.exam.institutionalaccess.model.vo.ThStatisticStudentVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudentBatchCourseVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudentBatchVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudentCourseVO;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.model.vo.*;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import org.springframework.stereotype.Repository;
@@ -35,4 +33,8 @@
    List<ThStudentBatch> getByIdCards(@Param("idcards") List<String> idcards);
    List<ThStudentBatchVO> getStudentBatchVOByCourseUuid(@Param("courseUuid") String courseUuid);
    List<ThTrainVO> getStatistic(@Param("query") ThStatisticQuery thStatisticQuery);
    List<ThTrainVO> getStatisticHaveExam(@Param("query") ThStatisticQuery thStatisticQuery);
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/mapper/ThSubjectTypeMapper.java
对比新文件
@@ -0,0 +1,11 @@
package com.gkhy.exam.institutionalaccess.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.gkhy.exam.institutionalaccess.entity.ThSubjectType;
import org.apache.ibatis.annotations.Mapper;
import org.springframework.stereotype.Repository;
@Repository
@Mapper
public interface ThSubjectTypeMapper extends BaseMapper<ThSubjectType> {
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/query/ThBatchQuery.java
@@ -2,6 +2,7 @@
import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.Data;
import org.springframework.format.annotation.DateTimeFormat;
import java.time.LocalDate;
import java.util.Date;
@@ -10,9 +11,11 @@
public class ThBatchQuery {
    private Long institutionId;
    private String batchName;
    @JsonFormat(pattern = "yyyy-MM-dd")
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private Date startTime;
    @JsonFormat(pattern = "yyyy-MM-dd")
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private Date endTime;
    private String trainOrgName;
    private String subjectCode;
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/query/ThExamRecordQuery.java
@@ -2,6 +2,7 @@
import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.Data;
import org.springframework.format.annotation.DateTimeFormat;
import java.time.LocalDate;
import java.util.Date;
@@ -10,8 +11,8 @@
public class ThExamRecordQuery {
    private String name;
    private String idcard;
    @JsonFormat(pattern = "yyyy-MM-dd")
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private Date startTime;
    @JsonFormat(pattern = "yyyy-MM-dd")
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private Date endTime;
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/query/ThStatisticQuery.java
对比新文件
@@ -0,0 +1,23 @@
package com.gkhy.exam.institutionalaccess.model.query;
import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.Data;
import org.springframework.format.annotation.DateTimeFormat;
import java.util.Date;
/**
 * @author zf
 * @email 1603559716@qq.com
 * @date 2024/8/7 15:48
 * @description ThStatisticQuery
 */
@Data
public class ThStatisticQuery {
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private Date startTime;
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private Date endTime;
    private String trainOrgName;
    private String subjectCode;
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/query/ThStudyDetailQuery.java
@@ -2,6 +2,7 @@
import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.Data;
import org.springframework.format.annotation.DateTimeFormat;
import java.time.LocalDate;
import java.util.Date;
@@ -11,9 +12,9 @@
    private String idcard;
    private String name;
    private String courseUuid;
    @JsonFormat(pattern = "yyyy-MM-dd")
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private Date startTime;
    @JsonFormat(pattern = "yyyy-MM-dd")
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private Date endTime;
    private Integer pageNum;
@@ -21,4 +22,5 @@
    /** 每页显示记录数 */
    private Integer pageSize;
    private Integer startSize;
    private Long institutionId;
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/req/ThBatchReqDTO.java
@@ -4,6 +4,7 @@
import lombok.Data;
import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.List;
@Data
@@ -17,5 +18,10 @@
    private Byte status;
    private BigDecimal batchLessonNum;
    private Byte delFlag;
    private LocalDateTime actualStartTime;
    private LocalDateTime actualEndTime;
    private LocalDateTime expectStartTime;
    private LocalDateTime expectEndTime;
    private String subjectCode;
    private List<ThBatchCourseReqDTO> courseList;
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/req/ThStudyDetailReqDTO.java
@@ -28,6 +28,8 @@
    private Long finishPosition;
    private String videoUrl;
    private String lessonReportUrl;
    //该批次培训状态是否全部完成(0未完成,1完成)
    private Byte completeStatus;
    private List<ThStudyTrackReqDTO> trackList;
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/resp/ThPlatformStudentRespDTO.java
@@ -6,7 +6,6 @@
@Data
public class ThPlatformStudentRespDTO {
    private String studentUuid;
    private String name;
    private String idcard;
    private List<ThPlatformBatchRespDTO> batchList;
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/resp/ThStatisticRespDTO.java
对比新文件
@@ -0,0 +1,15 @@
package com.gkhy.exam.institutionalaccess.model.resp;
import lombok.Data;
import java.math.BigDecimal;
@Data
public class ThStatisticRespDTO {
    private String institutionName;
    private Integer studentCount;
    private Integer finishCount;
    private Integer eaxmStudentCount;
    private Integer passCount;
    private BigDecimal passRate;
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/vo/ThBatchVO.java
@@ -19,6 +19,12 @@
    private Integer studentCount;
    //删除标志(0代表存在 2代表删除)
    private Byte delFlag;
    private LocalDateTime actualStartTime;
    private LocalDateTime actualEndTime;
    private LocalDateTime expectStartTime;
    private LocalDateTime expectEndTime;
    private String subjectName;
    private String subjectCode;
    /** 创建者 */
    private String createBy;
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/vo/ThSubjectTypeVO.java
对比新文件
@@ -0,0 +1,14 @@
package com.gkhy.exam.institutionalaccess.model.vo;
import lombok.Data;
import java.util.List;
@Data
public class ThSubjectTypeVO {
    private Long id;
    private String name;
    private String code;
    private String parentCode;
    private List<ThSubjectTypeVO> children;
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/model/vo/ThTrainVO.java
对比新文件
@@ -0,0 +1,12 @@
package com.gkhy.exam.institutionalaccess.model.vo;
import lombok.Data;
@Data
public class ThTrainVO {
    private Long institutionId;
    private Integer studentCount;
    private Integer finishCount;
    private Integer passCount;
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThExamRecordService.java
@@ -3,7 +3,9 @@
import com.baomidou.mybatisplus.extension.service.IService;
import com.gkhy.exam.institutionalaccess.entity.ThExamRecord;
import com.gkhy.exam.institutionalaccess.model.query.ThExamRecordQuery;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.model.vo.ThExamRecordVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThTrainVO;
import org.springframework.scheduling.annotation.Async;
import java.util.List;
@@ -16,4 +18,6 @@
    List<ThExamRecord> getByUuids(List<String> examUuids);
    //@Async("SocketTaskExecutor")
    Integer insertBatch(List<ThExamRecord> examRecordList);
    List<ThTrainVO> getStatistic(ThStatisticQuery thStatisticQuery);
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThStudentBatchService.java
@@ -3,10 +3,8 @@
import com.baomidou.mybatisplus.extension.service.IService;
import com.gkhy.exam.institutionalaccess.entity.ThStudentBatch;
import com.gkhy.exam.institutionalaccess.model.vo.ThStatisticStudentVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudentBatchCourseVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudentBatchVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudentCourseVO;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.model.vo.*;
import org.springframework.scheduling.annotation.Async;
import java.util.List;
@@ -36,4 +34,8 @@
    List<ThStudentBatchVO> getStudentBatchVOByBatchUuid(String batchUuid);
    List<ThStudentBatchVO> getStudentBatchVOByCourseUuid(String courseUuid);
    List<ThTrainVO> getStatistic(ThStatisticQuery thStatisticQuery);
    List<ThTrainVO> getStatisticHaveExam(ThStatisticQuery thStatisticQuery);
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThStudyRecordManagerService.java
@@ -1,10 +1,13 @@
package com.gkhy.exam.institutionalaccess.service;
import com.gkhy.exam.institutionalaccess.model.query.ThStudyDetailQuery;
import com.gkhy.exam.institutionalaccess.model.resp.ThPlatformStudentRespDTO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudyDetailVO;
import java.util.List;
public interface ThStudyRecordManagerService {
    List<ThStudyDetailVO> listByPage(ThStudyDetailQuery query);
    ThPlatformStudentRespDTO getStudyRecordByIdcard(ThStudyDetailQuery query);
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThSubjectTypeService.java
对比新文件
@@ -0,0 +1,14 @@
package com.gkhy.exam.institutionalaccess.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.gkhy.exam.institutionalaccess.entity.ThSubjectType;
import com.gkhy.exam.institutionalaccess.model.vo.ThSubjectTypeVO;
import java.util.List;
public interface ThSubjectTypeService extends IService<ThSubjectType> {
    void subjectTypeCache();
    List<ThSubjectType> getSubjectTypeList();
    List<ThSubjectTypeVO> getTree();
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/ThstatisticService.java
对比新文件
@@ -0,0 +1,10 @@
package com.gkhy.exam.institutionalaccess.service;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.model.resp.ThStatisticRespDTO;
import java.util.List;
public interface ThstatisticService {
    List<ThStatisticRespDTO> getStatistic(ThStatisticQuery thStatisticQuery);
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/TripartiteInterfaceService.java
@@ -22,4 +22,5 @@
    AjaxResult receiveBatchOpen(JSONObject jsonObject);
    AjaxResult receiveBatchEnd(JSONObject jsonObject);
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThBatchManagerServiceImpl.java
@@ -1,14 +1,10 @@
package com.gkhy.exam.institutionalaccess.service.serviceImpl;
import com.gkhy.exam.institutionalaccess.entity.ThBatchCourse;
import com.gkhy.exam.institutionalaccess.entity.ThBatchCourseChapter;
import com.gkhy.exam.institutionalaccess.entity.ThStudentBatch;
import com.gkhy.exam.institutionalaccess.entity.ThStudyDetail;
import com.gkhy.exam.institutionalaccess.entity.*;
import com.gkhy.exam.institutionalaccess.enums.FinishStatus;
import com.gkhy.exam.institutionalaccess.model.query.ThBatchQuery;
import com.gkhy.exam.institutionalaccess.model.resp.ThBatchCourseRespDTO;
import com.gkhy.exam.institutionalaccess.model.resp.ThCourseChapterRespDTO;
import com.gkhy.exam.institutionalaccess.model.resp.ThStudentCourseRespDTO;
import com.gkhy.exam.institutionalaccess.model.resp.ThStudentStudyRespDTO;
import com.gkhy.exam.institutionalaccess.model.vo.*;
@@ -23,7 +19,6 @@
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.stream.Collectors;
@Service("ThBatchManagerService")
@@ -38,6 +33,8 @@
    private ThStudyDetailService thStudyDetailService;
    @Autowired
    private ThBatchCourseChapterService thBatchCourseChapterService;
    @Autowired
    private ThSubjectTypeService subjectTypeService;
    @Override
    public List<ThBatchVO> listByPage(ThBatchQuery query) {
@@ -51,6 +48,7 @@
            List<ThBatchCourseChapter> chapterList = thBatchCourseChapterService.getListByBatchUuids(batchUuids);
            for (ThBatchVO thBatchVO : thBatchVOS) {
                thBatchVO.setSubjectName(getObtainSuperiors(thBatchVO.getSubjectCode()));
                //课程
                List<ThBatchCourseVO> collect = batchCourseList.stream()
                        .filter(bc -> bc.getBatchUuid().equals(thBatchVO.getUuid()))
@@ -181,4 +179,40 @@
        }
        return respDTOS;
    }
    public String getObtainSuperiors(String code){
        List<ThSubjectType> subjectTypeList = subjectTypeService.getSubjectTypeList();
        if(StringUtils.isEmpty(code)){
            return "未知";
        }
        StringBuffer stringBuffer = new StringBuffer();
        String subjectName = "未知";
        ThSubjectType currentSubject = getThSubejctInfoByCode(subjectTypeList,code);
        if(currentSubject != null){
            subjectName = currentSubject.getName();
        }
        //一级
        if(code.length() == 1){
            stringBuffer.append(subjectName);
        }
        //二级
        if(code.length() == 3){
            ThSubjectType parentSubject = getThSubejctInfoByCode(subjectTypeList,currentSubject.getParentCode());
            stringBuffer.append(parentSubject.getName()).append("/").append(subjectName);
        }
        //三级
        if(code.length() == 5){
            ThSubjectType parentSubject = getThSubejctInfoByCode(subjectTypeList,currentSubject.getParentCode());
            ThSubjectType grandpaSubject = getThSubejctInfoByCode(subjectTypeList,parentSubject.getParentCode());
            stringBuffer.append(grandpaSubject.getName()).append("/").append(parentSubject.getName()).append("/").append(subjectName);
        }
        return stringBuffer.toString();
    }
   public ThSubjectType getThSubejctInfoByCode(List<ThSubjectType> list, String code){
       List<ThSubjectType> selectList = list.stream().filter(subjectType -> subjectType.getCode().equals(code)).collect(Collectors.toList());
        if(selectList.size() > 0){
            return selectList.get(0);
        }
        return null;
   }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThExamRecordServiceImpl.java
@@ -6,7 +6,9 @@
import com.gkhy.exam.institutionalaccess.entity.ThExamRecord;
import com.gkhy.exam.institutionalaccess.mapper.ThExamRecordMapper;
import com.gkhy.exam.institutionalaccess.model.query.ThExamRecordQuery;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.model.vo.ThExamRecordVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThTrainVO;
import com.gkhy.exam.institutionalaccess.service.ThExamRecordService;
import com.ruoyi.common.enums.coalmineEnums.DeleteStatusEnum;
import org.springframework.beans.factory.annotation.Autowired;
@@ -45,4 +47,9 @@
    public Integer insertBatch(List<ThExamRecord> examRecordList){
        return baseMapper.insertBatch(examRecordList);
    }
    @Override
    public List<ThTrainVO> getStatistic(ThStatisticQuery thStatisticQuery) {
        return baseMapper.getStatistic(thStatisticQuery);
    }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThStudentBatchServiceImpl.java
@@ -6,10 +6,8 @@
import com.gkhy.exam.institutionalaccess.entity.ThStudentBatch;
import com.gkhy.exam.institutionalaccess.mapper.ThStudentBatchMapper;
import com.gkhy.exam.institutionalaccess.model.vo.ThStatisticStudentVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudentBatchCourseVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudentBatchVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudentCourseVO;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.model.vo.*;
import com.gkhy.exam.institutionalaccess.service.ThStudentBatchService;
import com.ruoyi.common.enums.coalmineEnums.DeleteStatusEnum;
import org.springframework.beans.factory.annotation.Autowired;
@@ -101,4 +99,14 @@
    public List<ThStudentBatchVO> getStudentBatchVOByCourseUuid(String courseUuid) {
        return studentBatchMapper.getStudentBatchVOByCourseUuid(courseUuid);
    }
    @Override
    public List<ThTrainVO> getStatistic(ThStatisticQuery thStatisticQuery) {
        return studentBatchMapper.getStatistic(thStatisticQuery);
    }
    @Override
    public List<ThTrainVO> getStatisticHaveExam(ThStatisticQuery thStatisticQuery) {
        return studentBatchMapper.getStatisticHaveExam(thStatisticQuery);
    }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThStudyRecordManagerServiceImpl.java
@@ -1,23 +1,39 @@
package com.gkhy.exam.institutionalaccess.service.serviceImpl;
import com.alibaba.fastjson2.JSONObject;
import com.alibaba.fastjson2.TypeReference;
import com.gkhy.exam.institutionalaccess.entity.*;
import com.ruoyi.system.domain.enums.AccessAddressType;
import com.gkhy.exam.institutionalaccess.model.query.ThStudyDetailQuery;
import com.gkhy.exam.institutionalaccess.model.resp.ThPlatformStudentRespDTO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudyAuthVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudyDetailVO;
import com.gkhy.exam.institutionalaccess.model.vo.ThStudyTrackVO;
import com.gkhy.exam.institutionalaccess.service.*;
import com.gkhy.exam.institutionalaccess.utils.ConvertTimeUtils;
import com.ruoyi.common.utils.HttpClientUtil;
import com.gkhy.exam.noncoalmine.model.vo.ReturnVO;
import com.ruoyi.common.constant.ResultConstants;
import com.ruoyi.common.exception.BusinessException;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.signature.AESUtils;
import com.ruoyi.system.domain.ThAccessAddress;
import com.ruoyi.system.service.ThAccessAddressService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;
import java.util.ArrayList;
import java.util.List;
import java.util.*;
import java.util.stream.Collectors;
@Service("ThStudyRecordManagerService")
public class ThStudyRecordManagerServiceImpl implements ThStudyRecordManagerService {
    private Logger logger = LoggerFactory.getLogger(ThStudyRecordManagerServiceImpl.class);
    @Autowired
    private ThStudyDetailService thStudyDetailService;
    @Autowired
@@ -32,6 +48,8 @@
    private ThBatchService thBatchService;
    @Autowired
    private ThStudentService studentService;;
    @Autowired
    private ThAccessAddressService thAccessAddressService;
    @Override
    public List<ThStudyDetailVO> listByPage(ThStudyDetailQuery query) {
@@ -100,5 +118,54 @@
        return thStudyDetailVOS;
    }
    @Override
    public ThPlatformStudentRespDTO getStudyRecordByIdcard(ThStudyDetailQuery query) {
        if(StringUtils.isEmpty(query.getIdcard())){
            throw new BusinessException(this.getClass(), ResultConstants.PARAM_ERROR_NULL,"学生身份证不可为空");
        }
        if(query.getInstitutionId() == null){
            throw new BusinessException(this.getClass(), ResultConstants.PARAM_ERROR_NULL,"学生所属机构不可为空");
        }
        //获取该机构访问路径
        ThAccessAddress accessAddress = thAccessAddressService.getByInstitutionIdAndType(query.getInstitutionId(), AccessAddressType.STUDY_RECORD.getType());
        Map<String,String> params = new HashMap<>();
        params.put("idcard",query.getIdcard());
        String json = HttpClientUtil.doGet(accessAddress.getUrl(), params);
        ReturnVO<String> returnVo = JSONObject.parseObject(json, new TypeReference<ReturnVO<String>>() {});
        if(returnVo.getCode() == null || returnVo.getCode() != 200){
            throw new ServiceException("获取三方数据数据异常");
        }
        ThPlatformStudentRespDTO thPlatformStudentRespDTO = null;
        if(!StringUtils.isEmpty(returnVo.getData())){
            String decrypt = "";
            try {
                decrypt = AESUtils.decrypt(returnVo.getData());
            }catch (Exception e){
                throw new BusinessException(this.getClass(), ResultConstants.SYSTEM_ERROR,"解密异常");
            }
            if(!StringUtils.isEmpty(decrypt)){
                try {
                    thPlatformStudentRespDTO = JSONObject.parseObject(decrypt, new TypeReference<ThPlatformStudentRespDTO>() {});
                }catch (Exception e){
                    logger.error("学习实时记录反序列化失败!");
                    throw new BusinessException(this.getClass(), ResultConstants.SERIALIZE_ERROR);
                }
            }
        }
        return thPlatformStudentRespDTO;
    }
    public static void main(String[] args) {
        Map<String,String> params = new HashMap<>();
        params.put("idcard","652201198009174020");
        String s = HttpClientUtil.doGet("https://app.lgb360.com/egress/xj/getStuDetail", params);
        System.out.println(s);
    }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThSubjectTypeServiceImpl.java
对比新文件
@@ -0,0 +1,80 @@
package com.gkhy.exam.institutionalaccess.service.serviceImpl;
import com.alibaba.fastjson2.JSONArray;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.gkhy.exam.institutionalaccess.entity.ThSubjectType;
import com.gkhy.exam.institutionalaccess.mapper.ThSubjectTypeMapper;
import com.gkhy.exam.institutionalaccess.model.vo.ThSubjectTypeVO;
import com.gkhy.exam.institutionalaccess.service.ThSubjectTypeService;
import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.core.domain.entity.SysDictData;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.spring.SpringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
/**
 * @author zf
 * @email 1603559716@qq.com
 * @date 2024/8/6 15:09
 * @description ThSubjectTypeServiceImpl
 */
@Service("ThSubjectTypeService")
public class ThSubjectTypeServiceImpl extends ServiceImpl<ThSubjectTypeMapper, ThSubjectType> implements ThSubjectTypeService {
    @Autowired
    private RedisCache redisCache;
    @Override
    public void subjectTypeCache() {
        List<ThSubjectType> thSubjectTypes = baseMapper.selectList(new LambdaQueryWrapper<>());
        redisCache.setCacheObject(CacheConstants.THREE_SUBJECT_TYPE, thSubjectTypes);
    }
    @Override
    public List<ThSubjectType> getSubjectTypeList() {
        JSONArray arrayCache = SpringUtils.getBean(RedisCache.class).getCacheObject(CacheConstants.THREE_SUBJECT_TYPE);
        if (StringUtils.isNotNull(arrayCache))
        {
            return arrayCache.toList(ThSubjectType.class);
        }else {
            return baseMapper.selectList(new LambdaQueryWrapper<>());
        }
    }
    @Override
    public List<ThSubjectTypeVO> getTree() {
        List<ThSubjectType> subjectTypeList = getSubjectTypeList();
        List<ThSubjectTypeVO> children = getChildren(subjectTypeList, "0");
        return children;
    }
    private List<ThSubjectTypeVO> getChildren(List<ThSubjectType> thSubjectTypes, String parentCode){
        List<ThSubjectTypeVO> thSubjectTypeVOList = new ArrayList<>();
        List<ThSubjectType> selectList =  thSubjectTypes
                .stream()
                .filter(thSubjectType -> thSubjectType.getParentCode().equals(parentCode))
                .collect(Collectors.toList());
        for (ThSubjectType thSubjectType : selectList) {
            ThSubjectTypeVO thSubjectTypeVO = new ThSubjectTypeVO();
            thSubjectTypeVO.setId(thSubjectType.getId());
            thSubjectTypeVO.setName(thSubjectType.getName());
            thSubjectTypeVO.setCode(thSubjectType.getCode());
            thSubjectTypeVO.setParentCode(thSubjectType.getParentCode());
            //获取孩子节点
            thSubjectTypeVO.setChildren(getChildren(thSubjectTypes, thSubjectType.getCode()));
            thSubjectTypeVOList.add(thSubjectTypeVO);
        }
        return thSubjectTypeVOList;
    }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/ThstatisticServiceImpl.java
对比新文件
@@ -0,0 +1,77 @@
package com.gkhy.exam.institutionalaccess.service.serviceImpl;
import com.gkhy.exam.institutionalaccess.model.query.ThStatisticQuery;
import com.gkhy.exam.institutionalaccess.model.resp.ThStatisticRespDTO;
import com.gkhy.exam.institutionalaccess.model.vo.ThTrainVO;
import com.gkhy.exam.institutionalaccess.service.ThExamRecordService;
import com.gkhy.exam.institutionalaccess.service.ThStudentBatchService;
import com.gkhy.exam.institutionalaccess.service.ThstatisticService;
import com.ruoyi.system.domain.InstitutionalManager;
import com.ruoyi.system.service.InstitutionalManagerService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
@Service("ThstatisticService")
public class ThstatisticServiceImpl implements ThstatisticService {
    @Autowired
    private InstitutionalManagerService institutionalManagerService;
    @Autowired
    private ThStudentBatchService thStudentBatchService;
    @Autowired
    private ThExamRecordService thExamRecordService;
    @Override
    public List<ThStatisticRespDTO> getStatistic(ThStatisticQuery thStatisticQuery) {
        //获取所有平台
        List<InstitutionalManager> allList = institutionalManagerService.getAllList();
        //获取培训人员数量
        List<ThTrainVO> thTrainVOS = thStudentBatchService.getStatistic(thStatisticQuery);
        //获取考试数据
        List<ThTrainVO> examList = thExamRecordService.getStatistic(thStatisticQuery);
        //获取有考试的学生人数
        List<ThTrainVO> sudentCountList = thStudentBatchService.getStatisticHaveExam(thStatisticQuery);
        List<ThStatisticRespDTO> thStatisticRespDTOList = new ArrayList<ThStatisticRespDTO>();
        //循环平台
        for (InstitutionalManager institutionalManager : allList) {
            List<ThTrainVO> selectTrainVoList = thTrainVOS.stream().filter(thTrainVO -> thTrainVO.getInstitutionId().equals(institutionalManager.getId())).collect(Collectors.toList());
            ThStatisticRespDTO thStatisticRespDTO = new ThStatisticRespDTO();
            thStatisticRespDTO.setInstitutionName(institutionalManager.getInstitutionalName());
            if(selectTrainVoList.size() > 0){
                thStatisticRespDTO.setStudentCount(selectTrainVoList.get(0).getStudentCount());
                thStatisticRespDTO.setFinishCount(selectTrainVoList.get(0).getFinishCount());
            }else {
                thStatisticRespDTO.setStudentCount(0);
                thStatisticRespDTO.setFinishCount(0);
            }
            List<ThTrainVO> selectExamList = examList.stream().filter(thTrainVO -> thTrainVO.getInstitutionId().equals(institutionalManager.getId())).collect(Collectors.toList());
            if(selectExamList.size() > 0){
                thStatisticRespDTO.setPassCount(selectExamList.get(0).getPassCount());
            }else {
                thStatisticRespDTO.setPassCount(0);
            }
            //考试合格率
            List<ThTrainVO> selectList = sudentCountList.stream().filter(s -> s.getInstitutionId().equals(institutionalManager.getId())).collect(Collectors.toList());
            int examStudentCount = 0;
            if(selectList.size() > 0){
                examStudentCount = selectList.get(0).getStudentCount();
            }
            thStatisticRespDTO.setEaxmStudentCount(examStudentCount);
            if(examStudentCount > 0){
                thStatisticRespDTO.setPassRate((new BigDecimal(thStatisticRespDTO.getPassCount()).divide(new BigDecimal(examStudentCount), 2, BigDecimal.ROUND_HALF_UP)).multiply(new BigDecimal(100)));
            }else {
                thStatisticRespDTO.setPassRate(new BigDecimal(0));
            }
            thStatisticRespDTOList.add(thStatisticRespDTO);
        }
        return thStatisticRespDTOList;
    }
}
exam-system/src/main/java/com/gkhy/exam/institutionalaccess/service/serviceImpl/TripartiteInterfaceServiceImpl.java
@@ -5,7 +5,6 @@
import cn.hutool.core.util.IdUtil;
import com.alibaba.fastjson2.JSONObject;
import com.alibaba.fastjson2.TypeReference;
import com.gkhy.exam.institutionalaccess.config.ExecutorConfig;
import com.gkhy.exam.institutionalaccess.entity.*;
import com.gkhy.exam.institutionalaccess.enums.*;
import com.gkhy.exam.institutionalaccess.model.req.*;
@@ -60,9 +59,10 @@
    private ThStudyDetailService studyDetailService;
    @Autowired
    private ThExamRecordService examRecordService;
    @Autowired
    private ThBatchCourseChapterService batchCourseChapterService;
    @Autowired
    private ThSubjectTypeService subjectTypeService;
    @Override
    public boolean receiveQuestionBank(JSONObject jsonObject) {
@@ -163,10 +163,10 @@
                errorDataRespDTOS.add(new ThErrorDataRespDTO(courseReqDTO.getUuid(),"课程名称不可为空"));
                continue;
            }
            if(StringUtils.isEmpty(courseReqDTO.getTrainOrgName())){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(courseReqDTO.getUuid(),"培训机构名称不可为空"));
            /*if(StringUtils.isEmpty(courseReqDTO.getTrainOrgName())){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(courseReqDTO.getUuid(),"所属培训机构统一社会信用代码不可为空"));
                continue;
            }
            }*/
            if(courseReqDTO.getLessonNum() == null){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(courseReqDTO.getUuid(),"课程总课时不可为空"));
                continue;
@@ -546,7 +546,7 @@
                throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"学生删除标识不符合规范");
            }
            if (StringUtils.isEmpty(studentReqDTO.getTrainOrgName())){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(studentReqDTO.getUuid(),"培训机构名称不可为空"));
                errorDataRespDTOS.add(new ThErrorDataRespDTO(studentReqDTO.getUuid(),"所属培训机构统一社会信用代码不可为空"));
                continue;
            }
            if(StringUtils.isEmpty(studentReqDTO.getBatchUuid())){
@@ -728,6 +728,8 @@
        List<ThCourse> thCourseList = courseService.getByUuidList(reqCourseUuids);
        //获取章节
        List<ThCourseChapter> thCourseChapterList = courseChapterService.getByUuids(reqChapterUuids);
        //获取科目类别
        List<ThSubjectType> subjectTypeList = subjectTypeService.getSubjectTypeList();
        //校验
        List<ThErrorDataRespDTO> errorDataRespDTOS = new ArrayList<>();
        List<ThBatchReqDTO> saveBatchReqDTOList = new ArrayList<>();
@@ -742,8 +744,25 @@
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"班次(班级)名称不可为空"));
                continue;
            }
            if(StringUtils.isEmpty(batchReqDTO.getSubjectCode())){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"班次(班级)科目类别不可为空"));
                continue;
            }
            if(batchReqDTO.getExpectEndTime() == null){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"班次(班级)预期开始时间不可为空"));
                continue;
            }
            if(batchReqDTO.getExpectStartTime() == null){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"班次(班级)预期结束时间不可为空"));
                continue;
            }
            List<ThSubjectType> selectSubjectTypeList = subjectTypeList.stream().filter(st -> st.getCode().equals(batchReqDTO.getSubjectCode())).collect(Collectors.toList());
            if(selectSubjectTypeList.size() == 0){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"班次(班级)科目类别不合法"));
                continue;
            }
            if(StringUtils.isEmpty(batchReqDTO.getTrainOrgName())){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"培训机构名称不可为空"));
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"所属培训机构统一社会信用代码不可为空"));
                continue;
            }
            if(batchReqDTO.getHaveExam() == null || HaveExam.get(batchReqDTO.getHaveExam()) == null){
@@ -752,6 +771,14 @@
            }
            if(batchReqDTO.getStatus() == null || OpenStatus.get(batchReqDTO.getStatus()) == null ){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"批次(班级)状态标识不符合规范"));
                continue;
            }
            if(batchReqDTO.getStatus().equals(OpenStatus.START.getStatus()) && batchReqDTO.getActualStartTime() == null){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"开班后,实际开班时间不可为空"));
                continue;
            }
            if(batchReqDTO.getStatus().equals(OpenStatus.END.getStatus()) && batchReqDTO.getActualEndTime() == null){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(batchReqDTO.getUuid(),"结班,实际结束时间不可为空"));
                continue;
            }
            if(batchReqDTO.getBatchLessonNum() == null){
@@ -1287,6 +1314,7 @@
        List<ThStudentBatch> thStudentBatches = studentBatchService.getByIdCards(idcards);
        List<ThBatchCourseChapter> batchCourseChapters = batchCourseChapterService.getByChapterUuids(chapterUuids);
        //校验
        List<ThStudentBatch> updateStudentBatchList = new ArrayList<>();
        List<ThErrorDataRespDTO> errorDataRespDTOS = new ArrayList<>();
        List<ThStudyDetailReqDTO> saveStudyDetailReqDTOS = new ArrayList<>();
        for (ThStudyDetailReqDTO studentDetailReqDTO : thStudyDetailReqDTOS) {
@@ -1325,11 +1353,15 @@
                continue;
            }
            if(StringUtils.isEmpty(studentDetailReqDTO.getTrainOrgName())){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(studentDetailReqDTO.getUuid(),"培训机构名称不可为空"));
                errorDataRespDTOS.add(new ThErrorDataRespDTO(studentDetailReqDTO.getUuid(),"所属培训机构统一社会信用代码不可为空"));
                continue;
            }
            if(studentDetailReqDTO.getFinishStatus() == null || FinishStatus.get(studentDetailReqDTO.getFinishStatus()) == null){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(studentDetailReqDTO.getUuid(),"完成状态不规范"));
                errorDataRespDTOS.add(new ThErrorDataRespDTO(studentDetailReqDTO.getUuid(),"章节学习状态不规范"));
                continue;
            }
            if(studentDetailReqDTO.getCompleteStatus() == null || StudentFinishStatus.get(studentDetailReqDTO.getCompleteStatus()) == null){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(studentDetailReqDTO.getUuid(),"该学生在此批次(班级)学习状态不规范"));
                continue;
            }
            if(studentDetailReqDTO.getDuration() == null){
@@ -1425,6 +1457,13 @@
                continue;
            }
            saveStudyDetailReqDTOS.add(studentDetailReqDTO);
            //判断需要修改的批次学生
            if(studentDetailReqDTO.getCompleteStatus().equals(FinishStatus.YES.getStatus())){
                ThStudentBatch thStudentBatch = StudentBatchSelectList.get(0);
                thStudentBatch.setFinishStatus(studentDetailReqDTO.getCompleteStatus());
                updateStudentBatchList.add(thStudentBatch);
            }
        }
        //获取历史记录
@@ -1532,6 +1571,11 @@
        for (List<ThStudyTrack> thStudyTracks : splitSaveTrackList) {
            studyTrackService.insertBatch(thStudyTracks);
        }
        //修改学生完成状态
        List<List<ThStudentBatch>> splitUpdateThStudentBatchList = ListUtil.split(updateStudentBatchList, 500);
        for (List<ThStudentBatch> studentBatcheList : splitUpdateThStudentBatchList) {
            studentBatchService.updateBatch(studentBatcheList);
        }
        return AjaxResult.success(errorDataRespDTOS);
    }
@@ -1603,7 +1647,7 @@
                continue;
            }
            if(StringUtils.isEmpty(examRecordReqDTO.getTrainOrgName())){
                errorDataRespDTOS.add(new ThErrorDataRespDTO(examRecordReqDTO.getUuid(),"培训机构名称不可为空"));
                errorDataRespDTOS.add(new ThErrorDataRespDTO(examRecordReqDTO.getUuid(),"所属培训机构统一社会信用代码不可为空"));
                continue;
            }
            if(StringUtils.isEmpty(examRecordReqDTO.getExamName())){
@@ -1757,6 +1801,7 @@
        thBatch.setStatus(OpenStatus.START.getStatus());
        thBatch.setUpdateTime(LocalDateTime.now());
        thBatch.setUpdateBy(institutionUser.getInstitutionalName());
        thBatch.setActualStartTime(LocalDateTime.now());
        batchService.updateById(thBatch);
        return AjaxResult.success();
    }
@@ -1798,10 +1843,11 @@
        thBatch.setStatus(OpenStatus.END.getStatus());
        thBatch.setUpdateTime(LocalDateTime.now());
        thBatch.setUpdateBy(institutionUser.getInstitutionalName());
        thBatch.setActualEndTime(LocalDateTime.now());
        batchService.updateById(thBatch);
        studentBatchService.updateFinishStatusByBatchUuid(thBatchEndReqDTO.getBatchUuid());
        return AjaxResult.success();
    }
    private void validateStudyDetail(ThStudyDetailReqDTO studentDetailReqDTO) {
@@ -1836,7 +1882,7 @@
            throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"课程章节不存在");
        }
        if(StringUtils.isEmpty(studentDetailReqDTO.getTrainOrgName())){
            throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"培训机构名称不可为空");
            throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"所属培训机构统一社会信用代码不可为空");
        }
        if(studentDetailReqDTO.getFinishStatus() == null || FinishStatus.get(studentDetailReqDTO.getFinishStatus()) == null){
            throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"完成状态不规范");
@@ -1936,7 +1982,7 @@
                throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"实名认证照不可为空");
            }
            if (StringUtils.isEmpty(studentReqDTO.getTrainOrgName())){
                throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"培训机构名称不可为空");
                throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"所属培训机构统一社会信用代码不可为空");
            }
            /*if(CollectionUtils.isEmpty(studentReqDTO.getBatchUuids())){
                throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"关联课程uuidd不可为空");
@@ -1970,7 +2016,7 @@
            throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"课程名称不可为空");
        }
        if(StringUtils.isEmpty(courseReqDTO.getTrainOrgName())){
            throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"培训机构名称不可为空");
            throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"所属培训机构统一社会信用代码不可为空");
        }
        if(courseReqDTO.getLessonNum() == null){
            throw new BusinessException(this.getClass(), ResultConstants.THREE_INSTITUTION_PARAMM_NULL,"总课时不可为空");
exam-system/src/main/resources/mapper/institutionaccess/ThBatchMapper.xml
@@ -8,11 +8,17 @@
            batch_name,
            institution_id,
            institution_name,
            train_org_name,
            have_exam,
            status,
            del_flag,
            create_time,
            update_time
            update_time,
            actual_start_time,
            actual_end_time,
            expect_start_time,
            expect_end_time,
            subject_code
        from th_batch where del_flag = 0
        <if test="query.institutionId != null">
            and institution_id = #{query.institutionId}
@@ -20,11 +26,17 @@
        <if test="query.batchName != null and query.batchName != ''">
            and batch_name like concat('%', #{query.batchaName}, '%')
        </if>
        <if test="query.subjectCode != null and query.subjectCode != ''">
            and subject_code like concat(#{query.subjectCode}, '%')
        </if>
        <if test="query.trainOrgName != null and query.trainOrgName != ''">
            and train_org_name = #{query.trainOrgName}, '%')
        </if>
        <if test="query.startTime != null"><!-- 开始时间检索 -->
            and date_format(d.create_time,'%y-%m-%d') &gt;= date_format(#{query.startTime},'%y-%m-%d')
            and date_format(actual_start_time,'%y-%m-%d') &gt;= date_format(#{query.startTime},'%y-%m-%d')
        </if>
        <if test="query.endTime != null"><!-- 结束时间检索 -->
            and date_format(d.create_time,'%y-%m-%d') &lt;= date_format(#{query.endTime},'%y-%m-%d')
            and date_format(actual_start_time,'%y-%m-%d') &lt;= date_format(#{query.endTime},'%y-%m-%d')
        </if>
        order by id desc
@@ -32,11 +44,12 @@
    <!--批量插入-->
    <insert id="insertBatch">
        INSERT INTO th_batch (id, uuid, institution_id, institution_name,batch_name,have_exam,status,
        batch_lesson_num,train_org_name, del_flag,create_time,update_time,create_by,update_by) VALUES
        batch_lesson_num,train_org_name, del_flag,create_time,update_time,create_by,update_by,
            actual_start_time,actual_end_time,expect_start_time,expect_end_time,subject_code) VALUES
        <foreach collection="batchList" separator="," item="item">
            (#{item.id},#{item.uuid},#{item.institutionId},#{item.institutionName},#{item.batchName},#{item.haveExam},#{item.status},
            #{item.batchLessonNum},#{item.trainOrgName},#{item.delFlag},#{item.createTime},
            #{item.updateTime},#{item.createBy},#{item.updateBy})
            #{item.updateTime},#{item.createBy},#{item.updateBy},#{item.actualStartTime},#{item.actualEndTime},#{item.expectStartTime},#{item.expectEndTime},#{item.subjectCode})
        </foreach>
    </insert>
@@ -76,7 +89,22 @@
                    update_by = #{item.updateBy},
                </if>
                <if test="item.updateTime != null" >
                    update_time = #{item.updateTime}
                    update_time = #{item.updateTime},
                </if>
                <if test="item.actualStartTime != null" >
                    actual_start_time = #{item.actualStartTime},
                </if>
                <if test="item.actualEndTime != null" >
                    actual_end_time = #{item.actualEndTime},
                </if>
                <if test="item.expectStartTime != null" >
                    expect_start_time = #{item.expectStartTime},
                </if>
                <if test="item.expectEndTime != null" >
                    expect_end_time = #{item.expectEndTime},
                </if>
                <if test="item.subjectCode != null and item.subjectCode != ''" >
                    subject_code = #{item.subjectCode}
                </if>
            </set>
            where id = #{item.id}
@@ -122,7 +150,7 @@
    <select id="getByUuids" resultType="com.gkhy.exam.institutionalaccess.entity.ThBatch">
        select id, uuid, institution_id, institution_name,batch_name,have_exam,status,
        batch_lesson_num,train_org_name
        batch_lesson_num,train_org_name,actual_start_time,actual_end_time,expect_start_time,expect_end_time,subject_code
        from th_batch
        where del_flag = 0 and uuid in
        <foreach collection="batchUuids" item="uuid" index ="index" open="(" close=")" separator=",">
exam-system/src/main/resources/mapper/institutionaccess/ThExamRecordMapper.xml
@@ -46,5 +46,31 @@
        </foreach>
    </select>
    <select id="getStatistic" resultType="com.gkhy.exam.institutionalaccess.model.vo.ThTrainVO">
        SELECT
        e.institution_id,
        count( e.institution_id ) passCount
        FROM
        th_exam_record e
        LEFT JOIN th_batch b ON e.batch_uuid = b.uuid
        WHERE
        e.del_flag = 0
        AND e.exam_is_pass = 1
        AND b.have_exam = 1
        <if test="query.subjectCode != null and query.subjectCode != ''">
            and b.subject_code like concat(#{query.subjectCode}, '%')
        </if>
        <if test="query.trainOrgName != null and query.trainOrgName != ''">
            and b.train_org_name = #{query.trainOrgName}, '%')
        </if>
        <if test="query.startTime != null"><!-- 开始时间检索 -->
            and date_format(b.actual_start_time,'%y-%m-%d') &gt;= date_format(#{query.startTime},'%y-%m-%d')
        </if>
        <if test="query.endTime != null"><!-- 结束时间检索 -->
            and date_format(b.actual_start_time,'%y-%m-%d') &lt;= date_format(#{query.endTime},'%y-%m-%d')
        </if>
        GROUP BY
        e.institution_id
    </select>
</mapper>
exam-system/src/main/resources/mapper/institutionaccess/ThStudentBatchMapper.xml
@@ -127,7 +127,7 @@
    </select>
    <select id="getByIdCards" resultType="com.gkhy.exam.institutionalaccess.entity.ThStudentBatch" >
        select idcard, name, sex, phone, auth_photo,train_org_name, institution_id, institution_name,
        select id,uuid,idcard, name, sex, phone, auth_photo,train_org_name, institution_id, institution_name,
        industry,occupation,post,finish_status,batch_uuid from th_student_batch where del_flag = 0 and idcard in
        <foreach collection="idcards" item="idcard" index ="index" open="(" close=")" separator=",">
            #{idcard}
@@ -147,5 +147,58 @@
          AND bc.course_uuid = #{courseUuid}
    </select>
    <select id="getStatistic" resultType="com.gkhy.exam.institutionalaccess.model.vo.ThTrainVO">
        SELECT
        sb.institution_id,
        count( sb.institution_id ) studentCount,
        sum(case when sb.finish_status=1 then 1 else 0 end) finishCount
        FROM
        th_student_batch sb
        LEFT JOIN th_batch b ON sb.batch_uuid = b.uuid
        WHERE
        sb.del_flag = 0
        <if test="query.subjectCode != null and query.subjectCode != ''">
            and b.subject_code like concat(#{query.subjectCode}, '%')
        </if>
        <if test="query.trainOrgName != null and query.trainOrgName != ''">
            and b.train_org_name = #{query.trainOrgName}, '%')
        </if>
        <if test="query.startTime != null"><!-- 开始时间检索 -->
            and date_format(b.actual_start_time,'%y-%m-%d') &gt;= date_format(#{query.startTime},'%y-%m-%d')
        </if>
        <if test="query.endTime != null"><!-- 结束时间检索 -->
            and date_format(b.actual_start_time,'%y-%m-%d') &lt;= date_format(#{query.endTime},'%y-%m-%d')
        </if>
        GROUP BY
        sb.institution_id
    </select>
    <select id="getStatisticHaveExam" resultType="com.gkhy.exam.institutionalaccess.model.vo.ThTrainVO">
        SELECT
        sb.institution_id,
        count( sb.institution_id ) studentCount,
        sum(case when sb.finish_status=1 then 1 else 0 end) finishCount
        FROM
        th_student_batch sb
        LEFT JOIN th_batch b ON sb.batch_uuid = b.uuid
        WHERE
        sb.del_flag = 0
        AND b.have_exam = 1
        <if test="query.subjectCode != null and query.subjectCode != ''">
            and b.subject_code like concat(#{query.subjectCode}, '%')
        </if>
        <if test="query.trainOrgName != null and query.trainOrgName != ''">
            and b.train_org_name = #{query.trainOrgName}, '%')
        </if>
        <if test="query.startTime != null"><!-- 开始时间检索 -->
            and date_format(b.actual_start_time,'%y-%m-%d') &gt;= date_format(#{query.startTime},'%y-%m-%d')
        </if>
        <if test="query.endTime != null"><!-- 结束时间检索 -->
            and date_format(b.actual_start_time,'%y-%m-%d') &lt;= date_format(#{query.endTime},'%y-%m-%d')
        </if>
        GROUP BY
        sb.institution_id
    </select>
</mapper>
exam-system/src/main/resources/mapper/institutionaccess/ThStudyDetailMapper.xml
@@ -20,7 +20,8 @@
            d.finish_position,
            d.video_url,
            d.lesson_report_url,
            d.create_time
            d.create_time,
            d.complete_status
        FROM
            th_study_detail d
        where d.del_flag = 0
@@ -70,12 +71,13 @@
    <insert id="insertBatch">
        INSERT INTO th_study_detail (id,uuid,serial_num, idcard,institution_id, institution_name,course_uuid, train_org_name,batch_uuid,chapter_uuid,
        finish_status,duration,start_time,finish_time,start_position,finish_position,video_url,lesson_report_url,del_flag,create_time,update_time,create_by,update_by) VALUES
        finish_status,duration,start_time,finish_time,start_position,finish_position,video_url,lesson_report_url,del_flag,create_time,update_time,create_by,update_by,
        complete_status) VALUES
        <foreach collection="list" separator="," item="item">
            (#{item.id},#{item.uuid},#{item.serialNum},#{item.idcard},#{item.institutionId},#{item.institutionName},#{item.courseUuid},#{item.trainOrgName},#{item.batchUuid},#{item.chapterUuid},
             #{item.finishStatus},#{item.duration},#{item.startTime},
            #{item.finishTime},#{item.startPosition},#{item.finishPosition},#{item.videoUrl},#{item.lessonReportUrl},#{item.delFlag},#{item.createTime},
            #{item.updateTime},#{item.createBy},#{item.updateBy})
            #{item.updateTime},#{item.createBy},#{item.updateBy},#{item.completeStatus})
        </foreach>
    </insert>
    <update id="updateBatch" parameterType="java.util.List" >
@@ -140,7 +142,10 @@
                    update_by = #{item.updateBy},
                </if>
                <if test="item.updateTime != null" >
                    update_time = #{item.updateTime}
                    update_time = #{item.updateTime},
                </if>
                <if test="item.completeStatus != null" >
                    complete_status = #{item.completeStatus}
                </if>
            </set>
            where id = #{item.id}
ruoyi-admin/src/main/resources/application.yml
@@ -36,7 +36,7 @@
    # 国际化资源文件路径
    basename: i18n/messages
  profiles:
    active: pro
    active: dev
  # 文件上传
  servlet:
    multipart:
ruoyi-common/src/main/java/com/ruoyi/common/constant/CacheConstants.java
@@ -57,4 +57,9 @@
     * 七天内访问请求token次数
     */
    public static final String THREE_TOKEN_CNT_KEY = "swspkmas:three_token_cnt:";
    /**
     * 三陪类型
     */
    public static final String THREE_SUBJECT_TYPE = "swspkmas:three_subject_type";
}
ruoyi-common/src/main/java/com/ruoyi/common/core/domain/model/ResultVO.java
对比新文件
@@ -0,0 +1,16 @@
package com.ruoyi.common.core.domain.model;
import lombok.Data;
/**
 * @author zf
 * @email 1603559716@qq.com
 * @date 2024/7/29 10:06
 * @description ResultVO
 */
@Data
public class ResultVO<T> {
    private Integer code;
    private String msg;
    private T data;
}
ruoyi-common/src/main/java/com/ruoyi/common/utils/HttpClientUtil.java
对比新文件
@@ -0,0 +1,150 @@
package com.ruoyi.common.utils;
import java.io.IOException;
import java.net.URI;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import org.apache.http.NameValuePair;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.client.utils.URIBuilder;
import org.apache.http.entity.ContentType;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
public class HttpClientUtil {
    /**
     * 带参数的get请求
     * @param url
     * @param param
     * @return String
     */
    public static String doGet(String url, Map<String, String> param) {
        // 创建Httpclient对象
        CloseableHttpClient httpclient = HttpClients.createDefault();
        String resultString = "";
        CloseableHttpResponse response = null;
        try {
            // 创建uri
            URIBuilder builder = new URIBuilder(url);
            if (param != null) {
                for (String key : param.keySet()) {
                    builder.addParameter(key, param.get(key));
                }
            }
            URI uri = builder.build();
            // 创建http GET请求
            HttpGet httpGet = new HttpGet(uri);
            // 执行请求
            response = httpclient.execute(httpGet);
            // 判断返回状态是否为200
            if (response.getStatusLine().getStatusCode() == 200) {
                resultString = EntityUtils.toString(response.getEntity(), "UTF-8");
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                if (response != null) {
                    response.close();
                }
                httpclient.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return resultString;
    }
    /**
     * 不带参数的get请求
     * @param url
     * @return String
     */
    public static String doGet(String url) {
        return doGet(url, null);
    }
    /**
     * 带参数的post请求
     * @param url
     * @param param
     * @return String
     */
    public static String doPost(String url, String param) {
        // 创建Httpclient对象
        CloseableHttpClient httpClient = HttpClients.createDefault();
        CloseableHttpResponse response = null;
        String resultString = "";
        try {
            // 创建Http Post请求
            HttpPost httpPost = new HttpPost(url);
            // 创建参数列表
            StringEntity bodyData = new StringEntity(param.toString(), "UTF-8");
            httpPost.setEntity(bodyData);
            // 执行http请求
            response = httpClient.execute(httpPost);
            resultString = EntityUtils.toString(response.getEntity(), "utf-8");
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                response.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return resultString;
    }
    /**
     * 不带参数的post请求
     * @param url
     * @return String
     */
    public static String doPost(String url) {
        return doPost(url, null);
    }
    /**
     * 传送json类型的post请求
     * @param url
     * @param json
     * @return String
     */
    public static String doPostJson(String url, String json) {
        // 创建Httpclient对象
        CloseableHttpClient httpClient = HttpClients.createDefault();
        CloseableHttpResponse response = null;
        String resultString = "";
        try {
            // 创建Http Post请求
            HttpPost httpPost = new HttpPost(url);
            // 创建请求内容
            StringEntity entity = new StringEntity(json, ContentType.APPLICATION_JSON);
            httpPost.setEntity(entity);
            // 执行http请求
            response = httpClient.execute(httpPost);
            resultString = EntityUtils.toString(response.getEntity(), "utf-8");
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                response.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return resultString;
    }
}
ruoyi-system/src/main/java/com/ruoyi/system/domain/InstitutionalManager.java
@@ -50,4 +50,6 @@
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
    @TableField(fill = FieldFill.INSERT_UPDATE)
    private LocalDateTime updateTime;
    private String reason;
}
ruoyi-system/src/main/java/com/ruoyi/system/domain/ThAccessAddress.java
对比新文件
@@ -0,0 +1,15 @@
package com.ruoyi.system.domain;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
@TableName("th_access_address")
@Data
public class ThAccessAddress {
    private Long id;
    private Long institutionId;
    private Byte type;
    private String url;
}
ruoyi-system/src/main/java/com/ruoyi/system/domain/enums/AccessAddressType.java
对比新文件
@@ -0,0 +1,40 @@
package com.ruoyi.system.domain.enums;
public enum AccessAddressType {
    NOTICE((byte)0,"通知"),
    STUDY_RECORD((byte)1,"学习记录"),
    ;
    private Byte type;
    private String desc;
    AccessAddressType(Byte type, String desc) {
        this.type = type;
        this.desc = desc;
    }
    public Byte getType() {
        return type;
    }
    public void setType(Byte type) {
        this.type = type;
    }
    public String getDesc() {
        return desc;
    }
    public void setDesc(String desc) {
        this.desc = desc;
    }
    public static AccessAddressType get(Byte status) {
        for (AccessAddressType accessAddressType : AccessAddressType.values()) {
            if (accessAddressType.getType() == status) {
                return accessAddressType;
            }
        }
        return null;
    }
}
ruoyi-system/src/main/java/com/ruoyi/system/domain/req/InstitutionModStatusReqDTO.java
@@ -6,4 +6,5 @@
public class InstitutionModStatusReqDTO {
    private Long id;
    private Byte status;
    private String reason;
}
ruoyi-system/src/main/java/com/ruoyi/system/domain/vo/InstitutionVo.java
对比新文件
@@ -0,0 +1,10 @@
package com.ruoyi.system.domain.vo;
import lombok.Data;
@Data
public class InstitutionVo {
    private String institutionName;
    private Byte status;
    private String reason;
}
ruoyi-system/src/main/java/com/ruoyi/system/mapper/ThAccessAddressMapper.java
对比新文件
@@ -0,0 +1,12 @@
package com.ruoyi.system.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.ruoyi.system.domain.ThAccessAddress;
import org.apache.ibatis.annotations.Mapper;
import org.springframework.stereotype.Repository;
@Repository
@Mapper
public interface ThAccessAddressMapper extends BaseMapper<ThAccessAddress> {
}
ruoyi-system/src/main/java/com/ruoyi/system/service/InstitutionalManagerService.java
@@ -27,4 +27,6 @@
    int modStatus(InstitutionModStatusReqDTO reqDTO);
    List<InstitutionalManager> selectInstitutionInfo();
    List<InstitutionalManager> getAllList();
}
ruoyi-system/src/main/java/com/ruoyi/system/service/ThAccessAddressService.java
对比新文件
@@ -0,0 +1,8 @@
package com.ruoyi.system.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.ruoyi.system.domain.ThAccessAddress;
public interface ThAccessAddressService extends IService<ThAccessAddress> {
    ThAccessAddress getByInstitutionIdAndType(Long institutionId, Byte type);
}
ruoyi-system/src/main/java/com/ruoyi/system/service/impl/InstitutionalManagerServiceImpl.java
@@ -1,15 +1,26 @@
package com.ruoyi.system.service.impl;
import com.alibaba.fastjson2.JSONObject;
import com.alibaba.fastjson2.TypeReference;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ruoyi.common.constant.ResultConstants;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.model.ResultVO;
import com.ruoyi.common.enums.InstitutionStatus;
import com.ruoyi.common.exception.BusinessException;
import com.ruoyi.common.signature.AESUtils;
import com.ruoyi.common.utils.HttpClientUtil;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.system.domain.InstitutionalManager;
import com.ruoyi.system.domain.ThAccessAddress;
import com.ruoyi.system.domain.enums.AccessAddressType;
import com.ruoyi.system.domain.query.InstitutionManagerQuery;
import com.ruoyi.system.domain.req.InstitutionModStatusReqDTO;
import com.ruoyi.system.domain.vo.InstitutionVo;
import com.ruoyi.system.mapper.ThAccessAddressMapper;
import com.ruoyi.system.service.InstitutionalManagerService;
import com.ruoyi.system.domain.req.InstitutionalManagerAddReqDTO;
import com.ruoyi.system.domain.req.InstitutionalManagerModReqDTO;
@@ -17,16 +28,19 @@
import com.ruoyi.common.enums.coalmineEnums.DeleteStatusEnum;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.RandomUtil;
import com.ruoyi.system.service.ThAccessAddressService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.List;
import java.util.*;
@Service("InstitutionalManagerService")
public class InstitutionalManagerServiceImpl extends ServiceImpl<InstitutionalManagerMapper, InstitutionalManager> implements InstitutionalManagerService {
    @Autowired
    private InstitutionalManagerMapper institutionalManagerMapper;
    @Autowired
    private ThAccessAddressService thAccessAddressService;
    @Override
    public int add(InstitutionalManagerAddReqDTO reqDTO) {
@@ -88,10 +102,25 @@
    @Override
    public int modStatus(InstitutionModStatusReqDTO reqDTO) {
        InstitutionalManager institutionalManager = new InstitutionalManager();
        //获取该机构信息
        InstitutionalManager institutionalManager = this.getById(reqDTO.getId());
        //获取该机构访问路径
        ThAccessAddress accessAddress = thAccessAddressService.getByInstitutionIdAndType(reqDTO.getId(), AccessAddressType.NOTICE.getType());
        //推送到机构
        InstitutionVo institutionVo = new InstitutionVo();
        institutionVo.setInstitutionName(institutionalManager.getInstitutionalName());
        institutionVo.setStatus(reqDTO.getStatus());
        institutionVo.setReason(reqDTO.getReason());
       /* String json = HttpClientUtil.doPost(accessAddress.getUrl(), JSONObject.toJSONString(institutionVo));
        ResultVO<String> returnVo = JSONObject.parseObject(json, new TypeReference<ResultVO<String>>() {});
        if(returnVo.getCode() == null || returnVo.getCode() != 200){
            throw new ServiceException("推送平台信息异常");
        }*/
        institutionalManager.setId(reqDTO.getId());
        institutionalManager.setStatus(reqDTO.getStatus());
        return institutionalManagerMapper.updateById(institutionalManager);
        institutionalManager.setReason(reqDTO.getReason());
        int i = institutionalManagerMapper.updateById(institutionalManager);
        return i;
    }
    @Override
@@ -99,6 +128,11 @@
        return institutionalManagerMapper.selectList(new LambdaQueryWrapper<InstitutionalManager>().eq(InstitutionalManager::getDelFlag,DeleteStatusEnum.NO.getStatus()));
    }
    @Override
    public List<InstitutionalManager> getAllList() {
        return institutionalManagerMapper.selectList(new LambdaQueryWrapper<InstitutionalManager>().eq(InstitutionalManager::getDelFlag,DeleteStatusEnum.NO.getStatus()));
    }
    //生成编码
    private Long generateCode() {
ruoyi-system/src/main/java/com/ruoyi/system/service/impl/ThAccessAddressServiceImpl.java
对比新文件
@@ -0,0 +1,17 @@
package com.ruoyi.system.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ruoyi.system.domain.ThAccessAddress;
import com.ruoyi.system.mapper.ThAccessAddressMapper;
import com.ruoyi.system.service.ThAccessAddressService;
import org.springframework.stereotype.Service;
@Service("thAccessAddressService")
public class ThAccessAddressServiceImpl extends ServiceImpl<ThAccessAddressMapper, ThAccessAddress> implements ThAccessAddressService {
    public ThAccessAddress getByInstitutionIdAndType(Long institutionId, Byte type) {
        return baseMapper.selectOne(new LambdaQueryWrapper<ThAccessAddress>().eq(ThAccessAddress::getInstitutionId, institutionId)
                .eq(ThAccessAddress::getType, type));
    }
}