Bläddra i källkod

Merge branch 'pre'

dzx 1 år sedan
förälder
incheckning
9c1a2626ab
51 ändrade filer med 1535 tillägg och 98 borttagningar
  1. 11 2
      src/main/java/com/xjrsoft/module/banding/service/impl/BandingTaskServiceImpl.java
  2. 47 29
      src/main/java/com/xjrsoft/module/base/controller/BaseClassCourseController.java
  3. 15 5
      src/main/java/com/xjrsoft/module/base/controller/WhitelistManagementController.java
  4. 11 7
      src/main/java/com/xjrsoft/module/base/dto/AddWhitelistManagementDto.java
  5. 34 0
      src/main/java/com/xjrsoft/module/base/dto/SetWhitelistEndTimeDto.java
  6. 12 6
      src/main/java/com/xjrsoft/module/base/entity/WhitelistManagement.java
  7. 9 1
      src/main/java/com/xjrsoft/module/base/service/impl/WhitelistManagementServiceImpl.java
  8. 32 0
      src/main/java/com/xjrsoft/module/base/vo/BaseClassCourseExcelVo.java
  9. 1 0
      src/main/java/com/xjrsoft/module/base/vo/BaseClassCoursePageVo.java
  10. 57 12
      src/main/java/com/xjrsoft/module/databoard/controller/DataboardController.java
  11. 609 0
      src/main/java/com/xjrsoft/module/databoard/controller/DatadetailController.java
  12. 31 0
      src/main/java/com/xjrsoft/module/databoard/dto/StatisticsDetailDto.java
  13. 1 0
      src/main/java/com/xjrsoft/module/databoard/dto/StatisticsDto.java
  14. 29 0
      src/main/java/com/xjrsoft/module/databoard/vo/DistributionVo.java
  15. 27 0
      src/main/java/com/xjrsoft/module/databoard/vo/DurationVo.java
  16. 30 0
      src/main/java/com/xjrsoft/module/databoard/vo/HealthItemCountVo.java
  17. 35 0
      src/main/java/com/xjrsoft/module/databoard/vo/HealthStatisticsDetailVo.java
  18. 29 0
      src/main/java/com/xjrsoft/module/databoard/vo/ItemCountAmountVo.java
  19. 27 0
      src/main/java/com/xjrsoft/module/databoard/vo/ItemCountVo.java
  20. 27 0
      src/main/java/com/xjrsoft/module/databoard/vo/ItemDoubleVo.java
  21. 39 0
      src/main/java/com/xjrsoft/module/databoard/vo/ProcessStatisticsDetailVo.java
  22. 3 3
      src/main/java/com/xjrsoft/module/databoard/vo/ProcessStatisticsVo.java
  23. 39 0
      src/main/java/com/xjrsoft/module/databoard/vo/StudnetStatisticsDetailVo.java
  24. 39 0
      src/main/java/com/xjrsoft/module/databoard/vo/SubscriptionStatisticsDetailVo.java
  25. 33 0
      src/main/java/com/xjrsoft/module/databoard/vo/TeacherStatisticsDetailVo.java
  26. 1 1
      src/main/java/com/xjrsoft/module/evaluate/service/impl/EvaluateResultServiceImpl.java
  27. 1 0
      src/main/java/com/xjrsoft/module/organization/service/impl/UserPostRelationServiceImpl.java
  28. 1 0
      src/main/java/com/xjrsoft/module/student/controller/BaseStudentDevelopmentController.java
  29. 29 1
      src/main/java/com/xjrsoft/module/student/controller/BaseStudentInfoController.java
  30. 1 0
      src/main/java/com/xjrsoft/module/student/controller/BaseStudentScholarshipCategoryController.java
  31. 2 3
      src/main/java/com/xjrsoft/module/student/controller/BaseStudentScholarshipReleaseController.java
  32. 38 0
      src/main/java/com/xjrsoft/module/student/controller/StudentLeaveController.java
  33. 3 0
      src/main/java/com/xjrsoft/module/student/dto/BaseStudentScholarshipCategoryPageDto.java
  34. 28 0
      src/main/java/com/xjrsoft/module/student/dto/StudentLeavePageDto.java
  35. 5 0
      src/main/java/com/xjrsoft/module/student/mapper/StudentLeaveMapper.java
  36. 4 0
      src/main/java/com/xjrsoft/module/student/service/IBaseStudentScholarshipReleaseService.java
  37. 7 0
      src/main/java/com/xjrsoft/module/student/service/IStudentLeaveService.java
  38. 19 7
      src/main/java/com/xjrsoft/module/student/service/impl/BaseStudentScholarshipApplicantServiceImpl.java
  39. 20 0
      src/main/java/com/xjrsoft/module/student/service/impl/BaseStudentScholarshipReleaseServiceImpl.java
  40. 10 0
      src/main/java/com/xjrsoft/module/student/service/impl/StudentLeaveServiceImpl.java
  41. 7 0
      src/main/java/com/xjrsoft/module/student/vo/BaseStudentDevelopmentVo.java
  42. 5 5
      src/main/java/com/xjrsoft/module/student/vo/ScholarshipApplicantImportVo.java
  43. 53 0
      src/main/java/com/xjrsoft/module/student/vo/StudentLeavePageVo.java
  44. 26 0
      src/main/java/com/xjrsoft/module/student/vo/WhitelistInfoVo.java
  45. 2 2
      src/main/java/com/xjrsoft/module/system/service/impl/LoginServiceImpl.java
  46. 1 10
      src/main/java/com/xjrsoft/module/workflow/service/impl/WorkflowExecuteServiceImpl.java
  47. 25 0
      src/main/java/com/xjrsoft/module/workflow/utils/WorkFlowUtil.java
  48. 1 1
      src/main/resources/mapper/student/BaseStudentDevelopmentMapper.xml
  49. 1 1
      src/main/resources/mapper/student/PbVXsxxsfytbMapper.xml
  50. 16 0
      src/main/resources/mapper/student/StudentLeaveMapper.xml
  51. 2 2
      src/main/resources/sqlScript/all_sql.sql

+ 11 - 2
src/main/java/com/xjrsoft/module/banding/service/impl/BandingTaskServiceImpl.java

@@ -35,9 +35,11 @@ import com.xjrsoft.module.banding.vo.BandingTaskClassSureListVo;
 import com.xjrsoft.module.banding.vo.BandingTaskPageVo;
 import com.xjrsoft.module.banding.vo.IdManyCountVo;
 import com.xjrsoft.module.base.entity.BaseClass;
+import com.xjrsoft.module.base.entity.BaseGrade;
 import com.xjrsoft.module.base.entity.BaseMajorSet;
 import com.xjrsoft.module.base.mapper.BaseMajorSetMapper;
 import com.xjrsoft.module.base.service.IBaseClassService;
+import com.xjrsoft.module.base.service.IBaseGradeService;
 import com.xjrsoft.module.organization.entity.User;
 import com.xjrsoft.module.organization.entity.UserRoleRelation;
 import com.xjrsoft.module.organization.service.IUserRoleRelationService;
@@ -97,7 +99,7 @@ public class BandingTaskServiceImpl extends MPJBaseServiceImpl<BandingTaskMapper
     private final IBaseStudentSchoolRollService schoolRollService;
     private final IBaseStudentService studentService;
     private final IBaseStudentFamilyService familyService;
-
+    private final IBaseGradeService gradeService;
     private final BaseMajorSetMapper majorSetMapper;
 
 
@@ -575,7 +577,6 @@ public class BandingTaskServiceImpl extends MPJBaseServiceImpl<BandingTaskMapper
         Map<Long, Integer> classBoy = classSure.stream().collect(Collectors.toMap(BandingTaskClassSureListVo::getId, BandingTaskClassSureListVo::getMaleCount));
         Map<Long, Integer> classGirl = classSure.stream().collect(Collectors.toMap(BandingTaskClassSureListVo::getId, BandingTaskClassSureListVo::getFemaleCount));
 
-
         //生成班级数据
         Map<Long, Long> classMap = new HashMap<>();
         Map<Long, Long> taskClassMajorMap = new HashMap<>();
@@ -583,6 +584,13 @@ public class BandingTaskServiceImpl extends MPJBaseServiceImpl<BandingTaskMapper
         List<Long> classIds = classStudents.stream().map(BandingTaskClassStudent::getBandingTaskClassId).collect(Collectors.toList());
         List<BandingTaskClass> classList = taskClassMapper.selectList(new QueryWrapper<BandingTaskClass>().lambda().in(BandingTaskClass::getId, classIds));
 
