Răsfoiți Sursa

联考版-v3.1.0-分档模块初次提交

xiaof 2 ani în urmă
părinte
comite
7bc9339b1a
71 a modificat fișierele cu 4798 adăugiri și 1592 ștergeri
  1. 25 34
      stmms-ms-accesscontrol/src/main/java/cn/com/qmth/stmms/ms/accesscontrol/api/AuthApi.java
  2. 2 2
      stmms-ms-accesscontrol/src/main/java/cn/com/qmth/stmms/ms/accesscontrol/config/AccessConfig.java
  3. 4 4
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/InspectRangeApi.java
  4. 108 0
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/MessageApi.java
  5. 31 32
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/ParamApi.java
  6. 17 18
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/QualityAnalyseController.java
  7. 10 10
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/ScoreApi.java
  8. 5 8
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/TrialController.java
  9. 4 3
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/UserApi.java
  10. 5 6
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/WorkApi.java
  11. 4 6
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/assembler/WorkOverviewAssembler.java
  12. 15 4
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/dto/MarkExpDTO.java
  13. 1 0
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/exporter/PaperExporter.java
  14. 13 14
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/importer/StudentImporter.java
  15. 67 82
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/service/DataUploadService.java
  16. 58 41
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/service/TrialService.java
  17. 1 1
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/service/WorkService.java
  18. 11 11
      stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/utils/BuiltInParamUtils.java
  19. 1 1
      stmms-ms-commons/src/main/java/cn/com/qmth/stmms/ms/commons/lock/LockType.java
  20. 29 0
      stmms-ms-commons/src/main/java/cn/com/qmth/stmms/ms/commons/utils/RandomUtil.java
  21. 8 8
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/cache/ParamCache.java
  22. 48 48
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/Level.java
  23. 1 1
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/MarkStage.java
  24. 11 0
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/MarkSubject.java
  25. 29 5
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/MarkerGroupStudent.java
  26. 125 0
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/Message.java
  27. 72 0
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/Paper.java
  28. 17 17
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/ParamSetting.java
  29. 44 0
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/RoughLevel.java
  30. 1 1
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/enums/ParamSettingTypeEnum.java
  31. 5 5
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/paramsetting/LevelConfig.java
  32. 1 1
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/paramsetting/RoughLevelConfig.java
  33. 12 18
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/task/MarkTaskRoughLevel.java
  34. 0 3
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/task/MarkTaskScore.java
  35. 1 1
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/user/MarkerGroup.java
  36. 30 26
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkTaskLevelRepo.java
  37. 48 43
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkTaskRoughLevelRepo.java
  38. 30 26
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkTaskScoreRepo.java
  39. 4 0
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkUserRepo.java
  40. 2 0
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkerGroupRepo.java
  41. 8 0
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkerGroupStudentRepo.java
  42. 12 0
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MessageRepo.java
  43. 73 1
      stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/PaperRepo.java
  44. 37 15
      stmms-ms-log/src/main/java/cn/com/qmth/stmms/ms/log/aop/MarkLogAop.java
  45. 16 12
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/ChangeLevelApi.java
  46. 173 45
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/MakrerApi.java
  47. 230 42
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/MarkSubjectApi.java
  48. 135 338
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/MarkTaskApi.java
  49. 127 58
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/PaperApi.java
  50. 15 17
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/TaskApi.java
  51. 20 25
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/MarkTaskLevelAssembler.java
  52. 209 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/MarkTaskRoughLevelAssembler.java
  53. 206 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/MarkTaskScoreAssembler.java
  54. 6 7
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/PaperAssembler.java
  55. 23 26
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/QuestionStatAssembler.java
  56. 22 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/dto/LevleProgressDTO.java
  57. 9 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/dto/PaperDTO.java
  58. 308 129
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/AssignTaskService.java
  59. 27 20
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/AutoRun.java
  60. 9 9
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/DetermineLevelService.java
  61. 192 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/DetermineRoughLevelService.java
  62. 56 40
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/GroupingService.java
  63. 280 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkTaskLevelService.java
  64. 281 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkTaskRoughLevelService.java
  65. 260 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkTaskScoreService.java
  66. 46 18
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkerGroupLeaderService.java
  67. 384 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkingLevelService.java
  68. 376 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkingRoughLevelService.java
  69. 151 0
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkingScoreService.java
  70. 20 264
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkingService.java
  71. 187 46
      stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/StageControlService.java

+ 25 - 34
stmms-ms-accesscontrol/src/main/java/cn/com/qmth/stmms/ms/accesscontrol/api/AuthApi.java

@@ -1,24 +1,22 @@
 package cn.com.qmth.stmms.ms.accesscontrol.api;
 
 import cn.com.qmth.stmms.ms.accesscontrol.config.LoginConfig;
-import cn.com.qmth.stmms.ms.commons.utils.AesUtil;
 import cn.com.qmth.stmms.ms.commons.utils.EncrypAES;
 import cn.com.qmth.stmms.ms.core.cache.CacheService;
+import cn.com.qmth.stmms.ms.core.domain.MarkStage;
 import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.domain.user.Role;
-import cn.com.qmth.stmms.ms.core.repository.MarkSubjectRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkTaskRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
+import cn.com.qmth.stmms.ms.core.repository.*;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.util.CollectionUtils;
-import org.springframework.util.StringUtils;
 import org.springframework.web.bind.annotation.*;
 
+import javax.annotation.Resource;
 import javax.servlet.http.HttpServletRequest;
 import javax.servlet.http.HttpSession;
 import java.net.URLEncoder;
+import java.util.Arrays;
 import java.util.List;
 import java.util.Objects;
 
@@ -38,8 +36,14 @@ public class AuthApi {
     @Autowired
     private CacheService cacheService;
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
+    @Resource
+    private MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     @Autowired
     private MarkSubjectRepo markSubjectRepo;
@@ -47,39 +51,19 @@ public class AuthApi {
     @RequestMapping(value = "/login", method = RequestMethod.POST)
     public MarkUser login(MarkUser user, HttpServletRequest request) throws Exception {
         MarkUser domain = null;
-
-
-        if (loginConfig.adminLoginConfig().getLoginName().equals(user.getLoginName()) &&
+        String loginName = loginConfig.adminLoginConfig().getLoginName();
+        List<String> loginNames = Arrays.asList(loginName.split(","));
+        if (loginNames.indexOf(user.getLoginName()) > 0 &&
                 loginConfig.adminLoginConfig().getPassword().equals(user.getPassword())) {
             domain = new MarkUser(loginConfig.adminLoginConfig().getLoginName(), loginConfig.adminLoginConfig().getPassword(), null, null, "系统管理员", Role.ADMIN, null);
             domain.setId(0l);
-        }
-//        else if (loginConfig.clientLoginConfig().getLoginName().equals(user.getLoginName()) &&
-//                loginConfig.clientLoginConfig().getPassword().equals(user.getPassword())) {
-//            domain = new MarkUser(loginConfig.clientLoginConfig().getLoginName(), loginConfig.clientLoginConfig().getPassword(), null, null, "系统管理员", Role.ADMIN, null);
-//        }
-//        else if (loginConfig.inspectionLoginConfig().getLoginName().equals(user.getLoginName()) &&
-//                loginConfig.inspectionLoginConfig().getPassword().equals(user.getPassword())) {
-//            domain = new MarkUser(loginConfig.inspectionLoginConfig().getLoginName(), loginConfig.inspectionLoginConfig().getPassword(), null, null, "纪检员", Role.INSPECTION, null);
-//        }
-        else {
-//            Work activeWork = workRepo.findByActiveTrue();
-//            String loginName = activeWork.getId() + "-" + user.getLoginName();
-//            domain = markUserRepo.findByLoginName(loginName);
+        } else {
             domain = markUserRepo.findByLoginName(user.getLoginName());
             if (domain == null) {
                 if ((loginConfig.adminLoginConfig().getLoginName().equals(user.getLoginName()) && !loginConfig.adminLoginConfig().getPassword().equals(user.getPassword()))
-//                        || (loginConfig.inspectionLoginConfig().getLoginName().equals(user.getLoginName()) && !loginConfig.inspectionLoginConfig().getPassword().equals(user.getPassword()))
                 ) {
                     throw new RuntimeException("用户或密码错误");
-                }
-//                else if (loginConfig.clientLoginConfig().getLoginName().equals(user.getLoginName())) {
-//                    throw new RuntimeException("该账户只能在采集端登录");
-//                }
-//                else if (loginConfig.uploadLoginConfig().getLoginName().equals(user.getLoginName())) {
-//                    throw new RuntimeException("该账户只能在图片客户端登录");
-//                }
-                else {
+                } else {
                     throw new RuntimeException("用户不存在");
                 }
             }
@@ -98,7 +82,14 @@ public class AuthApi {
 
         if (Objects.equals(Role.MARKER, domain.getRole())) {
             MarkSubject markSubject = markSubjectRepo.findOne(domain.getWorkId() + "-" + domain.getSubject().name());
-            List<MarkTask> markTasks = markTaskRepo.findByWorkIdAndSubjectAndMarkerIdAndStageLimit(domain.getWorkId(), domain.getSubject().name(), domain.getId(), markSubject.getStage().ordinal());
+            List markTasks = null;
+            if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+                markTasks = markTaskRoughLevelRepo.findByWorkIdAndSubjectAndMarkerIdAndStageLimit(domain.getWorkId(), domain.getSubject().name(), domain.getId(), markSubject.getStage().ordinal());
+            } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+                markTasks = markTaskLevelRepo.findByWorkIdAndSubjectAndMarkerIdAndStageLimit(domain.getWorkId(), domain.getSubject().name(), domain.getId(), markSubject.getStage().ordinal());
+            } else if (MarkStage.SCORE.equals(markSubject.getStage())) {
+                markTasks = markTaskScoreRepo.findByWorkIdAndSubjectAndMarkerIdAndStageLimit(domain.getWorkId(), domain.getSubject().name(), domain.getId(), markSubject.getStage().ordinal());
+            }
             if (CollectionUtils.isEmpty(markTasks)) {
                 throw new RuntimeException("没有评卷任务");
             }

+ 2 - 2
stmms-ms-accesscontrol/src/main/java/cn/com/qmth/stmms/ms/accesscontrol/config/AccessConfig.java

@@ -10,7 +10,7 @@ import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter
 /**
  * Created by zhengmin on 2017/3/2.
  */
-@Configuration
+//@Configuration
 //@Profile(value = "dev")
 public class AccessConfig extends WebMvcConfigurerAdapter {
 
@@ -33,6 +33,6 @@ public class AccessConfig extends WebMvcConfigurerAdapter {
         registry.addInterceptor(loginInterceptor()).addPathPatterns("/api/**").excludePathPatterns("/api/admin/users/login","/api/login","/api/logout","/api/*/password",
                 "/api/user/login", "/api/user/getClientUser", "/api/exam/students", "/api/upload/student/*", "/api/file/image/**", "/api/marklog/saveCollectLog",
                 "/api/file/ms-slice/**", "/api/subject/collect-config", "/api/file/ms-sheet/**", "/api/oss/**", "/api/exam/listStudents/*", "/api/exam/getStudent/*","/api/level/*",
-                "/api/file/image/getExportData","/api/file/image/exportScorePicturesFromCollect","/api/admin/works","/api/score/missing/*");
+                "/api/file/image/getExportData","/api/file/image/exportScorePicturesFromCollect","/api/admin/works","/api/score/missing/*", "/api/papers/*/*/*");
     }
 }

+ 4 - 4
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/InspectRangeApi.java

@@ -4,7 +4,10 @@ import cn.com.qmth.stmms.ms.admin.service.InspectRangeService;
 import cn.com.qmth.stmms.ms.core.domain.InspectRange;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.domain.user.Role;
-import cn.com.qmth.stmms.ms.core.repository.*;
+import cn.com.qmth.stmms.ms.core.repository.InspectRangeRepo;
+import cn.com.qmth.stmms.ms.core.repository.InspectTaskRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
+import cn.com.qmth.stmms.ms.core.repository.PaperRepo;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.web.bind.annotation.*;
@@ -31,9 +34,6 @@ public class InspectRangeApi {
     @Autowired
     private PaperRepo paperRepo;
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
-
     @Autowired
     private InspectTaskRepo inspectTaskRepo;
 

+ 108 - 0
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/MessageApi.java

@@ -0,0 +1,108 @@
+package cn.com.qmth.stmms.ms.admin.api;
+
+import cn.com.qmth.stmms.ms.commons.utils.ServletUtil;
+import cn.com.qmth.stmms.ms.core.domain.MarkStage;
+import cn.com.qmth.stmms.ms.core.domain.Message;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.repository.MessageRepo;
+import cn.com.qmth.stmms.ms.core.vo.Subject;
+import com.alibaba.fastjson.JSONObject;
+import org.springframework.data.domain.Page;
+import org.springframework.data.domain.PageRequest;
+import org.springframework.data.domain.Pageable;
+import org.springframework.data.domain.Sort;
+import org.springframework.data.jpa.domain.Specification;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.persistence.criteria.Predicate;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+
+/**
+ * 消息管理
+ */
+@RestController
+@RequestMapping("api/message")
+public class MessageApi {
+
+    @Resource
+    private MessageRepo messageRepo;
+
+    @PostMapping("/save")
+    public void save(@RequestBody JSONObject data) {
+        Long workId = ServletUtil.getWordId();
+        List<MarkUser> markUsers = JSONObject.parseArray(data.getString("markers"), MarkUser.class);
+        List<Message> messages = new ArrayList<>();
+        long time = System.currentTimeMillis();
+        for (MarkUser markUser : markUsers) {
+            Message message = new Message();
+            message.setWorkId(workId);
+            message.setSubject(Subject.valueOf(data.getString("subject")));
+            message.setMarkerId(markUser.getId());
+            message.setMarkerName(markUser.getName());
+            message.setMarkerLeaderId(data.getLong("markerLeaderId"));
+            message.setMarkerLeaderName(data.getString("markerLeaderName"));
+            message.setContent(data.getString("content"));
+            message.setCreateTime(time);
+            message.setRead(false);
+            messages.add(message);
+        }
+        messageRepo.save(messages);
+    }
+
+    /**
+     * 评卷员查询消息
+     *
+     * @param subject  科目
+     * @param stage    阶段
+     * @param markerId 评卷员ID
+     * @param lastId   上次最后一次查询的消息ID最大值
+     * @param pageable 分页
+     */
+    @GetMapping("/list_by_marker")
+    public Page<Message> listByMarker(@RequestParam Subject subject,
+                                      @RequestParam MarkStage stage,
+                                      @RequestParam Long markerId,
+                                      @RequestParam Long lastId,
+                                      Pageable pageable) {
+        Long workId = ServletUtil.getWordId();
+        Specification<Message> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            if (lastId != null) {
+                predicates.add(builder.gt(root.get("id"), lastId));
+            }
+            predicates.add(builder.equal(root.get("workId"), workId));
+            predicates.add(builder.equal(root.get("subject"), subject));
+            predicates.add(builder.equal(root.get("stage"), stage));
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            predicates.add(builder.equal(root.get("read"), false));
+
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+
+        Sort sort = new Sort(Sort.Direction.DESC, "id");
+        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
+        return messageRepo.findAll(specification, pageable1);
+    }
+
+    @GetMapping("/list_by_marker_leader")
+    public void listByMarkerLeader(@RequestParam Subject subject,
+                                   @RequestParam MarkStage stage,
+                                   @RequestParam Long markerLeaderId) {
+    }
+
+    /**
+     * 标记已读
+     *
+     * @param id 消息ID
+     */
+    @GetMapping("/read/{id}")
+    public void listByMarkerLeader(@PathVariable Long id) {
+        Message message = messageRepo.findOne(id);
+        message.setRead(true);
+        messageRepo.save(message);
+    }
+
+}

+ 31 - 32
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/ParamApi.java

@@ -7,14 +7,11 @@ import cn.com.qmth.stmms.ms.core.domain.Paper;
 import cn.com.qmth.stmms.ms.core.domain.ParamSetting;
 import cn.com.qmth.stmms.ms.core.domain.enums.ParamSettingTypeEnum;
 import cn.com.qmth.stmms.ms.core.domain.enums.TrialEnum;
-import cn.com.qmth.stmms.ms.core.domain.paramsetting.CoarseLevelConfig;
+import cn.com.qmth.stmms.ms.core.domain.paramsetting.RoughLevelConfig;
 import cn.com.qmth.stmms.ms.core.domain.paramsetting.CollectConfig;
 import cn.com.qmth.stmms.ms.core.domain.paramsetting.LevelConfig;
 import cn.com.qmth.stmms.ms.core.domain.paramsetting.ScoreConfig;
-import cn.com.qmth.stmms.ms.core.repository.MarkSubjectRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkTaskRepo;
-import cn.com.qmth.stmms.ms.core.repository.PaperRepo;
-import cn.com.qmth.stmms.ms.core.repository.ParamSettingRepo;
+import cn.com.qmth.stmms.ms.core.repository.*;
 import com.alibaba.fastjson.JSON;
 import com.alibaba.fastjson.JSONObject;
 import org.springframework.http.HttpStatus;
@@ -42,7 +39,7 @@ public class ParamApi {
     private MarkSubjectRepo markSubjectRepo;
 
     @Resource
-    private MarkTaskRepo markTaskRepo;
+    private MarkTaskLevelRepo markTaskLevelRepo;
 
     /**
      * 查询
@@ -73,7 +70,8 @@ public class ParamApi {
         if (paramSetting == null) {
             paramSetting = ParamSetting.init(workId);
         }
-        int countMarkTasks = markTaskRepo.countByWorkId(workId);
+        // todo 需要改查询表,判断粗分档和细分档 20220728
+        int countMarkTasks = markTaskLevelRepo.countByWorkId(workId);
 
         CollectConfig oldCollectConfig = JSON.parseObject(paramSetting.getCollectConfig(), CollectConfig.class);
         if (countMarkTasks > 0 && !Objects.equals(packageScan, oldCollectConfig.getPackageScan())) {
@@ -121,11 +119,12 @@ public class ParamApi {
         Integer levelShowAllPaper = object.getInteger("levelShowAllPaper");
         Integer propDenominator = object.getInteger("propDenominator");
         Integer showStandardPaperManage = object.getInteger("showStandardPaperManage");
-        Integer coarseLevel = object.getInteger("coarseLevel");
+        Integer roughLevel = object.getInteger("roughLevel");
         Integer removeHighAndLow = object.getInteger("removeHighAndLow");
 
         List<MarkSubject> markSubjects = markSubjectRepo.findByWorkIdAndTestNot(workId, TrialEnum.DEFAULT.ordinal());
-        int countMarkTasks = markTaskRepo.countByWorkId(workId);
+        // todo 需要改查询表,判断粗分档和细分档 20220728
+        int countMarkTasks = markTaskLevelRepo.countByWorkId(workId);
         //保存分档参数
         ParamSetting paramSetting = paramSettingRepo.findByWorkId(workId);
         if (paramSetting == null) {
@@ -143,7 +142,7 @@ public class ParamApi {
             if (!Objects.equals(majority, oldLevelConfig.getMajority())) {
                 throw new RuntimeException("该评卷工作已有评卷数据,不能修改【是否过半定档】参数");
             }
-            if (!Objects.equals(coarseLevel, oldLevelConfig.getCoarseLevel())) {
+            if (!Objects.equals(roughLevel, oldLevelConfig.getRoughLevel())) {
                 throw new RuntimeException("该评卷工作已有评卷数据,不能修改【是否增加粗档位环节】参数");
             }
             if (!Objects.equals(removeHighAndLow, oldLevelConfig.getRemoveHighAndLow())) {
@@ -159,7 +158,7 @@ public class ParamApi {
         oldLevelConfig.setPropDenominator(propDenominator);
         oldLevelConfig.setShowStandardPaperManage(showStandardPaperManage);
         oldLevelConfig.setClearData(clearData);
-        oldLevelConfig.setCoarseLevel(coarseLevel);
+        oldLevelConfig.setRoughLevel(roughLevel);
         oldLevelConfig.setRemoveHighAndLow(removeHighAndLow);
 
         paramSetting.setLevelConfig(JSON.toJSONString(oldLevelConfig));
@@ -174,7 +173,7 @@ public class ParamApi {
      *
      * @param data data
      */
-    @PostMapping("/coarse_level")
+    @PostMapping("/rough_level")
     public ResponseEntity updateFirstLevelParam(@RequestBody String data) {
         Long workId = ServletUtil.getWordId();
         JSONObject object = JSON.parseObject(data);
@@ -189,43 +188,43 @@ public class ParamApi {
         Integer removeHighAndLow = object.getInteger("removeHighAndLow");
 
         List<MarkSubject> markSubjects = markSubjectRepo.findByWorkIdAndTestNot(workId, TrialEnum.DEFAULT.ordinal());
-        // todo 需要改查询表 20220728
-        int countMarkTasks = markTaskRepo.countByWorkId(workId);
+        // todo 需要改查询表,判断粗分档和细分档 20220728
+        int countMarkTasks = markTaskLevelRepo.countByWorkId(workId);
         //保存分档参数
         ParamSetting paramSetting = paramSettingRepo.findByWorkId(workId);
         if (paramSetting == null) {
             paramSetting = ParamSetting.init(workId);
         }
 
-        CoarseLevelConfig oldCoarseLevelConfig = JSON.parseObject(paramSetting.getCoarseLevelConfig(), CoarseLevelConfig.class);
+        RoughLevelConfig oldRoughLevelConfig = JSON.parseObject(paramSetting.getRoughLevelConfig(), RoughLevelConfig.class);
         if ((markSubjects == null || markSubjects.isEmpty()) && countMarkTasks > 0) {
-            if (!Objects.equals(deviation, oldCoarseLevelConfig.getDeviation())) {
+            if (!Objects.equals(deviation, oldRoughLevelConfig.getDeviation())) {
                 throw new RuntimeException("该评卷工作已有评卷数据,不能修改【仲裁档位差】参数");
             }
-            if (!Objects.equals(autoCallback, oldCoarseLevelConfig.getAutoCallback())) {
+            if (!Objects.equals(autoCallback, oldRoughLevelConfig.getAutoCallback())) {
                 throw new RuntimeException("该评卷工作已有评卷数据,不能修【系统自动打回】参数");
             }
-            if (!Objects.equals(majority, oldCoarseLevelConfig.getMajority())) {
+            if (!Objects.equals(majority, oldRoughLevelConfig.getMajority())) {
                 throw new RuntimeException("该评卷工作已有评卷数据,不能修改【是否过半定档】参数");
             }
-            if (!Objects.equals(removeHighAndLow, oldCoarseLevelConfig.getRemoveHighAndLow())) {
+            if (!Objects.equals(removeHighAndLow, oldRoughLevelConfig.getRemoveHighAndLow())) {
                 throw new RuntimeException("该评卷工作已有评卷数据,不能修改【是否开启去高去低再加权评卷】参数");
             }
         }
 
-        oldCoarseLevelConfig.setDeviation(deviation);
-        oldCoarseLevelConfig.setAutoCallback(autoCallback);
-        oldCoarseLevelConfig.setMajority(majority);
-        oldCoarseLevelConfig.setTakeBest(takeBest);
-        oldCoarseLevelConfig.setLevelShowAllPaper(levelShowAllPaper);
-        oldCoarseLevelConfig.setPropDenominator(propDenominator);
-        oldCoarseLevelConfig.setShowStandardPaperManage(showStandardPaperManage);
-        oldCoarseLevelConfig.setClearData(clearData);
-        oldCoarseLevelConfig.setRemoveHighAndLow(removeHighAndLow);
-
-        paramSetting.setCoarseLevelConfig(JSON.toJSONString(oldCoarseLevelConfig));
+        oldRoughLevelConfig.setDeviation(deviation);
+        oldRoughLevelConfig.setAutoCallback(autoCallback);
+        oldRoughLevelConfig.setMajority(majority);
+        oldRoughLevelConfig.setTakeBest(takeBest);
+        oldRoughLevelConfig.setLevelShowAllPaper(levelShowAllPaper);
+        oldRoughLevelConfig.setPropDenominator(propDenominator);
+        oldRoughLevelConfig.setShowStandardPaperManage(showStandardPaperManage);
+        oldRoughLevelConfig.setClearData(clearData);
+        oldRoughLevelConfig.setRemoveHighAndLow(removeHighAndLow);
+
+        paramSetting.setRoughLevelConfig(JSON.toJSONString(oldRoughLevelConfig));
         paramSettingRepo.saveAndFlush(paramSetting);
-        ParamCache.cacheParam(ParamSettingTypeEnum.FIRST_LEVEL, workId, paramSetting.getCoarseLevelConfig());
+        ParamCache.cacheParam(ParamSettingTypeEnum.ROUGH_LEVEL, workId, paramSetting.getRoughLevelConfig());
 
         return new ResponseEntity(HttpStatus.OK);
     }
@@ -253,7 +252,7 @@ public class ParamApi {
         ScoreConfig oldScoreConfig = JSON.parseObject(paramSetting.getScoreConfig(), ScoreConfig.class);
         List<MarkSubject> markSubjects = markSubjectRepo.findByWorkIdAndTestNot(workId, TrialEnum.DEFAULT.ordinal());
         // todo 更新查询表 20220801
-        int countMarkTasks = markTaskRepo.countByWorkId(workId);
+        int countMarkTasks = markTaskLevelRepo.countByWorkId(workId);
         if ((markSubjects == null || markSubjects.isEmpty()) && countMarkTasks > 0) {
             if (!Objects.equals(roundUp, oldScoreConfig.getRoundUp())) {
                 throw new RuntimeException("该评卷工作已有评卷数据,不能修改【分数处理方式】参数");

+ 17 - 18
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/QualityAnalyseController.java

@@ -4,10 +4,10 @@ import cn.com.qmth.stmms.ms.commons.utils.SqlUtil;
 import cn.com.qmth.stmms.ms.core.domain.Level;
 import cn.com.qmth.stmms.ms.core.domain.MarkLogOperType;
 import cn.com.qmth.stmms.ms.core.domain.MarkStage;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.repository.LevelRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkTaskRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkTaskLevelRepo;
 import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import cn.com.qmth.stmms.ms.marking.service.MarkerGroupLeaderService;
@@ -45,7 +45,7 @@ public class QualityAnalyseController {
     private SqlUtil sqlUtil;
 
     @Autowired
-    MarkTaskRepo markTaskRepo;
+    MarkTaskLevelRepo markTaskLevelRepo;
 
     @Autowired
     MarkUserRepo markUserRepo;
@@ -165,8 +165,7 @@ public class QualityAnalyseController {
             @RequestParam(required = false) String endTime) {
         List list = new ArrayList();
         List<Long> markerIds = markerGroupLeaderService.listByWorkIdAndSubjectAndStageAndGroupId(workId, subject, MarkStage.LEVEL, groupId);
-        ;
-        Specification<MarkTask> specification = (root, query, builder) -> {
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
             List<Predicate> predicates = new ArrayList<>();
             predicates.add(builder.equal(root.get("workId"), workId));
             if (Objects.nonNull(subject)) {
@@ -184,10 +183,10 @@ public class QualityAnalyseController {
             }
             return builder.and(predicates.toArray(new Predicate[predicates.size()]));
         };
-        List<MarkTask> markTasks = markTaskRepo.findAll(specification);
+        List<MarkTaskLevel> markTasks = markTaskLevelRepo.findAll(specification);
         if (Objects.nonNull(markTasks) && markTasks.size() > 0) {
-            Map<Long, MarkTask> markerMap = markTasks.stream().collect(Collectors.toMap(MarkTask::getMarkerId, Function.identity(), (dto1, dto2) -> dto1));
-            List<Long> markerIdList = markerMap.values().stream().map(MarkTask::getMarkerId).collect(Collectors.toList());
+            Map<Long, MarkTaskLevel> markerMap = markTasks.stream().collect(Collectors.toMap(MarkTaskLevel::getMarkerId, Function.identity(), (dto1, dto2) -> dto1));
+            List<Long> markerIdList = markerMap.values().stream().map(MarkTaskLevel::getMarkerId).collect(Collectors.toList());
             Object o = StringUtils.join(markerIdList.toArray(), ",");
             String sql = new StringBuffer("select mu.login_name as userName, count(t.create_user_id) as sumCount,t.create_user_id as userId from mark_log t left join mark_user mu on t.create_user_id = mu.id where t.oper_type BETWEEN ").append(MarkLogOperType.SYSTEM_CALLBACK_LEVEl.getId()).append(" and ").append(MarkLogOperType.HANDLE_LEVEl.getId()).append(" and t.create_user_id in (").append(o).append(")").toString();
             if (Objects.nonNull(startTime)) {
@@ -223,7 +222,7 @@ public class QualityAnalyseController {
         List list = new ArrayList();
         List<Long> markerIds = markerGroupLeaderService.listByWorkIdAndSubjectAndStageAndGroupId(workId, subject, MarkStage.LEVEL, groupId);
         ;
-        Specification<MarkTask> specification = (root, query, builder) -> {
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
             List<Predicate> predicates = new ArrayList<>();
             predicates.add(builder.equal(root.get("workId"), workId));
             if (Objects.nonNull(subject)) {
@@ -241,10 +240,10 @@ public class QualityAnalyseController {
             }
             return builder.and(predicates.toArray(new Predicate[predicates.size()]));
         };
-        List<MarkTask> markTasks = markTaskRepo.findAll(specification);
-        if (Objects.nonNull(markTasks) && markTasks.size() > 0) {
-            Map<Long, MarkTask> markerMap = markTasks.stream().collect(Collectors.toMap(MarkTask::getMarkerId, Function.identity(), (dto1, dto2) -> dto1));
-            List<Long> markerIdList = markerMap.values().stream().map(i -> i.getMarkerId()).collect(Collectors.toList());
+        List<MarkTaskLevel> markTasks = markTaskLevelRepo.findAll(specification);
+        if (Objects.nonNull(markTasks) && !markTasks.isEmpty()) {
+            Map<Long, MarkTaskLevel> markerMap = markTasks.stream().collect(Collectors.toMap(MarkTaskLevel::getMarkerId, Function.identity(), (dto1, dto2) -> dto1));
+            List<Long> markerIdList = markerMap.values().stream().map(MarkTaskLevel::getMarkerId).collect(Collectors.toList());
             Object o = StringUtils.join(markerIdList.toArray(), ",");
             String sql = new StringBuffer("select mu.login_name as userName, sum(t.oper_data_after) as sumCount,t.create_user_id as userId from mark_log t left join mark_user mu on t.create_user_id = mu.id where t.oper_type = ").append(MarkLogOperType.LEVEl_DIFFERENCE.getId()).append(" and t.create_user_id in (").append(o).append(")").toString();
             if (Objects.nonNull(startTime)) {
@@ -280,7 +279,7 @@ public class QualityAnalyseController {
         List list = new ArrayList();
         List<Long> markerIds = markerGroupLeaderService.listByWorkIdAndSubjectAndStageAndGroupId(workId, subject, MarkStage.LEVEL, groupId);
         ;
-        Specification<MarkTask> specification = (root, query, builder) -> {
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
             List<Predicate> predicates = new ArrayList<>();
             predicates.add(builder.equal(root.get("workId"), workId));
             if (Objects.nonNull(subject)) {
@@ -298,10 +297,10 @@ public class QualityAnalyseController {
             }
             return builder.and(predicates.toArray(new Predicate[predicates.size()]));
         };
-        List<MarkTask> markTasks = markTaskRepo.findAll(specification);
+        List<MarkTaskLevel> markTasks = markTaskLevelRepo.findAll(specification);
         if (Objects.nonNull(markTasks) && markTasks.size() > 0) {
-            Map<Long, MarkTask> markerMap = markTasks.stream().collect(Collectors.toMap(MarkTask::getMarkerId, Function.identity(), (dto1, dto2) -> dto1));
-            List<Long> markerIdList = markerMap.values().stream().map(MarkTask::getMarkerId).collect(Collectors.toList());
+            Map<Long, MarkTaskLevel> markerMap = markTasks.stream().collect(Collectors.toMap(MarkTaskLevel::getMarkerId, Function.identity(), (dto1, dto2) -> dto1));
+            List<Long> markerIdList = markerMap.values().stream().map(MarkTaskLevel::getMarkerId).collect(Collectors.toList());
             Object o = StringUtils.join(markerIdList.toArray(), ",");
             String sql = new StringBuffer("select mu.login_name as userName, sum(t.oper_data_after) as sumCount,t.create_user_id as userId from mark_log t left join mark_user mu on t.create_user_id = mu.id where t.oper_type = ").append(MarkLogOperType.LEVEl_DEVIATION.getId()).append(" and t.create_user_id in (").append(o).append(")").toString();
             if (Objects.nonNull(startTime)) {
@@ -325,7 +324,7 @@ public class QualityAnalyseController {
      * @param markerMap
      * @return
      */
-    public List distinctCommon(List list, List<Long> markerIdList, Map<Long, MarkTask> markerMap) {
+    public List distinctCommon(List list, List<Long> markerIdList, Map<Long, MarkTaskLevel> markerMap) {
         if (Objects.nonNull(list) && list.size() > 0) {
             List<Long> dataIdList = new ArrayList<>();
             for (int i = 0; i < list.size(); i++) {

+ 10 - 10
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/ScoreApi.java

@@ -11,8 +11,10 @@ import cn.com.qmth.stmms.ms.commons.utils.OssUtil;
 import cn.com.qmth.stmms.ms.commons.web.PageableDTO;
 import cn.com.qmth.stmms.ms.core.cache.ParamCache;
 import cn.com.qmth.stmms.ms.core.domain.*;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
-import cn.com.qmth.stmms.ms.core.repository.*;
+import cn.com.qmth.stmms.ms.core.repository.MarkSubjectRepo;
+import cn.com.qmth.stmms.ms.core.repository.PaperRepo;
+import cn.com.qmth.stmms.ms.core.repository.StudentRepo;
+import cn.com.qmth.stmms.ms.core.repository.WorkRepo;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import cn.com.qmth.stmms.ms.marking.assembler.PaperAssembler;
 import cn.com.qmth.stmms.ms.marking.dto.PaperDTO;
@@ -33,8 +35,8 @@ import java.io.File;
 import java.io.FileInputStream;
 import java.io.IOException;
 import java.nio.charset.Charset;
-import java.util.*;
 import java.util.List;
+import java.util.*;
 import java.util.stream.Collectors;
 
 /**
@@ -48,9 +50,6 @@ public class ScoreApi {
     @Autowired
     private PaperRepo paperRepo;
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
-
     @Autowired
     private MarkSubjectRepo markSubjectRepo;
 
@@ -120,7 +119,7 @@ public class ScoreApi {
     @RequestMapping(value = "search/byTaskSecretNumber", method = RequestMethod.GET)
     public ScoreCheckDTO getByTaskSecretNumber(@RequestParam Long workId,
                                                @RequestParam String secretNumber) {
-        List<Paper> papers = new ArrayList<Paper>();
+        /*List<Paper> papers = new ArrayList<Paper>();
         List<MarkTask> markTasks = markTaskRepo.findByWorkIdAndSecretNumber(workId, secretNumber);
         for (MarkTask markTask : markTasks) {
             papers.add(markTask.getPaper());
@@ -130,7 +129,8 @@ public class ScoreApi {
         }
         String examNumber = papers.get(0).getExamNumber();
         Student student = studentRepo.findByWorkIdAndExamNumber(workId, examNumber);
-        return scoreAssembler.toDTO(student, papers);
+        return scoreAssembler.toDTO(student, papers);*/
+        return null;
     }
 
     @RequestMapping(value = "search/byTotalScore", method = RequestMethod.GET)
@@ -222,7 +222,7 @@ public class ScoreApi {
         List<Paper> papers = paperRepo.findByWorkIdAndSubject(activedWork.getId(), subject);
         Iterator<Paper> paperIterator = papers.iterator();
         long count = 0;
-        while (paperIterator.hasNext()) {
+        /*while (paperIterator.hasNext()) {
             Paper paper = paperIterator.next();
             List<MarkTask> markTasks = markTaskRepo.findByPaperIdAndStage(paper.getId(), MarkStage.SCORE);
             long leftCount = markTasks.stream().filter(i -> i.getResult() == null).count();
@@ -237,7 +237,7 @@ public class ScoreApi {
             if (count % 500 == 0) {
                 System.out.println(subject.toString() + ":" + count);
             }
-        }
+        }*/
         return ResponseEntity.ok(null);
     }
 

+ 5 - 8
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/TrialController.java

@@ -2,10 +2,7 @@ package cn.com.qmth.stmms.ms.admin.api;
 
 import cn.com.qmth.stmms.ms.admin.service.TrialService;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
-import org.springframework.web.bind.annotation.RequestMapping;
-import org.springframework.web.bind.annotation.RequestMethod;
-import org.springframework.web.bind.annotation.RequestParam;
-import org.springframework.web.bind.annotation.RestController;
+import org.springframework.web.bind.annotation.*;
 
 import javax.annotation.Resource;
 
@@ -29,7 +26,7 @@ public class TrialController {
      * @param workId  工作ID
      * @param subject 科目
      */
-    @RequestMapping(value = "startTrial", method = RequestMethod.GET)
+    @GetMapping("/startTrial")
     public void startTrial(
             @RequestParam Long workId,
             @RequestParam Subject subject) throws Exception {
@@ -42,10 +39,10 @@ public class TrialController {
      * @param workId  工作ID
      * @param subject 科目
      */
-    @RequestMapping(value = "finishTrial", method = RequestMethod.GET)
+    @GetMapping("/finishTrial")
     public boolean finishTrial(
             @RequestParam Long workId,
-            @RequestParam Subject subject) throws Exception {
+            @RequestParam Subject subject) {
         trialService.finishTrial(workId, subject);
         return true;
     }
@@ -56,7 +53,7 @@ public class TrialController {
      * @param workId  工作ID
      * @param subject 科目
      */
-    @RequestMapping(value = "checkMissionStatus", method = RequestMethod.GET)
+    @GetMapping("/checkMissionStatus")
     public void checkMissionStatus(
             @RequestParam Long workId,
             @RequestParam Subject subject) throws Exception {

+ 4 - 3
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/UserApi.java

@@ -9,7 +9,7 @@ import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.domain.user.Role;
 import cn.com.qmth.stmms.ms.core.repository.MarkLogRepo;
 import cn.com.qmth.stmms.ms.core.repository.MarkSubjectRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkTaskRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkTaskLevelRepo;
 import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import cn.com.qmth.stmms.ms.marking.assembler.MarkerAssembler;
@@ -43,7 +43,7 @@ public class UserApi {
     private MarkSubjectRepo markSubjectRepo;
 
     @Autowired
-    private MarkTaskRepo markTaskRepo;
+    private MarkTaskLevelRepo markTaskLevelRepo;
 
     @Autowired
     private MarkLogRepo markLogRepo;
@@ -56,7 +56,8 @@ public class UserApi {
 
     @RequestMapping(value = "{userId}", method = RequestMethod.DELETE)
     public void remove(@PathVariable Long userId) {
-        long count = markTaskRepo.countByMarkerId(userId);
+        // todo 增加粗分档和细分档的区分  20220802
+        long count = markTaskLevelRepo.countByMarkerId(userId);
         if (count > 0) {
             throw new RuntimeException("已分配任务,不允许删除");
         }

+ 5 - 6
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/api/WorkApi.java

@@ -10,7 +10,7 @@ import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
 import cn.com.qmth.stmms.ms.core.domain.Work;
 import cn.com.qmth.stmms.ms.core.repository.LevelRepo;
 import cn.com.qmth.stmms.ms.core.repository.MarkSubjectRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkTaskRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkTaskLevelRepo;
 import cn.com.qmth.stmms.ms.core.repository.WorkRepo;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.data.domain.Sort;
@@ -49,7 +49,7 @@ public class WorkApi {
     private MarkSubjectRepo markSubjectRepo;
 
     @Autowired
-    private MarkTaskRepo markTaskRepo;
+    private MarkTaskLevelRepo markTaskLevelRepo;
 
     @Autowired
     RandomUtil randomUtil;
@@ -76,7 +76,7 @@ public class WorkApi {
         if (work.isActive()) {
             randomUtil.getRandom(work.getId(), false);
         }
-        int count = markTaskRepo.countByWorkIdAndStageAndResultNotNull(work.getId(), MarkStage.LEVEL);
+        int count = markTaskLevelRepo.countByWorkIdAndStageAndResultNotNull(work.getId(), MarkStage.LEVEL);
         work.setModifyOtherVal(count == 0);
         return work;
     }
@@ -86,7 +86,7 @@ public class WorkApi {
      *
      * @param work work对象
      */
-    @RequestMapping(method = RequestMethod.POST)
+    @PostMapping()
     public void create(@RequestBody Work work) {
         workService.save(work);
         //生成随机数
@@ -199,9 +199,8 @@ public class WorkApi {
      * 总览,各统计数据
      *
      * @param work
-     * @return
      */
-    @RequestMapping(value = "{work}/overview", method = RequestMethod.GET)
+    @GetMapping("{work}/overview")
     public WorkOverview overview(@PathVariable Work work) {
         //生成随机数,已生成的工作,直接跳过
         if (randomUtil.getRandomMap().get(work.getId()) == null) {

+ 4 - 6
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/assembler/WorkOverviewAssembler.java

@@ -4,7 +4,6 @@ import cn.com.qmth.stmms.ms.admin.dto.SubjectOverview;
 import cn.com.qmth.stmms.ms.admin.dto.WorkOverview;
 import cn.com.qmth.stmms.ms.core.domain.Student;
 import cn.com.qmth.stmms.ms.core.domain.Work;
-import cn.com.qmth.stmms.ms.core.domain.enums.TrialEnum;
 import cn.com.qmth.stmms.ms.core.domain.user.Role;
 import cn.com.qmth.stmms.ms.core.repository.ExamQuestionRepo;
 import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
@@ -46,12 +45,11 @@ public class WorkOverviewAssembler {
             workOverview.setQuestionCount(examQuestionRepo.countByWorkId(work.getId()));
 
             List<Student> students = studentRepo.findByWorkId(work.getId());
-            workOverview.setStuTotalCount(students.stream().count());
-            workOverview.setStuAbsentCount(students.stream().filter(s -> s.isAbsent()).count());
+            workOverview.setStuTotalCount(students.size());
+            workOverview.setStuAbsentCount(students.stream().filter(Student::isAbsent).count());
             workOverview.setStuUploadedCount(workOverview.getStuTotalCount() - workOverview.getStuAbsentCount());
 
-            ////// subject overview assemble
-
+            // subject overview assemble
             List<SubjectOverview> subjectOverviews = new ArrayList<>();
             work.getSubjects().forEach(s -> {
                 SubjectOverview so = new SubjectOverview();
@@ -70,7 +68,7 @@ public class WorkOverviewAssembler {
                 String[] uploadStatus = student.getUploadStatus().split(",");
                 for (String s : uploadStatus) {
                     if ("1".equals(s.split(":")[1])) {
-                        if(!subjectMap.containsKey(s.split(":")[0])){
+                        if (!subjectMap.containsKey(s.split(":")[0])) {
                             break;
                         }
                         long c = subjectMap.get(s.split(":")[0]);

+ 15 - 4
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/dto/MarkExpDTO.java

@@ -7,16 +7,19 @@ public class MarkExpDTO {
     @ExcelProperty(name = "工作ID", index = 0, type = 1)
     private Long workId;
 
-    @ExcelProperty(name = "科目", index = 1, type = 1)
+    @ExcelProperty(name = "科目ID", index = 1, type = 1)
+    private String subjectId;
+
+    @ExcelProperty(name = "科目", index = 2, type = 1)
     private String subject;
 
-    @ExcelProperty(name = "科目名称", index = 2, type = 1)
+    @ExcelProperty(name = "科目名称", index = 3, type = 1)
     private String subjectName;
 
-    @ExcelProperty(name = "考号", index = 3, type = 1)
+    @ExcelProperty(name = "考号", index = 4, type = 1)
     private String examNumber;
 
-    @ExcelProperty(name = "姓名", index = 4, type = 1)
+    @ExcelProperty(name = "姓名", index = 5, type = 1)
     private String studentName;
 
     public Long getWorkId() {
@@ -27,6 +30,14 @@ public class MarkExpDTO {
         this.workId = workId;
     }
 
+    public String getSubjectId() {
+        return subjectId;
+    }
+
+    public void setSubjectId(String subjectId) {
+        this.subjectId = subjectId;
+    }
+
     public String getSubject() {
         return subject;
     }

+ 1 - 0
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/exporter/PaperExporter.java

@@ -161,6 +161,7 @@ public class PaperExporter {
             MarkExpDTO markExpDTO = new MarkExpDTO();
             markExpDTO.setWorkId(workId);
             Subject subject = paper.getSubject();
+            markExpDTO.setSubjectId(String.valueOf(subject.ordinal() + 1));
             markExpDTO.setSubject(subject.name());
             String subjectName = subject.getName();
             markExpDTO.setSubjectName(subjectName);

+ 13 - 14
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/importer/StudentImporter.java

@@ -6,21 +6,22 @@ import cn.com.qmth.stmms.ms.commons.utils.excel.ExcelError;
 import cn.com.qmth.stmms.ms.commons.utils.excel.ExportUtils;
 import cn.com.qmth.stmms.ms.core.domain.MarkStage;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
-import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.web.bind.annotation.*;
 import org.springframework.web.multipart.MultipartFile;
 
+import javax.annotation.Resource;
 import javax.servlet.http.HttpServletResponse;
-import java.io.IOException;
 import java.util.ArrayList;
 import java.util.List;
 
-//@Api(tags = "学生导入接口controller")
+/**
+ * 考生相关文件导入Controller
+ */
 @RestController
 @RequestMapping("api/import/students")
 public class StudentImporter {
 
-    @Autowired
+    @Resource
     private DataUploadService dataUploadService;
 
     /**
@@ -44,7 +45,7 @@ public class StudentImporter {
      * @param subject 科目
      * @param file    试评文件
      */
-    @PostMapping("batchAllForTrial")
+    @PostMapping("/batchAllForTrial")
     public List<ExcelError> batchAllForTrial(
             @RequestParam Long workId,
             @RequestParam Subject subject,
@@ -72,10 +73,8 @@ public class StudentImporter {
     /**
      * 导入考生关联信息
      *
-     * @param workId
-     * @param file
-     * @return
-     * @throws IOException
+     * @param workId 工作ID
+     * @param file   关联考生文件
      */
     @PostMapping("/relateStudent")
     public List<ExcelError> relateStudent(@RequestParam Long workId,
@@ -84,12 +83,12 @@ public class StudentImporter {
     }
 
     /**
-     * 导入考生关联信息
+     * 导入分组学生名单
      *
-     * @param subject
-     * @param file
-     * @return
-     * @throws IOException
+     * @param subject 科目
+     * @param stage   阶段
+     * @param groupId 分组
+     * @param file    考生名单文件
      */
     @PostMapping("/import_group_student")
     public List<ExcelError> groupStudent(@RequestParam Subject subject,

+ 67 - 82
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/service/DataUploadService.java

@@ -64,7 +64,7 @@ public class DataUploadService {
     private ImageCompressionConfig compressionConfig;
 
     @Autowired
-    private MarkTaskRepo markTaskRepo;
+    private MarkTaskLevelRepo markTaskLevelRepo;
 
     @Resource
     private LevelRepo levelRepo;
@@ -203,7 +203,11 @@ public class DataUploadService {
                 sheetIn = new FileInputStream(savePath + File.separator + student.getExamNumber() + ".jpg");
                 slicein = new FileInputStream(thumbFileName);
             }
-            Paper exist = paperRepo.findByWorkIdAndSubjectAndExamNumberAndTest(student.getWorkId(), subject, student.getExamNumber(), TrialEnum.DEFAULT.getId());
+
+            List<Paper> allPapers = paperRepo.findByWorkIdAndSubjectAndTest(student.getWorkId(), subject, TrialEnum.DEFAULT.getId());
+            Map<Long, Object> randomMap = allPapers.stream().filter(m -> m.getRandomSeq() != null).collect(Collectors.toMap(Paper::getRandomSeq, Paper::getId));
+
+            Paper exist = allPapers.stream().filter(m -> student.getExamNumber().equals(m.getExamNumber())).collect(Collectors.toList()).get(0);
             String sheetMD5 = DigestUtils.md5Hex(sheetIn);
             String sliceMD5 = DigestUtils.md5Hex(slicein);
             sheetIn.close();
@@ -216,7 +220,7 @@ public class DataUploadService {
                 paperRepo.save(exist);
             } else {
                 ExamQuestion examQuestion = examQuestionRepo.findByWorkIdAndSubjectAndAreaCode(student.getWorkId(), subject, student.getAreaCode());
-                Long random = getRandom(student.getWorkId(), student.getExamNumber());
+                Long random = randomUtil.getRandom(student.getWorkId(), randomMap);
                 Paper paper = new Paper(student.getWorkId(), null, subject, examQuestion, student, false, random);
                 paper.setSheetMD5(sheetMD5);
                 paper.setSliceMD5(sliceMD5);
@@ -316,7 +320,8 @@ public class DataUploadService {
                             List<Paper> papers = paperRepo.findByWorkIdAndExamNumber(workId, student.getExamNumber());
                             if (!papers.isEmpty()) {
                                 for (Paper paper : papers) {
-                                    Long count = markTaskRepo.countByPaperId(paper.getId());
+                                    // todo 增加粗分档和细分档区分 20220802
+                                    Long count = markTaskLevelRepo.countByPaperId(paper.getId());
                                     if (count == 0) {
                                         paperRepo.delete(paper);
                                     }
@@ -373,7 +378,7 @@ public class DataUploadService {
      * @param inputStream 文件输入流
      */
     @Transactional
-    public List<ExcelError> uploadStudentsForTrial(Long workId, Subject subject, InputStream inputStream) throws Exception {
+    public List<ExcelError> uploadStudentsForTrial(Long workId, Subject subject, InputStream inputStream) {
         Work work = workRepo.findOne(workId);
         if (Objects.isNull(work)) {
             throw new RuntimeException("没有此工作区");
@@ -382,8 +387,7 @@ public class DataUploadService {
         if (count == 0) {
             throw new RuntimeException("没有采集数据,不能导入试评数据");
         }
-        List<MarkSubject> markSubjectList = work.getSubjects().stream().filter(o -> o.getId().toUpperCase().contains(subject.toString().toUpperCase())).collect(Collectors.toList());
-        MarkSubject markSubject = markSubjectList.get(0);
+        MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + subject.name());
         if (markSubject.getTest() == TrialEnum.START_TRIAL.getId()) {
             throw new RuntimeException("已经开始试评,请先结束试评再重新导入数据");
         }
@@ -404,7 +408,16 @@ public class DataUploadService {
             throw new RuntimeException("没有设定科组长");
         }
 
-        List<MarkerGroup> markerGroups = markerGroupRepo.findByWorkIdAndSubjectAndStage(workId, subject, markSubject.getStage());
+        MarkStage stage = markSubject.getStage();
+        if(MarkStage.INIT.equals(markSubject.getStage())){
+            if(ParamCache.levelConfigMap.get(String.valueOf(workId)).getRoughLevel() == 1){
+                stage = MarkStage.ROUGH_LEVEL;
+            } else {
+                stage = MarkStage.LEVEL;
+            }
+        }
+
+        List<MarkerGroup> markerGroups = markerGroupRepo.findByWorkIdAndSubjectAndStage(workId, subject, stage);
         if (markerGroups == null || markerGroups.isEmpty()) {
             throw new RuntimeException("评卷员没有进行分组");
         }
@@ -412,7 +425,7 @@ public class DataUploadService {
         //更新科目
         markSubject.setTest(TrialEnum.INIT.getId());
         markSubjectRepo.save(markSubject);
-        // 更新试卷试评状态
+        // 更新试卷试评状态(把导入考生数据状态更新为默认状态,等待重新导入数据)
         paperRepo.updateTestByWorkId(workId, TrialEnum.INIT.getId(), TrialEnum.DEFAULT.getId());
 
         List<Student> students = studentRepo.findByWorkId(workId);
@@ -422,9 +435,7 @@ public class DataUploadService {
         Map<String, Paper> paperMap = papers.stream().collect(Collectors.toMap(m -> m.getExamNumber() + "#" + m.getSubject() + "#" + m.getAreaCode(), Function.identity()));
 
         ExcelReader excelReader = new ExcelReader(StudentDTO.class);
-
         List<Paper> paperList = new ArrayList<>();
-
         List<ExcelError> excelErrors = excelReader.reader(inputStream, obj -> {
             try {
                 StudentDTO dto = (StudentDTO) obj;
@@ -441,8 +452,6 @@ public class DataUploadService {
                     return null;
                 }
 
-                //复制paper
-//                Paper paper = paperRepo.findByWorkIdAndSubjectAndExamNumberAndAreaCodeAndTest(workId, subject, student.getExamNumber(), dto.getAreaCode(), TrialEnum.DEFAULT.getId());
                 Paper paper = paperMap.get(student.getExamNumber() + "#" + subject + "#" + dto.getAreaCode());
                 if (Objects.isNull(paper) || paper.getIsMissing()) {
                     return null;
@@ -455,22 +464,6 @@ public class DataUploadService {
             }
             return null;
         });
-        /*if (!CollectionUtils.isEmpty(studentList)) {
-            List<Student> data = new ArrayList<>();
-            //500条提交一次
-            for (Student student : studentList) {
-                student.setTest(String.valueOf(TrialEnum.INIT.getId()));
-                if (data.size() == 1000) {
-                    studentRepo.save(data);
-                    data.clear();
-                }
-                data.add(student);
-            }
-            //将剩下的数据也导入
-            if (!data.isEmpty()) {
-                studentRepo.save(data);
-            }
-        }*/
         if (!CollectionUtils.isEmpty(paperList)) {
             List<Paper> data = new ArrayList<>();
             //500条提交一次
@@ -487,12 +480,12 @@ public class DataUploadService {
                 paperRepo.save(data);
             }
         }
-        if (Objects.nonNull(excelErrors) && excelErrors.size() > 0) {
+        if (excelErrors != null && !excelErrors.isEmpty()) {
             TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
         }
         String errors = errorsString(excelErrors);
         if (errors.length() > 0) {
-            throw new Exception(errors);
+            throw new RuntimeException(errors);
         }
         return excelErrors;
     }
@@ -515,9 +508,13 @@ public class DataUploadService {
     @Transactional
     public Paper savePaper(Student student, Subject subject, boolean isManual, String level, Long scanUserId) throws Exception {
         ExamQuestion examQuestion = examQuestionRepo.findByWorkIdAndSubjectAndAreaCode(student.getWorkId(), subject, student.getAreaCode());
-        Paper paper = paperRepo.findByWorkIdAndSubjectAndExamNumberAndTest(student.getWorkId(), subject, student.getExamNumber(), TrialEnum.DEFAULT.getId());
+
+        List<Paper> allPapers = paperRepo.findByWorkIdAndSubjectAndTest(student.getWorkId(), subject, TrialEnum.DEFAULT.getId());
+        Map<Long, Object> randomMap = allPapers.stream().filter(m -> m.getRandomSeq() != null).collect(Collectors.toMap(Paper::getRandomSeq, Paper::getId));
+        List<Paper> filterList = allPapers.stream().filter(m -> student.getExamNumber().equals(m.getExamNumber())).collect(Collectors.toList());
+        Paper paper = filterList.isEmpty() ? null : filterList.get(0);
         if (paper == null) {
-            Long random = getRandom(student.getWorkId(), student.getExamNumber());
+            Long random = randomUtil.getRandom(student.getWorkId(), randomMap);
             paper = new Paper(student.getWorkId(), null, subject, examQuestion, student, isManual, random);
         }
         paper.setUploadedOn(new Date());
@@ -632,39 +629,6 @@ public class DataUploadService {
         return excelErrors;
     }
 
-    /**
-     * 获取随机号
-     *
-     * @param workId
-     * @param examNumber
-     * @return
-     * @throws Exception
-     */
-    public Long getRandom(Long workId, String examNumber) throws Exception {
-        int count = 0, result = 0;
-        Long random = 0L;
-        while (true) {
-            random = randomUtil.getRandomMap().get(workId).get(new Random().nextInt(randomUtil.getRandomMap().get(workId).size()));
-            result = paperRepo.countByWorkIdAndExamNumberAndRandomSeq(workId, examNumber, random);
-            String examNumberSub;
-            if (examNumber.length() > 3) {
-                examNumberSub = examNumber.substring(3);
-            } else {
-                examNumberSub = examNumber;
-            }
-            if (result == 0 && !random.toString().equals(examNumberSub)) {
-                break;
-            } else {
-                count++;
-            }
-            if (count > 1000) {
-                randomUtil.getRandom(workId, true);
-                getRandom(workId, examNumber);
-            }
-        }
-        return random;
-    }
-
     /**
      * 校验学生导入所有属性
      *
@@ -691,42 +655,58 @@ public class DataUploadService {
     @Transactional
     public List<ExcelError> uploadGroupStudent(Subject subject, MarkStage stage, Long groupId, InputStream inputStream) throws Exception {
         Long workId = ServletUtil.getWordId();
+
+        MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + subject.name());
         //只能第一次分档才能导入
-        Integer coarseLevel = ParamCache.levelConfigMap.get(String.valueOf(workId)).getCoarseLevel();
-        if ((coarseLevel == 1 && !stage.equals(MarkStage.COARSE_LEVEL))
-                || (coarseLevel == 0 && !stage.equals(MarkStage.LEVEL))) {
+        Integer roughLevel = ParamCache.levelConfigMap.get(String.valueOf(workId)).getRoughLevel();
+        // todo 增加校验
+        /*if ((roughLevel == 1 && !stage.equals(MarkStage.INIT))
+                || (roughLevel == 0 && !stage.equals(MarkStage.LEVEL))) {
             throw new RuntimeException("当前阶段不能导入考生数据");
-        }
+        }*/
 
+        MarkerGroup markerGroup = markerGroupRepo.findOne(groupId);
         // 删除
         markerGroupStudentRepo.deleteByGroupIdAndUsed(groupId, false);
 
         // 查询考生
         List<Student> studentList = studentRepo.findByWorkId(workId);
         if (studentList == null || studentList.isEmpty()) {
-            throw new RuntimeException("没有考生信息");
+            throw new RuntimeException("没有考生信息,请先导入");
         }
         Map<String, Student> studentMap = studentList.stream().collect(Collectors.toMap(Student::getExamNumber, Function.identity()));
 
+        // 查询所有试卷
+        List<Paper> allPapers = paperRepo.findByWorkIdAndSubjectAndIsMissingAndTest(workId, subject, false, markSubject.getTest());
+        if (allPapers == null || allPapers.isEmpty()) {
+            throw new RuntimeException("没有可用试卷,请先采集");
+        }
+        Map<String, Paper> allPapersMap = allPapers.stream().collect(Collectors.toMap(Paper::getExamNumber, Function.identity()));
+
         // 查询已发布任务的所有试卷
-        List<Paper> paperList = paperRepo.findByWorkIdAndSubjectAndIsMissingFalseAndActiveTrue(workId, subject, null);
-        Map<String, Paper> paperMap = null;
-        if (paperList != null && !paperList.isEmpty()) {
-            paperMap = paperList.stream().collect(Collectors.toMap(Paper::getExamNumber, Function.identity()));
+        List<Paper> activePaperList = null;
+        if (MarkStage.ROUGH_LEVEL.equals(markerGroup.getStage())) {
+            activePaperList = allPapers.stream().filter(m -> m.getRoughBatchNo() != null).collect(Collectors.toList());
+        } else if (MarkStage.LEVEL.equals(markerGroup.getStage())) {
+            activePaperList = allPapers.stream().filter(m -> m.getBatchNo() != null).collect(Collectors.toList());
+        }
+        Map<String, Paper> activePaperMap = null;
+        if (activePaperList != null && !activePaperList.isEmpty()) {
+            activePaperMap = activePaperList.stream().collect(Collectors.toMap(Paper::getExamNumber, Function.identity()));
         }
-        final Map<String, Paper> finalPaperMap = paperMap;
+        final Map<String, Paper> finalActivePaperMap = activePaperMap;
         // 查询【工作+科目+阶段】下所有数据
-        List<MarkerGroupStudent> markerGroupStudents = markerGroupStudentRepo.findByWorkIdAndSubjectAndStageAndUsed(workId, subject, stage, false);
+        List<MarkerGroupStudent> markerGroupStudents = markerGroupStudentRepo.findByWorkIdAndSubjectAndStageAndUsed(workId, subject, markerGroup.getStage(), false);
         Map<String, MarkerGroupStudent> markerGroupStudentMap = null;
         if (markerGroupStudents != null && !markerGroupStudents.isEmpty()) {
-            // 别的人组
+            // 查询其它分组导入数据
             markerGroupStudentMap = markerGroupStudents.stream().filter(m -> !m.getGroupId().equals(groupId)).collect(Collectors.toMap(MarkerGroupStudent::getExamNumber, Function.identity()));
         }
         final Map<String, MarkerGroupStudent> finalMarkerGroupStudentMap = markerGroupStudentMap;
 
         List<MarkerGroupStudent> markerGroupStudentList = new ArrayList<>();
         long batchNo = System.currentTimeMillis();
-        ExcelReader excelReader = new ExcelReader(MarkerGroupStudent.class);
+        ExcelReader excelReader = new ExcelReader(StudentDTO.class);
         List<ExcelError> excelErrors = excelReader.reader(inputStream, obj -> {
             try {
                 StudentDTO dto = (StudentDTO) obj;
@@ -739,7 +719,12 @@ public class DataUploadService {
                     throw new RuntimeException(String.format("考生管理中未查到[%s]考生", examNumber));
                 }
 
-                if (finalPaperMap != null && finalPaperMap.get(examNumber) != null) {
+                Paper paper = allPapersMap.get(examNumber);
+                if (paper == null) {
+                    throw new RuntimeException(String.format("考生[%s]试卷未采集或已被标记缺考", examNumber));
+                }
+
+                if (finalActivePaperMap != null && finalActivePaperMap.get(examNumber) != null) {
                     throw new RuntimeException(String.format("考生[%s]已经发布任务,不能重复导入", examNumber));
                 }
 
@@ -747,7 +732,7 @@ public class DataUploadService {
                     throw new RuntimeException(String.format("考生[%s]已经导入其它分组,不能重复导入", examNumber));
                 }
 
-                MarkerGroupStudent markerGroupStudent = new MarkerGroupStudent(workId, stage, subject, groupId, dto.getExamNumber(), dto.getName(), dto.getAreaCode(), dto.getAreaName(), dto.getExamRoom(), dto.getSchool(), dto.getSourceName(), batchNo);
+                MarkerGroupStudent markerGroupStudent = new MarkerGroupStudent(workId, markerGroup.getStage(), subject, groupId, paper.getId(), paper.getQuestionId(), dto.getExamNumber(), dto.getName(), dto.getAreaCode(), dto.getAreaName(), dto.getExamRoom(), dto.getSchool(), dto.getSourceName(), batchNo);
                 markerGroupStudentList.add(markerGroupStudent);
                 return null;
             } catch (RuntimeException e) {
@@ -788,7 +773,7 @@ public class DataUploadService {
      */
     private String errorsString(List<ExcelError> excelErrors) {
         StringJoiner sj = new StringJoiner(";");
-        if (!excelErrors.isEmpty() && excelErrors.size() > 0) {
+        if (excelErrors != null && !excelErrors.isEmpty()) {
             int forint = excelErrors.size() < 10 ? excelErrors.size() : 9;
             for (int i = 0; i < forint; i++) {
                 ExcelError excelError = excelErrors.get(i);

+ 58 - 41
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/service/TrialService.java

@@ -2,6 +2,7 @@ package cn.com.qmth.stmms.ms.admin.service;
 
 import cn.com.qmth.stmms.ms.commons.utils.DbBackupUtils;
 import cn.com.qmth.stmms.ms.core.cache.CacheService;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
 import cn.com.qmth.stmms.ms.core.domain.MarkStage;
 import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
 import cn.com.qmth.stmms.ms.core.domain.Paper;
@@ -18,6 +19,7 @@ import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 import org.springframework.util.CollectionUtils;
 
+import javax.annotation.Resource;
 import java.util.*;
 import java.util.stream.Collectors;
 
@@ -40,8 +42,11 @@ public class TrialService {
     @Autowired
     StudentRepo studentRepo;
 
-    @Autowired
-    MarkTaskRepo markTaskRepo;
+    @Resource
+    MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
 
     @Autowired
     PaperRepo paperRepo;
@@ -76,44 +81,37 @@ public class TrialService {
     /**
      * 检查任务状态
      *
-     * @param workId
-     * @param subject
-     * @throws Exception
+     * @param workId  工作ID
+     * @param subject 科目
      */
     @Transactional
-    public void checkMissionStatus(Long workId, Subject subject) throws Exception {
+    public void checkMissionStatus(Long workId, Subject subject) {
         Work work = workRepo.findOne(workId);
         if (Objects.isNull(work)) {
-            throw new Exception("没有此工作区,请检查workId是否正确");
+            throw new RuntimeException("没有此工作区");
         }
-        List<MarkSubject> markSubjectList = work.getSubjects().stream().filter(o -> o.getId().toUpperCase().contains(subject.toString().toUpperCase()))
-                .collect(Collectors.toList());
-        MarkSubject markSubject = markSubjectList.get(0);
+        MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + subject.name());
         if (markSubject.getTest() == TrialEnum.INIT.getId() || markSubject.getTest() == TrialEnum.START_TRIAL.getId()) {
             finishTrial(workId, subject);
         }
-        //修改科目test
-        markSubject.setTest(TrialEnum.DEFAULT.getId());
-        markSubjectRepo.save(markSubject);
     }
 
     /**
      * 开始试评任务
      *
-     * @param workId
-     * @param subject
-     * @throws Exception
+     * @param workId  工作Id
+     * @param subject 科目
      */
     @Transactional
     public void startTrial(Long workId, Subject subject) throws Exception {
         Work work = workRepo.findOne(workId);
         if (Objects.isNull(work)) {
-            throw new Exception("没有此工作区");
+            throw new RuntimeException("没有此工作区");
         }
         List<MarkSubject> markSubjectList = work.getSubjects().stream().filter(o -> o.getId().toUpperCase().contains(subject.toString().toUpperCase())).collect(Collectors.toList());
         MarkSubject markSubject = markSubjectList.get(0);
         //分配任务
-        Map map = new HashMap();
+        Map<String, Integer> map = new HashMap();
         map.put("taskCount", 0);
         stageControlService.goNext(markSubject, map);
         //修改科目test
@@ -131,35 +129,47 @@ public class TrialService {
      * @param subject 科目
      */
     @Transactional
-    public void finishTrial(Long workId, Subject subject) throws Exception {
+    public void finishTrial(Long workId, Subject subject) {
         Work work = workRepo.findOne(workId);
         if (Objects.isNull(work)) {
-            throw new Exception("没有此工作区");
+            throw new RuntimeException("没有此工作区");
+        }
+        //更新科目为初始状态并设置test为false
+        MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + subject.name());
+        markSubject.setTest(TrialEnum.DEFAULT.getId());
+        // 开启粗分档且当前在粗分档试评,则重置为INIT
+        // 开启粗分档且当前在细分档试评,则重置为ROUGH_LEVEL
+        // 未开启粗分档(当前只能在细分档试评),则重置为INIT
+        boolean roughLevel = ParamCache.levelConfigMap.get(String.valueOf(workId)).getRoughLevel() == 1;
+        MarkStage stage = roughLevel && MarkStage.LEVEL.equals(markSubject.getStage()) ? MarkStage.ROUGH_LEVEL : MarkStage.INIT;
+        markSubject.setStage(stage);
+        markSubject.setSampleCount(0);
+        markSubjectRepo.save(markSubject);
+        //删除该科目下所有任务数据
+        if (roughLevel && MarkStage.INIT.equals(markSubject.getStage())) {
+            markTaskRoughLevelRepo.deleteByWorkIdAndSubject(workId, subject);
+        } else {
+            markTaskLevelRepo.deleteByWorkIdAndSubject(workId, subject);
         }
-        //1.更新科目为初始状态并设置test为false
-        work.getSubjects().stream().filter(o -> o.getId().toUpperCase().contains(subject.toString().toUpperCase()))
-                .collect(Collectors.toList())
-                .forEach(o -> {
-                    o.setTest(TrialEnum.DEFAULT.getId());
-                    o.setStage(MarkStage.INIT);
-                    o.setSampleCount(0);
-                    markSubjectRepo.save(o);
-                });
-        //2.删除该科目下所有任务数据
-        markTaskRepo.deleteByWorkIdAndSubject(workId, subject);
-
-        //3.更新该科目下的试卷信息(正式卷子,并删除试评卷子)
+
+
+        //更新该科目下的试卷信息(正式卷子,并删除试评卷子)
         List<Paper> paperList = paperRepo.findByWorkIdAndSubjectAndTest(workId, subject, TrialEnum.START_TRIAL.getId());
 
         for (Paper paper : paperList) {
             // 标准卷不清除档位
             paper.setActive(false);
             paper.setBatchNo(null);
-            paper.setLevel(paper.isSample() ? paper.getLevel() : null);
+            // 区分粗分档和细分档
+            if (roughLevel && MarkStage.INIT.equals(markSubject.getStage())) {
+                paper.setRoughLevel(paper.isRoughSample() ? paper.getRoughLevel() : null);
+            } else {
+                paper.setLevel(paper.isSample() ? paper.getLevel() : null);
+            }
             paper.setTest(TrialEnum.DEFAULT.getId());
         }
 
-        //5.更新试评状态
+        //更新试评状态
         if (!CollectionUtils.isEmpty(paperList)) {
             List<Paper> data = new ArrayList<>();
             //1000条提交一次
@@ -176,12 +186,19 @@ public class TrialService {
             }
         }
 
-        //5.删除分组
-        markerGroupRepo.deleteBySubjectAndWorkId(subject, workId);
-        // 6删除分组内成员
-        markerGroupLeaderRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, MarkStage.LEVEL);
+        // 删除分组,删除分组内成员
+        String backupPrefix = "";
+        if (roughLevel && MarkStage.INIT.equals(markSubject.getStage())) {
+            backupPrefix = "粗分档";
+            markerGroupRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, MarkStage.ROUGH_LEVEL);
+            markerGroupLeaderRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, MarkStage.ROUGH_LEVEL);
+        } else {
+            backupPrefix = "细分档";
+            markerGroupRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, MarkStage.LEVEL);
+            markerGroupLeaderRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, MarkStage.LEVEL);
+        }
 
-        // 7所有用户强制退出
+        // 所有用户强制退出
         List<MarkUser> userList = markUserRepo.findByWorkIdAndSubject(workId, subject);
         userList = userList.stream().filter(m -> Role.MARKER.equals(m.getRole()) || Role.MARK_LEADER.equals(m.getRole())).collect(Collectors.toList());
         if (!CollectionUtils.isEmpty(userList)) {
@@ -189,6 +206,6 @@ public class TrialService {
                 cacheService.deleteTokenCache(user.getId().toString());
             }
         }
-        dbBackupUtils.startBackup(workId, "试评");
+        dbBackupUtils.startBackup(workId, backupPrefix + "试评");
     }
 }

+ 1 - 1
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/service/WorkService.java

@@ -93,7 +93,7 @@ public class WorkService {
         paramSettingRepo.save(paramSetting);
 
         ParamCache.cacheParam(ParamSettingTypeEnum.COLLECT, work.getId(), paramSetting.getCollectConfig());
-        ParamCache.cacheParam(ParamSettingTypeEnum.FIRST_LEVEL, work.getId(), paramSetting.getCoarseLevelConfig());
+        ParamCache.cacheParam(ParamSettingTypeEnum.ROUGH_LEVEL, work.getId(), paramSetting.getRoughLevelConfig());
         ParamCache.cacheParam(ParamSettingTypeEnum.LEVEL, work.getId(), paramSetting.getLevelConfig());
         ParamCache.cacheParam(ParamSettingTypeEnum.SCORE, work.getId(), paramSetting.getScoreConfig());
 

+ 11 - 11
stmms-ms-admin/src/main/java/cn/com/qmth/stmms/ms/admin/utils/BuiltInParamUtils.java

@@ -32,17 +32,17 @@ public class BuiltInParamUtils {
      */
     public void createLevels(Long workId) {
         //默认增加档位
-        Level aLevel = new Level(workId, "A", 0, 100, 90, Level.LevelType.ADMITED, 95, "", 93);
-        Level bLevel = new Level(workId, "B", 1, 89, 85, Level.LevelType.ADMITED, 87, "", 93);
-        Level cLevel = new Level(workId, "C", 2, 84, 80, Level.LevelType.ADMITED, 82, "", 80);
-        Level dLevel = new Level(workId, "D", 3, 79, 75, Level.LevelType.ADMITED, 77, "", 80);
-        Level eLevel = new Level(workId, "E", 4, 74, 70, Level.LevelType.ADMITED, 72, "", 68);
-        Level fLevel = new Level(workId, "F", 5, 69, 65, Level.LevelType.ADMITED, 67, "", 68);
-        Level gLevel = new Level(workId, "G", 6, 64, 60, Level.LevelType.ADMITED, 62, "", 68);
-        Level hLevel = new Level(workId, "H", 7, 59, 55, Level.LevelType.ADMITED, 57, "", 55);
-        Level iLevel = new Level(workId, "I", 8, 54, 50, Level.LevelType.ADMITED, 52, "", 55);
-        Level jLevel = new Level(workId, "J", 9, 49, 45, Level.LevelType.ADMITED, 47, "", 35);
-        Level kLevel = new Level(workId, "K", 10, 44, 0, Level.LevelType.ADMITED, 40, "", 35);
+        Level aLevel = new Level(workId, "A", 0, 100, 90, Level.LevelType.ADMITED, 95, "1", 93);
+        Level bLevel = new Level(workId, "B", 1, 89, 85, Level.LevelType.ADMITED, 87, "1", 93);
+        Level cLevel = new Level(workId, "C", 2, 84, 80, Level.LevelType.ADMITED, 82, "2", 80);
+        Level dLevel = new Level(workId, "D", 3, 79, 75, Level.LevelType.ADMITED, 77, "2", 80);
+        Level eLevel = new Level(workId, "E", 4, 74, 70, Level.LevelType.ADMITED, 72, "3", 68);
+        Level fLevel = new Level(workId, "F", 5, 69, 65, Level.LevelType.ADMITED, 67, "3", 68);
+        Level gLevel = new Level(workId, "G", 6, 64, 60, Level.LevelType.ADMITED, 62, "3", 68);
+        Level hLevel = new Level(workId, "H", 7, 59, 55, Level.LevelType.ADMITED, 57, "4", 55);
+        Level iLevel = new Level(workId, "I", 8, 54, 50, Level.LevelType.ADMITED, 52, "4", 55);
+        Level jLevel = new Level(workId, "J", 9, 49, 45, Level.LevelType.ADMITED, 47, "5", 35);
+        Level kLevel = new Level(workId, "K", 10, 44, 0, Level.LevelType.ADMITED, 40, "5", 35);
         List<Level> levels = Arrays.asList(aLevel, bLevel, cLevel, dLevel, eLevel, fLevel, gLevel, hLevel, iLevel, jLevel, kLevel);
         levelRepo.save(levels);
     }

+ 1 - 1
stmms-ms-commons/src/main/java/cn/com/qmth/stmms/ms/commons/lock/LockType.java

@@ -1,7 +1,7 @@
 package cn.com.qmth.stmms.ms.commons.lock;
 
 public enum LockType {
-    LEVEL("level"), SCORE("score");
+    ROUGH_LEVEL("roughLevel"),LEVEL("level"), SCORE("score");
 
     private String name;
 

+ 29 - 0
stmms-ms-commons/src/main/java/cn/com/qmth/stmms/ms/commons/utils/RandomUtil.java

@@ -74,6 +74,35 @@ public class RandomUtil {
         }
     }
 
+    /**
+     * 获取随机号
+     *
+     * @param workId 工作ID
+     * @param usedRandomMap 使用过的密号集合
+     */
+    public Long getRandom(Long workId, Map<Long, Object> usedRandomMap) throws Exception {
+        int count = 0;
+        Long random;
+        List<Long> randomList = randomMap.get(workId);
+        while (true) {
+            random = randomList.get(new Random().nextInt(randomMap.get(workId).size()));
+            if (Objects.isNull(usedRandomMap) || usedRandomMap.size() == 0) {
+                break;
+            }
+            if (!usedRandomMap.containsKey(random)) {
+                break;
+            }
+            count++;
+            if (count > 1000) {
+                getRandom(workId, true);
+                getRandom(workId, usedRandomMap);
+            }
+        }
+        // 用过的,直接移除
+        randomList.remove(random);
+        return random;
+    }
+
     public Map<Long, List<Long>> getRandomMap() {
         return randomMap;
     }

+ 8 - 8
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/cache/ParamCache.java

@@ -3,7 +3,7 @@ package cn.com.qmth.stmms.ms.core.cache;
 import cn.com.qmth.stmms.ms.core.domain.ParamSetting;
 import cn.com.qmth.stmms.ms.core.domain.enums.ParamSettingTypeEnum;
 import cn.com.qmth.stmms.ms.core.domain.paramsetting.CollectConfig;
-import cn.com.qmth.stmms.ms.core.domain.paramsetting.CoarseLevelConfig;
+import cn.com.qmth.stmms.ms.core.domain.paramsetting.RoughLevelConfig;
 import cn.com.qmth.stmms.ms.core.domain.paramsetting.LevelConfig;
 import cn.com.qmth.stmms.ms.core.domain.paramsetting.ScoreConfig;
 import cn.com.qmth.stmms.ms.core.repository.ParamSettingRepo;
@@ -24,7 +24,7 @@ public class ParamCache {
     private static final Logger LOGGER = LoggerFactory.getLogger(ParamCache.class);
 
     public static Map<String, CollectConfig> collectConfigMap = new HashMap<>();
-    public static Map<String, CoarseLevelConfig> firstLevelConfigMap = new HashMap<>();
+    public static Map<String, RoughLevelConfig> roughLevelConfigMap = new HashMap<>();
     public static Map<String, LevelConfig> levelConfigMap = new HashMap<>();
     public static Map<String, ScoreConfig> scoreConfigMap = new HashMap<>();
 
@@ -39,14 +39,14 @@ public class ParamCache {
             // 采集
             cacheParam(ParamSettingTypeEnum.COLLECT, param.getWorkId(), param.getCollectConfig());
             // 粗分档
-            cacheParam(ParamSettingTypeEnum.FIRST_LEVEL, param.getWorkId(), param.getCoarseLevelConfig());
+            cacheParam(ParamSettingTypeEnum.ROUGH_LEVEL, param.getWorkId(), param.getRoughLevelConfig());
             // 细分档
             cacheParam(ParamSettingTypeEnum.LEVEL, param.getWorkId(), param.getLevelConfig());
             // 打分
             cacheParam(ParamSettingTypeEnum.SCORE, param.getWorkId(), param.getScoreConfig());
         }
         LOGGER.info("加载采集参数成功:{}", JSON.toJSONString(collectConfigMap));
-        LOGGER.info("加载粗分档参数成功:{}", JSON.toJSONString(firstLevelConfigMap));
+        LOGGER.info("加载粗分档参数成功:{}", JSON.toJSONString(roughLevelConfigMap));
         LOGGER.info("加载细分档参数成功:{}", JSON.toJSONString(levelConfigMap));
         LOGGER.info("加载打分参数成功:{}", JSON.toJSONString(scoreConfigMap));
     }
@@ -55,7 +55,7 @@ public class ParamCache {
     public void destroy() {
         //系统运行结束
         collectConfigMap.clear();
-        firstLevelConfigMap.clear();
+        roughLevelConfigMap.clear();
         levelConfigMap.clear();
         scoreConfigMap.clear();
     }
@@ -74,9 +74,9 @@ public class ParamCache {
             collectConfigMap.put(String.valueOf(workId), collectConfig);
         }
         // 粗分档
-        if (ParamSettingTypeEnum.FIRST_LEVEL.equals(typeEnum)) {
-            CoarseLevelConfig firstLevelConfig = JSON.parseObject(value, CoarseLevelConfig.class);
-            firstLevelConfigMap.put(String.valueOf(workId), firstLevelConfig);
+        if (ParamSettingTypeEnum.ROUGH_LEVEL.equals(typeEnum)) {
+            RoughLevelConfig roughLevelConfig = JSON.parseObject(value, RoughLevelConfig.class);
+            roughLevelConfigMap.put(String.valueOf(workId), roughLevelConfig);
         }
         // 细分档
         if (ParamSettingTypeEnum.LEVEL.equals(typeEnum)) {

+ 48 - 48
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/Level.java

@@ -16,41 +16,6 @@ public class Level implements Serializable {
 
     private static final long serialVersionUID = -5290818783456310642L;
 
-    public int getLevelValue() {
-        return levelValue;
-    }
-
-    public void setLevelValue(int levelValue) {
-        this.levelValue = levelValue;
-    }
-
-    public Long getWorkId() {
-        return workId;
-    }
-
-    public void setWorkId(Long workId) {
-        this.workId = workId;
-    }
-
-    public Long getId() {
-        return id;
-    }
-
-    public void setId(Long id) {
-        this.id = id;
-    }
-
-    public static enum LevelType {
-        /**
-         * 非录取
-         */
-        UNADMIT,
-        /**
-         * 录取
-         */
-        ADMITED
-    }
-
     @Id
     @GeneratedValue
     private Long id;
@@ -97,18 +62,18 @@ public class Level implements Serializable {
      * 粗分档档位
      */
     @NotNull
-    private String coarseCode;
+    private String roughCode;
 
     /**
      * 粗分档典型值
      */
     @NotNull
-    private Integer coarseWeight;
+    private Integer roughWeight;
 
     public Level() {
     }
 
-    public Level(Long workId, String code, int levelValue, int maxScore, int minScore, LevelType levelType, Integer weight, String coarseCode, Integer coarseWeight) {
+    public Level(Long workId, String code, int levelValue, int maxScore, int minScore, LevelType levelType, Integer weight, String roughCode, Integer roughWeight) {
         this.workId = workId;
         this.code = code;
         this.levelValue = levelValue;
@@ -116,12 +81,36 @@ public class Level implements Serializable {
         this.minScore = minScore;
         this.levelType = levelType;
         this.weight = weight;
-        this.coarseCode = coarseCode;
-        this.coarseWeight = coarseWeight;
+        this.roughCode = roughCode;
+        this.roughWeight = roughWeight;
         this.pt = 100;
         this.kdpt = 100;
     }
 
+    public int getLevelValue() {
+        return levelValue;
+    }
+
+    public void setLevelValue(int levelValue) {
+        this.levelValue = levelValue;
+    }
+
+    public Long getWorkId() {
+        return workId;
+    }
+
+    public void setWorkId(Long workId) {
+        this.workId = workId;
+    }
+
+    public Long getId() {
+        return id;
+    }
+
+    public void setId(Long id) {
+        this.id = id;
+    }
+
     public String getCode() {
         return code;
     }
@@ -194,19 +183,30 @@ public class Level implements Serializable {
         this.kdpt = kdpt;
     }
 
-    public String getCoarseCode() {
-        return coarseCode;
+    public String getRoughCode() {
+        return roughCode;
+    }
+
+    public void setRoughCode(String roughCode) {
+        this.roughCode = roughCode;
     }
 
-    public void setCoarseCode(String coarseCode) {
-        this.coarseCode = coarseCode;
+    public Integer getRoughWeight() {
+        return roughWeight;
     }
 
-    public Integer getCoarseWeight() {
-        return coarseWeight;
+    public void setRoughWeight(Integer roughWeight) {
+        this.roughWeight = roughWeight;
     }
 
-    public void setCoarseWeight(Integer coarseWeight) {
-        this.coarseWeight = coarseWeight;
+    public enum LevelType {
+        /**
+         * 非录取
+         */
+        UNADMIT,
+        /**
+         * 录取
+         */
+        ADMITED
     }
 }

+ 1 - 1
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/MarkStage.java

@@ -13,7 +13,7 @@ public enum MarkStage {
     /**
      * 粗分档
      */
-    COARSE_LEVEL,
+    ROUGH_LEVEL,
     /**
      * 分档
      */

+ 11 - 0
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/MarkSubject.java

@@ -47,6 +47,9 @@ public class MarkSubject implements Serializable {
     //是否禁用0:禁用 1:启用
     private boolean enable;
 
+    @Transient
+    private boolean formal = false;
+
     public boolean isAllLevel() {
         return allLevel;
     }
@@ -150,4 +153,12 @@ public class MarkSubject implements Serializable {
     public void setEnable(boolean enable) {
         this.enable = enable;
     }
+
+    public boolean isFormal() {
+        return formal;
+    }
+
+    public void setFormal(boolean formal) {
+        this.formal = formal;
+    }
 }

+ 29 - 5
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/MarkerGroupStudent.java

@@ -2,10 +2,8 @@ package cn.com.qmth.stmms.ms.core.domain;
 
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 
-import javax.persistence.Entity;
-import javax.persistence.GeneratedValue;
-import javax.persistence.Id;
-import javax.persistence.Table;
+import javax.persistence.*;
+import javax.validation.constraints.NotNull;
 import java.io.Serializable;
 
 /**
@@ -21,12 +19,20 @@ public class MarkerGroupStudent implements Serializable {
 
     private Long workId;
 
+    @NotNull
+    @Enumerated(value = EnumType.STRING)
     private Subject subject;
 
+    @NotNull
+    @Enumerated(value = EnumType.ORDINAL)
     private MarkStage stage;
 
     private Long groupId;
 
+    private Long paperId;
+
+    private Long questionId;
+
     private String examNumber;
 
     private String name;
@@ -48,11 +54,13 @@ public class MarkerGroupStudent implements Serializable {
     public MarkerGroupStudent() {
     }
 
-    public MarkerGroupStudent(Long workId, MarkStage stage, Subject subject, Long groupId, String examNumber, String name, String areaCode, String areaName, String examRoom, String school, String sourceName, Long batchNo) {
+    public MarkerGroupStudent(Long workId, MarkStage stage, Subject subject, Long groupId, Long paperId, Long questionId, String examNumber, String name, String areaCode, String areaName, String examRoom, String school, String sourceName, Long batchNo) {
         this.workId = workId;
         this.subject = subject;
         this.stage = stage;
         this.groupId = groupId;
+        this.questionId = questionId;
+        this.paperId = paperId;
         this.examNumber = examNumber;
         this.name = name;
         this.areaCode = areaCode;
@@ -104,6 +112,22 @@ public class MarkerGroupStudent implements Serializable {
         this.groupId = groupId;
     }
 
+    public Long getPaperId() {
+        return paperId;
+    }
+
+    public void setPaperId(Long paperId) {
+        this.paperId = paperId;
+    }
+
+    public Long getQuestionId() {
+        return questionId;
+    }
+
+    public void setQuestionId(Long questionId) {
+        this.questionId = questionId;
+    }
+
     public String getExamNumber() {
         return examNumber;
     }

+ 125 - 0
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/Message.java

@@ -0,0 +1,125 @@
+package cn.com.qmth.stmms.ms.core.domain;
+
+import cn.com.qmth.stmms.ms.core.vo.Subject;
+
+import javax.persistence.*;
+import java.util.Date;
+
+@Entity
+@Table(name = "message")
+public class Message {
+
+    @Id
+    @GeneratedValue
+    private Long id;
+
+    private Long workId;
+
+    @Enumerated(value = EnumType.STRING)
+    private Subject subject;
+
+    @Enumerated(value = EnumType.ORDINAL)
+    private MarkStage stage;
+
+    private Long markerId;
+
+    private String markerName;
+
+    private Long markerLeaderId;
+
+    private String markerLeaderName;
+
+    private String content;
+
+    private Long createTime;
+
+    private Boolean read;
+
+    public Long getId() {
+        return id;
+    }
+
+    public void setId(Long id) {
+        this.id = id;
+    }
+
+    public Long getWorkId() {
+        return workId;
+    }
+
+    public void setWorkId(Long workId) {
+        this.workId = workId;
+    }
+
+    public Subject getSubject() {
+        return subject;
+    }
+
+    public void setSubject(Subject subject) {
+        this.subject = subject;
+    }
+
+    public MarkStage getStage() {
+        return stage;
+    }
+
+    public void setStage(MarkStage stage) {
+        this.stage = stage;
+    }
+
+    public Long getMarkerId() {
+        return markerId;
+    }
+
+    public void setMarkerId(Long markerId) {
+        this.markerId = markerId;
+    }
+
+    public String getMarkerName() {
+        return markerName;
+    }
+
+    public void setMarkerName(String markerName) {
+        this.markerName = markerName;
+    }
+
+    public Long getMarkerLeaderId() {
+        return markerLeaderId;
+    }
+
+    public void setMarkerLeaderId(Long markerLeaderId) {
+        this.markerLeaderId = markerLeaderId;
+    }
+
+    public String getMarkerLeaderName() {
+        return markerLeaderName;
+    }
+
+    public void setMarkerLeaderName(String markerLeaderName) {
+        this.markerLeaderName = markerLeaderName;
+    }
+
+    public String getContent() {
+        return content;
+    }
+
+    public void setContent(String content) {
+        this.content = content;
+    }
+
+    public Long getCreateTime() {
+        return createTime;
+    }
+
+    public void setCreateTime(Long createTime) {
+        this.createTime = createTime;
+    }
+
+    public Boolean getRead() {
+        return read;
+    }
+
+    public void setRead(Boolean read) {
+        this.read = read;
+    }
+}

+ 72 - 0
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/Paper.java

@@ -47,8 +47,15 @@ public class Paper implements Serializable {
     @NotNull
     private String questionName;
 
+    private String roughLevel;
+
     private String level;
 
+    /**
+     * 粗分档建议重评档位
+     */
+    private String redoRoughLevel;
+
     /**
      * 建议重评档位
      */
@@ -99,6 +106,8 @@ public class Paper implements Serializable {
      */
     private boolean isSample;
 
+    private boolean isRoughSample;
+
     //抽查范围ID
     private Long inspectRange;
     //生源地
@@ -127,6 +136,8 @@ public class Paper implements Serializable {
     @Column(name = "is_active")
     private boolean active; //是否激活(false:不是,true:是)
 
+    private Long roughBatchNo;
+
     private Long batchNo;
 
     private Long scoreBatchNo;
@@ -318,6 +329,14 @@ public class Paper implements Serializable {
         isArbitrated = arbitrated;
     }
 
+    public String getRedoRoughLevel() {
+        return redoRoughLevel;
+    }
+
+    public void setRedoRoughLevel(String redoRoughLevel) {
+        this.redoRoughLevel = redoRoughLevel;
+    }
+
     public String getRedoLevel() {
         return redoLevel;
     }
@@ -342,6 +361,19 @@ public class Paper implements Serializable {
         isTagged = tagged;
     }
 
+    /**
+     * 定档
+     *
+     * @param level
+     */
+    public void determineRoughLevel(String level) {
+        this.setRoughLevel(level);
+        this.setRejected(false);
+        this.setArbitrated(false);
+        this.setRedoRoughLevel(null);
+        this.setUpdatedOn(new Date());
+    }
+
     /**
      * 定档
      *
@@ -371,6 +403,22 @@ public class Paper implements Serializable {
         this.setSortNum(null);
     }
 
+    /**
+     * 打回
+     *
+     * @param redoLevel
+     */
+    public void roughReject(String redoLevel) {
+        this.setRejected(true);
+        this.setArbitrated(false);
+        this.setRedoLevel(redoLevel);
+        this.setRoughLevel(null);
+        this.setTagged(true);
+        this.setMarkByLeader(false);
+        this.setUpdatedOn(new Date());
+        this.setSortNum(null);
+    }
+
     /**
      * 仲裁
      */
@@ -581,4 +629,28 @@ public class Paper implements Serializable {
     public void setMark(boolean mark) {
         isMark = mark;
     }
+
+    public String getRoughLevel() {
+        return roughLevel;
+    }
+
+    public void setRoughLevel(String roughLevel) {
+        this.roughLevel = roughLevel;
+    }
+
+    public boolean isRoughSample() {
+        return isRoughSample;
+    }
+
+    public void setRoughSample(boolean roughSample) {
+        isRoughSample = roughSample;
+    }
+
+    public Long getRoughBatchNo() {
+        return roughBatchNo;
+    }
+
+    public void setRoughBatchNo(Long roughBatchNo) {
+        this.roughBatchNo = roughBatchNo;
+    }
 }

+ 17 - 17
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/ParamSetting.java

@@ -30,7 +30,7 @@ public class ParamSetting implements Serializable {
     private String collectConfig;
 
     // 粗分档参数
-    private String coarseLevelConfig;
+    private String roughLevelConfig;
 
     // 细分档参数
     private String levelConfig;
@@ -60,22 +60,22 @@ public class ParamSetting implements Serializable {
         levelConfig.setPropDenominator(1);//档位百分比分母
         levelConfig.setShowStandardPaperManage(1);//是否显示标准卷管理
         levelConfig.setClearData(0);//是否显示清除当前阅卷数据
-        levelConfig.setCoarseLevel(0);//是否开启粗分档
+        levelConfig.setRoughLevel(0);//是否开启粗分档
         levelConfig.setRemoveHighAndLow(0);//是否开启去高去低再加权评卷
         paramSetting.setLevelConfig(JSON.toJSONString(levelConfig));
 
         // 粗分档参数
-        LevelConfig coarseLevelConfig = new LevelConfig();
-        coarseLevelConfig.setAutoCallback(0);//是否自动打回
-        coarseLevelConfig.setDeviation(4);//仲裁档位差
-        coarseLevelConfig.setMajority(1);//是否过半定档
-        coarseLevelConfig.setTakeBest(1);//取优原则
-        coarseLevelConfig.setLevelShowAllPaper(0);//阅卷员是否显示所有试卷
-        coarseLevelConfig.setPropDenominator(1);//档位百分比分母
-        coarseLevelConfig.setClearData(0);//是否显示清除当前阅卷数据
-        coarseLevelConfig.setShowStandardPaperManage(1);//是否显示标准卷管理
-        coarseLevelConfig.setRemoveHighAndLow(0);//是否开启去高去低再加权评卷
-        paramSetting.setCoarseLevelConfig(JSON.toJSONString(coarseLevelConfig));
+        LevelConfig roughLevelConfig = new LevelConfig();
+        roughLevelConfig.setAutoCallback(0);//是否自动打回
+        roughLevelConfig.setDeviation(4);//仲裁档位差
+        roughLevelConfig.setMajority(1);//是否过半定档
+        roughLevelConfig.setTakeBest(1);//取优原则
+        roughLevelConfig.setLevelShowAllPaper(0);//阅卷员是否显示所有试卷
+        roughLevelConfig.setPropDenominator(1);//档位百分比分母
+        roughLevelConfig.setClearData(0);//是否显示清除当前阅卷数据
+        roughLevelConfig.setShowStandardPaperManage(1);//是否显示标准卷管理
+        roughLevelConfig.setRemoveHighAndLow(0);//是否开启去高去低再加权评卷
+        paramSetting.setRoughLevelConfig(JSON.toJSONString(roughLevelConfig));
 
         // 打分参数
         ScoreConfig scoreConfig = new ScoreConfig();
@@ -113,12 +113,12 @@ public class ParamSetting implements Serializable {
         this.collectConfig = collectConfig;
     }
 
-    public String getCoarseLevelConfig() {
-        return coarseLevelConfig;
+    public String getRoughLevelConfig() {
+        return roughLevelConfig;
     }
 
-    public void setCoarseLevelConfig(String coarseLevelConfig) {
-        this.coarseLevelConfig = coarseLevelConfig;
+    public void setRoughLevelConfig(String roughLevelConfig) {
+        this.roughLevelConfig = roughLevelConfig;
     }
 
     public String getLevelConfig() {

+ 44 - 0
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/RoughLevel.java

@@ -0,0 +1,44 @@
+package cn.com.qmth.stmms.ms.core.domain;
+
+public class RoughLevel {
+
+    private String roughCode;
+
+    private Integer minScore;
+
+    private Integer maxScore;
+
+    private Integer weight;
+
+    public String getRoughCode() {
+        return roughCode;
+    }
+
+    public void setRoughCode(String roughCode) {
+        this.roughCode = roughCode;
+    }
+
+    public Integer getMinScore() {
+        return minScore;
+    }
+
+    public void setMinScore(Integer minScore) {
+        this.minScore = minScore;
+    }
+
+    public Integer getMaxScore() {
+        return maxScore;
+    }
+
+    public void setMaxScore(Integer maxScore) {
+        this.maxScore = maxScore;
+    }
+
+    public Integer getWeight() {
+        return weight;
+    }
+
+    public void setWeight(Integer weight) {
+        this.weight = weight;
+    }
+}

+ 1 - 1
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/enums/ParamSettingTypeEnum.java

@@ -18,7 +18,7 @@ public enum ParamSettingTypeEnum {
     /**
      * 粗分档参数
      */
-    FIRST_LEVEL("FIRST_LEVEL", "粗分档参数"),
+    ROUGH_LEVEL("ROUGH_LEVEL", "粗分档参数"),
     /**
      * 细分档参数
      */

+ 5 - 5
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/paramsetting/LevelConfig.java

@@ -48,7 +48,7 @@ public class LevelConfig {
     /**
      * 是否增加粗分档
      */
-    private Integer coarseLevel;
+    private Integer roughLevel;
 
     /**
      * 是否开启去高去低再加权评卷
@@ -119,12 +119,12 @@ public class LevelConfig {
         this.clearData = clearData;
     }
 
-    public Integer getCoarseLevel() {
-        return coarseLevel;
+    public Integer getRoughLevel() {
+        return roughLevel;
     }
 
-    public void setCoarseLevel(Integer coarseLevel) {
-        this.coarseLevel = coarseLevel;
+    public void setRoughLevel(Integer roughLevel) {
+        this.roughLevel = roughLevel;
     }
 
     public Integer getRemoveHighAndLow() {

+ 1 - 1
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/paramsetting/CoarseLevelConfig.java → stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/paramsetting/RoughLevelConfig.java

@@ -3,7 +3,7 @@ package cn.com.qmth.stmms.ms.core.domain.paramsetting;
 /**
  * 粗分档参数
  */
-public class CoarseLevelConfig {
+public class RoughLevelConfig {
 
     /**
      * 仲裁档位差

+ 12 - 18
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/task/MarkTask.java → stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/task/MarkTaskRoughLevel.java

@@ -13,13 +13,12 @@ import java.io.Serializable;
 import java.util.Date;
 
 /**
- * 评卷任务
- * Created by zhengmin on 2016/9/22.
+ * 粗分档评卷任务
  */
 @Entity
 @Table(indexes = {
         @Index(name = "idx_mark_task_paper_id", columnList = "paperId")})
-public class MarkTask implements Serializable {
+public class MarkTaskRoughLevel implements Serializable {
 
     private static final long serialVersionUID = -1095989485341316938L;
 
@@ -147,7 +146,7 @@ public class MarkTask implements Serializable {
         this.randomSeqNew = randomSeqNew;
     }
 
-    public MarkTask(MarkUser marker, Paper paper, MarkStage stage, Long randomSeqNew) {
+    public MarkTaskRoughLevel(MarkUser marker, Paper paper, MarkStage stage, Long randomSeqNew) {
         this.markerId = marker.getId();
         this.markerName = marker.getName();
         this.subject = marker.getSubject();
@@ -163,7 +162,7 @@ public class MarkTask implements Serializable {
         this.isMark = false;
     }
 
-    public MarkTask(MarkUser marker, Paper paper, MarkStage stage, Long randomSeqNew, int test) {
+    public MarkTaskRoughLevel(MarkUser marker, Paper paper, MarkStage stage, Long randomSeqNew, int test) {
         this.markerId = marker.getId();
         this.markerName = marker.getName();
         this.subject = marker.getSubject();
@@ -172,16 +171,14 @@ public class MarkTask implements Serializable {
         this.questionId = paper.getQuestionId();
         this.stage = stage;
         this.createdOn = new Date();
-        //随机号生成修改规则
-//        this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + paper.getExamNumber().substring(3, paper.getExamNumber().length());
         this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + randomSeqNew;
         this.randomSeqNew = randomSeqNew;
         this.test = test != TrialEnum.DEFAULT.getId() ? TrialEnum.START_TRIAL.getId() : test;
-        this.isSample = paper.isSample();
+        this.isSample = paper.isRoughSample();
         this.isMark = false;
     }
 
-    public MarkTask(MarkUser marker, Paper paper, Level level, MarkStage stage, Long randomSeqNew, int test) {
+    public MarkTaskRoughLevel(MarkUser marker, Paper paper, Level level, MarkStage stage, Long randomSeqNew, int test) {
         this.markerId = marker.getId();
         this.markerName = marker.getName();
         this.subject = marker.getSubject();
@@ -190,16 +187,13 @@ public class MarkTask implements Serializable {
         this.questionId = paper.getQuestionId();
         this.stage = stage;
         this.createdOn = new Date();
-        //随机号生成修改规则
-//        this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + paper.getExamNumber().substring(3, paper.getExamNumber().length());
         this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + randomSeqNew;
         this.randomSeqNew = randomSeqNew;
         this.test = test != TrialEnum.DEFAULT.getId() ? TrialEnum.START_TRIAL.getId() : test;
-
-        this.result = paper.getLevel();
-        this.level = paper.getLevel();
-        this.isSample = paper.isSample();
-        this.levelValue = level.getLevelValue();
+        this.result = paper.getRoughLevel();
+        this.level = paper.getRoughLevel();
+        this.isSample = paper.isRoughSample();
+        this.levelValue = Integer.valueOf(level.getRoughCode());
         this.updatedOn = new Date();
         this.isMark = false;
     }
@@ -213,7 +207,7 @@ public class MarkTask implements Serializable {
      * @param result       结果
      * @param secretNumber 任务密号
      */
-    public MarkTask(Long id, Long markerId, String markerName, String result, String secretNumber, MarkStage stage) {
+    public MarkTaskRoughLevel(Long id, Long markerId, String markerName, String result, String secretNumber, MarkStage stage) {
         this.id = id;
         this.markerId = markerId;
         this.markerName = markerName;
@@ -222,7 +216,7 @@ public class MarkTask implements Serializable {
         this.stage = stage;
     }
 
-    public MarkTask() {
+    public MarkTaskRoughLevel() {
     }
 
     public Long getId() {

+ 0 - 3
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/task/MarkTaskScore.java

@@ -157,7 +157,6 @@ public class MarkTaskScore implements Serializable {
         this.stage = stage;
         this.createdOn = new Date();
         //随机号生成修改规则
-//        this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + paper.getExamNumber().substring(3, paper.getExamNumber().length());
         this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + randomSeqNew;
         this.randomSeqNew = randomSeqNew;
         this.isMark = false;
@@ -173,7 +172,6 @@ public class MarkTaskScore implements Serializable {
         this.stage = stage;
         this.createdOn = new Date();
         //随机号生成修改规则
-//        this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + paper.getExamNumber().substring(3, paper.getExamNumber().length());
         this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + randomSeqNew;
         this.randomSeqNew = randomSeqNew;
         this.test = test != TrialEnum.DEFAULT.getId() ? TrialEnum.START_TRIAL.getId() : test;
@@ -191,7 +189,6 @@ public class MarkTaskScore implements Serializable {
         this.stage = stage;
         this.createdOn = new Date();
         //随机号生成修改规则
-//        this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + paper.getExamNumber().substring(3, paper.getExamNumber().length());
         this.secretNumber = marker.getId() + subject.ordinal() + paper.getAreaCode() + randomSeqNew;
         this.randomSeqNew = randomSeqNew;
         this.test = test != TrialEnum.DEFAULT.getId() ? TrialEnum.START_TRIAL.getId() : test;

+ 1 - 1
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/domain/user/MarkerGroup.java

@@ -34,7 +34,7 @@ public class MarkerGroup implements Serializable {
     private Subject subject;
 
     @NotNull
-    @Enumerated(value = EnumType.STRING)
+    @Enumerated(value = EnumType.ORDINAL)
     private MarkStage stage;
 
     @Transient

+ 30 - 26
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkTaskLevelRepo.java

@@ -29,7 +29,7 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
      */
     List<MarkTaskLevel> findByPaperIdAndStage(Long paperId, MarkStage stage);
 
-    @Query(value = "select new MarkTaskLevel(m.id, m.markerId , m.markerName, m.result, m.secretNumber, m.stage) from MarkTask m where m.paper.id = ?1 and m.stage = ?2")
+    @Query(value = "select new MarkTaskLevel(m.id, m.markerId , m.markerName, m.result, m.secretNumber, m.stage) from MarkTaskLevel m where m.paper.id = ?1 and m.stage = ?2")
     List<MarkTaskLevel> findByPaperIdAndStageNative(Long id, MarkStage level);
 
     /**
@@ -39,19 +39,19 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
      */
     long countByMarkerId(Long markerId);
 
-    @Query(value = "select count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?3 and m.batch_no = ?2", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m where m.question_id = ?1 and m.marker_id = ?3 and m.batch_no = ?2", nativeQuery = true)
     long countByQuestionIdAndBatchNo(Long questionId, Long batchNo, Long markerId);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.batch_no = ?5 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m inner join paper p on m.paper_id = p.id and p.batch_no = ?5 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResult(Long questionId, Long markerId, int stage, String result, Long batchNo);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResultAll(Long questionId, Long markerId, int stage, String result);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.score_batch_no = ?5 and p.level = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m inner join paper p on m.paper_id = p.id and p.score_batch_no = ?5 and p.level = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
     int countScoreByQuestionIdAndMarkerIdAndStageAndResult(Long questionId, Long markerId, int stage, String result, Long batchNo);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.level = ?4 and p.score_batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m inner join paper p on m.paper_id = p.id and p.level = ?4 and p.score_batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
     int countScoreByQuestionIdAndMarkerIdAndStageAndResultAll(Long questionId, Long markerId, int stage, String result);
 
     /**
@@ -60,7 +60,7 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
      * @param markerId 评卷员ID
      * @param stage    阶段
      */
-    @Query(value = "select mt from MarkTask mt left outer join fetch mt.paper where mt.markerId = ? and mt.stage = ?")
+    @Query(value = "select mt from MarkTaskLevel mt left outer join fetch mt.paper where mt.markerId = ? and mt.stage = ?")
     List<MarkTaskLevel> findByMarkerIdAndStage(Long markerId, MarkStage stage);
 
     /**
@@ -79,7 +79,7 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
      * @param test     试评状态
      */
     @Query(value = "SELECT q.`id`,q.`name`,SUM(IF(t.`result` IS NULL,1,0)),COUNT(t.question_id), q.area_code \n" +
-            "FROM mark_task t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_level t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.`marker_id` = ? and t.stage = ? and p.is_missing = false and p.is_test = ?  GROUP BY t.`question_id` ORDER BY q.`id`", nativeQuery = true)
     List<Object[]> countGroupByQuestion(Long markerId, Integer stageId, int test);
 
@@ -94,7 +94,7 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
      * @param markers 评卷员ID集合
      */
     @Query(value = "SELECT q.`id`,t.`marker_id` markerId,mu.login_name loginName,t.`marker_name` markerName,q.`name`,SUM(IF(t.`result` IS NULL,1,0)) leftCount,COUNT(t.question_id) totalCount, SUM(t.is_rejected) rejectedCount, q.area_code areaCode " +
-            "FROM mark_task t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_level t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.work_id = :workId and t.subject = :subject and t.stage = :stageId and p.is_missing = false and p.is_test = :test and p.batch_no = :batchNo and t.marker_id in (:markers) GROUP BY t.marker_id,mu.login_name, t.`marker_name` ORDER BY q.`id`,t.marker_id", nativeQuery = true)
     List<Object[]> listGroupByQuestionAndMarkerAndBatchNoAndMarkerId(@Param("workId") Long workId, @Param("subject") String subject, @Param("stageId") Integer stageId, @Param("test") int test, @Param("batchNo") Long batchNo, @Param("markers") List<Long> markers);
 
@@ -116,7 +116,7 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
      * @param name   科目
      * @param test   试评状态
      */
-    @Query(value = "SELECT q.area_code areaCode, q.area_name areaName, q.`name`,SUM(IF(p.`level` IS NULL or (p.level is not null and p.is_active = 0),1,0)) leftCount,COUNT(p.question_id) totalCount " +
+    @Query(value = "SELECT q.area_code areaCode, q.area_name areaName, q.`name`,SUM(IF(p.`level` IS NULL or (p.level is not null and p.batch_no is null),1,0)) leftCount,COUNT(p.question_id) totalCount " +
             "FROM exam_question q LEFT  JOIN paper p ON q.id = p.question_id AND q.subject = p.subject WHERE " +
             "p.work_id = ? and p.subject = ? and p.is_missing = false and p.is_test = ?  GROUP BY q.area_code, q.area_name ORDER BY q.area_code", nativeQuery = true)
     List<Object[]> listGroupByAreaName(Long workId, String name, int test);
@@ -128,7 +128,7 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
      * @param stageId  阶段
      */
     @Query(value = "SELECT q.`id`,q.`name`,SUM(IF(t.`result` IS NULL,1,0)),COUNT(t.question_id), q.area_code \n" +
-            "FROM mark_task t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_level t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.`marker_id` = ? and t.stage = ? and p.is_missing = false GROUP BY t.`question_id` ORDER BY q.`id`", nativeQuery = true)
     List<Object[]> countGroupByQuestion(Long markerId, Integer stageId);
 
@@ -142,7 +142,7 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
      * @param markers 评卷员ID集合
      */
     @Query(value = "SELECT q.`id`,t.`marker_id` markerId,mu.login_name loginName,t.`marker_name` markerName,q.`name`,SUM(IF(t.`result` IS NULL,1,0)) leftCount,COUNT(t.question_id) totalCount,SUM(t.is_rejected) rejectedCount, q.area_code areaCode " +
-            "FROM mark_task t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_level t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.work_id = :workId and t.subject = :subject and t.stage = :stageId and p.score_batch_no = :batchNo and t.`marker_id` in (:markers) and p.is_missing = false GROUP BY t.marker_id,mu.login_name, t.`marker_name` ORDER BY q.`id`, t.`marker_id`", nativeQuery = true)
     List<Object[]> listGroupByQuestionAndMarkerAndScoreBatchNoAndMakerId(@Param("workId") Long workId, @Param("subject") String subject, @Param("stageId") Integer stageId, @Param("batchNo") Long batchNo, @Param("markers") List<Long> markers);
 
@@ -159,51 +159,51 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
             "WHERE t.workId = ?1 and t.subject = ?2 and t.markerId = ?3 and t.stage = ?4 and t.questionId = ?5 ")
     Integer findRandomSeqByWorkIdAndSubjectAndMarkerIdAndStageAndQuestionId(Long workId, Subject subject, Long markerId, MarkStage stage, Long questionId);
 
-    @Query(value = "SELECT count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no = ?4 and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_level m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no = ?4 and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResultNull(Long questionId, Long markerId, int stage, Long batchNo);
 
-    @Query(value = "SELECT count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 0 and p.score_batch_no = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_level m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 0 and p.score_batch_no = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
     int countScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(Long questionId, Long markerId, int stage, Long batchNo);
 
     MarkTaskLevel findByPaperIdAndMarkerId(Long paperId, Long markId);
 
     List<MarkTaskLevel> findByWorkId(Long workId);
 
-    @Query(value = "SELECT count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.is_missing = ?4 and p.is_shift = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_level m inner join paper p on m.paper_id = p.id and p.is_missing = ?4 and p.is_shift = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
     int countShiftByQuestionIdAndMarkerIdAndStageAndResultIsNullAndIsMissing(Long questionId, Long id, int ordinal, boolean b);
 
-    @Query(value = "SELECT count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_level m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
     int countShiftScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(Long questionId, Long id, int ordinal);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2", nativeQuery = true)
     long countByQuestionIdAll(Long questionId, Long markId);
 
-    @Query(value = "SELECT count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no is not null and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_level m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no is not null and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResultIsNullAll(Long questionId, Long markerId, int stage);
 
-    @Query(value = "SELECT count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and  m.batch_no is not null and m.is_rejected = true", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_level m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and  m.batch_no is not null and m.is_rejected = true", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrue(Long questionId, Long markerId, int ordinal);
 
-    @Query(value = "select * from mark_task where work_id = ?1 and subject = ?2 and marker_id = ?3 and stage = ?4 limit 1", nativeQuery = true)
+    @Query(value = "select * from mark_task_level where work_id = ?1 and subject = ?2 and marker_id = ?3 and stage = ?4 limit 1", nativeQuery = true)
     List<MarkTaskLevel> findByWorkIdAndSubjectAndMarkerIdAndStageLimit(Long workId, String subject, Long valueOf, int stage);
 
     int countByWorkIdAndSubjectAndStage(Long workId, Subject subject, MarkStage stage);
 
     int countByWorkIdAndStageAndResultNotNull(Long id, MarkStage level);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift = true", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift = true", nativeQuery = true)
     int countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftAndResult(Long workId, String subject, Long valueOf, int stage);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift_score = 1", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift_score = 1", nativeQuery = true)
     int countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftScoreAndResult(Long workId, String subject, Long valueOf, int stage);
 
-    @Query(value = "select count(1) from mark_task m where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.is_rejected = 1", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.is_rejected = 1", nativeQuery = true)
     int findByWorkIdAndSubjectAndMarkerIdAndStageReject(Long workId, String subject, Long valueOf, int stage);
 
-    @Query(value = "select count(1) from mark_task m where m.work_id = ?1", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_level m where m.work_id = ?1", nativeQuery = true)
     int countByWorkId(Long workId);
 
-    @Query(value = "select id, random_seq_new randomSeqNew from mark_task m where m.work_id = ?1", nativeQuery = true)
+    @Query(value = "select id, random_seq_new randomSeqNew from mark_task_level m where m.work_id = ?1", nativeQuery = true)
     List<Object[]> findAllByWorkId(Long workId);
 
     @Modifying
@@ -213,7 +213,7 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
     @Query("select s.paper from MarkTaskLevel s where s.workId = :workId and s.subject = :subject and s.stage = :stage and s.markerId in (:markers)")
     List<Paper> findByWorkIdAndSubjectAndStageAndMarkerIdIn(@Param("workId") Long workId, @Param("subject") Subject subject, @Param("stage") MarkStage stage, @Param("markers") List<Long> markers);
 
-    @Query(value = "select s.paper_id, s.marker_id from mark_task s where s.work_id = :workId and s.subject = :subject and s.stage = :stage", nativeQuery = true)
+    @Query(value = "select s.paper_id, s.marker_id from mark_task_level s where s.work_id = :workId and s.subject = :subject and s.stage = :stage", nativeQuery = true)
     List<Object[]> findByWorkIdAndSubjectAndStage(@Param("workId") Long workId, @Param("subject") String subject, @Param("stage") int stage);
 
     List<MarkTaskLevel> findByWorkIdAndSubjectAndSecretNumberAndTest(Long workId, Subject subject, String secretNumber, int id);
@@ -223,4 +223,8 @@ public interface MarkTaskLevelRepo extends JpaRepository<MarkTaskLevel, Long>, J
     void updateMarkTaskMarkById(Long markTaskId, Boolean isMark);
 
     void deleteByWorkIdAndSubject(Long workId, Subject subject);
+
+    List<MarkTaskLevel> findByPaperId(Long paperId);
+
+    Integer findRandomSeqByWorkIdAndSubjectAndMarkerIdAndQuestionId(Long workId, Subject subject, Long markerId, Long questionId);
 }

+ 48 - 43
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkTaskRepo.java → stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkTaskRoughLevelRepo.java

@@ -2,7 +2,8 @@ package cn.com.qmth.stmms.ms.core.repository;
 
 import cn.com.qmth.stmms.ms.core.domain.MarkStage;
 import cn.com.qmth.stmms.ms.core.domain.Paper;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskRoughLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import org.springframework.data.jpa.repository.JpaRepository;
 import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
@@ -13,13 +14,13 @@ import org.springframework.data.repository.query.Param;
 import java.util.List;
 
 /**
- * Created by zhengmin on 2016/9/23.
+ *
  */
-public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecificationExecutor {
+public interface MarkTaskRoughLevelRepo extends JpaRepository<MarkTaskRoughLevel, Long>, JpaSpecificationExecutor {
 
     int countByMarkerIdAndPaperIdAndWorkIdAndRandomSeqNew(Long markerId, Long paperId, Long randomSeqNew, Long workId);
 
-    List<MarkTask> findByWorkIdAndStageAndPaperId(Long workId, MarkStage stage, Long paperId);
+    List<MarkTaskLevel> findByWorkIdAndStageAndPaperId(Long workId, MarkStage stage, Long paperId);
 
     /**
      * 查询指定阶段试卷的评卷任务
@@ -27,10 +28,10 @@ public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecific
      * @param paperId 试卷id
      * @param stage   评卷阶段
      */
-    List<MarkTask> findByPaperIdAndStage(Long paperId, MarkStage stage);
+    List<MarkTaskRoughLevel> findByPaperIdAndStage(Long paperId, MarkStage stage);
 
-    @Query(value = "select new MarkTask(m.id, m.markerId , m.markerName, m.result, m.secretNumber, m.stage) from MarkTask m where m.paper.id = ?1 and m.stage = ?2")
-    List<MarkTask> findByPaperIdAndStageNative(Long id, MarkStage level);
+    @Query(value = "select new MarkTaskRoughLevel(m.id, m.markerId , m.markerName, m.result, m.secretNumber, m.stage) from MarkTaskRoughLevel m where m.paper.id = ?1 and m.stage = ?2")
+    List<MarkTaskRoughLevel> findByPaperIdAndStageNative(Long id, MarkStage level);
 
     /**
      * 评卷员任务数量
@@ -39,19 +40,19 @@ public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecific
      */
     long countByMarkerId(Long markerId);
 
-    @Query(value = "select count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?3 and m.batch_no = ?2", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m where m.question_id = ?1 and m.marker_id = ?3 and m.batch_no = ?2", nativeQuery = true)
     long countByQuestionIdAndBatchNo(Long questionId, Long batchNo, Long markerId);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.batch_no = ?5 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id and p.rough_batch_no = ?5 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResult(Long questionId, Long markerId, int stage, String result, Long batchNo);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id and p.rough_batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResultAll(Long questionId, Long markerId, int stage, String result);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.score_batch_no = ?5 and p.level = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id and p.score_batch_no = ?5 and p.level = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
     int countScoreByQuestionIdAndMarkerIdAndStageAndResult(Long questionId, Long markerId, int stage, String result, Long batchNo);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.level = ?4 and p.score_batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id and p.level = ?4 and p.score_batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
     int countScoreByQuestionIdAndMarkerIdAndStageAndResultAll(Long questionId, Long markerId, int stage, String result);
 
     /**
@@ -60,8 +61,8 @@ public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecific
      * @param markerId 评卷员ID
      * @param stage    阶段
      */
-    @Query(value = "select mt from MarkTask mt left outer join fetch mt.paper where mt.markerId = ? and mt.stage = ?")
-    List<MarkTask> findByMarkerIdAndStage(Long markerId, MarkStage stage);
+    @Query(value = "select mt from MarkTaskRoughLevel mt left outer join fetch mt.paper where mt.markerId = ? and mt.stage = ?")
+    List<MarkTaskLevel> findByMarkerIdAndStage(Long markerId, MarkStage stage);
 
     /**
      * 删除评卷员所有任务
@@ -79,7 +80,7 @@ public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecific
      * @param test     试评状态
      */
     @Query(value = "SELECT q.`id`,q.`name`,SUM(IF(t.`result` IS NULL,1,0)),COUNT(t.question_id), q.area_code \n" +
-            "FROM mark_task t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_rough_level t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.`marker_id` = ? and t.stage = ? and p.is_missing = false and p.is_test = ?  GROUP BY t.`question_id` ORDER BY q.`id`", nativeQuery = true)
     List<Object[]> countGroupByQuestion(Long markerId, Integer stageId, int test);
 
@@ -94,8 +95,8 @@ public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecific
      * @param markers 评卷员ID集合
      */
     @Query(value = "SELECT q.`id`,t.`marker_id` markerId,mu.login_name loginName,t.`marker_name` markerName,q.`name`,SUM(IF(t.`result` IS NULL,1,0)) leftCount,COUNT(t.question_id) totalCount, SUM(t.is_rejected) rejectedCount, q.area_code areaCode " +
-            "FROM mark_task t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
-            "t.work_id = :workId and t.subject = :subject and t.stage = :stageId and p.is_missing = false and p.is_test = :test and p.batch_no = :batchNo and t.marker_id in (:markers) GROUP BY t.marker_id,mu.login_name, t.`marker_name` ORDER BY q.`id`,t.marker_id", nativeQuery = true)
+            "FROM mark_task_rough_level t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "t.work_id = :workId and t.subject = :subject and t.stage = :stageId and p.is_missing = false and p.is_test = :test and p.rough_batch_no = :batchNo and t.marker_id in (:markers) GROUP BY t.marker_id,mu.login_name, t.`marker_name` ORDER BY q.`id`,t.marker_id", nativeQuery = true)
     List<Object[]> listGroupByQuestionAndMarkerAndBatchNoAndMarkerId(@Param("workId") Long workId, @Param("subject") String subject, @Param("stageId") Integer stageId, @Param("test") int test, @Param("batchNo") Long batchNo, @Param("markers") List<Long> markers);
 
     /**
@@ -116,7 +117,7 @@ public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecific
      * @param name   科目
      * @param test   试评状态
      */
-    @Query(value = "SELECT q.area_code areaCode, q.area_name areaName, q.`name`,SUM(IF(p.`level` IS NULL or (p.level is not null and p.is_active = 0),1,0)) leftCount,COUNT(p.question_id) totalCount " +
+    @Query(value = "SELECT q.area_code areaCode, q.area_name areaName, q.`name`,SUM(IF(p.`rough_level` IS NULL or (p.rough_level is not null and p.rough_batch_no is null),1,0)) leftCount,COUNT(p.question_id) totalCount " +
             "FROM exam_question q LEFT  JOIN paper p ON q.id = p.question_id AND q.subject = p.subject WHERE " +
             "p.work_id = ? and p.subject = ? and p.is_missing = false and p.is_test = ?  GROUP BY q.area_code, q.area_name ORDER BY q.area_code", nativeQuery = true)
     List<Object[]> listGroupByAreaName(Long workId, String name, int test);
@@ -128,7 +129,7 @@ public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecific
      * @param stageId  阶段
      */
     @Query(value = "SELECT q.`id`,q.`name`,SUM(IF(t.`result` IS NULL,1,0)),COUNT(t.question_id), q.area_code \n" +
-            "FROM mark_task t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_rough_level t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.`marker_id` = ? and t.stage = ? and p.is_missing = false GROUP BY t.`question_id` ORDER BY q.`id`", nativeQuery = true)
     List<Object[]> countGroupByQuestion(Long markerId, Integer stageId);
 
@@ -142,7 +143,7 @@ public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecific
      * @param markers 评卷员ID集合
      */
     @Query(value = "SELECT q.`id`,t.`marker_id` markerId,mu.login_name loginName,t.`marker_name` markerName,q.`name`,SUM(IF(t.`result` IS NULL,1,0)) leftCount,COUNT(t.question_id) totalCount,SUM(t.is_rejected) rejectedCount, q.area_code areaCode " +
-            "FROM mark_task t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_rough_level t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.work_id = :workId and t.subject = :subject and t.stage = :stageId and p.score_batch_no = :batchNo and t.`marker_id` in (:markers) and p.is_missing = false GROUP BY t.marker_id,mu.login_name, t.`marker_name` ORDER BY q.`id`, t.`marker_id`", nativeQuery = true)
     List<Object[]> listGroupByQuestionAndMarkerAndScoreBatchNoAndMakerId(@Param("workId") Long workId, @Param("subject") String subject, @Param("stageId") Integer stageId, @Param("batchNo") Long batchNo, @Param("markers") List<Long> markers);
 
@@ -153,74 +154,78 @@ public interface MarkTaskRepo extends JpaRepository<MarkTask, Long>, JpaSpecific
      */
     Long countByPaperId(Long id);
 
-    List<MarkTask> findByWorkIdAndSecretNumber(Long workId, String secretNumber);
+    List<MarkTaskLevel> findByWorkIdAndSecretNumber(Long workId, String secretNumber);
 
-    @Query(value = "SELECT max(t.randomSeq) FROM MarkTask t " +
+    @Query(value = "SELECT max(t.randomSeq) FROM MarkTaskLevel t " +
             "WHERE t.workId = ?1 and t.subject = ?2 and t.markerId = ?3 and t.stage = ?4 and t.questionId = ?5 ")
     Integer findRandomSeqByWorkIdAndSubjectAndMarkerIdAndStageAndQuestionId(Long workId, Subject subject, Long markerId, MarkStage stage, Long questionId);
 
-    @Query(value = "SELECT count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no = ?4 and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_rough_level m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no = ?4 and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResultNull(Long questionId, Long markerId, int stage, Long batchNo);
 
-    @Query(value = "SELECT count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 0 and p.score_batch_no = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 0 and p.score_batch_no = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
     int countScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(Long questionId, Long markerId, int stage, Long batchNo);
 
-    MarkTask findByPaperIdAndMarkerId(Long paperId, Long markId);
+    MarkTaskLevel findByPaperIdAndMarkerId(Long paperId, Long markId);
 
-    List<MarkTask> findByWorkId(Long workId);
+    List<MarkTaskLevel> findByWorkId(Long workId);
 
-    @Query(value = "SELECT count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.is_missing = ?4 and p.is_shift = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id and p.is_missing = ?4 and p.is_shift = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
     int countShiftByQuestionIdAndMarkerIdAndStageAndResultIsNullAndIsMissing(Long questionId, Long id, int ordinal, boolean b);
 
-    @Query(value = "SELECT count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
     int countShiftScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(Long questionId, Long id, int ordinal);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2", nativeQuery = true)
     long countByQuestionIdAll(Long questionId, Long markId);
 
-    @Query(value = "SELECT count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no is not null and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_rough_level m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no is not null and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResultIsNullAll(Long questionId, Long markerId, int stage);
 
-    @Query(value = "SELECT count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and  m.batch_no is not null and m.is_rejected = true", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_rough_level m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and  m.batch_no is not null and m.is_rejected = true", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrue(Long questionId, Long markerId, int ordinal);
 
-    @Query(value = "select * from mark_task where work_id = ?1 and subject = ?2 and marker_id = ?3 and stage = ?4 limit 1", nativeQuery = true)
-    List<MarkTask> findByWorkIdAndSubjectAndMarkerIdAndStageLimit(Long workId, String subject, Long valueOf, int stage);
+    @Query(value = "select * from mark_task_rough_level where work_id = ?1 and subject = ?2 and marker_id = ?3 and stage = ?4 limit 1", nativeQuery = true)
+    List<MarkTaskRoughLevel> findByWorkIdAndSubjectAndMarkerIdAndStageLimit(Long workId, String subject, Long valueOf, int stage);
 
     int countByWorkIdAndSubjectAndStage(Long workId, Subject subject, MarkStage stage);
 
     int countByWorkIdAndStageAndResultNotNull(Long id, MarkStage level);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift = true", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift = true", nativeQuery = true)
     int countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftAndResult(Long workId, String subject, Long valueOf, int stage);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift_score = 1", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift_score = 1", nativeQuery = true)
     int countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftScoreAndResult(Long workId, String subject, Long valueOf, int stage);
 
-    @Query(value = "select count(1) from mark_task m where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.is_rejected = 1", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.is_rejected = 1", nativeQuery = true)
     int findByWorkIdAndSubjectAndMarkerIdAndStageReject(Long workId, String subject, Long valueOf, int stage);
 
-    @Query(value = "select count(1) from mark_task m where m.work_id = ?1", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_rough_level m where m.work_id = ?1", nativeQuery = true)
     int countByWorkId(Long workId);
 
-    @Query(value = "select id, random_seq_new randomSeqNew from mark_task m where m.work_id = ?1", nativeQuery = true)
+    @Query(value = "select id, random_seq_new randomSeqNew from mark_task_rough_level m where m.work_id = ?1", nativeQuery = true)
     List<Object[]> findAllByWorkId(Long workId);
 
     @Modifying
-    @Query(value = "update mark_task m set m.level = ?1 where m.paper_id = ?2", nativeQuery = true)
+    @Query(value = "update mark_task_rough_level m set m.level = ?1 where m.paper_id = ?2", nativeQuery = true)
     void updateLevelByPaperId(String level, Long id);
 
-    @Query("select s.paper from MarkTask s where s.workId = :workId and s.subject = :subject and s.stage = :stage and s.markerId in (:markers)")
+    @Query("select s.paper from MarkTaskRoughLevel s where s.workId = :workId and s.subject = :subject and s.stage = :stage and s.markerId in (:markers)")
     List<Paper> findByWorkIdAndSubjectAndStageAndMarkerIdIn(@Param("workId") Long workId, @Param("subject") Subject subject, @Param("stage") MarkStage stage, @Param("markers") List<Long> markers);
 
-    @Query(value = "select s.paper_id, s.marker_id from mark_task s where s.work_id = :workId and s.subject = :subject and s.stage = :stage", nativeQuery = true)
+    @Query(value = "select s.paper_id, s.marker_id from mark_task_rough_level s where s.work_id = :workId and s.subject = :subject and s.stage = :stage", nativeQuery = true)
     List<Object[]> findByWorkIdAndSubjectAndStage(@Param("workId") Long workId, @Param("subject") String subject, @Param("stage") int stage);
 
-    List<MarkTask> findByWorkIdAndSubjectAndSecretNumberAndTest(Long workId, Subject subject, String secretNumber, int id);
+    List<MarkTaskRoughLevel> findByWorkIdAndSubjectAndSecretNumberAndTest(Long workId, Subject subject, String secretNumber, int id);
 
     @Modifying
-    @Query("update MarkTask m set m.isMark = ?2 where m.id = ?1")
+    @Query("update MarkTaskRoughLevel m set m.isMark = ?2 where m.id = ?1")
     void updateMarkTaskMarkById(Long markTaskId, Boolean isMark);
 
     void deleteByWorkIdAndSubject(Long workId, Subject subject);
+
+    List<MarkTaskRoughLevel> findByPaperId(Long paperId);
+
+    Integer findRandomSeqByWorkIdAndSubjectAndMarkerIdAndQuestionId(Long workId, Subject subject, Long markerId, Long questionId);
 }

+ 30 - 26
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkTaskScoreRepo.java

@@ -29,7 +29,7 @@ public interface MarkTaskScoreRepo extends JpaRepository<MarkTaskScore, Long>, J
      */
     List<MarkTaskScore> findByPaperIdAndStage(Long paperId, MarkStage stage);
 
-    @Query(value = "select new MarkTaskScore(m.id, m.markerId , m.markerName, m.result, m.secretNumber, m.stage) from MarkTask m where m.paper.id = ?1 and m.stage = ?2")
+    @Query(value = "select new MarkTaskScore(m.id, m.markerId , m.markerName, m.result, m.secretNumber, m.stage) from MarkTaskScore m where m.paper.id = ?1 and m.stage = ?2")
     List<MarkTaskScore> findByPaperIdAndStageNative(Long id, MarkStage level);
 
     /**
@@ -39,19 +39,19 @@ public interface MarkTaskScoreRepo extends JpaRepository<MarkTaskScore, Long>, J
      */
     long countByMarkerId(Long markerId);
 
-    @Query(value = "select count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?3 and m.batch_no = ?2", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m where m.question_id = ?1 and m.marker_id = ?3 and m.batch_no = ?2", nativeQuery = true)
     long countByQuestionIdAndBatchNo(Long questionId, Long batchNo, Long markerId);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.batch_no = ?5 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m inner join paper p on m.paper_id = p.id and p.batch_no = ?5 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResult(Long questionId, Long markerId, int stage, String result, Long batchNo);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result = ?4 and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResultAll(Long questionId, Long markerId, int stage, String result);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.score_batch_no = ?5 and p.level = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m inner join paper p on m.paper_id = p.id and p.score_batch_no = ?5 and p.level = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
     int countScoreByQuestionIdAndMarkerIdAndStageAndResult(Long questionId, Long markerId, int stage, String result, Long batchNo);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.level = ?4 and p.score_batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m inner join paper p on m.paper_id = p.id and p.level = ?4 and p.score_batch_no is not null where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is not null", nativeQuery = true)
     int countScoreByQuestionIdAndMarkerIdAndStageAndResultAll(Long questionId, Long markerId, int stage, String result);
 
     /**
@@ -60,7 +60,7 @@ public interface MarkTaskScoreRepo extends JpaRepository<MarkTaskScore, Long>, J
      * @param markerId 评卷员ID
      * @param stage    阶段
      */
-    @Query(value = "select mt from MarkTask mt left outer join fetch mt.paper where mt.markerId = ? and mt.stage = ?")
+    @Query(value = "select mt from MarkTaskScore mt left outer join fetch mt.paper where mt.markerId = ? and mt.stage = ?")
     List<MarkTaskScore> findByMarkerIdAndStage(Long markerId, MarkStage stage);
 
     /**
@@ -79,7 +79,7 @@ public interface MarkTaskScoreRepo extends JpaRepository<MarkTaskScore, Long>, J
      * @param test     试评状态
      */
     @Query(value = "SELECT q.`id`,q.`name`,SUM(IF(t.`result` IS NULL,1,0)),COUNT(t.question_id), q.area_code \n" +
-            "FROM mark_task t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_score t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.`marker_id` = ? and t.stage = ? and p.is_missing = false and p.is_test = ?  GROUP BY t.`question_id` ORDER BY q.`id`", nativeQuery = true)
     List<Object[]> countGroupByQuestion(Long markerId, Integer stageId, int test);
 
@@ -94,7 +94,7 @@ public interface MarkTaskScoreRepo extends JpaRepository<MarkTaskScore, Long>, J
      * @param markers 评卷员ID集合
      */
     @Query(value = "SELECT q.`id`,t.`marker_id` markerId,mu.login_name loginName,t.`marker_name` markerName,q.`name`,SUM(IF(t.`result` IS NULL,1,0)) leftCount,COUNT(t.question_id) totalCount, SUM(t.is_rejected) rejectedCount, q.area_code areaCode " +
-            "FROM mark_task t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_score t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.work_id = :workId and t.subject = :subject and t.stage = :stageId and p.is_missing = false and p.is_test = :test and p.batch_no = :batchNo and t.marker_id in (:markers) GROUP BY t.marker_id,mu.login_name, t.`marker_name` ORDER BY q.`id`,t.marker_id", nativeQuery = true)
     List<Object[]> listGroupByQuestionAndMarkerAndBatchNoAndMarkerId(@Param("workId") Long workId, @Param("subject") String subject, @Param("stageId") Integer stageId, @Param("test") int test, @Param("batchNo") Long batchNo, @Param("markers") List<Long> markers);
 
@@ -128,7 +128,7 @@ public interface MarkTaskScoreRepo extends JpaRepository<MarkTaskScore, Long>, J
      * @param stageId  阶段
      */
     @Query(value = "SELECT q.`id`,q.`name`,SUM(IF(t.`result` IS NULL,1,0)),COUNT(t.question_id), q.area_code \n" +
-            "FROM mark_task t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_score t LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.`marker_id` = ? and t.stage = ? and p.is_missing = false GROUP BY t.`question_id` ORDER BY q.`id`", nativeQuery = true)
     List<Object[]> countGroupByQuestion(Long markerId, Integer stageId);
 
@@ -142,7 +142,7 @@ public interface MarkTaskScoreRepo extends JpaRepository<MarkTaskScore, Long>, J
      * @param markers 评卷员ID集合
      */
     @Query(value = "SELECT q.`id`,t.`marker_id` markerId,mu.login_name loginName,t.`marker_name` markerName,q.`name`,SUM(IF(t.`result` IS NULL,1,0)) leftCount,COUNT(t.question_id) totalCount,SUM(t.is_rejected) rejectedCount, q.area_code areaCode " +
-            "FROM mark_task t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
+            "FROM mark_task_score t LEFT JOIN mark_user mu on t.marker_id = mu.id LEFT OUTER JOIN exam_question q ON t.`question_id` = q.`id` LEFT  JOIN paper p ON t.paper_id = p.id WHERE " +
             "t.work_id = :workId and t.subject = :subject and t.stage = :stageId and p.score_batch_no = :batchNo and t.`marker_id` in (:markers) and p.is_missing = false GROUP BY t.marker_id,mu.login_name, t.`marker_name` ORDER BY q.`id`, t.`marker_id`", nativeQuery = true)
     List<Object[]> listGroupByQuestionAndMarkerAndScoreBatchNoAndMakerId(@Param("workId") Long workId, @Param("subject") String subject, @Param("stageId") Integer stageId, @Param("batchNo") Long batchNo, @Param("markers") List<Long> markers);
 
@@ -159,61 +159,61 @@ public interface MarkTaskScoreRepo extends JpaRepository<MarkTaskScore, Long>, J
             "WHERE t.workId = ?1 and t.subject = ?2 and t.markerId = ?3 and t.stage = ?4 and t.questionId = ?5 ")
     Integer findRandomSeqByWorkIdAndSubjectAndMarkerIdAndStageAndQuestionId(Long workId, Subject subject, Long markerId, MarkStage stage, Long questionId);
 
-    @Query(value = "SELECT count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no = ?4 and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_score m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no = ?4 and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResultNull(Long questionId, Long markerId, int stage, Long batchNo);
 
-    @Query(value = "SELECT count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 0 and p.score_batch_no = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_score m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 0 and p.score_batch_no = ?4 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
     int countScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(Long questionId, Long markerId, int stage, Long batchNo);
 
     MarkTaskScore findByPaperIdAndMarkerId(Long paperId, Long markId);
 
     List<MarkTaskScore> findByWorkId(Long workId);
 
-    @Query(value = "SELECT count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.is_missing = ?4 and p.is_shift = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_score m inner join paper p on m.paper_id = p.id and p.is_missing = ?4 and p.is_shift = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
     int countShiftByQuestionIdAndMarkerIdAndStageAndResultIsNullAndIsMissing(Long questionId, Long id, int ordinal, boolean b);
 
-    @Query(value = "SELECT count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_score m inner join paper p on m.paper_id = p.id and p.is_shift = 0 and p.is_shift_score = 1 where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null", nativeQuery = true)
     int countShiftScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(Long questionId, Long id, int ordinal);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m inner join paper p on m.paper_id = p.id and p.batch_no is not null where m.question_id = ?1 and m.marker_id = ?2", nativeQuery = true)
     long countByQuestionIdAll(Long questionId, Long markId);
 
-    @Query(value = "SELECT count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no is not null and m.is_rejected = false", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_score m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and m.result is null and m.batch_no is not null and m.is_rejected = false", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndResultIsNullAll(Long questionId, Long markerId, int stage);
 
-    @Query(value = "SELECT count(1) from mark_task m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and  m.batch_no is not null and m.is_rejected = true", nativeQuery = true)
+    @Query(value = "SELECT count(1) from mark_task_score m where m.question_id = ?1 and m.marker_id = ?2 and m.stage = ?3 and  m.batch_no is not null and m.is_rejected = true", nativeQuery = true)
     int countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrue(Long questionId, Long markerId, int ordinal);
 
-    @Query(value = "select * from mark_task where work_id = ?1 and subject = ?2 and marker_id = ?3 and stage = ?4 limit 1", nativeQuery = true)
+    @Query(value = "select * from mark_task_score where work_id = ?1 and subject = ?2 and marker_id = ?3 and stage = ?4 limit 1", nativeQuery = true)
     List<MarkTaskScore> findByWorkIdAndSubjectAndMarkerIdAndStageLimit(Long workId, String subject, Long valueOf, int stage);
 
     int countByWorkIdAndSubjectAndStage(Long workId, Subject subject, MarkStage stage);
 
     int countByWorkIdAndStageAndResultNotNull(Long id, MarkStage level);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift = true", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift = true", nativeQuery = true)
     int countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftAndResult(Long workId, String subject, Long valueOf, int stage);
 
-    @Query(value = "select count(1) from mark_task m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift_score = 1", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m inner join paper p on m.paper_id = p.id where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.result is null and p.is_shift_score = 1", nativeQuery = true)
     int countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftScoreAndResult(Long workId, String subject, Long valueOf, int stage);
 
-    @Query(value = "select count(1) from mark_task m where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.is_rejected = 1", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m where m.work_id = ?1 and m.subject = ?2 and m.marker_id = ?3 and m.stage = ?4 and m.is_rejected = 1", nativeQuery = true)
     int findByWorkIdAndSubjectAndMarkerIdAndStageReject(Long workId, String subject, Long valueOf, int stage);
 
-    @Query(value = "select count(1) from mark_task m where m.work_id = ?1", nativeQuery = true)
+    @Query(value = "select count(1) from mark_task_score m where m.work_id = ?1", nativeQuery = true)
     int countByWorkId(Long workId);
 
-    @Query(value = "select id, random_seq_new randomSeqNew from mark_task m where m.work_id = ?1", nativeQuery = true)
+    @Query(value = "select id, random_seq_new randomSeqNew from mark_task_score m where m.work_id = ?1", nativeQuery = true)
     List<Object[]> findAllByWorkId(Long workId);
 
     @Modifying
-    @Query(value = "update mark_task m set m.level = ?1 where m.paper_id = ?2", nativeQuery = true)
+    @Query(value = "update mark_task_score m set m.level = ?1 where m.paper_id = ?2", nativeQuery = true)
     void updateLevelByPaperId(String level, Long id);
 
     @Query("select s.paper from MarkTaskScore s where s.workId = :workId and s.subject = :subject and s.stage = :stage and s.markerId in (:markers)")
     List<Paper> findByWorkIdAndSubjectAndStageAndMarkerIdIn(@Param("workId") Long workId, @Param("subject") Subject subject, @Param("stage") MarkStage stage, @Param("markers") List<Long> markers);
 
-    @Query(value = "select s.paper_id, s.marker_id from mark_task s where s.work_id = :workId and s.subject = :subject and s.stage = :stage", nativeQuery = true)
+    @Query(value = "select s.paper_id, s.marker_id from mark_task_score s where s.work_id = :workId and s.subject = :subject and s.stage = :stage", nativeQuery = true)
     List<Object[]> findByWorkIdAndSubjectAndStage(@Param("workId") Long workId, @Param("subject") String subject, @Param("stage") int stage);
 
     List<MarkTaskScore> findByWorkIdAndSubjectAndSecretNumberAndTest(Long workId, Subject subject, String secretNumber, int id);
@@ -223,4 +223,8 @@ public interface MarkTaskScoreRepo extends JpaRepository<MarkTaskScore, Long>, J
     void updateMarkTaskMarkById(Long markTaskId, Boolean isMark);
 
     void deleteByWorkIdAndSubject(Long workId, Subject subject);
+
+    List<MarkTaskScore> findByPaperId(Long paperId);
+
+    Integer findRandomSeqByWorkIdAndSubjectAndMarkerIdAndQuestionId(Long workId, Subject subject, Long markerId, Long questionId);
 }

+ 4 - 0
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkUserRepo.java

@@ -35,4 +35,8 @@ public interface MarkUserRepo extends JpaRepository<MarkUser,Long>, JpaSpecifica
     void updateByWorkIdAndSubject(Long workId, Subject subject);
 
 	List<MarkUser> findByWorkIdAndSubjectAndRoleAndIdNotIn(Long workId, Subject subject, Role markLeader, List<Long> userMarkLeaders);
+
+	@Modifying
+	@Query("update MarkUser m set m.groupId = null where m.workId = ?1 and m.subject = ?2")
+    void updateGroupIdByWorkIdAndSubject(Long workId, Subject subject);
 }

+ 2 - 0
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkerGroupRepo.java

@@ -15,4 +15,6 @@ public interface MarkerGroupRepo extends JpaRepository<MarkerGroup, Long> {
     List<MarkerGroup> findByWorkIdAndSubjectAndStage(Long workId, Subject subject, MarkStage stage);
 
     void deleteBySubjectAndWorkId(Subject subject, Long workId);
+
+    void deleteByWorkIdAndSubjectAndStage(Long workId, Subject subject, MarkStage init);
 }

+ 8 - 0
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MarkerGroupStudentRepo.java

@@ -4,6 +4,9 @@ import cn.com.qmth.stmms.ms.core.domain.MarkStage;
 import cn.com.qmth.stmms.ms.core.domain.MarkerGroupStudent;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import org.springframework.data.jpa.repository.JpaRepository;
+import org.springframework.data.jpa.repository.Modifying;
+import org.springframework.data.jpa.repository.Query;
+import org.springframework.transaction.annotation.Transactional;
 
 import java.util.List;
 
@@ -12,9 +15,14 @@ import java.util.List;
  */
 public interface MarkerGroupStudentRepo extends JpaRepository<MarkerGroupStudent, Long> {
 
+    @Transactional
+    @Modifying
+    @Query("delete from MarkerGroupStudent s where s.groupId = ?1 and s.used = ?2")
     void deleteByGroupIdAndUsed(Long groupId, boolean b);
 
     List<MarkerGroupStudent> findByWorkIdAndSubjectAndStageAndUsed(Long workId, Subject subject, MarkStage stage, boolean used);
 
     long countByGroupIdAndUsed(Long groupId, boolean used);
+
+    long countByWorkIdAndSubjectAndStageAndUsed(Long workId, Subject subject, MarkStage stage, boolean b);
 }

+ 12 - 0
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/MessageRepo.java

@@ -0,0 +1,12 @@
+package cn.com.qmth.stmms.ms.core.repository;
+
+import cn.com.qmth.stmms.ms.core.domain.Message;
+import org.springframework.data.jpa.repository.JpaRepository;
+import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
+
+/**
+ *
+ */
+public interface MessageRepo extends JpaRepository<Message, Long>, JpaSpecificationExecutor<Message> {
+
+}

+ 73 - 1
stmms-ms-core/src/main/java/cn/com/qmth/stmms/ms/core/repository/PaperRepo.java

@@ -69,6 +69,30 @@ public interface PaperRepo extends JpaRepository<Paper, Long>, JpaSpecificationE
             "GROUP BY p.`level`", nativeQuery = true)
     List<Object[]> countGroupByLevel(Long questionId);
 
+    @Query(value = "SELECT p.`rough_level`,COUNT(*)," +
+            "SUM(p.`is_rejected`)," +
+            "SUM(p.`is_arbitrated`)" +
+            "FROM paper p " +
+            "WHERE p.`question_id` = ? and p.rough_batch_no is not null " +
+            "GROUP BY p.`rough_level`", nativeQuery = true)
+    List<Object[]> countGroupByRoughLevel(Long questionId);
+
+    /**
+     * 管理员-统计科目指定试题的各档位数量
+     *
+     * @param questionId 考区ID
+     * @param test       试评状态
+     */
+    @Query(value = "SELECT p.`rough_level`,COUNT(*)," +
+            "SUM(IF(p.`is_rejected` = 1, 1, 0))," +
+            "SUM(IF(p.`is_arbitrated` = 1, 1, 0))," +
+            "SUM(IF(p.`is_shift` = 1, 1, 0))," +
+            "SUM(IF(p.`is_shift_score` = 1, 1, 0))" +
+            "FROM paper p " +
+            "WHERE p.`question_id` = ? and p.is_missing = false and p.is_test = ? and p.rough_batch_no is not null " +
+            "GROUP BY p.`rough_level` ORDER BY p.`rough_level`", nativeQuery = true)
+    List<Object[]> countGroupByRoughLevelAll(Long questionId, int test);
+
     /**
      * 管理员-统计科目指定试题的各档位数量
      *
@@ -85,6 +109,24 @@ public interface PaperRepo extends JpaRepository<Paper, Long>, JpaSpecificationE
             "GROUP BY p.`level` ORDER BY p.`level`", nativeQuery = true)
     List<Object[]> countGroupByLevelAll(Long questionId, int test);
 
+    /**
+     * 科组长-统计科目指定试题的各档位数量
+     *
+     * @param questionId 考区ID
+     * @param test       试评状态
+     * @param paperIds   试卷ID集合
+     */
+    @Query(value = "SELECT p.`rough_level`,COUNT(*)," +
+            "SUM(IF(p.`is_rejected` = 1, 1, 0))," +
+            "SUM(IF(p.`is_arbitrated` = 1, 1, 0))," +
+            "SUM(IF(p.`is_shift` = 1, 1, 0))," +
+            "SUM(IF(p.`is_shift_score` = 1, 1, 0))" +
+            "FROM paper p " +
+            "WHERE p.`question_id` = :questionId and p.is_missing = false and p.is_test = :test and p.rough_batch_no is not null and p.id in (:paperIds) " +
+            "GROUP BY p.`rough_level` ORDER BY p.`rough_level`", nativeQuery = true)
+    List<Object[]> countGroupByRoughLevelAllAndIdIn(@Param("questionId") Long questionId, @Param("test") int test, @Param("paperIds") List<Long> paperIds);
+
+
     /**
      * 科组长-统计科目指定试题的各档位数量
      *
@@ -196,12 +238,16 @@ public interface PaperRepo extends JpaRepository<Paper, Long>, JpaSpecificationE
 
     int countByWorkIdAndSubjectAndIsMissingFalseAndTest(Long workId, Subject subject, int test);
 
-    int countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndActiveTrueAndBatchNoNotNullAndTest(Long workId, Subject subject, int test);
+    int countByWorkIdAndSubjectAndRoughLevelIsNullAndIsMissingFalseAndRoughBatchNoNotNullAndTest(Long workId, Subject subject, int test);
+
+    int countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndBatchNoNotNullAndTest(Long workId, Subject subject, int test);
 
     int countByWorkIdAndSubjectAndIsMissingFalseAndActiveFalseAndBatchNoIsNullAndTest(Long workId, Subject subject, int test);
 
     int countByWorkIdAndQuestionIdAndSubjectAndIsMissingFalseAndActiveFalseAndBatchNoIsNullAndTest(Long workId, Long questionId, Subject subject, int test);
 
+    int countByWorkIdAndSubjectAndRoughLevelNotNullAndIsMissingFalseAndActiveTrueAndTest(Long workId, Subject subject, int test);
+
     int countByWorkIdAndSubjectAndLevelNotNullAndIsMissingFalseAndActiveTrueAndTest(Long workId, Subject subject, int test);
 
     @Query("select max(p.batchNo) from Paper p where p.questionId = ?1")
@@ -248,9 +294,15 @@ public interface PaperRepo extends JpaRepository<Paper, Long>, JpaSpecificationE
 
     List<Paper> findByWorkIdAndQuestionIdAndSubjectAndLevelAndIsMissingFalseAndActiveTrueAndScoreBatchNoIsNull(Long workId, Long questionId0, Subject subject, String code, Sort sort);
 
+    @Query("select max(p.roughBatchNo) from Paper p where p.workId = ?1 and p.subject = ?2")
+    Long findMaxRoughBatchNoByWorkIdAndSubject(Long workId, Subject subject);
+
     @Query("select max(p.batchNo) from Paper p where p.workId = ?1 and p.subject = ?2")
     Long findMaxBatchNoByWorkIdAndSubject(Long workId, Subject subject);
 
+    @Query(value = "select cast(p.rough_batch_no as char) from paper p where p.work_id = ?1 and p.subject = ?2 order by p.rough_batch_no desc limit 1", nativeQuery = true)
+    List<Object> findRoughBatchNoByWorkIdAndSubject(Long workId, String subject);
+
     @Query(value = "select cast(p.batch_no as char) from paper p where p.work_id = ?1 and p.subject = ?2 order by p.batch_no desc limit 1", nativeQuery = true)
     List<Object> findBatchNoByWorkIdAndSubject(Long workId, String subject);
 
@@ -319,4 +371,24 @@ public interface PaperRepo extends JpaRepository<Paper, Long>, JpaSpecificationE
 
     long countByWorkId(Long workId);
 
+    int countByWorkIdAndSubjectAndIsMissingFalseAndBatchNoIsNullAndTestAndQuestionIdIn(Long workId, Subject subject, int test, List<Long> questionIds);
+
+    int countByWorkIdAndSubjectAndRoughLevelNotNullAndTest(Long workId, Subject subject, int test);
+
+    int countByWorkIdAndSubjectAndLevelNotNullAndTest(Long workId, Subject subject, int test);
+
+    int countByWorkIdAndSubjectAndScoreNotNullAndTest(Long workId, Subject subject, int test);
+
+    int countByWorkIdAndSubjectAndIsMissingFalseAndRoughBatchNoIsNullAndTest(Long workId, Subject subject, int test);
+
+    int countByWorkIdAndSubjectAndIsMissingFalseAndRoughBatchNoIsNullAndTestAndQuestionIdIn(Long workId, Subject subject, int test, List<Long> questionIdsLong);
+
+    int countByWorkIdAndSubjectAndIsMissingFalseAndBatchNoIsNullAndTest(Long workId, Subject subject, int test);
+
+    long countByQuestionIdAndRoughLevelAndSubjectAndWorkId(Long questionId, String valueOf, Subject subject, Long workId);
+
+    long countByWorkIdAndSubjectAndRoughLevelAndTestAndRoughBatchNoNotNull(Long workId, Subject subject, String valueOf, int test);
+
+    long countByWorkIdAndSubjectAndRoughLevelAndIdIn(Long workId, Subject subject, String valueOf, List<Long> finalPaperIds);
+
 }

+ 37 - 15
stmms-ms-log/src/main/java/cn/com/qmth/stmms/ms/log/aop/MarkLogAop.java

@@ -7,7 +7,9 @@ import cn.com.qmth.stmms.ms.commons.utils.EncrypAES;
 import cn.com.qmth.stmms.ms.commons.utils.SqlUtil;
 import cn.com.qmth.stmms.ms.core.cache.ParamCache;
 import cn.com.qmth.stmms.ms.core.domain.*;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskRoughLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskScore;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.domain.user.Role;
 import cn.com.qmth.stmms.ms.core.repository.*;
@@ -80,7 +82,13 @@ public class MarkLogAop {
     LevelConfig levelConfig;
 
     @Autowired
-    MarkTaskRepo markTaskRepo;
+    MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Autowired
+    MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Autowired
+    MarkTaskScoreRepo markTaskScoreRepo;
 
     @Autowired
     MarkingConfig markingConfig;
@@ -206,13 +214,26 @@ public class MarkLogAop {
             oldShiftScore = resultBody.isShiftScore();//旧的改档打分
             daterMineResult = resultBody.getDateMineResult();
         }
-        JSONObject jsonObject = (JSONObject) jsonArgsArray.get(0);
-        Paper paper = JSONObject.parseObject(((JSONObject) jsonObject.get(PAPER)).toJSONString(), Paper.class);
         JSONObject jsonObjectResult = (JSONObject) jsonArgsArray.get(1);
-        LOGGER.info("jsonObject:{},paper:{},jsonObjectResult:{}", jsonObject, paper, jsonObjectResult);
+        MarkStage markStage = MarkStage.valueOf(String.valueOf(jsonObjectResult.get(STAGE)));
+
+        long markTaskId = Long.parseLong(jsonArgsArray.get(0).toString());
+        Paper paper = null;
+        if(markStage.equals(MarkStage.ROUGH_LEVEL)){
+            MarkTaskRoughLevel markTaskRoughLevel = markTaskRoughLevelRepo.findOne(markTaskId);
+            paper = markTaskRoughLevel.getPaper();
+        } else if(markStage.equals(MarkStage.LEVEL)){
+            MarkTaskLevel markTaskLevel = markTaskLevelRepo.findOne(markTaskId);
+            paper = markTaskLevel.getPaper();
+        } else if(markStage.equals(MarkStage.SCORE)){
+            MarkTaskScore markTaskScore = markTaskScoreRepo.findOne(markTaskId);
+            paper = markTaskScore.getPaper();
+        }
+
+        LOGGER.info("markTaskId:{},paper:{},jsonObjectResult:{}", markTaskId, paper, jsonObjectResult);
         Integer operType = MarkLogOperType.LEVEL.getId();//分档,第一次为分档,之后为回评档位,档位打回后为档位打回回评
         //分档、打分、回评档位、回评分数、档位打回回评start
-        MarkStage markStage = MarkStage.valueOf(String.valueOf(jsonObjectResult.get(STAGE)));
+
         if (markStage.ordinal() == 1 && paper.isMarkByLeader()) {//分档,如果已经有科组长定档,则不允许评卷员再分档
             return;
         } else if (markStage.ordinal() == 1 && oldRejected && !isRejected) {//档位打回回评
@@ -276,7 +297,7 @@ public class MarkLogAop {
         //20191107wangliang加入仲裁自动打回算法 start
         if (markStage.ordinal() == 1 && paper.isArbitrated()) {
             if (ParamCache.levelConfigMap.get(String.valueOf(work.getId())).getAutoCallback() == 1) {//为true则自动打回
-                List<MarkTask> markTasks = markTaskRepo.findByPaperIdAndStage(paper.getId(), markStage);
+                List<MarkTaskLevel> markTasks = markTaskLevelRepo.findByPaperIdAndStage(paper.getId(), markStage);
                 JSONObject js = new JSONObject();
                 js.put("paperId", paper.getId());
                 js.put("type", "autoCallback");
@@ -299,8 +320,8 @@ public class MarkLogAop {
      * @param markTaskJob
      * @param workName
      */
-    public void autoCallback(List<MarkTask> markTasks, int deviation, Paper paper, MarkTaskJob markTaskJob, String workName, String daterMineResult) {
-        List<MarkTask> result = markTasks.stream().filter(x -> Objects.isNull(x.getResult())).collect(Collectors.toList());
+    public void autoCallback(List<MarkTaskLevel> markTasks, int deviation, Paper paper, MarkTaskJob markTaskJob, String workName, String daterMineResult) {
+        List<MarkTaskLevel> result = markTasks.stream().filter(x -> Objects.isNull(x.getResult())).collect(Collectors.toList());
         if (Objects.nonNull(result) && result.size() > 0) {
             LOGGER.info("数据有误,未完成评卷任务");
             markTaskJobRepo.updateMarkTaskJobByVersion(markTaskJob.getId(), markTaskJob.getVersion());
@@ -310,7 +331,7 @@ public class MarkLogAop {
         List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
         Map<String, Integer> levelMap = levels.stream().collect(Collectors.toMap(Level::getCode, Level::getLevelValue));
 
-        Map<Long, String> levelsMap = markTasks.stream().collect(Collectors.toMap(MarkTask::getMarkerId, o -> o.getResult().toUpperCase()));
+        Map<Long, String> levelsMap = markTasks.stream().collect(Collectors.toMap(MarkTaskLevel::getMarkerId, o -> o.getResult().toUpperCase()));
         LOGGER.info("this:{} markLogAop异步回调进来了", this);
         arbitrateCallback.judge(levelsMap, deviation, new ArbitrateResult() {
             @Override
@@ -323,7 +344,7 @@ public class MarkLogAop {
                     List<MarkLog> markLogList = new ArrayList<>();
                     Date date = new Date();
                     for (ArbitrateCallback.Distance d : list) {
-                        for (MarkTask m : markTasks) {
+                        for (MarkTaskLevel m : markTasks) {
                             if (Objects.equals(String.valueOf(d.getC()), m.getResult()) && d.getMarkId().longValue() == m.getMarkerId().longValue()) {
                                 m.setDeviationDirection(MarkingService.calcDeviationDirection(levelMap, m.getResult(), daterMineResult));
                                 m.setRejected(true);
@@ -342,7 +363,7 @@ public class MarkLogAop {
                     }
                     int count = markTaskJobRepo.updateMarkTaskJobByVersion(markTaskJob.getId(), markTaskJob.getVersion());
                     if (count > 0) {
-                        markTaskRepo.save(markTasks);
+                        markTaskLevelRepo.save(markTasks);
                         paperRepo.save(paper);
                         markLogRepo.save(markLogList);
                     }
@@ -406,12 +427,13 @@ public class MarkLogAop {
         token = URLDecoder.decode(token, "UTF-8");
         token = EncrypAES.decrypt(token);
         Object[] args = joinPoint.getArgs(); // 参数值
-        MarkTask markTask = null;
+        // todo 查看是否有阶段,根据阶段查询  20220802
+        MarkTaskLevel markTask = null;
         MarkUser markUser = null;
         if (Objects.nonNull(args) && args.length > 0) {
             for (Object o : args) {
-                if (o instanceof MarkTask) {
-                    markTask = (MarkTask) o;
+                if (o instanceof MarkTaskLevel) {
+                    markTask = (MarkTaskLevel) o;
                     break;
                 }
             }

+ 16 - 12
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/ChangeLevelApi.java

@@ -2,13 +2,14 @@ package cn.com.qmth.stmms.ms.marking.api;
 
 import cn.com.qmth.stmms.ms.commons.web.PageableDTO;
 import cn.com.qmth.stmms.ms.core.domain.*;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskScore;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.repository.*;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import cn.com.qmth.stmms.ms.marking.assembler.ChangeLevelAssembler;
 import cn.com.qmth.stmms.ms.marking.dto.ChangeLevelDTO;
-import cn.com.qmth.stmms.ms.marking.service.MarkingService;
+import cn.com.qmth.stmms.ms.marking.service.MarkingLevelService;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.data.domain.Page;
 import org.springframework.data.domain.Pageable;
@@ -38,14 +39,17 @@ public class ChangeLevelApi {
     @Autowired
     private ChangeLevelRepo changeLevelRepo;
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
 
-    @Autowired
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
+
+    @Resource
     private ChangeLevelAssembler changeLevelAssembler;
 
-    @Autowired
-    private MarkingService markingService;
+    @Resource
+    private MarkingLevelService markingLevelService;
 
     @Autowired
     private MarkLogRepo markLogRepo;
@@ -234,18 +238,18 @@ public class ChangeLevelApi {
             //状态设置
             paper.setShift(true);
             paper.setShiftScore(true);
-            List<MarkTask> markTasks = markTaskRepo.findByPaperIdAndStage(paper.getId(), MarkStage.LEVEL);
+            List<MarkTaskLevel> markTasks = markTaskLevelRepo.findByPaperId(paper.getId());
             List<String> ranges = markTasks.stream().map(m -> m.getMarkerId().toString()).collect(Collectors.toList());
-            markingService.reject(paper, changeLevel.getSuggestLevel(), String.join(",", ranges));
+            markingLevelService.reject(paper, changeLevel.getSuggestLevel(), String.join(",", ranges));
 
             //重置已经打分的数据
-            List<MarkTask> markTasksScore = markTaskRepo.findByPaperIdAndStage(paper.getId(), MarkStage.SCORE);
-            if (markTasksScore != null && markTasksScore.size() > 0) {
+            List<MarkTaskScore> markTasksScore = markTaskScoreRepo.findByPaperId(paper.getId());
+            if (markTasksScore != null && !markTasksScore.isEmpty()) {
                 markTasksScore.forEach(o -> {
                     o.setResult(null);
                     o.setLevel(null);
                 });
-                markTaskRepo.save(markTasksScore);
+                markTaskScoreRepo.save(markTasksScore);
             }
 
             //记录日志

+ 173 - 45
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/MakrerApi.java

@@ -32,6 +32,7 @@ import org.springframework.http.ResponseEntity;
 import org.springframework.util.CollectionUtils;
 import org.springframework.web.bind.annotation.*;
 
+import javax.annotation.Resource;
 import java.math.BigDecimal;
 import java.math.RoundingMode;
 import java.util.*;
@@ -51,8 +52,14 @@ public class MakrerApi {
     @Autowired
     private MarkUserRepo markUserRepo;
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
+    @Resource
+    private MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     @Autowired
     private MarkerAssembler markerAssembler;
@@ -178,10 +185,9 @@ public class MakrerApi {
                 //当前老师当前批次试卷总数
                 long kdtotal;
                 if (levelShowAllPaper == 1) {
-                    kdtotal = markTaskRepo.countByQuestionIdAll(questionId, marker.getId());
+                    kdtotal = markTaskLevelRepo.countByQuestionIdAll(questionId, marker.getId());
                 } else {
-//                    kdtotal = markTaskRepo.countByQuestionId(questionId, finalBatchNo, marker.getId());
-                    kdtotal = markTaskRepo.countByQuestionIdAndBatchNo(questionId, finalBatchNo, marker.getId());
+                    kdtotal = markTaskLevelRepo.countByQuestionIdAndBatchNo(questionId, finalBatchNo, marker.getId());
                 }
                 //当前考区内试卷总数
                 long total = 0;
@@ -206,13 +212,12 @@ public class MakrerApi {
                 //求任务数为null的条数
                 int count;
                 if (levelShowAllPaper == 1) {
-                    count = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndResultIsNullAll(questionId, marker.getId(), MarkStage.LEVEL.ordinal());
+                    count = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResultIsNullAll(questionId, marker.getId(), MarkStage.LEVEL.ordinal());
                 } else {
-                    count = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndResultNull(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), finalBatchNo);
+                    count = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResultNull(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), finalBatchNo);
                 }
                 //查询当前老师打回个数
-//                        int rejectCount = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrueAndIsMissing(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), false);
-                int rejectCount = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrue(questionId, marker.getId(), MarkStage.LEVEL.ordinal());
+                int rejectCount = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrue(questionId, marker.getId(), MarkStage.LEVEL.ordinal());
                 levelStatDTO.setCount(count);
                 levelStatDTO.setRejected(rejectCount);
             }
@@ -243,13 +248,12 @@ public class MakrerApi {
                 //当前老师各档位数量
                 int countNew;
                 if (levelShowAllPaper == 1) {
-                    countNew = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndResultAll(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), String.valueOf(o.getId()));
+                    countNew = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResultAll(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), String.valueOf(o.getId()));
                 } else {
-                    countNew = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndResult(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), String.valueOf(o.getId()), finalBatchNo);
+                    countNew = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResult(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), String.valueOf(o.getId()), finalBatchNo);
                 }
                 o.setCount(countNew);
                 //该档位考区内已定档数量
-//                long gcountNew = paperRepo.countByWorkIdAndSubjectAndQuestionIdAndLevel(marker.getWorkId(), markSubject.getSubject(), questionId, String.valueOf(o.getId()));
                 long gcountNew = paperRepo.countByQuestionIdAndLevelAndSubjectAndWorkId(questionId, String.valueOf(o.getId()), markSubject.getSubject(), marker.getWorkId());
                 o.setGcount((int) gcountNew);
 
@@ -274,6 +278,131 @@ public class MakrerApi {
         return levelStatDTOs;
     }
 
+    /**
+     * 评卷员分档数量及占比数据
+     *
+     * @param marker     评卷员用户id
+     * @param questionId 试题id
+     */
+    @GetMapping("{marker}/stat/totalRoughLevels")
+    public List<LevelStatDTO> totalRoughLevels(@PathVariable MarkUser marker, @RequestParam Long questionId) throws Exception {
+        List<LevelStatDTO> levelStatDTOs = new ArrayList<>();
+        MarkSubject markSubject = markSubjectRepo.findOne(marker.getWorkId() + "-" + marker.getSubject().toString());
+        List<Level> levels = levelRepo.findByWorkId(markSubject.getWorkId());
+        Integer levelShowAllPaper = ParamCache.levelConfigMap.get(String.valueOf(marker.getWorkId())).getLevelShowAllPaper();
+        Integer propDenominator = ParamCache.levelConfigMap.get(String.valueOf(marker.getWorkId())).getPropDenominator();
+        Long batchNo = null;
+        if (levelShowAllPaper == 0) {
+            batchNo = paperRepo.findMaxRoughBatchNoByWorkIdAndSubject(marker.getWorkId(), marker.getSubject());
+        }
+        Long finalBatchNo = batchNo;
+        Future future = myThreadPool.arbitratePoolTaskExecutor.submit(new Callable<Map<String, Long>>() {
+            @Override
+            public Map<String, Long> call() throws Exception {
+                Map<String, Long> map = new HashMap<>();
+                //当前老师当前批次试卷总数
+                long kdtotal = 0;
+                if (levelShowAllPaper == 1) {
+                    kdtotal = markTaskRoughLevelRepo.countByQuestionIdAll(questionId, marker.getId());
+                } else {
+                    kdtotal = markTaskRoughLevelRepo.countByQuestionIdAndBatchNo(questionId, finalBatchNo, marker.getId());
+                }
+
+                //当前考区内试卷总数
+                long total = 0;
+                if (propDenominator == 1) {
+                    // 全部考生
+                    total = paperRepo.countByWorkIdAndQuestionIdAndIsMissingIsFalse(markSubject.getWorkId(), questionId);
+                } else if (propDenominator == 2) {
+                    // 去除缺考考生
+                    total = paperRepo.countByWorkIdAndQuestionIdAndIsMissingIsFalse(markSubject.getWorkId(), questionId);
+                }
+                map.put("kdtotal", kdtotal);
+                map.put("total", total);
+                return map;
+            }
+        });
+        //当前考区各档位定档数量
+        List<Object[]> list = paperRepo.countGroupByRoughLevel(questionId);
+        list.forEach(o -> {
+            LevelStatDTO levelStatDTO = levelStatAssembler.toDTO(o);
+            levelStatDTO.setGcount(levelStatDTO.getCount());
+            if (Objects.isNull(levelStatDTO.getId())) {
+                //求任务数为null的条数
+                int count = 0;
+                if (levelShowAllPaper == 1) {
+                    count = markTaskRoughLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResultIsNullAll(questionId, marker.getId(), markSubject.getStage().ordinal());
+                } else {
+                    count = markTaskRoughLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResultNull(questionId, marker.getId(), markSubject.getStage().ordinal(), finalBatchNo);
+                }
+                //查询当前老师打回个数
+                int rejectCount = markTaskRoughLevelRepo.countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrue(questionId, marker.getId(), markSubject.getStage().ordinal());
+                levelStatDTO.setCount(count);
+                levelStatDTO.setRejected(rejectCount);
+            }
+            levelStatDTOs.add(levelStatDTO);
+        });
+
+        List<String> roughCodes = levels.stream().map(Level::getRoughCode).distinct().collect(Collectors.toList());
+        for (String roughCode : roughCodes) {
+            //所有档位依次比较
+            long count = levelStatDTOs.stream().filter(l -> String.valueOf(l.getId()).equals(roughCode)).count();
+            if (count == 0) {
+                LevelStatDTO dto = new LevelStatDTO();
+                dto.setId(roughCode);
+                dto.setCount(0);
+                dto.setPercent(0.0);
+                levelStatDTOs.add(dto);
+            }
+        }
+        long kdtotal = 0L, total = 0L;
+        if (Objects.nonNull(future) && Objects.nonNull(future.get())) {
+            Map<String, Long> map = (Map<String, Long>) future.get();
+            kdtotal = map.get("kdtotal");
+            total = map.get("total");
+        }
+
+        long finalKdtotal = kdtotal;
+        long finalTotal = total;
+        levelStatDTOs.forEach(o -> {
+            if (o.getId() != null) {
+                //当前老师各档位数量
+                int countNew;
+                if (levelShowAllPaper == 1) {
+                    countNew = markTaskRoughLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResultAll(questionId, marker.getId(), markSubject.getStage().ordinal(), String.valueOf(o.getId()));
+                } else {
+                    countNew = markTaskRoughLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResult(questionId, marker.getId(), markSubject.getStage().ordinal(), String.valueOf(o.getId()), finalBatchNo);
+                }
+                o.setCount(countNew);
+                //该档位考区内已定档数量
+                long gcountNew = paperRepo.countByQuestionIdAndRoughLevelAndSubjectAndWorkId(questionId, String.valueOf(o.getId()), markSubject.getSubject(), marker.getWorkId());
+                o.setGcount((int) gcountNew);
+
+//                o.setPt(levelMap.get(o.getId()).getPt());
+//                o.setKdpt(levelMap.get(o.getId()).getKdpt());
+                o.setPt(0);
+                o.setKdpt(0);
+                double p = finalKdtotal == 0 ? 0 : (double) o.getCount() / finalKdtotal * 100;
+                BigDecimal bd = new BigDecimal(p).setScale(3, RoundingMode.HALF_EVEN);
+                o.setPercent(bd.doubleValue());
+                o.setFinalKdTotal(Math.toIntExact(finalKdtotal));
+
+                o.setGcount(Objects.isNull(o.getGcount()) ? 0 : o.getGcount());
+                double gp = finalTotal == 0 ? 0 : (double) o.getGcount() / finalTotal * 100;
+                BigDecimal gbd = new BigDecimal(gp).setScale(3, RoundingMode.HALF_EVEN);
+                o.setGpercent(gbd.doubleValue());
+                o.setFinalTotal(Math.toIntExact(finalTotal));
+            }
+        });
+        Collections.sort(levelStatDTOs, (o1, o2) -> {
+            if (o1.getId() == null || o2.getId() == null) {
+                return 1;
+            }
+            return o1.getId().toString().compareTo(o2.getId().toString());
+        });
+        return levelStatDTOs;
+    }
+
     /**
      * 评卷员分档数量及占比数据
      *
@@ -299,12 +428,13 @@ public class MakrerApi {
             public Map<String, Long> call() throws Exception {
                 Map<String, Long> map = new HashMap<>();
                 //当前老师当前批次试卷总数
-                long kdtotal;
+                long kdtotal = 0;
                 if (levelShowAllPaper == 1) {
-                    kdtotal = markTaskRepo.countByQuestionIdAll(questionId, marker.getId());
+                    kdtotal = markTaskLevelRepo.countByQuestionIdAll(questionId, marker.getId());
                 } else {
-                    kdtotal = markTaskRepo.countByQuestionIdAndBatchNo(questionId, finalBatchNo, marker.getId());
+                    kdtotal = markTaskLevelRepo.countByQuestionIdAndBatchNo(questionId, finalBatchNo, marker.getId());
                 }
+
                 //当前考区内试卷总数
                 long total = 0;
                 if (propDenominator == 1) {
@@ -326,15 +456,14 @@ public class MakrerApi {
             levelStatDTO.setGcount(levelStatDTO.getCount());
             if (Objects.isNull(levelStatDTO.getId())) {
                 //求任务数为null的条数
-                int count;
+                int count = 0;
                 if (levelShowAllPaper == 1) {
-                    count = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndResultIsNullAll(questionId, marker.getId(), MarkStage.LEVEL.ordinal());
+                    count = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResultIsNullAll(questionId, marker.getId(), MarkStage.LEVEL.ordinal());
                 } else {
-                    count = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndResultNull(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), finalBatchNo);
+                    count = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResultNull(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), finalBatchNo);
                 }
                 //查询当前老师打回个数
-//                        int rejectCount = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrueAndIsMissing(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), false);
-                int rejectCount = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrue(questionId, marker.getId(), MarkStage.LEVEL.ordinal());
+                int rejectCount = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndIsRejectedTrue(questionId, marker.getId(), MarkStage.LEVEL.ordinal());
                 levelStatDTO.setCount(count);
                 levelStatDTO.setRejected(rejectCount);
             }
@@ -365,9 +494,9 @@ public class MakrerApi {
                 //当前老师各档位数量
                 int countNew;
                 if (levelShowAllPaper == 1) {
-                    countNew = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndResultAll(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), String.valueOf(o.getId()));
+                    countNew = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResultAll(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), String.valueOf(o.getId()));
                 } else {
-                    countNew = markTaskRepo.countByQuestionIdAndMarkerIdAndStageAndResult(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), String.valueOf(o.getId()), finalBatchNo);
+                    countNew = markTaskLevelRepo.countByQuestionIdAndMarkerIdAndStageAndResult(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), String.valueOf(o.getId()), finalBatchNo);
                 }
                 o.setCount(countNew);
                 //该档位考区内已定档数量
@@ -417,7 +546,6 @@ public class MakrerApi {
             public Map<String, Long> call() {
                 Map<String, Long> map = new HashMap<>();
                 //当前老师所有的评档次数(不分档位)
-//                long total = paperRepo.countByWorkIdAndQuestionId(markSubject.getWorkId(), questionId);
                 long total = paperRepo.countByQuestionId(questionId);
                 map.put("total", total);
                 return map;
@@ -425,15 +553,13 @@ public class MakrerApi {
         });
         LevelStatDTO levelStatDTO = new LevelStatDTO();
         //求任务数为null的条数
-//        int totalCount = markTaskRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResultIsNullAndIsMissing(questionId, marker.getId(), MarkStage.SCORE.ordinal(), false, batchNo);
-        int totalCount = markTaskRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(questionId, marker.getId(), MarkStage.SCORE.ordinal(), batchNo);
+        int totalCount = markTaskScoreRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(questionId, marker.getId(), MarkStage.SCORE.ordinal(), batchNo);
         levelStatDTO.setCount(totalCount);
         //查询改档
-        int shiftCount = markTaskRepo.countShiftByQuestionIdAndMarkerIdAndStageAndResultIsNullAndIsMissing(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), false);
+        int shiftCount = markTaskLevelRepo.countShiftByQuestionIdAndMarkerIdAndStageAndResultIsNullAndIsMissing(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), false);
         levelStatDTO.setShift(shiftCount);
         //查询改档打分
-//        int shiftScoreCount = markTaskRepo.countShiftScoreByQuestionIdAndMarkerIdAndStageAndResultIsNullAndIsMissing(questionId, marker.getId(), MarkStage.SCORE.ordinal(), false);
-        int shiftScoreCount = markTaskRepo.countShiftScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(questionId, marker.getId(), MarkStage.SCORE.ordinal());
+        int shiftScoreCount = markTaskScoreRepo.countShiftScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(questionId, marker.getId(), MarkStage.SCORE.ordinal());
         levelStatDTO.setShiftScore(shiftScoreCount);
         levelStatDTOs.add(levelStatDTO);
 
@@ -472,9 +598,9 @@ public class MakrerApi {
 
                 int count;
                 if (ParamCache.scoreConfigMap.get(String.valueOf(marker.getWorkId())).getScoreShowAllPaper() == 1) {
-                    count = markTaskRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResultAll(questionId, marker.getId(), MarkStage.SCORE.ordinal(), o.getId().toString());
+                    count = markTaskScoreRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResultAll(questionId, marker.getId(), MarkStage.SCORE.ordinal(), o.getId().toString());
                 } else {
-                    count = markTaskRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResult(questionId, marker.getId(), MarkStage.SCORE.ordinal(), o.getId().toString(), batchNo);
+                    count = markTaskScoreRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResult(questionId, marker.getId(), MarkStage.SCORE.ordinal(), o.getId().toString(), batchNo);
                 }
                 o.setPercent(count == 0 ? 0 : o.getPercent());
                 o.setCount(count);
@@ -510,13 +636,13 @@ public class MakrerApi {
         });
         LevelStatDTO levelStatDTO = new LevelStatDTO();
         //求任务数为null的条数
-        int totalCount = markTaskRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(questionId, marker.getId(), MarkStage.SCORE.ordinal(), batchNo);
+        int totalCount = markTaskScoreRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(questionId, marker.getId(), MarkStage.SCORE.ordinal(), batchNo);
         levelStatDTO.setCount(totalCount);
         //查询改档
-        int shiftCount = markTaskRepo.countShiftByQuestionIdAndMarkerIdAndStageAndResultIsNullAndIsMissing(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), false);
+        int shiftCount = markTaskLevelRepo.countShiftByQuestionIdAndMarkerIdAndStageAndResultIsNullAndIsMissing(questionId, marker.getId(), MarkStage.LEVEL.ordinal(), false);
         levelStatDTO.setShift(shiftCount);
         //查询改档打分
-        int shiftScoreCount = markTaskRepo.countShiftScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(questionId, marker.getId(), MarkStage.SCORE.ordinal());
+        int shiftScoreCount = markTaskScoreRepo.countShiftScoreByQuestionIdAndMarkerIdAndStageAndResultIsNull(questionId, marker.getId(), MarkStage.SCORE.ordinal());
         levelStatDTO.setShiftScore(shiftScoreCount);
         levelStatDTOs.add(levelStatDTO);
 
@@ -556,9 +682,9 @@ public class MakrerApi {
 
                 int count;
                 if (ParamCache.scoreConfigMap.get(String.valueOf(marker.getWorkId())).getScoreShowAllPaper() == 1) {
-                    count = markTaskRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResultAll(questionId, marker.getId(), MarkStage.SCORE.ordinal(), o.getId().toString());
+                    count = markTaskScoreRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResultAll(questionId, marker.getId(), MarkStage.SCORE.ordinal(), o.getId().toString());
                 } else {
-                    count = markTaskRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResult(questionId, marker.getId(), MarkStage.SCORE.ordinal(), o.getId().toString(), batchNo);
+                    count = markTaskScoreRepo.countScoreByQuestionIdAndMarkerIdAndStageAndResult(questionId, marker.getId(), MarkStage.SCORE.ordinal(), o.getId().toString(), batchNo);
                 }
                 o.setPercent(count == 0 ? 0 : o.getPercent());
                 o.setCount(count);
@@ -578,10 +704,10 @@ public class MakrerApi {
         List<QuestionStatDTO> questionStatDTOs = new ArrayList<>();
         List<Object[]> qStats = null;
         MarkSubject markSubject = markSubjectRepo.findOne(marker.getWorkId() + "-" + marker.getSubject().toString());
-        if (markSubject.getStage() == MarkStage.SCORE) {
-            qStats = markTaskRepo.countGroupByQuestion(marker.getId(), markSubject.getStage().ordinal());
-        } else {
-            qStats = markTaskRepo.countGroupByQuestion(marker.getId(), markSubject.getStage().ordinal(), markSubject.getTest());
+        if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+            qStats = markTaskLevelRepo.countGroupByQuestion(marker.getId(), markSubject.getStage().ordinal(), markSubject.getTest());
+        } else if (MarkStage.SCORE.equals(markSubject.getStage())) {
+            qStats = markTaskScoreRepo.countGroupByQuestion(marker.getId(), markSubject.getStage().ordinal());
         }
         if (qStats != null) {
             for (Object[] objects : qStats) {
@@ -595,9 +721,10 @@ public class MakrerApi {
     /**
      * 管理员-各评卷员评卷进度、考区评卷进度
      *
-     * @return
+     * @param workId  工作Id
+     * @param subject 科目
      */
-    @RequestMapping(value = "/stat/progress", method = RequestMethod.GET)
+    @GetMapping("/stat/progress")
     public Map markProgress(@RequestParam Long workId, @RequestParam Subject subject) {
         Map<String, Object> objectMap = new HashMap<>();
         MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + subject.toString());
@@ -611,9 +738,10 @@ public class MakrerApi {
                 String[] uploadStatus = student.getUploadStatus().split(",");
                 for (String s : uploadStatus) {
                     if ("1".equals(s.split(":")[1])) {
-                        if (subject.name().equals(s.split(":")[0])) {
-                            ++c;
+                        if (!subject.name().equals(s.split(":")[0])) {
+                            continue;
                         }
+                        ++c;
                     }
                 }
             }
@@ -639,7 +767,7 @@ public class MakrerApi {
         groupingService.getGroupMarkersProgress(workId, markSubject, userMarkLeaders, null, true, objectMap);
 
         //科组长
-        groupingService.getMakerLeaderProgress(workId, subject, userMarkLeaders, objectMap);
+        groupingService.getMakerLeaderProgress(workId, markSubject, userMarkLeaders, objectMap);
 
         return objectMap;
     }
@@ -670,7 +798,7 @@ public class MakrerApi {
 
         if (isTotalMarkLeader) {
             //科组长
-            groupingService.getMakerLeaderProgress(workId, subject, userMarkLeaders, objectMap);
+            groupingService.getMakerLeaderProgress(workId, markSubject, userMarkLeaders, objectMap);
         }
 
         return objectMap;

+ 230 - 42
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/MarkSubjectApi.java

@@ -1,9 +1,11 @@
 package cn.com.qmth.stmms.ms.marking.api;
 
 import cn.com.qmth.stmms.ms.commons.utils.ServletUtil;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
 import cn.com.qmth.stmms.ms.core.domain.*;
 import cn.com.qmth.stmms.ms.core.domain.user.*;
 import cn.com.qmth.stmms.ms.core.repository.*;
+import cn.com.qmth.stmms.ms.core.vo.Subject;
 import cn.com.qmth.stmms.ms.marking.assembler.LevelStatAssembler;
 import cn.com.qmth.stmms.ms.marking.assembler.QuestionStatAssembler;
 import cn.com.qmth.stmms.ms.marking.dto.LevelStatDTO;
@@ -15,6 +17,7 @@ import com.alibaba.fastjson.JSONObject;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.http.HttpStatus;
 import org.springframework.http.ResponseEntity;
+import org.springframework.transaction.annotation.Transactional;
 import org.springframework.util.CollectionUtils;
 import org.springframework.web.bind.annotation.*;
 
@@ -60,8 +63,14 @@ public class MarkSubjectApi {
     @Autowired
     private TaskPublishSettingRepo taskPublishSettingRepo;
 
-    @Autowired
-    MarkTaskRepo markTaskRepo;
+    @Resource
+    MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Resource
+    MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    MarkTaskScoreRepo markTaskScoreRepo;
 
     @Resource
     MarkerGroupStudentRepo markerGroupStudentRepo;
@@ -72,7 +81,7 @@ public class MarkSubjectApi {
     /**
      * 查询所有科目状态
      *
-     * @param workId
+     * @param workId 工作ID
      * @return
      */
     @RequestMapping(value = "getAllSubjectStage/{workId}", method = RequestMethod.GET)
@@ -80,16 +89,83 @@ public class MarkSubjectApi {
         return markSubjectRepo.findAllByWorkIdAndEnableTrue(workId);
     }
 
+    /**
+     * 查询所有科目状态
+     *
+     * @param workId 工作ID
+     */
+    @Transactional
+    @PostMapping("/go_next_stage")
+    public void goNextStage(@RequestParam Long workId,
+                            @RequestParam Subject subject) {
+        MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + subject.name());
+        if (MarkStage.INIT.equals(markSubject.getStage())) {
+            if (ParamCache.levelConfigMap.get(String.valueOf(workId)).getRoughLevel() == 1) {
+                markSubject.setStage(MarkStage.ROUGH_LEVEL);
+            } else {
+                markSubject.setStage(MarkStage.LEVEL);
+            }
+        } else if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+            markSubject.setStage(MarkStage.LEVEL);
+            //是否有未结束的分档任务
+            int count = paperRepo.countByWorkIdAndSubjectAndRoughLevelIsNullAndIsMissingFalseAndRoughBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
+            if (count > 0) {
+                throw new RuntimeException("没有分档完成");
+            }
+        } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+            markSubject.setStage(MarkStage.SCORE);
+            //是否有未结束的分档任务
+            int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
+            if (count > 0) {
+                throw new RuntimeException("没有分档完成");
+            }
+        }
+        markSubjectRepo.save(markSubject);
+
+        // 清除用户分组
+        markUserRepo.updateGroupIdByWorkIdAndSubject(workId, subject);
+    }
+
     /**
      * 当个评卷科目信息
      *
      * @param markSubjectId 评卷科目id
-     * @return
      */
-    @RequestMapping(value = "{markSubjectId}", method = RequestMethod.GET)
+    @GetMapping("{markSubjectId}")
     public MarkSubject get(@PathVariable String markSubjectId) {
-        MarkSubject subject = markSubjectRepo.findOne(markSubjectId);
-        return subject;
+        MarkSubject markSubject = markSubjectRepo.findOne(markSubjectId);
+        if (markSubject.getTest() == 0) {
+            int count = 0;
+            if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+                count = markTaskRoughLevelRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage());
+            } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+                count = markTaskLevelRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage());
+            }
+            markSubject.setFormal(count > 0);
+        }
+        return markSubject;
+    }
+
+    /**
+     * 该评卷科目进入下一阶段
+     *
+     * @param markSubject 评卷科目id
+     */
+    @PatchMapping("{markSubject}")
+    public void goNext(@PathVariable MarkSubject markSubject, @RequestBody Map map) throws Exception {
+        stageControlService.goNext(markSubject, map);
+    }
+
+    /**
+     * 打分任务发布
+     *
+     * @param markSubject 评卷科目id
+     */
+    @RequestMapping(value = "{markSubject}/publishScore", method = RequestMethod.POST)
+    public void publishScore(@PathVariable MarkSubject markSubject, @RequestBody Map map) throws Exception {
+        Object questionId = map.get("questionId");
+        List<TaskPublishSetting> taskList = JSONObject.parseArray(JSONObject.toJSONString(map.get("taskList")), TaskPublishSetting.class);
+        stageControlService.enterScoreStage(markSubject, taskList, questionId);
     }
 
     /**
@@ -187,6 +263,110 @@ public class MarkSubjectApi {
         return levelStatDTOs;
     }
 
+    /**
+     * 科组长-该评卷科目的分档统计信息
+     *
+     * @param markSubject 评卷科目id
+     * @param questionId  试题id
+     * @return
+     */
+    @GetMapping("{markSubject}/mark_leader/stat/roughLevels")
+    public List<LevelStatDTO> markLeaderRoughLevelStat(@PathVariable MarkSubject markSubject, @RequestParam Long questionId) {
+        Long markerId = ServletUtil.getUserId();
+        List<MarkerGroupLeader> markerGroupLeaders = markerGroupLeaderService.listByWorkIdAndSubjectAndStageAndMarkLeaderId(markSubject.getWorkId(), markSubject, markerId);
+        List<Long> paperIds = null;
+        if (!CollectionUtils.isEmpty(markerGroupLeaders)) {
+            List<Long> markers = markerGroupLeaders.stream().map(MarkerGroupLeader::getMarkerId).distinct().collect(Collectors.toList());
+            paperIds = markerGroupLeaderService.listPaperIdsByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage(), markers);
+        }
+        List<LevelStatDTO> levelStatDTOs = new ArrayList<>();
+        List<Level> levels = levelRepo.findByWorkId(markSubject.getWorkId());
+        List<String> roughCodes = levels.stream().map(Level::getRoughCode).distinct().collect(Collectors.toList());
+        if (CollectionUtils.isEmpty(paperIds)) {
+            paperRepo.countGroupByRoughLevelAll(questionId, markSubject.getTest())
+                    .forEach(o -> levelStatDTOs.add(levelStatAssembler.toDTO(o)));
+            for (String roughCode : roughCodes) {
+                long count = levelStatDTOs.stream().filter(l -> String.valueOf(l.getId()).equals(roughCode)).count();
+                //没有该档位,新增
+                if (count == 0) {
+                    LevelStatDTO dto = new LevelStatDTO();
+                    dto.setId(roughCode);
+                    dto.setCount(0);
+                    dto.setPercent(0.0);
+                    levelStatDTOs.add(dto);
+                }
+            }
+            //当前考区总数
+            long total = paperRepo.countByWorkIdAndQuestionIdAndIsMissingIsFalse(markSubject.getWorkId(), questionId);
+            //所有考区总数
+            long gtotal = paperRepo.countByWorkIdAndSubjectAndIsMissingFalse(markSubject.getWorkId(), markSubject.getSubject());
+            levelStatDTOs.forEach(o -> {
+                if (o.getId() != null) {
+                    //当前考区档位占比
+                    double p = total == 0 ? 0 : (double) o.getCount() / total * 100;
+                    BigDecimal bd = new BigDecimal(p).setScale(3, RoundingMode.HALF_EVEN);
+                    o.setPercent(bd.doubleValue());
+                    //考区阈值
+//                    Level level = levels.stream().filter(l -> l.getCode().equals(o.getId())).collect(Collectors.toList()).get(0);
+                    o.setKdpt(0);
+                    //所有考区档位数量
+                    long gcount = paperRepo.countByWorkIdAndSubjectAndRoughLevelAndTestAndRoughBatchNoNotNull(markSubject.getWorkId(), markSubject.getSubject(), String.valueOf(o.getId()), markSubject.getTest());
+                    o.setGcount((int) gcount);
+                    //所有考区档位占比
+                    double gp = gtotal == 0 ? 0 : (double) o.getGcount() / gtotal * 100;
+                    BigDecimal gbd = new BigDecimal(gp).setScale(3, RoundingMode.HALF_EVEN);
+                    o.setGpercent(gbd.doubleValue());
+                    o.setPt(0);
+                }
+            });
+        } else {
+            paperRepo.countGroupByRoughLevelAllAndIdIn(questionId, markSubject.getTest(), paperIds)
+                    .forEach(o -> levelStatDTOs.add(levelStatAssembler.toDTO(o)));
+            for (String roughCode : roughCodes) {
+                long count = levelStatDTOs.stream().filter(l -> String.valueOf(l.getId()).equals(roughCode)).count();
+                //没有该档位,新增
+                if (count == 0) {
+                    LevelStatDTO dto = new LevelStatDTO();
+                    dto.setId(roughCode);
+                    dto.setCount(0);
+                    dto.setPercent(0.0);
+                    levelStatDTOs.add(dto);
+                }
+            }
+            //当前考区总数
+            long total = paperRepo.countByWorkIdAndQuestionIdAndIdIn(markSubject.getWorkId(), questionId, paperIds);
+            //所有考区总数
+            long gtotal = paperRepo.countByWorkIdAndSubjectAndIdIn(markSubject.getWorkId(), markSubject.getSubject(), paperIds);
+            List<Long> finalPaperIds = paperIds;
+            levelStatDTOs.forEach(o -> {
+                if (o.getId() != null) {
+                    //当前考区档位占比
+                    double p = total == 0 ? 0 : (double) o.getCount() / total * 100;
+                    BigDecimal bd = new BigDecimal(p).setScale(3, RoundingMode.HALF_EVEN);
+                    o.setPercent(bd.doubleValue());
+                    //考区阈值
+//                    Level level = levels.stream().filter(l -> l.getCode().equals(o.getId())).collect(Collectors.toList()).get(0);
+                    o.setKdpt(0);
+                    //所有考区档位数量
+                    long gcount = paperRepo.countByWorkIdAndSubjectAndRoughLevelAndIdIn(markSubject.getWorkId(), markSubject.getSubject(), String.valueOf(o.getId()), finalPaperIds);
+                    o.setGcount((int) gcount);
+                    //所有考区档位占比
+                    double gp = gtotal == 0 ? 0 : (double) o.getGcount() / gtotal * 100;
+                    BigDecimal gbd = new BigDecimal(gp).setScale(3, RoundingMode.HALF_EVEN);
+                    o.setGpercent(gbd.doubleValue());
+                    o.setPt(0);
+                }
+            });
+        }
+        Collections.sort(levelStatDTOs, (o1, o2) -> {
+            if (o1.getId() == null || o2.getId() == null) {
+                return 1;
+            }
+            return o1.getId().toString().compareTo(o2.getId().toString());
+        });
+        return levelStatDTOs;
+    }
+
     /**
      * 科组长-该评卷科目的分档统计信息
      *
@@ -391,11 +571,18 @@ public class MarkSubjectApi {
      * 该评卷科目下的评卷员分组列表
      *
      * @param markSubject 评卷科目id
-     * @return
      */
-    @RequestMapping(value = "{markSubject}/markergroups", method = RequestMethod.GET)
+    @GetMapping("{markSubject}/markergroups")
     public List<MarkerGroup> getMarkerGroups(@PathVariable MarkSubject markSubject) {
-        List<MarkerGroup> markerGroups = markerGroupRepo.findByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage());
+        MarkStage stage = markSubject.getStage();
+        if (MarkStage.INIT.equals(markSubject.getStage())) {
+            if (ParamCache.levelConfigMap.get(String.valueOf(markSubject.getWorkId())).getRoughLevel() == 1) {
+                stage = MarkStage.ROUGH_LEVEL;
+            } else {
+                stage = MarkStage.LEVEL;
+            }
+        }
+        List<MarkerGroup> markerGroups = markerGroupRepo.findByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), stage);
         markerGroups.forEach(m -> {
             long count = markerGroupStudentRepo.countByGroupIdAndUsed(m.getId(), false);
             m.setHasStudent(count > 0);
@@ -409,13 +596,24 @@ public class MarkSubjectApi {
      * @param markSubject 评卷科目id
      * @param markerGroup 评卷组
      */
-    @RequestMapping(value = "{markSubject}/markergroups", method = RequestMethod.POST)
+    @PostMapping("{markSubject}/markergroups")
     public MarkerGroup createMarkerGroup(@PathVariable MarkSubject markSubject, @RequestBody MarkerGroup markerGroup) {
         if (markerGroup.getMarkers().isEmpty()) {
             throw new RuntimeException("不可创建空分组");
         }
-        if (MarkStage.LEVEL == markSubject.getStage() || MarkStage.SCORE == markSubject.getStage()) {
-            int count = markTaskRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage());
+        int count;
+        if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+            count = markTaskRoughLevelRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage());
+            if (count > 0) {
+                throw new RuntimeException("当前阶段已发布任务,不能编辑分组");
+            }
+        } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+            count = markTaskLevelRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage());
+            if (count > 0) {
+                throw new RuntimeException("当前阶段已发布任务,不能编辑分组");
+            }
+        } else if (MarkStage.SCORE.equals(markSubject.getStage())) {
+            count = markTaskScoreRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage());
             if (count > 0) {
                 throw new RuntimeException("当前阶段已发布任务,不能编辑分组");
             }
@@ -423,8 +621,16 @@ public class MarkSubjectApi {
 
         markerGroup.setWorkId(markSubject.getWorkId());
         markerGroup.setSubject(markSubject.getSubject());
-        markerGroup.setStage(markSubject.getStage());
-        return markerGroupLeaderService.save(markerGroup, markSubject.getStage().equals(MarkStage.INIT) ? MarkStage.LEVEL : markSubject.getStage());
+        MarkStage stage = markSubject.getStage();
+        if (markSubject.getStage().equals(MarkStage.INIT)) {
+            if (ParamCache.levelConfigMap.get(String.valueOf(markSubject.getWorkId())).getRoughLevel() == 1) {
+                stage = MarkStage.ROUGH_LEVEL;
+            } else {
+                stage = MarkStage.LEVEL;
+            }
+        }
+        markerGroup.setStage(stage);
+        return markerGroupLeaderService.save(markerGroup);
     }
 
     /**
@@ -433,7 +639,7 @@ public class MarkSubjectApi {
      * @param markSubject 评卷科目ID
      * @param groupId     评卷组ID
      */
-    @PostMapping("/marker_groups_student/{markSubject}/{groupId}")
+    @DeleteMapping("/marker_groups_student/{markSubject}/{groupId}")
     public void deleteMarkerGroupStudent(@PathVariable MarkSubject markSubject, @PathVariable Long groupId) {
         markerGroupStudentRepo.deleteByGroupIdAndUsed(groupId, false);
     }
@@ -520,38 +726,20 @@ public class MarkSubjectApi {
         return totalTaskCount - successTaskCount <= 0;
     }
 
-    /**
-     * 该评卷科目进入下一阶段
-     *
-     * @param markSubject 评卷科目id
-     */
-    @RequestMapping(value = "{markSubject}", method = RequestMethod.PATCH)
-    public void goNext(@PathVariable MarkSubject markSubject, @RequestBody Map map) throws Exception {
-        stageControlService.goNext(markSubject, map);
-    }
-
     /**
      * 检查是否已分档完成
      */
-    @RequestMapping(value = "{markSubject}/canLevel", method = RequestMethod.GET)
+    @GetMapping("{markSubject}/canLevel")
     public Boolean canLevel(@PathVariable MarkSubject markSubject) {
-        int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndActiveTrueAndBatchNoNotNullAndTest(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getTest());
+        int count = 0;
+        if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+            count = paperRepo.countByWorkIdAndSubjectAndRoughLevelIsNullAndIsMissingFalseAndRoughBatchNoNotNullAndTest(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getTest());
+        } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+            count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndBatchNoNotNullAndTest(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getTest());
+        }
         return count <= 0;
     }
 
-
-    /**
-     * 打分任务发布
-     *
-     * @param markSubject 评卷科目id
-     */
-    @RequestMapping(value = "{markSubject}/publishScore", method = RequestMethod.POST)
-    public void publishScore(@PathVariable MarkSubject markSubject, @RequestBody Map map) throws Exception {
-        Object questionId = map.get("questionId");
-        List<TaskPublishSetting> taskList = JSONObject.parseArray(JSONObject.toJSONString(map.get("taskList")), TaskPublishSetting.class);
-        stageControlService.enterScoreStage(markSubject, taskList, questionId);
-    }
-
     /**
      * 查询分档进度
      *
@@ -577,7 +765,7 @@ public class MarkSubjectApi {
      *
      * @param markSubject 评卷科目id
      */
-    @RequestMapping(value = "{markSubject}/areaProgress", method = RequestMethod.GET)
+    @GetMapping("{markSubject}/areaProgress")
     public List<LevleProgressDTO> areaProgress(@PathVariable MarkSubject markSubject) {
         return stageControlService.areaProgress(markSubject);
     }

+ 135 - 338
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/MarkTaskApi.java

@@ -1,26 +1,25 @@
 package cn.com.qmth.stmms.ms.marking.api;
 
-import cn.com.qmth.stmms.ms.commons.config.ScoreConfig;
 import cn.com.qmth.stmms.ms.commons.lock.LockService;
-import cn.com.qmth.stmms.ms.commons.lock.LockType;
 import cn.com.qmth.stmms.ms.commons.utils.ServletUtil;
-import cn.com.qmth.stmms.ms.commons.utils.SqlUtil;
 import cn.com.qmth.stmms.ms.commons.web.PageableDTO;
-import cn.com.qmth.stmms.ms.core.cache.ParamCache;
-import cn.com.qmth.stmms.ms.core.domain.*;
-import cn.com.qmth.stmms.ms.core.domain.enums.TrialEnum;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
-import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.domain.Level;
+import cn.com.qmth.stmms.ms.core.domain.MarkStage;
+import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
+import cn.com.qmth.stmms.ms.core.domain.Paper;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkerGroupLeader;
-import cn.com.qmth.stmms.ms.core.repository.*;
+import cn.com.qmth.stmms.ms.core.repository.LevelRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkSubjectRepo;
+import cn.com.qmth.stmms.ms.core.repository.PaperRepo;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
-import cn.com.qmth.stmms.ms.marking.assembler.MarkTaskAssembler;
 import cn.com.qmth.stmms.ms.marking.assembler.PaperAssembler;
 import cn.com.qmth.stmms.ms.marking.dto.LevelDetailDTO;
 import cn.com.qmth.stmms.ms.marking.dto.MarkTaskDTO;
 import cn.com.qmth.stmms.ms.marking.dto.PaperDTO;
+import cn.com.qmth.stmms.ms.marking.service.MarkTaskLevelService;
+import cn.com.qmth.stmms.ms.marking.service.MarkTaskRoughLevelService;
+import cn.com.qmth.stmms.ms.marking.service.MarkTaskScoreService;
 import cn.com.qmth.stmms.ms.marking.service.MarkerGroupLeaderService;
-import cn.com.qmth.stmms.ms.marking.service.MarkingService;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -35,13 +34,15 @@ import org.springframework.transaction.annotation.Transactional;
 import org.springframework.util.CollectionUtils;
 import org.springframework.web.bind.annotation.*;
 
+import javax.annotation.Resource;
 import javax.persistence.criteria.CriteriaBuilder;
-import javax.persistence.criteria.Join;
-import javax.persistence.criteria.JoinType;
 import javax.persistence.criteria.Predicate;
 import java.math.BigDecimal;
 import java.math.RoundingMode;
-import java.util.*;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Objects;
 import java.util.stream.Collectors;
 
 /**
@@ -53,44 +54,32 @@ import java.util.stream.Collectors;
 public class MarkTaskApi {
     private static Logger LOGGER = LoggerFactory.getLogger(MarkTaskApi.class);
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
-
-    @Autowired
-    private MarkingService markingService;
-
-    @Autowired
-    private MarkTaskAssembler markTaskAssembler;
-
     @Autowired
     private PaperAssembler paperAssembler;
 
     @Autowired
-    ExamQuestionRepo examQuestionRepo;
+    private PaperRepo paperRepo;
 
     @Autowired
-    PaperRepo paperRepo;
+    private LevelRepo levelRepo;
 
     @Autowired
-    MarkUserRepo markUserRepo;
+    private MarkSubjectRepo markSubjectRepo;
 
     @Autowired
-    ScoreConfig scoreConfig;
+    private LockService lockService;
 
-    @Autowired
-    LevelRepo levelRepo;
+    @Resource
+    private MarkerGroupLeaderService markerGroupLeaderService;
 
-    @Autowired
-    MarkSubjectRepo markSubjectRepo;
+    @Resource
+    private MarkTaskRoughLevelService markTaskRoughLevelService;
 
-    @Autowired
-    SqlUtil sqlUtil;
+    @Resource
+    private MarkTaskLevelService markTaskLevelService;
 
-    @Autowired
-    LockService lockService;
-
-    @Autowired
-    MarkerGroupLeaderService markerGroupLeaderService;
+    @Resource
+    private MarkTaskScoreService markTaskScoreService;
 
     /**
      * 评卷员的评卷任务
@@ -100,7 +89,6 @@ public class MarkTaskApi {
      * @param level      档位
      * @param sn         密号
      * @param questionId 试题id
-     * @return
      */
     @RequestMapping(method = RequestMethod.GET)
     public PageableDTO list(@RequestParam Long markerId,
@@ -113,109 +101,13 @@ public class MarkTaskApi {
                             @RequestParam Long questionId,
                             @RequestParam(required = false) String areaCode,
                             Pageable pageable) throws Exception {
-        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
-        MarkUser markUser = markUserRepo.findOne(markerId);
-        Long batchNo = null;
-        Long scoreBatchNo = null;
-        if (stage == MarkStage.LEVEL) {
-            List<Object> batchNos = paperRepo.findBatchNoByWorkIdAndSubject(workId, markUser.getSubject().name());
-            if (batchNos != null && !batchNos.isEmpty()) {
-                Object object = batchNos.get(0);
-                batchNo = Long.valueOf(object.toString());
-            }
-        } else if (stage == MarkStage.SCORE) {
-            List<Object> batchNos = paperRepo.findScoreBatchNoByWorkIdAndSubject(workId, markUser.getSubject().name());
-            if (batchNos != null && !batchNos.isEmpty()) {
-                Object object = batchNos.get(0);
-                scoreBatchNo = Long.valueOf(object.toString());
-            }
-        }
-        Long finalBatchNo = batchNo;
-        Long finalScoreBatchNo = scoreBatchNo;
-        Integer levelShowAllPaper = ParamCache.levelConfigMap.get(String.valueOf(workId)).getLevelShowAllPaper();
-        Integer scoreShowAllPaper = ParamCache.scoreConfigMap.get(String.valueOf(workId)).getScoreShowAllPaper();
-        Specification<MarkTask> specification = (root, query, builder) -> {
-            List<Predicate> predicates = new ArrayList<>();
-            List<Predicate> onPredicates = new ArrayList<>();
-            Join<MarkTask, Paper> join = root.join("paper", JoinType.INNER);
-            if (Objects.nonNull(questionId)) {
-                predicates.add(builder.equal(root.get("questionId"), questionId));
-            }
-            predicates.add(builder.equal(root.get("markerId"), markerId));
-            predicates.add(builder.equal(root.get("stage"), stage));
-            if (level == null) {
-                predicates.add(builder.isNull(root.get("result")));
-                if (stage == MarkStage.SCORE) {
-                    onPredicates.add(builder.equal(join.get("isShift"), false));
-                    onPredicates.add(builder.equal(join.get("isShiftScore"), false));
-                }
-            } else if (stage == MarkStage.LEVEL) {
-                //查询
-                predicates.add(builder.equal(root.get("result"), level));
-                if (levelShowAllPaper == 0) {
-                    if (!Objects.isNull(finalBatchNo)) {
-//                        predicates.add(builder.equal(root.get("paper").get("batchNo"), batchNo));
-                        onPredicates.add(builder.equal(join.get("batchNo"), finalBatchNo));
-                    }
-                }
-            } else if (stage == MarkStage.SCORE) {
-                onPredicates.add(builder.equal(join.get("level"), level));
-                predicates.add(builder.isNotNull(root.get("result")));
-                onPredicates.add(builder.equal(join.get("isShift"), false));
-                if (scoreShowAllPaper == 1) {
-                    onPredicates.add(builder.isNotNull(join.get("scoreBatchNo")));
-                } else {
-                    onPredicates.add(builder.equal(join.get("scoreBatchNo"), finalScoreBatchNo));
-                }
-            }
-            if (isSample != null) {
-                onPredicates.add(builder.equal(join.get("isSample"), isSample));
-            }
-            if (reject != null && reject) {
-                onPredicates.add(builder.equal(join.get("isRejected"), reject));
-            } else {
-                predicates.add(builder.equal(root.get("isRejected"), reject));
-            }
-            onPredicates.add(builder.equal(join.get("active"), true));
-            //过滤考区
-            if (Objects.nonNull(areaCode)) {
-                onPredicates.add(builder.equal(join.get("areaCode"), areaCode));
-            }
-            join.on(onPredicates.toArray(new Predicate[onPredicates.size()]));
-            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
-        };
-        Sort sort = new Sort("randomSeq", "randomSeqNew");
-        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
-        Page<MarkTask> markTasks = markTaskRepo.findAll(specification, pageable1);
-
-        if (Objects.isNull(markTasks) || markTasks.getContent().size() == 0) {
-            if (Objects.nonNull(isSample) && isSample) {
-                ExamQuestion examQuestion = examQuestionRepo.findOne(questionId);
-                MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + examQuestion.getSubject());
-                if (markSubject.getTest() == TrialEnum.DEFAULT.getId()) {
-                    List<Paper> paperList = paperRepo.findSample(level, isSample, false, examQuestion.getSubject().name(), TrialEnum.DEFAULT.getId(), examQuestion.getAreaCode(), examQuestion.getWorkId());
-                    if (Objects.nonNull(paperList) && !paperList.isEmpty()) {
-                        for (Paper p : paperList) {
-                            MarkTask markTask = new MarkTask(markUser, p, stage, 1L);
-                            markTaskDTOs.add(markTaskAssembler.toDTO(markTask));
-                        }
-                    }
-                }
-            }
-        }
-        markTasks.getContent().forEach(m -> {
-            markTaskDTOs.add(markTaskAssembler.toDTO(m));
-        });
-        if (stage == MarkStage.SCORE && Objects.isNull(level)) {
-//            if (Objects.nonNull(scoreConfig) && Objects.nonNull(scoreConfig.getTaskSort()) && Objects.equals("paper", scoreConfig.getTaskSort())) {
-//                Collections.sort(markTaskDTOs, Comparator.comparing(MarkTaskDTO::getPaperId));
-//            } else {
-//                randomSeqNewSort(markTaskDTOs);
-//            }
-        } else if (stage == MarkStage.LEVEL && Objects.isNull(level)) {
-            randomSeqNewSort(markTaskDTOs);
+        if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+            return markTaskRoughLevelService.listMarkTaskLevel(markerId, isSample, reject, level, questionId, areaCode, pageable);
+        } else if (MarkStage.LEVEL.equals(stage)) {
+            return markTaskLevelService.listMarkTaskLevel(markerId, isSample, reject, level, questionId, areaCode, pageable);
+        } else {
+            return markTaskScoreService.listMarkTaskScore(markerId, isSample, reject, level, questionId, areaCode, pageable);
         }
-        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
     }
 
     /**
@@ -232,52 +124,43 @@ public class MarkTaskApi {
                             @RequestParam(required = false) Boolean isShiftScore,
                             @RequestParam Long questionId,
                             Pageable pageable) {
-        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
-        Specification<MarkTask> specification = (root, query, builder) -> {
-            List<Predicate> predicates = new ArrayList<>();
-            predicates.add(builder.equal(root.get("questionId"), questionId));
-            predicates.add(builder.equal(root.get("markerId"), markerId));
-            if (isShift != null) {
-                //查询
-                predicates.add(builder.equal(root.get("paper").get("isShift"), isShift));
-                if (isShift) {
-                    predicates.add(builder.equal(root.get("stage"), MarkStage.LEVEL));
-                    predicates.add(builder.isNull(root.get("result")));
-                }
-            }
-            if (isShiftScore != null && isShiftScore && !isShift) {
-                predicates.add(builder.equal(root.get("paper").get("isShiftScore"), isShiftScore));
-                if (isShiftScore) {
-                    predicates.add(builder.equal(root.get("stage"), MarkStage.SCORE));
-                    predicates.add(builder.isNull(root.get("result")));
-                }
-            }
-            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
-        };
-        Sort sort = new Sort("paper.level", "serialNumber", "randomSeq");
-        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
-        Page<MarkTask> markTasks = markTaskRepo.findAll(specification, pageable1);
-
-        markTasks.getContent().forEach(m -> markTaskDTOs.add(markTaskAssembler.toShiftDTO(m)));
-        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
-    }
 
-    /**
-     * randomSeqNew排序
-     *
-     * @param markTaskDTOs
-     */
-    public void randomSeqNewSort(List<MarkTaskDTO> markTaskDTOs) {
-        boolean isSort = true;
-        for (MarkTaskDTO m : markTaskDTOs) {
-            if (Objects.nonNull(m.getRandomSeq())) {
-                isSort = false;
-                break;
-            }
+        if (isShift != null && isShift) {
+            return markTaskLevelService.shiftLevel(markerId, workId, isShift, isShiftScore, questionId, pageable);
         }
-        if (isSort) {
-            Collections.sort(markTaskDTOs, Comparator.comparing(MarkTaskDTO::getRandomSeqNew));
+        if (isShiftScore != null && isShiftScore && !isShift && isShiftScore) {
+            return markTaskScoreService.shiftScore(markerId, workId, isShift, isShiftScore, questionId, pageable);
         }
+        return null;
+
+//        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+//        Specification<MarkTask> specification = (root, query, builder) -> {
+//            List<Predicate> predicates = new ArrayList<>();
+//            predicates.add(builder.equal(root.get("questionId"), questionId));
+//            predicates.add(builder.equal(root.get("markerId"), markerId));
+//            if (isShift != null) {
+//                //查询
+//                predicates.add(builder.equal(root.get("paper").get("isShift"), isShift));
+//                if (isShift) {
+//                    predicates.add(builder.equal(root.get("stage"), MarkStage.LEVEL));
+//                    predicates.add(builder.isNull(root.get("result")));
+//                }
+//            }
+//            if (isShiftScore != null && isShiftScore && !isShift) {
+//                predicates.add(builder.equal(root.get("paper").get("isShiftScore"), isShiftScore));
+//                if (isShiftScore) {
+//                    predicates.add(builder.equal(root.get("stage"), MarkStage.SCORE));
+//                    predicates.add(builder.isNull(root.get("result")));
+//                }
+//            }
+//            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+//        };
+//        Sort sort = new Sort("paper.level", "serialNumber", "randomSeq");
+//        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
+//        Page<MarkTask> markTasks = markTaskRepo.findAll(specification, pageable1);
+//
+//        markTasks.getContent().forEach(m -> markTaskDTOs.add(markTaskAssembler.toShiftDTO(m)));
+//        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
     }
 
     /**
@@ -286,40 +169,17 @@ public class MarkTaskApi {
      * @param markTask 评卷你任务id
      * @param body     评卷内容
      */
-    @RequestMapping(value = "{markTask}", method = RequestMethod.PATCH)
-    public ResponseEntity marking(@PathVariable MarkTask markTask, @RequestBody HashMap<String, String> body) {
+    @PatchMapping("{markTask}")
+    public ResponseEntity marking(@PathVariable Long markTask, @RequestBody HashMap<String, String> body) {
         MarkStage stage = MarkStage.valueOf(body.get("stage"));
-        String result = body.get("result");
-        boolean oldRejected = markTask.isRejected();
-        boolean oldShift = markTask.getPaper().isShift();
-        boolean oldShiftScore = markTask.getPaper().isShiftScore();
-        if (result == null) {
-            return new ResponseEntity(HttpStatus.BAD_REQUEST);
+        if (stage.equals(MarkStage.ROUGH_LEVEL)) {
+            return markTaskRoughLevelService.markingLevel(markTask, body);
+        } else if (stage.equals(MarkStage.LEVEL)) {
+            return markTaskLevelService.markingLevel(markTask, body);
+        } else if (stage.equals(MarkStage.SCORE)) {
+            return markTaskScoreService.markingScore(markTask, body);
         }
-        switch (stage) {
-            case LEVEL:
-                try {
-                    lockService.waitlock(LockType.LEVEL, markTask.getPaper().getId());
-                    markingService.levelMark(markTask, result);
-                } catch (Exception e) {
-                    throw new RuntimeException("分档异常");
-                } finally {
-                    lockService.unlock(LockType.LEVEL, markTask.getPaper().getId());
-                }
-                break;
-            case SCORE:
-                int score = Integer.parseInt(result);
-                try {
-                    lockService.waitlock(LockType.SCORE, markTask.getPaper().getId());
-                    markingService.scoring(markTask, score);
-                } catch (Exception e) {
-                    throw new RuntimeException("打分异常");
-                } finally {
-                    lockService.unlock(LockType.SCORE, markTask.getPaper().getId());
-                }
-                break;
-        }
-        return new ResponseEntity(markTaskAssembler.toDTO(markTask, oldRejected, oldShift, oldShiftScore), HttpStatus.OK);
+        return null;
     }
 
     /**
@@ -331,40 +191,19 @@ public class MarkTaskApi {
     public ResponseEntity batch(@RequestBody HashMap<String, String> body) {
         MarkStage stage = MarkStage.valueOf(body.get("stage"));
         String markIds = body.get("taskIds");
-        String result = body.get("result");
         if (Objects.isNull(markIds)) {
             throw new RuntimeException("请选择待评试卷");
         }
         String[] ids = markIds.split(",");
         List<MarkTaskDTO> list = new ArrayList<>();
         for (String id : ids) {
-            MarkTask markTask = markTaskRepo.findOne(Long.valueOf(id));
-            boolean oldRejected = markTask.isRejected();
-            boolean oldShift = markTask.getPaper().isShift();
-            boolean oldShiftScore = markTask.getPaper().isShiftScore();
-            if (result == null) {
-                return new ResponseEntity(HttpStatus.BAD_REQUEST);
-            }
-            switch (stage) {
-                case LEVEL:
-                    try {
-                        lockService.waitlock(LockType.LEVEL, markTask.getPaper().getId());
-                        markingService.levelMark(markTask, result);
-                    } catch (Exception e) {
-                        throw new RuntimeException("分档异常");
-                    } finally {
-                        lockService.unlock(LockType.LEVEL, markTask.getPaper().getId());
-                    }
-                    break;
-                case SCORE:
-                    int score = Integer.parseInt(result);
-                    synchronized (this) {
-                        markingService.scoring(markTask, score);
-                    }
-                    break;
+            if (stage.equals(MarkStage.ROUGH_LEVEL)) {
+                return markTaskRoughLevelService.markingLevel(Long.valueOf(id), body);
+            } else if (stage.equals(MarkStage.LEVEL)) {
+                return markTaskLevelService.markingLevel(Long.valueOf(id), body);
+            } else if (stage.equals(MarkStage.SCORE)) {
+                return markTaskScoreService.markingScore(Long.valueOf(id), body);
             }
-            MarkTaskDTO markTaskDTO = markTaskAssembler.toDTO(markTask, oldRejected, oldShift, oldShiftScore);
-            list.add(markTaskDTO);
         }
 
         return new ResponseEntity(list, HttpStatus.OK);
@@ -376,88 +215,63 @@ public class MarkTaskApi {
      * @param markTaskId 评卷你任务id
      * @return
      */
-    @RequestMapping(value = "{markTaskId}/skip", method = RequestMethod.POST)
-    public ResponseEntity skip(@PathVariable Long markTaskId) {
-        MarkTask markTask = markingService.skip(markTaskId);
-        return new ResponseEntity(markTaskAssembler.toDTO(markTask), HttpStatus.OK);
+    @RequestMapping(value = "{stage}/{markTaskId}/skip", method = RequestMethod.POST)
+    public ResponseEntity skip(@PathVariable MarkStage stage, @PathVariable Long markTaskId) {
+        if (stage.equals(MarkStage.ROUGH_LEVEL)) {
+            return markTaskRoughLevelService.skipLevel(markTaskId);
+        } else if (stage.equals(MarkStage.LEVEL)) {
+            return markTaskLevelService.skipLevel(markTaskId);
+        } else if (stage.equals(MarkStage.SCORE)) {
+            return markTaskScoreService.skipScore(markTaskId);
+        }
+        return null;
     }
 
     /**
-     * 跳过评卷任务
+     * 查询标记试卷
      *
      * @param markTaskId 评卷你任务id
      */
-    @RequestMapping(value = "/mark_task", method = RequestMethod.POST)
+    @RequestMapping(value = "/{stage}/mark_task", method = RequestMethod.POST)
     @Transactional
-    public Object markTask(@RequestParam Long markTaskId,
+    public Object markTask(@PathVariable MarkStage stage,
+                           @RequestParam Long markTaskId,
                            @RequestParam Boolean isMark) {
-        markTaskRepo.updateMarkTaskMarkById(markTaskId, isMark);
+        if (stage.equals(MarkStage.ROUGH_LEVEL)) {
+            return markTaskRoughLevelService.updateMarkTaskMarkById(markTaskId, isMark);
+        } else if (stage.equals(MarkStage.LEVEL)) {
+            return markTaskLevelService.updateMarkTaskMarkById(markTaskId, isMark);
+        } else if (stage.equals(MarkStage.SCORE)) {
+            return markTaskScoreService.updateMarkTaskMarkById(markTaskId, isMark);
+        }
         return true;
     }
 
     /**
      * 已评试卷回显
      *
-     * @param markerId
-     * @param stage
-     * @param questionId
-     * @param areaCode
-     * @return
+     * @param markerId   工用ID
+     * @param stage      阶段
+     * @param questionId 考区ID
+     * @param areaCode   考区
      */
-    @RequestMapping(value = "/reviewPaper", method = RequestMethod.GET)
+    @GetMapping("/reviewPaper")
     public List<MarkTaskDTO> reviewPaper(@RequestParam Long markerId,
                                          @RequestParam MarkStage stage,
                                          @RequestParam Long questionId,
                                          @RequestParam(required = false) String areaCode) {
-        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
-        Sort sort = new Sort(Sort.Direction.DESC, "updatedOn");
-        Pageable pageable = new PageRequest(0, 5, sort);
-        Long batchNo = null;
-        Long socreBatchNo = null;
-        if (stage == MarkStage.LEVEL) {
-            batchNo = paperRepo.findByQuestionId(questionId);
-        } else if (stage == MarkStage.SCORE) {
-            socreBatchNo = paperRepo.findScoreBatchNoByQuestionId(questionId);
+        if (stage.equals(MarkStage.ROUGH_LEVEL)) {
+            return markTaskRoughLevelService.reviewPaperLevel(markerId, questionId, areaCode);
+        } else if (stage.equals(MarkStage.LEVEL)) {
+            return markTaskLevelService.reviewPaperLevel(markerId, questionId, areaCode);
+        } else if (stage.equals(MarkStage.SCORE)) {
+            return markTaskScoreService.reviewPaperScore(markerId, questionId, areaCode);
         }
-
-        Long finalBatchNo = batchNo;
-        Long finalSocreBatchNo = socreBatchNo;
-        Specification<MarkTask> specification = (root, query, builder) -> {
-            List<Predicate> predicates = new ArrayList<>();
-            if (Objects.nonNull(questionId)) {
-                predicates.add(builder.equal(root.get("questionId"), questionId));
-            }
-            predicates.add(builder.equal(root.get("markerId"), markerId));
-            predicates.add(builder.equal(root.get("stage"), stage));
-            if (stage == MarkStage.LEVEL) {
-                //查询
-                if (!Objects.isNull(finalBatchNo)) {
-                    predicates.add(builder.equal(root.get("paper").get("batchNo"), finalBatchNo));
-                }
-                predicates.add(builder.isNotNull(root.get("result")));
-                //分档需要过滤标准卷
-                predicates.add(builder.equal(root.get("paper").get("isSample"), false));
-            } else if (stage == MarkStage.SCORE) {
-                predicates.add(builder.isNotNull(root.get("result")));
-                if (!Objects.isNull(finalSocreBatchNo)) {
-                    predicates.add(builder.equal(root.get("paper").get("scoreBatchNo"), finalSocreBatchNo));
-                }
-            }
-            //过滤考区
-            if (Objects.nonNull(areaCode)) {
-                predicates.add(builder.equal(root.get("paper").get("areaCode"), areaCode));
-            }
-            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
-        };
-        Page<MarkTask> markTasks = markTaskRepo.findAll(specification, pageable);
-        markTasks.getContent().forEach(m -> {
-            markTaskDTOs.add(markTaskAssembler.toDTO(m));
-        });
-        return markTaskDTOs;
+        return new ArrayList<>();
     }
 
 
-    @RequestMapping(value = "/kzzReviewPaper", method = RequestMethod.GET)
+    @GetMapping("/kzzReviewPaper")
     public List<PaperDTO> reviewPaper(@RequestParam Long workId,
                                       @RequestParam Subject subject,
                                       @RequestParam Long questionId) {
@@ -467,7 +281,7 @@ public class MarkTaskApi {
         List<MarkerGroupLeader> markerGroupLeaders = markerGroupLeaderService.listByWorkIdAndSubjectAndStageAndMarkLeaderId(markSubject.getWorkId(), markSubject, markerId);
         List<Long> paperIds = null;
         if (!CollectionUtils.isEmpty(markerGroupLeaders)) {
-            List<Long> markers = markerGroupLeaders.stream().map(m -> m.getMarkerId()).distinct().collect(Collectors.toList());
+            List<Long> markers = markerGroupLeaders.stream().map(MarkerGroupLeader::getMarkerId).distinct().collect(Collectors.toList());
             paperIds = markerGroupLeaderService.listPaperIdsByWorkIdAndSubjectAndStage(workId, markSubject.getSubject(), markSubject.getStage(), markers);
         }
         List<Long> finalPaperIds = paperIds;
@@ -522,13 +336,6 @@ public class MarkTaskApi {
                                                 @RequestParam Subject subject,
                                                 @RequestParam(required = false) Long questionId) {
         MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + subject.name());
-        Long markerId = ServletUtil.getUserId();
-        /*List<MarkerGroupLeader> markerGroupLeaders = markerGroupLeaderService.listByWorkIdAndSubjectAndStageAndMarkLeaderId(markSubject.getWorkId(), markSubject, markerId);
-        List<Long> paperIds = null;
-        if (!CollectionUtils.isEmpty(markerGroupLeaders)) {
-            List<Long> markers = markerGroupLeaders.stream().map(m -> m.getMarkerId()).distinct().collect(Collectors.toList());
-            paperIds = markerGroupLeaderService.listPaperIdsByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage(), markers);
-        }*/
 
         List<Level> levels = levelRepo.findByWorkIdOrderByCode(workId);
         List<Paper> papers;
@@ -552,7 +359,7 @@ public class MarkTaskApi {
             //数量
             long count = papers.stream().filter(m -> Objects.nonNull(m.getLevel()) && Objects.equals(level.getCode(), m.getLevel())).count();
             levelDetailDTO.setLevelCount((int) count);
-            BigDecimal prop = papers.size() == 0 ? new BigDecimal("0") : new BigDecimal(String.valueOf(count * 100)).divide(new BigDecimal(String.valueOf(papers.size())), 2, BigDecimal.ROUND_HALF_UP);
+            BigDecimal prop = papers.isEmpty() ? new BigDecimal("0") : new BigDecimal(String.valueOf(count * 100)).divide(new BigDecimal(String.valueOf(papers.size())), 2, BigDecimal.ROUND_HALF_UP);
             //占比
             levelDetailDTO.setLevelProp(prop.doubleValue());
             //预设占比
@@ -564,7 +371,7 @@ public class MarkTaskApi {
             int sumCount = (int) (list.stream().mapToInt(LevelDetailDTO::getLevelCount).sum() + count);
             levelDetailDTO.setCumulateCount(sumCount);
             //累计占比
-            BigDecimal cumulateProp = papers.size() == 0 ? new BigDecimal("0") : new BigDecimal(String.valueOf(sumCount * 100)).divide(new BigDecimal(String.valueOf(papers.size())), 2, BigDecimal.ROUND_HALF_UP);
+            BigDecimal cumulateProp = papers.isEmpty() ? new BigDecimal("0") : new BigDecimal(String.valueOf(sumCount * 100)).divide(new BigDecimal(String.valueOf(papers.size())), 2, BigDecimal.ROUND_HALF_UP);
             levelDetailDTO.setCumulateProp(cumulateProp.doubleValue());
 
             //调整
@@ -595,11 +402,16 @@ public class MarkTaskApi {
      * @param secretNumber 密号
      */
     @RequestMapping(value = "/get_by_secret_number", method = RequestMethod.GET)
-    public List<MarkTask> getBySecretNumber(@RequestParam Long workId,
-                                            @RequestParam Subject subject,
-                                            @RequestParam String secretNumber) {
+    public List getBySecretNumber(@RequestParam Long workId,
+                                  @RequestParam Subject subject,
+                                  @RequestParam String secretNumber) {
         MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + subject);
-        return markTaskRepo.findByWorkIdAndSubjectAndSecretNumberAndTest(workId, subject, secretNumber, markSubject.getTest());
+        if (markSubject.getStage().equals(MarkStage.LEVEL)) {
+            return markTaskLevelService.getBySecretNumberLevel(workId, subject, secretNumber, markSubject.getTest());
+        } else if (markSubject.getStage().equals(MarkStage.SCORE)) {
+            return markTaskScoreService.getBySecretNumberScore(workId, subject, secretNumber, markSubject.getTest());
+        }
+        return null;
     }
 
     /**
@@ -610,32 +422,17 @@ public class MarkTaskApi {
      * @param stage    阶段
      * @param markerId 评卷员ID
      */
-    @RequestMapping(value = "/list_mark_task", method = RequestMethod.GET)
+    @GetMapping("/list_mark_task")
     public PageableDTO listMarkTask(@RequestParam Long workId,
                                     @RequestParam Subject subject,
                                     @RequestParam MarkStage stage,
                                     @RequestParam Long markerId,
                                     Pageable pageable) {
-        /*List<MarkTask> markTasks = markTaskRepo.findByWorkIdAndSubjectAndStageAndMarkerIdAndIsMarkTrue(workId, subject, stage, markerId);
-        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
-        markTasks.forEach(m -> {
-            markTaskDTOs.add(markTaskAssembler.toDTO(m));
-        });
-        return markTaskDTOs;*/
-
-        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
-        Specification<MarkTask> specification = (root, query, builder) -> {
-            List<Predicate> predicates = new ArrayList<>();
-            predicates.add(builder.equal(root.get("workId"), workId));
-            predicates.add(builder.equal(root.get("subject"), subject));
-            predicates.add(builder.equal(root.get("stage"), stage));
-            predicates.add(builder.equal(root.get("markerId"), markerId));
-            predicates.add(builder.equal(root.get("isMark"), true));
-            return builder.and(predicates.toArray(new Predicate[0]));
-        };
-        Page<MarkTask> markTasks = markTaskRepo.findAll(specification, pageable);
-
-        markTasks.getContent().forEach(m -> markTaskDTOs.add(markTaskAssembler.toDTO(m)));
-        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+        if (stage.equals(MarkStage.LEVEL)) {
+            return markTaskLevelService.listMarkedTaskLevel(workId, subject, markerId, pageable);
+        } else if (stage.equals(MarkStage.SCORE)) {
+            return markTaskScoreService.listMarkedTaskScore(workId, subject, markerId, pageable);
+        }
+        return null;
     }
 }

+ 127 - 58
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/PaperApi.java

@@ -8,19 +8,19 @@ import cn.com.qmth.stmms.ms.core.domain.MarkStage;
 import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
 import cn.com.qmth.stmms.ms.core.domain.Paper;
 import cn.com.qmth.stmms.ms.core.domain.enums.TrialEnum;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskRoughLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskScore;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkerGroupLeader;
-import cn.com.qmth.stmms.ms.core.repository.ExamQuestionRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkSubjectRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkTaskRepo;
-import cn.com.qmth.stmms.ms.core.repository.PaperRepo;
+import cn.com.qmth.stmms.ms.core.repository.*;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
-import cn.com.qmth.stmms.ms.marking.assembler.MarkTaskAssembler;
+import cn.com.qmth.stmms.ms.marking.assembler.MarkTaskLevelAssembler;
+import cn.com.qmth.stmms.ms.marking.assembler.MarkTaskRoughLevelAssembler;
+import cn.com.qmth.stmms.ms.marking.assembler.MarkTaskScoreAssembler;
 import cn.com.qmth.stmms.ms.marking.assembler.PaperAssembler;
 import cn.com.qmth.stmms.ms.marking.dto.MarkTaskDTO;
 import cn.com.qmth.stmms.ms.marking.dto.PaperDTO;
-import cn.com.qmth.stmms.ms.marking.service.MarkerGroupLeaderService;
-import cn.com.qmth.stmms.ms.marking.service.MarkingService;
+import cn.com.qmth.stmms.ms.marking.service.*;
 import com.alibaba.fastjson.JSONObject;
 import org.apache.commons.codec.digest.DigestUtils;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -37,6 +37,7 @@ import org.springframework.util.StringUtils;
 import org.springframework.web.bind.annotation.*;
 import org.springframework.web.multipart.MultipartFile;
 
+import javax.annotation.Resource;
 import javax.persistence.criteria.CriteriaBuilder;
 import javax.persistence.criteria.Predicate;
 import javax.servlet.http.HttpServletRequest;
@@ -59,33 +60,54 @@ public class PaperApi {
     @Autowired
     private PaperRepo paperRepo;
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
-
     @Autowired
     private MarkSubjectRepo markSubjectRepo;
 
     @Autowired
-    private MarkTaskAssembler markTaskAssembler;
+    private MarkingLevelService markingLevelService;
 
-    @Autowired
-    private MarkingService markingService;
+    @Resource
+    private MarkingRoughLevelService markingRoughLevelService;
+
+    @Resource
+    private MarkTaskLevelService markTaskLevelService;
+
+    @Resource
+    private MarkTaskScoreService markTaskScoreService;
 
     @Autowired
     ExamQuestionRepo examQuestionRepo;
 
+    @Resource
+    private MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
+
     @Autowired
     SystemConfig systemConfig;
 
     @Autowired
     MarkerGroupLeaderService markerGroupLeaderService;
 
+    @Resource
+    MarkTaskRoughLevelAssembler markTaskRoughLevelAssembler;
+
+    @Resource
+    MarkTaskLevelAssembler markTaskLevelAssembler;
+
+    @Resource
+    MarkTaskScoreAssembler markTaskScoreAssembler;
+
     /**
      * 单个试卷信息
      *
      * @param paperId 试卷id
      */
-    @RequestMapping(value = "{paperId}", method = RequestMethod.GET)
+    @GetMapping("{paperId}")
     public PaperDTO get(@PathVariable Long paperId) {
         return paperAssembler.toDTO(paperRepo.findOne(paperId));
     }
@@ -97,7 +119,7 @@ public class PaperApi {
      * @param sn         密号
      * @param examNumber 准考证号
      */
-    @RequestMapping(value = "/one", method = RequestMethod.GET)
+    @GetMapping(value = "/one")
     public PaperDTO getOne(@RequestParam Long questionId,
                            @RequestParam(required = false) String sn,
                            @RequestParam(required = false) String examNumber) {
@@ -122,24 +144,16 @@ public class PaperApi {
         return paperDTO;
     }
 
-    @RequestMapping(value = "search/byTaskSecretNumber", method = RequestMethod.GET)
+    @GetMapping("search/byTaskSecretNumber")
     public PaperDTO getByTaskSecretNumber(@RequestParam Long questionId,
+                                          @RequestParam MarkStage stage,
                                           @RequestParam String sn) {
-        PaperDTO paperDTO = null;
-        Specification<MarkTask> specification = (root, query, builder) -> {
-            List<Predicate> predicates = new ArrayList<>();
-            predicates.add(builder.equal(root.get("paper").get("questionId"), questionId));
-            if (sn != null) {
-                predicates.add(builder.equal(root.get("secretNumber"), sn));
-            }
-            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
-        };
-        Optional<MarkTask> taskOptional = markTaskRepo.findAll(specification, new PageRequest(0, 1))
-                .getContent().stream().findFirst();
-        if (taskOptional.isPresent()) {
-            paperDTO = paperAssembler.toDTO(taskOptional.get().getPaper());
+        if (MarkStage.LEVEL.equals(stage)) {
+            return markTaskLevelService.getByTaskSecretNumberLevel(questionId, sn);
+        } else if (MarkStage.SCORE.equals(stage)) {
+            return markTaskScoreService.getByTaskSecretNumberLevel(questionId, sn);
         }
-        return paperDTO;
+        return null;
     }
 
     /**
@@ -301,12 +315,21 @@ public class PaperApi {
                     }
                 } else {
                     if (StringUtils.isEmpty(level)) {
-                        predicates.add(builder.isNull(root.get("level")));
+                        if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+                            predicates.add(builder.isNull(root.get("roughLevel")));
+                        } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+                            predicates.add(builder.isNull(root.get("level")));
+                        }
                         //查询当前批次号数据
 //                predicates.add(builder.equal(root.get("batchNo"), batchNo));
                     } else {
-                        predicates.add(builder.equal(root.get("level"), level));
-                        predicates.add(builder.isNotNull(root.get("batchNo")));
+                        if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+                            predicates.add(builder.equal(root.get("roughLevel"), level));
+                            predicates.add(builder.isNotNull(root.get("roughBatchNo")));
+                        } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+                            predicates.add(builder.equal(root.get("level"), level));
+                            predicates.add(builder.isNotNull(root.get("batchNo")));
+                        }
                     }
                 }
                 if (!CollectionUtils.isEmpty(finalPaperIds)) {
@@ -324,7 +347,11 @@ public class PaperApi {
                 predicates.add(builder.equal(root.get("isRejected"), reject));
             }
             if (isSample != null) {
-                predicates.add(builder.equal(root.get("isSample"), isSample));
+                if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+                    predicates.add(builder.equal(root.get("isRoughSample"), isSample));
+                } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+                    predicates.add(builder.equal(root.get("isSample"), isSample));
+                }
             }
             if (markedLogic != null) {
                 predicates.add(builder.equal(root.get("markedLogic"), markedLogic));
@@ -343,11 +370,10 @@ public class PaperApi {
     }
 
     /**
-     * 试卷处理。提交评卷
+     * 科组长试卷处理。提交评卷
      *
      * @param paper 试卷id
      * @param body  试卷信息
-     * @return
      */
     @RequestMapping(value = "{paper}", method = RequestMethod.PATCH)
     @Transactional
@@ -355,21 +381,35 @@ public class PaperApi {
         String action = body.get("action");
         String level = body.get("level");
         String tagged = body.get("tagged");
+        MarkStage stage = MarkStage.valueOf(body.get("stage"));
+        // todo 增加科组长操作的粗分档阶段  20220806
         if (action != null && level != null) {
             if (action.equals("leveling")) {
                 paper.setOneClick(true);
                 paper.setRejectedByLeader(false);
-                markingService.levelMarkPaper(paper, level, false);
+                if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+                    markingRoughLevelService.levelMarkPaper(paper, level, false);
+                } else if (MarkStage.LEVEL.equals(stage)) {
+                    markingLevelService.levelMarkPaper(paper, level, false);
+                }
             } else if (action.equals("sampling")) {
                 paper.setOneClick(false);
                 paper.setRejectedByLeader(false);
-                markingService.levelMarkPaper(paper, level, true);
+                if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+                    markingRoughLevelService.levelMarkPaper(paper, level, true);
+                } else if (MarkStage.LEVEL.equals(stage)) {
+                    markingLevelService.levelMarkPaper(paper, level, true);
+                }
             } else if (action.equals("reject")) {
                 paper.setOneClick(false);
                 paper.setRejectedByLeader(true);
                 //需要打回的评卷员
                 String ranges = body.get("range");
-                markingService.reject(paper, level, ranges);
+                if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+                    markingRoughLevelService.reject(paper, level, ranges);
+                } else if (MarkStage.LEVEL.equals(stage)) {
+                    markingLevelService.reject(paper, level, ranges);
+                }
             }
         }
         if (tagged != null) {
@@ -393,6 +433,7 @@ public class PaperApi {
         String level = body.get("level");
         String tagged = body.get("tagged");
         String paperIds = body.get("paperIds");
+        MarkStage stage = MarkStage.valueOf(body.get("stage"));
         if (paperIds.length() > 0) {
             List<PaperDTO> list = new ArrayList<>();
             String[] ids = paperIds.split(",");
@@ -402,17 +443,29 @@ public class PaperApi {
                     if (action.equals("leveling")) {
                         paper.setOneClick(true);
                         paper.setRejectedByLeader(false);
-                        markingService.levelMarkPaper(paper, level, false);
+                        if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+                            markingRoughLevelService.levelMarkPaper(paper, level, false);
+                        } else if (MarkStage.LEVEL.equals(stage)) {
+                            markingLevelService.levelMarkPaper(paper, level, false);
+                        }
                     } else if (action.equals("sampling")) {
                         paper.setOneClick(false);
                         paper.setRejectedByLeader(false);
-                        markingService.levelMarkPaper(paper, level, true);
+                        if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+                            markingRoughLevelService.levelMarkPaper(paper, level, true);
+                        } else if (MarkStage.LEVEL.equals(stage)) {
+                            markingLevelService.levelMarkPaper(paper, level, true);
+                        }
                     } else if (action.equals("reject")) {
                         paper.setOneClick(false);
                         paper.setRejectedByLeader(true);
                         //需要打回的评卷员
                         String ranges = body.get("range");
-                        markingService.reject(paper, level, ranges);
+                        if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+                            markingRoughLevelService.reject(paper, level, ranges);
+                        } else if (MarkStage.LEVEL.equals(stage)) {
+                            markingLevelService.reject(paper, level, ranges);
+                        }
                     }
                 }
                 if (tagged != null) {
@@ -447,12 +500,12 @@ public class PaperApi {
                 paper.setSample(false);
                 paperRepo.save(paper);
 
-                List<MarkTask> markTasks = markTaskRepo.findByPaperIdAndStage(paper.getId(), MarkStage.LEVEL);
-                for (MarkTask markTask : markTasks) {
+                List<MarkTaskLevel> markTasks = markTaskLevelRepo.findByPaperIdAndStage(paper.getId(), MarkStage.LEVEL);
+                for (MarkTaskLevel markTask : markTasks) {
                     markTask.setResult(null);
                     markTask.setLevel(null);
                     markTask.setSample(false);
-                    markTaskRepo.save(markTask);
+                    markTaskLevelRepo.save(markTask);
                 }
             }
             return new ResponseEntity(true, HttpStatus.OK);
@@ -485,9 +538,19 @@ public class PaperApi {
     @RequestMapping(value = "{paperId}/marktasks", method = RequestMethod.GET)
     public List<MarkTaskDTO> markTasks(@PathVariable Long paperId, @RequestParam MarkStage stage) {
         List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
-        markTaskRepo.findByPaperIdAndStage(paperId, stage).forEach(o -> {
-            markTaskDTOs.add(markTaskAssembler.toDTO(o));
-        });
+        if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+            markTaskRoughLevelRepo.findByPaperId(paperId).forEach(o -> {
+                markTaskDTOs.add(markTaskRoughLevelAssembler.toDTO(o));
+            });
+        } else if (MarkStage.LEVEL.equals(stage)) {
+            markTaskLevelRepo.findByPaperId(paperId).forEach(o -> {
+                markTaskDTOs.add(markTaskLevelAssembler.toDTO(o));
+            });
+        } else if (MarkStage.SCORE.equals(stage)) {
+            markTaskScoreRepo.findByPaperId(paperId).forEach(o -> {
+                markTaskDTOs.add(markTaskScoreAssembler.toDTO(o));
+            });
+        }
         markTaskDTOs.sort(Comparator.comparing(MarkTaskDTO::getMarker));
         return markTaskDTOs;
     }
@@ -502,7 +565,7 @@ public class PaperApi {
      * @param number      号码
      * @param studentName 学生姓名
      */
-    @RequestMapping(value = "/studentScore", method = RequestMethod.GET)
+    @GetMapping("/studentScore")
     public List<Map> markTasks(@RequestParam Long workId,
                                @RequestParam(required = false) Long questionId,
                                @RequestParam(required = false) Subject subject,
@@ -526,14 +589,19 @@ public class PaperApi {
                 } else if (Objects.equals(type, "paper")) {
                     predicates.add(builder.equal(root.get("secretNumber"), number));
                 } else if (Objects.equals(type, "task")) {
-                    List<MarkTask> markTasks = markTaskRepo.findByWorkIdAndSecretNumber(workId, number);
-                    if (markTasks == null || markTasks.size() == 0) {
+                    List<MarkTaskLevel> markTasks = markTaskLevelRepo.findByWorkIdAndSecretNumber(workId, number);
+                    if (markTasks == null || markTasks.isEmpty()) {
+                        List<MarkTaskScore> markScoreTasks = markTaskScoreRepo.findByWorkIdAndSecretNumber(workId, number);
+                        if (markScoreTasks == null || markScoreTasks.isEmpty()) {
+                            predicates.add(builder.isNull(root.get("id")));
+                        } else {
+                            predicates.add(builder.equal(root.get("id"), markScoreTasks.get(0).getPaper().getId()));
+                        }
                         predicates.add(builder.isNull(root.get("id")));
                     } else {
                         predicates.add(builder.equal(root.get("id"), markTasks.get(0).getPaper().getId()));
                     }
                 }
-
             }
             if (!StringUtils.isEmpty(studentName)) {
                 predicates.add(builder.equal(root.get("studentName"), studentName));
@@ -564,17 +632,19 @@ public class PaperApi {
                 subObject.put("imgSrc", paperDTO.getImgSrc());
                 subObject.put("thumbSrc", paperDTO.getImgSrc());
                 subObject.put("sheetSrc", paperDTO.getSheetSrc());
+                // 粗分档明细
+                List<MarkTaskRoughLevel> taskRoughLevels = markTaskRoughLevelRepo.findByPaperIdAndStageNative(paper.getId(), MarkStage.ROUGH_LEVEL);
+                subObject.put("taskRoughLevels", taskRoughLevels.isEmpty() ? null : taskRoughLevels);
                 // 分档明细
-                List<MarkTask> taskLevels = markTaskRepo.findByPaperIdAndStageNative(paper.getId(), MarkStage.LEVEL);
+                List<MarkTaskLevel> taskLevels = markTaskLevelRepo.findByPaperIdAndStageNative(paper.getId(), MarkStage.LEVEL);
                 subObject.put("taskLevels", taskLevels.isEmpty() ? null : taskLevels);
                 // 打分明细
-                List<MarkTask> taskScores = markTaskRepo.findByPaperIdAndStageNative(paper.getId(), MarkStage.SCORE);
+                List<MarkTaskScore> taskScores = markTaskScoreRepo.findByPaperIdAndStageNative(paper.getId(), MarkStage.SCORE);
                 subObject.put("taskScores", taskScores.isEmpty() ? null : taskScores);
                 paperDTOs.add(subObject);
             }
             object.put("papers", paperDTOs);
             mapList.add(object);
-
         }
         return mapList;
     }
@@ -582,8 +652,7 @@ public class PaperApi {
     /**
      * 上传试题列表
      *
-     * @param workId
-     * @throws Exception
+     * @param workId 工作ID
      */
     @RequestMapping(value = "/{workId}/listUploadPaper", method = {RequestMethod.GET})
     public List<Map> uploadPaperFile(@PathVariable Long workId) {

+ 15 - 17
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/api/TaskApi.java

@@ -1,16 +1,8 @@
 package cn.com.qmth.stmms.ms.marking.api;
 
 import cn.com.qmth.stmms.ms.commons.utils.specification.PagingAndSortingDTO;
-import cn.com.qmth.stmms.ms.core.domain.MarkLog;
-import cn.com.qmth.stmms.ms.core.domain.MarkLogOperType;
 import cn.com.qmth.stmms.ms.core.domain.Paper;
-import cn.com.qmth.stmms.ms.core.domain.Work;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
-import cn.com.qmth.stmms.ms.core.domain.user.Role;
-import cn.com.qmth.stmms.ms.core.repository.MarkLogRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkTaskRepo;
-import cn.com.qmth.stmms.ms.core.repository.PaperRepo;
-import cn.com.qmth.stmms.ms.core.repository.WorkRepo;
+import cn.com.qmth.stmms.ms.core.repository.*;
 import cn.com.qmth.stmms.ms.marking.assembler.PaperAssembler;
 import cn.com.qmth.stmms.ms.marking.dto.PaperDTO;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -22,8 +14,12 @@ import org.springframework.web.bind.annotation.RequestMapping;
 import org.springframework.web.bind.annotation.RequestParam;
 import org.springframework.web.bind.annotation.RestController;
 
+import javax.annotation.Resource;
 import javax.persistence.criteria.Predicate;
-import java.util.*;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+import java.util.Objects;
 
 /**
  * @author by xf
@@ -39,8 +35,11 @@ public class TaskApi {
     @Autowired
     private PaperRepo paperRepo;
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     @Autowired
     private MarkLogRepo markLogRepo;
@@ -90,7 +89,7 @@ public class TaskApi {
             return new PagingAndSortingDTO(paperOptional.getNumber(), paperOptional.getSize(), paperOptional.getTotalPages(),
                     paperOptional.getTotalElements(), list);
         } else if ("task".equals(type)) {
-            Specification<MarkTask> specification = (root, query, builder) -> {
+            /*Specification<MarkTask> specification = (root, query, builder) -> {
                 List<Predicate> predicates = new ArrayList<>();
                 predicates.add(builder.equal(root.get("workId"), workId));
                 if (secretNumber != null) {
@@ -107,7 +106,7 @@ public class TaskApi {
                 list.add(paperDto);
             }
             return new PagingAndSortingDTO(taskOptional.getNumber(), taskOptional.getSize(), taskOptional.getTotalPages(),
-                    taskOptional.getTotalElements(), list);
+                    taskOptional.getTotalElements(), list);*/
         }
         return null;
 
@@ -127,11 +126,10 @@ public class TaskApi {
         Paper paper = paperRepo.findOne(paperId);
         paper.reject(null);
         //重评后撤销标准卷
-//        paper.setSample(false);
         String[] range = ranges.split(",");
         Date date = new Date();
         for (String markId : range) {
-            MarkTask markTask = markTaskRepo.findByPaperIdAndMarkerId(paperId, Long.valueOf(markId));
+            /*MarkTask markTask = markTaskRepo.findByPaperIdAndMarkerId(paperId, Long.valueOf(markId));
             if (markTask != null) {
                 markTask.setRejected(true);
                 markTask.setOriginLevel(markTask.getResult());
@@ -149,7 +147,7 @@ public class TaskApi {
             }
             Work work = workRepo.findOne(paper.getWorkId());
             MarkLog markLog = new MarkLog(markTask.getMarkerId(), markTask.getMarkerName(), Role.MARKER, markTask.getSubject(), paper.getExamNumber(), paper.getStudentName(), MarkLogOperType.REEVALUATION_LEVEl.getId(), paper.getWorkId(), paper.getId(), markTask.getStage(), operResult, markTask.getOriginLevel(), MarkLogOperType.REEVALUATION_LEVEl.getName(), work.getName(), date);
-            markLogRepo.save(markLog);
+            markLogRepo.save(markLog);*/
         }
 
         return true;

+ 20 - 25
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/MarkTaskAssembler.java → stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/MarkTaskLevelAssembler.java

@@ -5,44 +5,47 @@ import cn.com.qmth.stmms.ms.commons.config.SystemConfig;
 import cn.com.qmth.stmms.ms.commons.constant.SystemConstant;
 import cn.com.qmth.stmms.ms.commons.utils.MD5Util;
 import cn.com.qmth.stmms.ms.core.cache.ParamCache;
-import cn.com.qmth.stmms.ms.core.domain.*;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.ChangeLevel;
+import cn.com.qmth.stmms.ms.core.domain.MarkLogOperType;
+import cn.com.qmth.stmms.ms.core.domain.Paper;
+import cn.com.qmth.stmms.ms.core.domain.Student;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.repository.ChangeLevelRepo;
 import cn.com.qmth.stmms.ms.core.repository.MarkLogRepo;
 import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
 import cn.com.qmth.stmms.ms.core.repository.StudentRepo;
 import cn.com.qmth.stmms.ms.marking.dto.MarkTaskDTO;
-import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Component;
 
+import javax.annotation.Resource;
 import java.util.Objects;
 
 /**
  * Created by zhengmin on 2016/10/12.
  */
 @Component
-public class MarkTaskAssembler {
+public class MarkTaskLevelAssembler {
 
-    @Autowired
+    @Resource
     private SystemConfig systemConfig;
 
-    @Autowired
+    @Resource
     ImageConfig imageConfig;
 
-    @Autowired
+    @Resource
     StudentRepo studentRepo;
 
-    @Autowired
+    @Resource
     MarkLogRepo markLogRepo;
 
-    @Autowired
+    @Resource
     MarkUserRepo markUserRepo;
 
-    @Autowired
+    @Resource
     ChangeLevelRepo changeLevelRepo;
 
-    public MarkTaskDTO toDTO(MarkTask markTask) {
+    public MarkTaskDTO toDTO(MarkTaskLevel markTask) {
 
         MarkTaskDTO markTaskDTO = null;
         if (markTask != null) {
@@ -56,12 +59,8 @@ public class MarkTaskAssembler {
             markTaskDTO.setUpdatedOn(markTask.getUpdatedOn());
             markTaskDTO.setResult(markTask.getResult());
             Paper paper = markTask.getPaper();
-            if (markTask.getStage() == MarkStage.LEVEL) {
-                markTaskDTO.setLevel(markTask.getResult());
-                markTaskDTO.setOriginLevel(markTask.getOriginLevel() == null ? "" : markTask.getOriginLevel());
-            } else {
-                markTaskDTO.setLevel(paper.getLevel());
-            }
+            markTaskDTO.setLevel(markTask.getResult());
+            markTaskDTO.setOriginLevel(markTask.getOriginLevel() == null ? "" : markTask.getOriginLevel());
             markTaskDTO.setSn(markTask.getSecretNumber());
             markTaskDTO.setRedoLevel(paper.getRedoLevel());
             String imgSrc = null;
@@ -103,7 +102,7 @@ public class MarkTaskAssembler {
         return markTaskDTO;
     }
 
-    public MarkTaskDTO toDTO(MarkTask markTask, boolean oldRejected, boolean oldShift, boolean oldShiftScore) {
+    public MarkTaskDTO toDTO(MarkTaskLevel markTask, boolean oldRejected, boolean oldShift, boolean oldShiftScore) {
         MarkTaskDTO markTaskDTO = null;
         if (markTask != null) {
             markTaskDTO = new MarkTaskDTO();
@@ -114,12 +113,8 @@ public class MarkTaskAssembler {
             markTaskDTO.setUpdatedOn(markTask.getUpdatedOn());
             markTaskDTO.setResult(markTask.getResult());
             Paper paper = markTask.getPaper();
-            if (markTask.getStage() == MarkStage.LEVEL) {
-                markTaskDTO.setLevel(markTask.getResult());
-                markTaskDTO.setOriginLevel(markTask.getOriginLevel());
-            } else {
-                markTaskDTO.setLevel(paper.getLevel());
-            }
+            markTaskDTO.setLevel(markTask.getResult());
+            markTaskDTO.setOriginLevel(markTask.getOriginLevel());
             markTaskDTO.setSn(markTask.getSecretNumber());
             markTaskDTO.setRedoLevel(paper.getRedoLevel());
             String imgSrc = null;
@@ -157,7 +152,7 @@ public class MarkTaskAssembler {
      * @param markTask
      * @return
      */
-    public MarkTaskDTO toShiftDTO(MarkTask markTask) {
+    public MarkTaskDTO toShiftDTO(MarkTaskLevel markTask) {
 
         MarkTaskDTO markTaskDTO = null;
         if (markTask != null) {

+ 209 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/MarkTaskRoughLevelAssembler.java

@@ -0,0 +1,209 @@
+package cn.com.qmth.stmms.ms.marking.assembler;
+
+import cn.com.qmth.stmms.ms.commons.config.ImageConfig;
+import cn.com.qmth.stmms.ms.commons.config.SystemConfig;
+import cn.com.qmth.stmms.ms.commons.constant.SystemConstant;
+import cn.com.qmth.stmms.ms.commons.utils.MD5Util;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
+import cn.com.qmth.stmms.ms.core.domain.ChangeLevel;
+import cn.com.qmth.stmms.ms.core.domain.MarkLogOperType;
+import cn.com.qmth.stmms.ms.core.domain.Paper;
+import cn.com.qmth.stmms.ms.core.domain.Student;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskRoughLevel;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.repository.ChangeLevelRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkLogRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
+import cn.com.qmth.stmms.ms.core.repository.StudentRepo;
+import cn.com.qmth.stmms.ms.marking.dto.MarkTaskDTO;
+import org.springframework.stereotype.Component;
+
+import javax.annotation.Resource;
+import java.util.Objects;
+
+/**
+ * Created by zhengmin on 2016/10/12.
+ */
+@Component
+public class MarkTaskRoughLevelAssembler {
+
+    @Resource
+    private SystemConfig systemConfig;
+
+    @Resource
+    ImageConfig imageConfig;
+
+    @Resource
+    StudentRepo studentRepo;
+
+    @Resource
+    MarkLogRepo markLogRepo;
+
+    @Resource
+    MarkUserRepo markUserRepo;
+
+    @Resource
+    ChangeLevelRepo changeLevelRepo;
+
+    public MarkTaskDTO toDTO(MarkTaskRoughLevel markTask) {
+
+        MarkTaskDTO markTaskDTO = null;
+        if (markTask != null) {
+            markTaskDTO = new MarkTaskDTO();
+            markTaskDTO.setId(markTask.getId());
+            markTaskDTO.setRejected(markTask.isRejected());
+            markTaskDTO.setMarkerId(markTask.getMarkerId());
+            MarkUser markUser = markUserRepo.findOne(markTask.getMarkerId());
+            markTaskDTO.setLoginName(markUser.getLoginName());
+            markTaskDTO.setMarker(markTask.getMarkerName());
+            markTaskDTO.setUpdatedOn(markTask.getUpdatedOn());
+            markTaskDTO.setResult(markTask.getResult());
+            Paper paper = markTask.getPaper();
+            markTaskDTO.setLevel(markTask.getResult());
+            markTaskDTO.setOriginLevel(markTask.getOriginLevel() == null ? "" : markTask.getOriginLevel());
+            markTaskDTO.setSn(markTask.getSecretNumber());
+            markTaskDTO.setRedoLevel(paper.getRedoLevel());
+            String imgSrc = null;
+            String thumbSrc = null;
+            String fileName = paper.getExamNumber();
+            Student student = studentRepo.findByWorkIdAndExamNumber(paper.getWorkId(), paper.getExamNumber());
+            //0:随机码 1:考号
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getNameRule() == 1) {
+                fileName = MD5Util.getImageRuleMd5(paper.getWorkId(), paper.getSubject().ordinal(), student.getAreaCode(), student.getExamNumber(), student.getId());
+            }
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getImageEncrypt() == 1) {
+                imgSrc = systemConfig.getImageUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.IMAGE);
+                thumbSrc = systemConfig.getThumbUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.THUMB);
+            } else {
+                imgSrc = systemConfig.getImageUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+                thumbSrc = systemConfig.getThumbUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+            }
+            markTaskDTO.setThumbSrc(thumbSrc);
+            markTaskDTO.setImgSrc(imgSrc);
+            markTaskDTO.setSample(paper.isSample());
+            markTaskDTO.setMarkByLeader(paper.isMarkByLeader());
+            markTaskDTO.setRandomSeqNew(markTask.getRandomSeqNew());
+            markTaskDTO.setRandomSeq(markTask.getRandomSeq());
+            markTaskDTO.setPaperId(paper.getId());
+            markTaskDTO.setSerialNumber(markTask.getSerialNumber());
+            if (Objects.nonNull(markTask.getDisplayNumber())) {
+                markTaskDTO.setDisplayNumber(markTask.getDisplayNumber() == 1);
+            }
+            markTaskDTO.setShift(paper.isShift());
+            markTaskDTO.setShiftScore(paper.isShiftScore());
+
+            markTaskDTO.setIsRejectedByLeader(paper.isRejectedByLeader() != null && paper.isRejectedByLeader());
+            //打回总次数
+            int rejectedCount = markLogRepo.countByWorkIdAndPaperIdAndOperType(paper.getWorkId(), paper.getId(), Objects.nonNull(paper.isRejectedByLeader()) && paper.isRejectedByLeader() ? MarkLogOperType.CALLBACK_LEVEl.getId() : MarkLogOperType.SYSTEM_CALLBACK_LEVEl.getId());
+            markTaskDTO.setRejectedCount(rejectedCount);
+            markTaskDTO.setDeviationDirection(markTask.getDeviationDirection());
+            markTaskDTO.setMark(markTask.isMark());
+        }
+        return markTaskDTO;
+    }
+
+    public MarkTaskDTO toDTO(MarkTaskRoughLevel markTask, boolean oldRejected, boolean oldShift, boolean oldShiftScore) {
+        MarkTaskDTO markTaskDTO = null;
+        if (markTask != null) {
+            markTaskDTO = new MarkTaskDTO();
+            markTaskDTO.setId(markTask.getId());
+            markTaskDTO.setRejected(markTask.isRejected());
+            markTaskDTO.setOldRejected(oldRejected);
+            markTaskDTO.setMarker(markTask.getMarkerName());
+            markTaskDTO.setUpdatedOn(markTask.getUpdatedOn());
+            markTaskDTO.setResult(markTask.getResult());
+            Paper paper = markTask.getPaper();
+            markTaskDTO.setLevel(markTask.getResult());
+            markTaskDTO.setOriginLevel(markTask.getOriginLevel());
+            markTaskDTO.setSn(markTask.getSecretNumber());
+            markTaskDTO.setRedoLevel(paper.getRedoLevel());
+            String imgSrc = null;
+            String thumbSrc = null;
+            String fileName = paper.getExamNumber();
+            Student student = studentRepo.findByWorkIdAndExamNumber(paper.getWorkId(), paper.getExamNumber());
+            //0:随机码 1:考号
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getNameRule() == 1) {
+                fileName = MD5Util.getImageRuleMd5(paper.getWorkId(), paper.getSubject().ordinal(), student.getAreaCode(), student.getExamNumber(), student.getId());
+            }
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getImageEncrypt() == 1) {
+                imgSrc = systemConfig.getImageUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.IMAGE);
+                thumbSrc = systemConfig.getThumbUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.THUMB);
+            } else {
+                imgSrc = systemConfig.getImageUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+                thumbSrc = systemConfig.getThumbUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+            }
+            markTaskDTO.setThumbSrc(thumbSrc);
+            markTaskDTO.setImgSrc(imgSrc);
+            markTaskDTO.setSample(paper.isSample());
+            markTaskDTO.setMarkByLeader(paper.isMarkByLeader());
+            markTaskDTO.setRandomSeqNew(markTask.getRandomSeqNew());
+            markTaskDTO.setRandomSeq(markTask.getRandomSeq());
+            markTaskDTO.setPaperId(paper.getId());
+            markTaskDTO.setShift(oldShift);
+            markTaskDTO.setShiftScore(oldShiftScore);
+            markTaskDTO.setDateMineResult(markTask.getDateMineResult());
+        }
+        return markTaskDTO;
+    }
+
+    /**
+     * 改档,改档打分
+     *
+     * @param markTask
+     * @return
+     */
+    public MarkTaskDTO toShiftDTO(MarkTaskRoughLevel markTask) {
+
+        MarkTaskDTO markTaskDTO = null;
+        if (markTask != null) {
+            markTaskDTO = new MarkTaskDTO();
+            markTaskDTO.setId(markTask.getId());
+            markTaskDTO.setRejected(markTask.isRejected());
+            markTaskDTO.setMarkerId(markTask.getMarkerId());
+            markTaskDTO.setMarker(markTask.getMarkerName());
+            markTaskDTO.setUpdatedOn(markTask.getUpdatedOn());
+            markTaskDTO.setResult(markTask.getResult());
+            Paper paper = markTask.getPaper();
+            if (paper.isShift()) {
+                markTaskDTO.setLevel(markTask.getResult());
+                ChangeLevel changeLevel = changeLevelRepo.findByWorkIdAndSubjectAndPaperIdAndAuditStatusAndIsCurr(markTask.getWorkId(), markTask.getSubject().name(), paper.getId());
+                markTaskDTO.setOriginLevel(changeLevel != null ? changeLevel.getOriginalLevel() : "");
+            }
+            if (paper.isShiftScore()) {
+                markTaskDTO.setLevel(paper.getLevel());
+            }
+            markTaskDTO.setSn(markTask.getSecretNumber());
+            markTaskDTO.setRedoLevel(paper.getRedoLevel());
+            String imgSrc = null;
+            String thumbSrc = null;
+            String fileName = paper.getExamNumber();
+            Student student = studentRepo.findByWorkIdAndExamNumber(paper.getWorkId(), paper.getExamNumber());
+            //0:随机码 1:考号
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getNameRule() == 1) {
+                fileName = MD5Util.getImageRuleMd5(paper.getWorkId(), paper.getSubject().ordinal(), student.getAreaCode(), student.getExamNumber(), student.getId());
+            }
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getImageEncrypt() == 1) {
+                imgSrc = systemConfig.getImageUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.IMAGE);
+                thumbSrc = systemConfig.getThumbUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.THUMB);
+            } else {
+                imgSrc = systemConfig.getImageUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+                thumbSrc = systemConfig.getThumbUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+            }
+            markTaskDTO.setThumbSrc(thumbSrc);
+            markTaskDTO.setImgSrc(imgSrc);
+            markTaskDTO.setSample(paper.isSample());
+            markTaskDTO.setMarkByLeader(paper.isMarkByLeader());
+            markTaskDTO.setRandomSeqNew(markTask.getRandomSeqNew());
+            markTaskDTO.setRandomSeq(markTask.getRandomSeq());
+            markTaskDTO.setPaperId(paper.getId());
+            markTaskDTO.setSerialNumber(markTask.getSerialNumber());
+            if (Objects.nonNull(markTask.getDisplayNumber())) {
+                markTaskDTO.setDisplayNumber(markTask.getDisplayNumber() == 1);
+            }
+            markTaskDTO.setShift(paper.isShift());
+            markTaskDTO.setShiftScore(paper.isShiftScore());
+        }
+        return markTaskDTO;
+    }
+}

+ 206 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/MarkTaskScoreAssembler.java

@@ -0,0 +1,206 @@
+package cn.com.qmth.stmms.ms.marking.assembler;
+
+import cn.com.qmth.stmms.ms.commons.config.ImageConfig;
+import cn.com.qmth.stmms.ms.commons.config.SystemConfig;
+import cn.com.qmth.stmms.ms.commons.constant.SystemConstant;
+import cn.com.qmth.stmms.ms.commons.utils.MD5Util;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
+import cn.com.qmth.stmms.ms.core.domain.ChangeLevel;
+import cn.com.qmth.stmms.ms.core.domain.MarkLogOperType;
+import cn.com.qmth.stmms.ms.core.domain.Paper;
+import cn.com.qmth.stmms.ms.core.domain.Student;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskScore;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.repository.ChangeLevelRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkLogRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
+import cn.com.qmth.stmms.ms.core.repository.StudentRepo;
+import cn.com.qmth.stmms.ms.marking.dto.MarkTaskDTO;
+import org.springframework.stereotype.Component;
+
+import javax.annotation.Resource;
+import java.util.Objects;
+
+/**
+ * Created by zhengmin on 2016/10/12.
+ */
+@Component
+public class MarkTaskScoreAssembler {
+
+    @Resource
+    private SystemConfig systemConfig;
+
+    @Resource
+    ImageConfig imageConfig;
+
+    @Resource
+    StudentRepo studentRepo;
+
+    @Resource
+    MarkLogRepo markLogRepo;
+
+    @Resource
+    MarkUserRepo markUserRepo;
+
+    @Resource
+    ChangeLevelRepo changeLevelRepo;
+
+    public MarkTaskDTO toDTO(MarkTaskScore markTask) {
+
+        MarkTaskDTO markTaskDTO = null;
+        if (markTask != null) {
+            markTaskDTO = new MarkTaskDTO();
+            markTaskDTO.setId(markTask.getId());
+            markTaskDTO.setRejected(markTask.isRejected());
+            markTaskDTO.setMarkerId(markTask.getMarkerId());
+            MarkUser markUser = markUserRepo.findOne(markTask.getMarkerId());
+            markTaskDTO.setLoginName(markUser.getLoginName());
+            markTaskDTO.setMarker(markTask.getMarkerName());
+            markTaskDTO.setUpdatedOn(markTask.getUpdatedOn());
+            markTaskDTO.setResult(markTask.getResult());
+            Paper paper = markTask.getPaper();
+            markTaskDTO.setLevel(paper.getLevel());
+            markTaskDTO.setSn(markTask.getSecretNumber());
+            markTaskDTO.setRedoLevel(paper.getRedoLevel());
+            String imgSrc = null;
+            String thumbSrc = null;
+            String fileName = paper.getExamNumber();
+            Student student = studentRepo.findByWorkIdAndExamNumber(paper.getWorkId(), paper.getExamNumber());
+            //0:随机码 1:考号
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getNameRule() == 1) {
+                fileName = MD5Util.getImageRuleMd5(paper.getWorkId(), paper.getSubject().ordinal(), student.getAreaCode(), student.getExamNumber(), student.getId());
+            }
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getImageEncrypt() == 1) {
+                imgSrc = systemConfig.getImageUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.IMAGE);
+                thumbSrc = systemConfig.getThumbUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.THUMB);
+            } else {
+                imgSrc = systemConfig.getImageUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+                thumbSrc = systemConfig.getThumbUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+            }
+            markTaskDTO.setThumbSrc(thumbSrc);
+            markTaskDTO.setImgSrc(imgSrc);
+            markTaskDTO.setSample(paper.isSample());
+            markTaskDTO.setMarkByLeader(paper.isMarkByLeader());
+            markTaskDTO.setRandomSeqNew(markTask.getRandomSeqNew());
+            markTaskDTO.setRandomSeq(markTask.getRandomSeq());
+            markTaskDTO.setPaperId(paper.getId());
+            markTaskDTO.setSerialNumber(markTask.getSerialNumber());
+            if (Objects.nonNull(markTask.getDisplayNumber())) {
+                markTaskDTO.setDisplayNumber(markTask.getDisplayNumber() == 1);
+            }
+            markTaskDTO.setShift(paper.isShift());
+            markTaskDTO.setShiftScore(paper.isShiftScore());
+
+            markTaskDTO.setIsRejectedByLeader(paper.isRejectedByLeader() != null && paper.isRejectedByLeader());
+            //打回总次数
+            int rejectedCount = markLogRepo.countByWorkIdAndPaperIdAndOperType(paper.getWorkId(), paper.getId(), Objects.nonNull(paper.isRejectedByLeader()) && paper.isRejectedByLeader() ? MarkLogOperType.CALLBACK_LEVEl.getId() : MarkLogOperType.SYSTEM_CALLBACK_LEVEl.getId());
+            markTaskDTO.setRejectedCount(rejectedCount);
+            markTaskDTO.setDeviationDirection(markTask.getDeviationDirection());
+            markTaskDTO.setMark(markTask.isMark());
+        }
+        return markTaskDTO;
+    }
+
+    public MarkTaskDTO toDTO(MarkTaskScore markTask, boolean oldRejected, boolean oldShift, boolean oldShiftScore) {
+        MarkTaskDTO markTaskDTO = null;
+        if (markTask != null) {
+            markTaskDTO = new MarkTaskDTO();
+            markTaskDTO.setId(markTask.getId());
+            markTaskDTO.setRejected(markTask.isRejected());
+            markTaskDTO.setOldRejected(oldRejected);
+            markTaskDTO.setMarker(markTask.getMarkerName());
+            markTaskDTO.setUpdatedOn(markTask.getUpdatedOn());
+            markTaskDTO.setResult(markTask.getResult());
+            Paper paper = markTask.getPaper();
+            markTaskDTO.setLevel(paper.getLevel());
+            markTaskDTO.setSn(markTask.getSecretNumber());
+            markTaskDTO.setRedoLevel(paper.getRedoLevel());
+            String imgSrc = null;
+            String thumbSrc = null;
+            String fileName = paper.getExamNumber();
+            Student student = studentRepo.findByWorkIdAndExamNumber(paper.getWorkId(), paper.getExamNumber());
+            //0:随机码 1:考号
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getNameRule() == 1) {
+                fileName = MD5Util.getImageRuleMd5(paper.getWorkId(), paper.getSubject().ordinal(), student.getAreaCode(), student.getExamNumber(), student.getId());
+            }
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getImageEncrypt() == 1) {
+                imgSrc = systemConfig.getImageUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.IMAGE);
+                thumbSrc = systemConfig.getThumbUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.THUMB);
+            } else {
+                imgSrc = systemConfig.getImageUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+                thumbSrc = systemConfig.getThumbUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+            }
+            markTaskDTO.setThumbSrc(thumbSrc);
+            markTaskDTO.setImgSrc(imgSrc);
+            markTaskDTO.setSample(paper.isSample());
+            markTaskDTO.setMarkByLeader(paper.isMarkByLeader());
+            markTaskDTO.setRandomSeqNew(markTask.getRandomSeqNew());
+            markTaskDTO.setRandomSeq(markTask.getRandomSeq());
+            markTaskDTO.setPaperId(paper.getId());
+            markTaskDTO.setShift(oldShift);
+            markTaskDTO.setShiftScore(oldShiftScore);
+            markTaskDTO.setDateMineResult(markTask.getDateMineResult());
+        }
+        return markTaskDTO;
+    }
+
+    /**
+     * 改档,改档打分
+     *
+     * @param markTask
+     * @return
+     */
+    public MarkTaskDTO toShiftDTO(MarkTaskScore markTask) {
+
+        MarkTaskDTO markTaskDTO = null;
+        if (markTask != null) {
+            markTaskDTO = new MarkTaskDTO();
+            markTaskDTO.setId(markTask.getId());
+            markTaskDTO.setRejected(markTask.isRejected());
+            markTaskDTO.setMarkerId(markTask.getMarkerId());
+            markTaskDTO.setMarker(markTask.getMarkerName());
+            markTaskDTO.setUpdatedOn(markTask.getUpdatedOn());
+            markTaskDTO.setResult(markTask.getResult());
+            Paper paper = markTask.getPaper();
+            if (paper.isShift()) {
+                markTaskDTO.setLevel(markTask.getResult());
+                ChangeLevel changeLevel = changeLevelRepo.findByWorkIdAndSubjectAndPaperIdAndAuditStatusAndIsCurr(markTask.getWorkId(), markTask.getSubject().name(), paper.getId());
+                markTaskDTO.setOriginLevel(changeLevel != null ? changeLevel.getOriginalLevel() : "");
+            }
+            if (paper.isShiftScore()) {
+                markTaskDTO.setLevel(paper.getLevel());
+            }
+            markTaskDTO.setSn(markTask.getSecretNumber());
+            markTaskDTO.setRedoLevel(paper.getRedoLevel());
+            String imgSrc = null;
+            String thumbSrc = null;
+            String fileName = paper.getExamNumber();
+            Student student = studentRepo.findByWorkIdAndExamNumber(paper.getWorkId(), paper.getExamNumber());
+            //0:随机码 1:考号
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getNameRule() == 1) {
+                fileName = MD5Util.getImageRuleMd5(paper.getWorkId(), paper.getSubject().ordinal(), student.getAreaCode(), student.getExamNumber(), student.getId());
+            }
+            if (ParamCache.collectConfigMap.get(String.valueOf(paper.getWorkId())).getImageEncrypt() == 1) {
+                imgSrc = systemConfig.getImageUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.IMAGE);
+                thumbSrc = systemConfig.getThumbUrl(paper.getWorkId(), paper.getSubject().ordinal(), student.getId(), SystemConstant.THUMB);
+            } else {
+                imgSrc = systemConfig.getImageUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+                thumbSrc = systemConfig.getThumbUrl(markTask.getWorkId(), paper.getSubject().toString(), paper.getAreaCode(), fileName);
+            }
+            markTaskDTO.setThumbSrc(thumbSrc);
+            markTaskDTO.setImgSrc(imgSrc);
+            markTaskDTO.setSample(paper.isSample());
+            markTaskDTO.setMarkByLeader(paper.isMarkByLeader());
+            markTaskDTO.setRandomSeqNew(markTask.getRandomSeqNew());
+            markTaskDTO.setRandomSeq(markTask.getRandomSeq());
+            markTaskDTO.setPaperId(paper.getId());
+            markTaskDTO.setSerialNumber(markTask.getSerialNumber());
+            if (Objects.nonNull(markTask.getDisplayNumber())) {
+                markTaskDTO.setDisplayNumber(markTask.getDisplayNumber() == 1);
+            }
+            markTaskDTO.setShift(paper.isShift());
+            markTaskDTO.setShiftScore(paper.isShiftScore());
+        }
+        return markTaskDTO;
+    }
+}

+ 6 - 7
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/PaperAssembler.java

@@ -6,12 +6,13 @@ import cn.com.qmth.stmms.ms.commons.constant.SystemConstant;
 import cn.com.qmth.stmms.ms.commons.utils.MD5Util;
 import cn.com.qmth.stmms.ms.core.cache.ParamCache;
 import cn.com.qmth.stmms.ms.core.domain.*;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
 import cn.com.qmth.stmms.ms.core.repository.*;
 import cn.com.qmth.stmms.ms.marking.dto.PaperDTO;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Component;
 
+import javax.annotation.Resource;
 import java.util.List;
 import java.util.Map;
 import java.util.Objects;
@@ -23,11 +24,8 @@ import java.util.stream.Collectors;
 @Component
 public class PaperAssembler {
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
-
-    @Autowired
-    private MarkTaskAssembler markTaskAssembler;
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
 
     @Autowired
     private SystemConfig systemConfig;
@@ -78,6 +76,7 @@ public class PaperAssembler {
             paperDTO.setExamNumber(paper.getExamNumber());
             paperDTO.setSn(paper.getSecretNumber());
             paperDTO.setLevel(paper.getLevel());
+            paperDTO.setRoughLevel(paper.getRoughLevel());
             paperDTO.setManual(paper.isManual());
             paperDTO.setScore(Objects.isNull(paper.getScore()) ? null : paper.getScore().intValue());
             paperDTO.setArbitrated(paper.isArbitrated());
@@ -119,7 +118,7 @@ public class PaperAssembler {
                     List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
                     if (!levels.isEmpty()) {
                         Map<String, Integer> map = levels.stream().collect(Collectors.toMap(Level::getCode, Level::getWeight));
-                        List<MarkTask> markTaskList = markTaskRepo.findByPaperIdAndStage(paper.getId(), MarkStage.LEVEL);
+                        List<MarkTaskLevel> markTaskList = markTaskLevelRepo.findByPaperIdAndStage(paper.getId(), MarkStage.LEVEL);
                         int sum = markTaskList.stream().mapToInt(m -> map.get(m.getResult()) == null ? 0 : map.get(m.getResult())).sum();
                         paperDTO.setSortSum(sum);
                     }

+ 23 - 26
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/assembler/QuestionStatAssembler.java

@@ -1,22 +1,15 @@
 package cn.com.qmth.stmms.ms.marking.assembler;
 
 import cn.com.qmth.stmms.ms.core.domain.MarkStage;
-import cn.com.qmth.stmms.ms.core.domain.Paper;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
-import cn.com.qmth.stmms.ms.core.repository.MarkTaskRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkTaskLevelRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkTaskRoughLevelRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkTaskScoreRepo;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import cn.com.qmth.stmms.ms.marking.dto.MarkQuestionStatDTO;
 import cn.com.qmth.stmms.ms.marking.dto.QuestionStatDTO;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Component;
 
-import cn.com.qmth.stmms.ms.core.repository.LevelRepo;
-import cn.com.qmth.stmms.ms.core.repository.PaperRepo;
-
-import java.util.List;
-import java.util.Map;
-import java.util.Objects;
-
 /**
  * Created by zhengmin on 2016/10/14.
  */
@@ -24,13 +17,13 @@ import java.util.Objects;
 public class QuestionStatAssembler {
 
     @Autowired
-    private LevelRepo levelRepo;
+    private MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
 
     @Autowired
-    private PaperRepo paperRepo;
+    private MarkTaskLevelRepo markTaskLevelRepo;
 
     @Autowired
-    private MarkTaskRepo markTaskRepo;
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     public QuestionStatDTO toDTO(Object[] qStats) {
         return this.assemble(qStats);
@@ -71,20 +64,24 @@ public class QuestionStatAssembler {
     }
 
 
-    public MarkQuestionStatDTO toMarkProgressDTO(Object[] qStats, Long workId, Subject subject) {
-//        List<Paper> papers = paperRepo.findByWorkIdAndSubject(workId, subject);
-//        long shift = papers.stream().filter(m->m.isShift()).count();
-//        long shiftScore = papers.stream().filter(m->m.isShiftScore()).count();
-//        List<MarkTask> tasks = markTaskRepo.findByWorkIdAndSubjectAndMarkerIdAndStage(workId, subject, Long.valueOf(qStats[1].toString()), MarkStage.LEVEL);
-//        long shift1 = tasks.stream().filter(m -> m.getPaper().isShift() && Objects.isNull(m.getResult())).count();
+    public MarkQuestionStatDTO toMarkProgressDTO(Object[] qStats, Long workId, Subject subject, MarkStage stage) {
+
+        int shift = 0;
+        int shiftScore = 0;
+        int rejectCount = 0;
+        if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+            shift = markTaskRoughLevelRepo.countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftAndResult(workId, subject.name(), Long.valueOf(qStats[1].toString()), stage.ordinal());
+            // todo 改档打分数量不对 202200817
+            shiftScore = markTaskRoughLevelRepo.countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftScoreAndResult(workId, subject.name(), Long.valueOf(qStats[1].toString()), MarkStage.SCORE.ordinal());
+            //所有打回
+            rejectCount = markTaskRoughLevelRepo.findByWorkIdAndSubjectAndMarkerIdAndStageReject(workId, subject.name(), Long.valueOf(qStats[1].toString()), stage.ordinal());
+        } else if (MarkStage.LEVEL.equals(stage)) {
+            shift = markTaskLevelRepo.countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftAndResult(workId, subject.name(), Long.valueOf(qStats[1].toString()), stage.ordinal());
+            shiftScore = markTaskScoreRepo.countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftScoreAndResult(workId, subject.name(), Long.valueOf(qStats[1].toString()), MarkStage.SCORE.ordinal());
+            //所有打回
+            rejectCount = markTaskLevelRepo.findByWorkIdAndSubjectAndMarkerIdAndStageReject(workId, subject.name(), Long.valueOf(qStats[1].toString()), stage.ordinal());
+        }
 
-        int shift = markTaskRepo.countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftAndResult(workId, subject.name(), Long.valueOf(qStats[1].toString()), MarkStage.LEVEL.ordinal());
-//        List<MarkTask> tasks1 = markTaskRepo.findByWorkIdAndSubjectAndMarkerIdAndStage(workId, subject, Long.valueOf(qStats[1].toString()), MarkStage.SCORE);
-//        long shiftScore1 = tasks1.stream().filter(m -> m.getPaper().isShiftScore() && Objects.isNull(m.getResult())).count();
-        int shiftScore = markTaskRepo.countByWorkIdAndSubjectAndMarkerIdAndStageAndShiftScoreAndResult(workId, subject.name(), Long.valueOf(qStats[1].toString()), MarkStage.SCORE.ordinal());
-        //所有打回
-//        long rejectCount = tasks.stream().filter(m->m.isRejected()).count();
-        int rejectCount = markTaskRepo.findByWorkIdAndSubjectAndMarkerIdAndStageReject(workId, subject.name(), Long.valueOf(qStats[1].toString()), MarkStage.LEVEL.ordinal());
         MarkQuestionStatDTO qpDTO = null;
         if (qStats != null) {
             qpDTO = new MarkQuestionStatDTO();

+ 22 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/dto/LevleProgressDTO.java

@@ -20,6 +20,12 @@ public class LevleProgressDTO implements Serializable {
 
     private Long questionId;
 
+    // 根据分组导入的名单统计
+    private int initCount;
+
+    // 是否默认选中
+    private boolean initChecked;
+
     public int getTotalCount() {
         return totalCount;
     }
@@ -67,4 +73,20 @@ public class LevleProgressDTO implements Serializable {
     public void setQuestionId(Long questionId) {
         this.questionId = questionId;
     }
+
+    public int getInitCount() {
+        return initCount;
+    }
+
+    public void setInitCount(int initCount) {
+        this.initCount = initCount;
+    }
+
+    public boolean isInitChecked() {
+        return initChecked;
+    }
+
+    public void setInitChecked(boolean initChecked) {
+        this.initChecked = initChecked;
+    }
 }

+ 9 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/dto/PaperDTO.java

@@ -18,6 +18,7 @@ public class PaperDTO implements Serializable{
     private String sn;
     private String examNumber;
     private String level;
+    private String roughLevel;
     private Integer score;
     private boolean isArbitrated;
     private boolean isRejected;
@@ -366,4 +367,12 @@ public class PaperDTO implements Serializable{
     public void setScanUserId(Long scanUserId) {
         this.scanUserId = scanUserId;
     }
+
+    public String getRoughLevel() {
+        return roughLevel;
+    }
+
+    public void setRoughLevel(String roughLevel) {
+        this.roughLevel = roughLevel;
+    }
 }

+ 308 - 129
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/AssignTaskService.java

@@ -5,18 +5,19 @@ import cn.com.qmth.stmms.ms.commons.utils.RandomUtil;
 import cn.com.qmth.stmms.ms.commons.utils.SqlUtil;
 import cn.com.qmth.stmms.ms.core.cache.CacheService;
 import cn.com.qmth.stmms.ms.core.domain.*;
-import cn.com.qmth.stmms.ms.core.domain.enums.TrialEnum;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskRoughLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskScore;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkerGroup;
 import cn.com.qmth.stmms.ms.core.domain.user.Role;
 import cn.com.qmth.stmms.ms.core.repository.*;
 import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.beans.factory.annotation.Value;
 import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 import org.springframework.util.CollectionUtils;
 
+import javax.annotation.Resource;
 import java.util.*;
 import java.util.function.Function;
 import java.util.stream.Collectors;
@@ -28,8 +29,14 @@ import java.util.stream.Collectors;
 @Service
 public class AssignTaskService {
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
+    @Resource
+    private MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     @Autowired
     private PaperRepo paperRepo;
@@ -38,17 +45,11 @@ public class AssignTaskService {
     private LevelRepo levelRepo;
 
     @Autowired
-    private MarkSubjectRepo markSubjectRepo;
-
-    @Autowired
-    private MarkerGroupRepo markerGroupRepo;
+    private MarkerGroupStudentRepo markerGroupStudentRepo;
 
     @Autowired
     private TaskPublishSettingRepo taskPublishSettingRepo;
 
-    @Value("${sys.config.random-bundle-size}")
-    private int randomBundleSize;
-
     @Autowired
     RandomUtil randomUtil;
 
@@ -65,86 +66,180 @@ public class AssignTaskService {
     MarkUserRepo markUserRepo;
 
     /**
-     * 单评任务模式,每个科目评卷员都需要对该科目每份试卷进行评卷
-     * 比如,色彩有1000份试卷,那么每个评卷员都需要评1000份
+     * 粗分档任务发布
      *
-     * @param papers
-     * @param markers
+     * @param groupPaperMap 各分组待发试卷集合
+     * @param markerGroups  所有分组
+     * @param markSubject   科目
      */
     @Transactional
-    public void assignForAll(List<Paper> papers, Iterable<MarkUser> markers, MarkSubject markSubject) throws Exception {
-        List<MarkTask> markTasks = new ArrayList<>();
-        int paperCount = papers.size();
-        int randomBundleCount = paperCount / randomBundleSize;
-        if (paperCount % randomBundleSize != 0) {
-            randomBundleCount += 1;
+    public void assignForGroupingRoughLevel(Map<Long, List<Paper>> groupPaperMap, List<MarkerGroup> markerGroups, MarkSubject markSubject) throws Exception {
+        markerGroups = markerGroups.stream().filter(m -> m.getMarkers() != null && !m.getMarkers().isEmpty()).collect(Collectors.toList());
+        long currentTime = System.currentTimeMillis();
+        List<MarkTaskRoughLevel> markTaskLevelList = new ArrayList<>();
+        List<Paper> paperList = new ArrayList<>();
+        List<Object[]> markTasks = markTaskRoughLevelRepo.findAllByWorkId(markSubject.getWorkId());
+        Map<Long, Object> randomMap = new HashMap<>();
+        markTasks.forEach(m -> randomMap.put(Long.valueOf(m[1].toString()), m[0]));
+        List<Level> levels = levelRepo.findByWorkId(markSubject.getWorkId());
+
+        Map<Long, MarkerGroup> groupMap = markerGroups.stream().collect(Collectors.toMap(MarkerGroup::getId, Function.identity()));
+        for (Map.Entry<Long, List<Paper>> entry : groupPaperMap.entrySet()) {
+            Long groupId = entry.getKey();
+            List<Paper> papers = entry.getValue();
+
+            for (Paper paper : papers) {
+                int markerCount = 0;
+                Set<MarkUser> markUsers = groupMap.get(groupId).getMarkers();
+                markUsers = markUsers.stream().filter(m -> Role.MARKER.equals(m.getRole())).collect(Collectors.toSet());
+                for (MarkUser marker : markUsers) {
+                    markerCount++;
+                    Long random = randomUtil.getRandom(marker.getWorkId(), randomMap);
+                    MarkTaskRoughLevel markTask;
+                    if (paper.isRoughSample() && paper.getLevel() != null) {
+                        Level level = levels.stream().filter(m -> String.valueOf(m.getRoughCode()).equals(paper.getLevel())).findFirst().orElseGet(null);
+                        markTask = new MarkTaskRoughLevel(marker, paper, level, markSubject.getStage(), random, markSubject.getTest());
+
+                        // 初始化排序值
+                        if (markerCount == markUsers.size()) {
+                            paper.setSortNum(level.getRoughWeight() * markerCount);
+                        }
+                    } else {
+                        markTask = new MarkTaskRoughLevel(marker, paper, markSubject.getStage(), random, markSubject.getTest());
+                    }
+                    markTask.setBatchNo(currentTime);
+
+                    markTaskLevelList.add(markTask);
+                    randomMap.put(random, markTask);
+                }
+//                paper.setActive(true);
+                paper.setRoughBatchNo(currentTime);
+                paperList.add(paper);
+            }
         }
-        List<MarkTask> markTaskList = markTaskRepo.findByWorkId(markSubject.getWorkId());
-        Map<Long, Object> randomMap = markTaskList.stream().collect(Collectors.toMap(MarkTask::getRandomSeqNew, Function.identity(), (dto1, dto2) -> dto1));
-        for (int i = 0; i < randomBundleCount; i++) {
-            int fromIndex = i * randomBundleSize;
-            int endIndex = i * randomBundleSize + randomBundleSize;
-            if (endIndex > paperCount) {
-                endIndex = paperCount;
+
+
+        List<MarkTaskRoughLevel> data = new ArrayList<>();
+        //5000条提交一次
+        for (MarkTaskRoughLevel markTask : markTaskLevelList) {
+            if (data.size() == 2000) {
+                markTaskRoughLevelRepo.save(data);
+                data.clear();
             }
-            List<Paper> bundleList = papers.subList(fromIndex, endIndex);
+            data.add(markTask);
+        }
+        //将剩下的数据也导入
+        if (!data.isEmpty()) {
+            markTaskRoughLevelRepo.save(data);
+        }
+        paperRepo.save(paperList);
+    }
+
+    /**
+     * 粗分档任务发布
+     *
+     * @param groupPaperMap 各分组待发试卷集合
+     * @param markerGroups  所有分组
+     * @param markSubject   科目
+     */
+    @Transactional
+    public void assignForGroupingLevel(Map<Long, List<Paper>> groupPaperMap, List<MarkerGroup> markerGroups, MarkSubject markSubject) throws Exception {
+        markerGroups = markerGroups.stream().filter(m -> m.getMarkers() != null && !m.getMarkers().isEmpty()).collect(Collectors.toList());
+        long currentTime = System.currentTimeMillis();
+        List<MarkTaskLevel> markTaskLevelList = new ArrayList<>();
+        List<Paper> paperList = new ArrayList<>();
+        List<Object[]> markTasks = markTaskLevelRepo.findAllByWorkId(markSubject.getWorkId());
+        Map<Long, Object> randomMap = new HashMap<>();
+        markTasks.forEach(m -> randomMap.put(Long.valueOf(m[1].toString()), m[0]));
+        List<Level> levels = levelRepo.findByWorkId(markSubject.getWorkId());
 
-            for (MarkUser marker : markers) {
-                List<Paper> markerPaperList = Arrays.asList(new Paper[bundleList.size()]);
+        Map<Long, MarkerGroup> groupMap = markerGroups.stream().collect(Collectors.toMap(MarkerGroup::getId, Function.identity()));
+        for (Map.Entry<Long, List<Paper>> entry : groupPaperMap.entrySet()) {
+            Long groupId = entry.getKey();
+            List<Paper> papers = entry.getValue();
+
+            for (Paper paper : papers) {
+                int markerCount = 0;
+                Set<MarkUser> markUsers = groupMap.get(groupId).getMarkers();
+                markUsers = markUsers.stream().filter(m -> Role.MARKER.equals(m.getRole())).collect(Collectors.toSet());
+                for (MarkUser marker : markUsers) {
+                    markerCount++;
+                    Long random = randomUtil.getRandom(marker.getWorkId(), randomMap);
+                    MarkTaskLevel markTask;
+                    if (paper.isRoughSample() && paper.getLevel() != null) {
+                        Level level = levels.stream().filter(m -> m.getCode().equals(paper.getLevel())).findFirst().orElseGet(null);
+                        markTask = new MarkTaskLevel(marker, paper, level, markSubject.getStage(), random, markSubject.getTest());
 
-                Collections.copy(markerPaperList, bundleList);
-                Collections.shuffle(markerPaperList);//乱序
+                        // 初始化排序值
+                        if (markerCount == markUsers.size()) {
+                            paper.setSortNum(level.getWeight() * markerCount);
+                        }
+                    } else {
+                        markTask = new MarkTaskLevel(marker, paper, markSubject.getStage(), random, markSubject.getTest());
+                    }
+                    markTask.setBatchNo(currentTime);
 
-                for (int j = 0; j < markerPaperList.size(); j++) {
-                    Paper paper = markerPaperList.get(j);
-                    Long random = getRandom(marker.getId(), paper.getId(), marker.getWorkId(), paper.getExamNumber(), randomMap);
-                    MarkTask markTask = new MarkTask(marker, paper, markSubject.getStage(), random, markSubject.getTest());
-                    markTask.setRandomSeq(i * randomBundleSize + j + 1);
-                    markTasks.add(markTask);
+                    markTaskLevelList.add(markTask);
+                    randomMap.put(random, markTask);
                 }
+//                paper.setActive(true);
+                paper.setBatchNo(currentTime);
+                paperList.add(paper);
             }
-
         }
 
-        markTaskRepo.save(markTasks);
-
-//        Iterator<Paper> iterator = papers.iterator();
-//        while (iterator.hasNext()) {
-//            Paper paper = iterator.next();
-//            for (MarkUser marker : markers) {
-//                MarkTask markTask = new MarkTask(marker, paper, markSubject.getStage());
-//                markTaskRepo.save(markTask);
-//                //taskExecutor.execute(papers,marker,stage);
-//            }
-//        }
+
+        List<MarkTaskLevel> data = new ArrayList<>();
+        //5000条提交一次
+        for (MarkTaskLevel markTask : markTaskLevelList) {
+            if (data.size() == 2000) {
+                markTaskLevelRepo.save(data);
+                data.clear();
+            }
+            data.add(markTask);
+        }
+        //将剩下的数据也导入
+        if (!data.isEmpty()) {
+            markTaskLevelRepo.save(data);
+        }
+        paperRepo.save(paperList);
     }
 
     /**
      * 分组任务模式,将该科目的评卷员分成N组,将该科目试卷平均分给这些组,每组内的评卷员每人将这些试卷打分
      * 比如:6个评卷员分2组,有1000份试卷,每组评500份,每个评卷员评500份
      *
-     * @param papers
-     * @param markerGroups
-     * @param taskList
+     * @param papers       试卷
+     * @param markerGroups 分组
+     * @param markSubject  科目
+     * @param taskList     打分任务
      */
     @Transactional
     public void assignForGrouping(List<Paper> papers, List<MarkerGroup> markerGroups, MarkSubject markSubject, List<TaskPublishSetting> taskList) throws Exception {
-        markerGroups = markerGroups.stream().filter(m -> m.getMarkers().size() > 0).collect(Collectors.toList());
+        markerGroups = markerGroups.stream().filter(m -> m.getMarkers() != null && !m.getMarkers().isEmpty()).collect(Collectors.toList());
         int sum = markerGroups.stream().mapToInt(m -> m.getMarkers().size()).sum();
         int groupSize = markerGroups.size();
         int idx = 0;
         long currentTime = System.currentTimeMillis();
         Iterator<Paper> iterator = papers.iterator();
-        List<MarkTask> markTaskList = new ArrayList<>(papers.size() * sum);
+        List<MarkTaskLevel> markTaskLevelList = new ArrayList<>(papers.size() * sum);
+        List<MarkTaskScore> markTaskScoreList = new ArrayList<>(papers.size() * sum);
         List<Paper> paperList = new ArrayList<>(papers.size());
-        List<Object[]> markTasks = markTaskRepo.findAllByWorkId(markSubject.getWorkId());
+        List<Object[]> markTasks = new ArrayList<>();
+        if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+            markTasks = markTaskRoughLevelRepo.findAllByWorkId(markSubject.getWorkId());
+        } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+            markTasks = markTaskLevelRepo.findAllByWorkId(markSubject.getWorkId());
+        } else if (MarkStage.SCORE.equals(markSubject.getStage())) {
+            markTasks = markTaskScoreRepo.findAllByWorkId(markSubject.getWorkId());
+        }
         Map<Long, Object> randomMap = new HashMap<>();
         markTasks.forEach(m -> randomMap.put(Long.valueOf(m[1].toString()), m[0]));
         List<Level> levels = levelRepo.findByWorkId(markSubject.getWorkId());
         Map<String, Level> levelMap = levels.stream().collect(Collectors.toMap(Level::getCode, l -> l));
         //定序序号记录
-        Map map = new HashMap();
-        Map seqNewMap = new HashMap();
+        Map<String, Integer> map = new HashMap();
+        Map<String, Integer> seqNewMap = new HashMap();
         while (iterator.hasNext()) {
             if (idx >= groupSize) {
                 idx = 0;
@@ -159,9 +254,9 @@ public class AssignTaskService {
                 long sortRule = taskList.stream().filter(m -> Objects.equals(m.getCode(), paper.getLevel()) && m.getSortRule() == 1).count();
                 if (sortRule != 0) {
                     if (map.containsKey(paper.getLevel() + idx)) {
-                        seq = (int) map.get(paper.getLevel() + idx);
+                        seq = map.get(paper.getLevel() + idx);
                     }
-                    seq = ++seq;
+                    ++seq;
                     serialNumber = paper.getLevel() + seq;
                     //是否显示序号
                     long display = taskList.stream().filter(m -> Objects.equals(m.getCode(), paper.getLevel()) && m.getDisplayNumber() == 1).count();
@@ -171,7 +266,7 @@ public class AssignTaskService {
 
                     int seqNew = 0;
                     if (seqNewMap.containsKey(paper.getLevel())) {
-                        seqNew = (int) seqNewMap.get(paper.getLevel());
+                        seqNew = seqNewMap.get(paper.getLevel());
                     }
                     seqNewNumber = ++seqNew;
                     seqNewMap.put(paper.getLevel(), seqNew);
@@ -182,23 +277,26 @@ public class AssignTaskService {
             markUsers = markUsers.stream().filter(m -> Role.MARKER.equals(m.getRole())).collect(Collectors.toSet());
             for (MarkUser marker : markUsers) {
                 markerCount++;
-                Long random = getRandom(marker.getId(), paper.getId(), marker.getWorkId(), paper.getExamNumber(), randomMap);
-                MarkTask markTask;
+                Long random = randomUtil.getRandom(marker.getWorkId(), randomMap);
                 if (Objects.equals(MarkStage.LEVEL, markSubject.getStage())) {
+                    MarkTaskLevel markTask = null;
                     if (paper.isSample() && paper.getLevel() != null) {
                         Level level = levelRepo.findByWorkIdAndCode(markSubject.getWorkId(), paper.getLevel());
-                        markTask = new MarkTask(marker, paper, level, markSubject.getStage(), random, markSubject.getTest());
+                        markTask = new MarkTaskLevel(marker, paper, level, markSubject.getStage(), random, markSubject.getTest());
 
                         // 初始化排序值
                         if (markerCount == markerGroups.get(idx).getMarkers().size()) {
                             paper.setSortNum(level.getWeight() * markerCount);
                         }
                     } else {
-                        markTask = new MarkTask(marker, paper, markSubject.getStage(), random, markSubject.getTest());
+                        markTask = new MarkTaskLevel(marker, paper, markSubject.getStage(), random, markSubject.getTest());
                     }
                     markTask.setBatchNo(currentTime);
+
+                    markTaskLevelList.add(markTask);
+                    randomMap.put(random, markTask);
                 } else {
-                    markTask = new MarkTask(marker, paper, markSubject.getStage(), random, markSubject.getTest());
+                    MarkTaskScore markTask = new MarkTaskScore(marker, paper, markSubject.getStage(), random, markSubject.getTest());
                     String levelValue = String.valueOf(levelMap.get(paper.getLevel()).getLevelValue() + 1);
                     if (Objects.nonNull(serialNumber)) {
                         //和随机数位数保持一致(8位)
@@ -211,9 +309,10 @@ public class AssignTaskService {
                     markTask.setSerialNumber(serialNumber);
                     markTask.setDisplayNumber(displayNumber);
                     markTask.setLevel(paper.getLevel());
+
+                    markTaskScoreList.add(markTask);
+                    randomMap.put(random, markTask);
                 }
-                markTaskList.add(markTask);
-                randomMap.put(random, markTask);
             }
             if (markSubject.getTest() != 1) {
                 if (MarkStage.LEVEL.equals(markSubject.getStage())) {
@@ -234,49 +333,40 @@ public class AssignTaskService {
             idx++;
         }
 
-        List<MarkTask> data = new ArrayList<>();
-        //5000条提交一次
-        for (MarkTask markTask : markTaskList) {
-            if (data.size() == 2000) {
-                markTaskRepo.save(data);
-                data.clear();
+        if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+            List<MarkTaskLevel> data = new ArrayList<>();
+            //5000条提交一次
+            for (MarkTaskLevel markTask : markTaskLevelList) {
+                if (data.size() == 2000) {
+                    markTaskLevelRepo.save(data);
+                    data.clear();
+                }
+                data.add(markTask);
+            }
+            //将剩下的数据也导入
+            if (!data.isEmpty()) {
+                markTaskLevelRepo.save(data);
+            }
+        } else if (MarkStage.SCORE.equals(markSubject.getStage())) {
+            List<MarkTaskScore> data = new ArrayList<>();
+            //5000条提交一次
+            for (MarkTaskScore markTask : markTaskScoreList) {
+                if (data.size() == 2000) {
+                    markTaskScoreRepo.save(data);
+                    data.clear();
+                }
+                data.add(markTask);
+            }
+            //将剩下的数据也导入
+            if (!data.isEmpty()) {
+                markTaskScoreRepo.save(data);
             }
-            data.add(markTask);
-        }
-        //将剩下的数据也导入
-        if (!data.isEmpty()) {
-            markTaskRepo.save(data);
         }
-
-//        markTaskRepo.save(markTaskList);
         paperRepo.save(paperList);
-        /*if (markSubject.getTest() != 1) {
-            markSubject.setFormal(true);
-            markSubjectRepo.saveAndFlush(markSubject);
-        }*/
-        //只有全部任务投放完成,才能删除分组
-//        int count = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndActiveFalseAndBatchNoIsNullAndTest(markSubject.getWorkId(), markSubject.getSubject(), 0);
-        //进入分档阶段后,清空当前分组,以便打分阶段前重新分组
-        /*if (MarkStage.LEVEL.equals(markSubject.getStage()) && count == 0) {
-            for (MarkerGroup markerGroup : markerGroups) {
-                markerGroup.setMarkers(null);
-            }
-            markerGroupRepo.delete(markerGroups);
-        }*/
-//        if (MarkStage.SCORE.equals(markSubject.getStage()) && count == 0) {
-//            //初始化打分任务数据
-//            initTaskPublishData(markSubject);
-//
-//        }
     }
 
     @Transactional
     public void assignForGroupingScore(MarkSubject markSubject, List<MarkerGroup> markerGroups) {
-        /*if (markSubject.getTest() != 1) {
-            //更新subject表formal为正试评卷
-            markSubject.setFormal(true);
-            markSubjectRepo.saveAndFlush(markSubject);
-        }*/
         //只有全部任务投放完成,才能删除分组
         int count = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndActiveFalseAndBatchNoIsNullAndTest(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getTest());
         if (MarkStage.SCORE.equals(markSubject.getStage()) && count == 0) {
@@ -340,35 +430,124 @@ public class AssignTaskService {
     }
 
     /**
-     * 获取随机号
+     * 根据分组,分配任务
      *
-     * @param markerId
-     * @param paperId
-     * @param workId
-     * @param examNumber
-     * @param randomMap
-     * @return
-     * @throws Exception
+     * @param allPapers    所有试卷
+     * @param markSubject  科目
+     * @param markerGroups 分组
+     * @param questionIds  考区
+     * @param taskCount    分档数量
      */
-    public Long getRandom(Long markerId, Long paperId, Long workId, String examNumber, Map<Long, Object> randomMap) throws Exception {
-        int count = 0;
-        Long random = 0L;
-        while (true) {
-            random = randomUtil.getRandomMap().get(workId).get(new Random().nextInt(randomUtil.getRandomMap().get(workId).size()));
-            if (Objects.isNull(randomMap) || randomMap.size() == 0) {
-                break;
+    @Transactional
+    public Map<Long, List<Paper>> assignGroupTasks(List<Paper> allPapers, MarkSubject markSubject, List<MarkerGroup> markerGroups, List<Long> questionIds, int taskCount) {
+        // 按分组循环
+        Map<Long, List<Paper>> groupPaperMap = new HashMap<>();
+        if (markSubject.getTest() != 1) {
+            // 所有未分档任务
+            List<Paper> papersList = new ArrayList<>();
+            // 所有分组导入的考生名单
+            List<MarkerGroupStudent> markerGroupStudentList = markerGroupStudentRepo.findByWorkIdAndSubjectAndStageAndUsed(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage(), false);
+            if (questionIds.isEmpty()) {
+                if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+                    papersList = allPapers.stream().filter(m -> m.getRoughBatchNo() == null).collect(Collectors.toList());
+                } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+                    papersList = allPapers.stream().filter(m -> m.getBatchNo() == null).collect(Collectors.toList());
+                }
+            } else {
+                // 按考区过滤数据
+                if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+                    papersList = allPapers.stream().filter(m -> questionIds.contains(m.getQuestionId()) && m.getRoughBatchNo() == null).collect(Collectors.toList());
+                } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+                    papersList = allPapers.stream().filter(m -> questionIds.contains(m.getQuestionId()) && m.getBatchNo() == null).collect(Collectors.toList());
+                }
+
+            }
+
+            Map<Long, List<MarkerGroupStudent>> markerGroupStudentMap = markerGroupStudentList.stream().collect(Collectors.groupingBy(MarkerGroupStudent::getGroupId));
+
+            for (MarkerGroup markerGroup : markerGroups) {
+                List<Paper> groupPaperList = new ArrayList<>();
+                // 默认为false
+                if (markerGroupStudentMap != null && markerGroupStudentMap.containsKey(markerGroup.getId())) {
+                    List<MarkerGroupStudent> groupStudents = markerGroupStudentMap.get(markerGroup.getId());
+                    if (groupStudents != null && !groupStudents.isEmpty()) {
+                        List<Long> paperIds = groupStudents.stream().map(MarkerGroupStudent::getPaperId).collect(Collectors.toList());
+                        groupPaperList = papersList.stream().filter(m -> paperIds.contains(m.getId())).collect(Collectors.toList());
+                        if (paperIds.size() != groupPaperList.size()) {
+                            throw new RuntimeException("任务数据有误");
+                        }
+                    }
+                }
+                groupPaperMap.put(markerGroup.getId(), groupPaperList);
             }
-            if (Objects.isNull(randomMap.get(random))) {
-                break;
+            // 根据分组导入名单进行任务分配
+            randomTaskList(papersList, groupPaperMap, taskCount);
+
+            //分组考生名单更新为已使用
+            markerGroupStudentList.forEach(m -> m.setUsed(true));
+            markerGroupStudentRepo.save(markerGroupStudentList);
+        } else {
+            for (MarkerGroup markerGroup : markerGroups) {
+                List<Paper> groupPaperList = new ArrayList<>();
+                groupPaperMap.put(markerGroup.getId(), groupPaperList);
+            }
+            randomTaskList(allPapers, groupPaperMap, allPapers.size());
+        }
+
+        return groupPaperMap;
+    }
+
+    /**
+     * 随机发任务
+     *
+     * @param papersList    试卷集合
+     * @param groupPaperMap 分组考生名单
+     * @param taskCount     任务数量
+     */
+    private void randomTaskList(List<Paper> papersList, Map<Long, List<Paper>> groupPaperMap, int taskCount) {
+
+        List<Paper> usedPaperList = new ArrayList<>();
+        List<Long> nullValueKeys = new ArrayList<>();
+        for (Map.Entry<Long, List<Paper>> entry : groupPaperMap.entrySet()) {
+            List<Paper> value = entry.getValue();
+            if (!value.isEmpty()) {
+                usedPaperList.addAll(value);
+                continue;
+            }
+            // 未导入考生名单的分组
+            nullValueKeys.add(entry.getKey());
+        }
+
+        //
+        if (!nullValueKeys.isEmpty()) {
+            // 剔除已导入的数据
+            papersList.removeAll(usedPaperList);
+            int leftCount = taskCount - usedPaperList.size();
+            if (leftCount < 0) {
+                throw new RuntimeException("任务数量有误");
+            }
+            // 随机取
+            List<Paper> list = new ArrayList<>();
+            if (leftCount == papersList.size()) {
+                list.addAll(papersList);
             } else {
-                count++;
+                Random random = new Random();
+                for (int i = 0; i < leftCount; i++) {
+                    int intRandom = random.nextInt(papersList.size() - 1);
+                    list.add(papersList.get(intRandom));
+                    papersList.remove(intRandom);
+                }
             }
-            if (count > 1000) {
-//                throw new Exception("重复几率较高,建议重新生成随机号");
-                randomUtil.getRandom(workId, true);
-                getRandom(markerId, paperId, workId, examNumber, randomMap);
+
+            // 给每个组发任务
+            int idx = 0;
+            for (Paper paper : list) {
+                if (idx >= nullValueKeys.size()) {
+                    idx = 0;
+                }
+                groupPaperMap.get(nullValueKeys.get(idx)).add(paper);
+                idx++;
             }
         }
-        return random;
     }
 }

+ 27 - 20
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/AutoRun.java

@@ -4,7 +4,8 @@ import cn.com.qmth.stmms.ms.core.domain.Level;
 import cn.com.qmth.stmms.ms.core.domain.MarkStage;
 import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
 import cn.com.qmth.stmms.ms.core.domain.Paper;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskScore;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.domain.user.Role;
 import cn.com.qmth.stmms.ms.core.repository.*;
@@ -14,11 +15,9 @@ import org.springframework.stereotype.Service;
 
 import java.util.ArrayList;
 import java.util.List;
-import java.util.Optional;
 import java.util.Random;
 import java.util.concurrent.ExecutorService;
 import java.util.concurrent.Executors;
-import java.util.stream.IntStream;
 
 /**
  * 调试用
@@ -34,7 +33,10 @@ public class AutoRun {
     private MarkSubjectRepo markSubjectRepo;
 
     @Autowired
-    private MarkTaskRepo markTaskRepo;
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Autowired
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     @Autowired
     private LevelRepo levelRepo;
@@ -42,51 +44,56 @@ public class AutoRun {
     @Autowired
     private MarkingService markingService;
 
+    @Autowired
+    private MarkingLevelService markingLevelService;
+
+    @Autowired
+    private MarkingScoreService markingScoreService;
+
     @Autowired
     private PaperRepo paperRepo;
 
-    public void run(Long workId, Subject subject){
+    public void run(Long workId, Subject subject) {
         MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + subject.toString());
-        List<MarkUser> markers = markUserRepo.findByWorkIdAndSubjectAndRole(workId,subject, Role.MARKER);
+        List<MarkUser> markers = markUserRepo.findByWorkIdAndSubjectAndRole(workId, subject, Role.MARKER);
         ExecutorService executor = Executors.newFixedThreadPool(markers.size());
         markers.forEach(m -> {
-            executor.submit(this.buildTask(m,markSubject.getStage()));
+            executor.submit(this.buildTask(m, markSubject.getStage()));
         });
     }
 
-    private Runnable buildTask(MarkUser marker,MarkStage markStage){
-        List<MarkTask> markTasks =  markTaskRepo.findByMarkerIdAndStage(marker.getId(),markStage);
+    private Runnable buildTask(MarkUser marker, MarkStage markStage) {
         Runnable task = null;
-        if(markStage == MarkStage.LEVEL) {
+        if (markStage == MarkStage.LEVEL) {
+            List<MarkTaskLevel> markTasks = markTaskLevelRepo.findByMarkerIdAndStage(marker.getId(), markStage);
             List<Level> levels = levelRepo.findByWorkId(marker.getWorkId());
             task = () -> {
                 markTasks.forEach(t -> {
                     Random random = new Random();
                     int index = random.nextInt(levels.size());
-                    markingService.levelMark(t, levels.get(index).getCode());
+                    markingLevelService.levelMark(t, levels.get(index).getCode());
                 });
             };
-        }
-        else if(markStage == MarkStage.SCORE){
+        } else if (markStage == MarkStage.SCORE) {
+            List<MarkTaskScore> markTasks = markTaskScoreRepo.findByMarkerIdAndStage(marker.getId(), markStage);
             task = () -> {
                 markTasks.forEach(t -> {
                     Paper paper = paperRepo.findOne(t.getPaper().getId());
-                    Level level = levelRepo.findByWorkIdAndCode(marker.getWorkId(),paper.getLevel());
+                    Level level = levelRepo.findByWorkIdAndCode(marker.getWorkId(), paper.getLevel());
                     List<Integer> scores = new ArrayList<Integer>();
-                    if(level.getLevelType() == Level.LevelType.ADMITED){
-                        for (int i = level.getMinScore();i <= level.getMaxScore();i+= level.getIntervalScore()){
+                    if (level.getLevelType() == Level.LevelType.ADMITED) {
+                        for (int i = level.getMinScore(); i <= level.getMaxScore(); i += level.getIntervalScore()) {
                             scores.add(i);
                         }
-                    }
-                    else{
+                    } else {
                         String[] strs = level.getScoreList().split(",");
-                        for(String s : strs){
+                        for (String s : strs) {
                             scores.add(Integer.parseInt(s));
                         }
                     }
                     Random random = new Random();
                     int index = random.nextInt(scores.size());
-                    markingService.scoring(t,scores.get(index));
+                    markingScoreService.scoring(t, scores.get(index));
                 });
             };
         }

+ 9 - 9
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/DetermineLevelService.java

@@ -2,7 +2,7 @@ package cn.com.qmth.stmms.ms.marking.service;
 
 import cn.com.qmth.stmms.ms.core.cache.ParamCache;
 import cn.com.qmth.stmms.ms.core.domain.Level;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.repository.LevelRepo;
 import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
@@ -46,13 +46,13 @@ public class DetermineLevelService {
      * @param workId    工作ID
      * @param markTasks 任务集合
      */
-    public DeterResult determine(Long workId, List<Level> levels, List<MarkTask> markTasks) {
+    public DeterResult determine(Long workId, List<Level> levels, List<MarkTaskLevel> markTasks) {
         // 是否过半定档(1:是)
         boolean majority = Optional.ofNullable(ParamCache.levelConfigMap.get(String.valueOf(String.valueOf(workId))).getMajority()).orElse(1) == 1;
         DeterResult majorityResult = null;
         DeterResult weightResult = null;
         if (majority) {
-            MarkTask[] tasks = markTasks.toArray(new MarkTask[0]);
+            MarkTaskLevel[] tasks = markTasks.toArray(new MarkTaskLevel[0]);
             majorityResult = calcMajority(tasks);
         }
         weightResult = calcWeight(workId, levels, markTasks);
@@ -84,16 +84,16 @@ public class DetermineLevelService {
      *
      * @param markTasks 任务集合
      */
-    private DeterResult calcWeight(Long workId, List<Level> levels, List<MarkTask> markTasks) {
+    private DeterResult calcWeight(Long workId, List<Level> levels, List<MarkTaskLevel> markTasks) {
         // 是否开启去高去低再加权评卷(1:是, 0:否,默认0)
         boolean removeHighAndLow = Optional.ofNullable(ParamCache.levelConfigMap.get(String.valueOf(String.valueOf(workId))).getRemoveHighAndLow()).orElse(0) == 1;
         if (removeHighAndLow && markTasks.size() > 2) {
-            markTasks.sort((Comparator.comparing(MarkTask::getResult)));
+            markTasks.sort((Comparator.comparing(MarkTaskLevel::getResult)));
             markTasks.remove(0);//去掉最大值
             markTasks.remove(markTasks.size() - 1);//去掉最小值
         }
 
-        MarkTask[] tasks = markTasks.toArray(new MarkTask[0]);
+        MarkTaskLevel[] tasks = markTasks.toArray(new MarkTaskLevel[0]);
         //通过权重计算,平均值四舍五入
         double[] values = new double[tasks.length];
         double[] weights = new double[tasks.length];
@@ -129,11 +129,11 @@ public class DetermineLevelService {
      *
      * @param tasks 任务集合
      */
-    private DeterResult calcMajority(MarkTask[] tasks) {
+    private DeterResult calcMajority(MarkTaskLevel[] tasks) {
         //如果相同的数量大于半数,直接定档
-        Stream<MarkTask> taskStream = Stream.of(tasks);
+        Stream<MarkTaskLevel> taskStream = Stream.of(tasks);
         Optional<Map.Entry<String, Long>> optional = taskStream
-                .collect(Collectors.groupingBy(MarkTask::getResult, Collectors.counting()))
+                .collect(Collectors.groupingBy(MarkTaskLevel::getResult, Collectors.counting()))
                 .entrySet()
                 .stream()
                 .max(Comparator.comparing(Map.Entry::getValue));

+ 192 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/DetermineRoughLevelService.java

@@ -0,0 +1,192 @@
+package cn.com.qmth.stmms.ms.marking.service;
+
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
+import cn.com.qmth.stmms.ms.core.domain.Level;
+import cn.com.qmth.stmms.ms.core.domain.RoughLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskRoughLevel;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.repository.LevelRepo;
+import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.util.*;
+import java.util.stream.Collectors;
+import java.util.stream.DoubleStream;
+import java.util.stream.Stream;
+
+/**
+ * 定档
+ * Created by zhengmin on 2016/9/22.
+ */
+@Service
+public class DetermineRoughLevelService {
+
+    public enum DeterType {
+        /**
+         * 多数
+         */
+        MAJORITY,
+        /**
+         * 权重
+         */
+        WEIGHT
+    }
+
+    @Autowired
+    private MarkUserRepo markUserRepo;
+
+    /**
+     * 计算定档值(规则:1.不是过半定档,取权重,2.是过半定档,没有取优,取过半定档,3.是过半定档,是取优,取过半定档和权重最优值)
+     *
+     * @param workId    工作ID
+     * @param markTasks 任务集合
+     */
+    public RoughDeterResult determine(Long workId, List<Level> levels, List<MarkTaskRoughLevel> markTasks) {
+        List<RoughLevel> roughLevels = parseRoughLevels(levels);
+        // 是否过半定档(1:是)
+        boolean majority = Optional.ofNullable(ParamCache.levelConfigMap.get(String.valueOf(String.valueOf(workId))).getMajority()).orElse(1) == 1;
+        RoughDeterResult majorityResult = null;
+        RoughDeterResult weightResult = null;
+        if (majority) {
+            MarkTaskRoughLevel[] tasks = markTasks.toArray(new MarkTaskRoughLevel[0]);
+            majorityResult = calcMajority(tasks);
+        }
+        weightResult = calcWeight(workId, roughLevels, markTasks);
+
+        if (majorityResult != null) {
+            // 是否取优(过半定档和权重,取最优值)
+            boolean takeBest = Optional.ofNullable(ParamCache.levelConfigMap.get(String.valueOf(String.valueOf(workId))).getTakeBest()).orElse(1) == 1;
+            if (takeBest) {
+                Map<String, String> levelMap = roughLevels.stream().collect(Collectors.toMap(RoughLevel::getRoughCode, RoughLevel::getRoughCode));
+                // 取优
+                int majorityLevelValue = Integer.parseInt(levelMap.get(majorityResult.getResult()));
+                int weightLevelValue = Integer.parseInt(levelMap.get(weightResult.getResult()));
+                // 值越大,档位越大
+                if (majorityLevelValue < weightLevelValue) {
+                    return weightResult;
+                } else {
+                    return majorityResult;
+                }
+            } else {
+                return majorityResult;
+            }
+        } else {
+            return weightResult;
+        }
+    }
+
+    /**
+     * 计算权重值
+     *
+     * @param markTasks 任务集合
+     */
+    private RoughDeterResult calcWeight(Long workId, List<RoughLevel> roughLevels, List<MarkTaskRoughLevel> markTasks) {
+        // 是否开启去高去低再加权评卷(1:是, 0:否,默认0)
+        boolean removeHighAndLow = Optional.ofNullable(ParamCache.levelConfigMap.get(String.valueOf(String.valueOf(workId))).getRemoveHighAndLow()).orElse(0) == 1;
+        if (removeHighAndLow && markTasks.size() > 2) {
+            markTasks.sort((Comparator.comparing(MarkTaskRoughLevel::getResult)));
+            markTasks.remove(0);//去掉最大值
+            markTasks.remove(markTasks.size() - 1);//去掉最小值
+        }
+
+        MarkTaskRoughLevel[] tasks = markTasks.toArray(new MarkTaskRoughLevel[0]);
+        //通过权重计算,平均值四舍五入
+        double[] values = new double[tasks.length];
+        double[] weights = new double[tasks.length];
+        for (int i = 0; i < tasks.length; i++) {
+            String levelResult = tasks[i].getResult();
+            RoughLevel level = roughLevels.stream().filter(m -> m.getRoughCode().equals(levelResult)).findFirst().orElse(null);
+            if (level == null) {
+                throw new RuntimeException("无此档位");
+            }
+            MarkUser marker = markUserRepo.findOne(tasks[i].getMarkerId());
+            double markerWeight = marker.getWeight();
+            values[i] = level.getWeight() * markerWeight;
+            weights[i] = markerWeight;
+        }
+        int avg = (int) Math.round(DoubleStream.of(values).sum() / DoubleStream.of(weights).sum());
+        Optional<RoughLevel> levelOptional = roughLevels.stream().filter(o -> o.getMaxScore() >= avg && o.getMinScore() <= avg).findFirst();
+        RoughLevel level = levelOptional.orElse(null);
+        if (level == null) {
+            roughLevels = roughLevels.stream().sorted(Comparator.comparing(RoughLevel::getMaxScore).reversed()).collect(Collectors.toList());
+            if (avg > roughLevels.get(0).getMaxScore()) {
+                level = roughLevels.get(0);
+            }
+            roughLevels = roughLevels.stream().sorted(Comparator.comparing(RoughLevel::getMinScore)).collect(Collectors.toList());
+            if (avg < roughLevels.get(0).getMinScore()) {
+                level = roughLevels.get(0);
+            }
+        }
+        return new RoughDeterResult(level.getRoughCode(), DeterType.WEIGHT);
+    }
+
+    /**
+     * 计算过半定档值
+     *
+     * @param tasks 任务集合
+     */
+    private RoughDeterResult calcMajority(MarkTaskRoughLevel[] tasks) {
+        //如果相同的数量大于半数,直接定档
+        Stream<MarkTaskRoughLevel> taskStream = Stream.of(tasks);
+        Optional<Map.Entry<String, Long>> optional = taskStream
+                .collect(Collectors.groupingBy(MarkTaskRoughLevel::getResult, Collectors.counting()))
+                .entrySet()
+                .stream()
+                .max(Comparator.comparing(Map.Entry::getValue));
+        if (optional.isPresent()) {
+            Map.Entry<String, Long> entry = optional.get();
+            if (entry.getValue() > tasks.length / 2) {
+                return new RoughDeterResult(entry.getKey(), DeterType.MAJORITY);
+            }
+        }
+        return null;
+    }
+
+
+    private List<RoughLevel> parseRoughLevels(List<Level> levels){
+        List<RoughLevel> roughLevels = new ArrayList<>();
+
+        Map<String, List<Level>> listMap = levels.stream().collect(Collectors.groupingBy(Level::getRoughCode));
+        for (Map.Entry<String, List<Level>> entry : listMap.entrySet()) {
+            RoughLevel roughLevel = new RoughLevel();
+            roughLevel.setRoughCode(entry.getKey());
+
+            List<Level> levelList = entry.getValue();
+            roughLevel.setWeight(levelList.get(0).getRoughWeight());
+            int minScore = levelList.stream().min(Comparator.comparing(Level::getMinScore)).get().getMinScore();
+            roughLevel.setMinScore(minScore);
+            int maxScore = levelList.stream().max(Comparator.comparing(Level::getMaxScore)).get().getMaxScore();
+            roughLevel.setMaxScore(maxScore);
+            roughLevels.add(roughLevel);
+        }
+        return roughLevels;
+    }
+}
+
+class RoughDeterResult {
+    private String result;
+    private DetermineRoughLevelService.DeterType deterType;
+
+    public RoughDeterResult(String result, DetermineRoughLevelService.DeterType deterType) {
+        this.result = result;
+        this.deterType = deterType;
+    }
+
+    public String getResult() {
+        return result;
+    }
+
+    public void setResult(String result) {
+        this.result = result;
+    }
+
+    public DetermineRoughLevelService.DeterType getDeterType() {
+        return deterType;
+    }
+
+    public void setDeterType(DetermineRoughLevelService.DeterType deterType) {
+        this.deterType = deterType;
+    }
+}

+ 56 - 40
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/GroupingService.java

@@ -16,6 +16,7 @@ import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 import org.springframework.util.CollectionUtils;
 
+import javax.annotation.Resource;
 import java.math.BigDecimal;
 import java.util.*;
 import java.util.stream.Collectors;
@@ -33,8 +34,14 @@ public class GroupingService {
     @Autowired
     PaperRepo paperRepo;
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
+    @Resource
+    private MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     @Autowired
     private MarkerGroupRepo markerGroupRepo;
@@ -84,11 +91,12 @@ public class GroupingService {
      */
     public void getTotalProgress(Long workId, MarkSubject markSubject, Map<String, Object> objectMap) {
         int successCount = 0;
-        if (markSubject.getStage().name().equals(MarkStage.LEVEL.name())) {
-            successCount = paperRepo.countByWorkIdAndSubjectAndLevelNotNullAndIsMissingFalseAndActiveTrueAndTest(workId, markSubject.getSubject(), markSubject.getTest());
-        }
-        if (markSubject.getStage().name().equals(MarkStage.SCORE.name())) {
-            successCount = paperRepo.countByWorkIdAndSubjectAndScoreNotNullAndIsMissingFalseAndActiveTrueAndTest(workId, markSubject.getSubject(), markSubject.getTest());
+        if (markSubject.getStage().equals(MarkStage.ROUGH_LEVEL)) {
+            successCount = paperRepo.countByWorkIdAndSubjectAndRoughLevelNotNullAndTest(workId, markSubject.getSubject(), markSubject.getTest());
+        } else if (markSubject.getStage().equals(MarkStage.LEVEL)) {
+            successCount = paperRepo.countByWorkIdAndSubjectAndLevelNotNullAndTest(workId, markSubject.getSubject(), markSubject.getTest());
+        } else if (markSubject.getStage().equals(MarkStage.SCORE)) {
+            successCount = paperRepo.countByWorkIdAndSubjectAndScoreNotNullAndTest(workId, markSubject.getSubject(), markSubject.getTest());
         }
         //所有任务数(查询所有有效试卷)
         int totalCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndTest(workId, markSubject.getSubject(), markSubject.getTest());
@@ -108,16 +116,18 @@ public class GroupingService {
     /**
      * 考区进度
      *
-     * @param workId
-     * @param markSubject
-     * @param objectMap
+     * @param workId      工作ID
+     * @param markSubject 科目
+     * @param objectMap   结果map
      */
     public void getAreaProgress(Long workId, MarkSubject markSubject, Map<String, Object> objectMap) {
-        List<Object[]> areas;
-        if (markSubject.getStage().name().equals(MarkStage.SCORE.name())) {
-            areas = markTaskRepo.listGroupByAreaName(workId, markSubject.getSubject().name());
-        } else {
-            areas = markTaskRepo.listGroupByAreaName(workId, markSubject.getSubject().name(), markSubject.getTest());
+        List<Object[]> areas = null;
+        if (markSubject.getStage().equals(MarkStage.ROUGH_LEVEL)) {
+            areas = markTaskRoughLevelRepo.listGroupByAreaName(workId, markSubject.getSubject().name(), markSubject.getTest());
+        } else if (markSubject.getStage().equals(MarkStage.LEVEL)) {
+            areas = markTaskLevelRepo.listGroupByAreaName(workId, markSubject.getSubject().name(), markSubject.getTest());
+        } else if (markSubject.getStage().name().equals(MarkStage.SCORE.name())) {
+            areas = markTaskScoreRepo.listGroupByAreaName(workId, markSubject.getSubject().name());
         }
         if (areas != null) {
             List<QuestionStatDTO> questionStatDTOs = new ArrayList<>();
@@ -132,11 +142,12 @@ public class GroupingService {
     /**
      * 各评卷员进度
      *
-     * @param workId
-     * @param markSubject
-     * @param userMarkLeaders
-     * @param isTotalMarkLeader
-     * @param objectMap
+     * @param workId            工作ID
+     * @param markSubject       科目
+     * @param userMarkLeaders   科组长
+     * @param markerId          评卷员ID
+     * @param isTotalMarkLeader 是否大科组长
+     * @param objectMap         返回对象
      */
     public void getGroupMarkersProgress(Long workId, MarkSubject markSubject, List<Long> userMarkLeaders, Long markerId, boolean isTotalMarkLeader, Map<String, Object> objectMap) {
         List<Map<String, Object>> groupMarkers = new ArrayList<>();
@@ -145,11 +156,13 @@ public class GroupingService {
             groupLeaderAndMarkers = groupLeaderAndMarkers.stream().filter(m -> m.get("markLeaders").contains(markerId)).collect(Collectors.toList());
         }
         if (!CollectionUtils.isEmpty(groupLeaderAndMarkers)) {
-            Long batchNo;
-            if (markSubject.getStage().name() == MarkStage.SCORE.name()) {
-                batchNo = paperRepo.findMaxScoreBatchNoByWorkIdAndSubject(workId, markSubject.getSubject());
-            } else {
+            Long batchNo = null;
+            if (markSubject.getStage().equals(MarkStage.ROUGH_LEVEL)) {
+                batchNo = paperRepo.findMaxRoughBatchNoByWorkIdAndSubject(workId, markSubject.getSubject());
+            } else if (markSubject.getStage().equals(MarkStage.LEVEL)) {
                 batchNo = paperRepo.findMaxBatchNoByWorkIdAndSubject(workId, markSubject.getSubject());
+            } else if (markSubject.getStage().equals(MarkStage.SCORE)) {
+                batchNo = paperRepo.findMaxScoreBatchNoByWorkIdAndSubject(workId, markSubject.getSubject());
             }
             for (Map<String, List<Long>> groupLeaderAndMarker : groupLeaderAndMarkers) {
                 Map<String, Object> tempMap = new HashMap<>();
@@ -176,16 +189,19 @@ public class GroupingService {
 
                 // 评卷员
                 //各评卷员评卷进度
-                List<Object[]> qStats;
-                if (markSubject.getStage().name() == MarkStage.SCORE.name()) {
-                    qStats = markTaskRepo.listGroupByQuestionAndMarkerAndScoreBatchNoAndMakerId(workId, markSubject.getSubject().name(), markSubject.getStage().ordinal(), batchNo, markers);
-                } else {
-                    qStats = markTaskRepo.listGroupByQuestionAndMarkerAndBatchNoAndMarkerId(workId, markSubject.getSubject().name(), markSubject.getStage().ordinal(), markSubject.getTest(), batchNo, markers);
+                List<Object[]> qStats = null;
+                if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+                    qStats = markTaskRoughLevelRepo.listGroupByQuestionAndMarkerAndBatchNoAndMarkerId(workId, markSubject.getSubject().name(), markSubject.getStage().ordinal(), markSubject.getTest(), batchNo, markers);
+                } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+                    qStats = markTaskLevelRepo.listGroupByQuestionAndMarkerAndBatchNoAndMarkerId(workId, markSubject.getSubject().name(), markSubject.getStage().ordinal(), markSubject.getTest(), batchNo, markers);
+                } else if (MarkStage.SCORE.equals(markSubject.getStage())) {
+                    qStats = markTaskScoreRepo.listGroupByQuestionAndMarkerAndScoreBatchNoAndMakerId(workId, markSubject.getSubject().name(), markSubject.getStage().ordinal(), batchNo, markers);
+
                 }
                 if (qStats != null) {
                     List<MarkQuestionStatDTO> questionStatDTOs = new ArrayList<>();
                     for (Object[] objects : qStats) {
-                        MarkQuestionStatDTO dto = questionStatAssembler.toMarkProgressDTO(objects, workId, markSubject.getSubject());
+                        MarkQuestionStatDTO dto = questionStatAssembler.toMarkProgressDTO(objects, workId, markSubject.getSubject(), markSubject.getStage());
                         questionStatDTOs.add(dto);
                     }
                     tempMap.put("markerProgress", questionStatDTOs);
@@ -199,19 +215,19 @@ public class GroupingService {
     /**
      * 总科组长进度
      *
-     * @param workId
-     * @param subject
-     * @param userMarkLeaders
-     * @param objectMap
+     * @param workId 工作ID
+     * @param markSubject 科目
+     * @param userMarkLeaders 乘组长
+     * @param objectMap 返回对象
      */
-    public void getMakerLeaderProgress(Long workId, Subject subject, List<Long> userMarkLeaders, Map<String, Object> objectMap) {
-        List<MarkUser> markUsers = markUserRepo.findByWorkIdAndSubjectAndRoleAndIdNotIn(workId, subject, Role.MARK_LEADER, userMarkLeaders);
+    public void getMakerLeaderProgress(Long workId, MarkSubject markSubject, List<Long> userMarkLeaders, Map<String, Object> objectMap) {
+        List<MarkUser> markUsers = markUserRepo.findByWorkIdAndSubjectAndRoleAndIdNotIn(workId, markSubject.getSubject(), Role.MARK_LEADER, userMarkLeaders);
         //仲裁数量
-        int arbitrate = paperRepo.countByWorkIdAndSubjectAndIsArbitratedTrue(workId, subject);
-        if (markUsers != null && markUsers.size() > 0) {
-            List<Map> mapList = new ArrayList<>();
+        int arbitrate = paperRepo.countByWorkIdAndSubjectAndIsArbitratedTrue(workId, markSubject.getSubject());
+        if (markUsers != null && !markUsers.isEmpty()) {
+            List<Map<String, Object>> mapList = new ArrayList<>();
             for (MarkUser markUser : markUsers) {
-                Map map = new HashMap();
+                Map<String, Object> map = new HashMap();
                 map.put("loginName", markUser.getLoginName());
                 map.put("name", markUser.getName());
                 map.put("arbitrated", arbitrate);

+ 280 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkTaskLevelService.java

@@ -0,0 +1,280 @@
+package cn.com.qmth.stmms.ms.marking.service;
+
+import cn.com.qmth.stmms.ms.commons.lock.LockService;
+import cn.com.qmth.stmms.ms.commons.lock.LockType;
+import cn.com.qmth.stmms.ms.commons.utils.ServletUtil;
+import cn.com.qmth.stmms.ms.commons.web.PageableDTO;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
+import cn.com.qmth.stmms.ms.core.domain.ExamQuestion;
+import cn.com.qmth.stmms.ms.core.domain.MarkStage;
+import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
+import cn.com.qmth.stmms.ms.core.domain.Paper;
+import cn.com.qmth.stmms.ms.core.domain.enums.TrialEnum;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.repository.*;
+import cn.com.qmth.stmms.ms.core.vo.Subject;
+import cn.com.qmth.stmms.ms.marking.assembler.MarkTaskLevelAssembler;
+import cn.com.qmth.stmms.ms.marking.assembler.PaperAssembler;
+import cn.com.qmth.stmms.ms.marking.dto.MarkTaskDTO;
+import cn.com.qmth.stmms.ms.marking.dto.PaperDTO;
+import org.springframework.data.domain.Page;
+import org.springframework.data.domain.PageRequest;
+import org.springframework.data.domain.Pageable;
+import org.springframework.data.domain.Sort;
+import org.springframework.data.jpa.domain.Specification;
+import org.springframework.http.HttpStatus;
+import org.springframework.http.ResponseEntity;
+import org.springframework.stereotype.Service;
+
+import javax.annotation.Resource;
+import javax.persistence.criteria.Join;
+import javax.persistence.criteria.JoinType;
+import javax.persistence.criteria.Predicate;
+import java.util.*;
+
+/**
+ * 评卷工作服务
+ */
+@Service
+public class MarkTaskLevelService {
+
+    @Resource
+    private MarkUserRepo markUserRepo;
+
+    @Resource
+    private PaperRepo paperRepo;
+
+    @Resource
+    private MarkSubjectRepo markSubjectRepo;
+
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    private ExamQuestionRepo examQuestionRepo;
+
+    @Resource
+    private MarkTaskLevelAssembler markTaskLevelAssembler;
+
+    @Resource
+    MarkingLevelService markingLevelService;
+
+    @Resource
+    private LockService lockService;
+
+    @Resource
+    private PaperAssembler paperAssembler;
+
+
+    public PageableDTO listMarkTaskLevel(Long markerId, Boolean isSample, Boolean reject, String level, Long questionId, String areaCode, Pageable pageable) {
+        Long workId = ServletUtil.getWordId();
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        MarkUser markUser = markUserRepo.findOne(markerId);
+        Long batchNo = null;
+        List<Object> batchNos = paperRepo.findBatchNoByWorkIdAndSubject(workId, markUser.getSubject().name());
+        if (batchNos != null && !batchNos.isEmpty()) {
+            Object object = batchNos.get(0);
+            batchNo = Long.valueOf(object.toString());
+        }
+
+        Long finalBatchNo = batchNo;
+        Integer levelShowAllPaper = ParamCache.levelConfigMap.get(String.valueOf(workId)).getLevelShowAllPaper();
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            List<Predicate> onPredicates = new ArrayList<>();
+            Join<MarkTaskLevel, Paper> join = root.join("paper", JoinType.INNER);
+            if (Objects.nonNull(questionId)) {
+                predicates.add(builder.equal(root.get("questionId"), questionId));
+            }
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            if (level == null) {
+                predicates.add(builder.isNull(root.get("result")));
+            } else {
+                //查询
+                predicates.add(builder.equal(root.get("result"), level));
+                if (levelShowAllPaper == 0) {
+                    if (!Objects.isNull(finalBatchNo)) {
+                        onPredicates.add(builder.equal(join.get("batchNo"), finalBatchNo));
+                    }
+                }
+            }
+            if (isSample != null) {
+                onPredicates.add(builder.equal(join.get("isSample"), isSample));
+            }
+            if (reject != null && reject) {
+                onPredicates.add(builder.equal(join.get("isRejected"), reject));
+            } else {
+                predicates.add(builder.equal(root.get("isRejected"), reject));
+            }
+            onPredicates.add(builder.isNotNull(join.get("batchNo")));
+            //过滤考区
+            if (Objects.nonNull(areaCode)) {
+                onPredicates.add(builder.equal(join.get("areaCode"), areaCode));
+            }
+            join.on(onPredicates.toArray(new Predicate[onPredicates.size()]));
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Sort sort = new Sort("randomSeq", "randomSeqNew");
+        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
+        Page<MarkTaskLevel> markTasks = markTaskLevelRepo.findAll(specification, pageable1);
+
+        if (Objects.isNull(markTasks) || markTasks.getContent().size() == 0) {
+            if (Objects.nonNull(isSample) && isSample) {
+                ExamQuestion examQuestion = examQuestionRepo.findOne(questionId);
+                MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + examQuestion.getSubject());
+                if (markSubject.getTest() == TrialEnum.DEFAULT.getId()) {
+                    List<Paper> paperList = paperRepo.findSample(level, isSample, false, examQuestion.getSubject().name(), TrialEnum.DEFAULT.getId(), examQuestion.getAreaCode(), examQuestion.getWorkId());
+                    if (Objects.nonNull(paperList) && !paperList.isEmpty()) {
+                        for (Paper p : paperList) {
+                            MarkTaskLevel markTask = new MarkTaskLevel(markUser, p, MarkStage.LEVEL, 1L);
+                            markTaskDTOs.add(markTaskLevelAssembler.toDTO(markTask));
+                        }
+                    }
+                }
+            }
+        }
+        markTasks.getContent().forEach(m -> {
+            markTaskDTOs.add(markTaskLevelAssembler.toDTO(m));
+        });
+        if (Objects.isNull(level)) {
+            randomSeqNewSort(markTaskDTOs);
+        }
+        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+    }
+
+
+    public void randomSeqNewSort(List<MarkTaskDTO> markTaskDTOs) {
+        boolean isSort = true;
+        for (MarkTaskDTO m : markTaskDTOs) {
+            if (Objects.nonNull(m.getRandomSeq())) {
+                isSort = false;
+                break;
+            }
+        }
+        if (isSort) {
+            markTaskDTOs.sort(Comparator.comparing(MarkTaskDTO::getRandomSeqNew));
+        }
+    }
+
+    public ResponseEntity markingLevel(Long markTaskId, HashMap<String, String> body) {
+        MarkTaskLevel markTask = markTaskLevelRepo.findOne(markTaskId);
+        String result = body.get("result");
+        boolean oldRejected = markTask.isRejected();
+        boolean oldShift = markTask.getPaper().isShift();
+        boolean oldShiftScore = markTask.getPaper().isShiftScore();
+        if (result == null) {
+            return new ResponseEntity(HttpStatus.BAD_REQUEST);
+        }
+        try {
+            lockService.waitlock(LockType.LEVEL, markTask.getPaper().getId());
+            markingLevelService.levelMark(markTask, result);
+        } catch (Exception e) {
+            throw new RuntimeException("分档异常");
+        } finally {
+            lockService.unlock(LockType.LEVEL, markTask.getPaper().getId());
+        }
+        return new ResponseEntity(markTaskLevelAssembler.toDTO(markTask, oldRejected, oldShift, oldShiftScore), HttpStatus.OK);
+    }
+
+    public ResponseEntity skipLevel(Long markTaskId) {
+        MarkTaskLevel markTask = markingLevelService.skip(markTaskId);
+        return new ResponseEntity(markTaskLevelAssembler.toDTO(markTask), HttpStatus.OK);
+    }
+
+    public boolean updateMarkTaskMarkById(Long markTaskId, Boolean isMark) {
+        markTaskLevelRepo.updateMarkTaskMarkById(markTaskId, isMark);
+        return true;
+    }
+
+    public List<MarkTaskDTO> reviewPaperLevel(Long markerId, Long questionId, String areaCode) {
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        Sort sort = new Sort(Sort.Direction.DESC, "updatedOn");
+        Pageable pageable = new PageRequest(0, 5, sort);
+        Long batchNo = paperRepo.findByQuestionId(questionId);
+        ;
+
+        Long finalBatchNo = batchNo;
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            if (Objects.nonNull(questionId)) {
+                predicates.add(builder.equal(root.get("questionId"), questionId));
+            }
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            //查询
+            if (!Objects.isNull(finalBatchNo)) {
+                predicates.add(builder.equal(root.get("paper").get("batchNo"), finalBatchNo));
+            }
+            predicates.add(builder.isNotNull(root.get("result")));
+            //分档需要过滤标准卷
+            predicates.add(builder.equal(root.get("paper").get("isSample"), false));
+            //过滤考区
+            if (Objects.nonNull(areaCode)) {
+                predicates.add(builder.equal(root.get("paper").get("areaCode"), areaCode));
+            }
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Page<MarkTaskLevel> markTasks = markTaskLevelRepo.findAll(specification, pageable);
+        markTasks.getContent().forEach(m -> {
+            markTaskDTOs.add(markTaskLevelAssembler.toDTO(m));
+        });
+        return markTaskDTOs;
+    }
+
+    public PageableDTO listMarkedTaskLevel(Long workId, Subject subject, Long markerId, Pageable pageable) {
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            predicates.add(builder.equal(root.get("workId"), workId));
+            predicates.add(builder.equal(root.get("subject"), subject));
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            predicates.add(builder.equal(root.get("isMark"), true));
+            return builder.and(predicates.toArray(new Predicate[0]));
+        };
+        Page<MarkTaskLevel> markTasks = markTaskLevelRepo.findAll(specification, pageable);
+
+        markTasks.getContent().forEach(m -> markTaskDTOs.add(markTaskLevelAssembler.toDTO(m)));
+        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+    }
+
+    public List<MarkTaskLevel> getBySecretNumberLevel(Long workId, Subject subject, String secretNumber, int test) {
+        return markTaskLevelRepo.findByWorkIdAndSubjectAndSecretNumberAndTest(workId, subject, secretNumber, test);
+    }
+
+    public PageableDTO shiftLevel(Long markerId, Long workId, Boolean isShift, Boolean isShiftScore, Long questionId, Pageable pageable) {
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            predicates.add(builder.equal(root.get("questionId"), questionId));
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            //查询
+            predicates.add(builder.equal(root.get("paper").get("isShift"), isShift));
+            predicates.add(builder.equal(root.get("stage"), MarkStage.LEVEL));
+            predicates.add(builder.isNull(root.get("result")));
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Sort sort = new Sort("paper.level", "serialNumber", "randomSeq");
+        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
+        Page<MarkTaskLevel> markTasks = markTaskLevelRepo.findAll(specification, pageable1);
+
+        markTasks.getContent().forEach(m -> markTaskDTOs.add(markTaskLevelAssembler.toShiftDTO(m)));
+        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+    }
+
+    public PaperDTO getByTaskSecretNumberLevel(Long questionId, String sn) {
+        PaperDTO paperDTO = null;
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            predicates.add(builder.equal(root.get("paper").get("questionId"), questionId));
+            if (sn != null) {
+                predicates.add(builder.equal(root.get("secretNumber"), sn));
+            }
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Optional<MarkTaskLevel> taskOptional = markTaskLevelRepo.findAll(specification, new PageRequest(0, 1)).getContent().stream().findFirst();
+        if (taskOptional.isPresent()) {
+            paperDTO = paperAssembler.toDTO(taskOptional.get().getPaper());
+        }
+        return paperDTO;
+    }
+}

+ 281 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkTaskRoughLevelService.java

@@ -0,0 +1,281 @@
+package cn.com.qmth.stmms.ms.marking.service;
+
+import cn.com.qmth.stmms.ms.commons.lock.LockService;
+import cn.com.qmth.stmms.ms.commons.lock.LockType;
+import cn.com.qmth.stmms.ms.commons.utils.ServletUtil;
+import cn.com.qmth.stmms.ms.commons.web.PageableDTO;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
+import cn.com.qmth.stmms.ms.core.domain.ExamQuestion;
+import cn.com.qmth.stmms.ms.core.domain.MarkStage;
+import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
+import cn.com.qmth.stmms.ms.core.domain.Paper;
+import cn.com.qmth.stmms.ms.core.domain.enums.TrialEnum;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskRoughLevel;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.repository.*;
+import cn.com.qmth.stmms.ms.core.vo.Subject;
+import cn.com.qmth.stmms.ms.marking.assembler.MarkTaskRoughLevelAssembler;
+import cn.com.qmth.stmms.ms.marking.assembler.PaperAssembler;
+import cn.com.qmth.stmms.ms.marking.dto.MarkTaskDTO;
+import cn.com.qmth.stmms.ms.marking.dto.PaperDTO;
+import org.springframework.data.domain.Page;
+import org.springframework.data.domain.PageRequest;
+import org.springframework.data.domain.Pageable;
+import org.springframework.data.domain.Sort;
+import org.springframework.data.jpa.domain.Specification;
+import org.springframework.http.HttpStatus;
+import org.springframework.http.ResponseEntity;
+import org.springframework.stereotype.Service;
+
+import javax.annotation.Resource;
+import javax.persistence.criteria.Join;
+import javax.persistence.criteria.JoinType;
+import javax.persistence.criteria.Predicate;
+import java.util.*;
+
+/**
+ * 评卷工作服务
+ */
+@Service
+public class MarkTaskRoughLevelService {
+
+    @Resource
+    private MarkUserRepo markUserRepo;
+
+    @Resource
+    private PaperRepo paperRepo;
+
+    @Resource
+    private MarkSubjectRepo markSubjectRepo;
+
+    @Resource
+    private MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Resource
+    private ExamQuestionRepo examQuestionRepo;
+
+    @Resource
+    private MarkTaskRoughLevelAssembler markTaskRoughLevelAssembler;
+
+    @Resource
+    MarkingRoughLevelService markingRoughLevelService;
+
+    @Resource
+    private LockService lockService;
+
+    @Resource
+    private PaperAssembler paperAssembler;
+
+
+    public PageableDTO listMarkTaskLevel(Long markerId, Boolean isSample, Boolean reject, String level, Long questionId, String areaCode, Pageable pageable) {
+        Long workId = ServletUtil.getWordId();
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        MarkUser markUser = markUserRepo.findOne(markerId);
+        Long batchNo = null;
+        List<Object> batchNos = paperRepo.findRoughBatchNoByWorkIdAndSubject(workId, markUser.getSubject().name());
+        if (batchNos != null && !batchNos.isEmpty()) {
+            Object object = batchNos.get(0);
+            batchNo = Long.valueOf(object.toString());
+        }
+
+        Long finalBatchNo = batchNo;
+        Integer levelShowAllPaper = ParamCache.levelConfigMap.get(String.valueOf(workId)).getLevelShowAllPaper();
+        Specification<MarkTaskRoughLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            List<Predicate> onPredicates = new ArrayList<>();
+            Join<MarkTaskRoughLevel, Paper> join = root.join("paper", JoinType.INNER);
+            if (Objects.nonNull(questionId)) {
+                predicates.add(builder.equal(root.get("questionId"), questionId));
+            }
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            if (level == null) {
+                predicates.add(builder.isNull(root.get("result")));
+            } else {
+                //查询
+                predicates.add(builder.equal(root.get("result"), level));
+                if (levelShowAllPaper == 0) {
+                    if (!Objects.isNull(finalBatchNo)) {
+                        onPredicates.add(builder.equal(join.get("roughBatchNo"), finalBatchNo));
+                    }
+                }
+            }
+            if (isSample != null) {
+                onPredicates.add(builder.equal(join.get("isRoughSample"), isSample));
+            }
+            if (reject != null && reject) {
+                onPredicates.add(builder.equal(join.get("isRejected"), reject));
+            } else {
+                predicates.add(builder.equal(root.get("isRejected"), reject));
+            }
+            onPredicates.add(builder.isNotNull(join.get("roughBatchNo")));
+            //过滤考区
+            if (Objects.nonNull(areaCode)) {
+                onPredicates.add(builder.equal(join.get("areaCode"), areaCode));
+            }
+            join.on(onPredicates.toArray(new Predicate[onPredicates.size()]));
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Sort sort = new Sort("randomSeq", "randomSeqNew");
+        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
+        Page<MarkTaskRoughLevel> markTasks = markTaskRoughLevelRepo.findAll(specification, pageable1);
+
+        if (Objects.isNull(markTasks) || markTasks.getContent().isEmpty()) {
+            if (Objects.nonNull(isSample) && isSample) {
+                ExamQuestion examQuestion = examQuestionRepo.findOne(questionId);
+                MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + examQuestion.getSubject());
+                if (markSubject.getTest() == TrialEnum.DEFAULT.getId()) {
+                    List<Paper> paperList = paperRepo.findSample(level, isSample, false, examQuestion.getSubject().name(), TrialEnum.DEFAULT.getId(), examQuestion.getAreaCode(), examQuestion.getWorkId());
+                    if (Objects.nonNull(paperList) && !paperList.isEmpty()) {
+                        for (Paper p : paperList) {
+                            MarkTaskRoughLevel markTask = new MarkTaskRoughLevel(markUser, p, MarkStage.LEVEL, 1L);
+                            markTaskDTOs.add(markTaskRoughLevelAssembler.toDTO(markTask));
+                        }
+                    }
+                }
+            }
+        }
+        markTasks.getContent().forEach(m -> {
+            markTaskDTOs.add(markTaskRoughLevelAssembler.toDTO(m));
+        });
+        if (Objects.isNull(level)) {
+            randomSeqNewSort(markTaskDTOs);
+        }
+        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+    }
+
+
+    public void randomSeqNewSort(List<MarkTaskDTO> markTaskDTOs) {
+        boolean isSort = true;
+        for (MarkTaskDTO m : markTaskDTOs) {
+            if (Objects.nonNull(m.getRandomSeq())) {
+                isSort = false;
+                break;
+            }
+        }
+        if (isSort) {
+            markTaskDTOs.sort(Comparator.comparing(MarkTaskDTO::getRandomSeqNew));
+        }
+    }
+
+    public ResponseEntity markingLevel(Long markTaskId, HashMap<String, String> body) {
+        MarkTaskRoughLevel markTask = markTaskRoughLevelRepo.findOne(markTaskId);
+        String result = body.get("result");
+        boolean oldRejected = markTask.isRejected();
+        boolean oldShift = markTask.getPaper().isShift();
+        boolean oldShiftScore = markTask.getPaper().isShiftScore();
+        if (result == null) {
+            return new ResponseEntity(HttpStatus.BAD_REQUEST);
+        }
+        try {
+            lockService.waitlock(LockType.ROUGH_LEVEL, markTask.getPaper().getId());
+            markingRoughLevelService.levelMark(markTask, result);
+        } catch (Exception e) {
+            throw new RuntimeException("分档异常");
+        } finally {
+            lockService.unlock(LockType.ROUGH_LEVEL, markTask.getPaper().getId());
+        }
+        return new ResponseEntity(markTaskRoughLevelAssembler.toDTO(markTask, oldRejected, oldShift, oldShiftScore), HttpStatus.OK);
+    }
+
+    public ResponseEntity skipLevel(Long markTaskId) {
+        MarkTaskRoughLevel markTask = markingRoughLevelService.skip(markTaskId);
+        return new ResponseEntity(markTaskRoughLevelAssembler.toDTO(markTask), HttpStatus.OK);
+    }
+
+    public boolean updateMarkTaskMarkById(Long markTaskId, Boolean isMark) {
+        markTaskRoughLevelRepo.updateMarkTaskMarkById(markTaskId, isMark);
+        return true;
+    }
+
+    public List<MarkTaskDTO> reviewPaperLevel(Long markerId, Long questionId, String areaCode) {
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        Sort sort = new Sort(Sort.Direction.DESC, "updatedOn");
+        Pageable pageable = new PageRequest(0, 5, sort);
+        Long batchNo = paperRepo.findByQuestionId(questionId);
+        ;
+
+        Long finalBatchNo = batchNo;
+        Specification<MarkTaskRoughLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            if (Objects.nonNull(questionId)) {
+                predicates.add(builder.equal(root.get("questionId"), questionId));
+            }
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            //查询
+            if (!Objects.isNull(finalBatchNo)) {
+                predicates.add(builder.equal(root.get("paper").get("batchNo"), finalBatchNo));
+            }
+            predicates.add(builder.isNotNull(root.get("result")));
+            //分档需要过滤标准卷
+            predicates.add(builder.equal(root.get("paper").get("isSample"), false));
+            //过滤考区
+            if (Objects.nonNull(areaCode)) {
+                predicates.add(builder.equal(root.get("paper").get("areaCode"), areaCode));
+            }
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Page<MarkTaskRoughLevel> markTasks = markTaskRoughLevelRepo.findAll(specification, pageable);
+        markTasks.getContent().forEach(m -> {
+            markTaskDTOs.add(markTaskRoughLevelAssembler.toDTO(m));
+        });
+        return markTaskDTOs;
+    }
+
+    public PageableDTO listMarkedTaskLevel(Long workId, Subject subject, Long markerId, Pageable pageable) {
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            predicates.add(builder.equal(root.get("workId"), workId));
+            predicates.add(builder.equal(root.get("subject"), subject));
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            predicates.add(builder.equal(root.get("isMark"), true));
+            return builder.and(predicates.toArray(new Predicate[0]));
+        };
+        Page<MarkTaskRoughLevel> markTasks = markTaskRoughLevelRepo.findAll(specification, pageable);
+
+        markTasks.getContent().forEach(m -> markTaskDTOs.add(markTaskRoughLevelAssembler.toDTO(m)));
+        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+    }
+
+    public List<MarkTaskRoughLevel> getBySecretNumberLevel(Long workId, Subject subject, String secretNumber, int test) {
+        return markTaskRoughLevelRepo.findByWorkIdAndSubjectAndSecretNumberAndTest(workId, subject, secretNumber, test);
+    }
+
+    public PageableDTO shiftLevel(Long markerId, Long workId, Boolean isShift, Boolean isShiftScore, Long questionId, Pageable pageable) {
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            predicates.add(builder.equal(root.get("questionId"), questionId));
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            //查询
+            predicates.add(builder.equal(root.get("paper").get("isShift"), isShift));
+            predicates.add(builder.equal(root.get("stage"), MarkStage.LEVEL));
+            predicates.add(builder.isNull(root.get("result")));
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Sort sort = new Sort("paper.level", "serialNumber", "randomSeq");
+        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
+        Page<MarkTaskRoughLevel> markTasks = markTaskRoughLevelRepo.findAll(specification, pageable1);
+
+        markTasks.getContent().forEach(m -> markTaskDTOs.add(markTaskRoughLevelAssembler.toShiftDTO(m)));
+        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+    }
+
+    public PaperDTO getByTaskSecretNumberLevel(Long questionId, String sn) {
+        PaperDTO paperDTO = null;
+        Specification<MarkTaskLevel> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            predicates.add(builder.equal(root.get("paper").get("questionId"), questionId));
+            if (sn != null) {
+                predicates.add(builder.equal(root.get("secretNumber"), sn));
+            }
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Optional<MarkTaskRoughLevel> taskOptional = markTaskRoughLevelRepo.findAll(specification, new PageRequest(0, 1)).getContent().stream().findFirst();
+        if (taskOptional.isPresent()) {
+            paperDTO = paperAssembler.toDTO(taskOptional.get().getPaper());
+        }
+        return paperDTO;
+    }
+}

+ 260 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkTaskScoreService.java

@@ -0,0 +1,260 @@
+package cn.com.qmth.stmms.ms.marking.service;
+
+import cn.com.qmth.stmms.ms.commons.lock.LockService;
+import cn.com.qmth.stmms.ms.commons.lock.LockType;
+import cn.com.qmth.stmms.ms.commons.utils.ServletUtil;
+import cn.com.qmth.stmms.ms.commons.web.PageableDTO;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
+import cn.com.qmth.stmms.ms.core.domain.ExamQuestion;
+import cn.com.qmth.stmms.ms.core.domain.MarkStage;
+import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
+import cn.com.qmth.stmms.ms.core.domain.Paper;
+import cn.com.qmth.stmms.ms.core.domain.enums.TrialEnum;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskScore;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.repository.*;
+import cn.com.qmth.stmms.ms.core.vo.Subject;
+import cn.com.qmth.stmms.ms.marking.assembler.MarkTaskScoreAssembler;
+import cn.com.qmth.stmms.ms.marking.assembler.PaperAssembler;
+import cn.com.qmth.stmms.ms.marking.dto.MarkTaskDTO;
+import cn.com.qmth.stmms.ms.marking.dto.PaperDTO;
+import org.springframework.data.domain.Page;
+import org.springframework.data.domain.PageRequest;
+import org.springframework.data.domain.Pageable;
+import org.springframework.data.domain.Sort;
+import org.springframework.data.jpa.domain.Specification;
+import org.springframework.http.HttpStatus;
+import org.springframework.http.ResponseEntity;
+import org.springframework.stereotype.Service;
+
+import javax.annotation.Resource;
+import javax.persistence.criteria.Join;
+import javax.persistence.criteria.JoinType;
+import javax.persistence.criteria.Predicate;
+import java.util.*;
+
+/**
+ * 评卷工作服务
+ */
+@Service
+public class MarkTaskScoreService {
+
+    @Resource
+    private MarkUserRepo markUserRepo;
+
+    @Resource
+    private PaperRepo paperRepo;
+
+    @Resource
+    private MarkSubjectRepo markSubjectRepo;
+
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
+
+    @Resource
+    private ExamQuestionRepo examQuestionRepo;
+
+    @Resource
+    private MarkingScoreService markingScoreService;
+
+    @Resource
+    private LockService lockService;
+
+    @Resource
+    private PaperAssembler paperAssembler;
+
+    @Resource
+    private MarkTaskScoreAssembler markTaskScoreAssembler;
+
+    public PageableDTO listMarkTaskScore(Long markerId, Boolean isSample, Boolean reject, String level, Long questionId, String areaCode, Pageable pageable) {
+        Long workId = ServletUtil.getWordId();
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        MarkUser markUser = markUserRepo.findOne(markerId);
+        Long scoreBatchNo = null;
+        List<Object> batchNos = paperRepo.findScoreBatchNoByWorkIdAndSubject(workId, markUser.getSubject().name());
+        if (batchNos != null && !batchNos.isEmpty()) {
+            Object object = batchNos.get(0);
+            scoreBatchNo = Long.valueOf(object.toString());
+        }
+        Long finalScoreBatchNo = scoreBatchNo;
+        Integer scoreShowAllPaper = ParamCache.scoreConfigMap.get(String.valueOf(workId)).getScoreShowAllPaper();
+        Specification<MarkTaskScore> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            List<Predicate> onPredicates = new ArrayList<>();
+            Join<MarkTaskScore, Paper> join = root.join("paper", JoinType.INNER);
+            if (Objects.nonNull(questionId)) {
+                predicates.add(builder.equal(root.get("questionId"), questionId));
+            }
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            if (level == null) {
+                predicates.add(builder.isNull(root.get("result")));
+                onPredicates.add(builder.equal(join.get("isShift"), false));
+                onPredicates.add(builder.equal(join.get("isShiftScore"), false));
+            } else {
+                onPredicates.add(builder.equal(join.get("level"), level));
+                predicates.add(builder.isNotNull(root.get("result")));
+                onPredicates.add(builder.equal(join.get("isShift"), false));
+                if (scoreShowAllPaper == 1) {
+                    onPredicates.add(builder.isNotNull(join.get("scoreBatchNo")));
+                } else {
+                    onPredicates.add(builder.equal(join.get("scoreBatchNo"), finalScoreBatchNo));
+                }
+            }
+            if (isSample != null) {
+                onPredicates.add(builder.equal(join.get("isSample"), isSample));
+            }
+            if (reject != null && reject) {
+                onPredicates.add(builder.equal(join.get("isRejected"), reject));
+            } else {
+                predicates.add(builder.equal(root.get("isRejected"), reject));
+            }
+            onPredicates.add(builder.equal(join.get("active"), true));
+            //过滤考区
+            if (Objects.nonNull(areaCode)) {
+                onPredicates.add(builder.equal(join.get("areaCode"), areaCode));
+            }
+            join.on(onPredicates.toArray(new Predicate[onPredicates.size()]));
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Sort sort = new Sort("randomSeq", "randomSeqNew");
+        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
+        Page<MarkTaskScore> markTasks = markTaskScoreRepo.findAll(specification, pageable1);
+
+        if (Objects.isNull(markTasks) || markTasks.getContent().size() == 0) {
+            if (Objects.nonNull(isSample) && isSample) {
+                ExamQuestion examQuestion = examQuestionRepo.findOne(questionId);
+                MarkSubject markSubject = markSubjectRepo.findOne(workId + "-" + examQuestion.getSubject());
+                if (markSubject.getTest() == TrialEnum.DEFAULT.getId()) {
+                    List<Paper> paperList = paperRepo.findSample(level, isSample, false, examQuestion.getSubject().name(), TrialEnum.DEFAULT.getId(), examQuestion.getAreaCode(), examQuestion.getWorkId());
+                    if (Objects.nonNull(paperList) && !paperList.isEmpty()) {
+                        for (Paper p : paperList) {
+                            MarkTaskScore markTask = new MarkTaskScore(markUser, p, MarkStage.SCORE, 1L);
+                            markTaskDTOs.add(markTaskScoreAssembler.toDTO(markTask));
+                        }
+                    }
+                }
+            }
+        }
+        markTasks.getContent().forEach(m -> {
+            markTaskDTOs.add(markTaskScoreAssembler.toDTO(m));
+        });
+        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+    }
+
+    public ResponseEntity markingScore(Long markTaskId, HashMap<String, String> body) {
+        MarkTaskScore markTask = markTaskScoreRepo.getOne(markTaskId);
+        String result = body.get("result");
+        boolean oldRejected = markTask.isRejected();
+        boolean oldShift = markTask.getPaper().isShift();
+        boolean oldShiftScore = markTask.getPaper().isShiftScore();
+        if (result == null) {
+            return new ResponseEntity(HttpStatus.BAD_REQUEST);
+        }
+        int score = Integer.parseInt(result);
+        try {
+            lockService.waitlock(LockType.SCORE, markTask.getPaper().getId());
+            markingScoreService.scoring(markTask, score);
+        } catch (Exception e) {
+            throw new RuntimeException("打分异常");
+        } finally {
+            lockService.unlock(LockType.SCORE, markTask.getPaper().getId());
+        }
+        return new ResponseEntity(markTaskScoreAssembler.toDTO(markTask, oldRejected, oldShift, oldShiftScore), HttpStatus.OK);
+    }
+
+    public ResponseEntity skipScore(Long markTaskId) {
+        MarkTaskScore markTask = markingScoreService.skip(markTaskId);
+        return new ResponseEntity(markTaskScoreAssembler.toDTO(markTask), HttpStatus.OK);
+    }
+
+    public boolean updateMarkTaskMarkById(Long markTaskId, Boolean isMark) {
+        markTaskScoreRepo.updateMarkTaskMarkById(markTaskId, isMark);
+        return true;
+    }
+
+    public List<MarkTaskDTO> reviewPaperScore(Long markerId, Long questionId, String areaCode) {
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        Sort sort = new Sort(Sort.Direction.DESC, "updatedOn");
+        Pageable pageable = new PageRequest(0, 5, sort);
+        Long scoreBatchNo = paperRepo.findScoreBatchNoByQuestionId(questionId);
+
+        Long finalScoreBatchNo = scoreBatchNo;
+        Specification<MarkTaskScore> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            if (Objects.nonNull(questionId)) {
+                predicates.add(builder.equal(root.get("questionId"), questionId));
+            }
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            predicates.add(builder.isNotNull(root.get("result")));
+            if (!Objects.isNull(finalScoreBatchNo)) {
+                predicates.add(builder.equal(root.get("paper").get("scoreBatchNo"), finalScoreBatchNo));
+            }
+            //过滤考区
+            if (Objects.nonNull(areaCode)) {
+                predicates.add(builder.equal(root.get("paper").get("areaCode"), areaCode));
+            }
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Page<MarkTaskScore> markTasks = markTaskScoreRepo.findAll(specification, pageable);
+        markTasks.getContent().forEach(m -> {
+            markTaskDTOs.add(markTaskScoreAssembler.toDTO(m));
+        });
+        return markTaskDTOs;
+    }
+
+    public PageableDTO listMarkedTaskScore(Long workId, Subject subject, Long markerId, Pageable pageable) {
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        Specification<MarkTaskScore> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            predicates.add(builder.equal(root.get("workId"), workId));
+            predicates.add(builder.equal(root.get("subject"), subject));
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            predicates.add(builder.equal(root.get("isMark"), true));
+            return builder.and(predicates.toArray(new Predicate[0]));
+        };
+        Page<MarkTaskScore> markTasks = markTaskScoreRepo.findAll(specification, pageable);
+
+        markTasks.getContent().forEach(m -> markTaskDTOs.add(markTaskScoreAssembler.toDTO(m)));
+        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+    }
+
+    public List<MarkTaskScore> getBySecretNumberScore(Long workId, Subject subject, String secretNumber, int test) {
+        return markTaskScoreRepo.findByWorkIdAndSubjectAndSecretNumberAndTest(workId, subject, secretNumber, test);
+    }
+
+    public PageableDTO shiftScore(Long markerId, Long workId, Boolean isShift, Boolean isShiftScore, Long questionId, Pageable pageable) {
+        List<MarkTaskDTO> markTaskDTOs = new ArrayList<>();
+        Specification<MarkTaskScore> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            predicates.add(builder.equal(root.get("questionId"), questionId));
+            predicates.add(builder.equal(root.get("markerId"), markerId));
+            predicates.add(builder.equal(root.get("paper").get("isShiftScore"), isShiftScore));
+            predicates.add(builder.equal(root.get("stage"), MarkStage.SCORE));
+            predicates.add(builder.isNull(root.get("result")));
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Sort sort = new Sort("paper.level", "serialNumber", "randomSeq");
+        Pageable pageable1 = new PageRequest(pageable.getPageNumber(), pageable.getPageSize(), sort);
+        Page<MarkTaskScore> markTasks = markTaskScoreRepo.findAll(specification, pageable1);
+
+        markTasks.getContent().forEach(m -> markTaskDTOs.add(markTaskScoreAssembler.toShiftDTO(m)));
+        return new PageableDTO(markTaskDTOs, markTasks.getTotalElements(), markTasks.getTotalPages(), pageable.getPageNumber());
+    }
+
+    public PaperDTO getByTaskSecretNumberLevel(Long questionId, String sn) {
+        PaperDTO paperDTO = null;
+        Specification<MarkTaskScore> specification = (root, query, builder) -> {
+            List<Predicate> predicates = new ArrayList<>();
+            predicates.add(builder.equal(root.get("paper").get("questionId"), questionId));
+            if (sn != null) {
+                predicates.add(builder.equal(root.get("secretNumber"), sn));
+            }
+            return builder.and(predicates.toArray(new Predicate[predicates.size()]));
+        };
+        Optional<MarkTaskScore> taskOptional = markTaskScoreRepo.findAll(specification, new PageRequest(0, 1)).getContent().stream().findFirst();
+        if (taskOptional.isPresent()) {
+            paperDTO = paperAssembler.toDTO(taskOptional.get().getPaper());
+        }
+        return paperDTO;
+    }
+}

+ 46 - 18
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkerGroupLeaderService.java

@@ -1,5 +1,6 @@
 package cn.com.qmth.stmms.ms.marking.service;
 
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
 import cn.com.qmth.stmms.ms.core.domain.MarkStage;
 import cn.com.qmth.stmms.ms.core.domain.MarkSubject;
 import cn.com.qmth.stmms.ms.core.domain.Paper;
@@ -7,12 +8,8 @@ import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkerGroup;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkerGroupLeader;
 import cn.com.qmth.stmms.ms.core.domain.user.Role;
-import cn.com.qmth.stmms.ms.core.repository.MarkTaskRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkUserRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkerGroupLeaderRepo;
-import cn.com.qmth.stmms.ms.core.repository.MarkerGroupRepo;
+import cn.com.qmth.stmms.ms.core.repository.*;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
-import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 import org.springframework.util.CollectionUtils;
@@ -31,7 +28,13 @@ public class MarkerGroupLeaderService {
     private MarkUserRepo markUserRepo;
 
     @Resource
-    private MarkTaskRepo markTaskRepo;
+    private MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     @Resource
     private MarkerGroupRepo markerGroupRepo;
@@ -43,13 +46,12 @@ public class MarkerGroupLeaderService {
      * 创建分组
      *
      * @param markerGroup
-     * @param stage
      * @return
      */
     @Transactional
-    public MarkerGroup save(MarkerGroup markerGroup, MarkStage stage) {
+    public MarkerGroup save(MarkerGroup markerGroup) {
         if (Objects.nonNull(markerGroup.getId())) {
-            markerGroupLeaderRepo.deleteByWorkIdAndSubjectAndStageAndGroupId(markerGroup.getWorkId(), markerGroup.getSubject(), stage, markerGroup.getId());
+            markerGroupLeaderRepo.deleteByWorkIdAndSubjectAndStageAndGroupId(markerGroup.getWorkId(), markerGroup.getSubject(), markerGroup.getStage(), markerGroup.getId());
         }
         Set<MarkUser> groupMarkers = markerGroup.getMarkers();
         List<MarkUser> markLeaders = groupMarkers.stream().filter(m -> Role.MARK_LEADER.equals(m.getRole())).collect(Collectors.toList());
@@ -65,7 +67,7 @@ public class MarkerGroupLeaderService {
                     MarkerGroupLeader markerGroupLeader = new MarkerGroupLeader();
                     markerGroupLeader.setWorkId(markerGroup.getWorkId());
                     markerGroupLeader.setSubject(markerGroup.getSubject());
-                    markerGroupLeader.setStage(stage);
+                    markerGroupLeader.setStage(markerGroup.getStage());
                     markerGroupLeader.setGroupId(group.getId());
                     markerGroupLeader.setGroupName(group.getName());
                     markerGroupLeader.setMarkLeaderId(markLeader.getId());
@@ -88,15 +90,28 @@ public class MarkerGroupLeaderService {
     @Transactional
     public void delete(MarkSubject markSubject, MarkerGroup domain) {
         int count = 0;
-        if (MarkStage.LEVEL == markSubject.getStage() || MarkStage.SCORE == markSubject.getStage()) {
-            count = markTaskRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage());
+        MarkStage stage = markSubject.getStage();
+        if (MarkStage.INIT.equals(markSubject.getStage())) {
+            if (ParamCache.levelConfigMap.get(String.valueOf(markSubject.getWorkId())).getRoughLevel() == 1) {
+                stage = MarkStage.ROUGH_LEVEL;
+                count = markTaskRoughLevelRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), stage);
+            } else {
+                stage = MarkStage.LEVEL;
+                count = markTaskLevelRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), stage);
+            }
+        } else if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+            count = markTaskRoughLevelRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), stage);
+        } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+            count = markTaskLevelRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), stage);
+        } else if (MarkStage.SCORE.equals(markSubject.getStage())) {
+            count = markTaskScoreRepo.countByWorkIdAndSubjectAndStage(markSubject.getWorkId(), markSubject.getSubject(), stage);
         }
         if (count > 0) {
             throw new RuntimeException("当前阶段已发布任务,不能删除分组");
         }
         markerGroupRepo.delete(domain);
 
-        markerGroupLeaderRepo.deleteByWorkIdAndSubjectAndStageAndGroupId(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getStage(), domain.getId());
+        markerGroupLeaderRepo.deleteByWorkIdAndSubjectAndStageAndGroupId(markSubject.getWorkId(), markSubject.getSubject(), stage, domain.getId());
     }
 
     /**
@@ -135,7 +150,13 @@ public class MarkerGroupLeaderService {
      * @return
      */
     public List<Long> listPaperIdsByWorkIdAndSubjectAndStageAndMarkerIds(Long workId, Subject subject, MarkStage stage, List<Long> markers) {
-        List<Paper> papers = markTaskRepo.findByWorkIdAndSubjectAndStageAndMarkerIdIn(workId, subject, stage, markers);
+        List<Paper> papers = null;
+        if (MarkStage.LEVEL.equals(stage)) {
+            papers = markTaskLevelRepo.findByWorkIdAndSubjectAndStageAndMarkerIdIn(workId, subject, stage, markers);
+        } else if (MarkStage.SCORE.equals(stage)) {
+            papers = markTaskScoreRepo.findByWorkIdAndSubjectAndStageAndMarkerIdIn(workId, subject, stage, markers);
+        }
+
         if (!CollectionUtils.isEmpty(papers)) {
             return papers.stream().map(Paper::getId).distinct().collect(Collectors.toList());
         }
@@ -143,7 +164,14 @@ public class MarkerGroupLeaderService {
     }
 
     public List<Long> listPaperIdsByWorkIdAndSubjectAndStage(Long workId, Subject subject, MarkStage stage, List<Long> markers) {
-        List<Object[]> papers = markTaskRepo.findByWorkIdAndSubjectAndStage(workId, subject.name(), stage.ordinal());
+        List<Object[]> papers = null;
+        if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+            papers = markTaskRoughLevelRepo.findByWorkIdAndSubjectAndStage(workId, subject.name(), stage.ordinal());
+        }  else if (MarkStage.LEVEL.equals(stage)) {
+            papers = markTaskLevelRepo.findByWorkIdAndSubjectAndStage(workId, subject.name(), stage.ordinal());
+        } else if (MarkStage.SCORE.equals(stage)) {
+            papers = markTaskScoreRepo.findByWorkIdAndSubjectAndStage(workId, subject.name(), stage.ordinal());
+        }
         if (!CollectionUtils.isEmpty(papers)) {
             return papers.stream().filter(m -> markers.contains(Long.valueOf(m[1].toString()))).map(m -> Long.valueOf(m[0].toString())).distinct().collect(Collectors.toList());
         }
@@ -214,15 +242,15 @@ public class MarkerGroupLeaderService {
      */
     public List<MarkUser> listGroupUsersByWorkIdAndSubjectAndStageAndMarkerId(Long workId, Subject subject, MarkStage stage, Long markerId) {
         MarkUser markUser = markUserRepo.getOne(markerId);
-        if(markUser == null){
+        if (markUser == null) {
             return null;
         }
 
-        if(markUser.getGroupId() == null){
+        if (markUser.getGroupId() == null) {
             return markUserRepo.findByWorkIdAndSubjectAndRole(workId, subject, Role.MARKER);
         } else {
             List<MarkerGroupLeader> markerGroupLeaders = markerGroupLeaderRepo.findByWorkIdAndSubjectAndStageAndGroupId(workId, subject, stage, markUser.getGroupId());
-            if(markerGroupLeaders == null){
+            if (markerGroupLeaders == null) {
                 return null;
             } else {
                 List<Long> markerIds = markerGroupLeaders.stream().map(MarkerGroupLeader::getMarkerId).distinct().collect(Collectors.toList());

+ 384 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkingLevelService.java

@@ -0,0 +1,384 @@
+package cn.com.qmth.stmms.ms.marking.service;
+
+import cn.com.qmth.stmms.ms.commons.config.LevelConfig;
+import cn.com.qmth.stmms.ms.commons.constant.ArbitrateCallback;
+import cn.com.qmth.stmms.ms.commons.constant.ArbitrateResult;
+import cn.com.qmth.stmms.ms.core.cache.CacheService;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
+import cn.com.qmth.stmms.ms.core.domain.*;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.domain.user.Role;
+import cn.com.qmth.stmms.ms.core.repository.*;
+import cn.com.qmth.stmms.ms.marking.config.MarkingConfig;
+import cn.com.qmth.stmms.ms.marking.service.arbitration.ArbitrationService;
+import com.alibaba.fastjson.JSONObject;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import javax.annotation.Resource;
+import java.util.*;
+import java.util.stream.Collectors;
+
+/**
+ * 评卷,分档仲裁及打分服务
+ * Created by zhengmin on 2016/9/23.
+ */
+@Service
+public class MarkingLevelService {
+
+    private static final Logger LOG = LoggerFactory.getLogger(MarkingLevelService.class);
+    @Autowired
+    private MarkingConfig markingConfig;
+
+    @Autowired
+    private DetermineLevelService determineLevelService;
+
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Autowired
+    private MarkUserRepo markUserRepo;
+
+    @Autowired
+    private PaperRepo paperRepo;
+
+    @Autowired
+    private LevelRepo levelRepo;
+
+    @Autowired
+    MarkingLevelService markingService;
+
+    @Autowired
+    MarkLogRepo markLogRepo;
+
+    @Autowired
+    WorkRepo workRepo;
+
+    @Autowired
+    LevelConfig levelConfig;
+
+    @Autowired
+    ArbitrateCallback arbitrateCallback;
+
+    @Resource
+    MarkTaskJobRepo markTaskJobRepo;
+
+    @Autowired
+    MarkerGroupRepo markerGroupRepo;
+
+    @Autowired
+    MarkerGroupLeaderRepo markerGroupLeaderRepo;
+
+    @Autowired
+    TaskPublishSettingRepo taskPublishSettingRepo;
+
+    @Autowired
+    ChangeLevelRepo changeLevelRepo;
+
+    @Autowired
+    private CacheService cacheService;
+
+    @Autowired
+    AssignTaskService assignTaskService;
+
+    /**
+     * 提交分档。如果每个评卷都提交了,则进行仲裁判定,如果没有触发仲裁就定档
+     *
+     * @param markTask
+     * @param levelCode
+     * @return
+     */
+    @Transactional
+    public MarkTaskLevel levelMark(MarkTaskLevel markTask, String levelCode) {
+        long start = System.currentTimeMillis();
+        LOG.info("提交分档:{}", start);
+
+        //如果已经由科组长定档,则不做处理
+        Paper paper = markTask.getPaper();
+        if (paper.isMarkByLeader() && Objects.nonNull(paper.getLevel())) {
+            return markTask;
+        }
+
+        MarkUser maker = markUserRepo.findOne(markTask.getMarkerId());
+
+        List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
+        Level level = levels.stream().filter(m -> levelCode.equals(m.getCode())).findFirst().get();
+
+        markTask.setResult(levelCode);
+        markTask.setLevelValue(level.getLevelValue());
+        markTask.setRejected(false);
+        markTask.setDeviationDirection(null);
+        markTask.setUpdatedOn(new Date());
+        markTask.setMarkerName(maker.getName());
+        //激活试卷
+//        markTask.setActive(true);
+
+        markTaskLevelRepo.save(markTask);
+
+        //判断该任务的试卷是否所有评卷员都评完,要进行仲裁判定或定档
+        List<MarkTaskLevel> markTasks = markTaskLevelRepo.findByPaperId(paper.getId());
+        long leftCount = markTasks.stream().filter(i -> i.getResult() == null).count();
+        if (leftCount == 0) {
+            //定档
+            DeterResult determine = determineLevelService.determine(markTask.getWorkId(), levels, markTasks);
+            if (Objects.nonNull(determine) && Objects.nonNull(determine.getResult())) {
+                markTask.setDateMineResult(determine.getResult());
+            }
+            //1.过半定档
+            if (Objects.nonNull(determine) && Objects.nonNull(determine.getResult()) && determine.getDeterType() == DetermineLevelService.DeterType.MAJORITY) {
+                paper.determineLevel(determine.getResult());
+                paper.setMarkedLogic(false);
+                //档位落差值日志
+                levelsLog(markTasks, paper);
+            } else {
+                int[] values = markTasks.stream().mapToInt(MarkTaskLevel::getLevelValue).toArray();
+                Integer deviation = Optional.ofNullable(ParamCache.levelConfigMap.get(String.valueOf(markTask.getWorkId())).getDeviation()).orElse(3);
+                boolean result = ArbitrationService.arbitrate(deviation, values);
+                //2.最大落差超过仲裁档位,则仲裁打回
+                if (result) {
+                    //仲裁
+                    paper.arbitrate();
+                }
+                //3.最大落差未超过仲裁档位,则权重计算定档
+                else if (Objects.nonNull(determine) && Objects.nonNull(determine.getResult()) && determine.getDeterType() == DetermineLevelService.DeterType.WEIGHT) {
+                    paper.determineLevel(determine.getResult());
+                    paper.setMarkedLogic(true);
+                    //档位落差值日志
+                    levelsLog(markTasks, paper);
+                }
+            }
+            //改档后重新分档,状态改为false
+            paper.setShift(false);
+            //重新分档,打回科组长打回状态改为false
+            paper.setRejectedByLeader(false);
+            paper.setSortNum(calcSortNum(paper, markTasks, levels));
+            paperRepo.save(paper);
+
+            //同步mark_task表中level
+            markTaskLevelRepo.updateLevelByPaperId(paper.getLevel(), paper.getId());
+        }
+        long end = System.currentTimeMillis();
+        LOG.info("提交分档耗时:{}", (end - start) / 1000 + "s");
+        return markTask;
+    }
+
+    /**
+     * 档位落差值计算日志
+     *
+     * @param markTasks
+     * @param paper
+     */
+    @Transactional
+    public void levelsLog(List<MarkTaskLevel> markTasks, Paper paper) {
+        //20191108wangliang加入档位落差值计算
+        LOG.info("this:{} levelsLog异步回调进来了", this);
+        JSONObject js = new JSONObject();
+        js.put("paperId", paper.getId());
+        js.put("type", "levelsLog");
+        MarkTaskJob markTaskJob = new MarkTaskJob(js.toJSONString(), false, paper.getWorkId());
+        levelsLog(markTasks, paper, markTaskJob);
+        markTaskJobRepo.save(markTaskJob);
+        LOG.info("this:{} levelsLog异步回调结束了", this);
+    }
+
+    /**
+     * 档位落差值计算日志
+     *
+     * @param markTasks
+     * @param paper
+     * @param markTaskJob
+     */
+    public void levelsLog(List<MarkTaskLevel> markTasks, Paper paper, MarkTaskJob markTaskJob) {
+        Map<Long, String> levelsMap = markTasks.stream().collect(Collectors.toMap(MarkTaskLevel::getMarkerId, o -> o.getResult().toUpperCase()));
+        arbitrateCallback.judge(levelsMap, paper.getLevel(), new ArbitrateResult() {
+            @Override
+            public void callback(List<ArbitrateCallback.Distance> list) {
+                LOG.info("this:{} callback levelsLog异步回调进来了", this);
+                String operResult = "-";
+                Date date = new Date();
+                for (ArbitrateCallback.Distance d : list) {
+                    for (MarkTaskLevel m : markTasks) {
+                        if (Objects.equals(String.valueOf(d.getC()), m.getResult()) && d.getMarkId().longValue() == m.getMarkerId().longValue()) {
+                            MarkLog markLogPrev = markLogRepo.findTopByCreateUserIdAndOperTypeAndSubjectAndExamNumberOrderByCreateTimeDesc(m.getMarkerId(), MarkLogOperType.LEVEl_DIFFERENCE.getId(), m.getSubject().toString(), paper.getExamNumber());
+                            JSONObject jsonObject = new JSONObject();
+                            jsonObject.put("task", m.getResult());
+                            jsonObject.put("paper", paper.getLevel());
+                            if (Objects.isNull(markLogPrev)) {//新建日志
+                                //加入档位落差值日志
+                                Work work = workRepo.findOne(paper.getWorkId());
+                                MarkLog markLog = new MarkLog(m.getMarkerId(), m.getMarkerName(), Role.MARKER, m.getSubject(), paper.getExamNumber(), paper.getStudentName(), MarkLogOperType.LEVEl_DIFFERENCE.getId(), paper.getWorkId(), paper.getId(), MarkStage.LEVEL, operResult, String.valueOf(d.getDistance()), jsonObject.toJSONString(), work.getName(), date);
+                                markLogRepo.save(markLog);
+                            } else {//更新日志
+                                operResult = Optional.ofNullable(markLogPrev.getOperDataAfter()).orElse("-");
+                                markLogPrev.setOperDataBefore(operResult);
+                                markLogPrev.setOperDataAfter(String.valueOf(d.getDistance()));
+                                markLogPrev.setRemark(jsonObject.toJSONString());
+                                markLogRepo.save(markLogPrev);
+                            }
+                            //档位偏差
+                            MarkLog markLogDevi = markLogRepo.findTopByCreateUserIdAndOperTypeAndSubjectAndExamNumberOrderByCreateTimeDesc(m.getMarkerId(), MarkLogOperType.LEVEl_DEVIATION.getId(), m.getSubject().toString(), paper.getExamNumber());
+                            if (Objects.isNull(markLogDevi)) {//新建日志
+                                //加入档位偏差值日志
+                                Work work = workRepo.findOne(paper.getWorkId());
+                                MarkLog markLog = new MarkLog(m.getMarkerId(), m.getMarkerName(), Role.MARKER, m.getSubject(), paper.getExamNumber(), paper.getStudentName(), MarkLogOperType.LEVEl_DEVIATION.getId(), paper.getWorkId(), paper.getId(), MarkStage.LEVEL, operResult, String.valueOf(d.getDeviation()), jsonObject.toJSONString(), work.getName(), date);
+                                markLogRepo.save(markLog);
+                            } else {//更新日志
+                                operResult = Optional.ofNullable(markLogDevi.getOperDataAfter()).orElse("-");
+                                markLogDevi.setOperDataBefore(operResult);
+                                markLogDevi.setOperDataAfter(String.valueOf(d.getDeviation()));
+                                markLogDevi.setRemark(jsonObject.toJSONString());
+                                markLogRepo.save(markLogDevi);
+                            }
+                        }
+                    }
+                }
+                markTaskJobRepo.updateMarkTaskJobByVersion(markTaskJob.getId(), markTaskJob.getVersion());
+                LOG.info("this:{},callback levelsLog异步回调结束了", this);
+            }
+        });
+    }
+
+    /**
+     * 直接给试卷分档
+     *
+     * @param paper
+     * @param level
+     */
+    @Transactional
+    public Paper levelMarkPaper(Paper paper, String level, boolean isSample) {
+        List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
+
+        paper.determineLevel(level);
+        paper.setMarkByLeader(true);
+        paper.setSample(isSample);
+
+        List<MarkTaskLevel> markTasks = markTaskLevelRepo.findByPaperId(paper.getId());
+        for (MarkTaskLevel markTask : markTasks) {
+            markTask.setRejected(false);
+            markTask.setResult(level);
+            markTask.setLevel(level);
+            markTask.setSample(paper.isSample());
+        }
+        markTaskLevelRepo.save(markTasks);
+
+        paper.setSortNum(calcSortNum(paper, markTasks, levels));
+        paperRepo.save(paper);
+        levelsLog(markTasks, paper);
+        return paper;
+    }
+
+    /**
+     * 打回重评
+     * 更新试卷状态
+     * 更新评卷任务状态为打回
+     * 如果评卷任务的档位和建议档位一致,不打回该任务
+     *  @param paper
+     * @param redoLevel 建议重评档位
+     * @param ranges
+     * @param stage
+     */
+    @Transactional
+    public Paper reject(Paper paper, String redoLevel, String ranges) {
+        paper.reject(redoLevel);
+        //科组长打回标记
+        paper.setRejectedByLeader(true);
+        paper.setMarkByLeader(true);
+        //打回后撤销标准卷
+        paper.setSample(false);
+
+
+        List<MarkTaskLevel> markTasks = markTaskLevelRepo.findByPaperId(paper.getId());
+
+        List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
+        Map<String, Integer> levelMap = levels.stream().collect(Collectors.toMap(Level::getCode, Level::getLevelValue));
+
+        List<MarkLog> markLogList = new ArrayList<>();
+        Date date = new Date();
+        for (MarkTaskLevel markTask : markTasks) {
+            String[] range = ranges.split(",");
+            if (range.length > 0) {
+                //加入手动打回日志
+                String operResult = "-";
+                for (String r : range) {
+                    // 建议的档位与其中评委所评档位相同时就不打回给此评委
+                    if (Objects.equals(String.valueOf(markTask.getMarkerId()), r) && !redoLevel.equals(markTask.getResult())) {
+                        markTask.setRejected(true);
+                        markTask.setOriginLevel(markTask.getResult());
+                        markTask.setResult(null);
+                        markTask.setLevel(null);
+                        markTask.setDeviationDirection(calcDeviationDirection(levelMap, markTask.getOriginLevel(), redoLevel));
+                        MarkLog markLogPrev = markLogRepo.findTopByCreateUserIdAndOperTypeAndSubjectAndExamNumberOrderByCreateTimeDesc(markTask.getMarkerId(), MarkLogOperType.HANDLE_LEVEl.getId(), markTask.getSubject().toString(), paper.getExamNumber());
+                        if (Objects.nonNull(markLogPrev)) {
+                            operResult = Optional.ofNullable(markLogPrev.getOperDataAfter()).orElse("-");
+                        }
+                        Work work = workRepo.findOne(paper.getWorkId());
+                        MarkLog markLog = new MarkLog(markTask.getMarkerId(), markTask.getMarkerName(), Role.MARKER, markTask.getSubject(), paper.getExamNumber(), paper.getStudentName(), MarkLogOperType.HANDLE_LEVEl.getId(), paper.getWorkId(), paper.getId(), MarkStage.LEVEL, operResult, markTask.getOriginLevel(), MarkLogOperType.HANDLE_LEVEl.getName(), work.getName(), date);
+                        markLogList.add(markLog);
+                    }
+                }
+            }
+        }
+        markTaskLevelRepo.save(markTasks);
+        paperRepo.save(paper);
+        markLogRepo.save(markLogList);
+        return paper;
+    }
+
+    /**
+     * 跳过该任务,最后处理
+     *
+     * @param markTaskId
+     */
+    @Transactional
+    public MarkTaskLevel skip(Long markTaskId) {
+        try {
+            MarkTaskLevel m = markTaskLevelRepo.findOne(markTaskId);
+            Integer randomSeq = markTaskLevelRepo.findRandomSeqByWorkIdAndSubjectAndMarkerIdAndQuestionId(m.getWorkId(), m.getSubject(), m.getMarkerId(), m.getQuestionId());
+            if (randomSeq == null) {
+                randomSeq = 0;
+            }
+            m.setRandomSeq(randomSeq + 1);
+            markTaskLevelRepo.save(m);
+            return m;
+        } catch (Exception e) {
+            e.printStackTrace();
+            throw new RuntimeException("该任务可能被占用,跳过失败");
+        }
+
+    }
+
+    /**
+     * 计算偏差方向
+     *
+     * @param levelMap
+     * @param result   定档档位
+     * @param level    评卷员打的档位
+     * @return
+     */
+    public static String calcDeviationDirection(Map<String, Integer> levelMap, String result, String level) {
+        if (Objects.nonNull(result) && Objects.nonNull(level)) {
+            Integer resultInt = levelMap.get(result);
+            Integer levelInt = levelMap.get(level);
+            if (resultInt != null && levelInt != null) {
+                return String.valueOf(levelInt - resultInt);
+            }
+        }
+        return null;
+    }
+
+    public static Integer calcSortNum(Paper paper, List<MarkTaskLevel> markTaskList, List<Level> levels) {
+        //计算levelValue和(试评阶段不用)
+        if (paper.getTest() == 0 && Objects.nonNull(paper.getLevel())) {
+            if (!levels.isEmpty()) {
+                Map<String, Integer> map = levels.stream().collect(Collectors.toMap(Level::getCode, Level::getWeight));
+                return markTaskList.stream().mapToInt(m -> map.get(m.getResult()) == null ? 0 : map.get(m.getResult())).sum();
+            }
+        }
+        return 0;
+    }
+
+}

+ 376 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkingRoughLevelService.java

@@ -0,0 +1,376 @@
+package cn.com.qmth.stmms.ms.marking.service;
+
+import cn.com.qmth.stmms.ms.commons.config.LevelConfig;
+import cn.com.qmth.stmms.ms.commons.constant.ArbitrateCallback;
+import cn.com.qmth.stmms.ms.commons.constant.ArbitrateResult;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
+import cn.com.qmth.stmms.ms.core.domain.*;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskLevel;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskRoughLevel;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.domain.user.Role;
+import cn.com.qmth.stmms.ms.core.repository.*;
+import cn.com.qmth.stmms.ms.marking.service.arbitration.ArbitrationService;
+import com.alibaba.fastjson.JSONObject;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import javax.annotation.Resource;
+import java.util.*;
+import java.util.stream.Collectors;
+
+/**
+ * 评卷,分档仲裁及打分服务
+ * Created by zhengmin on 2016/9/23.
+ */
+@Service
+public class MarkingRoughLevelService {
+
+    private static final Logger LOG = LoggerFactory.getLogger(MarkingRoughLevelService.class);
+
+    @Autowired
+    private DetermineRoughLevelService determineRoughLevelService;
+
+    @Resource
+    private MarkTaskRoughLevelRepo markTaskRoughLevelRepo;
+
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Autowired
+    private MarkUserRepo markUserRepo;
+
+    @Autowired
+    private PaperRepo paperRepo;
+
+    @Autowired
+    private LevelRepo levelRepo;
+
+    @Autowired
+    MarkingRoughLevelService markingService;
+
+    @Autowired
+    MarkLogRepo markLogRepo;
+
+    @Autowired
+    WorkRepo workRepo;
+
+    @Autowired
+    LevelConfig levelConfig;
+
+    @Autowired
+    ArbitrateCallback arbitrateCallback;
+
+    @Resource
+    MarkTaskJobRepo markTaskJobRepo;
+
+    @Autowired
+    MarkerGroupRepo markerGroupRepo;
+
+    @Autowired
+    MarkerGroupLeaderRepo markerGroupLeaderRepo;
+
+    @Autowired
+    TaskPublishSettingRepo taskPublishSettingRepo;
+
+    @Autowired
+    ChangeLevelRepo changeLevelRepo;
+
+    @Autowired
+    AssignTaskService assignTaskService;
+
+    /**
+     * 提交分档。如果每个评卷都提交了,则进行仲裁判定,如果没有触发仲裁就定档
+     *
+     * @param markTask
+     * @param levelCode
+     * @return
+     */
+    @Transactional
+    public MarkTaskRoughLevel levelMark(MarkTaskRoughLevel markTask, String levelCode) {
+        long start = System.currentTimeMillis();
+        LOG.info("提交分档:{}", start);
+
+        //如果已经由科组长定档,则不做处理
+        Paper paper = markTask.getPaper();
+        if (paper.isMarkByLeader() && Objects.nonNull(paper.getLevel())) {
+            return markTask;
+        }
+
+        MarkUser maker = markUserRepo.findOne(markTask.getMarkerId());
+        markTask.setResult(levelCode);
+        markTask.setLevelValue(Integer.valueOf(levelCode));
+        markTask.setRejected(false);
+        markTask.setDeviationDirection(null);
+        markTask.setUpdatedOn(new Date());
+        markTask.setMarkerName(maker.getName());
+        //激活试卷
+//        markTask.setActive(true);
+
+        markTaskRoughLevelRepo.save(markTask);
+
+        //判断该任务的试卷是否所有评卷员都评完,要进行仲裁判定或定档
+        List<MarkTaskRoughLevel> markTasks = markTaskRoughLevelRepo.findByPaperId(paper.getId());
+        long leftCount = markTasks.stream().filter(i -> i.getResult() == null).count();
+        if (leftCount == 0) {
+            List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
+            //定档
+            RoughDeterResult determine = determineRoughLevelService.determine(markTask.getWorkId(), levels, markTasks);
+            if (Objects.nonNull(determine) && Objects.nonNull(determine.getResult())) {
+                markTask.setDateMineResult(determine.getResult());
+            }
+            //1.过半定档
+            if (Objects.nonNull(determine) && Objects.nonNull(determine.getResult()) && determine.getDeterType() == DetermineRoughLevelService.DeterType.MAJORITY) {
+                paper.determineRoughLevel(determine.getResult());
+                paper.setMarkedLogic(false);
+                //档位落差值日志
+                levelsLog(markTasks, paper);
+            } else {
+                int[] values = markTasks.stream().mapToInt(MarkTaskRoughLevel::getLevelValue).toArray();
+                Integer deviation = Optional.ofNullable(ParamCache.levelConfigMap.get(String.valueOf(markTask.getWorkId())).getDeviation()).orElse(3);
+                boolean result = ArbitrationService.arbitrate(deviation, values);
+                //2.最大落差超过仲裁档位,则仲裁打回
+                if (result) {
+                    //仲裁
+                    paper.arbitrate();
+                }
+                //3.最大落差未超过仲裁档位,则权重计算定档
+                else if (Objects.nonNull(determine) && Objects.nonNull(determine.getResult()) && determine.getDeterType() == DetermineRoughLevelService.DeterType.WEIGHT) {
+                    paper.determineRoughLevel(determine.getResult());
+                    paper.setMarkedLogic(true);
+                    //档位落差值日志
+                    levelsLog(markTasks, paper);
+                }
+            }
+            //改档后重新分档,状态改为false
+            paper.setShift(false);
+            //重新分档,打回科组长打回状态改为false
+            paper.setRejectedByLeader(false);
+            paper.setSortNum(calcSortNum(paper, markTasks, levels));
+            paperRepo.save(paper);
+
+            //同步mark_task表中level
+            markTaskLevelRepo.updateLevelByPaperId(paper.getLevel(), paper.getId());
+        }
+        long end = System.currentTimeMillis();
+        LOG.info("提交分档耗时:{}", (end - start) / 1000 + "s");
+        return markTask;
+    }
+
+    /**
+     * 档位落差值计算日志
+     *
+     * @param markTasks
+     * @param paper
+     */
+    @Transactional
+    public void levelsLog(List<MarkTaskRoughLevel> markTasks, Paper paper) {
+        //20191108wangliang加入档位落差值计算
+        LOG.info("this:{} levelsLog异步回调进来了", this);
+        JSONObject js = new JSONObject();
+        js.put("paperId", paper.getId());
+        js.put("type", "levelsLog");
+        MarkTaskJob markTaskJob = new MarkTaskJob(js.toJSONString(), false, paper.getWorkId());
+        levelsLog(markTasks, paper, markTaskJob);
+        markTaskJobRepo.save(markTaskJob);
+        LOG.info("this:{} levelsLog异步回调结束了", this);
+    }
+
+    /**
+     * 档位落差值计算日志
+     *
+     * @param markTasks
+     * @param paper
+     * @param markTaskJob
+     */
+    public void levelsLog(List<MarkTaskRoughLevel> markTasks, Paper paper, MarkTaskJob markTaskJob) {
+        Map<Long, String> levelsMap = markTasks.stream().collect(Collectors.toMap(MarkTaskRoughLevel::getMarkerId, o -> o.getResult().toUpperCase()));
+        arbitrateCallback.judge(levelsMap, paper.getLevel(), new ArbitrateResult() {
+            @Override
+            public void callback(List<ArbitrateCallback.Distance> list) {
+                LOG.info("this:{} callback levelsLog异步回调进来了", this);
+                String operResult = "-";
+                Date date = new Date();
+                for (ArbitrateCallback.Distance d : list) {
+                    for (MarkTaskRoughLevel m : markTasks) {
+                        if (Objects.equals(String.valueOf(d.getC()), m.getResult()) && d.getMarkId().longValue() == m.getMarkerId().longValue()) {
+                            MarkLog markLogPrev = markLogRepo.findTopByCreateUserIdAndOperTypeAndSubjectAndExamNumberOrderByCreateTimeDesc(m.getMarkerId(), MarkLogOperType.LEVEl_DIFFERENCE.getId(), m.getSubject().toString(), paper.getExamNumber());
+                            JSONObject jsonObject = new JSONObject();
+                            jsonObject.put("task", m.getResult());
+                            jsonObject.put("paper", paper.getLevel());
+                            if (Objects.isNull(markLogPrev)) {//新建日志
+                                //加入档位落差值日志
+                                Work work = workRepo.findOne(paper.getWorkId());
+                                MarkLog markLog = new MarkLog(m.getMarkerId(), m.getMarkerName(), Role.MARKER, m.getSubject(), paper.getExamNumber(), paper.getStudentName(), MarkLogOperType.LEVEl_DIFFERENCE.getId(), paper.getWorkId(), paper.getId(), MarkStage.LEVEL, operResult, String.valueOf(d.getDistance()), jsonObject.toJSONString(), work.getName(), date);
+                                markLogRepo.save(markLog);
+                            } else {//更新日志
+                                operResult = Optional.ofNullable(markLogPrev.getOperDataAfter()).orElse("-");
+                                markLogPrev.setOperDataBefore(operResult);
+                                markLogPrev.setOperDataAfter(String.valueOf(d.getDistance()));
+                                markLogPrev.setRemark(jsonObject.toJSONString());
+                                markLogRepo.save(markLogPrev);
+                            }
+                            //档位偏差
+                            MarkLog markLogDevi = markLogRepo.findTopByCreateUserIdAndOperTypeAndSubjectAndExamNumberOrderByCreateTimeDesc(m.getMarkerId(), MarkLogOperType.LEVEl_DEVIATION.getId(), m.getSubject().toString(), paper.getExamNumber());
+                            if (Objects.isNull(markLogDevi)) {//新建日志
+                                //加入档位偏差值日志
+                                Work work = workRepo.findOne(paper.getWorkId());
+                                MarkLog markLog = new MarkLog(m.getMarkerId(), m.getMarkerName(), Role.MARKER, m.getSubject(), paper.getExamNumber(), paper.getStudentName(), MarkLogOperType.LEVEl_DEVIATION.getId(), paper.getWorkId(), paper.getId(), MarkStage.LEVEL, operResult, String.valueOf(d.getDeviation()), jsonObject.toJSONString(), work.getName(), date);
+                                markLogRepo.save(markLog);
+                            } else {//更新日志
+                                operResult = Optional.ofNullable(markLogDevi.getOperDataAfter()).orElse("-");
+                                markLogDevi.setOperDataBefore(operResult);
+                                markLogDevi.setOperDataAfter(String.valueOf(d.getDeviation()));
+                                markLogDevi.setRemark(jsonObject.toJSONString());
+                                markLogRepo.save(markLogDevi);
+                            }
+                        }
+                    }
+                }
+                markTaskJobRepo.updateMarkTaskJobByVersion(markTaskJob.getId(), markTaskJob.getVersion());
+                LOG.info("this:{},callback levelsLog异步回调结束了", this);
+            }
+        });
+    }
+
+    /**
+     * 直接给试卷分档
+     *
+     * @param paper
+     * @param level
+     */
+    @Transactional
+    public Paper levelMarkPaper(Paper paper, String level, boolean isSample) {
+        List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
+
+        paper.determineRoughLevel(level);
+        paper.setMarkByLeader(true);
+        paper.setRoughSample(isSample);
+
+        List<MarkTaskRoughLevel> markTasks = markTaskRoughLevelRepo.findByPaperId(paper.getId());
+        for (MarkTaskRoughLevel markTask : markTasks) {
+            markTask.setRejected(false);
+            markTask.setResult(level);
+            markTask.setLevel(level);
+            markTask.setSample(paper.isSample());
+        }
+        markTaskRoughLevelRepo.save(markTasks);
+
+        paper.setSortNum(calcSortNum(paper, markTasks, levels));
+        paperRepo.save(paper);
+        levelsLog(markTasks, paper);
+        return paper;
+    }
+
+    /**
+     * 打回重评
+     * 更新试卷状态
+     * 更新评卷任务状态为打回
+     * 如果评卷任务的档位和建议档位一致,不打回该任务
+     *
+     * @param paper
+     * @param redoLevel 建议重评档位
+     * @param ranges
+     */
+    @Transactional
+    public Paper reject(Paper paper, String redoLevel, String ranges) {
+        paper.roughReject(redoLevel);
+        //科组长打回标记
+        paper.setRejectedByLeader(true);
+        paper.setMarkByLeader(true);
+        //打回后撤销标准卷
+        paper.setRoughSample(false);
+        List<MarkTaskRoughLevel> markTasks = markTaskRoughLevelRepo.findByPaperId(paper.getId());
+
+        List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
+        Map<String, Integer> levelMap = levels.stream().collect(Collectors.toMap(Level::getCode, Level::getLevelValue));
+
+        List<MarkLog> markLogList = new ArrayList<>();
+        Date date = new Date();
+        for (MarkTaskRoughLevel markTask : markTasks) {
+            String[] range = ranges.split(",");
+            if (range.length > 0) {
+                //加入手动打回日志
+                String operResult = "-";
+                for (String r : range) {
+                    // 建议的档位与其中评委所评档位相同时就不打回给此评委
+                    if (Objects.equals(String.valueOf(markTask.getMarkerId()), r) && !redoLevel.equals(markTask.getResult())) {
+                        markTask.setRejected(true);
+                        markTask.setOriginLevel(markTask.getResult());
+                        markTask.setResult(null);
+                        markTask.setLevel(null);
+                        markTask.setDeviationDirection(calcDeviationDirection(levelMap, markTask.getOriginLevel(), redoLevel));
+                        MarkLog markLogPrev = markLogRepo.findTopByCreateUserIdAndOperTypeAndSubjectAndExamNumberOrderByCreateTimeDesc(markTask.getMarkerId(), MarkLogOperType.HANDLE_LEVEl.getId(), markTask.getSubject().toString(), paper.getExamNumber());
+                        if (Objects.nonNull(markLogPrev)) {
+                            operResult = Optional.ofNullable(markLogPrev.getOperDataAfter()).orElse("-");
+                        }
+                        Work work = workRepo.findOne(paper.getWorkId());
+                        MarkLog markLog = new MarkLog(markTask.getMarkerId(), markTask.getMarkerName(), Role.MARKER, markTask.getSubject(), paper.getExamNumber(), paper.getStudentName(), MarkLogOperType.HANDLE_LEVEl.getId(), paper.getWorkId(), paper.getId(), MarkStage.LEVEL, operResult, markTask.getOriginLevel(), MarkLogOperType.HANDLE_LEVEl.getName(), work.getName(), date);
+                        markLogList.add(markLog);
+                    }
+                }
+            }
+        }
+        markTaskRoughLevelRepo.save(markTasks);
+        paperRepo.save(paper);
+        markLogRepo.save(markLogList);
+        return paper;
+    }
+
+    /**
+     * 跳过该任务,最后处理
+     *
+     * @param markTaskId
+     */
+    @Transactional
+    public MarkTaskRoughLevel skip(Long markTaskId) {
+        try {
+            MarkTaskRoughLevel m = markTaskRoughLevelRepo.findOne(markTaskId);
+            Integer randomSeq = markTaskRoughLevelRepo.findRandomSeqByWorkIdAndSubjectAndMarkerIdAndQuestionId(m.getWorkId(), m.getSubject(), m.getMarkerId(), m.getQuestionId());
+            if (randomSeq == null) {
+                randomSeq = 0;
+            }
+            m.setRandomSeq(randomSeq + 1);
+            markTaskRoughLevelRepo.save(m);
+            return m;
+        } catch (Exception e) {
+            e.printStackTrace();
+            throw new RuntimeException("该任务可能被占用,跳过失败");
+        }
+
+    }
+
+    /**
+     * 计算偏差方向
+     *
+     * @param levelMap
+     * @param result   定档档位
+     * @param level    评卷员打的档位
+     * @return
+     */
+    public static String calcDeviationDirection(Map<String, Integer> levelMap, String result, String level) {
+        if (Objects.nonNull(result) && Objects.nonNull(level)) {
+            Integer resultInt = levelMap.get(result);
+            Integer levelInt = levelMap.get(level);
+            if (resultInt != null && levelInt != null) {
+                return String.valueOf(levelInt - resultInt);
+            }
+        }
+        return null;
+    }
+
+    public static Integer calcSortNum(Paper paper, List<MarkTaskRoughLevel> markTaskList, List<Level> levels) {
+        //计算levelValue和(试评阶段不用)
+        if (paper.getTest() == 0 && Objects.nonNull(paper.getLevel())) {
+            if (!levels.isEmpty()) {
+                Map<String, Integer> map = levels.stream().collect(Collectors.toMap(Level::getCode, Level::getWeight));
+                return markTaskList.stream().mapToInt(m -> map.get(m.getResult()) == null ? 0 : map.get(m.getResult())).sum();
+            }
+        }
+        return 0;
+    }
+
+}

+ 151 - 0
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkingScoreService.java

@@ -0,0 +1,151 @@
+package cn.com.qmth.stmms.ms.marking.service;
+
+import cn.com.qmth.stmms.ms.commons.config.LevelConfig;
+import cn.com.qmth.stmms.ms.commons.constant.ArbitrateCallback;
+import cn.com.qmth.stmms.ms.core.cache.CacheService;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
+import cn.com.qmth.stmms.ms.core.domain.Paper;
+import cn.com.qmth.stmms.ms.core.domain.task.MarkTaskScore;
+import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
+import cn.com.qmth.stmms.ms.core.repository.*;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import javax.annotation.Resource;
+import java.util.*;
+
+/**
+ * 评卷,分档仲裁及打分服务
+ * Created by zhengmin on 2016/9/23.
+ */
+@Service
+public class MarkingScoreService {
+
+    private static final Logger LOG = LoggerFactory.getLogger(MarkingScoreService.class);
+
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
+
+    @Autowired
+    private MarkUserRepo markUserRepo;
+
+    @Autowired
+    private PaperRepo paperRepo;
+
+    @Autowired
+    MarkingScoreService markingService;
+
+    @Autowired
+    MarkLogRepo markLogRepo;
+
+    @Autowired
+    WorkRepo workRepo;
+
+    @Autowired
+    LevelConfig levelConfig;
+
+    @Autowired
+    ArbitrateCallback arbitrateCallback;
+
+    @Autowired
+    MarkerGroupRepo markerGroupRepo;
+
+    @Autowired
+    MarkerGroupLeaderRepo markerGroupLeaderRepo;
+
+    @Autowired
+    TaskPublishSettingRepo taskPublishSettingRepo;
+
+    @Autowired
+    ChangeLevelRepo changeLevelRepo;
+
+    @Autowired
+    private CacheService cacheService;
+
+    @Autowired
+    AssignTaskService assignTaskService;
+
+
+    /**
+     * 打分。取出组内所有评分,如果都给了分,取平均分更新试卷成绩
+     *
+     * @param markTask
+     * @param score
+     */
+    @Transactional
+    public MarkTaskScore scoring(MarkTaskScore markTask, int score) {
+        markTask.setResult(String.valueOf(score));
+        markTask.setUpdatedOn(new Date());
+        MarkUser maker = markUserRepo.findOne(markTask.getMarkerId());
+        markTask.setMarkerName(maker.getName());
+        markTaskScoreRepo.save(markTask);
+        Paper paper = markTask.getPaper();
+        List<MarkTaskScore> markTasks = markTaskScoreRepo.findByPaperId(paper.getId());
+        long leftCount = markTasks.stream().filter(i -> i.getResult() == null).count();
+        if (leftCount == 0) {
+            // 分数计算方式 (1:去高去低再加权评卷, 0:全部加权平均,默认0)
+            boolean removeHighAndLow = Optional.ofNullable(ParamCache.scoreConfigMap.get(String.valueOf(String.valueOf(markTask.getWorkId()))).getRemoveHighAndLow()).orElse(0) == 1;
+            if (removeHighAndLow) {
+                markTasks.sort(Comparator.comparingInt(x -> Integer.parseInt(x.getResult())));
+                markTasks.remove(0);//去掉最大值
+                markTasks.remove(markTasks.size() - 1);//去掉最小值
+            }
+
+            OptionalDouble finalScore = markTasks.stream().map(MarkTaskScore::getResult).mapToInt(Integer::valueOf).average();
+            //湖北省,平均分非零进一
+            Integer roundUp = Optional.ofNullable(ParamCache.scoreConfigMap.get(String.valueOf(markTask.getWorkId())).getRoundUp()).orElse(1);
+            double fs = roundUp == 0 ? Math.ceil(finalScore.orElse(0)) : Math.round(finalScore.orElse(0));
+            paper.setScore(fs);
+            //改档打分完成,更新状态为false
+            paper.setShiftScore(false);
+            paperRepo.save(paper);
+        }
+        return markTask;
+    }
+
+    /**
+     * 跳过该任务,最后处理
+     *
+     * @param markTaskId
+     */
+    @Transactional
+    public MarkTaskScore skip(Long markTaskId) {
+        try {
+            MarkTaskScore m = markTaskScoreRepo.findOne(markTaskId);
+            Integer randomSeq = markTaskScoreRepo.findRandomSeqByWorkIdAndSubjectAndMarkerIdAndQuestionId(m.getWorkId(), m.getSubject(), m.getMarkerId(), m.getQuestionId());
+            if (randomSeq == null) {
+                randomSeq = 0;
+            }
+            m.setRandomSeq(randomSeq + 1);
+            markTaskScoreRepo.save(m);
+            return m;
+        } catch (Exception e) {
+            e.printStackTrace();
+            throw new RuntimeException("该任务可能被占用,跳过失败");
+        }
+
+    }
+
+    /**
+     * 计算偏差方向
+     *
+     * @param levelMap
+     * @param result   定档档位
+     * @param level    评卷员打的档位
+     * @return
+     */
+    public static String calcDeviationDirection(Map<String, Integer> levelMap, String result, String level) {
+        if (Objects.nonNull(result) && Objects.nonNull(level)) {
+            Integer resultInt = levelMap.get(result);
+            Integer levelInt = levelMap.get(level);
+            if (resultInt != null && levelInt != null) {
+                return String.valueOf(levelInt - resultInt);
+            }
+        }
+        return null;
+    }
+
+}

+ 20 - 264
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/MarkingService.java

@@ -2,18 +2,14 @@ package cn.com.qmth.stmms.ms.marking.service;
 
 import cn.com.qmth.stmms.ms.commons.config.LevelConfig;
 import cn.com.qmth.stmms.ms.commons.constant.ArbitrateCallback;
-import cn.com.qmth.stmms.ms.commons.constant.ArbitrateResult;
 import cn.com.qmth.stmms.ms.core.cache.CacheService;
-import cn.com.qmth.stmms.ms.core.cache.ParamCache;
-import cn.com.qmth.stmms.ms.core.domain.*;
-import cn.com.qmth.stmms.ms.core.domain.task.MarkTask;
+import cn.com.qmth.stmms.ms.core.domain.ChangeLevel;
+import cn.com.qmth.stmms.ms.core.domain.MarkStage;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.domain.user.Role;
 import cn.com.qmth.stmms.ms.core.repository.*;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import cn.com.qmth.stmms.ms.marking.config.MarkingConfig;
-import cn.com.qmth.stmms.ms.marking.service.arbitration.ArbitrationService;
-import com.alibaba.fastjson.JSONObject;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -22,7 +18,9 @@ import org.springframework.transaction.annotation.Transactional;
 import org.springframework.util.CollectionUtils;
 
 import javax.annotation.Resource;
-import java.util.*;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
 import java.util.stream.Collectors;
 
 /**
@@ -39,9 +37,6 @@ public class MarkingService {
     @Autowired
     private DetermineLevelService determineLevelService;
 
-    @Autowired
-    private MarkTaskRepo markTaskRepo;
-
     @Autowired
     private MarkUserRepo markUserRepo;
 
@@ -87,86 +82,11 @@ public class MarkingService {
     @Autowired
     AssignTaskService assignTaskService;
 
-    /**
-     * 提交分档。如果每个评卷都提交了,则进行仲裁判定,如果没有触发仲裁就定档
-     *
-     * @param markTask
-     * @param levelCode
-     * @return
-     */
-    @Transactional
-    public MarkTask levelMark(MarkTask markTask, String levelCode) {
-        long start = System.currentTimeMillis();
-        LOG.info("提交分档:{}", start);
-
-        //如果已经由科组长定档,则不做处理
-        Paper paper = markTask.getPaper();
-        if (paper.isMarkByLeader() && Objects.nonNull(paper.getLevel())) {
-            return markTask;
-        }
-
-        MarkUser maker = markUserRepo.findOne(markTask.getMarkerId());
-
-        List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
-        Level level = levels.stream().filter(m -> levelCode.equals(m.getCode())).findFirst().get();
-
-        markTask.setResult(levelCode);
-        markTask.setLevelValue(level.getLevelValue());
-        markTask.setRejected(false);
-        markTask.setDeviationDirection(null);
-        markTask.setUpdatedOn(new Date());
-        markTask.setMarkerName(maker.getName());
-        //激活试卷
-//        markTask.setActive(true);
-
-        markTaskRepo.save(markTask);
-
-        //判断该任务的试卷是否所有评卷员都评完,要进行仲裁判定或定档
-        List<MarkTask> markTasks = markTaskRepo.findByPaperIdAndStage(paper.getId(), markTask.getStage());
-        long leftCount = markTasks.stream().filter(i -> i.getResult() == null).count();
-        if (leftCount == 0) {
-            //定档
-            DeterResult determine = determineLevelService.determine(markTask.getWorkId(), levels, markTasks);
-            if (Objects.nonNull(determine) && Objects.nonNull(determine.getResult())) {
-                markTask.setDateMineResult(determine.getResult());
-            }
-            //1.过半定档
-            if (Objects.nonNull(determine) && Objects.nonNull(determine.getResult()) && determine.getDeterType() == DetermineLevelService.DeterType.MAJORITY) {
-                paper.determineLevel(determine.getResult());
-                paper.setMarkedLogic(false);
-                //档位落差值日志
-                levelsLog(markTasks, paper);
-            } else {
-                int[] values = markTasks.stream().mapToInt(MarkTask::getLevelValue).toArray();
-                Integer deviation = Optional.ofNullable(ParamCache.levelConfigMap.get(String.valueOf(markTask.getWorkId())).getDeviation()).orElse(3);
-                boolean result = ArbitrationService.arbitrate(deviation, values);
-                //2.最大落差超过仲裁档位,则仲裁打回
-                if (result) {
-                    //仲裁
-                    paper.arbitrate();
-                }
-                //3.最大落差未超过仲裁档位,则权重计算定档
-                else if (Objects.nonNull(determine) && Objects.nonNull(determine.getResult()) && determine.getDeterType() == DetermineLevelService.DeterType.WEIGHT) {
-                    paper.determineLevel(determine.getResult());
-                    paper.setMarkedLogic(true);
-                    //档位落差值日志
-                    levelsLog(markTasks, paper);
-                }
-            }
-            //改档后重新分档,状态改为false
-            paper.setShift(false);
-            //重新分档,打回科组长打回状态改为false
-            paper.setRejectedByLeader(false);
-            paper.setSortNum(calcSortNum(paper, markTasks, levels));
-            paperRepo.save(paper);
+    @Resource
+    private MarkTaskLevelRepo markTaskLevelRepo;
 
-            //同步mark_task表中level
-            markTaskRepo.updateLevelByPaperId(paper.getLevel(), paper.getId());
-        }
-        long end = System.currentTimeMillis();
-        LOG.info("提交分档耗时:{}", (end - start) / 1000 + "s");
-        return markTask;
-    }
+    @Resource
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     /**
      * 档位落差值计算日志
@@ -174,7 +94,7 @@ public class MarkingService {
      * @param markTasks
      * @param paper
      */
-    @Transactional
+    /*@Transactional
     public void levelsLog(List<MarkTask> markTasks, Paper paper) {
         //20191108wangliang加入档位落差值计算
         LOG.info("this:{} levelsLog异步回调进来了", this);
@@ -185,15 +105,15 @@ public class MarkingService {
         levelsLog(markTasks, paper, markTaskJob);
         markTaskJobRepo.save(markTaskJob);
         LOG.info("this:{} levelsLog异步回调结束了", this);
-    }
+    }*/
 
     /**
      * 档位落差值计算日志
      *
-     * @param markTasks
-     * @param paper
-     * @param markTaskJob
-     */
+//     * @param markTasks
+//     * @param paper
+//     * @param markTaskJob
+     *//*
     public void levelsLog(List<MarkTask> markTasks, Paper paper, MarkTaskJob markTaskJob) {
 //        List<MarkTask> result = markTasks.stream().filter(x -> Objects.isNull(x.getResult())).collect(Collectors.toList());
 //        if (Objects.nonNull(result) && result.size() > 0) {
@@ -248,167 +168,10 @@ public class MarkingService {
                 LOG.info("this:{},callback levelsLog异步回调结束了", this);
             }
         });
-    }
-
-    /**
-     * 直接给试卷分档
-     *
-     * @param paper
-     * @param level
-     */
-    @Transactional
-    public Paper levelMarkPaper(Paper paper, String level, boolean isSample) {
-        //2019.10.12 湖北美术统考去掉标准卷设置数量
-//    	if(isSample){
-//    		MarkSubject markSubject = markSubjectRepo.findOne(paper.getWorkId() + "-" + paper.getSubject().toString());
-//    		long sampleCount = paperRepo.countByWorkIdAndSubjectAndIsSampleIsTrue(paper.getWorkId(), paper.getSubject());
-//    		if(sampleCount >= markSubject.getSampleCount()){
-//    			throw new RuntimeException("标准卷上限已达到");
-//    		}
-//    	}
-        List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
-
-        paper.determineLevel(level);
-        paper.setMarkByLeader(true);
-        paper.setSample(isSample);
-
-        List<MarkTask> markTasks = markTaskRepo.findByPaperIdAndStage(paper.getId(), MarkStage.LEVEL);
-        for (MarkTask markTask : markTasks) {
-            markTask.setRejected(false);
-            markTask.setResult(level);
-            markTask.setLevel(level);
-            markTask.setSample(paper.isSample());
-        }
-        markTaskRepo.save(markTasks);
-
-        paper.setSortNum(calcSortNum(paper, markTasks, levels));
-        paperRepo.save(paper);
-        levelsLog(markTasks, paper);
-        return paper;
-    }
-
-    /**
-     * 打回重评
-     * 更新试卷状态
-     * 更新评卷任务状态为打回
-     * 如果评卷任务的档位和建议档位一致,不打回该任务
-     *
-     * @param paper
-     * @param redoLevel 建议重评档位
-     * @param ranges
-     */
-    @Transactional
-    public Paper reject(Paper paper, String redoLevel, String ranges) {
-        paper.reject(redoLevel);
-        //科组长打回标记
-        paper.setRejectedByLeader(true);
-        paper.setMarkByLeader(true);
-        //打回后撤销标准卷
-        paper.setSample(false);
-        List<MarkTask> markTasks = markTaskRepo.findByPaperIdAndStage(paper.getId(), MarkStage.LEVEL);
-
-        List<Level> levels = levelRepo.findByWorkId(paper.getWorkId());
-        Map<String, Integer> levelMap = levels.stream().collect(Collectors.toMap(Level::getCode, Level::getLevelValue));
-
-        List<MarkLog> markLogList = new ArrayList<>();
-        Date date = new Date();
-        for (MarkTask markTask : markTasks) {
-            String[] range = ranges.split(",");
-            if (range.length > 0) {
-                //加入手动打回日志
-                String operResult = "-";
-                for (String r : range) {
-                    // 建议的档位与其中评委所评档位相同时就不打回给此评委
-                    if (Objects.equals(String.valueOf(markTask.getMarkerId()), r) && !redoLevel.equals(markTask.getResult())) {
-                        markTask.setRejected(true);
-                        markTask.setOriginLevel(markTask.getResult());
-                        markTask.setResult(null);
-                        markTask.setLevel(null);
-                        markTask.setDeviationDirection(calcDeviationDirection(levelMap, markTask.getOriginLevel(), redoLevel));
-                        MarkLog markLogPrev = markLogRepo.findTopByCreateUserIdAndOperTypeAndSubjectAndExamNumberOrderByCreateTimeDesc(markTask.getMarkerId(), MarkLogOperType.HANDLE_LEVEl.getId(), markTask.getSubject().toString(), paper.getExamNumber());
-                        if (Objects.nonNull(markLogPrev)) {
-                            operResult = Optional.ofNullable(markLogPrev.getOperDataAfter()).orElse("-");
-                        }
-                        Work work = workRepo.findOne(paper.getWorkId());
-                        MarkLog markLog = new MarkLog(markTask.getMarkerId(), markTask.getMarkerName(), Role.MARKER, markTask.getSubject(), paper.getExamNumber(), paper.getStudentName(), MarkLogOperType.HANDLE_LEVEl.getId(), paper.getWorkId(), paper.getId(), markTask.getStage(), operResult, markTask.getOriginLevel(), MarkLogOperType.HANDLE_LEVEl.getName(), work.getName(), date);
-                        markLogList.add(markLog);
-                    }
-                }
-            }
-        }
-        markTaskRepo.save(markTasks);
-        paperRepo.save(paper);
-        markLogRepo.save(markLogList);
-        return paper;
-    }
-
-    /**
-     * 打分。取出组内所有评分,如果都给了分,取平均分更新试卷成绩
-     *
-     * @param markTask
-     * @param score
-     */
-    @Transactional
-    public MarkTask scoring(MarkTask markTask, int score) {
-        if (markTask.getStage() != MarkStage.SCORE) {
-            throw new RuntimeException("该任务不是打分任务");
-        }
-        markTask.setResult(String.valueOf(score));
-        markTask.setUpdatedOn(new Date());
-        MarkUser maker = markUserRepo.findOne(markTask.getMarkerId());
-        markTask.setMarkerName(maker.getName());
-        markTaskRepo.save(markTask);
-        Paper paper = markTask.getPaper();
-        List<MarkTask> markTasks = markTaskRepo.findByPaperIdAndStage(paper.getId(), markTask.getStage());
-        long leftCount = markTasks.stream().filter(i -> i.getResult() == null).count();
-        if (leftCount == 0) {
-            // 分数计算方式 (1:去高去低再加权评卷, 0:全部加权平均,默认0)
-            boolean removeHighAndLow = Optional.ofNullable(ParamCache.scoreConfigMap.get(String.valueOf(String.valueOf(markTask.getWorkId()))).getRemoveHighAndLow()).orElse(0) == 1;
-            if (removeHighAndLow) {
-                markTasks.sort(Comparator.comparingInt(x -> Integer.parseInt(x.getResult())));
-                markTasks.remove(0);//去掉最大值
-                markTasks.remove(markTasks.size() - 1);//去掉最小值
-            }
-
-            OptionalDouble finalScore = markTasks.stream().map(MarkTask::getResult).mapToInt(Integer::valueOf).average();
-            //湖北省,平均分非零进一
-            Integer roundUp = Optional.ofNullable(ParamCache.scoreConfigMap.get(String.valueOf(markTask.getWorkId())).getRoundUp()).orElse(1);
-            double fs = roundUp == 0 ? Math.ceil(finalScore.orElse(0)) : Math.round(finalScore.orElse(0));
-            paper.setScore(fs);
-            //改档打分完成,更新状态为false
-            paper.setShiftScore(false);
-            paperRepo.save(paper);
-        }
-        return markTask;
-    }
-
-    /**
-     * 跳过该任务,最后处理
-     *
-     * @param markTaskId
-     */
-    @Transactional
-    public MarkTask skip(Long markTaskId) {
-        try {
-            MarkTask m = markTaskRepo.findOne(markTaskId);
-            Integer randomSeq = markTaskRepo.findRandomSeqByWorkIdAndSubjectAndMarkerIdAndStageAndQuestionId(m.getWorkId(), m.getSubject(), m.getMarkerId(), m.getStage(), m.getQuestionId());
-            if (randomSeq == null) {
-                randomSeq = 0;
-            }
-            m.setRandomSeq(randomSeq + 1);
-            markTaskRepo.save(m);
-            return m;
-        } catch (Exception e) {
-            e.printStackTrace();
-            throw new RuntimeException("该任务可能被占用,跳过失败");
-        }
-
-    }
+    }*/
 
     @Transactional
     public void subjectReset(Long workId, Subject subject, MarkStage stage) {
-        // 删除mark_task阶段数据
-        markTaskRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, stage);
         // 清除mark_user分组
         markUserRepo.updateByWorkIdAndSubject(workId, subject);
         // 删除mark_group分组
@@ -417,11 +180,15 @@ public class MarkingService {
         markerGroupLeaderRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, stage);
         // 分档阶段
         if (MarkStage.LEVEL.equals(stage)) {
+            // 删除mark_task阶段数据
+            markTaskLevelRepo.deleteByWorkIdAndSubject(workId, subject);
             // 清除paper中的档位,各种状态
             paperRepo.updateLevelByWorkIdAndSubject(workId, subject.name());
         }
         // 打分阶段
         else if (MarkStage.SCORE.equals(stage)) {
+            // 删除mark_task阶段数据
+            markTaskScoreRepo.deleteByWorkIdAndSubject(workId, subject);
             // 清除paper中的分数
             paperRepo.updateScoreByWorkIdAndSubject(workId, subject.name());
             // 删除task_publish_setting数据
@@ -468,15 +235,4 @@ public class MarkingService {
         return null;
     }
 
-    public static Integer calcSortNum(Paper paper, List<MarkTask> markTaskList, List<Level> levels) {
-        //计算levelValue和(试评阶段不用)
-        if (paper.getTest() == 0 && Objects.nonNull(paper.getLevel())) {
-            if (!levels.isEmpty()) {
-                Map<String, Integer> map = levels.stream().collect(Collectors.toMap(Level::getCode, Level::getWeight));
-                return markTaskList.stream().mapToInt(m -> map.get(m.getResult()) == null ? 0 : map.get(m.getResult())).sum();
-            }
-        }
-        return 0;
-    }
-
 }

+ 187 - 46
stmms-ms-marking/src/main/java/cn/com/qmth/stmms/ms/marking/service/StageControlService.java

@@ -2,8 +2,8 @@ package cn.com.qmth.stmms.ms.marking.service;
 
 import cn.com.qmth.stmms.ms.commons.config.ScoreConfig;
 import cn.com.qmth.stmms.ms.commons.utils.SqlUtil;
+import cn.com.qmth.stmms.ms.core.cache.ParamCache;
 import cn.com.qmth.stmms.ms.core.domain.*;
-import cn.com.qmth.stmms.ms.core.domain.enums.TrialEnum;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkRight;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkUser;
 import cn.com.qmth.stmms.ms.core.domain.user.MarkerGroup;
@@ -11,11 +11,13 @@ import cn.com.qmth.stmms.ms.core.domain.user.Role;
 import cn.com.qmth.stmms.ms.core.repository.*;
 import cn.com.qmth.stmms.ms.core.vo.Subject;
 import cn.com.qmth.stmms.ms.marking.dto.LevleProgressDTO;
+import org.apache.commons.lang.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.data.domain.Sort;
 import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 
+import javax.annotation.Resource;
 import java.math.BigDecimal;
 import java.util.*;
 import java.util.stream.Collectors;
@@ -31,7 +33,10 @@ public class StageControlService {
     private MarkSubjectRepo markSubjectRepo;
 
     @Autowired
-    private MarkTaskRepo markTaskRepo;
+    private MarkTaskLevelRepo markTaskLevelRepo;
+
+    @Autowired
+    private MarkTaskScoreRepo markTaskScoreRepo;
 
     @Autowired
     private LevelRepo levelRepo;
@@ -51,6 +56,9 @@ public class StageControlService {
     @Autowired
     private MarkerGroupRepo markerGroupRepo;
 
+    @Resource
+    private MarkerGroupStudentRepo markerGroupStudentRepo;
+
     @Autowired
     private TaskPublishSettingRepo taskPublishSettingRepo;
 
@@ -65,50 +73,138 @@ public class StageControlService {
     /**
      * 进入下一阶段
      *
-     * @param markSubject
+     * @param markSubject 科目
      */
     @Transactional
-    public void goNext(MarkSubject markSubject, Map map) throws Exception {
+    public void goNext(MarkSubject markSubject, Map<String, Integer> map) throws Exception {
         if (statusMap.get(markSubject.getId()) != null && statusMap.get(markSubject.getId())) {
             return;
         }
         statusMap.put(markSubject.getId(), true);
         MarkStage markStage = markSubject.getStage();
         //是否还有未投放的试卷
-        int waitCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndActiveFalseAndBatchNoIsNullAndTest(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getTest());
-        if (waitCount > 0 && markStage.equals(MarkStage.LEVEL)) {
-            markStage = MarkStage.INIT;
-        }
-        switch (markStage) {
-            case INIT:
+//        int waitCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndActiveFalseAndBatchNoIsNullAndTest(markSubject.getWorkId(), markSubject.getSubject(), markSubject.getTest());
+//        if (waitCount > 0 && markStage.equals(MarkStage.LEVEL)) {
+//            markStage = MarkStage.INIT;
+//        }
+        /*if (MarkStage.INIT.equals(markStage)) {
+            // 开启粗分档
+            if (ParamCache.levelConfigMap.get(String.valueOf(markSubject.getWorkId())).getRoughLevel() == 1) {
+                markSubject.setStage(MarkStage.ROUGH_LEVEL);
+                int taskCount = (int) map.get("taskCount");
+                Object questionId = map.get("questionId");
+                enterRoughLevelStage(markSubject, taskCount, questionId);
+            } else {
                 markSubject.setStage(MarkStage.LEVEL);
                 int taskCount = (int) map.get("taskCount");
                 Object questionId = map.get("questionId");
                 enterLevelStage(markSubject, taskCount, questionId);
-                break;
-            case LEVEL:
+            }
+        } else*/
+        if (MarkStage.ROUGH_LEVEL.equals(markStage)) {
+//            markSubject.setStage(MarkStage.LEVEL);
+            int taskCount = (int) map.get("taskCount");
+            Object questionId = map.get("questionId");
+//            enterLevelStage(markSubject, taskCount, questionId);
+            enterRoughLevelStage(markSubject, taskCount, questionId);
+        } else if (MarkStage.LEVEL.equals(markStage)) {
+//            markSubject.setStage(MarkStage.SCORE);
+//            enterToScoreStage(markSubject);
+            int taskCount = (int) map.get("taskCount");
+            Object questionId = map.get("questionId");
+            enterLevelStage(markSubject, taskCount, questionId);
+        } else if (MarkStage.SCORE.equals(markStage)) {
+            enterToScoreStage(markSubject);
+            //TODO 进入抽查阶段
+            /*if (!markSubject.isAllLevel()) {
                 markSubject.setStage(MarkStage.SCORE);
-                enterToScoreStage(markSubject);
-                break;
-            case SCORE:
-                //TODO 进入抽查阶段
-                if (!markSubject.isAllLevel()) {
-                    markSubject.setStage(MarkStage.SCORE);
-                    enterScoreStage(markSubject);
-                } else {
-                    markSubject.setStage(MarkStage.INSPECT);
-                    enterInspectStage(markSubject);
-                }
-                break;
-            case INSPECT:
-                //TODO 结束评卷
-                markSubject.setStage(MarkStage.END);
-                break;
+                enterScoreStage(markSubject);
+            } else {
+                markSubject.setStage(MarkStage.INSPECT);
+                enterInspectStage(markSubject);
+            }*/
+        } else if (MarkStage.INSPECT.equals(markStage)) {
+            //TODO 结束评卷
+            markSubject.setStage(MarkStage.END);
         }
         markSubjectRepo.save(markSubject);
         statusMap.put(markSubject.getId(), false);
     }
 
+    /**
+     * 进入粗分档阶段
+     * 1.检查是否有设定档位,如果有,将所有level设置连续的levelValue值,用于仲裁误差判定
+     * 2.检查有无可分档的评卷员,没有则终止
+     * 3.给所有能够分档的评卷员分配任务
+     */
+    private void enterRoughLevelStage(MarkSubject markSubject, int taskCount, Object questionId) throws Exception {
+        Long workId = markSubject.getWorkId();
+        Subject subject = markSubject.getSubject();
+        List<Level> levels = levelRepo.findByWorkId(workId);
+        if (levels.isEmpty()) {
+            statusMap.put(markSubject.getId(), false);
+            throw new RuntimeException("没有设定分档档位");
+        }
+
+        List<MarkUser> markers = markUserRepo.findByWorkIdAndSubjectAndRole(workId, subject, Role.MARKER);
+        List<MarkUser> levelMarkers = markers.stream().filter(m -> m.getMarkRight() == MarkRight.ALLOW_ALL || m.getMarkRight() == MarkRight.ALLOW_LEVELING).collect(Collectors.toList());
+        if (levelMarkers.isEmpty()) {
+            statusMap.put(markSubject.getId(), false);
+            throw new RuntimeException("没有设定评卷员");
+        }
+
+        List<MarkUser> markerLeader = markUserRepo.findByWorkIdAndSubjectAndRole(workId, subject, Role.MARK_LEADER);
+        if (markerLeader.isEmpty()) {
+            statusMap.put(markSubject.getId(), false);
+            throw new RuntimeException("没有设定科组长");
+        }
+
+        List<MarkerGroup> markerGroups = markerGroupRepo.findByWorkIdAndSubjectAndStage(workId, subject, markSubject.getStage());
+        if (markerGroups.isEmpty()) {
+            statusMap.put(markSubject.getId(), false);
+            throw new RuntimeException("评卷员没有进行分组");
+        }
+        List<Long> questionIdsLong = new ArrayList<>();
+        if (Objects.nonNull(questionId)) {
+            List<Integer> questionIds = (List<Integer>) questionId;
+            questionIdsLong = questionIds.stream().map(m -> Long.parseLong(m.toString())).collect(Collectors.toList());
+        }
+        List<Paper> allPapers = paperRepo.findByWorkIdAndSubjectAndIsMissingAndTest(workId, subject, false, markSubject.getTest());
+        if (markSubject.getTest() != 1) {
+            //是否有未结束的分档任务
+            long count = allPapers.stream().filter(m -> m.getRoughLevel() == null && m.getRoughBatchNo() != null).count();
+            if (count > 0) {
+                statusMap.put(markSubject.getId(), false);
+                throw new RuntimeException("没有分档完成");
+            }
+
+            //任务数量大于0,小于等于待评数量
+            if (taskCount == 0) {
+                statusMap.put(markSubject.getId(), false);
+                throw new RuntimeException("请输入正确的分配任务数量");
+            }
+            int waitCount;
+            if (questionIdsLong.isEmpty()) {
+                waitCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndRoughBatchNoIsNullAndTest(workId, subject, markSubject.getTest());
+            } else {
+                waitCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndRoughBatchNoIsNullAndTestAndQuestionIdIn(workId, subject, markSubject.getTest(), questionIdsLong);
+            }
+
+            if (waitCount == 0) {
+                statusMap.put(markSubject.getId(), false);
+                throw new RuntimeException("没有可分档任务");
+            }
+
+            if (taskCount - waitCount > 0) {
+                statusMap.put(markSubject.getId(), false);
+                throw new RuntimeException("分配任务数量不能大于待评数量");
+            }
+        }
+
+        Map<Long, List<Paper>> groupPaperMap = assignTaskService.assignGroupTasks(allPapers, markSubject, markerGroups, questionIdsLong, taskCount);
+        assignTaskService.assignForGroupingRoughLevel(groupPaperMap, markerGroups, markSubject);
+    }
+
     /**
      * 进入分档阶段
      * 1.检查是否有设定档位,如果有,将所有level设置连续的levelValue值,用于仲裁误差判定
@@ -150,9 +246,15 @@ public class StageControlService {
             throw new RuntimeException("评卷员没有进行分组");
         }
 
+        List<Long> questionIdsLong = new ArrayList<>();
+        if (Objects.nonNull(questionId)) {
+            List<Integer> questionIds = (List<Integer>) questionId;
+            questionIdsLong = questionIds.stream().map(m -> Long.parseLong(m.toString())).collect(Collectors.toList());
+        }
+
         if (markSubject.getTest() != 1) {
             //是否有未结束的分档任务
-            int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndActiveTrueAndBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
+            int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
             if (count > 0) {
                 statusMap.put(markSubject.getId(), false);
                 throw new RuntimeException("没有分档完成");
@@ -164,11 +266,10 @@ public class StageControlService {
                 throw new RuntimeException("请输入正确的分配任务数量");
             }
             int waitCount;
-            if (Objects.isNull(questionId)) {
-                waitCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndActiveFalseAndBatchNoIsNullAndTest(workId, subject, markSubject.getTest());
+            if (questionIdsLong.isEmpty()) {
+                waitCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndBatchNoIsNullAndTest(workId, subject, markSubject.getTest());
             } else {
-                Long questionId1 = Long.valueOf(questionId.toString());
-                waitCount = paperRepo.countByWorkIdAndQuestionIdAndSubjectAndIsMissingFalseAndActiveFalseAndBatchNoIsNullAndTest(workId, questionId1, subject, markSubject.getTest());
+                waitCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndBatchNoIsNullAndTestAndQuestionIdIn(workId, subject, markSubject.getTest(), questionIdsLong);
             }
 
             if (waitCount == 0) {
@@ -180,9 +281,17 @@ public class StageControlService {
                 statusMap.put(markSubject.getId(), false);
                 throw new RuntimeException("分配任务数量不能大于待评数量");
             }
+
+            // 分配任务数量必须大于名单总数量
+            long markerGroupStudentCount = markerGroupStudentRepo.countByWorkIdAndSubjectAndStageAndUsed(workId, subject, markSubject.getStage(), false);
+            if (taskCount - markerGroupStudentCount < 0) {
+                statusMap.put(markSubject.getId(), false);
+                throw new RuntimeException("分配任务数量必须大于各分组名单总数量");
+            }
         }
 
-        List<Paper> papers;
+        List<Paper> allPapers = paperRepo.findByWorkIdAndSubjectAndIsMissingAndTest(workId, subject, false, markSubject.getTest());
+        /*List<Paper> papers;
         if (markSubject.getTest() == 1) {
             papers = paperRepo.findByWorkIdAndSubjectAndIsMissingAndTest(workId, subject, false, markSubject.getTest());
         } else {
@@ -195,7 +304,9 @@ public class StageControlService {
             }
             papers = randomList(papersList, taskCount);
         }
-        assignTaskService.assignForGrouping(papers, markerGroups, markSubject, null);
+        assignTaskService.assignForGrouping(papers, markerGroups, markSubject, null);*/
+        Map<Long, List<Paper>> groupPaperMap = assignTaskService.assignGroupTasks(allPapers, markSubject, markerGroups, questionIdsLong, taskCount);
+        assignTaskService.assignForGroupingLevel(groupPaperMap, markerGroups, markSubject);
     }
 
     /**
@@ -235,7 +346,7 @@ public class StageControlService {
             statusMap.put(markSubject.getId(), false);
             throw new RuntimeException("没有设定评卷员");
         }
-        int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndActiveTrueAndBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
+        int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
         if (count > 0) {
             statusMap.put(markSubject.getId(), false);
             throw new RuntimeException("没有分档完成");
@@ -349,7 +460,7 @@ public class StageControlService {
             statusMap.put(markSubject.getId(), false);
             throw new RuntimeException("没有设定评卷员");
         }
-        int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndActiveTrueAndBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
+        int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
         if (count > 0) {
             statusMap.put(markSubject.getId(), false);
             throw new RuntimeException("没有分档完成");
@@ -374,7 +485,7 @@ public class StageControlService {
             statusMap.put(markSubject.getId(), false);
             throw new RuntimeException("没有设定评卷员");
         }
-        int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndActiveTrueAndBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
+        int count = paperRepo.countByWorkIdAndSubjectAndLevelIsNullAndIsMissingFalseAndBatchNoNotNullAndTest(workId, subject, markSubject.getTest());
         if (count > 0) {
             statusMap.put(markSubject.getId(), false);
             throw new RuntimeException("没有分档完成");
@@ -559,7 +670,11 @@ public class StageControlService {
     public void reset(MarkSubject markSubject, MarkStage stage, boolean force) {
         Subject subject = markSubject.getSubject();
         Long workId = markSubject.getWorkId();
-        markTaskRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, markSubject.getStage());
+        if (MarkStage.LEVEL.equals(stage)) {
+            markTaskLevelRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, markSubject.getStage());
+        } else if (MarkStage.SCORE.equals(stage)) {
+            markTaskScoreRepo.deleteByWorkIdAndSubjectAndStage(workId, subject, markSubject.getStage());
+        }
         markSubject.setStage(stage);
         markSubjectRepo.save(markSubject);
     }
@@ -642,38 +757,64 @@ public class StageControlService {
 
         List<LevleProgressDTO> list = new ArrayList<>();
         List<ExamQuestion> examQuestions = examQuestionRepo.findByWorkIdAndSubject(workId, markSubject.getSubject());
+        List<Paper> allPapers = paperRepo.findByWorkIdAndSubjectAndIsMissingAndTest(workId, subject, false, markSubject.getTest());
+        MarkStage stage = markSubject.getStage();
+        if (MarkStage.INIT.equals(markSubject.getStage())) {
+            if (ParamCache.levelConfigMap.get(String.valueOf(workId)).getRoughLevel() == 1) {
+                stage = MarkStage.ROUGH_LEVEL;
+            } else {
+                stage = MarkStage.LEVEL;
+            }
+        }
+
+        List<MarkerGroupStudent> markerGroupStudents = markerGroupStudentRepo.findByWorkIdAndSubjectAndStageAndUsed(workId, subject, stage, false);
+
         for (ExamQuestion examQuestion : examQuestions) {
             //已评任务数
-            int areaSuccessCount = paperRepo.countByWorkIdAndSubjectAndLevelNotNullAndIsMissingFalseAndActiveTrueAndTestAndQuestionId(workId, subject, 0, examQuestion.getId());
+            long areaSuccessCount = 0;
+            if (MarkStage.ROUGH_LEVEL.equals(stage)) {
+                areaSuccessCount = allPapers.stream().filter(m -> m.getRoughLevel() != null && m.getRoughBatchNo() != null && m.getQuestionId().equals(examQuestion.getId())).count();
+            } else if (MarkStage.LEVEL.equals(stage)) {
+                areaSuccessCount = allPapers.stream().filter(m -> StringUtils.isNotBlank(m.getLevel()) && m.getBatchNo() != null && m.getQuestionId().equals(examQuestion.getId())).count();
+            }
             //所有任务数(查询所有有效试卷)
-            int areaTotalCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndTestAndQuestionId(workId, subject, 0, examQuestion.getId());
+            long areaTotalCount = allPapers.stream().filter(m -> m.getQuestionId().equals(examQuestion.getId())).count();
 
             BigDecimal areaWaitTotal = BigDecimal.valueOf(areaTotalCount).subtract(BigDecimal.valueOf(areaSuccessCount));
             //进度
             BigDecimal areaProgress = BigDecimal.ZERO.compareTo(BigDecimal.valueOf(areaTotalCount)) == 0 ? BigDecimal.ZERO : BigDecimal.valueOf(areaSuccessCount).multiply(BigDecimal.valueOf(100)).divide(BigDecimal.valueOf(areaTotalCount), 2, BigDecimal.ROUND_HALF_UP);
 
             LevleProgressDTO areaProgressDTO = new LevleProgressDTO();
-            areaProgressDTO.setSuccessCount(areaSuccessCount);
-            areaProgressDTO.setTotalCount(areaTotalCount);
+            areaProgressDTO.setSuccessCount(Math.toIntExact(areaSuccessCount));
+            areaProgressDTO.setTotalCount(Math.toIntExact(areaTotalCount));
             areaProgressDTO.setWaitCount(areaWaitTotal.intValue());
             areaProgressDTO.setProgress(areaProgress.doubleValue());
             areaProgressDTO.setAreaName(examQuestion.getAreaName());
             areaProgressDTO.setQuestionId(examQuestion.getId());
+            // 查询初始值
+            long initCount = markerGroupStudents.isEmpty() ? 0 : markerGroupStudents.stream().filter(m -> m.getQuestionId().equals(examQuestion.getId())).count();
+            areaProgressDTO.setInitCount(Math.toIntExact(initCount));
+            areaProgressDTO.setInitChecked(initCount > 0);
             list.add(areaProgressDTO);
         }
 
         if (examQuestions.size() > 1) {
             //已评任务数
-            int successCount = paperRepo.countByWorkIdAndSubjectAndLevelNotNullAndIsMissingFalseAndActiveTrueAndTest(workId, subject, markSubject.getTest());
+            long successCount = 0;
+            if (MarkStage.ROUGH_LEVEL.equals(markSubject.getStage())) {
+                successCount = allPapers.stream().filter(m -> m.getRoughLevel() != null && m.getRoughBatchNo() != null).count();
+            } else if (MarkStage.LEVEL.equals(markSubject.getStage())) {
+                successCount = allPapers.stream().filter(m -> StringUtils.isNotBlank(m.getLevel()) && m.getBatchNo() != null).count();
+            }
             //所有任务数(查询所有有效试卷)
-            int totalCount = paperRepo.countByWorkIdAndSubjectAndIsMissingFalseAndTest(workId, subject, markSubject.getTest());
+            int totalCount = allPapers.size();
 
             BigDecimal waitTotal = BigDecimal.valueOf(totalCount).subtract(BigDecimal.valueOf(successCount));
             //进度
             BigDecimal progress = BigDecimal.ZERO.compareTo(BigDecimal.valueOf(totalCount)) == 0 ? BigDecimal.ZERO : BigDecimal.valueOf(successCount).multiply(BigDecimal.valueOf(100)).divide(BigDecimal.valueOf(totalCount), 2, BigDecimal.ROUND_HALF_UP);
 
             LevleProgressDTO progressDTO = new LevleProgressDTO();
-            progressDTO.setSuccessCount(successCount);
+            progressDTO.setSuccessCount(Math.toIntExact(successCount));
             progressDTO.setTotalCount(totalCount);
             progressDTO.setWaitCount(waitTotal.intValue());
             progressDTO.setProgress(progress.doubleValue());