+        long maxCode = classService.count(
+                new QueryWrapper<BaseClass>().lambda()
+                        .eq(BaseClass::getGradeId, bandingTask.getGradeId())
+        );
+        BaseGrade baseGrade = gradeService.getById(bandingTask.getGradeId());
+        String gradeCode = baseGrade.getTitle().replace("年", "");
+
         Map<Long, Long> majorDeptMap = majorSetMapper.selectList(new QueryWrapper<BaseMajorSet>()).stream().collect(Collectors.toMap(BaseMajorSet::getId, BaseMajorSet::getDepartmentId));
         for (BandingTaskClass taskClass : classList) {
             BaseClass baseClass = new BaseClass() {{
@@ -595,6 +603,7 @@ public class BandingTaskServiceImpl extends MPJBaseServiceImpl<BandingTaskMapper
                 setDeleteMark(DeleteMark.NODELETE.getCode());
                 setEnrollType(bandingTask.getEnrollType());
                 setOrgId(majorDeptMap.get(taskClass.getMajorSetId()));
+                setCode(gradeCode + String.format("%03d", maxCode));
             }};
 
             classService.save(baseClass);

+ 47 - 29
src/main/java/com/xjrsoft/module/base/controller/BaseClassCourseController.java

@@ -26,6 +26,7 @@ import com.xjrsoft.module.base.service.IBaseClassCourseService;
 import com.xjrsoft.module.base.service.IBaseClassService;
 import com.xjrsoft.module.base.service.IBaseCourseSubjectService;
 import com.xjrsoft.module.base.service.IBaseSemesterService;
+import com.xjrsoft.module.base.vo.BaseClassCourseExcelVo;
 import com.xjrsoft.module.base.vo.BaseClassCourseExportListVo;
 import com.xjrsoft.module.base.vo.BaseClassCourseListVo;
 import com.xjrsoft.module.base.vo.BaseClassCoursePageVo;
@@ -56,7 +57,6 @@ import java.util.Date;
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
-import java.util.stream.Collectors;
 
 /**
  * @title: 班级课程
@@ -207,7 +207,7 @@ public class BaseClassCourseController {
     @PostMapping("/import")
     @ApiOperation(value = "导入")
     public RT<Boolean> importData(@RequestParam MultipartFile file) throws IOException {
-        List<BaseClassCoursePageVo> savedDataList = EasyExcel.read(file.getInputStream()).headRowNumber(3).head(BaseClassCoursePageVo.class).sheet().doReadSync();
+        List<BaseClassCourseExcelVo> savedDataList = EasyExcel.read(file.getInputStream()).headRowNumber(3).head(BaseClassCourseExcelVo.class).sheet().doReadSync();
 
         List<BaseClassCourse> baseClassCourses = new ArrayList<>();
         List<String> duplicateLogs = new ArrayList<>();
@@ -234,36 +234,54 @@ public class BaseClassCourseController {
             semesterMap.put(baseSemester.getName(), baseSemester.getId());
         }
 
-        for (BaseClassCoursePageVo vo : savedDataList) {
-            String[] textbookNames = vo.getTextbookName().split(" ");
-            for (String textbookName : textbookNames) {
-                try {
-                    Long classId = classMap.get(vo.getClassName());
-                    Long courseId = courseSubjectMap.get(vo.getCourseName());
-                    Long textbookId = textbookMap.get(textbookName);
-                    Long baseSemesterId = semesterMap.get(vo.getSemester());
-
-                    if (baseClassCourseService.checkExits(classId, courseId, textbookId)) {
-                        duplicateLogs.add(String.format("[输入的信息重复添加] 班级: %s, 课程: %s, 教材: %s", vo.getClassName(), vo.getCourseName(), vo.getTextbookName()));
-                        continue;
-                    }
-
-                    if (classId != null && courseId != null && textbookId != null && baseSemesterId != null) {
-                        BaseClassCourse baseClassCourse = new BaseClassCourse();
-                        baseClassCourse.setClassId(classId);
-                        baseClassCourse.setCourseId(courseId);
-                        baseClassCourse.setTextbookId(textbookId);
-                        baseClassCourse.setCreateDate(new Date());
-                        baseClassCourse.setDeleteMark(0);
-                        baseClassCourse.setBaseSemesterId(baseSemesterId);
-                        baseClassCourses.add(baseClassCourse);
+        for (BaseClassCourseExcelVo vo : savedDataList) {
+            if(vo.getClassName() == null){
+                continue;
+            }
+            if(vo.getTextbookName() != null){
+                String[] textbookNames = vo.getTextbookName().split(" ");
+                for (String textbookName : textbookNames) {
+                    try {
+                        Long classId = classMap.get(vo.getClassName());
+                        Long courseId = courseSubjectMap.get(vo.getCourseName());
+                        Long textbookId = textbookMap.get(textbookName);
+                        Long baseSemesterId = semesterMap.get(vo.getSemester());
+
+                        if (baseClassCourseService.checkExits(classId, courseId, textbookId)) {
+                            duplicateLogs.add(String.format("[输入的信息重复添加] 班级: %s, 课程: %s, 教材: %s", vo.getClassName(), vo.getCourseName(), vo.getTextbookName()));
+                            continue;
+                        }
+
+                        if (classId != null && courseId != null && textbookId != null && baseSemesterId != null) {
+                            BaseClassCourse baseClassCourse = new BaseClassCourse();
+                            baseClassCourse.setClassId(classId);
+                            baseClassCourse.setCourseId(courseId);
+                            baseClassCourse.setTextbookId(textbookId);
+                            baseClassCourse.setCreateDate(new Date());
+                            baseClassCourse.setDeleteMark(0);
+                            baseClassCourse.setBaseSemesterId(baseSemesterId);
+                            baseClassCourses.add(baseClassCourse);
+                        }
+                    } catch (NumberFormatException e) {
+                        errorLogs.add(String.format("[无法解析输入的信息] 班级: %s, 班级: %s, 教材: %s", vo.getClassName(), vo.getCourseName(), vo.getTextbookName()));
+                    } catch (Exception e) {
+                        errorLogs.add(String.format("[意外错误(检查输入的名称是否正确且存在,输入错误可能返回 null)] 班级: %s, 课程: %s, 教材: %s - 错误信息:%s", vo.getClassName(), vo.getCourseName(), vo.getTextbookName(), e.getMessage()));
                     }
-                } catch (NumberFormatException e) {
-                    errorLogs.add(String.format("[无法解析输入的信息] 班级: %s, 班级: %s, 教材: %s", vo.getClassName(), vo.getCourseName(), vo.getTextbookName()));
-                } catch (Exception e) {
-                    errorLogs.add(String.format("[意外错误(检查输入的名称是否正确且存在,输入错误可能返回 null)] 班级: %s, 课程: %s, 教材: %s - 错误信息:%s", vo.getClassName(), vo.getCourseName(), vo.getTextbookName(), e.getMessage()));
                 }
+            }else{
+                Long classId = classMap.get(vo.getClassName());
+                Long courseId = courseSubjectMap.get(vo.getCourseName());
+                Long baseSemesterId = semesterMap.get(vo.getSemester());
+
+                BaseClassCourse baseClassCourse = new BaseClassCourse();
+                baseClassCourse.setClassId(classId);
+                baseClassCourse.setCourseId(courseId);
+                baseClassCourse.setCreateDate(new Date());
+                baseClassCourse.setDeleteMark(0);
+                baseClassCourse.setBaseSemesterId(baseSemesterId);
+                baseClassCourses.add(baseClassCourse);
             }
+
         }
 
         Boolean result = baseClassCourseService.saveBatch(baseClassCourses);

+ 15 - 5
src/main/java/com/xjrsoft/module/base/controller/WhitelistManagementController.java

@@ -3,11 +3,13 @@ package com.xjrsoft.module.base.controller;
 import cn.dev33.satoken.annotation.SaCheckPermission;
 import cn.hutool.core.bean.BeanUtil;
 import com.alibaba.excel.EasyExcel;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.xjrsoft.common.model.result.RT;
 import com.xjrsoft.common.page.ConventPage;
 import com.xjrsoft.common.page.PageOutput;
 import com.xjrsoft.module.base.dto.AddWhitelistManagementDto;
+import com.xjrsoft.module.base.dto.SetWhitelistEndTimeDto;
 import com.xjrsoft.module.base.dto.UpdateWhitelistManagementDto;
 import com.xjrsoft.module.base.dto.WhitelistManagementPageDto;
 import com.xjrsoft.module.base.entity.TreeNode;
@@ -18,8 +20,6 @@ import com.xjrsoft.module.base.vo.WhitelistManagementVo;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
 import lombok.AllArgsConstructor;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
 import org.springframework.http.ResponseEntity;
 import org.springframework.web.bind.annotation.DeleteMapping;
 import org.springframework.web.bind.annotation.GetMapping;
@@ -34,7 +34,6 @@ import org.springframework.web.multipart.MultipartFile;
 import javax.validation.Valid;
 import java.io.IOException;
 import java.util.ArrayList;
-import java.util.Date;
 import java.util.LinkedHashMap;
 import java.util.List;
 import java.util.Map;
@@ -52,8 +51,6 @@ import java.util.concurrent.CompletableFuture;
 @AllArgsConstructor
 public class WhitelistManagementController {
 
-
-    private static final Logger log = LoggerFactory.getLogger(WhitelistManagementController.class);
     private final IWhitelistManagementService whitelistManagementService;
 
     @GetMapping(value = "/page")
@@ -92,6 +89,19 @@ public class WhitelistManagementController {
         return RT.ok(isSuccess);
     }
 
+    @PostMapping("/set-endtime-batch")
+    @ApiOperation(value = "批量设置结束时间")
+    @SaCheckPermission("whitelistmanagement:add")
+    public RT<Boolean> setEndtimeBatch(@Valid @RequestBody SetWhitelistEndTimeDto dto){
+        List<WhitelistManagement> list = whitelistManagementService.listByIds(dto.getIds());
+        for (WhitelistManagement whitelistManagement : list) {
+            whitelistManagement.setIsTemporary(1);
+            whitelistManagement.setEndTime(dto.getEndTime());
+        }
+        boolean updated = whitelistManagementService.updateBatchById(list);
+        return RT.ok(updated);
+    }
+
     @PutMapping
     @ApiOperation(value = "修改白名单管理")
     @SaCheckPermission("whitelistmanagement:edit")

+ 11 - 7
src/main/java/com/xjrsoft/module/base/dto/AddWhitelistManagementDto.java

@@ -2,14 +2,9 @@ package com.xjrsoft.module.base.dto;
 
 import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
-import java.io.Serializable;
-import com.fasterxml.jackson.annotation.JsonFormat;
 
-import java.time.LocalTime;
-import java.time.LocalDateTime;
-import java.math.BigDecimal;
-import java.util.List;
-import java.util.Date;
+import java.io.Serializable;
+import java.time.LocalDate;
 
 
 
@@ -45,4 +40,13 @@ public class AddWhitelistManagementDto implements Serializable {
     @ApiModelProperty("手机号")
     private String phone;
 
+    @ApiModelProperty("是否临时性的(1:是 0:否)")
+    private Integer isTemporary;
+
+    @ApiModelProperty("临时使用开始时间")
+    private LocalDate startTime;
+
+    @ApiModelProperty("临时使用结束时间")
+    private LocalDate endTime;
+
 }

+ 34 - 0
src/main/java/com/xjrsoft/module/base/dto/SetWhitelistEndTimeDto.java

@@ -0,0 +1,34 @@
+package com.xjrsoft.module.base.dto;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import org.springframework.format.annotation.DateTimeFormat;
+
+import java.io.Serializable;
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.util.List;
+
+
+/**
+* @title: 白名单管理
+* @Author brealinxx
+* @Date: 2024-06-24
+* @Version 1.0
+*/
+@Data
+public class SetWhitelistEndTimeDto implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+    * 用户id
+    */
+    @ApiModelProperty("用户id")
+    private List<Long> ids;
+
+    @DateTimeFormat(pattern = "yyyy-MM-dd")
+    @ApiModelProperty("临时使用结束时间")
+    private LocalDate endTime;
+
+}

+ 12 - 6
src/main/java/com/xjrsoft/module/base/entity/WhitelistManagement.java

@@ -2,18 +2,15 @@ package com.xjrsoft.module.base.entity;
 
 import com.baomidou.mybatisplus.annotation.FieldFill;
 import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
 import com.baomidou.mybatisplus.annotation.TableLogic;
 import com.baomidou.mybatisplus.annotation.TableName;
-import com.baomidou.mybatisplus.annotation.TableId;
-import com.github.yulichang.annotation.EntityMapping;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
+
 import java.io.Serializable;
-import java.time.LocalTime;
-import java.time.LocalDateTime;
-import java.math.BigDecimal;
-import java.util.List;
+import java.time.LocalDate;
 import java.util.Date;
 
 
@@ -82,5 +79,14 @@ public class WhitelistManagement implements Serializable {
     @ApiModelProperty("手机号")
     private String phone;
 
+    @ApiModelProperty("是否临时性的(1:是 0:否)")
+    private Integer isTemporary;
+
+    @ApiModelProperty("临时使用开始时间")
+    private LocalDate startTime;
+
+    @ApiModelProperty("临时使用结束时间")
+    private LocalDate endTime;
+
 
 }

+ 9 - 1
src/main/java/com/xjrsoft/module/base/service/impl/WhitelistManagementServiceImpl.java

@@ -37,7 +37,9 @@ import lombok.extern.slf4j.Slf4j;
 import org.springframework.scheduling.annotation.Async;
 import org.springframework.stereotype.Service;
 
+import java.time.LocalDate;
 import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
 import java.util.ArrayList;
 import java.util.Date;
 import java.util.HashMap;
@@ -143,7 +145,7 @@ public class WhitelistManagementServiceImpl extends MPJBaseServiceImpl<Whitelist
 
         List<WhitelistManagement> whitelistManagements = new ArrayList<>();
         List<String> errorLogs = new ArrayList<>();
-
+        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
         for (Map<Integer, Object> vo : savedDataList) {
             if(vo.get(0) == null || vo.get(1) == null || vo.get(2) == null){
                 errorList.add(vo);
@@ -158,6 +160,7 @@ public class WhitelistManagementServiceImpl extends MPJBaseServiceImpl<Whitelist
             Long userId = this.getUserId(credentialNumber);
             String phone = vo.get(2).toString();
 
+
             if (!name.isEmpty() && !credentialNumber.isEmpty() && !phone.isEmpty()) {
                 WhitelistManagement whitelistManagement = new WhitelistManagement();
                 whitelistManagement.setCreateDate(new Date());
@@ -168,6 +171,11 @@ public class WhitelistManagementServiceImpl extends MPJBaseServiceImpl<Whitelist
                 whitelistManagement.setCredentialNumber(credentialNumber);
                 whitelistManagement.setPhone(phone);
                 whitelistManagements.add(whitelistManagement);
+                if(vo.get(3) != null && "".equals(vo.get(3).toString())){
+                    LocalDate date = LocalDate.parse(vo.get(3).toString(), formatter);
+                    whitelistManagement.setEndTime(date);
+                    whitelistManagement.setIsTemporary(1);
+                }
             }
         }
 

+ 32 - 0
src/main/java/com/xjrsoft/module/base/vo/BaseClassCourseExcelVo.java

@@ -0,0 +1,32 @@
+package com.xjrsoft.module.base.vo;
+
+import com.alibaba.excel.annotation.ExcelProperty;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+* @title: 班级课程分页列表出参
+* @Author brealinxx
+* @Date: 2024-06-04
+* @Version 1.0
+*/
+@Data
+public class BaseClassCourseExcelVo {
+
+
+    @ApiModelProperty("班级名称")
+    @ExcelProperty("班级名称")
+    private String className;
+
+    @ApiModelProperty("教学课程")
+    @ExcelProperty("教学课程")
+    private String courseName;
+
+    @ApiModelProperty("对应教材")
+    @ExcelProperty("对应教材")
+    private String textbookName;
+
+    @ApiModelProperty("学期")
+    @ExcelProperty("学期")
+    private String semester;
+}

+ 1 - 0
src/main/java/com/xjrsoft/module/base/vo/BaseClassCoursePageVo.java

@@ -104,6 +104,7 @@ public class BaseClassCoursePageVo {
     @ExcelProperty("对应教材")
     private String textbookName;
 
+    @ApiModelProperty("学期")
     @ExcelProperty("学期")
     private String semester;
 }

+ 57 - 12
src/main/java/com/xjrsoft/module/databoard/controller/DataboardController.java

@@ -7,7 +7,6 @@ import com.github.yulichang.wrapper.MPJLambdaWrapper;
 import com.xjrsoft.common.enums.DeleteMark;
 import com.xjrsoft.common.enums.GenderDictionaryEnum;
 import com.xjrsoft.common.enums.StudyStatusEnum;
-import com.xjrsoft.common.enums.WorkflowIsRecycleType;
 import com.xjrsoft.common.model.result.RT;
 import com.xjrsoft.common.mybatis.SqlRunnerAdapter;
 import com.xjrsoft.common.utils.VoToColumnUtil;
@@ -31,10 +30,14 @@ import com.xjrsoft.module.teacher.entity.XjrUser;
 import com.xjrsoft.module.teacher.service.ITeacherbaseManagerService;
 import com.xjrsoft.module.teacher.vo.XjrUserPageVo;
 import com.xjrsoft.module.workflow.constant.WorkflowConstant;
+import com.xjrsoft.module.workflow.entity.WorkflowExtra;
+import com.xjrsoft.module.workflow.entity.WorkflowSchema;
+import com.xjrsoft.module.workflow.service.IWorkflowExtraService;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
 import lombok.AllArgsConstructor;
 import org.camunda.bpm.engine.HistoryService;
+import org.camunda.bpm.engine.history.HistoricProcessInstance;
 import org.camunda.bpm.engine.history.HistoricProcessInstanceQuery;
 import org.springframework.web.bind.annotation.GetMapping;
 import org.springframework.web.bind.annotation.RequestMapping;
@@ -42,6 +45,8 @@ import org.springframework.web.bind.annotation.RestController;
 
 import javax.validation.Valid;
 import java.time.LocalDate;
+import java.util.ArrayList;
+import java.util.Comparator;
 import java.util.Date;
 import java.util.List;
 import java.util.Map;
@@ -55,7 +60,7 @@ import java.util.stream.Collectors;
 */
 @RestController
 @RequestMapping("/databoard" + "/databoard")
-@Api(value = "/dataexpert"  + "/databoard",tags = "数据看板代码")
+@Api(value = "/databoard"  + "/databoard",tags = "数据看板代码")
 @AllArgsConstructor
 public class DataboardController {
 
@@ -64,21 +69,61 @@ public class DataboardController {
     private final IVisitorOutInRecordService visitorService;
     private final IBaseStudentService studentService;
     private final ITeacherbaseManagerService teacherService;
+    private final IWorkflowExtraService extraService;
 
     @GetMapping(value = "/process-statistics")
     @ApiOperation(value="流程统计")
     @SaCheckPermission("databoard:detail")
     public RT<ProcessStatisticsVo> processStatistics(@Valid StatisticsDto dto){
-        HistoricProcessInstanceQuery historicProcessInstanceQuery = historyService.createHistoricProcessInstanceQuery()
-                .variableValueEquals(WorkflowConstant.PROCESS_ISRECYCLE_FLAG_KEY, WorkflowIsRecycleType.NO.getCode());
+        HistoricProcessInstanceQuery instanceQuery = historyService.createHistoricProcessInstanceQuery();
         if(dto.getUserId() != null){
-            historicProcessInstanceQuery.variableValueEquals(WorkflowConstant.PROCESS_START_USER_ID_KEY, dto.getUserId());
+            instanceQuery.variableValueEquals(WorkflowConstant.PROCESS_START_USER_ID_KEY, dto.getUserId());
         }
 
+        List<WorkflowExtra> workflowExtras = extraService.list(
+                new MPJLambdaWrapper<WorkflowExtra>()
+                        .select(WorkflowExtra.class, x -> VoToColumnUtil.fieldsToColumns(WorkflowExtra.class).contains(x.getProperty()))
+                        .leftJoin(WorkflowSchema.class, WorkflowSchema::getId, WorkflowExtra::getSchemaId)
+                        .leftJoin(DictionaryDetail.class, DictionaryDetail::getId, WorkflowSchema::getCategory)
+        );
+
+
         ProcessStatisticsVo result = new ProcessStatisticsVo();
-        result.setAllCount(historicProcessInstanceQuery.list().size());
-        result.setCompleteCount(historicProcessInstanceQuery.finished().list().size());
-        result.setUncompleteCount(historicProcessInstanceQuery.unfinished().list().size());
+        List<HistoricProcessInstance> list = instanceQuery.list();
+        List<WorkflowExtra> allCountList = new ArrayList<>();
+        for (HistoricProcessInstance historicProcessInstance : list) {
+            workflowExtras.stream()
+                    .filter(e -> e.getProcessId().equals(historicProcessInstance.getId()))
+                    .max(Comparator.comparing(WorkflowExtra::getStartTime))
+                    .ifPresent(e -> {
+                        allCountList.add(e);
+                    });
+        }
+        result.setAllCount(Long.parseLong(allCountList.size() + ""));
+
+        List<HistoricProcessInstance> finished = historyService.createHistoricProcessInstanceQuery().finished().list();
+        List<WorkflowExtra> completeCountList = new ArrayList<>();
+        for (HistoricProcessInstance historicProcessInstance : finished) {
+            workflowExtras.stream()
+                    .filter(e -> e.getProcessId().equals(historicProcessInstance.getId()))
+                    .max(Comparator.comparing(WorkflowExtra::getStartTime))
+                    .ifPresent(e -> {
+                        completeCountList.add(e);
+                    });
+        }
+        result.setCompleteCount(Long.parseLong(completeCountList.size() + ""));
+
+        List<HistoricProcessInstance> unfinished = historyService.createHistoricProcessInstanceQuery().unfinished().list();
+        List<WorkflowExtra> uncompleteCountList = new ArrayList<>();
+        for (HistoricProcessInstance historicProcessInstance : unfinished) {
+            workflowExtras.stream()
+                    .filter(e -> e.getProcessId().equals(historicProcessInstance.getId()))
+                    .max(Comparator.comparing(WorkflowExtra::getStartTime))
+                    .ifPresent(e -> {
+                        uncompleteCountList.add(e);
+                    });
+        }
+        result.setUncompleteCount(Long.parseLong(uncompleteCountList.size() + ""));
 
         return RT.ok(result);
     }
@@ -268,9 +313,9 @@ public class DataboardController {
         List<Map<String, Object>> list = SqlRunnerAdapter.db().selectList(sql);
         HealthStatisticsVo result = new HealthStatisticsVo();
         for (Map<String, Object> objectMap : list) {
-            if(GenderDictionaryEnum.FEMALE.getCode().equals(objectMap.get("gender").toString())){
+            if(objectMap.get("gender") != null && GenderDictionaryEnum.FEMALE.getCode().equals(objectMap.get("gender").toString())){
                 result.setInfectionFemaleCount(Integer.parseInt(objectMap.get("a_count").toString()));
-            }if(GenderDictionaryEnum.MALE.getCode().equals(objectMap.get("gender").toString())){
+            }if(objectMap.get("gender") != null && GenderDictionaryEnum.MALE.getCode().equals(objectMap.get("gender").toString())){
                 result.setInfectionMaleCount(Integer.parseInt(objectMap.get("a_count").toString()));
             }
         }
@@ -278,9 +323,9 @@ public class DataboardController {
         sql = "SELECT gender,COUNT(*) AS a_count FROM student_psychological WHERE status = 1 GROUP BY gender";
         list = SqlRunnerAdapter.db().selectList(sql);
         for (Map<String, Object> objectMap : list) {
-            if(GenderDictionaryEnum.FEMALE.getCode().equals(objectMap.get("gender").toString())){
+            if(objectMap.get("gender") != null && GenderDictionaryEnum.FEMALE.getCode().equals(objectMap.get("gender").toString())){
                 result.setInfectionFemaleCount(Integer.parseInt(objectMap.get("a_count").toString()));
-            }if(GenderDictionaryEnum.MALE.getCode().equals(objectMap.get("gender").toString())){
+            }if(objectMap.get("gender") != null && GenderDictionaryEnum.MALE.getCode().equals(objectMap.get("gender").toString())){
                 result.setPsychologicalMaleCount(Integer.parseInt(objectMap.get("a_count").toString()));
             }
         }

+ 609 - 0
src/main/java/com/xjrsoft/module/databoard/controller/DatadetailController.java

@@ -0,0 +1,609 @@
+package com.xjrsoft.module.databoard.controller;
+
+import cn.dev33.satoken.annotation.SaCheckPermission;
+import cn.hutool.core.util.ObjectUtil;
+import cn.hutool.core.util.StrUtil;
+import com.github.yulichang.toolkit.MPJWrappers;
+import com.github.yulichang.wrapper.MPJLambdaWrapper;
+import com.xjrsoft.common.enums.GenderDictionaryEnum;
+import com.xjrsoft.common.enums.StudyStatusEnum;
+import com.xjrsoft.common.model.result.RT;
+import com.xjrsoft.common.mybatis.SqlRunnerAdapter;
+import com.xjrsoft.common.utils.VoToColumnUtil;
+import com.xjrsoft.module.databoard.dto.StatisticsDetailDto;
+import com.xjrsoft.module.databoard.vo.DistributionVo;
+import com.xjrsoft.module.databoard.vo.DurationVo;
+import com.xjrsoft.module.databoard.vo.HealthItemCountVo;
+import com.xjrsoft.module.databoard.vo.HealthStatisticsDetailVo;
+import com.xjrsoft.module.databoard.vo.ItemCountAmountVo;
+import com.xjrsoft.module.databoard.vo.ItemCountVo;
+import com.xjrsoft.module.databoard.vo.ItemDoubleVo;
+import com.xjrsoft.module.databoard.vo.ProcessStatisticsDetailVo;
+import com.xjrsoft.module.databoard.vo.StudnetStatisticsDetailVo;
+import com.xjrsoft.module.databoard.vo.SubscriptionStatisticsDetailVo;
+import com.xjrsoft.module.databoard.vo.TeacherStatisticsDetailVo;
+import com.xjrsoft.module.ledger.entity.WfSubscription;
+import com.xjrsoft.module.ledger.service.IWfSubscriptionService;
+import com.xjrsoft.module.student.dto.BaseStudentUserPageDto;
+import com.xjrsoft.module.student.service.IBaseStudentService;
+import com.xjrsoft.module.student.vo.BaseStudentUserPageVo;
+import com.xjrsoft.module.system.entity.DictionaryDetail;
+import com.xjrsoft.module.teacher.entity.BaseTeacher;
+import com.xjrsoft.module.teacher.entity.XjrUser;
+import com.xjrsoft.module.teacher.service.ITeacherbaseManagerService;
+import com.xjrsoft.module.teacher.vo.XjrUserPageVo;
+import com.xjrsoft.module.workflow.constant.WorkflowConstant;
+import com.xjrsoft.module.workflow.entity.WorkflowExtra;
+import com.xjrsoft.module.workflow.entity.WorkflowSchema;
+import com.xjrsoft.module.workflow.service.IWorkflowExtraService;
+import com.xjrsoft.module.workflow.utils.WorkFlowUtil;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import lombok.AllArgsConstructor;
+import org.camunda.bpm.engine.HistoryService;
+import org.camunda.bpm.engine.history.HistoricProcessInstance;
+import org.camunda.bpm.engine.history.HistoricProcessInstanceQuery;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import javax.validation.Valid;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.time.Duration;
+import java.time.LocalDate;
+import java.time.Period;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.stream.Collectors;
+
+/**
+* @title: 数据看板代码
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@RestController
+@RequestMapping("/datadetail" + "/datadetail")
+@Api(value = "/datadetail"  + "/datadetail",tags = "数据看板详情代码")
+@AllArgsConstructor
+public class DatadetailController {
+
+    private final HistoryService historyService;
+    private final IWorkflowExtraService extraService;
+    private final ITeacherbaseManagerService teacherService;
+    private final IBaseStudentService studentService;
+    private final IWfSubscriptionService subscriptionService;
+
+    @GetMapping(value = "/process-statistics")
+    @ApiOperation(value="流程统计详情")
+    @SaCheckPermission("datadetail:detail")
+    public RT<ProcessStatisticsDetailVo> processStatistics(@Valid StatisticsDetailDto dto){
+        HistoricProcessInstanceQuery instanceQuery = historyService.createHistoricProcessInstanceQuery();
+        if(dto.getUserId() != null){
+            instanceQuery.variableValueEquals(WorkflowConstant.PROCESS_START_USER_ID_KEY, dto.getUserId());
+        }
+        if (!ObjectUtil.isNull(dto.getStartDate())) {
+            instanceQuery.startedAfter(WorkFlowUtil.getStartOfDay(dto.getStartDate()));
+        }
+        if (!ObjectUtil.isNull(dto.getEndDate())) {
+            instanceQuery.startedBefore(WorkFlowUtil.getEndOfDay(dto.getEndDate()));
+        }
+
+        List<WorkflowExtra> workflowExtras = extraService.list(
+                new MPJLambdaWrapper<WorkflowExtra>()
+                        .select(WorkflowExtra.class, x -> VoToColumnUtil.fieldsToColumns(WorkflowExtra.class).contains(x.getProperty()))
+                        .leftJoin(WorkflowSchema.class, WorkflowSchema::getId, WorkflowExtra::getSchemaId)
+                        .leftJoin(DictionaryDetail.class, DictionaryDetail::getId, WorkflowSchema::getCategory)
+        );
+
+
+        ProcessStatisticsDetailVo result = new ProcessStatisticsDetailVo();
+        List<HistoricProcessInstance> list = instanceQuery.list();
+        List<WorkflowExtra> allCountList = new ArrayList<>();
+        for (HistoricProcessInstance historicProcessInstance : list) {
+            workflowExtras.stream()
+                    .filter(e -> e.getProcessId().equals(historicProcessInstance.getId()))
+                    .max(Comparator.comparing(WorkflowExtra::getStartTime))
+                    .ifPresent(e -> {
+                        allCountList.add(e);
+                    });
+        }
+        result.setAllCount(Long.parseLong(allCountList.size() + ""));
+
+        List<HistoricProcessInstance> finished = historyService.createHistoricProcessInstanceQuery().finished().list();
+        List<WorkflowExtra> completeCountList = new ArrayList<>();
+        for (HistoricProcessInstance historicProcessInstance : finished) {
+            workflowExtras.stream()
+                    .filter(e -> e.getProcessId().equals(historicProcessInstance.getId()))
+                    .max(Comparator.comparing(WorkflowExtra::getStartTime))
+                    .ifPresent(e -> {
+                        completeCountList.add(e);
+                    });
+        }
+        result.setCompleteCount(Long.parseLong(completeCountList.size() + ""));
+
+        List<HistoricProcessInstance> unfinished = historyService.createHistoricProcessInstanceQuery().unfinished().list();
+        List<WorkflowExtra> uncompleteCountList = new ArrayList<>();
+        for (HistoricProcessInstance historicProcessInstance : unfinished) {
+            workflowExtras.stream()
+                    .filter(e -> e.getProcessId().equals(historicProcessInstance.getId()))
+                    .max(Comparator.comparing(WorkflowExtra::getStartTime))
+                    .ifPresent(e -> {
+                        uncompleteCountList.add(e);
+                    });
+        }
+        result.setUncompleteCount(Long.parseLong(uncompleteCountList.size() + ""));
+
+        Map<String, Long> finishedMap = completeCountList.stream()
+                .collect(Collectors.groupingBy(WorkflowExtra::getSchemaName, Collectors.counting()));
+        Map<String, Long> unfinishedMap = uncompleteCountList.stream()
+                .collect(Collectors.groupingBy(WorkflowExtra::getSchemaName, Collectors.counting()));
+
+        Set<String> itemSet = new HashSet<>();
+        itemSet.addAll(finishedMap.keySet());
+        itemSet.addAll(unfinishedMap.keySet());
+        List<DistributionVo> distributionList = new ArrayList();
+        for (String item : itemSet) {
+            Long uncompleteCount = unfinishedMap.get(item) == null?0L:unfinishedMap.get(item);
+            Long completeCount = finishedMap.get(item) == null?0L:finishedMap.get(item);
+            distributionList.add(
+                    new DistributionVo(){{
+                        setItem(item);
+                        setCompleteCount(completeCount);
+                        setUncompleteCount(uncompleteCount);
+                    }}
+            );
+        }
+        result.setDistributionList(distributionList);
+        List<DurationVo> durationList = new ArrayList<>();
+
+        List<Duration> timeDifferences = new ArrayList<>();
+        completeCountList.stream().filter(el -> el.getEndTime() != null && el.getStartTime() != null).forEach(el -> {
+            Duration diff = Duration.between(el.getEndTime(), el.getStartTime());
+            timeDifferences.add(diff);
+        });
+
+        int zeroHour = 0;
+        int oneHour = 0;
+        int fourHour = 0;
+        int eightHour = 0;
+        for (Duration timeDifference : timeDifferences) {
+            long seconds = timeDifference.getSeconds();
+            if(seconds < 3600){
+                zeroHour ++;
+            }else if(seconds < 14400){
+                oneHour ++;
+            }else if(seconds < 28800){
+                fourHour ++;
+            }else{
+                eightHour ++;
+            }
+        }
+        DurationVo zeroVo = new DurationVo();
+        zeroVo.setDuration("0-1h");
+        zeroVo.setCount(zeroHour);
+        durationList.add(zeroVo);
+
+        zeroVo = new DurationVo();
+        zeroVo.setDuration("1-4h");
+        zeroVo.setCount(oneHour);
+        durationList.add(zeroVo);
+
+        zeroVo = new DurationVo();
+        zeroVo.setDuration("4-8h");
+        zeroVo.setCount(fourHour);
+        durationList.add(zeroVo);
+
+        zeroVo = new DurationVo();
+        zeroVo.setDuration("8h以上");
+        zeroVo.setCount(eightHour);
+        durationList.add(zeroVo);
+
+        result.setDurationList(durationList);
+
+        return RT.ok(result);
+    }
+
+    @GetMapping(value = "/health-statistics")
+    @ApiOperation(value="学生健康统计")
+    @SaCheckPermission("datadetail:detail")
+    public RT<HealthStatisticsDetailVo> healthStatistics(@Valid StatisticsDetailDto dto){
+        String sql = "SELECT gender,COUNT(*) AS a_count FROM student_infection WHERE status = 1 GROUP BY gender";
+        List<Map<String, Object>> list = SqlRunnerAdapter.db().selectList(sql);
+        HealthStatisticsDetailVo result = new HealthStatisticsDetailVo();
+        for (Map<String, Object> objectMap : list) {
+            if(objectMap.get("gender") != null && GenderDictionaryEnum.FEMALE.getCode().equals(objectMap.get("gender").toString())){
+                result.setInfectionFemaleCount(Integer.parseInt(objectMap.get("a_count").toString()));
+            }if(objectMap.get("gender") != null && GenderDictionaryEnum.MALE.getCode().equals(objectMap.get("gender").toString())){
+                result.setInfectionMaleCount(Integer.parseInt(objectMap.get("a_count").toString()));
+            }
+        }
+
+        sql = "SELECT gender,COUNT(*) AS a_count FROM student_psychological WHERE status = 1 GROUP BY gender";
+        list = SqlRunnerAdapter.db().selectList(sql);
+        for (Map<String, Object> objectMap : list) {
+            if(objectMap.get("gender") != null && GenderDictionaryEnum.FEMALE.getCode().equals(objectMap.get("gender").toString())){
+                result.setInfectionFemaleCount(Integer.parseInt(objectMap.get("a_count").toString()));
+            }if(objectMap.get("gender") != null && GenderDictionaryEnum.MALE.getCode().equals(objectMap.get("gender").toString())){
+                result.setPsychologicalMaleCount(Integer.parseInt(objectMap.get("a_count").toString()));
+            }
+        }
+
+        List<HealthItemCountVo> gradeList = new ArrayList<>();
+        sql = "SELECT t1.name as item,COUNT(t3.student_id) AS count FROM base_grade t1" +
+            " INNER JOIN base_student_school_roll t2 ON t1.id=  t2.grade_id" +
+            " INNER JOIN student_infection t3 ON t3.student_id = t2.user_id" +
+            " WHERE t3.status = 1 AND t1.delete_mark = 0" +
+            " GROUP BY t1.name";
+        list = SqlRunnerAdapter.db().selectList(sql);
+        for (Map<String, Object> objectMap : list) {
+            gradeList.add(
+                new HealthItemCountVo(){{
+                    setItem(objectMap.get("item").toString());
+                    setInfectionCount(Long.parseLong(objectMap.get("count").toString()));
+                }}
+            );
+        }
+
+        sql = "SELECT t1.name as item,COUNT(t3.student_id) AS count FROM base_grade t1" +
+            " INNER JOIN base_student_school_roll t2 ON t1.id=  t2.grade_id" +
+            " INNER JOIN student_psychological t3 ON t3.student_id = t2.user_id" +
+            " WHERE t3.status = 1 AND t1.delete_mark = 0" +
+            " GROUP BY t1.name";
+        list = SqlRunnerAdapter.db().selectList(sql);
+        for (Map<String, Object> objectMap : list) {
+            for (HealthItemCountVo itemCountVo : gradeList) {
+                if(objectMap.get("item").toString().equals(itemCountVo.getItem())){
+                    itemCountVo.setPsychologicalCount(Long.parseLong(objectMap.get("count").toString()));
+                }
+            }
+        }
+        result.setGradeList(gradeList);
+
+        List<HealthItemCountVo> classList = new ArrayList<>();
+        sql = "SELECT t1.name as item,COUNT(t3.student_id) AS count FROM base_class t1" +
+                " INNER JOIN base_student_school_roll t2 ON t1.id=  t2.grade_id" +
+                " INNER JOIN student_infection t3 ON t3.student_id = t2.user_id" +
+                " WHERE t3.status = 1 AND t1.delete_mark = 0" +
+                " GROUP BY t1.name";
+        list = SqlRunnerAdapter.db().selectList(sql);
+        for (Map<String, Object> objectMap : list) {
+            classList.add(
+                    new HealthItemCountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setInfectionCount(Long.parseLong(objectMap.get("count").toString()));
+                    }}
+            );
+        }
+
+        sql = "SELECT t1.name as item,COUNT(t3.student_id) AS count FROM base_class t1" +
+                " INNER JOIN base_student_school_roll t2 ON t1.id=  t2.grade_id" +
+                " INNER JOIN student_psychological t3 ON t3.student_id = t2.user_id" +
+                " WHERE t3.status = 1 AND t1.delete_mark = 0" +
+                " GROUP BY t1.name";
+        list = SqlRunnerAdapter.db().selectList(sql);
+        for (Map<String, Object> objectMap : list) {
+            for (HealthItemCountVo itemCountVo : classList) {
+                if(objectMap.get("item").toString().equals(itemCountVo.getItem())){
+                    itemCountVo.setPsychologicalCount(Long.parseLong(objectMap.get("count").toString()));
+                }
+            }
+        }
+        result.setClassList(classList);
+        return RT.ok(result);
+    }
+
+
+    @GetMapping(value = "/person-statistics")
+    @ApiOperation(value="教职工详情数据统计")
+    @SaCheckPermission("datadetail:detail")
+    public RT<TeacherStatisticsDetailVo> teahcerStatistics(@Valid StatisticsDetailDto dto) throws ParseException {
+        String sql = "SELECT IFNULL(t2.name,'未填写') AS item ,ifnull(COUNT(*), 0) AS a_count FROM base_teacher_education t1" +
+                " LEFT JOIN xjr_dictionary_detail t2 ON t1.education  = t2.code" +
+                " WHERE t1.delete_mark = 0 GROUP BY t2.name";
+        List<Map<String, Object>> list = SqlRunnerAdapter.db().selectList(sql);
+        TeacherStatisticsDetailVo result = new TeacherStatisticsDetailVo();
+        List<ItemCountVo> educationList = new ArrayList<>();
+        for (Map<String, Object> objectMap : list) {
+            educationList.add(
+                    new ItemCountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setCount(Integer.parseInt(objectMap.get("a_count").toString()));
+                    }}
+            );
+        }
+        result.setEducationList(educationList);
+
+        sql = "SELECT IFNULL(t3.name,'未填写') AS item ,ifnull(COUNT(*), 0) AS a_count FROM xjr_user t1" +
+            " INNER JOIN base_teacher t2 ON t1.id = t2.user_id" +
+            " LEFT JOIN xjr_dictionary_detail t3 ON t1.gender  = t3.code AND t3.item_id = 2023000000000000004" +
+            " WHERE t1.delete_mark = 0 GROUP BY t3.name";
+        list = SqlRunnerAdapter.db().selectList(sql);
+        List<ItemCountVo> genderList = new ArrayList<>();
+        for (Map<String, Object> objectMap : list) {
+            genderList.add(
+                    new ItemCountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setCount(Integer.parseInt(objectMap.get("a_count").toString()));
+                    }}
+            );
+        }
+        result.setGenderList(genderList);
+
+        sql = "SELECT IFNULL(t3.name,'未填写') AS item ,ifnull(COUNT(*), 0) AS a_count FROM xjr_user t1" +
+            " INNER JOIN base_teacher t2 ON t1.id = t2.user_id" +
+            " LEFT JOIN xjr_dictionary_detail t3 ON t2.employ_way  = t3.code AND t3.item_id = 2023000000000000016" +
+            " WHERE t1.delete_mark = 0 GROUP BY t3.name";
+        list = SqlRunnerAdapter.db().selectList(sql);
+        List<ItemCountVo> employList = new ArrayList<>();
+        for (Map<String, Object> objectMap : list) {
+            employList.add(
+                    new ItemCountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setCount(Integer.parseInt(objectMap.get("a_count").toString()));
+                    }}
+            );
+        }
+        result.setEmployList(employList);
+
+        sql = "SELECT IFNULL(t4.name,'未填写') AS item ,ifnull(COUNT(*), 0) AS a_count FROM xjr_user t1" +
+            " INNER JOIN base_teacher t2 ON t1.id = t2.user_id" +
+            " LEFT JOIN xjr_user_dept_relation t3 ON t1.id  = t3.user_id" +
+            " LEFT JOIN xjr_department t4 ON t3.dept_id = t4.id" +
+            " WHERE t1.delete_mark = 0 AND t4.is_major = 1 GROUP BY t4.name";
+
+        list = SqlRunnerAdapter.db().selectList(sql);
+        List<ItemCountVo> deptList = new ArrayList<>();
+        for (Map<String, Object> objectMap : list) {
+            deptList.add(
+                    new ItemCountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setCount(Integer.parseInt(objectMap.get("a_count").toString()));
+                    }}
+            );
+        }
+        result.setDeptList(deptList);
+
+        MPJLambdaWrapper<XjrUser> queryWrapper = MPJWrappers.<XjrUser>lambdaJoin()
+                .disableSubLogicDel()
+                .orderByDesc(XjrUser::getId)
+                .select(XjrUser::getId)
+                .select(XjrUser.class,x -> VoToColumnUtil.fieldsToColumns(XjrUserPageVo.class).contains(x.getProperty()))
+                .innerJoin(BaseTeacher.class,BaseTeacher::getUserId,XjrUser::getId)
+                .leftJoin(DictionaryDetail.class,DictionaryDetail::getCode,BaseTeacher::getJobState, ext->ext.selectAs(DictionaryDetail::getName, XjrUserPageVo::getJobState))
+                .leftJoin(DictionaryDetail.class,DictionaryDetail::getCode,XjrUser::getCredentialType,ext->ext.selectAs(DictionaryDetail::getName, XjrUserPageVo::getCredentialType))
+                .leftJoin(DictionaryDetail.class,DictionaryDetail::getCode,BaseTeacher::getEmployWay,ext->ext.selectAs(DictionaryDetail::getName, XjrUserPageVo::getEmployWay))
+
+                .selectAsClass(BaseTeacher.class, XjrUserPageVo.class);
+
+        List<XjrUserPageVo> teacherList = teacherService.selectJoinList(XjrUserPageVo.class, queryWrapper);
+        List<String> idCardList = teacherList.stream().map(XjrUserPageVo::getCredentialNumber).collect(Collectors.toList());
+        SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMdd");
+        LocalDate currentDate = LocalDate.now();
+        int age20 = 0;
+        int age30 = 0;
+        int age40 = 0;
+        int age50 = 0;
+        int age60 = 0;
+        for (String idCard : idCardList) {
+            if(StrUtil.isEmpty(idCard) || idCard.length() < 18){
+                continue;
+            }
+            String birthdayStr = idCard.substring(6, 14);
+            java.util.Date date = sdf.parse(birthdayStr);
+
+            // 将Date对象转换为LocalDate对象
+            LocalDate birthDate = date.toInstant().atZone(java.time.ZoneId.systemDefault()).toLocalDate();
+            Period ageObj = Period.between(birthDate, currentDate);
+            int age = ageObj.getYears();
+            if(age >= 20 && age <= 29){
+                age20 ++;
+            }else if(age >= 30 && age <= 39){
+                age30 ++;
+            }else if(age >= 40 && age <= 49){
+                age40 ++;
+            }else if(age >= 50 && age <= 59){
+                age50 ++;
+            }else if(age >= 60){
+                age60 ++;
+            }
+        }
+
+        List<ItemCountVo> ageList = new ArrayList<>();
+        ItemCountVo itemCountVo = new ItemCountVo();
+        itemCountVo.setItem("20-29岁");
+        itemCountVo.setCount(age20);
+        ageList.add(itemCountVo);
+
+        itemCountVo = new ItemCountVo();
+        itemCountVo.setItem("30-39岁");
+        itemCountVo.setCount(age30);
+        ageList.add(itemCountVo);
+
+        itemCountVo = new ItemCountVo();
+        itemCountVo.setItem("40-49岁");
+        itemCountVo.setCount(age40);
+        ageList.add(itemCountVo);
+
+        itemCountVo = new ItemCountVo();
+        itemCountVo.setItem("50-59岁");
+        itemCountVo.setCount(age50);
+        ageList.add(itemCountVo);
+
+        itemCountVo = new ItemCountVo();
+        itemCountVo.setItem("60岁以上");
+        itemCountVo.setCount(age60);
+        ageList.add(itemCountVo);
+
+        result.setAgeList(ageList);
+
+        return RT.ok(result);
+    }
+
+    @GetMapping(value = "/student-statistics")
+    @ApiOperation(value="学生详情数据统计")
+    @SaCheckPermission("datadetail:detail")
+    public RT<StudnetStatisticsDetailVo> studentStatistics(@Valid StatisticsDetailDto dto) throws ParseException {
+        StudnetStatisticsDetailVo result = new StudnetStatisticsDetailVo();
+
+        String sql = "SELECT IFNULL(t3.name,'未填写') AS item ,COUNT(*) AS a_count FROM xjr_user t1" +
+            " INNER JOIN base_student t2 ON t1.id = t2.user_id" +
+            " LEFT JOIN xjr_dictionary_detail t3 ON t1.gender  = t3.code AND t3.item_id = 2023000000000000004" +
+            " WHERE t1.delete_mark = 0 GROUP BY t3.name";
+        List<Map<String, Object>> list = SqlRunnerAdapter.db().selectList(sql);
+        List<ItemCountVo> genderList = new ArrayList<>();
+        for (Map<String, Object> objectMap : list) {
+            genderList.add(
+                    new ItemCountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setCount(Integer.parseInt(objectMap.get("a_count").toString()));
+                    }}
+            );
+        }
+        result.setGenderList(genderList);
+
+        sql = "SELECT IFNULL(t3.name,'未填写') AS item ,COUNT(*) AS a_count FROM xjr_user t1" +
+            " INNER JOIN base_student_school_roll t2 ON t1.id = t2.user_id" +
+            " LEFT JOIN xjr_dictionary_detail t3 ON t2.student_type = t3.code AND t3.item_id = 2023000000000000028" +
+            " WHERE t1.delete_mark = 0 GROUP BY t3.name";
+        list = SqlRunnerAdapter.db().selectList(sql);
+        List<ItemCountVo> studentTypeList = new ArrayList<>();
+        for (Map<String, Object> objectMap : list) {
+            studentTypeList.add(
+                    new ItemCountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setCount(Integer.parseInt(objectMap.get("a_count").toString()));
+                    }}
+            );
+        }
+        result.setStudentTypeList(studentTypeList);
+
+
+        List<BaseStudentUserPageVo> studentList = studentService.getStudentList(new BaseStudentUserPageDto());
+        Set<String> studentStayMaleSet = studentList.stream()
+                .filter(x -> (
+                        x.getGenderCn() != null
+                                && x.getGenderCn().equals(GenderDictionaryEnum.MALE.getCode())
+                                && x.getStduyStatusCn() != null
+                                && x.getStduyStatusCn().equals(StudyStatusEnum.InResidence.getCode())
+                ))
+                .map(BaseStudentUserPageVo::getId).collect(Collectors.toSet());
+        result.setStudentStayMaleCount(studentStayMaleSet.size());
+
+        Set<String> studentNotStayMaleSet = studentList.stream()
+                .filter(x -> (
+                        x.getGenderCn() != null
+                                && x.getGenderCn().equals(GenderDictionaryEnum.MALE.getCode())
+                                && x.getStduyStatusCn() != null
+                                && x.getStduyStatusCn().equals(StudyStatusEnum.AttendDaySchool.getCode())
+                ))
+                .map(BaseStudentUserPageVo::getId).collect(Collectors.toSet());
+        result.setStudentNotStayMaleCount(studentNotStayMaleSet.size());
+
+        Set<String> studentStayFemaleSet = studentList.stream()
+                .filter(x -> (
+                        x.getGenderCn() != null
+                                && x.getGenderCn().equals(GenderDictionaryEnum.FEMALE.getCode())
+                                && x.getStduyStatusCn() != null
+                                && x.getStduyStatusCn().equals(StudyStatusEnum.InResidence.getCode())
+                ))
+                .map(BaseStudentUserPageVo::getId).collect(Collectors.toSet());
+        result.setStudentStayFemaleCount(studentStayFemaleSet.size());
+
+        Set<String> studentNotStayFemaleSet = studentList.stream()
+                .filter(x -> (
+                        x.getGenderCn() != null
+                                && x.getGenderCn().equals(GenderDictionaryEnum.FEMALE.getCode())
+                                && x.getStduyStatusCn() != null
+                                && x.getStduyStatusCn().equals(StudyStatusEnum.AttendDaySchool.getCode())
+                ))
+                .map(BaseStudentUserPageVo::getId).collect(Collectors.toSet());
+        result.setStudentNotStayFemaleCount(studentNotStayFemaleSet.size());
+
+        sql = "SELECT name AS item,(" +
+            " SELECT COUNT(*) FROM xjr_user t1" +
+            " INNER JOIN base_student_school_roll t2 ON t1.id = t2.user_id" +
+            " WHERE t1.delete_mark = 0 AND t2.grade_id = base_grade.id" +
+            " ) AS a_count FROM base_grade" +
+            " WHERE delete_mark = 0 AND status = 1 ORDER BY name DESC LIMIT 3";
+        list = SqlRunnerAdapter.db().selectList(sql);
+        Collections.reverse(list);
+        List<ItemCountVo> gradeList = new ArrayList<>();
+        for (Map<String, Object> objectMap : list) {
+            gradeList.add(
+                    new ItemCountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setCount(Integer.parseInt(objectMap.get("a_count").toString()));
+                    }}
+            );
+        }
+        result.setGradeList(gradeList);
+        return RT.ok(result);
+    }
+
+    @GetMapping(value = "/subscription-statistics")
+    @ApiOperation(value="物品申购详情数据统计")
+    @SaCheckPermission("datadetail:detail")
+    public RT<SubscriptionStatisticsDetailVo> subscriptionStatistics(@Valid StatisticsDetailDto dto) {
+        SubscriptionStatisticsDetailVo result = new SubscriptionStatisticsDetailVo();
+        List<WfSubscription> list = subscriptionService.list();
+        double totalAmount = list.stream().filter(x -> x.getTotalAmount() != null).mapToDouble(WfSubscription::getTotalAmount).sum();
+        result.setTotalAmount(totalAmount);
+
+        int adoptCount = list.stream().filter(x -> x.getStatus() == 1).collect(Collectors.toList()).size();
+        result.setAdoptCount(adoptCount);
+
+        int pendingCount = list.stream().filter(x -> x.getStatus() == null || x.getStatus() == 0).collect(Collectors.toList()).size();
+        result.setPendingCount(pendingCount);
+
+        String sql = "SELECT IFNULL(t3.name, '未填写') AS item,COUNT(t1.id) AS a_count,SUM(t1.amount) as a_sum FROM wf_subscription_list t1" +
+                " INNER JOIN wf_subscription t2 ON t1.parent_id = t2.id" +
+                " LEFT JOIN xjr_dictionary_detail t3 ON t1.item_type = t3.code" +
+                " AND t3.item_id = 1752140413593518081" +
+                " WHERE t2.status = 1 GROUP BY t3.name";
+        List<Map<String, Object>> datalist = SqlRunnerAdapter.db().selectList(sql);
+        List<ItemCountVo> categoryCountList = new ArrayList<>();
+        List<ItemDoubleVo> categoryAmountList = new ArrayList<>();
+        for (Map<String, Object> objectMap : datalist) {
+            categoryCountList.add(
+                    new ItemCountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setCount(Integer.parseInt(objectMap.get("a_count").toString()));
+                    }}
+            );
+
+            categoryAmountList.add(
+                    new ItemDoubleVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setAmount(Double.parseDouble(objectMap.get("a_sum").toString()));
+                    }}
+            );
+        }
+        result.setCategoryCountList(categoryCountList);
+        result.setCategoryAmountList(categoryAmountList);
+
+        sql = "SELECT IFNULL(t3.name, '未填写') AS item,COUNT(t1.id) AS a_count,SUM(t1.amount) as a_sum FROM wf_subscription_list t1" +
+            " INNER JOIN wf_subscription t2 ON t1.parent_id = t2.id" +
+            " LEFT JOIN xjr_department t3 ON t2.application_department = t3.id" +
+            " WHERE t2.status = 1 GROUP BY t3.name";
+        datalist = SqlRunnerAdapter.db().selectList(sql);
+        List<ItemCountAmountVo> deptList = new ArrayList<>();
+        for (Map<String, Object> objectMap : datalist) {
+            deptList.add(
+                    new ItemCountAmountVo(){{
+                        setItem(objectMap.get("item").toString());
+                        setCount(Integer.parseInt(objectMap.get("a_count").toString()));
+                        setAmount(Double.parseDouble(objectMap.get("a_sum").toString()));
+                    }}
+            );
+        }
+        result.setDeptList(deptList);
+        return RT.ok(result);
+    }
+
+}

+ 31 - 0
src/main/java/com/xjrsoft/module/databoard/dto/StatisticsDetailDto.java

@@ -0,0 +1,31 @@
+package com.xjrsoft.module.databoard.dto;
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import org.springframework.format.annotation.DateTimeFormat;
+
+import java.time.LocalDate;
+
+
+/**
+* @title: 数据看板-流程统计入参
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class StatisticsDetailDto {
+
+    @ApiModelProperty("用户id")
+    private Long userId;
+
+    @DateTimeFormat(pattern = "yyyy-MM-dd")
+    @ApiModelProperty("查询开始日期")
+    private LocalDate startDate;
+
+    @DateTimeFormat(pattern = "yyyy-MM-dd")
+    @ApiModelProperty("查询结束日期")
+    private LocalDate endDate;
+
+}

+ 1 - 0
src/main/java/com/xjrsoft/module/databoard/dto/StatisticsDto.java

@@ -4,6 +4,7 @@ import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
 
 
+
 /**
 * @title: 数据看板-流程统计入参
 * @Author dzx

+ 29 - 0
src/main/java/com/xjrsoft/module/databoard/vo/DistributionVo.java

@@ -0,0 +1,29 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+* @title: 数据看板-流程统计出参
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class DistributionVo {
+
+    /**
+    * 发起流程总数
+    */
+    @ApiModelProperty("统计项")
+    private String item;
+    /**
+    * 完成总数
+    */
+    @ApiModelProperty("完成数量")
+    private Long completeCount;
+
+    @ApiModelProperty("未完成数量")
+    private Long uncompleteCount;
+
+}

+ 27 - 0
src/main/java/com/xjrsoft/module/databoard/vo/DurationVo.java

@@ -0,0 +1,27 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+
+/**
+* @title: 数据看板-流程统计出参
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class DurationVo {
+
+    /**
+    * 发起流程总数
+    */
+    @ApiModelProperty("时间段")
+    private String duration;
+    /**
+    * 完成总数
+    */
+    @ApiModelProperty("数量")
+    private Integer count;
+
+}

+ 30 - 0
src/main/java/com/xjrsoft/module/databoard/vo/HealthItemCountVo.java

@@ -0,0 +1,30 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+
+/**
+* @title: 数据看板-流程统计出参
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class HealthItemCountVo {
+
+    /**
+    * 发起流程总数
+    */
+    @ApiModelProperty("统计项")
+    private String item;
+    /**
+    * 完成总数
+    */
+    @ApiModelProperty("学生传染病数量")
+    private Long infectionCount;
+
+    @ApiModelProperty("学生心理咨询数量")
+    private Long psychologicalCount;
+
+}

+ 35 - 0
src/main/java/com/xjrsoft/module/databoard/vo/HealthStatisticsDetailVo.java

@@ -0,0 +1,35 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+* @title: 数据看板-课程统计出参
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class HealthStatisticsDetailVo {
+
+
+    @ApiModelProperty("传染病登记人数-男")
+    private Integer infectionMaleCount;
+
+    @ApiModelProperty("传染病登记人数-女")
+    private Integer infectionFemaleCount;
+
+    @ApiModelProperty("心理咨询人数-男")
+    private Integer psychologicalMaleCount;
+
+    @ApiModelProperty("心理咨询人数-女")
+    private Integer psychologicalFemaleCount;
+
+    @ApiModelProperty("年级统计")
+    private List<HealthItemCountVo> gradeList;
+
+    @ApiModelProperty("班级统计")
+    private List<HealthItemCountVo> classList;
+}

+ 29 - 0
src/main/java/com/xjrsoft/module/databoard/vo/ItemCountAmountVo.java

@@ -0,0 +1,29 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+
+/**
+* @title: 数据看板-流程统计出参
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class ItemCountAmountVo {
+
+    /**
+    * 发起流程总数
+    */
+    @ApiModelProperty("统计项")
+    private String item;
+    /**
+    * 完成总数
+    */
+    @ApiModelProperty("次数")
+    private Integer count;
+
+    @ApiModelProperty("金额")
+    private Double amount;
+}

+ 27 - 0
src/main/java/com/xjrsoft/module/databoard/vo/ItemCountVo.java

@@ -0,0 +1,27 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+
+/**
+* @title: 数据看板-流程统计出参
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class ItemCountVo {
+
+    /**
+    * 发起流程总数
+    */
+    @ApiModelProperty("统计项")
+    private String item;
+    /**
+    * 完成总数
+    */
+    @ApiModelProperty("数量")
+    private Integer count;
+
+}

+ 27 - 0
src/main/java/com/xjrsoft/module/databoard/vo/ItemDoubleVo.java

@@ -0,0 +1,27 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+
+/**
+* @title: 数据看板-流程统计出参
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class ItemDoubleVo {
+
+    /**
+    * 发起流程总数
+    */
+    @ApiModelProperty("统计项")
+    private String item;
+    /**
+    * 完成总数
+    */
+    @ApiModelProperty("金额")
+    private Double amount;
+
+}

+ 39 - 0
src/main/java/com/xjrsoft/module/databoard/vo/ProcessStatisticsDetailVo.java

@@ -0,0 +1,39 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+* @title: 数据看板-流程统计出参
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class ProcessStatisticsDetailVo {
+
+    /**
+    * 发起流程总数
+    */
+    @ApiModelProperty("发起流程总数")
+    private Long allCount;
+    /**
+    * 完成总数
+    */
+    @ApiModelProperty("完成总数")
+    private Long completeCount;
+    /**
+    * 未完成总数
+    */
+    @ApiModelProperty("未完成总数")
+    private Long uncompleteCount;
+
+    @ApiModelProperty("流程分布情况")
+    private List<DistributionVo> distributionList;
+
+    @ApiModelProperty("审核完结时长分布")
+    private List<DurationVo> durationList;
+
+}

+ 3 - 3
src/main/java/com/xjrsoft/module/databoard/vo/ProcessStatisticsVo.java

@@ -16,16 +16,16 @@ public class ProcessStatisticsVo {
     * 发起流程总数
     */
     @ApiModelProperty("发起流程总数")
-    private Integer allCount;
+    private Long allCount;
     /**
     * 完成总数
     */
     @ApiModelProperty("完成总数")
-    private Integer completeCount;
+    private Long completeCount;
     /**
     * 未完成总数
     */
     @ApiModelProperty("未完成总数")
-    private Integer uncompleteCount;
+    private Long uncompleteCount;
 
 }

+ 39 - 0
src/main/java/com/xjrsoft/module/databoard/vo/StudnetStatisticsDetailVo.java

@@ -0,0 +1,39 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+* @title: 教职工数据
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class StudnetStatisticsDetailVo {
+
+
+    @ApiModelProperty("性别占比数据")
+    private List<ItemCountVo> genderList;
+
+    @ApiModelProperty("学生类型占比数据")
+    private List<ItemCountVo> studentTypeList;
+
+    @ApiModelProperty("年级占比数据")
+    private List<ItemCountVo> gradeList;
+
+    @ApiModelProperty("住校男学生总人数")
+    private Integer studentStayMaleCount;
+
+    @ApiModelProperty("住校女学生总人数")
+    private Integer studentStayFemaleCount;
+
+    @ApiModelProperty("走读男学生总人数")
+    private Integer studentNotStayMaleCount;
+
+    @ApiModelProperty("走读女学生总人数")
+    private Integer studentNotStayFemaleCount;
+
+}

+ 39 - 0
src/main/java/com/xjrsoft/module/databoard/vo/SubscriptionStatisticsDetailVo.java

@@ -0,0 +1,39 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+* @title: 物品申购数据
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class SubscriptionStatisticsDetailVo {
+
+
+    @ApiModelProperty("总金额")
+    private Double totalAmount;
+
+    @ApiModelProperty("申购类型次数对比数据")
+    private List<ItemCountVo> categoryCountList;
+
+    @ApiModelProperty("申购类型金额对比数据")
+    private List<ItemDoubleVo> categoryAmountList;
+
+    @ApiModelProperty("申购次数")
+    private Integer allCount;
+
+    @ApiModelProperty("通过次数")
+    private Integer adoptCount;
+
+    @ApiModelProperty("待审次数")
+    private Integer pendingCount;
+
+    @ApiModelProperty("部门申购统计数据")
+    private List<ItemCountAmountVo> deptList;
+
+}

+ 33 - 0
src/main/java/com/xjrsoft/module/databoard/vo/TeacherStatisticsDetailVo.java

@@ -0,0 +1,33 @@
+package com.xjrsoft.module.databoard.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+* @title: 教职工数据
+* @Author dzx
+* @Date: 2024年8月2日
+* @Version 1.0
+*/
+@Data
+public class TeacherStatisticsDetailVo {
+
+
+    @ApiModelProperty("学历占比数据")
+    private List<ItemCountVo> educationList;
+
+    @ApiModelProperty("性别占比数据")
+    private List<ItemCountVo> genderList;
+
+    @ApiModelProperty("聘用占比数据")
+    private List<ItemCountVo> employList;
+
+    @ApiModelProperty("年龄占比数据")
+    private List<ItemCountVo> ageList;
+
+    @ApiModelProperty("部门统计数据")
+    private List<ItemCountVo> deptList;
+
+}

+ 1 - 1
src/main/java/com/xjrsoft/module/evaluate/service/impl/EvaluateResultServiceImpl.java

@@ -146,7 +146,7 @@ public class EvaluateResultServiceImpl extends MPJBaseServiceImpl<EvaluateResult
                 .selectSum(EvaluateExecuter::getStatus, ResultViewingPageVo::getActualExecuterNum)//这里值得推敲
                 .leftJoin(EvaluateObject.class, EvaluateObject::getId, EvaluateExecuter::getEvaluateObjectId)
                 .eq(EvaluateExecuter::getEvaluateManageId, dto.getEvaluateManageId())
-                .in(EvaluateObject::getObjectId, evaluateObjectIdList)
+                .in(!evaluateObjectIdList.isEmpty(), EvaluateObject::getObjectId, evaluateObjectIdList)
                 .groupBy(EvaluateObject::getObjectId)
                 .disableSubLogicDel();
         List<ResultViewingPageVo> planAndActualExecuterNum = evaluateExecuterMapper.selectJoinList(ResultViewingPageVo.class, evaluateExecuterMPJLambdaWrapper);

+ 1 - 0
src/main/java/com/xjrsoft/module/organization/service/impl/UserPostRelationServiceImpl.java

@@ -98,6 +98,7 @@ public class UserPostRelationServiceImpl extends ServiceImpl<UserPostRelationMap
         }
 
         List<Long> finalUserIds1 = userIds;
+        finalUserIds1.addAll(userIdList);
         CompletableFuture.runAsync(() -> {
             List<UserPostRelation> userRelationList = this.list();
             redisUtil.set(GlobalConstant.USER_POST_RELATION_CACHE_KEY, userRelationList);

+ 1 - 0
src/main/java/com/xjrsoft/module/student/controller/BaseStudentDevelopmentController.java

@@ -59,6 +59,7 @@ public class BaseStudentDevelopmentController {
         queryWrapper
                 .eq(BaseStudentDevelopment::getBaseStudentGraduateId, dto.getBaseStudentGraduateId())
                     .orderByDesc(BaseStudentDevelopment::getId)
+                .select(BaseStudentDevelopment::getId)
                 .select(BaseStudentDevelopment.class,x -> VoToColumnUtil.fieldsToColumns(BaseStudentDevelopmentPageVo.class).contains(x.getProperty()));
         IPage<BaseStudentDevelopment> page = developmentService.page(ConventPage.getPage(dto), queryWrapper);
         PageOutput<BaseStudentDevelopmentPageVo> pageOutput = ConventPage.getPageOutput(page, BaseStudentDevelopmentPageVo.class);

+ 29 - 1
src/main/java/com/xjrsoft/module/student/controller/BaseStudentInfoController.java

@@ -1,11 +1,15 @@
 package com.xjrsoft.module.student.controller;
 
 import cn.dev33.satoken.annotation.SaCheckPermission;
+import cn.dev33.satoken.stp.StpUtil;
 import cn.hutool.core.bean.BeanUtil;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.xjrsoft.common.model.result.RT;
 import com.xjrsoft.common.page.ConventPage;
 import com.xjrsoft.common.page.PageOutput;
+import com.xjrsoft.module.base.entity.WhitelistManagement;
+import com.xjrsoft.module.base.service.IWhitelistManagementService;
 import com.xjrsoft.module.student.dto.BaseStudentInfoDetailDto;
 import com.xjrsoft.module.student.dto.BaseStudentInfoPageDto;
 import com.xjrsoft.module.student.dto.BaseStudentSimpleInfoDto;
@@ -18,6 +22,7 @@ import com.xjrsoft.module.student.vo.BaseStudentInfoPageDataVo;
 import com.xjrsoft.module.student.vo.BaseStudentInfoPageVo;
 import com.xjrsoft.module.student.vo.BaseStudentSompleInfoVo;
 import com.xjrsoft.module.student.vo.MobileClassStatisticsVo;
+import com.xjrsoft.module.student.vo.WhitelistInfoVo;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
 import lombok.AllArgsConstructor;
@@ -45,7 +50,7 @@ public class  BaseStudentInfoController {
 
     private final IStudentManagerService studentManagerService;
     private final IBaseStudentSchoolRollService baseStudentSchoolRollService;
-
+    private final IWhitelistManagementService whitelistService;
     @GetMapping(value = "/mobile-page")
     @ApiOperation(value="学生列表(分页)")
     @SaCheckPermission("basestudentpost:detail")
@@ -103,4 +108,27 @@ public class  BaseStudentInfoController {
         return RT.ok(infos);
     }
 
+    @GetMapping(value = "/getWhitelistInfo")
+    @ApiOperation(value="根据userId查询白名单信息(不传默认查询登录者)")
+    @SaCheckPermission("room:detail")
+    public RT<WhitelistInfoVo> getWhitelistInfo(Long userId){
+        if(userId == null){
+            userId = StpUtil.getLoginIdAsLong();
+        }
+
+        WhitelistManagement one = whitelistService.getOne(
+                new QueryWrapper<WhitelistManagement>().lambda()
+                        .eq(WhitelistManagement::getUserId, userId)
+        );
+        WhitelistInfoVo whitelistInfoVo = new WhitelistInfoVo();
+        whitelistInfoVo.setWhitelistStatus(0);
+        if(one != null){
+            whitelistInfoVo.setWhitelistStatus(1);
+            whitelistInfoVo.setEndTime(one.getEndTime());
+            whitelistInfoVo.setIsTemporary(one.getIsTemporary());
+        }
+
+        return RT.ok(whitelistInfoVo);
+    }
+
 }

+ 1 - 0
src/main/java/com/xjrsoft/module/student/controller/BaseStudentScholarshipCategoryController.java

@@ -60,6 +60,7 @@ public class BaseStudentScholarshipCategoryController {
             .like(StrUtil.isNotEmpty(dto.getScholarshipName()), BaseStudentScholarshipCategory::getName, dto.getScholarshipName())
             .like(StrUtil.isNotEmpty(dto.getScholarshipSource()), DictionaryDetail::getCode, dto.getScholarshipSource())
             .eq(ObjectUtil.isNotNull(dto.getScholarshipLevel()), BaseStudentScholarshipCategory::getScholarshipLevel, dto.getScholarshipLevel())
+            .eq(ObjectUtil.isNotNull(dto.getBaseSemesterId()), BaseStudentScholarshipCategory::getBaseSemesterId, dto.getBaseSemesterId())
             .select(BaseStudentScholarshipCategory::getId)
             .selectAs(DictionaryDetail::getName, BaseStudentScholarshipCategoryPageVo::getScholarshipSourceCn)
             .select("t2.name", BaseStudentScholarshipCategoryPageVo::getCategoryCn)

+ 2 - 3
src/main/java/com/xjrsoft/module/student/controller/BaseStudentScholarshipReleaseController.java

@@ -10,7 +10,6 @@ import com.xjrsoft.common.model.result.RT;
 import com.xjrsoft.common.page.ConventPage;
 import com.xjrsoft.common.page.PageOutput;
 import com.xjrsoft.common.utils.VoToColumnUtil;
-import com.xjrsoft.module.organization.service.IUserService;
 import com.xjrsoft.module.student.dto.AddBaseStudentScholarshipReleaseDto;
 import com.xjrsoft.module.student.dto.AddStudentScholarshipDto;
 import com.xjrsoft.module.student.dto.BaseStudentScholarshipReleasePageDto;
@@ -126,7 +125,7 @@ public class BaseStudentScholarshipReleaseController {
     @ApiOperation(value = "删除奖学金发放记录表")
     @SaCheckPermission("basestudentscholarshiprelease:delete")
     public RT<Boolean> delete(@Valid @RequestBody List<Long> ids) {
-        return RT.ok(releaseService.removeBatchByIds(ids));
+        return RT.ok(releaseService.remove(ids));
     }
 
     @PostMapping("add-student")
@@ -166,7 +165,7 @@ public class BaseStudentScholarshipReleaseController {
     }
 
     @PostMapping("/import")
-    @ApiOperation(value = "成绩导入")
+    @ApiOperation(value = "奖助学金发放导入")
     public RT<List<Map<String, String>>> scoreImport(@RequestParam MultipartFile file) throws IOException {
         List<Map<String, String>> maps = applicantService.importData(file);
         return RT.ok(maps);

+ 38 - 0
src/main/java/com/xjrsoft/module/student/controller/StudentLeaveController.java

@@ -0,0 +1,38 @@
+package com.xjrsoft.module.student.controller;
+
+import cn.dev33.satoken.annotation.SaCheckPermission;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.xjrsoft.common.model.result.R;
+import com.xjrsoft.common.page.ConventPage;
+import com.xjrsoft.common.page.PageOutput;
+import com.xjrsoft.module.student.dto.StudentLeavePageDto;
+import com.xjrsoft.module.student.service.IStudentLeaveService;
+import com.xjrsoft.module.student.vo.StudentLeavePageVo;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import lombok.AllArgsConstructor;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import javax.validation.Valid;
+
+@RestController
+@RequestMapping("/student" + "/leave")
+@Api(value = "/student" + "/leave", tags = "学生请假")
+@AllArgsConstructor
+public class StudentLeaveController {
+
+    private final IStudentLeaveService studentLeaveService;
+
+    @GetMapping(value = "/page")
+    @ApiOperation(value = "学生请假列表(分页)")
+    @SaCheckPermission("studentleave:detail")
+    public R page(@Valid StudentLeavePageDto dto) {
+        IPage<StudentLeavePageVo> page = studentLeaveService.getLeavePage(new Page<>(dto.getLimit(), dto.getSize()), dto);
+
+        PageOutput<StudentLeavePageVo> pageOutput = ConventPage.getPageOutput(page, StudentLeavePageVo.class);
+        return R.ok(pageOutput);
+    }
+}

+ 3 - 0
src/main/java/com/xjrsoft/module/student/dto/BaseStudentScholarshipCategoryPageDto.java

@@ -24,4 +24,7 @@ public class BaseStudentScholarshipCategoryPageDto extends PageInput {
 
     @ApiModelProperty("奖学金等级")
     private Integer scholarshipLevel;
+
+    @ApiModelProperty("学期id")
+    private Long baseSemesterId;
 }

+ 28 - 0
src/main/java/com/xjrsoft/module/student/dto/StudentLeavePageDto.java

@@ -0,0 +1,28 @@
+package com.xjrsoft.module.student.dto;
+
+import com.xjrsoft.common.page.PageInput;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+@Data
+@EqualsAndHashCode(callSuper = false)
+public class StudentLeavePageDto  extends PageInput {
+    /**
+     * 账户
+     */
+    @ApiModelProperty("账户")
+    private Long userId;
+
+    /**
+     * 开始时间
+     */
+    @ApiModelProperty("开始时间")
+    private String startDate;
+
+    /**
+     * 结束时间
+     */
+    @ApiModelProperty("结束时间")
+    private String endDate;
+}

+ 5 - 0
src/main/java/com/xjrsoft/module/student/mapper/StudentLeaveMapper.java

@@ -1,9 +1,12 @@
 package com.xjrsoft.module.student.mapper;
 
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.github.yulichang.base.MPJBaseMapper;
 import com.xjrsoft.module.attendance.dto.AttendanceStatisticDto;
 import com.xjrsoft.module.outint.vo.IdCountVo;
+import com.xjrsoft.module.student.dto.StudentLeavePageDto;
 import com.xjrsoft.module.student.entity.StudentLeave;
+import com.xjrsoft.module.student.vo.StudentLeavePageVo;
 import org.apache.ibatis.annotations.Mapper;
 import org.apache.ibatis.annotations.Param;
 
@@ -25,4 +28,6 @@ public interface StudentLeaveMapper extends MPJBaseMapper<StudentLeave> {
 
 
     List<StudentLeave> getLeaveList(@Param("startTime") LocalDateTime startTime, @Param("endTime") LocalDateTime endTime);
+
+    Page<StudentLeavePageVo> getLeavePage(Page<StudentLeavePageVo> page, StudentLeavePageDto dto);
 }

+ 4 - 0
src/main/java/com/xjrsoft/module/student/service/IBaseStudentScholarshipReleaseService.java

@@ -6,6 +6,8 @@ import com.xjrsoft.module.student.dto.BaseStudentScholarshipReleasePageDto;
 import com.xjrsoft.module.student.entity.BaseStudentScholarshipRelease;
 import com.xjrsoft.module.student.vo.BaseStudentScholarshipReleasePageVo;
 
+import java.util.List;
+
 /**
 * @title: 奖学金发放记录表
 * @Author dzx
@@ -16,4 +18,6 @@ import com.xjrsoft.module.student.vo.BaseStudentScholarshipReleasePageVo;
 public interface IBaseStudentScholarshipReleaseService extends MPJBaseService<BaseStudentScholarshipRelease> {
 
     Page<BaseStudentScholarshipReleasePageVo> getPage(Page<BaseStudentScholarshipReleasePageVo> page, BaseStudentScholarshipReleasePageDto dto);
+
+    Boolean remove(List<Long> ids);
 }

+ 7 - 0
src/main/java/com/xjrsoft/module/student/service/IStudentLeaveService.java

@@ -1,8 +1,13 @@
 package com.xjrsoft.module.student.service;
 
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.github.yulichang.base.MPJBaseService;
 import com.xjrsoft.module.attendance.dto.AttendanceStatisticDto;
+import com.xjrsoft.module.student.dto.BaseStudentUserPageDto;
+import com.xjrsoft.module.student.dto.StudentLeavePageDto;
 import com.xjrsoft.module.student.entity.StudentLeave;
+import com.xjrsoft.module.student.vo.BaseStudentUserPageVo;
+import com.xjrsoft.module.student.vo.StudentLeavePageVo;
 import org.apache.ibatis.annotations.Param;
 
 import java.time.LocalDateTime;
@@ -25,4 +30,6 @@ public interface IStudentLeaveService extends MPJBaseService<StudentLeave> {
 
 
     Map<Long, StudentLeave> getLeaveList(@Param("startTime") LocalDateTime startTime, @Param("endTime") LocalDateTime endTime);
+
+    Page<StudentLeavePageVo> getLeavePage(Page<StudentLeavePageVo> page, StudentLeavePageDto dto);
 }

+ 19 - 7
src/main/java/com/xjrsoft/module/student/service/impl/BaseStudentScholarshipApplicantServiceImpl.java

@@ -10,6 +10,8 @@ import com.xjrsoft.common.enums.GenderEnum;
 import com.xjrsoft.common.utils.VoToColumnUtil;
 import com.xjrsoft.module.base.entity.BaseSemester;
 import com.xjrsoft.module.base.service.IBaseSemesterService;
+import com.xjrsoft.module.organization.entity.User;
+import com.xjrsoft.module.organization.service.IUserService;
 import com.xjrsoft.module.student.dto.BaseStudentScholarshipApplicantCategoryPageDto;
 import com.xjrsoft.module.student.entity.BaseStudentScholarshipApplicant;
 import com.xjrsoft.module.student.entity.BaseStudentScholarshipCategory;
@@ -44,6 +46,7 @@ public class BaseStudentScholarshipApplicantServiceImpl extends MPJBaseServiceIm
     private final BaseStudentScholarshipApplicantMapper applicantMapper;
     private final IBaseSemesterService semesterService;
     private final IBaseStudentScholarshipCategoryService categoryService;
+    private final IUserService userService;
     @Override
     public Page<BaseStudentScholarshipApplicantCategoryPageVo> getScholarshiPage(Page<BaseStudentScholarshipApplicantCategoryPageDto> page, BaseStudentScholarshipApplicantCategoryPageDto dto) {
         Page<BaseStudentScholarshipApplicantCategoryPageVo> result = applicantMapper.getScholarshiPage(page, dto);
@@ -77,7 +80,7 @@ public class BaseStudentScholarshipApplicantServiceImpl extends MPJBaseServiceIm
 
     @Override
     public List<Map<String, String>> importData(MultipartFile file) throws IOException {
-        List<ScholarshipApplicantImportVo> dataList = EasyExcel.read(file.getInputStream()).headRowNumber(2).head(ScholarshipApplicantImportVo.class).sheet().doReadSync();
+        List<ScholarshipApplicantImportVo> dataList = EasyExcel.read(file.getInputStream()).headRowNumber(3).head(ScholarshipApplicantImportVo.class).sheet().doReadSync();
         List<BaseStudentScholarshipApplicant> applicantList = this.list(
                 new QueryWrapper<BaseStudentScholarshipApplicant>().lambda()
                         .select(BaseStudentScholarshipApplicant::getId)
@@ -85,6 +88,9 @@ public class BaseStudentScholarshipApplicantServiceImpl extends MPJBaseServiceIm
                         .eq(BaseStudentScholarshipApplicant::getStatus, 1)
         );
 
+        List<Long> userIds = applicantList.stream().map(BaseStudentScholarshipApplicant::getApplicantUserId).collect(Collectors.toList());
+        Map<Long, User> userMap = userService.list(new QueryWrapper<User>().lambda().in(User::getId, userIds)).stream().collect(Collectors.toMap(x -> x.getId(), x -> x));
+
         List<BaseSemester> semesterList = semesterService.list(
                 new QueryWrapper<BaseSemester>().lambda()
                         .select(BaseSemester::getId)
@@ -100,7 +106,8 @@ public class BaseStudentScholarshipApplicantServiceImpl extends MPJBaseServiceIm
                         .eq(BaseStudentScholarshipCategory::getDeleteMark, DeleteMark.NODELETE.getCode())
         );
 
-        Map<String, Long> categoryMap = categoryList.stream().collect(Collectors.toMap(BaseStudentScholarshipCategory::getName, BaseStudentScholarshipCategory::getId));
+        Map<String, BaseStudentScholarshipCategory> categoryMap = categoryList.stream().collect(Collectors.toMap(BaseStudentScholarshipCategory::getName, x -> x));
+        Map<String, Long> categorySemeterMap = categoryList.stream().collect(Collectors.toMap(BaseStudentScholarshipCategory::getName, BaseStudentScholarshipCategory::getBaseSemesterId));
 
         List<Map<String, String>> errorList = new ArrayList<>();
         List<BaseStudentScholarshipApplicant> updateList = new ArrayList<>();
@@ -111,24 +118,29 @@ public class BaseStudentScholarshipApplicantServiceImpl extends MPJBaseServiceIm
                 errorMsg.add("有未填写的列");
             }
             if(semesterMap.get(importVo.getSemesterName()) == null){
-                errorMsg.add("学期名称填写不正确");
+                errorMsg.add("学期填写不正确");
             }
             Long semesterId = semesterMap.get(importVo.getSemesterName());
             if(categoryMap.get(importVo.getScholarshipCategoryName()) == null){
                 errorMsg.add("奖学金名称填写不正确");
             }
-            Long categoryId = categoryMap.get(importVo.getScholarshipCategoryName());
+            BaseStudentScholarshipCategory category = categoryMap.get(importVo.getScholarshipCategoryName());
             for (BaseStudentScholarshipApplicant applicant : applicantList) {
-                if(applicant.getBaseSemesterId() == semesterId && importVo.getName().equals(applicant.getName()) && importVo.getCredentialNumber().equals(applicant.getStudentId())){
-                    applicant.setBaseStudentScholarshipCategoryId(categoryId);
+                User user = userMap.get(applicant.getApplicantUserId());
+                Long baseSemesterId = categorySemeterMap.get(importVo.getScholarshipCategoryName());
+                if(baseSemesterId.equals(semesterId)
+                        && importVo.getName().equals(user.getName())
+                        && importVo.getCredentialNumber().equals(user.getCredentialNumber())){
+                    applicant.setBaseStudentScholarshipCategoryId(category.getId());
                     applicant.setReviewStatus(1);
+                    applicant.setAmount(category.getTotalAmount());
                     applicant.setScholarshipLevel(importVo.getScholarshipLevel());
                     updateList.add(applicant);
                 }
             }
             if(!errorMsg.isEmpty()){
                 LinkedHashMap<String, String> map = new LinkedHashMap<>();
-                map.put("学期名称", importVo.getSemesterName());
+                map.put("学期", importVo.getSemesterName());
                 map.put("姓名", importVo.getName());
                 map.put("身份证号", importVo.getCredentialNumber());
                 map.put("奖学金名称", importVo.getScholarshipCategoryName());

+ 20 - 0
src/main/java/com/xjrsoft/module/student/service/impl/BaseStudentScholarshipReleaseServiceImpl.java

@@ -1,15 +1,21 @@
 package com.xjrsoft.module.student.service.impl;
 
+import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
 import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.github.yulichang.base.MPJBaseServiceImpl;
+import com.xjrsoft.module.room.entity.RoomBed;
 import com.xjrsoft.module.student.dto.BaseStudentScholarshipReleasePageDto;
+import com.xjrsoft.module.student.entity.BaseStudentScholarshipApplicant;
 import com.xjrsoft.module.student.entity.BaseStudentScholarshipRelease;
+import com.xjrsoft.module.student.mapper.BaseStudentScholarshipApplicantMapper;
 import com.xjrsoft.module.student.mapper.BaseStudentScholarshipReleaseMapper;
 import com.xjrsoft.module.student.service.IBaseStudentScholarshipReleaseService;
 import com.xjrsoft.module.student.vo.BaseStudentScholarshipReleasePageVo;
 import lombok.AllArgsConstructor;
 import org.springframework.stereotype.Service;
 
+import java.util.List;
+
 /**
 * @title: 奖学金发放记录表
 * @Author dzx
@@ -19,8 +25,22 @@ import org.springframework.stereotype.Service;
 @Service
 @AllArgsConstructor
 public class BaseStudentScholarshipReleaseServiceImpl extends MPJBaseServiceImpl<BaseStudentScholarshipReleaseMapper, BaseStudentScholarshipRelease> implements IBaseStudentScholarshipReleaseService {
+    private BaseStudentScholarshipApplicantMapper applicantMapper;
     @Override
     public Page<BaseStudentScholarshipReleasePageVo> getPage(Page<BaseStudentScholarshipReleasePageVo> page, BaseStudentScholarshipReleasePageDto dto) {
         return this.baseMapper.getPage(page, dto);
     }
+
+    @Override
+    public Boolean remove(List<Long> ids) {
+        List<BaseStudentScholarshipApplicant> applicantList = applicantMapper.selectBatchIds(ids);
+        for (BaseStudentScholarshipApplicant applicant : applicantList) {
+            UpdateWrapper<BaseStudentScholarshipApplicant> updateWrapper = new UpdateWrapper<>();
+            updateWrapper.eq("id", applicant.getId());
+            updateWrapper.setSql("review_status = null");
+            applicantMapper.update(applicant, updateWrapper);
+        }
+
+        return this.removeBatchByIds(ids);
+    }
 }

+ 10 - 0
src/main/java/com/xjrsoft/module/student/service/impl/StudentLeaveServiceImpl.java

@@ -1,6 +1,7 @@
 package com.xjrsoft.module.student.service.impl;
 
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.github.yulichang.base.MPJBaseServiceImpl;
 import com.google.gson.JsonArray;
 import com.google.gson.JsonElement;
@@ -11,9 +12,13 @@ import com.xjrsoft.module.hikvision.entity.HikvisionData;
 import com.xjrsoft.module.hikvision.mapper.HikvisionDataMapper;
 import com.xjrsoft.module.hikvision.util.ApiUtil;
 import com.xjrsoft.module.outint.vo.IdCountVo;
+import com.xjrsoft.module.student.dto.BaseStudentUserPageDto;
+import com.xjrsoft.module.student.dto.StudentLeavePageDto;
 import com.xjrsoft.module.student.entity.StudentLeave;
 import com.xjrsoft.module.student.mapper.StudentLeaveMapper;
 import com.xjrsoft.module.student.service.IStudentLeaveService;
+import com.xjrsoft.module.student.vo.BaseStudentUserPageVo;
+import com.xjrsoft.module.student.vo.StudentLeavePageVo;
 import lombok.AllArgsConstructor;
 import org.springframework.stereotype.Service;
 
@@ -105,6 +110,11 @@ public class StudentLeaveServiceImpl extends MPJBaseServiceImpl<StudentLeaveMapp
         return result;
     }
 
+    @Override
+    public Page<StudentLeavePageVo> getLeavePage(Page<StudentLeavePageVo> page, StudentLeavePageDto dto) {
+        return baseMapper.getLeavePage(page, dto);
+    }
+
     JsonArray selectResource(ApiUtil apiUtil){
         String apiPath = "/api/irds/v2/resource/resourcesByParams";
         JsonObject jsonObject = new JsonObject();

+ 7 - 0
src/main/java/com/xjrsoft/module/student/vo/BaseStudentDevelopmentVo.java

@@ -79,6 +79,9 @@ public class BaseStudentDevelopmentVo {
     */
     @ApiModelProperty("就业单位规模(xjr_dictionary_item[company_scale])")
     private String companyScaleCn;
+
+    @ApiModelProperty("就业单位规模(xjr_dictionary_item[company_scale])")
+    private String companyScale;
     /**
     * 是否对口(1:是 0:否)
     */
@@ -137,6 +140,10 @@ public class BaseStudentDevelopmentVo {
     */
     @ApiModelProperty("升学层次(xjr_dictionary_item[ascending_arrangement])")
     private String ascendingArrangementCn;
+
+    @ApiModelProperty("升学层次(xjr_dictionary_item[ascending_arrangement])")
+    private String ascendingArrangement;
+
     /**
     * 未就业类型(xjr_dictionary_item[unemployed_type])
     */

+ 5 - 5
src/main/java/com/xjrsoft/module/student/vo/ScholarshipApplicantImportVo.java

@@ -13,23 +13,23 @@ import lombok.Data;
 @Data
 public class ScholarshipApplicantImportVo {
 
-    @ExcelProperty("学期名称")
+    @ExcelProperty("*学期")
     @ApiModelProperty("学期名称")
     private String semesterName;
 
-    @ExcelProperty("姓名")
+    @ExcelProperty("*姓名")
     @ApiModelProperty("姓名")
     private String name;
 
-    @ExcelProperty("身份证号")
+    @ExcelProperty("*身份证号")
     @ApiModelProperty("身份证号")
     private String credentialNumber;
 
-    @ExcelProperty("奖学金名称")
+    @ExcelProperty("*奖学金名称")
     @ApiModelProperty("奖学金名称")
     private String scholarshipCategoryName;
 
-    @ExcelProperty("获奖等级")
+    @ExcelProperty("*获奖等级")
     @ApiModelProperty("获奖等级")
     private Integer scholarshipLevel;
 

+ 53 - 0
src/main/java/com/xjrsoft/module/student/vo/StudentLeavePageVo.java

@@ -0,0 +1,53 @@
+package com.xjrsoft.module.student.vo;
+
+import com.baomidou.mybatisplus.annotation.TableId;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.time.LocalDate;
+
+@Data
+public class StudentLeavePageVo {
+    /**
+     * 主键编号
+     */
+    @ApiModelProperty("主键编号")
+    @TableId
+    private Long id;
+
+    @ApiModelProperty("学生id")
+    private Long studentUserId;
+
+    @ApiModelProperty("班级id")
+    private Long classId;
+
+    @ApiModelProperty("开始时间")
+    private LocalDate startDate;
+
+    @ApiModelProperty("开始时间")
+    private LocalDate endDate;
+
+    @ApiModelProperty("请假原因")
+    private String reason;
+
+    @ApiModelProperty("班主任")
+    private Long teacherId;
+
+    @ApiModelProperty("附件id")
+    private Long folderId;
+
+    /**
+     * 状态(1:结束 0:未结束)
+     */
+    @ApiModelProperty("状态(1:结束 0:未结束)")
+    private Integer status;
+
+    @ApiModelProperty("时长(天)")
+    private Double dayDuration;
+
+    @ApiModelProperty("请假类型")
+    private String leaveType;
+
+    @ApiModelProperty("海康接口返回信息")
+    private String hikvisionResult;
+}

+ 26 - 0
src/main/java/com/xjrsoft/module/student/vo/WhitelistInfoVo.java

@@ -0,0 +1,26 @@
+package com.xjrsoft.module.student.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+
+/**
+* @title: 专业分类表表单出参
+* @Author szs
+* @Date: 2024-04-01
+* @Version 1.0
+*/
+@Data
+public class WhitelistInfoVo {
+
+    @ApiModelProperty("是否存在于白名单中(1:是 0:否)")
+    public Integer whitelistStatus;
+
+    @ApiModelProperty("截止日期")
+    private LocalDate endTime;
+
+    @ApiModelProperty("是否临时性的(1:是 0:否)")
+    private Integer isTemporary;
+}

+ 2 - 2
src/main/java/com/xjrsoft/module/system/service/impl/LoginServiceImpl.java

@@ -137,12 +137,12 @@ public class LoginServiceImpl implements ILoginService {
         }else{
             weChatUserInfo = weChatUtil.getOpenid(dto.getCode());
         }
+
+        if (weChatUserInfo == null) throw new MyException("code无效");
         LoginByCodeVo result = new LoginByCodeVo(){{
             setOpenId(weChatUserInfo.getOpenid());
             setUnionId(weChatUserInfo.getUnionid());
         }};
-        if (weChatUserInfo == null) throw new MyException("code无效");
-
         LambdaQueryWrapper<User> queryWrapper = new LambdaQueryWrapper<>();
         queryWrapper.eq(User::getUnionId, weChatUserInfo.getUnionid());
 

+ 1 - 10
src/main/java/com/xjrsoft/module/workflow/service/impl/WorkflowExecuteServiceImpl.java

@@ -4194,14 +4194,11 @@ public class WorkflowExecuteServiceImpl implements IWorkflowExecuteService {
             historicProcessInstanceQuery.unfinished();
         }
 
-        long count = historicProcessInstanceQuery.count();
-//        List<HistoricProcessInstance> historicProcessInstances = historicProcessInstanceQuery.listPage(Convert.toInt((dto.getLimit() - 1) * dto.getSize()), dto.getSize());
         List<HistoricProcessInstance> historicProcessInstances = historicProcessInstanceQuery.list();
 
         //获取到所有流程id
         List<String> processIds = historicProcessInstances.stream().map(HistoricProcessInstance::getId).collect(Collectors.toList());
 
-
         List<MonitorPageVo> result = new ArrayList<>(historicProcessInstances.size());
         if (processIds.size() > 0) {
             List<WorkflowExtra> workflowExtras = extraService.list(
@@ -4211,13 +4208,7 @@ public class WorkflowExecuteServiceImpl implements IWorkflowExecuteService {
                             .leftJoin(DictionaryDetail.class, DictionaryDetail::getId, WorkflowSchema::getCategory)
                             .eq(StrUtil.isNotEmpty(dto.getCategory()), DictionaryDetail::getCode, dto.getCategory())
             );
-//            List<WorkflowExtra> workflowExtras = workflowExtraMapper.selectList(
-//                    Wrappers.lambdaQuery(WorkflowExtra.class).in(WorkflowExtra::getProcessId, processIds)
-//            );
-
             for (HistoricProcessInstance historicProcessInstance : historicProcessInstances) {
-
-
                 //找到当前流程的 任务开始时间 最大值  为当前审批节点
                 workflowExtras.stream()
                         .filter(e -> e.getProcessId().equals(historicProcessInstance.getId()))
@@ -4256,7 +4247,7 @@ public class WorkflowExecuteServiceImpl implements IWorkflowExecuteService {
         PageOutput<MonitorPageVo> output = new PageOutput<>();
         output.setCurrentPage(dto.getLimit());
         output.setPageSize(dto.getSize());
-        output.setTotal(Convert.toInt(count));
+        output.setTotal(result.size());
         output.setList(result);
         return output;
     }

+ 25 - 0
src/main/java/com/xjrsoft/module/workflow/utils/WorkFlowUtil.java

@@ -77,7 +77,9 @@ import org.camunda.bpm.model.bpmn.instance.SequenceFlow;
 import org.camunda.bpm.model.xml.instance.ModelElementInstance;
 import org.ssssssss.magicapi.core.service.MagicAPIService;
 
+import java.time.LocalDate;
 import java.time.LocalDateTime;
+import java.time.ZoneId;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Calendar;
@@ -1380,6 +1382,17 @@ public class WorkFlowUtil {
         return calendar.getTime();
     }
 
+    /**
+     * 获取一天的开始时间 00:00:00
+     *
+     * @param date 某一天时间
+     * @return 某一天的开始时间, 比如2023-01-01 00:00:00
+     */
+    public static Date getStartOfDay(LocalDate date) {
+        LocalDateTime localDateTime = date.atStartOfDay();
+        return Date.from(localDateTime.atZone(ZoneId.systemDefault()).toInstant());
+    }
+
     /**
      * 获取一天的结束时间 23:59:59
      *
@@ -1395,5 +1408,17 @@ public class WorkFlowUtil {
         calendar.set(Calendar.MILLISECOND, 999);
         return calendar.getTime();
     }
+
+    /**
+     * 获取一天的结束时间 23:59:59
+     *
+     * @param date 某一天时间
+     * @return 某一天的结束时间, 比如2023-01-01 23:59:59
+     */
+    public static Date getEndOfDay(LocalDate date) {
+        LocalDateTime localDateTime = date.plusDays(1).atStartOfDay();
+        LocalDateTime dateTime = localDateTime.plusNanos(-1);
+        return Date.from(dateTime.atZone(ZoneId.systemDefault()).toInstant());
+    }
 }
 

+ 1 - 1
src/main/resources/mapper/student/BaseStudentDevelopmentMapper.xml

@@ -8,7 +8,7 @@
                t1.is_company_coop,t1.work_company,t7.name AS company_industry,t8.name AS company_nature,t2.name AS company_scale_cn,t1.is_matching,
                t1.money,t1.work_date,t1.work_city,t3.name AS culture_type_cn,t4.name AS ascending_channels_cn,
                t1.school,t1.admission_major,t1.score,t5.name AS ascending_arrangement_cn,t6.name AS unemployed_type_cn,t1.remark,t1.enroll_type,
-               t1.culture_type,t1.ascending_channels,t1.unemployed_type
+               t1.culture_type,t1.ascending_channels,t1.unemployed_type,t1.company_scale,t1.ascending_arrangement
         FROM base_student_development t1
                  LEFT JOIN xjr_dictionary_detail t2 ON t1.company_scale = t2.code
                  LEFT JOIN xjr_dictionary_detail t3 ON t1.culture_type = t3.code

+ 1 - 1
src/main/resources/mapper/student/PbVXsxxsfytbMapper.xml

@@ -55,7 +55,7 @@
         GROUP BY t2.name
     </select>
     <select id="stduyStatusStat" parameterType="com.xjrsoft.module.student.dto.PbVXsxxsfytbStatDto" resultType="com.xjrsoft.module.student.vo.StringCountVo">
-        SELECT replace(t2.name,'住校','住读'),COUNT(t1.credential_number) as count FROM xjr_user t1
+        SELECT replace(t2.name,'住校','住读') as name,COUNT(t1.credential_number) as count FROM xjr_user t1
         INNER JOIN base_student_school_roll t3 ON t1.id = t3.user_id
         left JOIN xjr_dictionary_detail t2 ON t3.stduy_status = t2.code and t2.item_id = 2023000000000000030
         WHERE t3.delete_mark = 0

+ 16 - 0
src/main/resources/mapper/student/StudentLeaveMapper.xml

@@ -43,4 +43,20 @@
                 OR (DATE_FORMAT(#{startTime}, '%Y-%m-%d') > start_date and end_date > DATE_FORMAT(#{endTime}, '%Y-%m-%d'))
         )
     </select>
+    <select id="getLeavePage" resultType="com.xjrsoft.module.student.vo.StudentLeavePageVo">
+        SELECT t1.* FROM student_leave t1
+                             INNER JOIN xjr_user t2 ON t1.student_user_id = t2.id
+        WHERE t1.status = 1 AND t2.delete_mark = 0
+        <if test="dto.userId != null">
+            and t1.student_user_id = #{dto.userId}
+        </if>
+        <if test="dto.startDate != null and dto.startDate != '' and dto.endDate != null and dto.endDate != ''">
+          AND (
+                (start_date BETWEEN DATE_FORMAT(#{dto.startDate}, '%Y-%m-%d') and DATE_FORMAT(#{dto.endDate}, '%Y-%m-%d'))
+                OR (end_date BETWEEN DATE_FORMAT(#{dto.startDate}, '%Y-%m-%d') and DATE_FORMAT(#{dto.endDate}, '%Y-%m-%d'))
+                OR (start_date > DATE_FORMAT(#{dto.startDate}, '%Y-%m-%d') and DATE_FORMAT(#{dto.endDate}, '%Y-%m-%d') > end_date)
+                OR (DATE_FORMAT(#{dto.startDate}, '%Y-%m-%d') > start_date and end_date > DATE_FORMAT(#{dto.endDate}, '%Y-%m-%d'))
+            )
+        </if>
+    </select>
 </mapper>

+ 2 - 2
src/main/resources/sqlScript/all_sql.sql

@@ -384,9 +384,9 @@ CREATE TABLE IF NOT EXISTS course_subject_detail
     core_course            varchar(16)  NOT NULL COMMENT '是否专业核心课程',
     theory_time            int          NOT NULL COMMENT '理论教学时数',
     practice_time          int          NOT NULL COMMENT '实践教学时数',
-    online_course          varchar(1)   NOT NULL COMMENT '是否有线上课程',
+    online_course          varchar(20)   NOT NULL COMMENT '是否有线上课程',
     course_url             longtext     NULL COMMENT '线上课程网址',
-    ideology_demo          varchar(1)   NOT NULL COMMENT '是否思政示范课程',
+    ideology_demo          varchar(20)   NOT NULL COMMENT '是否思政示范课程',
     course_resource        varchar(10)  NULL DEFAULT '' COMMENT '课堂教学设计主要选用课程资源',
     emulation_time         int          NOT NULL COMMENT '虚拟仿真实训课时数',
     emulation_name         varchar(256) NULL DEFAULT '' COMMENT '主要开设虚拟仿真实训项目名称',