Commit 6696c58d841defc9408447c10792cbb33dbcc701

Authored by 姜超
2 parents af797b5c 29ea29c9

Merge branch 'main' into jc-custom-indicator-2024-3-22

# Conflicts:
#	doc/2023-05-18_update.sql
Showing 45 changed files with 1396 additions and 481 deletions
doc/2023-05-18_update.sql
... ... @@ -2,6 +2,17 @@
2 2 ALTER TABLE `fw_morax`.`eval_indicator_import_record`
3 3 ADD COLUMN `import_type` tinyint(4) NULL DEFAULT 1 COMMENT '考评指标导入类型;1:结果数据 2:原始数据' AFTER `status`;
4 4  
  5 +-- 2024年4月3日
  6 +ALTER TABLE `fw_morax`.`eval_group_user`
  7 + ADD COLUMN `staff_status` tinyint(8) NULL COMMENT '当前员工状态:1->试用,2->正式,8->待离职,9->离职' AFTER `data_date`;
  8 +
  9 +ALTER TABLE `fw_morax`.`eval_user_report`
  10 + ADD COLUMN `staff_type` tinyint(4) default 0 COMMENT '员工分类: 0->绩效员工: 非0->其他员工(KpiIgnoreCauseEnum枚举取值)' AFTER `user_name`;
  11 +
  12 +ALTER TABLE `fw_morax`.`eval_group_user`
  13 + ADD COLUMN `leave_date` date NULL COMMENT '离职时间' AFTER `staff_status`;
  14 +
  15 +
5 16 -- 2024年3月20日
6 17 ALTER TABLE `fw_morax`.`eval_group_indicator_hit_log`
7 18 DROP INDEX `eval_reward_hit_log_index`,
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/bo/eval/EvalExtractStageIndicatorBO.java
... ... @@ -22,7 +22,7 @@ import java.util.concurrent.atomic.AtomicInteger;
22 22 public class EvalExtractStageIndicatorBO {
23 23 private Long evalCalcId;
24 24 private Long evalGroupRankId;
25   - private Set<Long> evalGroupIds;
  25 +// private Set<Long> evalGroupIds;
26 26 private LocalDate localDate;
27 27 private Boolean realTimeCalc;
28 28 // private AtomicInteger atomicInteger;
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/bo/eval/EvalGroupCalculableBO.java
... ... @@ -21,6 +21,6 @@ import java.util.Set;
21 21 public class EvalGroupCalculableBO {
22 22 private Long evalCalcId;
23 23 private Long evalGroupRankId;
24   - private Set<Long> evalGroupIds;
  24 +// private Set<Long> evalGroupIds;
25 25 private LocalDate localDate;
26 26 }
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/bo/eval/EvalGroupRankConfigBO.java 0 → 100644
  1 +package cn.fw.morax.domain.bo.eval;
  2 +
  3 +import cn.fw.morax.domain.db.eval.EvalGroup;
  4 +import cn.fw.morax.domain.db.eval.EvalGroupRank;
  5 +import cn.fw.morax.domain.db.eval.EvalGroupRankStage;
  6 +import lombok.AllArgsConstructor;
  7 +import lombok.Data;
  8 +import lombok.NoArgsConstructor;
  9 +
  10 +import java.time.LocalDate;
  11 +import java.util.Set;
  12 +
  13 +/**
  14 + * @author : kurisu
  15 + * @version : 1.0
  16 + * @className : KpiGroupCalculableBO
  17 + * @description : 需要计算绩效的考评组
  18 + * @date : 2022-04-16 11:31
  19 + */
  20 +@Data
  21 +@NoArgsConstructor
  22 +@AllArgsConstructor
  23 +public class EvalGroupRankConfigBO {
  24 +
  25 + private EvalGroupRank evalGroupRank;
  26 +
  27 + private EvalGroupRankStage evalGroupRankStage;
  28 +
  29 + private EvalGroup evalGroup;
  30 +}
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/bo/eval/EvalGroupUserShop.java
... ... @@ -133,7 +133,12 @@ public class EvalGroupUserShop {
133 133 /**
134 134 * 是否计不入考评考核
135 135 */
136   - private Boolean ignored;
  136 +// private Boolean ignored;
  137 +
  138 + /**
  139 + * 是否参与考评考核
  140 + */
  141 + private Boolean inclusion;
137 142  
138 143 /**
139 144 * 考评得分率排名
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/db/eval/EvalGroupUser.java
... ... @@ -2,6 +2,7 @@ package cn.fw.morax.domain.db.eval;
2 2  
3 3 import cn.fw.common.data.entity.BaseAuditableTimeEntity;
4 4 import cn.fw.morax.domain.enums.KpiIgnoreCauseEnum;
  5 +import cn.fw.morax.domain.enums.SalaryStaffStatusEnum;
5 6 import com.baomidou.mybatisplus.annotation.TableName;
6 7 import lombok.*;
7 8  
... ... @@ -87,6 +88,16 @@ public class EvalGroupUser extends BaseAuditableTimeEntity&lt;EvalGroupUser, Long&gt;
87 88 * 数据日期
88 89 */
89 90 private LocalDate dataDate;
  91 +
  92 + /**
  93 + * 离职日期
  94 + */
  95 + private LocalDate leaveDate;
  96 +
  97 + /**
  98 + * '当前员工状态' 当前员工状态:1->试用,2->正式,8->待离职,9->离职
  99 + */
  100 + private SalaryStaffStatusEnum staffStatus;
90 101 /**
91 102 * 集团id
92 103 */
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/db/eval/EvalUserPool.java
... ... @@ -2,6 +2,7 @@ package cn.fw.morax.domain.db.eval;
2 2  
3 3 import cn.fw.common.data.entity.BaseAuditableTimeEntity;
4 4 import cn.fw.morax.domain.enums.EvalPoolBusinessTypeEnum;
  5 +import com.baomidou.mybatisplus.annotation.FieldStrategy;
5 6 import com.baomidou.mybatisplus.annotation.TableField;
6 7 import com.baomidou.mybatisplus.annotation.TableLogic;
7 8 import com.baomidou.mybatisplus.annotation.TableName;
... ... @@ -111,6 +112,7 @@ public class EvalUserPool extends BaseAuditableTimeEntity&lt;EvalUserPool, Long&gt; {
111 112 /**
112 113 * 排名
113 114 */
  115 + @TableField(updateStrategy = FieldStrategy.IGNORED)
114 116 private Integer rank;
115 117  
116 118 /**
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/db/eval/EvalUserReport.java
... ... @@ -54,6 +54,12 @@ public class EvalUserReport extends BaseEntity&lt;EvalUserReport, Long&gt; {
54 54 */
55 55 private String userName;
56 56  
  57 +
  58 + /**
  59 + * 绩效员工取值0,其他非绩效员工取值 KpiIgnoreCauseEnum 枚举的值value
  60 + */
  61 + private Integer staffType;
  62 +
57 63 /**
58 64 * 岗位id
59 65 */
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/dto/IgnoreCauseDTO.java
... ... @@ -15,6 +15,11 @@ public class IgnoreCauseDTO {
15 15 private LocalDate startKpiDate;
16 16 private String ignoreConfig;
17 17 /**
  18 + * 触发事件
  19 + */
  20 + private LocalDate eventTime;
  21 +
  22 + /**
18 23 * 不计入原因描述
19 24 */
20 25 private String ignoreCauseDesc;
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/enums/ExtraSalarySubTypeEnum.java
... ... @@ -40,6 +40,7 @@ public enum ExtraSalarySubTypeEnum implements IEnum&lt;Integer&gt; {
40 40 DISABILITY(44, "残障补贴"),
41 41 OVERSEAS(45, "驻外补贴"),
42 42 TEMPORARY_MEAL(46, "临时餐补"),
  43 + NIGHT_SHIFT(47, "晚班补贴"),
43 44 EVAL_SHOP_ROLE_REWARD(60, "考评门店角色奖励"),
44 45 EVAL_SHOP_ROLE_PUNISH(61, "考评门店角色惩罚"),
45 46 EVAL_SHOP_REWARD_DIST(62, "考评门店奖惩分配"),
... ...
fw-morax-domain/src/main/java/cn/fw/morax/domain/enums/KpiIgnoreCauseEnum.java
... ... @@ -27,6 +27,8 @@ public enum KpiIgnoreCauseEnum implements IEnum&lt;Integer&gt; {
27 27 TRANSPOST_BEFORE_15(10, "15号以前调岗不计入绩效考核"),
28 28 LEAVE_DAY_OVERLENGTH_IGNORE_KPI(11, "请假超过X天不计入绩效考核"),
29 29 TURN_POSITIVE_POSITION(12, "调岗保护期内不计入绩效考核"),
  30 + EVAL_MULTISTAGE_TIME_POST_CHANGE(13, "考评多阶段时间内调岗,不纳入考评计算"),
  31 + EVAL_MULTISTAGE_TIME_LEAVE(14, "考评多阶段时间内离职,不纳入考评计算"),
30 32 ;
31 33  
32 34 /**
... ...
fw-morax-rpc/src/main/java/cn/fw/morax/rpc/ehr/EhrRpcService.java
... ... @@ -393,7 +393,7 @@ public class EhrRpcService {
393 393 * @return
394 394 */
395 395 public List<PerformanceStaffDTO> queryKpiStaff(Long groupId, Long postId, List<Long> shopIds, LocalDate date) {
396   - return this.queryKpiStaffByName(groupId, Lists.newArrayList(postId), shopIds, null, date);
  396 + return this.getPointTimeStaffs(groupId, Lists.newArrayList(postId), shopIds, null, date);
397 397 }
398 398  
399 399 /**
... ... @@ -404,7 +404,7 @@ public class EhrRpcService {
404 404 * @return
405 405 */
406 406 public List<PerformanceStaffDTO> queryKpiStaff(Long groupId, List<Long> postIds, List<Long> shopIds, LocalDate date) {
407   - return this.queryKpiStaffByName(groupId, postIds, shopIds, null, date);
  407 + return this.getPointTimeStaffs(groupId, postIds, shopIds, null, date);
408 408 }
409 409  
410 410 /**
... ... @@ -416,7 +416,7 @@ public class EhrRpcService {
416 416 */
417 417 @Nullable
418 418 public List<PerformanceStaffDTO> queryRealTimeKpiStaff(Long groupId, Long postId, List<Long> shopIds, String staffName) {
419   - return this.queryKpiStaffByName(groupId, Lists.newArrayList(postId), shopIds, staffName, LocalDate.now());
  419 + return this.getPointTimeStaffs(groupId, Lists.newArrayList(postId), shopIds, staffName, LocalDate.now());
420 420 }
421 421  
422 422 /**
... ... @@ -450,6 +450,82 @@ public class EhrRpcService {
450 450 return new ArrayList<>();
451 451 }
452 452  
  453 + /**
  454 + * 获取某一时间点集团人员简要信息
  455 + * <span>
  456 + * 张三: 3-1 A门店 A岗位
  457 + * 3-5 调至B门店 B岗位
  458 + * 3-10 离职
  459 + * pointTime: 3-2、3-5 返回张三 A门店 A岗位;
  460 + * 3-6、3-10 返回张三 B门店 B岗位;
  461 + * 3-11 不会返回张三
  462 + */
  463 + @Nullable
  464 + public List<PerformanceStaffDTO> getPointTimeStaffs(Long groupId, List<Long> postIds, List<Long> shopIds, String staffName, LocalDate date) {
  465 + if (PublicUtil.isEmpty(groupId) || PublicUtil.isEmpty(postIds) ||
  466 + PublicUtil.isEmpty(shopIds) || PublicUtil.isEmpty(date)) {
  467 + return new ArrayList<>();
  468 + }
  469 + Date queryDate = DateUtil.localDateTime2Date(date.atTime(00, 00, 00));
  470 + Long queryDateTime = queryDate.getTime();
  471 + try {
  472 + log.info("StaffApi.getStaffByPostShopList: 开始进行请求。groupId:[{}],queryDate:[{}],time:[{}] ",
  473 + groupId, queryDate, queryDateTime);
  474 + final Message<List<StaffSimpleInfoVo>> msg = staffApi.getPointTimeStaffList(groupId, queryDate.getTime());
  475 + log.info("StaffApi.getPointTimeStaffList: groupId:[{}],queryDate:[{}],time:[{}], msg.code={}, msg.result={}, msg.data={}",
  476 + groupId, queryDate, queryDateTime, msg.getCode(), JSON.toJSONString(msg.getResult()), JSON.toJSONString(msg.getData()));
  477 + if (msg.isSuccess() && !Objects.isNull(msg.getData())) {
  478 + return getSimplePerformanceStaffDTOS(staffName, msg, postIds , shopIds);
  479 + }
  480 + } catch (Exception e) {
  481 + log.error("获取人员信息失败:", e);
  482 + }
  483 + return new ArrayList<>();
  484 + }
  485 +
  486 + private List<PerformanceStaffDTO> getSimplePerformanceStaffDTOS(String staffName, Message<List<StaffSimpleInfoVo>> msg, List<Long> postIds , List<Long> shopIds) {
  487 + List<PerformanceStaffDTO> staffDTOS = new ArrayList<>(msg.getData().size());
  488 + PerformanceStaffDTO staffDTO = null;
  489 + for (StaffSimpleInfoVo staffVo : msg.getData()) {
  490 + //判断岗位、门店
  491 + if (! postIds.contains(staffVo.getPostId()) || (! shopIds.contains(staffVo.getShopId()))) {
  492 + continue;
  493 + }
  494 + if (PublicUtil.isNotEmpty(staffName) && (! staffVo.getStaffName().contains(staffName))) {
  495 + continue;
  496 + }
  497 + staffDTO = PublicUtil.copy(staffVo, PerformanceStaffDTO.class);
  498 + staffDTO.setId(Optional.ofNullable(staffVo.getStaffId()).orElse(-1L));
  499 + staffDTO.setName(Optional.ofNullable(staffVo.getStaffName()).orElse(""));
  500 + staffDTO.setWorkAge(Optional.ofNullable(staffVo.getWorkAge()).orElse(1));
  501 + ZoneId zoneId = ZoneId.systemDefault();
  502 + if (PublicUtil.isNotEmpty(staffVo.getEntryDate())) {
  503 + staffDTO.setEntryDate(staffVo.getEntryDate().toInstant().atZone(zoneId).toLocalDate());
  504 + }
  505 + if (PublicUtil.isNotEmpty(staffVo.getRegularDate())) {
  506 + staffDTO.setRegularDate(staffVo.getRegularDate().toInstant().atZone(zoneId).toLocalDate());
  507 + }
  508 + if (PublicUtil.isNotEmpty(staffVo.getLeaveDate())) {
  509 + staffDTO.setLeaveDate(DateUtil.date2LocalDate(staffVo.getLeaveDate()));
  510 + }
  511 + staffDTO.setStaffStatus(staffVo.getStaffStatus());
  512 + //原来员工状态 (针对离职员工之前的状态,未离职的就是当前状态一致)
  513 + staffDTO.setOriginStaffStatus(staffVo.getStaffStatus());
  514 + //判断离职员工
  515 + if (StaffStatusEnum.DUTY_OFF.getValue().equals(staffVo.getStaffStatus()) ||
  516 + StaffStatusEnum.LEAVE.getValue().equals(staffVo.getStaffStatus())) {
  517 + //试用期员工 转正时间为空。是否是试用期员工,并修改原始状态
  518 + if (PublicUtil.isEmpty(staffVo.getRegularDate())) {
  519 + staffDTO.setOriginStaffStatus(StaffStatusEnum.PROBATION.getValue());
  520 + } else {
  521 + staffDTO.setOriginStaffStatus(StaffStatusEnum.REGULAR.getValue());
  522 + }
  523 + }
  524 + staffDTOS.add(staffDTO);
  525 + }
  526 + return staffDTOS;
  527 + }
  528 +
453 529 private List<PerformanceStaffDTO> getPerformanceStaffDTOS(String staffName, Message<List<StaffBaseInfo>> msg) {
454 530 List<PerformanceStaffDTO> staffDTOS = new ArrayList<>(msg.getData().size());
455 531 PerformanceStaffDTO staffDTO = null;
... ...
fw-morax-rpc/src/main/java/cn/fw/morax/rpc/ehr/dto/PostChangeDTO.java 0 → 100644
  1 +package cn.fw.morax.rpc.ehr.dto;
  2 +
  3 +import cn.fw.ehr.sdk.api.mq.StaffPostChangeEvent;
  4 +import lombok.Data;
  5 +
  6 +import java.util.List;
  7 +
  8 +/**
  9 + * 员工门店列表
  10 + */
  11 +@Data
  12 +public class PostChangeDTO {
  13 + /**
  14 + * 人员id
  15 + */
  16 + private List<StaffPostChangeEvent> events;
  17 +
  18 +}
... ...
fw-morax-sdk/src/main/java/cn/fw/morax/sdk/dto/common/SalaryExtraProjectSubTypeEnum.java
... ... @@ -22,6 +22,7 @@ public enum SalaryExtraProjectSubTypeEnum {
22 22 DISABILITY(44, "残障补贴"),
23 23 OVERSEAS(45, "驻外补贴"),
24 24 TEMPORARY_MEAL(46, "临时餐补"),
  25 + NIGHT_SHIFT(47, "晚班补贴"),
25 26 SOCIAL_SECURITY(300, "社保"),
26 27 MEDICAL_INSURANCE(301, "医保"),
27 28 ACCUMULATION_FUND(302, "公积金"),
... ...
fw-morax-server/src/main/java/cn/fw/morax/server/consumer/EhrStaffEndAwaitJobConsumer.java
... ... @@ -27,9 +27,9 @@ public class EhrStaffEndAwaitJobConsumer implements RocketMQListener&lt;EndWaitJobE
27 27 private final CommonService commonService;
28 28 private final KpiGroupService kpiGroupService;
29 29  
30   - @Value("${spring.cache.custom.global-prefix}:kpi:anticipated_date:")
31   - @Getter
32   - private String key;
  30 +// @Value("${spring.cache.custom.global-prefix}:kpi:anticipated_date:")
  31 +// @Getter
  32 +// private String key;
33 33  
34 34 /***
35 35 * 人员待岗开始事件
... ...
fw-morax-server/src/main/java/cn/fw/morax/server/consumer/EhrStaffPostConsumer.java
... ... @@ -54,10 +54,6 @@ public class EhrStaffPostConsumer implements RocketMQListener&lt;StaffPostChangeEve
54 54 final Integer postChangeDay = changeTime.getDayOfMonth();
55 55 final Long originPostId = result.getPostId();
56 56 final Long newPostId = result.getNewPostId();
57   - //记录调岗日期
58   - commonService.recordTranspostAfterDate(staffId, changeTime);
59   - //记录旧调岗日期
60   - commonService.recordPostChangeDate(staffId, originPostId, changeTime, result.getShopId());
61 57  
62 58 StaffBaseInfoDTO staffBaseInfo = ehrRpcService.queryStaffBaseInfo(staffId);
63 59 if (PublicUtil.isEmpty(staffBaseInfo)) {
... ... @@ -65,15 +61,32 @@ public class EhrStaffPostConsumer implements RocketMQListener&lt;StaffPostChangeEve
65 61 return;
66 62 }
67 63 final Long groupId = staffBaseInfo.getGroupId();
68   -
69 64 //不同岗位调岗 才记录调岗时间
70 65 if (! newPostId.equals(originPostId)) {
  66 + //记录旧调岗日期
  67 + commonService.recordOldPostChangeDate(staffId, originPostId, changeTime);
  68 + commonService.recordNewPostChangeDate(staffId, newPostId, changeTime.plusDays(1));
71 69 PostInfoDTO newPost = ehrRpcService.getPostInfo(newPostId);
72 70 PostInfoDTO originPost = ehrRpcService.getPostInfo(originPostId);
73 71 if (PublicUtil.isEmpty(newPost) || PublicUtil.isEmpty(originPost)) {
74 72 log.error("岗位信息找不到,newPostId:{},originPostId:{}", newPostId, originPostId);
75 73 return;
76 74 }
  75 + //岗位当月是否参与绩效
  76 + final Integer afterTransPostIgnoreKpiDay = kpiDictBizService.getAfterTransPostDay(groupId).intValue();
  77 + final Integer beforeTransferIgnoreKpiDay = kpiDictBizService.getBeforeTransPostDay(groupId).intValue();
  78 + //日期在当月X之后(包含),新岗位次月参与绩效考核,旧岗位当月参与绩效考核(调岗日期 大于等于 配置日期)
  79 + if (postChangeDay >= afterTransPostIgnoreKpiDay) {
  80 + //下月1号
  81 + LocalDate newPostStartKpiDate = YearMonth.from(changeTime).plusMonths(1).atDay(1);
  82 + commonService.recordNewPostStartKpiDate(staffId, newPostId, newPostStartKpiDate);
  83 + }
  84 + //日期在当月X之前(不包含),新岗位当月参与绩效考核,旧岗位当月不参与绩效考核(配置日期 大于 调岗日期)
  85 + if (beforeTransferIgnoreKpiDay > postChangeDay) {
  86 + //下月1号
  87 + LocalDate newPostStartKpiDate = YearMonth.from(changeTime).plusMonths(1).atDay(1);
  88 + commonService.recordOldPostStartKpiDate(staffId, originPostId, newPostStartKpiDate, result.getShopId());
  89 + }
77 90  
78 91 //降级没有保护期,旧岗位角色 是 新岗位角色 的上级
79 92 String newPostRoleCode = newPost.getRoleCode();
... ... @@ -87,22 +100,8 @@ public class EhrStaffPostConsumer implements RocketMQListener&lt;StaffPostChangeEve
87 100 }
88 101  
89 102 //记录新调岗日期(岗位降级不需要记录,以免触发保护期)
90   - commonService.recordNonDemotionNewPostChangeDate(staffId, newPostId, changeTime, result.getNewShopId());
  103 + commonService.recordNonDemotionNewPostChangeDate(staffId, newPostId, changeTime);
91 104  
92   - final Integer afterTransPostIgnoreKpiDay = kpiDictBizService.getAfterTransPostDay(groupId).intValue();
93   - final Integer beforeTransferIgnoreKpiDay = kpiDictBizService.getBeforeTransPostDay(groupId).intValue();
94   - //日期在当月X之后(包含),新岗位次月参与绩效考核,旧岗位当月参与绩效考核(调岗日期 大于等于 配置日期)
95   - if (postChangeDay >= afterTransPostIgnoreKpiDay) {
96   - //下月1号
97   - LocalDate newPostStartKpiDate = YearMonth.from(changeTime).plusMonths(1).atDay(1);
98   - commonService.recordNewPostStartKpiDate(staffId, newPostId, newPostStartKpiDate, result.getNewShopId());
99   - }
100   - //日期在当月X之前(不包含),新岗位当月参与绩效考核,旧岗位当月不参与绩效考核(配置日期 大于 调岗日期)
101   - if (beforeTransferIgnoreKpiDay > postChangeDay) {
102   - //下月1号
103   - LocalDate newPostStartKpiDate = YearMonth.from(changeTime).plusMonths(1).atDay(1);
104   - commonService.recordOldPostStartKpiDate(staffId, originPostId, newPostStartKpiDate, result.getShopId());
105   - }
106 105 }
107 106 //同一个门店 不触发保护期
108 107 // if (result.getPostId().equals(result.getNewPostId())) {
... ...
fw-morax-server/src/main/java/cn/fw/morax/server/controller/erp/EvalDebugController.kt 0 → 100644
  1 +package cn.fw.morax.server.controller.erp
  2 +
  3 +import cn.fw.common.web.annotation.ControllerMethod
  4 +import cn.fw.common.web.util.ResultBuilder.success
  5 +import cn.fw.data.base.domain.common.Message
  6 +import cn.fw.morax.common.utils.DateUtil
  7 +import cn.fw.morax.domain.db.eval.EvalGroupUser
  8 +import cn.fw.morax.service.biz.eval.EvalGroupUserBizService
  9 +import cn.fw.security.auth.client.annotation.Authorization
  10 +import cn.fw.security.auth.client.enums.AuthType
  11 +import org.springframework.validation.annotation.Validated
  12 +import org.springframework.web.bind.annotation.GetMapping
  13 +import org.springframework.web.bind.annotation.RequestMapping
  14 +import org.springframework.web.bind.annotation.RestController
  15 +import java.time.LocalDate
  16 +import java.util.Date
  17 +
  18 +/**
  19 + * @author jiangchao
  20 + * @des:
  21 + * @date 2024/3/29 18:50
  22 + */
  23 +@RestController
  24 +@Authorization(AuthType.NONE)
  25 +@Validated
  26 +@RequestMapping("/debug/eval")
  27 +class EvalDebugController(private val evalGroupUserBizService: EvalGroupUserBizService) {
  28 +
  29 +
  30 + @GetMapping("/users")
  31 + @ControllerMethod("查看考评人员")
  32 + fun fetchPostUsers(groupId: Long, postId: Long, shopId: Long, date: Date?): Message<List<EvalGroupUser>> {
  33 + val dataDate = date?.let {
  34 + DateUtil.date2LocalDate(date)
  35 + } ?: LocalDate.now().minusDays(1)
  36 + return success(evalGroupUserBizService.fetchPostUsers(groupId, postId, listOf(shopId), dataDate));
  37 + }
  38 +}
0 39 \ No newline at end of file
... ...
fw-morax-server/src/main/java/cn/fw/morax/server/controller/erp/EvalTaskController.java
1 1 package cn.fw.morax.server.controller.erp;
2 2  
  3 +import cn.fw.common.exception.BusinessException;
3 4 import cn.fw.common.web.annotation.ControllerMethod;
4 5 import cn.fw.data.base.domain.common.Message;
5 6 import cn.fw.morax.common.utils.DateUtil;
... ... @@ -71,6 +72,7 @@ public class EvalTaskController {
71 72 private final EvalGroupIndicatorParamService evalGroupIndicatorParamService;
72 73 private final EvalGroupIndicatorPreconditionService evalGroupIndicatorPreconditionService;
73 74 private final IndicatorsService indicatorsService;
  75 + private final EvalCalcService evalCalcService;
74 76 private final EvalIndicatorService evalIndicatorService;
75 77 private final KpiStageIndicatorBizService kpiStageIndicatorBizService;
76 78 private final EvalIndicatorValueBizService evalIndicatorValueBizService;
... ... @@ -102,6 +104,18 @@ public class EvalTaskController {
102 104 return success();
103 105 }
104 106  
  107 + @GetMapping("/cache-stage-mq")
  108 + @ControllerMethod("缓存发送考评指标上报mq")
  109 + public Message<Void> sendStageMQ(Long evalCalcId, Date date) {
  110 + EvalCalc evalCalc = evalCalcService.getById(evalCalcId);
  111 + if (PublicUtil.isEmpty(evalCalc) || PublicUtil.isEmpty(evalCalc.getEvalGroupRankId()) || PublicUtil.isEmpty(evalCalc.getEvalGroupIds())) {
  112 + throw new BusinessException("参数为空");
  113 + }
  114 + LocalDate calcDate = PublicUtil.isEmpty(date) ? evalCalc.getCalcDate() : DateUtil.date2LocalDate(date);
  115 + evalCalculateTaskService.cacheStageIndicator(evalCalcId, evalCalc.getEvalGroupRankId(), Boolean.TRUE, calcDate);
  116 + return success();
  117 + }
  118 +
105 119 @GetMapping("/stage-mq")
106 120 @ControllerMethod("发送考评指标上报mq")
107 121 public Message<Void> sendStageMQ() {
... ...
fw-morax-server/src/main/java/cn/fw/morax/server/controller/erp/SalaryDebugController.java
... ... @@ -30,6 +30,7 @@ import cn.fw.morax.rpc.approval.FlowApproveRpc;
30 30 import cn.fw.morax.rpc.backlog.TodoRpcService;
31 31 import cn.fw.morax.rpc.backlog.dto.BackLogItemDTO;
32 32 import cn.fw.morax.rpc.ehr.EhrRpcService;
  33 +import cn.fw.morax.rpc.ehr.dto.PostChangeDTO;
33 34 import cn.fw.morax.rpc.ehr.dto.StaffBaseInfoDTO;
34 35 import cn.fw.morax.rpc.ehr.dto.StaffInfoDTO;
35 36 import cn.fw.morax.rpc.ehr.dto.StaffShopInfoDTO;
... ... @@ -282,6 +283,21 @@ public class SalaryDebugController {
282 283 }
283 284  
284 285 /**
  286 + * 人事系统人员调岗MQ消息
  287 + *
  288 + * @return
  289 + */
  290 + @PostMapping("/alter/posts")
  291 + @IgnoreUserToken
  292 + @ControllerMethod("人事系统人员调岗MQ消息")
  293 + public Message<List<SalaryGroupVO>> postChange(@RequestBody PostChangeDTO event) {
  294 + for (StaffPostChangeEvent event1 : event.getEvents()) {
  295 + ehrStaffPostConsumer.onMessage(event1);
  296 + }
  297 + return success();
  298 + }
  299 +
  300 + /**
285 301 * 门店名称变更
286 302 *
287 303 * @return
... ...
fw-morax-server/src/main/java/cn/fw/morax/server/task/EvalUserReportTask.java
... ... @@ -45,6 +45,7 @@ import java.math.BigDecimal;
45 45 import java.math.RoundingMode;
46 46 import java.time.LocalDate;
47 47 import java.time.YearMonth;
  48 +import java.time.temporal.TemporalAdjusters;
48 49 import java.util.*;
49 50 import java.util.concurrent.RejectedExecutionException;
50 51 import java.util.concurrent.atomic.AtomicInteger;
... ... @@ -197,9 +198,9 @@ public class EvalUserReportTask {
197 198 }
198 199 List<EvalUserPool> userPools = evalUserPoolService.getPools(evalGroupRankStageId, YearMonth.from(dataDate));
199 200 // .filter(pool -> ! evalGroupUserService.probationStaff(pool.getUserId(), rankStage.getBeginTime(), rankStage.getOverTime()))
200   - List<EvalUserPool> nonProbationStaffs = userPools.stream()
201   - .filter(pool -> Boolean.TRUE.equals(pool.getInclusion()))
202   - .collect(Collectors.toList());
  201 +// List<EvalUserPool> nonProbationStaffs = userPools.stream()
  202 +// .filter(pool -> Boolean.TRUE.equals(pool.getInclusion()))
  203 +// .collect(Collectors.toList());
203 204 List<Long> disableShopIds = invalidShopLogService.queryInvalidShopIds(groupId, dataDate);
204 205 List<EvalShopPool> shopPools = evalShopPoolService.list(Wrappers.<EvalShopPool>lambdaQuery()
205 206 .in(EvalShopPool::getEvalGroupId, evalGroupIds)
... ... @@ -223,10 +224,10 @@ public class EvalUserReportTask {
223 224 EvalGroupReportParamsBO paramsBO = new EvalGroupReportParamsBO(stageDim, rankStage, rank.getGroupId(), multiStage, dataDate);
224 225 //排名组指标编码、人员、门店
225 226 List<EvalUserRankCodeReport> rankCodes = this.saveRankCodeReports(evalGroupIndicators, evalUserRankReportId, evalUserRankStageReportId, paramsBO);
226   - List<EvalUserReport> evalUserReports = this.saveStaffReports(nonProbationStaffs, evalUserRankReportId, evalUserRankStageReportId,paramsBO);
227   - List<EvalUserReport> evalShopReports = this.saveShopReports(shopPools, evalUserRankReportId, evalUserRankStageReportId,paramsBO);
  227 + List<EvalUserReport> evalUserReports = this.saveStaffReports(userPools, evalUserRankReportId, evalUserRankStageReportId, paramsBO);
  228 + List<EvalUserReport> evalShopReports = this.saveShopReports(shopPools, evalUserRankReportId, evalUserRankStageReportId, paramsBO);
228 229 //人员维度
229   - calcUser(nonProbationStaffs, evalGroupIndicators, evalGroupIndicatorParamMap, evalUserReports, paramsBO);
  230 + calcUser(userPools, evalGroupIndicators, evalGroupIndicatorParamMap, evalUserReports, paramsBO);
230 231 //门店维度
231 232 calcShop(shopPools, evalGroupIndicators, evalGroupIndicatorParamMap, evalShopReports, paramsBO);
232 233 //门店维度
... ... @@ -427,6 +428,10 @@ public class EvalUserReportTask {
427 428 } else {
428 429 indicatorValue = commonService.queryMonthValue(userId, scopeType, dataDate, param.getCodeType(), param.getCode());
429 430 }
  431 + //计算目标
  432 + if (!TargetTypeEnum.NO.equals(targetType)) {
  433 + indicatorValue = this.calculateTargetValue(param.getTargetCalcType(), param.getTargetValue(), indicatorValue, param.getMinimumStandardValue());
  434 + }
430 435 boolean isCap = Boolean.TRUE.equals(param.getCap());
431 436 BigDecimal proportion = param.getProportion();
432 437 if (isCap) {
... ... @@ -453,6 +458,35 @@ public class EvalUserReportTask {
453 458 }
454 459  
455 460 /**
  461 + * 经过目标计算后的用户指标值
  462 + *
  463 + * @param targetCalcType
  464 + * @param targetValue
  465 + * @param userValue
  466 + * @return
  467 + */
  468 + protected BigDecimal calculateTargetValue(TargetCalcTypeEnum targetCalcType, BigDecimal targetValue,
  469 + BigDecimal userValue, BigDecimal minimumStandardValue) {
  470 + if (Objects.isNull(targetValue) || targetValue.compareTo(BigDecimal.ZERO) <= 0) {
  471 + return userValue;
  472 + }
  473 + if (TargetCalcTypeEnum.TARGET_VALUE.equals(targetCalcType)) {
  474 + return userValue.divide(targetValue, 4, RoundingMode.HALF_UP);
  475 + }
  476 + //最低目标计算方式 高线要求
  477 + BigDecimal diffValue = Optional.ofNullable(minimumStandardValue).orElse(BigDecimal.ONE).subtract(targetValue);
  478 +// BigDecimal diffValue = BigDecimal.ONE.subtract(targetValue);
  479 + BigDecimal userDiffValue = userValue.subtract(targetValue);
  480 + if (userDiffValue.compareTo(BigDecimal.ZERO) <= 0) {
  481 + return BigDecimal.ZERO;
  482 + }
  483 + if (diffValue.compareTo(BigDecimal.ZERO) <= 0) {
  484 + return userDiffValue;
  485 + }
  486 + return userDiffValue.divide(diffValue, 4, RoundingMode.HALF_UP);
  487 + }
  488 +
  489 + /**
456 490 * 人员得分情况
457 491 */
458 492 public MultiKeyMap<Long, BigDecimal> getUserIndicatorScoreMap(List<EvalGroupIndicator> evalGroupIndicators, LocalDate date, List<EvalUserPool> userPools) {
... ... @@ -575,27 +609,38 @@ public class EvalUserReportTask {
575 609 if (PublicUtil.isEmpty(pools)) {
576 610 return new ArrayList<>();
577 611 }
  612 + final Long evalGroupRankStageId = paramsBO.getStage().getId();
578 613 final LocalDate dataDate = paramsBO.getDataDate();
  614 + final LocalDate stageStartDate = paramsBO.getStage().getBeginTime();
579 615 List<EvalUserReport> evalUserReports = new ArrayList<>();
580 616 for (EvalUserPool userPool : pools) {
581   - EvalUserReport report = new EvalUserReport();
582   - report.setStageDim(paramsBO.getStageDimEnum());
583   - report.setEvalUserRankReportId(evalUserRankReportId);
584   - report.setEvalUserRankStageReportId(evalUserRankStageReportId);
585   - report.setDimension(ReportDimensionEnum.STAFF);
586   - report.setReward(userPool.getReward());
587   - report.setScore(userPool.getScore());
588   - report.setScoreRatio(userPool.getScoreRatio().multiply(Constant.ONE_HUNDRED));
589   - report.setUserId(userPool.getUserId());
590   - report.setUserName(userPool.getUserName());
591   - report.setPostId(userPool.getPostId());
592   - report.setPostName(userPool.getPostName());
593   - report.setShopId(userPool.getShopId());
594   - report.setShopName(userPool.getShopName());
595   - report.setEvalUserPoolId(userPool.getId());
596   - report.setDataDate(dataDate);
597   - report.setInclusion(userPool.getInclusion());
598   - evalUserReports.add(report);
  617 + EvalUserReport userReport = new EvalUserReport();
  618 + userReport.setStageDim(paramsBO.getStageDimEnum());
  619 + userReport.setEvalUserRankReportId(evalUserRankReportId);
  620 + userReport.setEvalUserRankStageReportId(evalUserRankStageReportId);
  621 + userReport.setDimension(ReportDimensionEnum.STAFF);
  622 + userReport.setReward(userPool.getReward());
  623 + userReport.setScore(userPool.getScore());
  624 + userReport.setScoreRatio(userPool.getScoreRatio().multiply(Constant.ONE_HUNDRED));
  625 + userReport.setUserId(userPool.getUserId());
  626 + userReport.setUserName(userPool.getUserName());
  627 + userReport.setPostId(userPool.getPostId());
  628 + userReport.setPostName(userPool.getPostName());
  629 + userReport.setShopId(userPool.getShopId());
  630 + userReport.setShopName(userPool.getShopName());
  631 + userReport.setEvalUserPoolId(userPool.getId());
  632 + userReport.setDataDate(dataDate);
  633 + userReport.setInclusion(userPool.getInclusion());
  634 + //默认为绩效员工
  635 + userReport.setStaffType(0);
  636 +
  637 + EvalGroupUser evalGroupUser = evalGroupUserService.getMonthStageLastData(evalGroupRankStageId, userPool.getUserId(),
  638 + stageStartDate, dataDate);
  639 + //处理员工分类
  640 + if (PublicUtil.isNotEmpty(evalGroupUser) && PublicUtil.isNotEmpty(evalGroupUser.getIgnoreCause()) ){
  641 + userReport.setStaffType(evalGroupUser.getIgnoreCause().getValue());
  642 + }
  643 + evalUserReports.add(userReport);
599 644 }
600 645 evalUserReportService.insertBatchSomeColumn(evalUserReports);
601 646 return evalUserReports;
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/CommonService.java
... ... @@ -11,6 +11,7 @@ import cn.fw.morax.common.utils.DateUtil;
11 11 import cn.fw.morax.common.utils.ExcelDataUtil;
12 12 import cn.fw.morax.common.utils.PublicUtil;
13 13 import cn.fw.morax.common.utils.StringUtils;
  14 +import cn.fw.morax.domain.db.PayrollRecord;
14 15 import cn.fw.morax.domain.db.SettingDraft;
15 16 import cn.fw.morax.domain.db.eval.EvalGroupRewardRankLog;
16 17 import cn.fw.morax.domain.db.eval.EvalIndicator;
... ... @@ -116,8 +117,8 @@ public class CommonService {
116 117 private final KpiGroupIndicatorParamService kpiGroupIndicatorParamService;
117 118 private final IndicatorUserStageValueService indicatorUserStageValueService;
118 119  
119   - @Value("${spring.cache.custom.global-prefix}:kpi:anticipated_date:")
120   - private String startKpiKey;
  120 +// @Value("${spring.cache.custom.global-prefix}:kpi:anticipated_date:")
  121 +// private String startKpiKey;
121 122  
122 123 @Value("${spring.cache.custom.global-prefix}:kpi:await_job:anticipated_date:")
123 124 private String awaitJobAfterStartKpiKey;
... ... @@ -125,17 +126,24 @@ public class CommonService {
125 126 @Value("${spring.cache.custom.global-prefix}:kpi:transpost_after:anticipated_date:")
126 127 private String transPostDate;
127 128 //员工旧岗位变动日期
128   - @Value("${spring.cache.custom.global-prefix}:kpi:staff:post:change:date:")
129   - private String staffPostChangeDate;
  129 + @Value("${spring.cache.custom.global-prefix}:kpi:staff:old_post_change_date:")
  130 + private String staffOldPostChangeDate;
130 131 //员工新岗位变动日期
131   - @Value("${spring.cache.custom.global-prefix}:kpi:staff_new_post:change_date:")
  132 + @Value("${spring.cache.custom.global-prefix}:kpi:staff:new_post_change_date:")
132 133 private String staffNewPostChangeDate;
  134 + //员工新岗位变动日期
  135 + @Value("${spring.cache.custom.global-prefix}:kpi:staff_non_demotion_new_post:change_date:")
  136 + private String staffNonDemotionNewPostChangeDate;
133 137 //员工调岗旧岗位开始绩效考核日期
134 138 @Value("${spring.cache.custom.global-prefix}:kpi:staff_old_post:start_kpi_date:")
135 139 private String staffOldPostChangeStartKpiDate;
136   - //员工调岗新岗位开始绩效考核日期
  140 + //员工调岗新岗位新门店开始绩效考核日期
  141 + // A门店销售主管 调岗到 B门店销售顾问 再调岗到A门店销售顾问,A门店销售顾问依然不参与绩效考核
137 142 @Value("${spring.cache.custom.global-prefix}:kpi:staff_new_post:start_kpi_date:")
138 143 private String staffNewPostChangeStartKpiDate;
  144 +// //员工调岗新岗位开始绩效考核日期
  145 +// @Value("${spring.cache.custom.global-prefix}:kpi:staff_only_new_post:start_kpi_date:")
  146 +// private String staffNewPostChangeStartKpiDate;
139 147  
140 148 /**
141 149 * 检查阶梯
... ... @@ -863,40 +871,40 @@ public class CommonService {
863 871 return salaryClosure.getClosure();
864 872 }
865 873  
866   - /**
867   - * 记录员工调岗日期
868   - *
869   - * @param userId 员工id
870   - * @param localDate 调岗日期
871   - */
872   - public void recordTranspostAfterDate(Long userId,LocalDate localDate) {
873   - BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(getTransPostDateKey(userId));
874   - strOps.set(localDate.toString(), 30, TimeUnit.DAYS);
875   - }
  874 +// /**
  875 +// * 记录员工调岗日期
  876 +// *
  877 +// * @param userId 员工id
  878 +// * @param localDate 调岗日期
  879 +// */
  880 +// public void recordTranspostAfterDate(Long userId,LocalDate localDate) {
  881 +// BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(getTransPostDateKey(userId));
  882 +// strOps.set(localDate.toString(), 30, TimeUnit.DAYS);
  883 +// }
876 884  
877 885 /**
878 886 * 获取员工的调岗日期
879 887 *
880 888 * @param userId 员工id
881 889 */
882   - public LocalDate getTransPostDate(Long userId) {
883   - String key = getTransPostDateKey(userId);
884   - if (! stringRedisTemplate.hasKey(key)) {
885   - return null;
886   - }
887   - BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(key);
888   - return LocalDate.parse(strOps.get());
889   - }
  890 +// public LocalDate getTransPostDate(Long userId) {
  891 +// String key = getTransPostDateKey(userId);
  892 +// if (! stringRedisTemplate.hasKey(key)) {
  893 +// return null;
  894 +// }
  895 +// BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(key);
  896 +// return LocalDate.parse(strOps.get());
  897 +// }
890 898  
891   - private String getTransPostDateKey(Long userId){
892   - return String.join(":", transPostDate,userId+"");
893   - }
  899 +// private String getTransPostDateKey(Long userId){
  900 +// return String.join(":", transPostDate,userId+"");
  901 +// }
894 902  
895 903 /**
896 904 * 获取员工旧岗位的调岗日期
897 905 */
898   - public LocalDate getOldPostChangeDate(Long userId, Long postId, Long shopId) {
899   - String key = getStaffPostChangeDateKey(userId, postId, shopId);
  906 + public LocalDate getOldPostChangeDate(Long userId, Long postId) {
  907 + String key = String.join(":", staffOldPostChangeDate, userId+"", postId+"");
900 908 if (! stringRedisTemplate.hasKey(key)) {
901 909 return null;
902 910 }
... ... @@ -907,20 +915,43 @@ public class CommonService {
907 915 /**
908 916 * 记录员工旧岗位调岗日期
909 917 */
910   - public void recordPostChangeDate(Long userId, Long postId, LocalDate localDate, Long shopId) {
911   - BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(getStaffPostChangeDateKey(userId, postId, shopId));
  918 + public void recordOldPostChangeDate(Long userId, Long postId, LocalDate localDate) {
  919 + String staffOldPostChangeKey = String.join(":", staffOldPostChangeDate, userId+"", postId+"");
  920 + BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(staffOldPostChangeKey);
912 921 strOps.set(localDate.toString(), 90, TimeUnit.DAYS);
913 922 }
914 923  
915   - private String getStaffPostChangeDateKey(Long userId, Long postId, Long shopId){
916   - return String.join(":", staffPostChangeDate, userId+"", postId+"", shopId+"");
  924 +
  925 +// private String getStaffPostChangeDateKey(Long userId, Long postId, Long shopId){
  926 +// return String.join(":", staffOldPostChangeDate, userId+"", postId+"", shopId+"");
  927 +// }
  928 +
  929 + /**
  930 + * 记录员工非降级旧岗位调岗日期
  931 + */
  932 + public void recordNonDemotionNewPostChangeDate(Long userId, Long postId, LocalDate localDate) {
  933 + String newPostChangeKey = String.join(":", staffNonDemotionNewPostChangeDate, userId+"", postId+"");
  934 + BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(newPostChangeKey);
  935 + strOps.set(localDate.toString(), 90, TimeUnit.DAYS);
  936 + }
  937 +
  938 + /**
  939 + * 获取员工非降级旧岗位调岗日期
  940 + */
  941 + private LocalDate getStaffNonDemotionNewPostChangeDate(Long userId, Long postId){
  942 + String newPostChangeKey = String.join(":", staffNonDemotionNewPostChangeDate, userId+"", postId+"");
  943 + if (! stringRedisTemplate.hasKey(newPostChangeKey)) {
  944 + return null;
  945 + }
  946 + BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(newPostChangeKey);
  947 + return LocalDate.parse(strOps.get());
917 948 }
918 949  
919 950 /**
920 951 * 记录员工非降级旧岗位调岗日期
921 952 */
922   - public void recordNonDemotionNewPostChangeDate(Long userId, Long postId, LocalDate localDate, Long shopId) {
923   - String newPostChangeKey = String.join(":", staffNewPostChangeDate, userId+"", postId+"", shopId+"");
  953 + public void recordNewPostChangeDate(Long userId, Long postId, LocalDate localDate) {
  954 + String newPostChangeKey = String.join(":", staffNewPostChangeDate, userId+"", postId+"");
924 955 BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(newPostChangeKey);
925 956 strOps.set(localDate.toString(), 90, TimeUnit.DAYS);
926 957 }
... ... @@ -928,8 +959,8 @@ public class CommonService {
928 959 /**
929 960 * 获取员工非降级旧岗位调岗日期
930 961 */
931   - private LocalDate getStaffNonDemotionNewPostChangeDate(Long userId, Long postId, Long shopId){
932   - String newPostChangeKey = String.join(":", staffNewPostChangeDate, userId+"", postId+"", shopId+"");
  962 + public LocalDate getNewPostChangeDate(Long userId, Long postId){
  963 + String newPostChangeKey = String.join(":", staffNewPostChangeDate, userId+"", postId+"");
933 964 if (! stringRedisTemplate.hasKey(newPostChangeKey)) {
934 965 return null;
935 966 }
... ... @@ -962,8 +993,8 @@ public class CommonService {
962 993 /**
963 994 * 记录员工新岗位调岗日期
964 995 */
965   - public void recordNewPostStartKpiDate(Long userId, Long postId, LocalDate localDate, Long shopId) {
966   - String userPostStartKpiDay = String.join(":", staffNewPostChangeStartKpiDate, userId+"", postId+"", shopId+"");
  996 + public void recordNewPostStartKpiDate(Long userId, Long postId, LocalDate localDate) {
  997 + String userPostStartKpiDay = String.join(":", staffNewPostChangeStartKpiDate, userId+"", postId+"");
967 998 BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(userPostStartKpiDay);
968 999 strOps.set(localDate.toString(), 90, TimeUnit.DAYS);
969 1000 }
... ... @@ -971,54 +1002,75 @@ public class CommonService {
971 1002 /**
972 1003 * 记录员工新岗位调岗日期
973 1004 */
974   - public LocalDate getNewPostStartKpiDate(Long userId, Long postId, Long shopId) {
975   - String userPostStartKpiDay = String.join(":", staffNewPostChangeStartKpiDate, userId+"", postId+"", shopId+"");
  1005 + public LocalDate getNewPostStartKpiDate(Long userId, Long postId) {
  1006 + String userPostStartKpiDay = String.join(":", staffNewPostChangeStartKpiDate, userId+"", postId+"");
976 1007 if (! stringRedisTemplate.hasKey(userPostStartKpiDay)) {
977 1008 return null;
978 1009 }
979 1010 BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(userPostStartKpiDay);
980 1011 return LocalDate.parse(strOps.get());
981 1012 }
  1013 +//
  1014 +// /**
  1015 +// * 记录员工新岗位调岗日期
  1016 +// */
  1017 +// public void recordNewPostStartKpiDate(Long userId, Long postId, LocalDate localDate) {
  1018 +// String userPostStartKpiDay = String.join(":", staffNewPostChangeStartKpiDate, userId+"", postId+"");
  1019 +// BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(userPostStartKpiDay);
  1020 +// strOps.set(localDate.toString(), 90, TimeUnit.DAYS);
  1021 +// }
  1022 +//
  1023 +// /**
  1024 +// * 记录员工新岗位调岗日期
  1025 +// */
  1026 +// public LocalDate getNewPostStartKpiDate(Long userId, Long postId) {
  1027 +// String userPostStartKpiDay = String.join(":", staffNewPostChangeStartKpiDate, userId+"", postId+"");
  1028 +// if (! stringRedisTemplate.hasKey(userPostStartKpiDay)) {
  1029 +// return null;
  1030 +// }
  1031 +// BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(userPostStartKpiDay);
  1032 +// return LocalDate.parse(strOps.get());
  1033 +// }
982 1034  
983 1035 /**
984 1036 * 记录开始计算绩效时间
985 1037 *
986 1038 * @param userId
987 1039 */
988   - public LocalDate calcStartKpiDate(Long userId) {
989   - BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(getStartKpiKey(userId));
990   - LocalDate currentDate = LocalDate.now();
991   - LocalDate startKpiDate = PublicUtil.getKpiDateOfTransferPostStaff(currentDate);
992   - long days = currentDate.until(startKpiDate, ChronoUnit.DAYS);
993   - //若定时器执行之前key失效,那么不能正确赋值开始计算考核时间,多加一天
994   - days = days + 1;
995   - strOps.set(startKpiDate.toString(), days, TimeUnit.DAYS);
996   - return startKpiDate;
997   - }
  1040 +// public LocalDate calcStartKpiDate(Long userId) {
  1041 +// BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(getStartKpiKey(userId));
  1042 +// LocalDate currentDate = LocalDate.now();
  1043 +// LocalDate startKpiDate = PublicUtil.getKpiDateOfTransferPostStaff(currentDate);
  1044 +// long days = currentDate.until(startKpiDate, ChronoUnit.DAYS);
  1045 +// //若定时器执行之前key失效,那么不能正确赋值开始计算考核时间,多加一天
  1046 +// days = days + 1;
  1047 +// strOps.set(startKpiDate.toString(), days, TimeUnit.DAYS);
  1048 +// return startKpiDate;
  1049 +// }
998 1050  
999 1051 /**
1000 1052 * 获取开始计算绩效时间
1001 1053 *
1002 1054 * @param userId
1003 1055 */
1004   - public LocalDate getStartKpiDate(Long userId) {
1005   - String key = getStartKpiKey(userId);
1006   - if (! stringRedisTemplate.hasKey(key)) {
1007   - return null;
1008   - }
1009   - BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(key);
1010   - LocalDate startKpiDate = LocalDate.parse(strOps.get());
1011   - LocalDate currentDate = LocalDate.now();
1012   - //当前时间在开始计算绩效时间 之后,已经开始计算绩效
1013   - if (currentDate.isAfter(startKpiDate)) {
1014   - return null;
1015   - }
1016   - return startKpiDate;
1017   - }
  1056 +// public LocalDate getStartKpiDate(Long userId) {
  1057 +// String key = getStartKpiKey(userId);
  1058 +// if (! stringRedisTemplate.hasKey(key)) {
  1059 +// return null;
  1060 +// }
  1061 +// BoundValueOperations<String, String> strOps = stringRedisTemplate.boundValueOps(key);
  1062 +// LocalDate startKpiDate = LocalDate.parse(strOps.get());
  1063 +// LocalDate currentDate = LocalDate.now();
  1064 +// //当前时间在开始计算绩效时间 之后,已经开始计算绩效
  1065 +// if (currentDate.isAfter(startKpiDate)) {
  1066 +// return null;
  1067 +// }
  1068 +// return startKpiDate;
  1069 +// }
1018 1070  
1019   - private String getStartKpiKey(Long userId){
1020   - return String.join(":",startKpiKey,userId+"");
1021   - }
  1071 +// private String getStartKpiKey(Long userId){
  1072 +// return String.join(":",startKpiKey,userId+"");
  1073 +// }
1022 1074  
1023 1075 /**
1024 1076 * 记录待岗后开始计算绩效时间
... ... @@ -1128,6 +1180,10 @@ public class CommonService {
1128 1180 if (PublicUtil.isNotEmpty(fundShop)) {
1129 1181 return fundShop;
1130 1182 }
  1183 + fundShop = filterShop(staffShops, StaffShopTypeEnum.LEAVE_SHOP);
  1184 + if (PublicUtil.isNotEmpty(fundShop)) {
  1185 + return fundShop;
  1186 + }
1131 1187 fundShop = filterShop(staffShops, StaffShopTypeEnum.ENTRY_SHOP);
1132 1188 if (PublicUtil.isNotEmpty(fundShop)) {
1133 1189 return fundShop;
... ... @@ -1138,56 +1194,32 @@ public class CommonService {
1138 1194 /**
1139 1195 * 判断是否纳入绩效考核
1140 1196 * 当月申请参与绩效考核 保护期标签取消
1141   - * 1. 试用期不计算绩效
1142   - * 2. 转正时间15号之后
1143   - * 3. 转正两个月保护期
1144   - * 4. 15号以后调岗不计算绩效
1145   - * 5. 15号之前调岗 原岗位不计算绩效 新岗位计算绩效
1146   - * 6. 绩效组变动不足完整2个月 绩效开始时间为获得岗位的两个月后
1147   - * 7. 主动申请不考核绩效
1148   - * 8. 待岗结束两个月期间
1149   - * 9. 15号以前离职(正式员工)不计入绩效考核
1150   - * 10. 请假天数 大于 配置不纳入绩效考核
  1197 + * 试用期不计算绩效
  1198 + * 转正时间15号之后
  1199 + * 转正两个月保护期
  1200 + * 调岗保护期
  1201 + * 15号以后调岗不计算绩效
  1202 + * 15号之前调岗 原岗位不计算绩效 新岗位计算绩效
  1203 + * 待岗结束两个月期间
  1204 + * 15号以前离职(正式员工)不计入绩效考核
  1205 + * 请假天数 大于 配置不纳入绩效考核
  1206 + * 主动申请不考核绩效
1151 1207 */
1152 1208 public IgnoreCauseDTO findIgnoreCauseDTO(PerformanceStaffDTO staff, IgnoreCauseReqDTO reqDTO){
1153 1209 IgnoreCauseDTO ignoreCauseDTO = new IgnoreCauseDTO();
1154 1210 final Long userId = staff.getId();
1155 1211 final LocalDate calcDate = reqDTO.getCurrentTime();
  1212 + final YearMonth calcMonthly = YearMonth.from(reqDTO.getCurrentTime());
1156 1213 //用原来员工状态(离职了就是离职前的状态,未离职就是当前自身状态)
1157 1214 final Integer originStaffStatus = staff.getOriginStaffStatus();
1158 1215  
1159   - /**
1160   - * 离职配置对比,放最后,优先级最高,可覆盖前面的不考核情况
1161   - * 仅 覆盖那种 '正式员工离职' 的,因为试用期员工本来就不考核绩效,没必要进行覆盖
1162   - */
1163   - LeaveStaffKpiSalaryConfigDTO config = reqDTO.getConfig();
1164   - if (Objects.nonNull(config)
1165   - && StaffStatusEnum.REGULAR.getValue().equals(originStaffStatus)
1166   - && Objects.nonNull(staff.getStaffStatus())
1167   - && Objects.nonNull(staff.getLeaveDate())
1168   - && staff.getStaffStatus() == 9
1169   - && reqDTO.getCurrentTime().compareTo(staff.getLeaveDate()) >= 0){
1170   - if (staff.getLeaveDate().compareTo(config.getKpiRankThresholdLocalDate()) < 0){
1171   - //离职离得早-不考核绩效-因为会拉低整个绩效组的考核情况
1172   - ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.LEAVE_DATE_BEFORE_15);
1173   - //随便设置一个时间,占个位,怕那个地方取他报错,反正他也离职了,下个月不会有他的数据了
1174   - ignoreCauseDTO.setStartKpiDate(reqDTO.getCurrentTime().with(TemporalAdjusters.lastDayOfMonth()).plusDays(1));
1175   - ignoreCauseDTO.setIgnoreCauseDesc(String.join("",config.getKpiRankThresholdLocalDate().getDayOfMonth()+"","号以前离职不计入绩效考核"));
1176   - ignoreCauseDTO.setIgnoreConfig(config.getKpiRankThresholdDay().toString());
1177   - }
1178   - }
1179   -
1180   - //当月申请参与绩效考核 保护期标签取消
1181   - Boolean curMonthlyApplyStartKpi = this.curMonthlyApplyStartKpi(userId, YearMonth.from(calcDate));
1182   - if (Boolean.TRUE.equals(curMonthlyApplyStartKpi)) {
1183   - return ignoreCauseDTO;
1184   - }
1185   -
1186 1216 //试用期不计算绩效 绩效开始时间为试用期转正的两个月后
1187 1217 if (StaffStatusEnum.PROBATION.getValue().equals(originStaffStatus)) {
1188   - LocalDate startKpiDate = PublicUtil.getKpiDateOfProbationStaff(PublicUtil.isNotEmpty(staff.getEntryDate()) ? staff.getEntryDate() : LocalDate.now());
  1218 + final LocalDate entryDate = PublicUtil.isNotEmpty(staff.getEntryDate()) ? staff.getEntryDate() : LocalDate.now();
  1219 + LocalDate startKpiDate = PublicUtil.getKpiDateOfProbationStaff(entryDate);
1189 1220 ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.PROBATION);
1190 1221 ignoreCauseDTO.setStartKpiDate(startKpiDate);
  1222 + ignoreCauseDTO.setEventTime(entryDate);
1191 1223 }
1192 1224  
1193 1225 //转正是否计算绩效判断
... ... @@ -1202,99 +1234,95 @@ public class CommonService {
1202 1234 //当月太晚转正不纳入绩效考核(15号之后,不含15号转正,不纳入绩效考核)(不需要参与人员质量评测。转正保护期需要参与人员质量评测)
1203 1235 if (Boolean.TRUE.equals(regularMonthlyIgnoreKpi) && Boolean.TRUE.equals(curMonthRegular)) {
1204 1236 LocalDate newStartKpiDate = regularDate.plusMonths(1).with(TemporalAdjusters.firstDayOfMonth());
1205   - if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), newStartKpiDate, reqDTO.getCurrentTime())) {
  1237 + if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), newStartKpiDate, calcDate)) {
1206 1238 String regularDayStr = reqDTO.getRegularOneDicValue().stripTrailingZeros().toPlainString();
1207 1239 ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.POSITIVE_AFTER_15);
1208 1240 ignoreCauseDTO.setStartKpiDate(newStartKpiDate);
1209 1241 ignoreCauseDTO.setIgnoreCauseDesc(String.join("",regularDayStr+"","号以后转正不计算绩效"));
1210 1242 ignoreCauseDTO.setIgnoreConfig(regularDayStr);
  1243 + ignoreCauseDTO.setEventTime(regularDate);
1211 1244 }
1212 1245 //再判断 转正保护期
1213 1246 } else {
1214   - Integer regularProtectionMonth = kpiDictBizService.getProtectionMonth(staff.getPostId(), staff.getShopId(),reqDTO.getRegularProtectionMultiMap());
  1247 + Integer regularProtectionMonth = kpiDictBizService.getProtectionMonth(staff.getPostId(), staff.getShopId(), reqDTO.getRegularProtectionMultiMap());
1215 1248 if (Objects.nonNull(regularProtectionMonth) && regularProtectionMonth > 0){
1216 1249 //有设定保护期,比如销售需要各种培训才能上岗需要保护加持 (当月转正不纳入绩效考核,保护期加一个月)
1217 1250 LocalDate newStartKpiDate = this.getNewStartKpiDate(regularDate, regularMonthlyIgnoreKpi, regularProtectionMonth);
1218   - if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), newStartKpiDate, reqDTO.getCurrentTime())) {
  1251 + if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), newStartKpiDate, calcDate)) {
1219 1252 ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TURN_POSITIVE_AFTER);
1220 1253 ignoreCauseDTO.setStartKpiDate(newStartKpiDate);
1221 1254 ignoreCauseDTO.setIgnoreConfig(regularProtectionMonth.toString());
  1255 + ignoreCauseDTO.setEventTime(regularDate);
1222 1256 }
1223 1257 }
1224 1258 }
1225 1259 }
1226 1260  
1227   - //15号以后调岗不计算绩效
1228   -// LocalDate transPostDate = getTransPostDate(userId);
1229   -// if (PublicUtil.isNotEmpty(transPostDate)) {
1230   -// //当月调岗时间分界点
1231   -// LocalDate transpostLocalDate = kpiDictBizService.getTranspostLocalDate(reqDTO.getAfterTransPostIgnoreKpi(), transPostDate);
1232   -// Boolean afterDateAfter = transPostDate.isAfter(transpostLocalDate);
1233   -// LocalDate newStartKpiDate = getNewStartKpiDate(transPostDate, afterDateAfter, 0);
1234   -// if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), newStartKpiDate, reqDTO.getCurrentTime())) {
1235   -// ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TRANSPOST_AFTER_15);
1236   -// ignoreCauseDTO.setStartKpiDate(newStartKpiDate);
1237   -// ignoreCauseDTO.setIgnoreCauseDesc(String.join("",transpostLocalDate.getDayOfMonth()+"","号以后调岗不计算绩效"));
1238   -// ignoreCauseDTO.setIgnoreConfig(reqDTO.getAfterTransPostIgnoreKpi().stripTrailingZeros().toPlainString());
1239   -// }
1240   -// }
1241   -
1242 1261 //15号之前调岗 原岗位不计算绩效 新岗位计算绩效
1243   - LocalDate changePostDate = this.getOldPostChangeDate(userId, staff.getPostId(), staff.getShopId());
1244   - if (PublicUtil.isNotEmpty(changePostDate)) {
1245   - LocalDate beforeTransferIgnoreKpiDate = kpiDictBizService.getTranspostLocalDate(reqDTO.getBeforeTransPostIgnoreKpi(), changePostDate);
1246   - if (changePostDate.isBefore(beforeTransferIgnoreKpiDate)) {
  1262 + LocalDate oldPostChangeDate = this.getOldPostChangeDate(userId, staff.getPostId());
  1263 + //计算日期大于调岗日期,3月12号调岗,3月10号还是参与考评考核
  1264 + if (PublicUtil.isNotEmpty(oldPostChangeDate) && calcDate.compareTo(oldPostChangeDate) >= 0 && YearMonth.from(oldPostChangeDate).compareTo(calcMonthly) == 0) {
  1265 + //调岗日期在当月X(不含)之前,旧岗位当月不参与绩效考核
  1266 + if (reqDTO.getBeforeTransPostIgnoreKpi().intValue() > oldPostChangeDate.getDayOfMonth()) {
1247 1267 //这个岗位开始计算绩效时间,下个月1号
1248   - LocalDate newStartKpiDate = YearMonth.from(changePostDate).plusMonths(1).atDay(1);
1249   - //判断配置日期
  1268 + LocalDate newStartKpiDate = YearMonth.from(oldPostChangeDate).plusMonths(1).atDay(1);
1250 1269 ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TRANSPOST_BEFORE_15);
1251 1270 ignoreCauseDTO.setStartKpiDate(newStartKpiDate);
1252   - ignoreCauseDTO.setIgnoreCauseDesc(String.join("",beforeTransferIgnoreKpiDate.getDayOfMonth()+"","号之前调岗不计算绩效"));
  1271 + ignoreCauseDTO.setIgnoreCauseDesc(String.join("",reqDTO.getBeforeTransPostIgnoreKpi().intValue()+"","号之前调岗不计算绩效"));
1253 1272 ignoreCauseDTO.setIgnoreConfig(reqDTO.getBeforeTransPostIgnoreKpi().stripTrailingZeros().toPlainString());
  1273 + ignoreCauseDTO.setEventTime(oldPostChangeDate);
1254 1274 }
1255 1275 }
1256 1276  
1257 1277 //15号之前调岗(不包含) 新岗位当月参与绩效考核,旧岗位当月不参与绩效考核
1258   - LocalDate oldPostStartKpiDate = this.getOldPostStartKpiDate(userId, staff.getPostId(), staff.getShopId());
1259   - if (PublicUtil.isNotEmpty(oldPostStartKpiDate) && oldPostStartKpiDate.compareTo(calcDate) > 0) {
1260   - ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TRANSPOST_BEFORE_15);
1261   - ignoreCauseDTO.setStartKpiDate(oldPostStartKpiDate);
1262   - ignoreCauseDTO.setIgnoreCauseDesc(String.join("",reqDTO.getBeforeTransPostIgnoreKpi().intValue()+"","号之前调岗不计算绩效"));
1263   - ignoreCauseDTO.setIgnoreConfig(reqDTO.getBeforeTransPostIgnoreKpi().stripTrailingZeros().toPlainString());
1264   - }
  1278 +// LocalDate oldPostStartKpiDate = this.getOldPostStartKpiDate(userId, staff.getPostId(), staff.getShopId());
  1279 +// if (PublicUtil.isNotEmpty(oldPostStartKpiDate) && oldPostStartKpiDate.compareTo(calcDate) > 0) {
  1280 +// ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TRANSPOST_BEFORE_15);
  1281 +// ignoreCauseDTO.setStartKpiDate(oldPostStartKpiDate);
  1282 +// ignoreCauseDTO.setIgnoreCauseDesc(String.join("",reqDTO.getBeforeTransPostIgnoreKpi().intValue()+"","号之前调岗不计算绩效"));
  1283 +// ignoreCauseDTO.setIgnoreConfig(reqDTO.getBeforeTransPostIgnoreKpi().stripTrailingZeros().toPlainString());
  1284 +// ignoreCauseDTO.setEventTime(changePostDate);
  1285 +// }
1265 1286  
1266 1287 //调岗保护期(15号之后调岗 优先)(非降级)
1267   - LocalDate newPostChangeDate = this.getStaffNonDemotionNewPostChangeDate(userId, staff.getPostId(), staff.getShopId());
1268   - final LocalDate newPostStartKpiDate = this.getNewPostStartKpiDate(userId, staff.getPostId(), staff.getShopId());
  1288 + LocalDate nonDemotionNewPostChangeDate = this.getStaffNonDemotionNewPostChangeDate(userId, staff.getPostId());
  1289 + final LocalDate newPostStartKpiDate = this.getNewPostStartKpiDate(userId, staff.getPostId());
1269 1290 final Integer transPostProtectionMonth = kpiDictBizService.getProtectionMonth(staff.getPostId(), staff.getShopId(), reqDTO.getTransPostProtectionMultiMap());
1270   - if (PublicUtil.isNotEmpty(newPostChangeDate) && PublicUtil.isNotEmpty(transPostProtectionMonth) && transPostProtectionMonth > 0 ){
  1291 + if (PublicUtil.isNotEmpty(nonDemotionNewPostChangeDate) && PublicUtil.isNotEmpty(transPostProtectionMonth) && transPostProtectionMonth > 0 ){
1271 1292 //当月调岗不纳入绩效考核,保护期加一个月
1272 1293 Boolean addOneMonthTransPostProtection = PublicUtil.isNotEmpty(newPostStartKpiDate);
1273   - LocalDate newStartKpiDate = this.getNewStartKpiDate(newPostChangeDate, addOneMonthTransPostProtection, transPostProtectionMonth);
1274   - if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), newStartKpiDate, reqDTO.getCurrentTime())) {
  1294 + LocalDate newStartKpiDate = this.getNewStartKpiDate(nonDemotionNewPostChangeDate, addOneMonthTransPostProtection, transPostProtectionMonth);
  1295 + if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), newStartKpiDate, calcDate)) {
1275 1296 ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TURN_POSITIVE_POSITION);
1276 1297 ignoreCauseDTO.setStartKpiDate(newStartKpiDate);
1277 1298 ignoreCauseDTO.setIgnoreConfig(transPostProtectionMonth.toString());
  1299 + ignoreCauseDTO.setEventTime(nonDemotionNewPostChangeDate);
1278 1300 }
1279 1301 }
1280 1302  
1281   - //todo 新版本,启用一段时间注释之前逻辑
1282 1303 //15号之后调岗(包含) 新岗位次月参与绩效考核,旧岗位当月参与绩效考核
1283   - if (PublicUtil.isNotEmpty(newPostStartKpiDate) && newPostStartKpiDate.compareTo(calcDate) > 0) {
1284   - ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TRANSPOST_AFTER_15);
1285   - ignoreCauseDTO.setStartKpiDate(newPostStartKpiDate);
1286   - ignoreCauseDTO.setIgnoreCauseDesc(String.join("",reqDTO.getAfterTransPostIgnoreKpi().intValue()+"","号以后调岗不计算绩效"));
1287   - ignoreCauseDTO.setIgnoreConfig(reqDTO.getAfterTransPostIgnoreKpi().stripTrailingZeros().toPlainString());
1288   - }
1289   -
1290   - //绩效组变动不足完整2个月 绩效开始时间为获得岗位的两个月后
1291   - LocalDate postChangeStartKpiDate = this.getStartKpiDate(userId);
1292   - if (PublicUtil.isNotEmpty(postChangeStartKpiDate)) {
1293   - if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), postChangeStartKpiDate, reqDTO.getCurrentTime())) {
1294   - ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TRANSFER_NEW_POSITION_AFTER);
1295   - ignoreCauseDTO.setStartKpiDate(postChangeStartKpiDate);
  1304 + LocalDate newPostChangeDate = this.getNewPostChangeDate(userId, staff.getPostId());
  1305 + //计算日期大于调岗日期,3月12号调岗,3月10号还是参与考评考核
  1306 + if (PublicUtil.isNotEmpty(newPostChangeDate) && calcDate.compareTo(newPostChangeDate) >= 0 && YearMonth.from(newPostChangeDate).compareTo(calcMonthly) == 0) {
  1307 + //调岗日期在当月X(含)之后,新岗位次月参与绩效考核
  1308 + if (newPostChangeDate.getDayOfMonth() >= reqDTO.getAfterTransPostIgnoreKpi().intValue()) {
  1309 + //这个岗位开始计算绩效时间,下个月1号
  1310 + LocalDate newStartKpiDate = YearMonth.from(newPostChangeDate).plusMonths(1).atDay(1);
  1311 + ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TRANSPOST_AFTER_15);
  1312 + ignoreCauseDTO.setStartKpiDate(newStartKpiDate);
  1313 + ignoreCauseDTO.setIgnoreCauseDesc(String.join("",reqDTO.getAfterTransPostIgnoreKpi().intValue()+"","号以后调岗不计算绩效"));
  1314 + ignoreCauseDTO.setIgnoreConfig(reqDTO.getAfterTransPostIgnoreKpi().stripTrailingZeros().toPlainString());
  1315 + ignoreCauseDTO.setEventTime(newPostChangeDate);
1296 1316 }
1297 1317 }
  1318 +// final LocalDate newPostChangeDate = this.getOldPostChangeDate(userId, staff.getPostId(), staff.getShopId());
  1319 +// if (PublicUtil.isNotEmpty(newPostChangeDate) && calcDate.compareTo(newPostChangeDate) > 0) {
  1320 +// ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.TRANSPOST_AFTER_15);
  1321 +// ignoreCauseDTO.setStartKpiDate(newPostStartKpiDate);
  1322 +// ignoreCauseDTO.setIgnoreCauseDesc(String.join("",reqDTO.getAfterTransPostIgnoreKpi().intValue()+"","号以后调岗不计算绩效"));
  1323 +// ignoreCauseDTO.setIgnoreConfig(reqDTO.getAfterTransPostIgnoreKpi().stripTrailingZeros().toPlainString());
  1324 +// ignoreCauseDTO.setEventTime(newPostChangeDate);
  1325 +// }
1298 1326  
1299 1327 //主动申请不考核绩效 绩效开始时间为设置的申请开始绩效考核时间
1300 1328 if (CollectionUtils.isNotEmpty(reqDTO.getUserRuleMap())){
... ... @@ -1303,47 +1331,68 @@ public class CommonService {
1303 1331 if (PublicUtil.isNotEmpty(specialRule) && PublicUtil.isNotEmpty(specialRule.getEarliestStartingMonthly())) {
1304 1332 LocalDate newStartKpiDate = specialRule.getEarliestStartingMonthly();
1305 1333 //当前时间在开始考核时间之之前 审批通过后,前面月份的绩效不纳入后续计算
1306   - if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), newStartKpiDate, reqDTO.getCurrentTime())) {
  1334 + if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), newStartKpiDate, calcDate)) {
1307 1335 ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.APPLY_NO_ASSESSMENT);
1308 1336 ignoreCauseDTO.setStartKpiDate(newStartKpiDate);
1309 1337 }
1310 1338 }
1311 1339 }
1312 1340  
1313   - //待岗期间
1314   - if (PublicUtil.isNotEmpty(staff.getAwaitJob()) && staff.getAwaitJob()) {
1315   - ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.AWAIT_JOB_DURATION);
1316   - //@todo 人事系统待岗中人员没有待岗结束时间
1317   - ignoreCauseDTO.setStartKpiDate(null);
1318   - }
1319   -
1320   - //待岗结束两个月期间
1321   - LocalDate afterAwaitJobStartKpiDate = this.getAfterAwaitJobStartKpiDate(userId);
1322   - if (PublicUtil.isNotEmpty(afterAwaitJobStartKpiDate) ) {
1323   - if (this.checkNewStartKpiDateValid(ignoreCauseDTO.getStartKpiDate(), afterAwaitJobStartKpiDate, reqDTO.getCurrentTime())) {
1324   - ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.AWAIT_JOB_AFTER);
1325   - ignoreCauseDTO.setStartKpiDate(afterAwaitJobStartKpiDate);
1326   - }
1327   - }
  1341 + //@todo 人事系统待岗中人员没有待岗结束时间
1328 1342  
1329 1343 //请假天数 大于 配置不纳入绩效考核
1330 1344 if (PublicUtil.isEmpty(ignoreCauseDTO.getIgnoreCauseEnum())) {
1331 1345 BigDecimal leaveDays = staffLeaveSummaryService.getLeaveDays(userId, YearMonth.from(calcDate));
1332 1346 if (leaveDays.compareTo(reqDTO.getLeaveIgnoreKpiDays()) >= 0) {
1333 1347 ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.LEAVE_DAY_OVERLENGTH_IGNORE_KPI);
1334   - ignoreCauseDTO.setStartKpiDate(YearMonth.from(reqDTO.getCurrentTime()).plusMonths(1).atDay(1));
  1348 + ignoreCauseDTO.setStartKpiDate(YearMonth.from(calcDate).plusMonths(1).atDay(1));
1335 1349 ignoreCauseDTO.setIgnoreCauseDesc("请假超过" + reqDTO.getLeaveIgnoreKpiDays().intValue() + "天不计入绩效考核");
1336 1350 ignoreCauseDTO.setIgnoreConfig(reqDTO.getLeaveIgnoreKpiDays().stripTrailingZeros().toPlainString());
  1351 + ignoreCauseDTO.setEventTime(calcDate);
  1352 + }
  1353 + }
  1354 +
  1355 + /**
  1356 + * 离职配置对比,放最后,优先级最高,可覆盖前面的不考核情况
  1357 + * 仅 覆盖那种 '正式员工离职' 的,因为试用期员工本来就不考核绩效,没必要进行覆盖
  1358 + */
  1359 + //离职不考核: 离职前是转正员工,计算日期大于等于离职日期(3月26号离职,3月25号还是要计算)
  1360 + LeaveStaffKpiSalaryConfigDTO config = reqDTO.getConfig();
  1361 + if (PublicUtil.isNotEmpty(config)
  1362 + && StaffStatusEnum.REGULAR.getValue().equals(originStaffStatus)
  1363 + && PublicUtil.isNotEmpty(staff.getStaffStatus())
  1364 + && PublicUtil.isNotEmpty(staff.getLeaveDate())
  1365 + && staff.getStaffStatus() == 9
  1366 + && calcDate.compareTo(staff.getLeaveDate()) >= 0){
  1367 + //配置日期 大于 离职日期
  1368 + if (config.getKpiRankThresholdLocalDate().compareTo(staff.getLeaveDate()) > 0){
  1369 + //离职离得早-不考核绩效-因为会拉低整个绩效组的考核情况
  1370 + ignoreCauseDTO.setIgnoreCauseEnum(KpiIgnoreCauseEnum.LEAVE_DATE_BEFORE_15);
  1371 + //随便设置一个时间,占个位,怕那个地方取他报错,反正他也离职了,下个月不会有他的数据了
  1372 + ignoreCauseDTO.setStartKpiDate(calcDate.with(TemporalAdjusters.lastDayOfMonth()).plusDays(1));
  1373 + ignoreCauseDTO.setIgnoreCauseDesc(String.join("",config.getKpiRankThresholdLocalDate().getDayOfMonth()+"","号以前离职不计入绩效考核"));
  1374 + ignoreCauseDTO.setIgnoreConfig(config.getKpiRankThresholdDay().toString());
  1375 + ignoreCauseDTO.setEventTime(staff.getLeaveDate());
1337 1376 }
1338 1377 }
1339 1378  
  1379 + //当月申请参与绩效考核 保护期标签取消
  1380 + Optional<KpiStarSpecialRule> specialRuleOptional = this.curMonthlyApplyStartKpi(userId, YearMonth.from(calcDate));
  1381 + if (Boolean.TRUE.equals(specialRuleOptional.isPresent())) {
  1382 + KpiStarSpecialRule kpiStarSpecialRule = specialRuleOptional.get();
  1383 + final LocalDate applyKpiTime = DateUtil.date2LocalDate(kpiStarSpecialRule.getCreateTime());
  1384 + //申请绩效考核时间 大于 忽略绩效考核时间,以新复旧
  1385 + if (PublicUtil.isNotEmpty(ignoreCauseDTO.getEventTime()) && applyKpiTime.compareTo(ignoreCauseDTO.getEventTime()) > 0) {
  1386 + return new IgnoreCauseDTO();
  1387 + }
  1388 + }
1340 1389 return ignoreCauseDTO;
1341 1390 }
1342 1391  
1343 1392 /**
1344 1393 * 当月申请参与绩效考核
1345 1394 */
1346   - public Boolean curMonthlyApplyStartKpi(Long userId, YearMonth monthly) {
  1395 + public Optional<KpiStarSpecialRule> curMonthlyApplyStartKpi(Long userId, YearMonth monthly) {
1347 1396 List<KpiStarSpecialRuleStatusEnum> status = new ArrayList<KpiStarSpecialRuleStatusEnum>(){{
1348 1397 add(KpiStarSpecialRuleStatusEnum.EFFECTIVE);
1349 1398 add(KpiStarSpecialRuleStatusEnum.INEFFECTIVE);
... ... @@ -1353,15 +1402,18 @@ public class CommonService {
1353 1402 .eq(KpiStarSpecialRule::getUserId, userId)
1354 1403 .eq(KpiStarSpecialRule::getYn, Boolean.TRUE)
1355 1404 );
1356   - for (KpiStarSpecialRule kpiStarSpecialRule : specialRules) {
1357   - if (PublicUtil.isNotEmpty(kpiStarSpecialRule.getEarliestStartingMonthly()) &&
1358   - YearMonth.from(kpiStarSpecialRule.getEarliestStartingMonthly()).compareTo(monthly) == 0) {
1359   - log.info("员工当月已申请当月参与绩效考核,userId:{}, monthly:{},kpiStarSpecialRule:{}",
1360   - userId, monthly, JSON.toJSONString(kpiStarSpecialRule));
1361   - return Boolean.TRUE;
1362   - }
1363   - }
1364   - return Boolean.FALSE;
  1405 + Optional<KpiStarSpecialRule> specialRuleOptional = specialRules.stream()
  1406 + .filter(kpiStarSpecialRule -> {
  1407 + if (PublicUtil.isNotEmpty(kpiStarSpecialRule.getEarliestStartingMonthly()) &&
  1408 + YearMonth.from(kpiStarSpecialRule.getEarliestStartingMonthly()).compareTo(monthly) == 0) {
  1409 + log.info("员工当月已申请当月参与绩效考核,userId:{}, monthly:{},kpiStarSpecialRule:{}",
  1410 + userId, monthly, JSON.toJSONString(kpiStarSpecialRule));
  1411 + return Boolean.TRUE;
  1412 + }
  1413 + return Boolean.FALSE;
  1414 + })
  1415 + .max(Comparator.comparing(KpiStarSpecialRule::getCreateTime));
  1416 + return specialRuleOptional;
1365 1417 }
1366 1418  
1367 1419 public LocalDate getNewStartKpiDate(LocalDate regularDate, Boolean regularDateAfter, Integer protectionMonth) {
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/calculator/eval/reward/EvalRewardBaseCalculator.java
... ... @@ -592,7 +592,7 @@ public abstract class EvalRewardBaseCalculator implements Calculator&lt;EvalGroupUs
592 592 boolean isCap = Boolean.TRUE.equals(param.getCap());
593 593 BigDecimal proportion = param.getProportion();
594 594 TargetTypeEnum targetType = param.getTargetType();
595   - final BigDecimal userOriginValue = queryValue(userShop, param.getCodeType(), indicatorCode).orElse(BigDecimal.ZERO);
  595 + final BigDecimal userOriginValue = queryStageAccumulationValue(userShop, param.getCodeType(), indicatorCode).orElse(BigDecimal.ZERO);
596 596 BigDecimal reachValue = userOriginValue;
597 597 if (!TargetTypeEnum.NO.equals(targetType)) {
598 598 reachValue = calculateTargetValue(param.getTargetCalcType(), param.getTargetValue(), reachValue, param.getMinimumStandardValue());
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/calculator/eval/reward/EvalRewardProportionCalculator.java
... ... @@ -49,7 +49,7 @@ public class EvalRewardProportionCalculator extends EvalRewardBaseCalculator {
49 49  
50 50 @Override
51 51 public void calculateGroup(List<EvalGroupUserShop> userShops, EvalGroupRewardBO reward) {
52   - userShops = userShops.stream().filter(userShop -> Boolean.FALSE.equals(userShop.getIgnored())).collect(Collectors.toList());
  52 + userShops = userShops.stream().filter(userShop -> Boolean.TRUE.equals(userShop.getInclusion())).collect(Collectors.toList());
53 53 if (PublicUtil.isEmpty(userShops)) {
54 54 return;
55 55 }
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/calculator/eval/reward/EvalRewardRankCalculator.java
... ... @@ -44,7 +44,7 @@ public class EvalRewardRankCalculator extends EvalRewardBaseCalculator {
44 44  
45 45 @Override
46 46 public void calculateGroup(List<EvalGroupUserShop> userShops, EvalGroupRewardBO reward) {
47   - userShops = userShops.stream().filter(userShop -> Boolean.FALSE.equals(userShop.getIgnored())).collect(Collectors.toList());
  47 + userShops = userShops.stream().filter(userShop -> Boolean.TRUE.equals(userShop.getInclusion())).collect(Collectors.toList());
48 48 if (PublicUtil.isEmpty(userShops)) {
49 49 return;
50 50 }
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/calculator/salary/StarSalaryCalculator.java
... ... @@ -62,7 +62,7 @@ public class StarSalaryCalculator extends SalaryBaseCalculator {
62 62 //只能查询指定日期月份人员岗位纬度的最新星级
63 63 Optional<KpiPool> optionalKpiPool = kpiPoolCommonService.queryPool(param2);
64 64 if (! optionalKpiPool.isPresent()) {
65   - log.error("用户[{}]的绩效数据不存在", userId);
  65 +// log.error("用户[{}]的绩效数据不存在", userId);
66 66 return BigDecimal.ZERO;
67 67 }
68 68 KpiPool kpiPool = optionalKpiPool.get();
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/eval/EvalCalculateService.java
... ... @@ -9,7 +9,6 @@ import cn.fw.morax.common.utils.ThreadPoolUtil;
9 9 import cn.fw.morax.domain.bo.eval.*;
10 10 import cn.fw.morax.domain.bo.kpi.EvalGroupCalculableRankBO;
11 11 import cn.fw.morax.domain.db.eval.*;
12   -import cn.fw.morax.domain.dto.salary.SalaryExtraDTO;
13 12 import cn.fw.morax.domain.enums.*;
14 13 import cn.fw.morax.service.biz.CommonService;
15 14 import cn.fw.morax.service.biz.calculator.eval.kpi.EvalKpiBaseCalculator;
... ... @@ -40,7 +39,6 @@ import java.time.YearMonth;
40 39 import java.util.*;
41 40 import java.util.concurrent.*;
42 41 import java.util.concurrent.atomic.AtomicReference;
43   -import java.util.function.Consumer;
44 42 import java.util.stream.Collectors;
45 43  
46 44 /**
... ... @@ -164,23 +162,27 @@ public class EvalCalculateService {
164 162 final Long evalGroupRankId = bo.getEvalGroupRankId();
165 163 final LocalDate dataDate = bo.getLocalDate();
166 164 List<EvalGroup> evalGroups = evalGroupService.getAllUnclosedGroups(evalGroupRankId, dataDate);
  165 + //清除薪酬 奖惩数据
  166 + evalPoolCommonService.cleanOldSalaryExtraProject(evalGroups, dataDate);
167 167 Map<Long, List<EvalGroup>> stageEvalGroupMap = evalGroups.stream().collect(Collectors.groupingBy(EvalGroup::getEvalGroupRankStageId));
168 168 //计算考评得分
169 169 CompletableFuture<Void>[] futuresArr = evalGroups.stream().map(evalGroup -> CompletableFuture.runAsync(() -> {
170   - Long start = System.currentTimeMillis();
  170 + if (Boolean.FALSE.equals(this.checkEvalConfigValid(evalGroup, dataDate))){
  171 + return;
  172 + }
  173 + final EvalGroupRankConfigBO calcConfigBo = this.getEvalCalcConfig(evalGroup, dataDate);
  174 + final Long start = System.currentTimeMillis();
171 175 log.info(" 考评组计算:考评组进行计算:{}", evalGroup.getId());
172 176 TransactionStatus transactionStatus = platformTransactionManager.getTransaction(transactionDefinition);
173   - final Long evalGroupRankStageId = evalGroup.getEvalGroupRankStageId();
174   - final Long evalGroupId = evalGroup.getId();
175 177 try {
176   - EvalGroupCalcParamsBO calcDateParam = this.getCalcDate(evalGroupRankStageId, dataDate, EvalCalStageDimEnum.STAGE_STAGE);
177   - calculateEvalGroup(evalGroupId, calcDateParam, EvalScopeEnum.STAFF);
178   - calculateEvalGroup(evalGroupId, calcDateParam, EvalScopeEnum.SHOP);
  178 + EvalGroupCalcParamsBO calcDateParam = this.getCalcDate(calcConfigBo, dataDate, EvalCalStageDimEnum.STAGE_STAGE);
  179 + calculateEvalGroup(calcConfigBo, calcDateParam, EvalScopeEnum.STAFF);
  180 + calculateEvalGroup(calcConfigBo, calcDateParam, EvalScopeEnum.SHOP);
179 181 //多阶段才需要计算-阶段累计
180 182 if (calcDateParam.getMultiStage()) {
181   - EvalGroupCalcParamsBO calcDateParamM = this.getCalcDate(evalGroupRankStageId, dataDate, EvalCalStageDimEnum.STAGE_MONTH);
182   - calculateEvalGroup(evalGroupId, calcDateParamM, EvalScopeEnum.STAFF);
183   - calculateEvalGroup(evalGroupId, calcDateParamM, EvalScopeEnum.SHOP);
  183 + EvalGroupCalcParamsBO calcDateParamM = this.getCalcDate(calcConfigBo, dataDate, EvalCalStageDimEnum.STAGE_MONTH);
  184 + calculateEvalGroup(calcConfigBo, calcDateParamM, EvalScopeEnum.STAFF);
  185 + calculateEvalGroup(calcConfigBo, calcDateParamM, EvalScopeEnum.SHOP);
184 186 }
185 187 platformTransactionManager.commit(transactionStatus);
186 188 log.info(" 考评组计算:考评组计算完成:{},耗时:{} s", evalGroup.getId(), TimeUnit.MILLISECONDS.toSeconds(System.currentTimeMillis() - start));
... ... @@ -195,19 +197,24 @@ public class EvalCalculateService {
195 197 this.calcEvalRank(evalGroupRankId, dataDate);
196 198 //计算考评奖惩
197 199 CompletableFuture<List<EvalRewardPushSalaryBO>>[] futuresRewardArr = stageEvalGroupMap.entrySet().stream().map(stage -> CompletableFuture.supplyAsync(() -> {
198   - Long start = System.currentTimeMillis();
199   - log.info("考评奖惩计算:考评奖惩开始进行计算,考评排名组:{}", evalGroupRankId);
  200 + final Long evalGroupRankStageId = stage.getKey();
  201 + if (Boolean.FALSE.equals(this.checkEvalRewardConfigValid(evalGroupRankStageId, dataDate))){
  202 + return new ArrayList<>();
  203 + }
  204 + final EvalGroupRankConfigBO calcConfigBo = this.getEvalRewardCalcConfig(evalGroupRankStageId, dataDate);
  205 + final Long start = System.currentTimeMillis();
  206 + log.info("考评奖惩计算:考评奖惩开始进行计算,考评阶段:{}", evalGroupRankStageId);
200 207 List<EvalRewardPushSalaryBO> res = new ArrayList<>();
201 208 TransactionStatus transactionStatus = platformTransactionManager.getTransaction(transactionDefinition);
202 209 try {
203   - res = calculateEvalStageReward(evalGroupRankId, stage, dataDate);
  210 + res = calculateEvalStageReward(calcConfigBo, stage, dataDate);
204 211 platformTransactionManager.commit(transactionStatus);
205 212 } catch (Exception ex) {
206 213 platformTransactionManager.rollback(transactionStatus);
207 214 log.error("计算考评奖惩数据失败:{}", bo, ex);
208 215 success.set(Boolean.FALSE);
209 216 }
210   - log.info("考评奖惩计算:考评奖惩计算完成,考评排名组:{},耗时:{} s", evalGroupRankId, TimeUnit.MILLISECONDS.toSeconds(System.currentTimeMillis() - start));
  217 + log.info("考评奖惩计算:考评奖惩计算完成,考评阶段:{},耗时:{} s", evalGroupRankStageId, TimeUnit.MILLISECONDS.toSeconds(System.currentTimeMillis() - start));
211 218 return res;
212 219 }, threadPool)).<CompletableFuture<List<EvalRewardPushSalaryBO>>>toArray(CompletableFuture[]::new);
213 220 CompletableFuture.allOf(futuresRewardArr).join();
... ... @@ -216,14 +223,14 @@ public class EvalCalculateService {
216 223 overflowsList.add(str);
217 224 } else {
218 225 //计算排名、报表数据抽取
219   - //考评奖惩
  226 + //考评奖惩推送薪酬
220 227 this.cacheEvalRewardPushSalary(futuresRewardArr);
221 228 //考评门店角色奖惩
222 229 this.cacheEvalShopRoleRewardPushSalary(evalGroupRankId, dataDate);
223 230 //保存计算结果
224 231 this.cacheSaveCalcResult(evalCalcId, bo.getEvalGroupRankId(), dataDate, evalGroups);
225 232 evalCalcService.modifyStatus(evalCalcId, EvalCalcStatusEnum.SAVE_CALC_RESULT);
226   - //是否分配奖惩
  233 + //是否分配门店奖惩
227 234 this.cacheDistShopReward(evalCalcId, evalGroupRankId, dataDate);
228 235 }
229 236 } catch (Exception re) {
... ... @@ -249,6 +256,62 @@ public class EvalCalculateService {
249 256 stringRedisTemplate.opsForSet().add(evalCalculationVal.getCacheSaveCalcResult(), json);
250 257 }
251 258  
  259 + public Boolean checkEvalConfigValid(EvalGroup evalGroup, LocalDate calcDate) {
  260 + if (PublicUtil.isEmpty(evalGroup)) {
  261 + return Boolean.FALSE;
  262 + }
  263 + EvalGroupRankStage evalGroupRankStage = evalGroupRankStageService.getByIdAndSetTime(evalGroup.getEvalGroupRankStageId(), calcDate);
  264 + if (PublicUtil.isEmpty(evalGroupRankStage)) {
  265 + log.error("考评排名组阶段[{}]不存在,终止计算!", JSON.toJSONString(evalGroup));
  266 + return Boolean.FALSE;
  267 + }
  268 + EvalGroupRank evalGroupRank = evalGroupRankService.getById(evalGroup.getEvalGroupRankId());
  269 + if (PublicUtil.isEmpty(evalGroupRank)) {
  270 + log.error("考评组[{}]排名组不存在,终止计算!", evalGroup.getEvalGroupRankId());
  271 + return Boolean.FALSE;
  272 + }
  273 + return Boolean.TRUE;
  274 + }
  275 +
  276 + public EvalGroupRankConfigBO getEvalCalcConfig(EvalGroup evalGroup, LocalDate calcDate) {
  277 + EvalGroupRankConfigBO rankConfigBO = new EvalGroupRankConfigBO();
  278 + EvalGroupRank evalGroupRank = evalGroupRankService.getById(evalGroup.getEvalGroupRankId());
  279 + EvalGroupRankStage evalGroupRankStage = evalGroupRankStageService.getByIdAndSetTime(evalGroup.getEvalGroupRankStageId(), calcDate);
  280 +
  281 + rankConfigBO.setEvalGroupRank(evalGroupRank);
  282 + rankConfigBO.setEvalGroupRankStage(evalGroupRankStage);
  283 + rankConfigBO.setEvalGroup(evalGroup);
  284 + return rankConfigBO;
  285 + }
  286 +
  287 + public Boolean checkEvalRewardConfigValid(Long evalGroupRankStageId, LocalDate calcDate) {
  288 + if (PublicUtil.isEmpty(evalGroupRankStageId)) {
  289 + return Boolean.FALSE;
  290 + }
  291 + EvalGroupRankStage evalGroupRankStage = evalGroupRankStageService.getByIdAndSetTime(evalGroupRankStageId, calcDate);
  292 + if (PublicUtil.isEmpty(evalGroupRankStage)) {
  293 + log.error("考评排名组阶段[{}]不存在,终止计算!", JSON.toJSONString(evalGroupRankStageId));
  294 + return Boolean.FALSE;
  295 + }
  296 + EvalGroupRank evalGroupRank = evalGroupRankService.getById(evalGroupRankStage.getEvalGroupRankId());
  297 + if (PublicUtil.isEmpty(evalGroupRank)) {
  298 + log.error("考评组[{}]排名组不存在,终止计算!", evalGroupRankStage.getEvalGroupRankId());
  299 + return Boolean.FALSE;
  300 + }
  301 + return Boolean.TRUE;
  302 + }
  303 +
  304 + public EvalGroupRankConfigBO getEvalRewardCalcConfig(Long evalGroupRankStageId, LocalDate calcDate) {
  305 + EvalGroupRankConfigBO rankConfigBO = new EvalGroupRankConfigBO();
  306 + EvalGroupRankStage evalGroupRankStage = evalGroupRankStageService.getByIdAndSetTime(evalGroupRankStageId, calcDate);
  307 + EvalGroupRank evalGroupRank = evalGroupRankService.getById(evalGroupRankStage.getEvalGroupRankId());
  308 +
  309 + rankConfigBO.setEvalGroupRank(evalGroupRank);
  310 + rankConfigBO.setEvalGroupRankStage(evalGroupRankStage);
  311 + return rankConfigBO;
  312 + }
  313 +
  314 +
252 315 private void cacheEvalRewardPushSalary(CompletableFuture<List<EvalRewardPushSalaryBO>>[] futuresRewardArr) {
253 316 List<EvalRewardPushSalaryBO> evalRewardPushSalaryBOS = new ArrayList<>();
254 317 Arrays.stream(futuresRewardArr).forEach(future -> {
... ... @@ -296,17 +359,9 @@ public class EvalCalculateService {
296 359 * @param localDate
297 360 * @return
298 361 */
299   - public EvalGroupCalcParamsBO getCalcDate(Long evalGroupRankStageId, final LocalDate localDate,EvalCalStageDimEnum stageDimEnum) {
300   - EvalGroupRankStage evalGroupRankStage = evalGroupRankStageService.getByIdAndSetTime(evalGroupRankStageId, localDate);
301   - if (Objects.isNull(evalGroupRankStage)) {
302   - log.error("考评排名组阶段[{}]不存在,终止计算!", evalGroupRankStageId);
303   - return null;
304   - }
305   - EvalGroupRank evalGroupRank = evalGroupRankService.getById(evalGroupRankStage.getEvalGroupRankId());
306   - if (Objects.isNull(evalGroupRank)) {
307   - log.error("考评排名组[{}]不存在,终止计算!", evalGroupRankStage.getEvalGroupRankId());
308   - return null;
309   - }
  362 + public EvalGroupCalcParamsBO getCalcDate(EvalGroupRankConfigBO calcConfigBo, final LocalDate localDate,EvalCalStageDimEnum stageDimEnum) {
  363 + EvalGroupRankStage evalGroupRankStage = calcConfigBo.getEvalGroupRankStage();
  364 + EvalGroupRank evalGroupRank = calcConfigBo.getEvalGroupRank();
310 365 EvalGroupCalcParamsBO paramsBO = new EvalGroupCalcParamsBO();
311 366 LocalDate firstStageStartTime = evalGroupRankStageService.getRankStartTime(evalGroupRank.getId(), evalGroupRank.getPeriod(), localDate);
312 367 paramsBO.setCalcMonthBeginDate(firstStageStartTime);
... ... @@ -328,12 +383,11 @@ public class EvalCalculateService {
328 383 return paramsBO;
329 384 }
330 385  
331   - public void calculateEvalGroup(final Long evalGroupId, final EvalGroupCalcParamsBO calcDateParam, EvalScopeEnum scopeType) {
332   - if (Objects.isNull(calcDateParam)){
333   - log.error("参数不够,终止计算!");
334   - return;
335   - }
336   - List<EvalGroupUserShop> userShops = this.buildEvalGroupObj(evalGroupId, calcDateParam, scopeType);
  386 + public void calculateEvalGroup(EvalGroupRankConfigBO calcConfigBo, final EvalGroupCalcParamsBO calcDateParam, EvalScopeEnum scopeType) {
  387 + EvalGroup evalGroup = calcConfigBo.getEvalGroup();
  388 +
  389 + final Long evalGroupId = evalGroup.getId();
  390 + List<EvalGroupUserShop> userShops = this.buildEvalGroupObj(calcConfigBo, calcDateParam, scopeType);
337 391 if (PublicUtil.isEmpty(userShops)) {
338 392 log.error("考评组[{}]人员为空,终止计算!", evalGroupId);
339 393 return;
... ... @@ -354,28 +408,22 @@ public class EvalCalculateService {
354 408 }
355 409 }
356 410  
357   - public List<EvalRewardPushSalaryBO> calculateEvalStageReward(final Long evalGroupRankId,
  411 + public List<EvalRewardPushSalaryBO> calculateEvalStageReward(EvalGroupRankConfigBO calcConfigBo,
358 412 Map.Entry<Long, List<EvalGroup>> stageEvalGroupEntry,
359 413 LocalDate dataDate) {
360 414 final Long evalGroupRankStageId = stageEvalGroupEntry.getKey();
361 415 final List<EvalGroup> evalGroups = stageEvalGroupEntry.getValue();
362   - EvalGroupCalcParamsBO calcDateParam = this.getCalcDate(evalGroupRankStageId, dataDate, EvalCalStageDimEnum.STAGE_STAGE);
363   - if (Objects.isNull(calcDateParam)){
364   - log.error("参数不够,终止计算!");
365   - return new ArrayList<>();
366   - }
  416 + EvalGroupCalcParamsBO calcDateParam = this.getCalcDate(calcConfigBo, dataDate, EvalCalStageDimEnum.STAGE_STAGE);
367 417 final LocalDate calcEndDate = calcDateParam.getCalcEndDate();
368 418 final Date date = DateUtil.localDateTime2Date(calcDateParam.getCalcEndDate().atTime(23, 23, 59));
369   - EvalGroupRankStage evalGroupRankStage = evalGroupRankStageService.getByIdAndSetTime(evalGroupRankStageId, calcEndDate);
370   - if (Objects.isNull(evalGroupRankStage)) {
371   - log.error("考评排名组阶段[{}]不存在,终止计算!", evalGroupRankStageId);
372   - return new ArrayList<>();
373   - }
  419 + EvalGroupRank evalGroupRank = calcConfigBo.getEvalGroupRank();
  420 + EvalGroupRankStage evalGroupRankStage = calcConfigBo.getEvalGroupRankStage();
  421 + final Long evalGroupRankId = evalGroupRank.getId();
374 422  
375 423 List<EvalRewardPushSalaryBO> evalRewards = new ArrayList<>();
376 424 for (EvalScopeEnum scopeType : EvalScopeEnum.values()) {
377 425 List<EvalGroupRewardDimBO> rewardDims = this.getRewardBOS(evalGroupRankStageId, scopeType);
378   - List<EvalGroupUserShop> userShops = this.getRewardObjs(calcDateParam, evalGroupRankStageId , evalGroups, scopeType);
  426 + List<EvalGroupUserShop> userShops = this.getRewardObjs(calcConfigBo, calcDateParam, evalGroupRankStageId , evalGroups, scopeType);
379 427 if (PublicUtil.isEmpty(userShops)) {
380 428 log.error("考评阶段[{}]人员为空,终止计算!", evalGroupRankStageId);
381 429 continue;
... ... @@ -695,53 +743,25 @@ public class EvalCalculateService {
695 743 }
696 744  
697 745 /**
698   - * @param evalGroupId
699 746 * @param calcDateParam .getCalcEndDate() <=阶段的截止时间的一个计算时间
700 747 * @param scopeType
701 748 * @return
702 749 */
703   - public List<EvalGroupUserShop> buildEvalGroupObj(Long evalGroupId, EvalGroupCalcParamsBO calcDateParam, EvalScopeEnum scopeType) {
704   - EvalGroup evalGroup = evalGroupService.getById(evalGroupId);
705   - if (Objects.isNull(evalGroup)) {
706   - log.error("考评组[{}]不存在,终止计算!", evalGroupId);
707   - return new ArrayList<>();
708   - }
  750 + public List<EvalGroupUserShop> buildEvalGroupObj(EvalGroupRankConfigBO calcConfigBo, EvalGroupCalcParamsBO calcDateParam, EvalScopeEnum scopeType) {
  751 + final EvalGroupRank evalGroupRank = calcConfigBo.getEvalGroupRank();
  752 + final EvalGroupRankStage evalGroupRankStage = calcConfigBo.getEvalGroupRankStage();
  753 + final EvalGroup evalGroup = calcConfigBo.getEvalGroup();
709 754 final Long groupId = evalGroup.getGroupId();
710   - EvalGroupRankStage evalGroupRankStage = evalGroupRankStageService.getByIdAndSetTime(evalGroup.getEvalGroupRankStageId(), calcDateParam.getCalcEndDate());
711   - if (Objects.isNull(evalGroupRankStage)) {
712   - log.error("考评排名组阶段[{}]不存在,终止计算!", JSON.toJSONString(evalGroup));
713   - return new ArrayList<>();
714   - }
715   - EvalGroupRank evalGroupRank = evalGroupRankService.getById(evalGroup.getEvalGroupRankId());
716   - if (Objects.isNull(evalGroupRank)) {
717   - log.error("考评组[{}]排名组不存在,终止计算!", evalGroup.getEvalGroupRankId());
718   - return new ArrayList<>();
719   - }
720 755  
721 756 List<EvalGroupUserShop> userShops = new ArrayList<>();
722 757 if (EvalScopeEnum.STAFF.equals(scopeType)) {
723   - //考评不计算保护期员工
724   - List<EvalGroupUser> users = evalGroupUserService.list(Wrappers.<EvalGroupUser>lambdaQuery()
725   - .eq(EvalGroupUser::getEvalGroupId, evalGroup.getId())
726   - .eq(EvalGroupUser::getDataDate, calcDateParam.getCalcEndDate())
727   - .eq(EvalGroupUser::getYn, Boolean.TRUE)
728   - .eq(EvalGroupUser::getIgnored, Boolean.FALSE)
729   - );
730   - //转正员工要计算
731   - List<EvalGroupUser> turnPositiveUsers = evalGroupUserService.list(Wrappers.<EvalGroupUser>lambdaQuery()
732   - .eq(EvalGroupUser::getEvalGroupId, evalGroup.getId())
733   - .eq(EvalGroupUser::getDataDate, calcDateParam.getCalcEndDate())
734   - .eq(EvalGroupUser::getYn, Boolean.TRUE)
735   - .eq(EvalGroupUser::getIgnored, Boolean.TRUE)
736   - .eq(EvalGroupUser::getIgnoreCause, KpiIgnoreCauseEnum.TURN_POSITIVE_AFTER)
  758 + List<EvalUserPool> pools = evalUserPoolService.list(Wrappers.<EvalUserPool>lambdaQuery()
  759 + .eq(EvalUserPool::getEvalGroupRankStageId, evalGroupRankStage.getId())
  760 + .eq(EvalUserPool::getMonthly, YearMonth.from(calcDateParam.getCalcEndDate()))
  761 + .eq(EvalUserPool::getYn, Boolean.TRUE)
737 762 );
738   - if (PublicUtil.isNotEmpty(turnPositiveUsers)) {
739   - users.addAll(turnPositiveUsers);
740   - }
741   - Map<Long, EvalUserPool> userPoolMap = evalPoolCommonService.inspectionUserPoolMap(evalGroupRankStage, users, calcDateParam.getCalcEndDate(), scopeType);
742   - for (EvalGroupUser user : users) {
743   - EvalUserPool userPool = userPoolMap.get(user.getUserId());
744   - userShops.add(convertBO(user, userPool, evalGroupRank, evalGroupRankStage,calcDateParam, scopeType));
  763 + for (EvalUserPool userPool : pools) {
  764 + userShops.add(this.convertBO(userPool, evalGroupRank, evalGroupRankStage,calcDateParam, scopeType));
745 765 }
746 766 return userShops;
747 767 }
... ... @@ -751,8 +771,7 @@ public class EvalCalculateService {
751 771 List<Long> calcShopIds = commonService.filterInvalidShop(groupId, calcDateParam.getCalcEndDate(), evalGroup.getShopIds());
752 772 for (Long shopId : calcShopIds) {
753 773 EvalShopPool shopPool = shopPoolBOMap.get(shopId);
754   -// Boolean ignored = ! distShopIds.contains(shopId);
755   - userShops.add(this.convertBO(shopPool, evalGroup, evalGroupRank, evalGroupRankStage, calcDateParam));
  774 + userShops.add(this.convertShopBO(shopPool, evalGroup, evalGroupRank, evalGroupRankStage, calcDateParam));
756 775 }
757 776 return userShops;
758 777 }
... ... @@ -797,25 +816,26 @@ public class EvalCalculateService {
797 816 Map<Long, EvalUserPool> userPoolMap = evalPoolCommonService.inspectionUserPoolMap(evalGroupRankStage, users, calcDateParam.getCalcEndDate(), scopeType);
798 817 for (EvalGroupUser user : users) {
799 818 EvalUserPool userPool = userPoolMap.get(user.getUserId());
800   - userShops.add(convertBO(user, userPool, evalGroupRank, evalGroupRankStage,calcDateParam, EvalScopeEnum.MANAGEMENT));
  819 + userShops.add(convertBO(userPool, evalGroupRank, evalGroupRankStage,calcDateParam, EvalScopeEnum.MANAGEMENT));
801 820 }
802 821 return userShops;
803 822 }
804 823  
805   - public List<EvalGroupUserShop> getRewardObjs(EvalGroupCalcParamsBO calcDateParam, Long evalGroupRankStageId , List<EvalGroup> evalGroups, EvalScopeEnum scopeType) {
  824 + public List<EvalGroupUserShop> getRewardObjs(EvalGroupRankConfigBO calcConfigBo, EvalGroupCalcParamsBO calcDateParam, Long evalGroupRankStageId , List<EvalGroup> evalGroups, EvalScopeEnum scopeType) {
806 825 List<EvalGroupUserShop> userShops = Lists.newArrayListWithCapacity(80);
807 826 if (EvalScopeEnum.MANAGEMENT.equals(scopeType)) {
808 827 userShops = this.buildManagerEvalGroupObj(evalGroupRankStageId, calcDateParam, scopeType);
809   - return userShops.stream().filter(userShop -> Boolean.FALSE.equals(userShop.getIgnored()))
  828 + return userShops.stream().filter(userShop -> Boolean.TRUE.equals(userShop.getInclusion()))
810 829 .collect(Collectors.toList());
811 830 }
812 831  
813   - final List<Long> evalGroupIds = evalGroups.stream().map(EvalGroup::getId).collect(Collectors.toList());
814   - for (Long evalGroupId : evalGroupIds) {
815   - List<EvalGroupUserShop> evalGroupUserShops = this.buildEvalGroupObj(evalGroupId, calcDateParam, scopeType);
  832 + //普通岗位、门店 奖惩对象
  833 + for (EvalGroup evalGroup : evalGroups) {
  834 + calcConfigBo.setEvalGroup(evalGroup);
  835 + List<EvalGroupUserShop> evalGroupUserShops = this.buildEvalGroupObj(calcConfigBo, calcDateParam, scopeType);
816 836 if (PublicUtil.isNotEmpty(evalGroupUserShops)) {
817 837 List<EvalGroupUserShop> calcKpiEvalGroupUserShops = evalGroupUserShops.stream()
818   - .filter(userShop -> Boolean.FALSE.equals(userShop.getIgnored()))
  838 + .filter(userShop -> Boolean.TRUE.equals(userShop.getInclusion()))
819 839 .collect(Collectors.toList());
820 840 if (PublicUtil.isNotEmpty(calcKpiEvalGroupUserShops)) {
821 841 userShops.addAll(calcKpiEvalGroupUserShops);
... ... @@ -1000,21 +1020,21 @@ public class EvalCalculateService {
1000 1020 }
1001 1021 }
1002 1022  
1003   - public List<EvalGroupUserShop> filterUserShops(EvalGroupRewardDimBO dim, EvalScopeEnum scopeType, List<EvalGroupUserShop> userShops) {
1004   - if (EvalScopeEnum.STAFF.equals(scopeType)) {
1005   - return userShops.stream().filter(userShop -> Boolean.FALSE.equals(userShop.getIgnored())).collect(Collectors.toList());
1006   - }
1007   - List<EvalGroupUserShop> filterUserShops = new ArrayList<>();
  1023 +// public List<EvalGroupUserShop> filterUserShops(EvalGroupRewardDimBO dim, EvalScopeEnum scopeType, List<EvalGroupUserShop> userShops) {
1008 1024 // if (EvalScopeEnum.STAFF.equals(scopeType)) {
1009   -// filterUserShops = userShops.stream().filter(userShop -> dim.getPostIds().contains(userShop.getPostId())).collect(Collectors.toList());
1010   -// } else {
  1025 +// return userShops.stream().filter(userShop -> Boolean.FALSE.equals(userShop.getIgnored())).collect(Collectors.toList());
  1026 +// }
  1027 +// List<EvalGroupUserShop> filterUserShops = new ArrayList<>();
  1028 +//// if (EvalScopeEnum.STAFF.equals(scopeType)) {
  1029 +//// filterUserShops = userShops.stream().filter(userShop -> dim.getPostIds().contains(userShop.getPostId())).collect(Collectors.toList());
  1030 +//// } else {
  1031 +//// filterUserShops = userShops.stream().filter(userShop -> dim.getShopIds().contains(userShop.getShopId())).collect(Collectors.toList());
  1032 +//// }
  1033 +// if (EvalScopeEnum.SHOP.equals(scopeType)) {
1011 1034 // filterUserShops = userShops.stream().filter(userShop -> dim.getShopIds().contains(userShop.getShopId())).collect(Collectors.toList());
1012 1035 // }
1013   - if (EvalScopeEnum.SHOP.equals(scopeType)) {
1014   - filterUserShops = userShops.stream().filter(userShop -> dim.getShopIds().contains(userShop.getShopId())).collect(Collectors.toList());
1015   - }
1016   - return filterUserShops;
1017   - }
  1036 +// return filterUserShops;
  1037 +// }
1018 1038  
1019 1039 /**
1020 1040 * 计算绩效金额
... ... @@ -1352,16 +1372,15 @@ public class EvalCalculateService {
1352 1372 return poolDetail;
1353 1373 }
1354 1374  
1355   - public EvalGroupUserShop convertBO(EvalGroupUser user,
1356   - EvalUserPool userPool,
  1375 + public EvalGroupUserShop convertBO(EvalUserPool userPool,
1357 1376 EvalGroupRank evalGroupRank,
1358 1377 EvalGroupRankStage evalGroupRankStage,
1359 1378 EvalGroupCalcParamsBO calcDateParam,
1360 1379 EvalScopeEnum evalScopeType) {
1361 1380 EvalGroupUserShop userShop = new EvalGroupUserShop();
1362   - userShop.setName(user.getUserName());
  1381 + userShop.setName(userPool.getUserName());
1363 1382 userShop.setScopeType(evalScopeType);
1364   - userShop.setEvalGroupId(user.getEvalGroupId());
  1383 + userShop.setEvalGroupId(userPool.getEvalGroupId());
1365 1384 userShop.setEvalGroupRankId(evalGroupRankStage.getEvalGroupRankId());
1366 1385 userShop.setEvalGroupRankStageId(evalGroupRankStage.getId());
1367 1386 userShop.setPoolId(userPool.getId());
... ... @@ -1370,14 +1389,14 @@ public class EvalCalculateService {
1370 1389 userShop.setShopId(userPool.getShopId());
1371 1390 userShop.setScoreRatio(Optional.ofNullable(userPool.getScoreRatio()).orElse(BigDecimal.ZERO));
1372 1391 userShop.setStageAccumulationScoreRatio(Optional.ofNullable(userPool.getStageAccumulationScoreRatio()).orElse(BigDecimal.ZERO));
1373   - userShop.setReferId(user.getUserId());
  1392 + userShop.setReferId(userPool.getUserId());
1374 1393 userShop.setBeginDate(calcDateParam.getCalcBeginDate());
1375   - userShop.setDataDate(user.getDataDate());
  1394 + userShop.setDataDate(userPool.getDataDate());
1376 1395 userShop.setMultiStage(evalGroupRank.getMultiStage());
1377   - userShop.setGroupId(user.getGroupId());
  1396 + userShop.setGroupId(userPool.getGroupId());
1378 1397 userShop.setScore(BigDecimal.ZERO);
1379 1398 // userShop.setReward(BigDecimal.ZERO);
1380   - userShop.setIgnored(user.getIgnored());
  1399 + userShop.setInclusion(userPool.getInclusion());
1381 1400 userShop.setStageDimEnum(calcDateParam.getStageDimEnum());
1382 1401 if (PublicUtil.isNotEmpty(calcDateParam.getCalcMonthBeginDate())) {
1383 1402 userShop.setCalcMonthBeginDate(calcDateParam.getCalcMonthBeginDate());
... ... @@ -1410,7 +1429,7 @@ public class EvalCalculateService {
1410 1429 // return userShop;
1411 1430 // }
1412 1431  
1413   - public EvalGroupUserShop convertBO(EvalShopPool shopPool,
  1432 + public EvalGroupUserShop convertShopBO(EvalShopPool shopPool,
1414 1433 EvalGroup evalGroup,
1415 1434 EvalGroupRank evalGroupRank,
1416 1435 EvalGroupRankStage evalGroupRankStage,
... ... @@ -1436,7 +1455,7 @@ public class EvalCalculateService {
1436 1455 userShop.setMultiStage(evalGroupRank.getMultiStage());
1437 1456 userShop.setGroupId(evalGroup.getGroupId());
1438 1457 // userShop.setIgnored(ignored);
1439   - userShop.setIgnored(Boolean.FALSE);
  1458 + userShop.setInclusion(Boolean.TRUE);
1440 1459 userShop.setScore(BigDecimal.ZERO);
1441 1460 userShop.setStageDimEnum(calcDateParam.getStageDimEnum());
1442 1461 if (PublicUtil.isNotEmpty(calcDateParam.getCalcMonthBeginDate())) {
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/eval/EvalCalculateTaskService.java
... ... @@ -20,6 +20,7 @@ import cn.fw.morax.rpc.ehr.dto.ManagerDTO;
20 20 import cn.fw.morax.rpc.ehr.dto.ManagerStaffDTO;
21 21 import cn.fw.morax.sdk.dto.common.IndicatorReportTypeEnum;
22 22 import cn.fw.morax.sdk.dto.kpi.KpiStageReportNoticeMQ;
  23 +import cn.fw.morax.service.biz.CommonService;
23 24 import cn.fw.morax.service.component.KpiStageIndicatorReportProducer;
24 25 import cn.fw.morax.service.data.eval.*;
25 26 import cn.fw.morax.service.data.kpi.IndicatorsService;
... ... @@ -40,6 +41,7 @@ import org.springframework.transaction.TransactionDefinition;
40 41 import org.springframework.transaction.TransactionStatus;
41 42 import org.springframework.transaction.annotation.Transactional;
42 43  
  44 +import java.math.BigDecimal;
43 45 import java.time.LocalDate;
44 46 import java.time.LocalDateTime;
45 47 import java.time.YearMonth;
... ... @@ -80,6 +82,7 @@ public class EvalCalculateTaskService {
80 82 private final KpiStageMqLogService kpiStageMqLogService;
81 83 private final EvalCalcClosureService evalCalcClosureService;
82 84 private final EvalPoolCommonService evalPoolCommonService;
  85 + private final EvalUserPoolService evalUserPoolService;
83 86 private final EvalGroupRankService evalGroupRankService;
84 87 private final StringRedisTemplate stringRedisTemplate;
85 88 private final DistributedLocker distributedLocker;
... ... @@ -87,6 +90,7 @@ public class EvalCalculateTaskService {
87 90 private final IndicatorsService indicatorsService;
88 91 private final EvalGroupService evalGroupService;
89 92 private final EvalCalcService evalCalcService;
  93 + private final CommonService commonService;
90 94 private final EhrRpcService ehrRpcService;
91 95  
92 96 /**
... ... @@ -118,11 +122,11 @@ public class EvalCalculateTaskService {
118 122 if (EvalCalcStatusEnum.COLLECT_STAGE_DATA.equals(evalCalc.getStatus())) {
119 123 //多阶段先抽取指标数据
120 124 if (evalCalc.getMultiStage()) {
121   - this.cacheStageIndicator(evalCalcId, evalGroupRankId, evalGroupIds, Boolean.TRUE, localDate);
  125 + this.cacheStageIndicator(evalCalcId, evalGroupRankId, Boolean.TRUE, localDate);
122 126 return;
123 127 }
124 128 //单阶段直接计算
125   - this.cacheCalcGroupIds(evalCalc.getId(), evalCalc.getEvalGroupRankId(), new HashSet<>(evalCalc.getEvalGroupIds()), evalCalc.getCalcDate());
  129 + this.cacheCalcGroupIds(evalCalc.getId(), evalCalc.getEvalGroupRankId(), evalCalc.getCalcDate());
126 130 return;
127 131 }
128 132 //抽取人员信息
... ... @@ -167,11 +171,11 @@ public class EvalCalculateTaskService {
167 171 if (EvalCalcStatusEnum.COLLECT_STAGE_DATA.equals(evalCalc.getStatus())) {
168 172 //多阶段先抽取指标数据
169 173 if (evalCalc.getMultiStage()) {
170   - this.cacheStageIndicator(evalCalcId, evalGroupRankId, evalGroupIds, Boolean.FALSE, localDate);
  174 + this.cacheStageIndicator(evalCalcId, evalGroupRankId, Boolean.FALSE, localDate);
171 175 continue;
172 176 }
173 177 //单阶段直接计算
174   - this.cacheCalcGroupIds(evalCalc.getId(), evalCalc.getEvalGroupRankId(), new HashSet<>(evalCalc.getEvalGroupIds()), evalCalc.getCalcDate());
  178 + this.cacheCalcGroupIds(evalCalc.getId(), evalCalc.getEvalGroupRankId(), evalCalc.getCalcDate());
175 179 continue;
176 180 }
177 181 //抽取人员信息
... ... @@ -256,7 +260,12 @@ public class EvalCalculateTaskService {
256 260 continue;
257 261 }
258 262 try {
259   - this.extractEvalUser(bo);
  263 + //实时计算抽取每天的人员数据
  264 + if (Boolean.TRUE.equals(bo.getRealTimeCalc())) {
  265 + this.extractStageEveryDateEvalUser(bo);
  266 + } else {
  267 + this.extractEvalUser(bo);
  268 + }
260 269 } catch (Exception re) {
261 270 log.error("考评人员抽取异常", re);
262 271 bo.getAtomicInteger().incrementAndGet();
... ... @@ -290,56 +299,54 @@ public class EvalCalculateTaskService {
290 299 for (EvalGroupRankStage stage : stages) {
291 300 final Long evalGroupRankStageId = stage.getId();
292 301 List<EvalGroupUser> evalGroupUsersForSave = Lists.newArrayListWithCapacity(100);
  302 + List<EvalGroupUser> managerEvalGroupUsersForSave = Lists.newArrayListWithCapacity(100);
293 303 List<EvalGroup> evalGroups = evalGroupService.list(Wrappers.<EvalGroup>lambdaQuery()
294 304 .eq(EvalGroup::getEvalGroupRankStageId, evalGroupRankStageId)
295 305 .eq(EvalGroup::getYn, Boolean.TRUE)
296 306 );
297 307 LocalDate dataDate = yesterday.isAfter(stage.getOverTime()) ? stage.getOverTime() : yesterday;
  308 + //普通岗位员工
298 309 for (EvalGroup evalGroup : evalGroups) {
299 310 evalGroupIds.add(evalGroup.getId());
300   - if (PublicUtil.isEmpty(evalGroup.getPostIds())) {
301   - continue;
302   - }
303 311 //昨天已经在 阶段结束时间之后
304   - for (Long postId : evalGroup.getPostIds()) {
305   - evalGroupUsersForSave.addAll(evalGroupUserBizService.fetchBuildKpiUser(groupId, postId, evalGroup, dataDate));
  312 + for (Long postId : Optional.ofNullable(evalGroup.getPostIds()).orElse(new ArrayList<>())) {
  313 + List<EvalGroupUser> evalGroupUsers = evalGroupUserBizService.fetchBuildKpiUser(groupId, postId, evalGroup, dataDate);
  314 + this.setMultiStageIgnoreCase(evalGroupRank, stage, evalGroupUsers);
  315 + evalGroupUsersForSave.addAll(evalGroupUsers);
306 316 }
307 317 }
  318 + //管理层人员
308 319 List<EvalGroupRewardDim> rewardDims = evalGroupRewardDimService.getManageReward(evalGroupRankStageId);
309 320 for (EvalGroupRewardDim rewardDim : rewardDims) {
310 321 for (Long postId : rewardDim.getPostIds()) {
311   - List<EvalGroupUser> evalGroupUsers = evalGroupUserBizService.fetchPostUsers(groupId, postId, rewardDim.getShopIds(), dataDate);
312   - if (PublicUtil.isNotEmpty(evalGroupUsers)) {
313   - for (EvalGroupUser user : evalGroupUsers) {
314   - user.setEvalGroupRankId(evalGroupRankId);
315   - user.setEvalGroupRankStageId(evalGroupRankStageId);
316   - user.setEvalGroupId(-1L);
317   - user.setEgc("");
318   - }
319   - evalGroupUsersForSave.addAll(evalGroupUsers);
  322 + List<EvalGroupUser> manageEvalGroupUsers = evalGroupUserBizService.fetchPostUsers(groupId, postId, rewardDim.getShopIds(), dataDate);
  323 + if (PublicUtil.isNotEmpty(manageEvalGroupUsers)) {
  324 + this.initManageEvalUser(manageEvalGroupUsers, evalGroupRankId, evalGroupRankStageId);
  325 + this.setMultiStageIgnoreCase(evalGroupRank, stage, manageEvalGroupUsers);
  326 + managerEvalGroupUsersForSave.addAll(manageEvalGroupUsers);
320 327 }
321 328 }
322 329 }
323   -
  330 + //去重
  331 + Set<Long> repeatUserIds = this.queryRepeatUserEvalIds(evalGroupRankStageId, dataDate);
  332 + if (PublicUtil.isNotEmpty(repeatUserIds)) {
  333 + evalGroupUserService.removeByIds(repeatUserIds);
  334 + }
324 335 if (PublicUtil.isNotEmpty(evalGroupUsersForSave)) {
325   - List<EvalGroupUser> repeatUsers = evalGroupUserService.list(Wrappers.<EvalGroupUser>lambdaQuery()
326   - .eq(EvalGroupUser::getEvalGroupRankStageId, evalGroupRankStageId)
327   - .eq(EvalGroupUser::getDataDate, dataDate)
328   - .eq(EvalGroupUser::getYn, Boolean.TRUE)
329   - .select(EvalGroupUser::getId)
330   - );
331   - if (PublicUtil.isNotEmpty(repeatUsers)) {
332   - evalGroupUserService.removeByIds(repeatUsers.stream().map(EvalGroupUser::getId).collect(Collectors.toSet()));
333   - }
334 336 evalGroupUserService.insertBatchSomeColumn(evalGroupUsersForSave);
  337 + evalPoolCommonService.createUserPools(evalGroupUsersForSave, EvalScopeEnum.STAFF);
  338 + }
  339 + if (PublicUtil.isNotEmpty(managerEvalGroupUsersForSave)) {
  340 + evalGroupUserService.insertBatchSomeColumn(managerEvalGroupUsersForSave);
  341 + evalPoolCommonService.createUserPools(managerEvalGroupUsersForSave, EvalScopeEnum.MANAGEMENT);
335 342 }
336 343 }
337 344 evalCalcService.modifyStatus(evalCalcId, EvalCalcStatusEnum.COLLECT_STAGE_DATA);
338 345 //多阶段
339 346 if (bo.getMultiStage()) {
340   - this.cacheStageIndicator(evalCalcId, evalGroupRankId, evalGroupIds, realTimeCalc, yesterday);
  347 + this.cacheStageIndicator(evalCalcId, evalGroupRankId, realTimeCalc, yesterday);
341 348 } else {
342   - this.cacheCalcGroupIds(evalCalcId, evalGroupRankId, evalGroupIds, yesterday);
  349 + this.cacheCalcGroupIds(evalCalcId, evalGroupRankId, yesterday);
343 350 }
344 351 platformTransactionManager.commit(transactionStatus);
345 352 } catch (Exception e) {
... ... @@ -349,8 +356,189 @@ public class EvalCalculateTaskService {
349 356  
350 357 }
351 358  
352   - private void cacheStageIndicator(final Long evalCalcId, final Long evalGroupRankId, final Set<Long> evalGroupIds, Boolean realTimeCalc, final LocalDate localDate) {
353   - String json = JSONObject.toJSONString(new EvalExtractStageIndicatorBO(evalCalcId, evalGroupRankId, evalGroupIds, localDate, realTimeCalc));
  359 + public void extractStageEveryDateEvalUser(EvalExtractUserBO bo) {
  360 + final Long evalCalcId = bo.getEvalCalcId();
  361 + final Long evalGroupRankId = bo.getEvalGroupRankId();
  362 + final Boolean realTimeCalc = bo.getRealTimeCalc();
  363 + final LocalDate yesterday = bo.getLocalDate();
  364 + EvalGroupRank evalGroupRank = evalGroupRankService.getById(evalGroupRankId);
  365 + if (PublicUtil.isEmpty(evalGroupRank)) {
  366 + log.error("考评抽取人员找不到考评排名组信息:{}", JSON.toJSONString(bo));
  367 + return;
  368 + }
  369 + final Long groupId = evalGroupRank.getGroupId();
  370 + List<EvalGroupRankStage> stages = evalGroupRankStageService.getRankStages(evalGroupRankId, yesterday, realTimeCalc);
  371 + TransactionStatus transactionStatus = platformTransactionManager.getTransaction(transactionDefinition);
  372 + try {
  373 + for (EvalGroupRankStage stage : stages) {
  374 + final Long start = System.currentTimeMillis();
  375 + log.info(" 考评抽取历史人员数据:考评排名组阶段id:{}", stage.getId());
  376 + Set<Long> stageRepeatEvalUserIds = new HashSet<>();
  377 + final Long evalGroupRankStageId = stage.getId();
  378 + List<EvalGroupUser> evalGroupUsersForSave = Lists.newArrayListWithCapacity(100);
  379 + List<EvalGroupUser> managerEvalGroupUsersForSave = Lists.newArrayListWithCapacity(100);
  380 + List<EvalGroup> evalGroups = evalGroupService.list(Wrappers.<EvalGroup>lambdaQuery()
  381 + .eq(EvalGroup::getEvalGroupRankStageId, evalGroupRankStageId)
  382 + .eq(EvalGroup::getYn, Boolean.TRUE)
  383 + );
  384 + LocalDate stageEveryDataTime = stage.getBeginTime();
  385 + //计算时间 在阶段结束时间之后 阶段结束时间
  386 + final LocalDate stageEndTime = yesterday.isAfter(stage.getOverTime()) ? stage.getOverTime() : yesterday;
  387 +
  388 + //阶段开始时间大于 阶段结束时间
  389 + while (stageEndTime.compareTo(stageEveryDataTime) >= 0) {
  390 + log.info("抽取考评排名组人员信息:{},阶段:{},日期:{}", evalGroupRankId, evalGroupRankStageId, stageEveryDataTime);
  391 + //先记录 重复员工信息
  392 + stageRepeatEvalUserIds.addAll(this.queryRepeatUserEvalIds(evalGroupRankStageId, stageEveryDataTime));
  393 + //普通岗位员工
  394 + for (EvalGroup evalGroup : evalGroups) {
  395 + for (Long postId : Optional.ofNullable(evalGroup.getPostIds()).orElse(new ArrayList<>())) {
  396 + List<EvalGroupUser> evalGroupUsers = evalGroupUserBizService.fetchBuildKpiUser(groupId, postId, evalGroup, stageEveryDataTime);
  397 + this.setMultiStageIgnoreCase(evalGroupRank, stage, evalGroupUsers);
  398 + evalGroupUsersForSave.addAll(evalGroupUsers);
  399 + evalPoolCommonService.createUserPools(evalGroupUsers, EvalScopeEnum.STAFF);
  400 + }
  401 + }
  402 + //管理层人员
  403 + List<EvalGroupRewardDim> rewardDims = evalGroupRewardDimService.getManageReward(evalGroupRankStageId);
  404 + for (EvalGroupRewardDim rewardDim : rewardDims) {
  405 + for (Long postId : rewardDim.getPostIds()) {
  406 + List<EvalGroupUser> manageEvalGroupUsers = evalGroupUserBizService.fetchPostUsers(groupId, postId, rewardDim.getShopIds(), stageEveryDataTime);
  407 + this.initManageEvalUser(manageEvalGroupUsers, evalGroupRankId, evalGroupRankStageId);
  408 + this.setMultiStageIgnoreCase(evalGroupRank, stage, managerEvalGroupUsersForSave);
  409 + managerEvalGroupUsersForSave.addAll(manageEvalGroupUsers);
  410 + evalPoolCommonService.createUserPools(manageEvalGroupUsers, EvalScopeEnum.MANAGEMENT);
  411 + }
  412 + }
  413 + //日期+1
  414 + stageEveryDataTime = stageEveryDataTime.plusDays(1);
  415 + }
  416 + //去重
  417 + if (PublicUtil.isNotEmpty(stageRepeatEvalUserIds)) {
  418 + evalGroupUserService.removeByIds(stageRepeatEvalUserIds);
  419 + }
  420 + if (PublicUtil.isNotEmpty(evalGroupUsersForSave)) {
  421 + evalGroupUserService.insertBatchSomeColumn(evalGroupUsersForSave);
  422 + }
  423 + if (PublicUtil.isNotEmpty(managerEvalGroupUsersForSave)) {
  424 + evalGroupUserService.insertBatchSomeColumn(managerEvalGroupUsersForSave);
  425 + }
  426 + log.info(" 考评抽取历史人员数据完成:考评排名组阶段id:{},耗时:{} s", stage.getId(), TimeUnit.MILLISECONDS.toSeconds(System.currentTimeMillis() - start));
  427 + }
  428 + //多阶段
  429 + if (bo.getMultiStage()) {
  430 + this.cacheStageIndicator(evalCalcId, evalGroupRankId, realTimeCalc, yesterday);
  431 + } else {
  432 + this.cacheCalcGroupIds(evalCalcId, evalGroupRankId, yesterday);
  433 + }
  434 + platformTransactionManager.commit(transactionStatus);
  435 + } catch (Exception e) {
  436 + platformTransactionManager.rollback(transactionStatus);
  437 + throw e;
  438 + }
  439 + }
  440 +
  441 + /**
  442 + * 设置阶段忽略原因
  443 + * 1. 阶段内有调岗,不参与考评
  444 + * 2. 阶段内离职,不参与考评
  445 + */
  446 + public void setMultiStageIgnoreCase(EvalGroupRank evalGroupRank, EvalGroupRankStage stage, List<EvalGroupUser> evalGroupUsers) {
  447 + if (Boolean.FALSE.equals(evalGroupRank.getMultiStage())) {
  448 + return;
  449 + }
  450 + if (PublicUtil.isEmpty(evalGroupUsers)) {
  451 + return;
  452 + }
  453 + for (EvalGroupUser evalGroupUser : evalGroupUsers) {
  454 + final Long userId = evalGroupUser.getUserId();
  455 + final Long postId = evalGroupUser.getPostId();
  456 + final LocalDate newPostChangeDate = commonService.getNewPostChangeDate(userId, postId);
  457 + final LocalDate oldPostChangeDate = commonService.getOldPostChangeDate(userId, postId);
  458 + if (PublicUtil.isNotEmpty(newPostChangeDate)) {
  459 + //调岗时间大于阶段开始时间 阶段结束时间大于调岗时间(在阶段时间范围内调岗)
  460 + if (newPostChangeDate.compareTo(stage.getBeginTime()) > 0 && stage.getOverTime().compareTo(newPostChangeDate) > 0) {
  461 + evalGroupUser.setIgnored(Boolean.TRUE);
  462 + evalGroupUser.setIgnoreCauseDesc(KpiIgnoreCauseEnum.EVAL_MULTISTAGE_TIME_POST_CHANGE.getName());
  463 + evalGroupUser.setIgnoreCause(KpiIgnoreCauseEnum.EVAL_MULTISTAGE_TIME_POST_CHANGE);
  464 + }
  465 + }
  466 + if (PublicUtil.isNotEmpty(oldPostChangeDate)) {
  467 + //调岗时间大于阶段开始时间 阶段结束时间大于调岗时间(在阶段时间范围内调岗)
  468 + if (oldPostChangeDate.compareTo(stage.getBeginTime()) > 0 && stage.getOverTime().compareTo(oldPostChangeDate) > 0) {
  469 + evalGroupUser.setIgnored(Boolean.TRUE);
  470 + evalGroupUser.setIgnoreCause(KpiIgnoreCauseEnum.EVAL_MULTISTAGE_TIME_POST_CHANGE);
  471 + evalGroupUser.setIgnoreCauseDesc(KpiIgnoreCauseEnum.EVAL_MULTISTAGE_TIME_POST_CHANGE.getName());
  472 + }
  473 + }
  474 + final LocalDate leaveDate = evalGroupUser.getLeaveDate();
  475 + if (PublicUtil.isNotEmpty(leaveDate)) {
  476 + //调岗时间大于阶段开始时间 阶段结束时间大于调岗时间(在阶段时间范围内调岗)
  477 + if (leaveDate.compareTo(stage.getBeginTime()) > 0 && stage.getOverTime().compareTo(leaveDate) > 0) {
  478 + evalGroupUser.setIgnored(Boolean.TRUE);
  479 + evalGroupUser.setIgnoreCause(KpiIgnoreCauseEnum.EVAL_MULTISTAGE_TIME_LEAVE);
  480 + evalGroupUser.setIgnoreCauseDesc(KpiIgnoreCauseEnum.EVAL_MULTISTAGE_TIME_LEAVE.getName());
  481 + }
  482 + }
  483 + }
  484 + }
  485 +
  486 + /**
  487 + * 多阶段重置 是否参与考评字段
  488 + * 张三3月18号离职,按照规则 15号之后离职需要参与绩效考核。第二阶段考评 3月11号 到 3月20号 ,这个期间张三不是所有时间都在考评范围内,所以不参与考评。
  489 + */
  490 + public void multiStageResetPoolInclusion(EvalGroupRank evalGroupRank, EvalGroupRankStage evalGroupRankStage, LocalDate dataDate) {
  491 + if (Boolean.TRUE.equals(evalGroupRank.getMultiStage())) {
  492 + List<EvalUserPool> stageEvalUserPools = evalUserPoolService.list(Wrappers.<EvalUserPool>lambdaQuery()
  493 + .eq(EvalUserPool::getEvalGroupRankStageId, evalGroupRankStage.getId())
  494 + .eq(EvalUserPool::getMonthly, YearMonth.from(dataDate))
  495 + .eq(EvalUserPool::getYn, Boolean.TRUE));
  496 + for (EvalUserPool evalUserPool : stageEvalUserPools) {
  497 + evalUserPool.setInclusion(Boolean.FALSE);
  498 + evalUserPool.setReward(BigDecimal.ZERO);
  499 + evalUserPoolService.updateById(evalUserPool);
  500 + }
  501 + }
  502 + }
  503 +
  504 + public Set<Long> queryRepeatUserEvalIds(Long evalGroupRankStageId, LocalDate dataDate) {
  505 + List<EvalGroupUser> repeatUsers = evalGroupUserService.list(Wrappers.<EvalGroupUser>lambdaQuery()
  506 + .eq(EvalGroupUser::getEvalGroupRankStageId, evalGroupRankStageId)
  507 + .eq(EvalGroupUser::getDataDate, dataDate)
  508 + .eq(EvalGroupUser::getYn, Boolean.TRUE)
  509 + .select(EvalGroupUser::getId)
  510 + );
  511 + return repeatUsers.stream().map(EvalGroupUser::getId).collect(Collectors.toSet());
  512 + }
  513 +
  514 + public void initManageEvalUser(List<EvalGroupUser> manageEvalGroupUsers, Long evalGroupRankId, Long evalGroupRankStageId) {
  515 + if (PublicUtil.isEmpty(manageEvalGroupUsers)) {
  516 + return;
  517 + }
  518 + for (EvalGroupUser user : manageEvalGroupUsers) {
  519 + user.setEvalGroupRankId(evalGroupRankId);
  520 + user.setEvalGroupRankStageId(evalGroupRankStageId);
  521 + user.setEvalGroupId(-1L);
  522 + user.setEgc("");
  523 + }
  524 + }
  525 +
  526 + public void updatePoolOtherInfo(List<EvalGroupUser> users, EvalScopeEnum scopeType) {
  527 + for (EvalGroupUser user : users) {
  528 + EvalUserPool userPool = evalPoolCommonService.inspectionUserPool(user, scopeType);
  529 + //忽略就不计算
  530 + Boolean inclusion = Boolean.TRUE.equals(user.getIgnored()) ? Boolean.FALSE : Boolean.TRUE;
  531 + userPool.setInclusion(inclusion);
  532 + //不纳入计算,奖惩清空
  533 + if (Boolean.FALSE.equals(inclusion)) {
  534 + userPool.setReward(BigDecimal.ZERO);
  535 + }
  536 + evalUserPoolService.updateById(userPool);
  537 + }
  538 + }
  539 +
  540 + public void cacheStageIndicator(final Long evalCalcId, final Long evalGroupRankId, Boolean realTimeCalc, final LocalDate localDate) {
  541 + String json = JSONObject.toJSONString(new EvalExtractStageIndicatorBO(evalCalcId, evalGroupRankId, localDate, realTimeCalc));
354 542 stringRedisTemplate.opsForSet().add(evalCalculationVal.getCacheSendStageIndicatorMQ(), json);
355 543 }
356 544  
... ... @@ -379,6 +567,7 @@ public class EvalCalculateTaskService {
379 567  
380 568 public void extractStageIndicator(EvalExtractStageIndicatorBO stageIndicatorBO) {
381 569 final Long evalGroupRankId = stageIndicatorBO.getEvalGroupRankId();
  570 + final Long evalCalcId = stageIndicatorBO.getEvalCalcId();
382 571 final LocalDate dataDate = stageIndicatorBO.getLocalDate();
383 572 final Boolean realTimeCalc = stageIndicatorBO.getRealTimeCalc();
384 573  
... ... @@ -400,7 +589,7 @@ public class EvalCalculateTaskService {
400 589 if (PublicUtil.isEmpty(sysIndicatorCodes)) {
401 590 evalCalc.setStatus(EvalCalcStatusEnum.CALC_EVAL);
402 591 evalCalcService.updateById(evalCalc);
403   - cacheCalcGroupIds(evalCalc.getId(), evalCalc.getEvalGroupRankId(), new HashSet<>(evalCalc.getEvalGroupIds()), evalCalc.getCalcDate());
  592 + cacheCalcGroupIds(evalCalcId, evalCalc.getEvalGroupRankId(), evalCalc.getCalcDate());
404 593 platformTransactionManager.commit(status);
405 594 return;
406 595 }
... ... @@ -410,16 +599,15 @@ public class EvalCalculateTaskService {
410 599 //保存发送记录,构建发送mq
411 600 EvalRankReportBO evalRankReportBO = this.getReportObj(evalGroupRank, dataDate, evalGroupRankStages);
412 601 for (String sysIndicatorCode : sysIndicatorCodes) {
413   - KpiStageReportNoticeMQ noticeMQ = this.sendNotice(evalRankReportBO, evalGroupRankStages, sysIndicatorCode, dataDate, evalCalc.getId());
414   - stageReportNoticeMQS.add(noticeMQ);
  602 + stageReportNoticeMQS.addAll(this.sendNotice(evalRankReportBO, evalGroupRankStages, sysIndicatorCode, dataDate, evalCalcId));
  603 + stageReportNoticeMQS.addAll(this.sendLeaveStaffNotice(evalRankReportBO, evalGroupRankStages, sysIndicatorCode, dataDate, evalCalcId));
415 604  
416 605 //关联指标也发MQ
417 606 Indicators indicators = indicatorsService.queryByCode(sysIndicatorCode, Boolean.FALSE);
418 607 if (PublicUtil.isNotEmpty(indicators) && PublicUtil.isNotEmpty(indicators.getOriginIndicatorCode())) {
419 608 final String originIndicatorCode = indicators.getOriginIndicatorCode();
420   - KpiStageReportNoticeMQ originNoticeMQ = this.sendNotice(evalRankReportBO, evalGroupRankStages,
421   - originIndicatorCode, dataDate, evalCalc.getId());
422   - stageReportNoticeMQS.add(originNoticeMQ);
  609 + stageReportNoticeMQS.addAll(this.sendNotice(evalRankReportBO, evalGroupRankStages, originIndicatorCode, dataDate, evalCalcId));
  610 + stageReportNoticeMQS.addAll(this.sendLeaveStaffNotice(evalRankReportBO, evalGroupRankStages, originIndicatorCode, dataDate, evalCalcId));
423 611 }
424 612 }
425 613 platformTransactionManager.commit(status);
... ... @@ -440,60 +628,141 @@ public class EvalCalculateTaskService {
440 628 *
441 629 * @param dataDate
442 630 */
443   - public KpiStageReportNoticeMQ sendNotice(EvalRankReportBO evalRankReportBO, List<EffectEvalStageBO> stages, String indicatorCode, final LocalDate dataDate, final Long evalCalcId) {
444   - KpiStageMqLog mqLog = this.createMqLog(evalRankReportBO, stages, indicatorCode, evalCalcId, dataDate);
445   - final LocalDate monthlyEndTime = YearMonth.from(dataDate).atEndOfMonth();
446   - KpiStageReportNoticeMQ noticeMQ = KpiStageReportNoticeMQ.builder()
447   - .indicatorCode(mqLog.getIndicatorCode())
448   - .shopIds(mqLog.getShopIds())
449   - .userIds(mqLog.getUserIds())
450   - .groupId(mqLog.getGroupId())
451   - .build();
452   - List<KpiStageReportNoticeMQ.ReportDate> reportStages = new ArrayList<>();
453   - //阶段时间
454   - for (EffectEvalStageBO stageIndicatorBO : stages) {
455   - LocalDate stageEndTime = stageIndicatorBO.getStageEndTime().isAfter(dataDate)
456   - ? dataDate : stageIndicatorBO.getStageEndTime();
  631 + public List<KpiStageReportNoticeMQ> sendNotice(EvalRankReportBO evalRankReportBO, List<EffectEvalStageBO> stages, String indicatorCode, final LocalDate dataDate, final Long evalCalcId) {
  632 + final Date monthlyEndTime = DateUtil.localDateTime2Date(YearMonth.from(dataDate).atEndOfMonth().atTime(23, 59, 59));
  633 + final Date monthlyStartTime = DateUtil.localDateTime2Date(evalRankReportBO.getWholeBeginTime().atTime(0, 0, 1));
  634 + List<KpiStageReportNoticeMQ> reportNoticeMQS = new ArrayList<>();
  635 + for (EffectEvalStageBO evalStageBO : stages) {
  636 + final LocalDate stageEndTime = evalStageBO.getStageEndTime().isAfter(dataDate)
  637 + ? dataDate : evalStageBO.getStageEndTime();
  638 + final Date stageEndDateTime = DateUtil.localDateTime2Date(stageEndTime.atTime(23, 59, 59));
  639 +
  640 + KpiStageMqLog mqLog = this.createMqLog(evalRankReportBO, evalStageBO, indicatorCode, evalCalcId, stageEndTime);
  641 + KpiStageReportNoticeMQ noticeMQ = KpiStageReportNoticeMQ.builder()
  642 + .indicatorCode(mqLog.getIndicatorCode())
  643 + .shopIds(mqLog.getShopIds())
  644 + .userIds(mqLog.getUserIds())
  645 + .groupId(mqLog.getGroupId())
  646 + .build();
  647 + List<KpiStageReportNoticeMQ.ReportDate> reportStages = new ArrayList<>();
457 648 KpiStageReportNoticeMQ.ReportDate reportStage = noticeMQ.new ReportDate(IndicatorReportTypeEnum.STAGE.getValue(),
458   - DateUtil.localDateTime2Date(stageIndicatorBO.getStageBeginTime().atTime(0, 0, 1)),
459   - DateUtil.localDateTime2Date(stageEndTime.atTime(23, 59, 59)),
460   - DateUtil.localDateTime2Date(stageIndicatorBO.getStageEndTime().atTime(23, 59, 59))
  649 + DateUtil.localDateTime2Date(evalStageBO.getStageBeginTime().atTime(0, 0, 1)),
  650 + stageEndDateTime,
  651 + DateUtil.localDateTime2Date(evalStageBO.getStageEndTime().atTime(23, 59, 59))
461 652 );
462 653 reportStages.add(reportStage);
  654 + mqLog.setStatus(KpiStageMqLogStatusEnum.WAIT_REPORT);
  655 + mqLog.setStageTimeStr(JSON.toJSONString(reportStages));
  656 + kpiStageMqLogService.save(mqLog);
  657 +
  658 + KpiStageReportNoticeMQ.ReportDate monthly = noticeMQ.new ReportDate(IndicatorReportTypeEnum.WHOLE.getValue(),
  659 + monthlyStartTime,
  660 + stageEndDateTime,
  661 + monthlyEndTime
  662 + );
  663 + noticeMQ.setWhole(monthly);
  664 + noticeMQ.setStages(reportStages);
  665 + noticeMQ.setUid(mqLog.getId().toString());
  666 +
  667 + reportNoticeMQS.add(noticeMQ);
  668 + //1. 初始状态放入
  669 + stringRedisTemplate.opsForHash().put(
  670 + evalCalculationVal.getMqCodeLogStatusKey(mqLog.getEvalCalcId()),
  671 + mqLog.getIndicatorCode(),
  672 + String.valueOf(mqLog.getStatus().getValue())
  673 + );
  674 + //设置过期
  675 + stringRedisTemplate.expire(
  676 + evalCalculationVal.getMqCodeLogStatusKey(mqLog.getEvalCalcId()),
  677 + 6L, TimeUnit.HOURS);
  678 + log.info("1. 初始状态放入 redis K: {},HK: {},HV: {},24H后过期",
  679 + evalCalculationVal.getMqCodeLogStatusKey(mqLog.getEvalCalcId()),
  680 + mqLog.getIndicatorCode(),
  681 + mqLog.getStatus().getValue()
  682 + );
463 683 }
464   - mqLog.setStatus(KpiStageMqLogStatusEnum.WAIT_REPORT);
465   - mqLog.setStageTimeStr(JSON.toJSONString(reportStages));
466   - kpiStageMqLogService.save(mqLog);
  684 + return reportNoticeMQS;
  685 + }
467 686  
468   - KpiStageReportNoticeMQ.ReportDate monthly = noticeMQ.new ReportDate(IndicatorReportTypeEnum.WHOLE.getValue(),
469   - DateUtil.localDateTime2Date(mqLog.getWholeBeginTime().atTime(0, 0, 1)),
470   - DateUtil.localDateTime2Date(mqLog.getWholeEndTime().atTime(23, 59, 59)),
471   - DateUtil.localDateTime2Date(monthlyEndTime.atTime(23, 59, 59))
472   - );
473   - noticeMQ.setWhole(monthly);
474   - noticeMQ.setStages(reportStages);
475   - noticeMQ.setUid(mqLog.getId().toString());
476   - //1. 初始状态放入
477   - stringRedisTemplate.opsForHash().put(
478   - evalCalculationVal.getMqCodeLogStatusKey(mqLog.getEvalCalcId()),
479   - mqLog.getIndicatorCode(),
480   - String.valueOf(mqLog.getStatus().getValue())
481   - );
482   - //设置过期
483   - stringRedisTemplate.expire(
484   - evalCalculationVal.getMqCodeLogStatusKey(mqLog.getEvalCalcId()),
485   - 6L, TimeUnit.HOURS);
486   - log.info("1. 初始状态放入 redis K: {},HK: {},HV: {},24H后过期",
487   - evalCalculationVal.getMqCodeLogStatusKey(mqLog.getEvalCalcId()),
488   - mqLog.getIndicatorCode(),
489   - mqLog.getStatus().getValue()
490   - );
491   - return noticeMQ;
  687 + /**
  688 + * 发送绩效数据上报mq
  689 + *
  690 + * @param dataDate
  691 + */
  692 + public List<KpiStageReportNoticeMQ> sendLeaveStaffNotice(EvalRankReportBO evalRankReportBO, List<EffectEvalStageBO> stages, String indicatorCode, final LocalDate dataDate, final Long evalCalcId) {
  693 + final Date monthlyEndTime = DateUtil.localDateTime2Date(YearMonth.from(dataDate).atEndOfMonth().atTime(23, 59, 59));
  694 + final Date monthlyStartTime = DateUtil.localDateTime2Date(evalRankReportBO.getWholeBeginTime().atTime(0, 0, 1));
  695 + List<KpiStageReportNoticeMQ> reportNoticeMQS = new ArrayList<>();
  696 +
  697 + for (EffectEvalStageBO evalStageBO : stages) {
  698 + final LocalDate stageEndTime = evalStageBO.getStageEndTime().isAfter(dataDate)
  699 + ? dataDate : evalStageBO.getStageEndTime();
  700 +
  701 + final Long evalGroupRankStageId = evalStageBO.getEvalGroupRankStageId();
  702 + List<EvalUserPool> userPools = evalUserPoolService.getLeaveOrChangePostPools(evalGroupRankStageId, stageEndTime);
  703 + if (PublicUtil.isEmpty(userPools)) {
  704 + log.info("阶段没有离职调岗员工:{}", JSON.toJSONString(evalStageBO));
  705 + continue;
  706 + }
  707 +
  708 + for (EvalUserPool userPool : userPools) {
  709 + final LocalDate staffLastDate = userPool.getDataDate();
  710 + //阶段时间、阶段累计时间
  711 + //员工离岗时间 与 阶段结束时间判断
  712 + final LocalDate staffStageEndTime = staffLastDate.compareTo(stageEndTime) > 0
  713 + ? stageEndTime : staffLastDate;
  714 + final Date staffStageEndDateTime = DateUtil.localDateTime2Date(staffStageEndTime.atTime(23, 59, 59));
  715 +
  716 + KpiStageMqLog mqLog = this.createLeaveStaffMqLog(userPool, evalRankReportBO, evalStageBO, indicatorCode, evalCalcId, staffStageEndTime);
  717 + KpiStageReportNoticeMQ noticeMQ = KpiStageReportNoticeMQ.builder()
  718 + .indicatorCode(mqLog.getIndicatorCode())
  719 + .shopIds(new ArrayList<Long>(){{add(userPool.getShopId());}})
  720 + .userIds(new ArrayList<Long>(){{add(userPool.getUserId());}})
  721 + .groupId(mqLog.getGroupId())
  722 + .build();
  723 + List<KpiStageReportNoticeMQ.ReportDate> reportStages = new ArrayList<>();
  724 + KpiStageReportNoticeMQ.ReportDate reportStage = noticeMQ.new ReportDate(IndicatorReportTypeEnum.STAGE.getValue(),
  725 + DateUtil.localDateTime2Date(evalStageBO.getStageBeginTime().atTime(0, 0, 1)),
  726 + staffStageEndDateTime,
  727 + DateUtil.localDateTime2Date(evalStageBO.getStageEndTime().atTime(23, 59, 59))
  728 + );
  729 + reportStages.add(reportStage);
  730 + mqLog.setStatus(KpiStageMqLogStatusEnum.WAIT_REPORT);
  731 + mqLog.setStageTimeStr(JSON.toJSONString(reportStages));
  732 + kpiStageMqLogService.save(mqLog);
  733 + KpiStageReportNoticeMQ.ReportDate monthly = noticeMQ.new ReportDate(IndicatorReportTypeEnum.WHOLE.getValue(),
  734 + monthlyStartTime,
  735 + staffStageEndDateTime,
  736 + monthlyEndTime
  737 + );
  738 + noticeMQ.setWhole(monthly);
  739 + noticeMQ.setStages(reportStages);
  740 + noticeMQ.setUid(mqLog.getId().toString());
  741 +
  742 + reportNoticeMQS.add(noticeMQ);
  743 + //1. 初始状态放入
  744 + stringRedisTemplate.opsForHash().put(
  745 + evalCalculationVal.getMqCodeLogStatusKey(mqLog.getEvalCalcId()),
  746 + mqLog.getIndicatorCode(),
  747 + String.valueOf(mqLog.getStatus().getValue())
  748 + );
  749 + //设置过期
  750 + stringRedisTemplate.expire(
  751 + evalCalculationVal.getMqCodeLogStatusKey(mqLog.getEvalCalcId()),
  752 + 6L, TimeUnit.HOURS);
  753 + log.info("1. 初始状态放入 redis K: {},HK: {},HV: {},24H后过期",
  754 + evalCalculationVal.getMqCodeLogStatusKey(mqLog.getEvalCalcId()),
  755 + mqLog.getIndicatorCode(),
  756 + mqLog.getStatus().getValue()
  757 + );
  758 + }
  759 + }
  760 + return reportNoticeMQS;
492 761 }
493 762  
494   - public KpiStageMqLog createMqLog(EvalRankReportBO evalRankReportBO, List<EffectEvalStageBO> stageIndicators, String indicatorCode, Long evalCalcId, LocalDate dataDate) {
  763 + public KpiStageMqLog createMqLog(EvalRankReportBO evalRankReportBO, EffectEvalStageBO stageBO, String indicatorCode, Long evalCalcId, LocalDate dataDate) {
495 764 final LocalDate wholeBeginTime = evalRankReportBO.getWholeBeginTime();
496   - final Long groupId = stageIndicators.stream().findFirst().get().getGroupId();
  765 + final Long groupId = stageBO.getGroupId();
497 766  
498 767 KpiStageMqLog mqLog = new KpiStageMqLog();
499 768 mqLog.setIndicatorCode(indicatorCode);
... ... @@ -507,21 +776,38 @@ public class EvalCalculateTaskService {
507 776 return mqLog;
508 777 }
509 778  
  779 + public KpiStageMqLog createLeaveStaffMqLog(EvalUserPool evalUserPool, EvalRankReportBO evalRankReportBO, EffectEvalStageBO stageBO, String indicatorCode, Long evalCalcId, LocalDate dataDate) {
  780 + final LocalDate wholeBeginTime = evalRankReportBO.getWholeBeginTime();
  781 + final Long groupId = stageBO.getGroupId();
  782 +
  783 + KpiStageMqLog mqLog = new KpiStageMqLog();
  784 + mqLog.setIndicatorCode(indicatorCode);
  785 + mqLog.setWholeBeginTime(wholeBeginTime);
  786 + mqLog.setWholeEndTime(dataDate);
  787 + mqLog.setEvalCalcId(evalCalcId);
  788 + mqLog.setDataDate(dataDate);
  789 + mqLog.setGroupId(groupId);
  790 + mqLog.setUserIds(new ArrayList<Long>(){{add(evalUserPool.getUserId());}});
  791 + mqLog.setShopIds(new ArrayList<Long>(){{add(evalUserPool.getShopId());}});
  792 + return mqLog;
  793 + }
  794 +
510 795 public void checkExtractStageIndicatorTimeOut() {
511 796 Lock lock = distributedLocker.lock(evalCalculationVal.getCheckExtractStageTimeOutKey());
512 797 if (!((RLock) lock).isLocked()) {
513 798 return;
514 799 }
515 800 try {
  801 + List<LocalDate> calcDates = this.getCheckTimeOutCalcDates();
516 802 //还在收集数据
517 803 List<EvalCalc> evalCalcs = evalCalcService.list(Wrappers.<EvalCalc>lambdaQuery()
518   - .eq(EvalCalc::getCalcDate, LocalDate.now().minusDays(1))
  804 + .in(EvalCalc::getCalcDate, calcDates)
519 805 .le(EvalCalc::getStageReportDeadline, LocalDateTime.now())
520 806 .eq(EvalCalc::getStatus, EvalCalcStatusEnum.COLLECT_STAGE_DATA)
521 807 .eq(EvalCalc::getYn, Boolean.TRUE)
522 808 );
523 809 for (EvalCalc evalCalc : evalCalcs) {
524   - cacheCalcGroupIds(evalCalc.getId(), evalCalc.getEvalGroupRankId(), new HashSet<>(evalCalc.getEvalGroupIds()), evalCalc.getCalcDate());
  810 + cacheCalcGroupIds(evalCalc.getId(), evalCalc.getEvalGroupRankId(), evalCalc.getCalcDate());
525 811 evalCalcService.modifyStatus(evalCalc.getId(), EvalCalcStatusEnum.CALC_EVAL);
526 812 stringRedisTemplate.delete(evalCalculationVal.getMqCodeLogStatusKey(evalCalc.getId()));
527 813 }
... ... @@ -533,8 +819,8 @@ public class EvalCalculateTaskService {
533 819  
534 820 }
535 821  
536   - private void cacheCalcGroupIds(final Long evalCalcId, final Long evalGroupRankId, final Set<Long> evalGroupIds, final LocalDate localDate) {
537   - String json = JSONObject.toJSONString(new EvalGroupCalculableBO(evalCalcId, evalGroupRankId, evalGroupIds, localDate));
  822 + private void cacheCalcGroupIds(final Long evalCalcId, final Long evalGroupRankId, final LocalDate localDate) {
  823 + String json = JSONObject.toJSONString(new EvalGroupCalculableBO(evalCalcId, evalGroupRankId, localDate));
538 824 stringRedisTemplate.opsForSet().add(evalCalculationVal.getCacheCalculation(), json);
539 825 }
540 826  
... ... @@ -577,7 +863,7 @@ public class EvalCalculateTaskService {
577 863 evalCalc.setStatus(EvalCalcStatusEnum.CALC_EVAL);
578 864 evalCalcService.save(evalCalc);
579 865 evalCalcs.add(evalCalc);
580   - String json = JSONObject.toJSONString(new EvalGroupCalculableBO(evalCalc.getId(), evalGroupRankId, evalGroupIds, localDate));
  866 + String json = JSONObject.toJSONString(new EvalGroupCalculableBO(evalCalc.getId(), evalGroupRankId, localDate));
581 867 stringRedisTemplate.opsForSet().add(evalCalculationVal.getCacheCalculation(), json);
582 868 }
583 869 if (Boolean.TRUE.equals(distReward)) {
... ... @@ -624,7 +910,7 @@ public class EvalCalculateTaskService {
624 910 evalCalc.setYn(Boolean.TRUE);
625 911 evalCalc.setStatus(EvalCalcStatusEnum.CALC_EVAL);
626 912 evalCalcService.save(evalCalc);
627   - String json = JSONObject.toJSONString(new EvalGroupCalculableBO(evalCalc.getId(), evalGroupRankId, evalGroupIds, localDate));
  913 + String json = JSONObject.toJSONString(new EvalGroupCalculableBO(evalCalc.getId(), evalGroupRankId, localDate));
628 914 stringRedisTemplate.opsForSet().add(evalCalculationVal.getCacheCalculation(), json);
629 915 }
630 916  
... ... @@ -788,6 +1074,25 @@ public class EvalCalculateTaskService {
788 1074 }
789 1075 }
790 1076  
  1077 + public List<LocalDate> getCheckTimeOutCalcDates() {
  1078 + List<LocalDate> calcDates = new ArrayList<LocalDate>() {{
  1079 + add(LocalDate.now());
  1080 + add(LocalDate.now().minusDays(1));
  1081 + add(LocalDate.now().minusDays(2));
  1082 + add(LocalDate.now().minusDays(3));
  1083 + add(LocalDate.now().minusDays(4));
  1084 + add(LocalDate.now().minusDays(5));
  1085 + add(LocalDate.now().minusDays(6));
  1086 + add(LocalDate.now().minusDays(7));
  1087 + add(LocalDate.now().minusDays(8));
  1088 + add(LocalDate.now().minusDays(9));
  1089 + add(LocalDate.now().minusDays(10));
  1090 + add(LocalDate.now().minusDays(11));
  1091 + add(LocalDate.now().minusDays(12));
  1092 + }};
  1093 + return calcDates;
  1094 + }
  1095 +
791 1096 }
792 1097  
793 1098  
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/eval/EvalGroupUserBizService.java
... ... @@ -7,6 +7,7 @@ import cn.fw.morax.domain.db.eval.EvalUserPool;
7 7 import cn.fw.morax.domain.dto.IgnoreCauseDTO;
8 8 import cn.fw.morax.domain.dto.IgnoreCauseReqDTO;
9 9 import cn.fw.morax.domain.dto.query.ShopsPostsQueryDTO;
  10 +import cn.fw.morax.domain.enums.SalaryStaffStatusEnum;
10 11 import cn.fw.morax.domain.vo.eval.EvalGroupUserVO;
11 12 import cn.fw.morax.rpc.ehr.EhrRpcService;
12 13 import cn.fw.morax.rpc.ehr.dto.PerformanceStaffDTO;
... ... @@ -81,11 +82,13 @@ public class EvalGroupUserBizService {
81 82 user.setEvalGroupRankStageId(evalGroup.getEvalGroupRankStageId());
82 83 user.setEvalGroupId(evalGroup.getId());
83 84 user.setEgc(evalGroup.getEgc());
84   - //如果忽略 更新表数据
  85 + //阶段按照时间范围计算,25号离职不参与考评,1-10,11-20号继续参与考评计算 13号调岗
85 86 if (Boolean.TRUE.equals(user.getIgnored())) {
86 87 //不纳入绩效后,当月整个考评排名组的考评池设置为不参与绩效考核(张三 2月20号申请次月参与考核,20号之前的所有阶段 设置不参与绩效考核)
87 88 List<EvalUserPool> pools = evalUserPoolService.list(Wrappers.<EvalUserPool>lambdaQuery()
88   - .eq(EvalUserPool::getEvalGroupRankId, user.getEvalGroupRankId())
  89 + .eq(EvalUserPool::getEvalGroupRankStageId, user.getEvalGroupRankStageId())
  90 + //之前更新整个考评
  91 +// .eq(EvalUserPool::getEvalGroupRankId, user.getEvalGroupRankId())
89 92 .eq(EvalUserPool::getMonthly, YearMonth.from(localDate))
90 93 .eq(EvalUserPool::getUserId, user.getUserId())
91 94 .eq(EvalUserPool::getInclusion, Boolean.TRUE)
... ... @@ -189,6 +192,7 @@ public class EvalGroupUserBizService {
189 192 */
190 193 public void handleStaffKpi(PerformanceStaffDTO staff, EvalGroupUser evalUser, IgnoreCauseReqDTO rejectCauseReq) {
191 194 try {
  195 + evalUser.setStaffStatus(SalaryStaffStatusEnum.ofValue(staff.getStaffStatus()));
192 196 //获取忽略绩效理由
193 197 IgnoreCauseDTO ignoreCauseDTO = commonService.findIgnoreCauseDTO(staff, rejectCauseReq);
194 198  
... ... @@ -267,6 +271,9 @@ public class EvalGroupUserBizService {
267 271 if (PublicUtil.isNotEmpty(now)) {
268 272 evalGroupUser.setDataDate(now);
269 273 }
  274 + if (PublicUtil.isNotEmpty(staff.getLeaveDate())) {
  275 + evalGroupUser.setLeaveDate(staff.getLeaveDate());
  276 + }
270 277 return evalGroupUser;
271 278 }
272 279  
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/eval/EvalPoolCommonService.java
... ... @@ -180,6 +180,69 @@ public class EvalPoolCommonService {
180 180 return userPool;
181 181 }
182 182  
  183 +// @Transactional(rollbackFor = Exception.class)
  184 + public void createUserPools(List<EvalGroupUser> users, EvalScopeEnum scopeType) {
  185 + for (EvalGroupUser user : Optional.ofNullable(users).orElse(new ArrayList<>())) {
  186 + this.createUserPool(user, scopeType);
  187 + }
  188 + }
  189 +
  190 + /**
  191 + * 查询薪酬池
  192 + *
  193 + * @param user
  194 + * @return
  195 + */
  196 +// @Transactional(rollbackFor = Exception.class)
  197 + public void createUserPool(EvalGroupUser user, EvalScopeEnum scopeType) {
  198 + EvalPoolBusinessTypeEnum businessType = EvalScopeEnum.MANAGEMENT.equals(scopeType)
  199 + ? EvalPoolBusinessTypeEnum.REWARD : EvalPoolBusinessTypeEnum.SCORE_REWARD;
  200 +
  201 + EvalUserPool evalUserPool = evalUserPoolService.getOne(Wrappers.<EvalUserPool>lambdaQuery()
  202 + .eq(EvalUserPool::getEvalGroupRankStageId, user.getEvalGroupRankStageId())
  203 + .eq(EvalUserPool::getUserId, user.getUserId())
  204 + .eq(EvalUserPool::getPostId, user.getPostId())
  205 + .eq(EvalUserPool::getShopId, user.getShopId())
  206 + .eq(EvalUserPool::getBusinessType, businessType)
  207 + .eq(EvalUserPool::getMonthly, YearMonth.from(user.getDataDate()))
  208 + .eq(EvalUserPool::getYn, Boolean.TRUE)
  209 + , Boolean.FALSE);
  210 + if (PublicUtil.isNotEmpty(evalUserPool)) {
  211 + Boolean inclusion = Boolean.TRUE.equals(user.getIgnored()) ? Boolean.FALSE : Boolean.TRUE;
  212 + evalUserPool.setInclusion(inclusion);
  213 + //不纳入计算,奖惩清空
  214 + if (Boolean.FALSE.equals(inclusion)) {
  215 + evalUserPool.setReward(BigDecimal.ZERO);
  216 + evalUserPool.setRank(null);
  217 + }
  218 + evalUserPool.setDataDate(user.getDataDate());
  219 + evalUserPoolService.updateById(evalUserPool);
  220 + return;
  221 + }
  222 + //同一个考评组的 调岗员工 修改调岗数据(调岗同岗位,合并数据,不同岗位,两条数据)
  223 + evalUserPool = evalUserPoolService.getOne(Wrappers.<EvalUserPool>lambdaQuery()
  224 + .eq(EvalUserPool::getEvalGroupRankStageId, user.getEvalGroupRankStageId())
  225 + .eq(EvalUserPool::getEvalGroupId, user.getEvalGroupId())
  226 + .eq(EvalUserPool::getUserId, user.getUserId())
  227 + .eq(EvalUserPool::getPostId, user.getPostId())
  228 + .eq(EvalUserPool::getBusinessType, businessType)
  229 + .eq(EvalUserPool::getMonthly, YearMonth.from(user.getDataDate()))
  230 + .eq(EvalUserPool::getYn, Boolean.TRUE)
  231 + , Boolean.FALSE);
  232 + if (PublicUtil.isNotEmpty(evalUserPool)) {
  233 + evalUserPool.setPostId(user.getPostId());
  234 + evalUserPool.setPostName(user.getPostName());
  235 + evalUserPool.setShopId(user.getShopId());
  236 + evalUserPool.setShopName(user.getShopName());
  237 + if (PublicUtil.isNotEmpty(user.getEgc())) {
  238 + evalUserPool.setEgc(user.getEgc());
  239 + }
  240 + evalUserPoolService.updateById(evalUserPool);
  241 + return;
  242 + }
  243 + this.createUserPoolData(user, scopeType);
  244 + }
  245 +
183 246 /**
184 247 * 获取员工社保公积金门店
185 248 *
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/kpi/KpiCacheService.java
... ... @@ -10,7 +10,9 @@ import cn.fw.morax.domain.db.kpi.*;
10 10 import cn.fw.morax.domain.enums.KpiCalcProcessStatusEnum;
11 11 import cn.fw.morax.domain.enums.KpiCalcStatusEnum;
12 12 import cn.fw.morax.rpc.ehr.EhrRpcService;
  13 +import cn.fw.morax.rpc.ehr.dto.PostInfoDTO;
13 14 import cn.fw.morax.rpc.erp.ErpRpcService;
  15 +import cn.fw.morax.rpc.erp.dto.RoleInfoDTO;
14 16 import cn.fw.morax.rpc.erp.dto.UserAuthRangeDTO;
15 17 import cn.fw.morax.rpc.oop.OopRpcService;
16 18 import cn.fw.morax.rpc.oop.dto.GroupDTO;
... ... @@ -22,6 +24,7 @@ import com.alibaba.fastjson.JSONObject;
22 24 import com.baomidou.mybatisplus.core.toolkit.Wrappers;
23 25 import lombok.RequiredArgsConstructor;
24 26 import lombok.extern.slf4j.Slf4j;
  27 +import org.apache.commons.collections.CollectionUtils;
25 28 import org.redisson.api.RLock;
26 29 import org.springframework.data.redis.core.StringRedisTemplate;
27 30 import org.springframework.stereotype.Service;
... ... @@ -43,6 +46,7 @@ public class KpiCacheService {
43 46  
44 47 private KpiAssessPenaltyStaffService kpiAssessPenaltyStaffService;
45 48 private KpiAssessPenaltyService kpiAssessPenaltyService;
  49 + private KpiAssessDetailService kpiAssessDetailService;
46 50 private KpiCalcProcessService kpiCalcProcessService;
47 51 private KpiGroupRankService kpiGroupRankService;
48 52 private StringRedisTemplate stringRedisTemplate;
... ... @@ -53,6 +57,7 @@ public class KpiCacheService {
53 57 private KpiCalcService kpiCalcService;
54 58 private OopRpcService oopRpcService;
55 59 private ErpRpcService erpRpcService;
  60 + private EhrRpcService ehrRpcService;
56 61 private RoleVal roleVal;
57 62 private KpiVal kpiVal;
58 63 private Map<KpiCalcProcessStatusEnum, KpiCalcProcessStrategy> processCalcMap;
... ... @@ -60,6 +65,7 @@ public class KpiCacheService {
60 65 public KpiCacheService(final KpiAssessPenaltyStaffService kpiAssessPenaltyStaffService,
61 66 final KpiAssessPenaltyService kpiAssessPenaltyService,
62 67 final KpiCalcProcessService kpiCalcProcessService,
  68 + final KpiAssessDetailService kpiAssessDetailService,
63 69 final KpiGroupRankService kpiGroupRankService,
64 70 final StringRedisTemplate stringRedisTemplate,
65 71 final DistributedLocker distributedLocker,
... ... @@ -69,12 +75,14 @@ public class KpiCacheService {
69 75 final KpiCalcService kpiCalcService,
70 76 final OopRpcService oopRpcService,
71 77 final ErpRpcService erpRpcService,
  78 + final EhrRpcService ehrRpcService,
72 79 final RoleVal roleVal,
73 80 final KpiVal kpiVal,
74 81 final List<KpiCalcProcessStrategy> kpiCalcProcessStrategies) {
75 82 this.kpiAssessPenaltyStaffService = kpiAssessPenaltyStaffService;
76 83 this.kpiAssessPenaltyService = kpiAssessPenaltyService;
77 84 this.kpiCalcProcessService = kpiCalcProcessService;
  85 + this.kpiAssessDetailService = kpiAssessDetailService;
78 86 this.kpiGroupRankService = kpiGroupRankService;
79 87 this.stringRedisTemplate = stringRedisTemplate;
80 88 this.distributedLocker = distributedLocker;
... ... @@ -84,6 +92,7 @@ public class KpiCacheService {
84 92 this.kpiCalcService = kpiCalcService;
85 93 this.oopRpcService = oopRpcService;
86 94 this.erpRpcService = erpRpcService;
  95 + this.ehrRpcService = ehrRpcService;
87 96 this.roleVal = roleVal;
88 97 this.kpiVal = kpiVal;
89 98 this.processCalcMap = kpiCalcProcessStrategies.stream().collect(Collectors.toMap(KpiCalcProcessStrategy::getStatus, v -> v));
... ... @@ -117,6 +126,8 @@ public class KpiCacheService {
117 126  
118 127 //删除人员质量评测重复数据
119 128 List<KpiAssess> kpiAssesses = kpiAssessService.getGroupConfigs(calcGroupId, calcDate, calcBackupAssess);
  129 + //要计算人员质量评测的管理岗位
  130 + Set<Long> managePostIds = this.getCalcKpiAssessManagePostIds(calcGroupId, kpiAssesses);
120 131 this.cleanRepeatPenalty(kpiAssesses, calcDate, calcBackupAssess);
121 132  
122 133 //人事绩效排名组
... ... @@ -136,17 +147,24 @@ public class KpiCacheService {
136 147 kpiCalc.setCalcBackupAssess(calcBackupAssess);
137 148 kpiCalc.setIgnoreExtraUser(ignoreExtraUser);
138 149 kpiCalcService.save(kpiCalc);
139   - if (PublicUtil.isNotEmpty(kpiAssesses)) {
140   - //分类
141   - if (hrKpiGroupRankIds.contains(kpiGroupRankId)) {
142   - hrKpiCalcs.add(kpiCalc);
143   - } else if (Boolean.TRUE.equals(calcAssess)) {
144   - assessKpiCalcs.add(kpiCalc);
145   - } else {
  150 + //人员质量评测为空 都归为
  151 + if (PublicUtil.isEmpty(kpiAssesses)) {
  152 + noAssessKpiCalcs.add(kpiCalc);
  153 + continue;
  154 + }
  155 + //人事绩效组
  156 + if (hrKpiGroupRankIds.contains(kpiGroupRankId)) {
  157 + hrKpiCalcs.add(kpiCalc);
  158 + continue;
  159 + }
  160 + //计算人员质量评测
  161 + if (Boolean.TRUE.equals(calcAssess)) {
  162 + assessKpiCalcs.add(kpiCalc);
  163 + //要计算人员质量评测的管理岗位 最终还需要再计算一次
  164 + if (CollectionUtils.containsAny(managePostIds, kpiGroupRank.getPostIds())) {
146 165 noAssessKpiCalcs.add(kpiCalc);
147 166 }
148 167 } else {
149   - //人员质量评测为空 都归为
150 168 noAssessKpiCalcs.add(kpiCalc);
151 169 }
152 170 }
... ... @@ -467,4 +485,30 @@ public class KpiCacheService {
467 485 }
468 486 }
469 487  
  488 + /**
  489 + * 获取要计算人员质量评测的管理岗位
  490 + */
  491 + public Set<Long> getCalcKpiAssessManagePostIds(Long groupId, List<KpiAssess> kpiAssesses) {
  492 + List<RoleInfoDTO> manageRoles = erpRpcService.manageRoles();
  493 + if (PublicUtil.isEmpty(manageRoles) || PublicUtil.isEmpty(kpiAssesses)) {
  494 + return new HashSet<>();
  495 + }
  496 + List<KpiAssessDetail> kpiAssessDetails = kpiAssessDetailService.list(Wrappers.<KpiAssessDetail>lambdaQuery()
  497 + .in(KpiAssessDetail::getKpiAssessId, kpiAssesses.stream().map(KpiAssess::getId).collect(Collectors.toSet()))
  498 + .eq(KpiAssessDetail::getYn, Boolean.TRUE)
  499 + );
  500 + Set<String> kpiAssessRoleCodes = kpiAssessDetails.stream().flatMap(detail -> detail.getRoleCodes().stream()).collect(Collectors.toSet());
  501 + Set<String> manageRoleCodes = manageRoles.stream().map(RoleInfoDTO::getRoleCode).collect(Collectors.toSet());
  502 +
  503 + List<PostInfoDTO> groupPostInfos = ehrRpcService.getGroupPosts(groupId);
  504 + Set<Long> calcKpiAssessManagePostIds = new HashSet<>();
  505 + for (PostInfoDTO postInfoDTO : groupPostInfos) {
  506 + //角色在 管理角色 人员质量考核角色 中
  507 + if (manageRoleCodes.contains(postInfoDTO.getRoleCode()) && kpiAssessRoleCodes.contains(postInfoDTO.getRoleCode())) {
  508 + calcKpiAssessManagePostIds.add(postInfoDTO.getId());
  509 + }
  510 + }
  511 + return calcKpiAssessManagePostIds;
  512 + }
  513 +
470 514 }
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/kpi/KpiCalculateService.java
... ... @@ -240,13 +240,13 @@ public class KpiCalculateService {
240 240 List<KpiPoolIndicatorValue> poolIndicatorValueList = new ArrayList<>();
241 241 for (KpiIndicatorBO kpiIndicatorBO : kpiIndicatorBos) {
242 242 //2024年3月开始检查 指标是否需要判断授权
243   -// if (kpiPool.getMonthly().compareTo(Constant.CHECK_HAS_INDICATOR_ROLE_START_MONTH) >= 0 && Boolean.TRUE.equals(kpiIndicatorBO.getCheckHasIndicatorRole())) {
244   -// //员工是否有指标角色授权,有才进行考核,没有跳过不考核
245   -// if (! kpiIndicatorBO.getRoleAuthUserIds().contains(user.getUserId())) {
246   -// log.info("用户没有角色授权记录:{}", JSON.toJSONString(user));
247   -// continue;
248   -// }
249   -// }
  243 + if (kpiPool.getMonthly().compareTo(Constant.CHECK_HAS_INDICATOR_ROLE_START_MONTH) >= 0 && Boolean.TRUE.equals(kpiIndicatorBO.getCheckHasIndicatorRole())) {
  244 + //员工是否有指标角色授权,有才进行考核,没有跳过不考核
  245 + if (! kpiIndicatorBO.getRoleAuthUserIds().contains(user.getUserId())) {
  246 + log.info("用户没有角色授权记录:{}", JSON.toJSONString(user));
  247 + continue;
  248 + }
  249 + }
250 250 calcKpiGroupIndicatorIds.add(kpiIndicatorBO.getKpiGroupIndicatorId());
251 251 KpiAbsBaseCalculator calculator = calculatorMap.get(kpiIndicatorBO.getScoreWay());
252 252 if (calculator == null) {
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/kpi/KpiGroupUserTaskService.java
... ... @@ -147,9 +147,8 @@ public class KpiGroupUserTaskService {
147 147 kpiGroupUserService.insertBatchSomeColumn(kpiGroupUsersForSave);
148 148 }
149 149  
150   -// Set<Long> userIds = kpiGroupUsersForSave.stream().map(KpiGroupUser::getUserId).collect(Collectors.toSet());
151 150 //保存用户角色授权日志
152   -// this.saveUserRoleAuthLogs(groupId, calcDate, kpiGroupIds, shopIds);
  151 + this.saveUserRoleAuthLogs(groupId, calcDate, kpiGroupIds, shopIds);
153 152  
154 153 //缓存计算绩效
155 154 kpiCacheService.cacheCalcKpi(extractUserBO, groupId);
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/kpi/KpiPoolBizService.java
... ... @@ -1808,9 +1808,16 @@ public class KpiPoolBizService {
1808 1808 for (KpiPoolVO kpiPoolVO : kpiPoolVOS) {
1809 1809 //处理得分率 乘以 100
1810 1810 kpiPoolVO.setKpiScoreRatio(Optional.ofNullable(kpiPoolVO.getKpiScoreRatio()).orElse(BigDecimal.ZERO).multiply(Constant.ONE_HUNDRED));
1811   - kpiPoolVO.setLastOneKpiScoreRatio(Optional.ofNullable(kpiPoolVO.getLastOneKpiScoreRatio()).orElse(BigDecimal.ZERO).multiply(Constant.ONE_HUNDRED));
1812   - kpiPoolVO.setLastTwoKpiScoreRatio(Optional.ofNullable(kpiPoolVO.getLastTwoKpiScoreRatio()).orElse(BigDecimal.ZERO).multiply(Constant.ONE_HUNDRED));
1813   - kpiPoolVO.setAverageKpiScoreRatio(Optional.ofNullable(kpiPoolVO.getAverageKpiScoreRatio()).orElse(BigDecimal.ZERO).multiply(Constant.ONE_HUNDRED));
  1811 + //上两月绩效不参与考核就不展示
  1812 + if (PublicUtil.isNotEmpty(kpiPoolVO.getLastOneKpiScoreRatio())) {
  1813 + kpiPoolVO.setLastOneKpiScoreRatio(kpiPoolVO.getLastOneKpiScoreRatio().multiply(Constant.ONE_HUNDRED));
  1814 + }
  1815 + if (PublicUtil.isNotEmpty(kpiPoolVO.getLastTwoKpiScoreRatio())) {
  1816 + kpiPoolVO.setLastTwoKpiScoreRatio(kpiPoolVO.getLastTwoKpiScoreRatio().multiply(Constant.ONE_HUNDRED));
  1817 + }
  1818 + if (PublicUtil.isNotEmpty(kpiPoolVO.getAverageKpiScoreRatio())) {
  1819 + kpiPoolVO.setAverageKpiScoreRatio(kpiPoolVO.getAverageKpiScoreRatio().multiply(Constant.ONE_HUNDRED));
  1820 + }
1814 1821 //默认无比较者
1815 1822 kpiPoolVO.setMonthRankHasCompete(Boolean.FALSE);
1816 1823 kpiPoolVO.setRankHasCompete(Boolean.FALSE);
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/kpi/KpiPoolCommonService.java
... ... @@ -89,7 +89,7 @@ public class KpiPoolCommonService {
89 89 .eq(KpiPool::getYn, Boolean.TRUE)
90 90 , Boolean.FALSE);
91 91 if (PublicUtil.isEmpty(kpiPool)) {
92   - log.error("绩效数据不存在,用户:{}", JSON.toJSONString(user));
  92 +// log.error("绩效数据不存在,用户:{}", JSON.toJSONString(user));
93 93 // throw new BusinessException("用户[" + user.getUserId() + "]的绩效数据不存在");
94 94 }
95 95 return Optional.ofNullable(kpiPool);
... ... @@ -110,7 +110,7 @@ public class KpiPoolCommonService {
110 110 .eq(KpiPool::getYn, Boolean.TRUE)
111 111 , Boolean.FALSE);
112 112 if (PublicUtil.isEmpty(kpiPool)) {
113   - log.error("绩效数据不存在,薪酬池:{}", JSON.toJSONString(pool));
  113 +// log.error("绩效数据不存在,薪酬池:{}", JSON.toJSONString(pool));
114 114 // throw new BusinessException("用户[" + pool.getUserId() + "]的绩效数据不存在");
115 115 }
116 116 return kpiPool;
... ... @@ -128,7 +128,7 @@ public class KpiPoolCommonService {
128 128 .eq(KpiPool::getYn, Boolean.TRUE)
129 129 , Boolean.FALSE);
130 130 if (PublicUtil.isEmpty(kpiPool)) {
131   - log.error("绩效数据不存在,薪酬池:{}", JSON.toJSONString(pool));
  131 +// log.error("绩效数据不存在,薪酬池:{}", JSON.toJSONString(pool));
132 132 // throw new BusinessException("用户[" + pool.getUserId() + "]的绩效数据不存在");
133 133 }
134 134 return kpiPool;
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/kpi/KpiReportBizService.java
... ... @@ -11,6 +11,7 @@ import cn.fw.morax.domain.db.CombineIndicator;
11 11 import cn.fw.morax.domain.db.IndicatorSortConfig;
12 12 import cn.fw.morax.domain.db.eval.EvalIndicator;
13 13 import cn.fw.morax.domain.db.kpi.*;
  14 +import cn.fw.morax.domain.dto.kpi.KpiGroupDTO;
14 15 import cn.fw.morax.domain.dto.kpi.KpiGroupInfoDTO;
15 16 import cn.fw.morax.domain.enums.*;
16 17 import cn.fw.morax.domain.event.ReCalcKpiReportEvent;
... ... @@ -202,10 +203,11 @@ public class KpiReportBizService {
202 203 return;
203 204 }
204 205 //查询当月最后一条数据,包括离职的
205   - LocalDate startTime = date.with(TemporalAdjusters.firstDayOfMonth());
206   - LocalDate endTime = date.with(TemporalAdjusters.lastDayOfMonth());
207   - List<KpiGroupUser> kpiGroupUserLastOneList = kpiGroupUserService.getKpiGroupUserLastOneList(startTime, endTime, groupId);
208   - Map<Long, KpiGroupUser> longKpiGroupUserMap = kpiGroupUserLastOneList.stream().collect(Collectors.toMap(KpiGroupUser::getUserId, Function.identity(), (v1, v2) -> v1));
  206 +// LocalDate startTime = date.with(TemporalAdjusters.firstDayOfMonth());
  207 +// LocalDate endTime = date.with(TemporalAdjusters.lastDayOfMonth());
  208 +// List<KpiGroupUser> kpiGroupUserLastOneList = kpiGroupUserService.getKpiGroupUserLastOneList(startTime, endTime, groupId);
  209 +// Map<Long, KpiGroupUser> longKpiGroupUserMap = kpiGroupUserLastOneList.stream().collect(Collectors.toMap(KpiGroupUser::getUserId, Function.identity(), (v1, v2) -> v1));
  210 + Map<Long, KpiGroupUser> longKpiGroupUserMap = this.getShopPostLastKpiUsers(kpiGroups, date, pools);
209 211 //保存 报表绩效排名组 信息
210 212 ReportKpiRank reportKpiRank = saveReportKpiRank(kpiGroupRank, groupId, date, kpiGroups, kpiGroupIds);
211 213  
... ... @@ -946,4 +948,26 @@ public class KpiReportBizService {
946 948 }
947 949 return reportKpiDimValue;
948 950 }
  951 +
  952 + /**
  953 + * 获取门店岗位的 绩效人员
  954 + */
  955 + public Map<Long, KpiGroupUser> getShopPostLastKpiUsers(List<KpiGroup> kpiGroups, LocalDate date, List<KpiPool> pools) {
  956 + //查询当月最后一条数据,包括离职的
  957 + LocalDate startTime = date.with(TemporalAdjusters.firstDayOfMonth());
  958 + LocalDate endTime = date.with(TemporalAdjusters.lastDayOfMonth());
  959 +
  960 + Map<Long, KpiGroupUser> userKpiGroupUserMap = new HashMap<>();
  961 + List<Long> shopIds = kpiGroups.stream().map(kpiGroup -> kpiGroup.getShopIds()).distinct().collect(ArrayList::new, List::addAll, List::addAll);
  962 +
  963 + for (KpiPool kpiPool : pools) {
  964 + Long userId = kpiPool.getUserId();
  965 + Long postId = kpiPool.getPostId();
  966 + KpiGroupUser kpiGroupUser = kpiGroupUserService.getMonthLastData(userId, postId, shopIds, startTime, endTime);
  967 + if (PublicUtil.isNotEmpty(kpiGroupUser)) {
  968 + userKpiGroupUserMap.put(userId, kpiGroupUser);
  969 + }
  970 + }
  971 + return userKpiGroupUserMap;
  972 + }
949 973 }
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/kpi/KpiStageIndicatorBizService.java
... ... @@ -102,6 +102,10 @@ public class KpiStageIndicatorBizService {
102 102 final Long evalCalcId = kpiStageMqLog.getEvalCalcId();
103 103  
104 104 EvalCalc evalCalc = evalCalcService.getById(evalCalcId);
  105 + if (PublicUtil.isEmpty(evalCalc) || PublicUtil.isEmpty(evalCalc.getStatus())) {
  106 + log.info("确认完成阶段数据上报 evalCalc为空,evalCalcId:{}", evalCalcId);
  107 + return Message.success();
  108 + }
105 109 //正在收集数据
106 110 if (EvalCalcStatusEnum.COLLECT_STAGE_DATA.equals(evalCalc.getStatus())) {
107 111 //在确认最晚时间之内 完成,其他业务系统可能还没确认
... ... @@ -141,7 +145,7 @@ public class KpiStageIndicatorBizService {
141 145 log.info("当前状态: {}, 无需重复处理!",evalCalc1.getStatus().getValue());
142 146 }else {
143 147 evalCalcService.modifyStatus(evalCalcId, EvalCalcStatusEnum.CALC_EVAL);
144   - cacheCalcGroupIds(evalCalcId, evalCalc.getEvalGroupRankId(), new HashSet<>(evalCalc.getEvalGroupIds()), evalCalc.getCalcDate());
  148 + cacheCalcGroupIds(evalCalcId, evalCalc.getEvalGroupRankId(), evalCalc.getCalcDate());
145 149 }
146 150 stringRedisTemplate.delete(evalCalculationVal.getMqCodeLogStatusKey(kpiStageMqLog.getEvalCalcId()));
147 151 }
... ... @@ -150,8 +154,8 @@ public class KpiStageIndicatorBizService {
150 154 return Message.success();
151 155 }
152 156  
153   - private void cacheCalcGroupIds(final Long evalCalcId, final Long evalGroupRankId, final Set<Long> evalGroupIds, final LocalDate localDate) {
154   - String json = JSONObject.toJSONString(new EvalGroupCalculableBO(evalCalcId, evalGroupRankId, evalGroupIds, localDate));
  157 + private void cacheCalcGroupIds(final Long evalCalcId, final Long evalGroupRankId, final LocalDate localDate) {
  158 + String json = JSONObject.toJSONString(new EvalGroupCalculableBO(evalCalcId, evalGroupRankId, localDate));
155 159 stringRedisTemplate.opsForSet().add(evalCalculationVal.getCacheCalculation(), json);
156 160 }
157 161  
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/biz/salary/SalaryGroupUserBizService.java
... ... @@ -491,7 +491,7 @@ public class SalaryGroupUserBizService {
491 491 * @return
492 492 */
493 493 public List<SalaryGroupUser> fetchRealTimeSalaryGroup(SalaryGroupStaffQueryDTO dto, LocalDate date) {
494   - List<PerformanceStaffDTO> staffs = ehrRpcService.queryKpiStaffByName(dto.getGroupId(), Lists.newArrayList(dto.getPostId()), dto.getShopIds(), dto.getStaffName(), date);
  494 + List<PerformanceStaffDTO> staffs = ehrRpcService.getPointTimeStaffs(dto.getGroupId(), Lists.newArrayList(dto.getPostId()), dto.getShopIds(), dto.getStaffName(), date);
495 495 if (PublicUtil.isEmpty(staffs)) {
496 496 return new ArrayList<>();
497 497 }
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/data/eval/EvalGroupUserService.java
... ... @@ -20,6 +20,8 @@ public interface EvalGroupUserService extends ILocalService&lt;EvalGroupUser&gt; {
20 20  
21 21 EvalGroupUser getMonthLastData(Long evalGroupId, Long userId, YearMonth yearMonth);
22 22  
  23 + EvalGroupUser getMonthStageLastData(Long evalGroupStageId, Long userId, LocalDate startDate, LocalDate endDate);
  24 +
23 25 /**
24 26 * 试用期员工
25 27 *
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/data/eval/EvalUserPoolService.java
... ... @@ -7,6 +7,7 @@ import cn.fw.morax.domain.enums.EvalScopeEnum;
7 7 import cn.fw.morax.domain.vo.eval.EvalUserPoolVO;
8 8 import com.baomidou.mybatisplus.extension.service.IService;
9 9  
  10 +import java.time.LocalDate;
10 11 import java.time.YearMonth;
11 12 import java.util.List;
12 13  
... ... @@ -37,4 +38,12 @@ public interface EvalUserPoolService extends IService&lt;EvalUserPool&gt; {
37 38 List<EvalUserPool> getPools(Long evalGroupRankStageId, YearMonth monthly);
38 39  
39 40 List<EvalUserPool> getRankPools(Long evalGroupRankStageId, YearMonth monthly, EvalScopeEnum scopeType);
  41 +
  42 + /**
  43 + * 获取离职或调岗人员
  44 + * @param evalGroupRankStageId
  45 + * @param monthly
  46 + * @return
  47 + */
  48 + List<EvalUserPool> getLeaveOrChangePostPools(Long evalGroupRankStageId, LocalDate stageEndTime);
40 49 }
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/data/eval/impl/EvalGroupServiceUserImpl.java
... ... @@ -33,6 +33,20 @@ public class EvalGroupServiceUserImpl extends ServiceImpl&lt;EvalGroupUserDao, Eval
33 33 }
34 34  
35 35 @Override
  36 + public EvalGroupUser getMonthStageLastData(Long evalGroupStageId, Long userId, LocalDate startDate, LocalDate endDate) {
  37 + return this.getOne(Wrappers.<EvalGroupUser>lambdaQuery()
  38 + .eq(EvalGroupUser::getEvalGroupRankStageId, evalGroupStageId)
  39 + .eq(EvalGroupUser::getUserId, userId)
  40 + .ge(EvalGroupUser::getDataDate, startDate)
  41 + .le(EvalGroupUser::getDataDate, endDate)
  42 + .eq(EvalGroupUser::getYn, Boolean.TRUE)
  43 + .orderByDesc(EvalGroupUser::getDataDate)
  44 + .last(" limit 1 ")
  45 + , Boolean.FALSE
  46 + );
  47 + }
  48 +
  49 + @Override
36 50 public Boolean probationStaff(Long userId, LocalDate beginTime, LocalDate endTime) {
37 51 List<EvalGroupUser> users = this.list(Wrappers.<EvalGroupUser>lambdaQuery()
38 52 .ge(EvalGroupUser::getDataDate, beginTime)
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/data/eval/impl/EvalUserPoolServiceImpl.java
... ... @@ -14,6 +14,7 @@ import com.baomidou.mybatisplus.core.toolkit.Wrappers;
14 14 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
15 15 import org.springframework.stereotype.Service;
16 16  
  17 +import java.time.LocalDate;
17 18 import java.time.YearMonth;
18 19 import java.util.ArrayList;
19 20 import java.util.List;
... ... @@ -87,4 +88,21 @@ public class EvalUserPoolServiceImpl extends ServiceImpl&lt;EvalUserPoolDao, EvalUs
87 88 );
88 89 return pools;
89 90 }
  91 +
  92 + @Override
  93 + public List<EvalUserPool> getLeaveOrChangePostPools(Long evalGroupRankStageId, LocalDate stageEndTime) {
  94 + if (PublicUtil.isEmpty(evalGroupRankStageId)) {
  95 + return new ArrayList<>();
  96 + }
  97 + YearMonth monthly = YearMonth.from(stageEndTime);
  98 + //在考评期间,但结束日期不是阶段结束日期
  99 + List<EvalUserPool> pools = this.list(Wrappers.<EvalUserPool>lambdaQuery()
  100 + .in(EvalUserPool::getEvalGroupRankStageId, evalGroupRankStageId)
  101 + .eq(EvalUserPool::getMonthly, monthly)
  102 + .ne(EvalUserPool::getDataDate, stageEndTime)
  103 + .eq(EvalUserPool::getBusinessType, EvalPoolBusinessTypeEnum.SCORE_REWARD)
  104 + .eq(EvalUserPool::getYn, Boolean.TRUE)
  105 + );
  106 + return pools;
  107 + }
90 108 }
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/data/kpi/KpiGroupUserService.java
... ... @@ -27,6 +27,13 @@ public interface KpiGroupUserService extends ILocalService&lt;KpiGroupUser&gt; {
27 27 KpiGroupUser getMonthLastData(Set<Long> kpiGroupIds, Long userId, LocalDate startTime, LocalDate endTime);
28 28  
29 29 /**
  30 + * 获取某月最近的绩效组人员数据
  31 + *
  32 + * @return
  33 + */
  34 + KpiGroupUser getMonthLastData(Long userId, Long postId, List<Long> shopIds, LocalDate startTime, LocalDate endTime);
  35 +
  36 + /**
30 37 * 试用期员工
31 38 *
32 39 * @param yearMonth
... ...
fw-morax-service/src/main/java/cn/fw/morax/service/data/kpi/impl/KpiGroupUserServiceImpl.java
... ... @@ -46,6 +46,40 @@ public class KpiGroupUserServiceImpl extends ServiceImpl&lt;KpiGroupUserDao, KpiGro
46 46 , Boolean.FALSE
47 47 );
48 48 }
  49 +
  50 + @Override
  51 + public KpiGroupUser getMonthLastData(Long userId, Long postId, List<Long> shopIds, LocalDate startTime, LocalDate endTime) {
  52 + if (PublicUtil.isEmpty(postId) || PublicUtil.isEmpty(shopIds) || PublicUtil.isEmpty(startTime) || PublicUtil.isEmpty(endTime)) {
  53 + return null;
  54 + }
  55 + //以岗位、门店去搜索绩效人员最新数据
  56 + KpiGroupUser kpiGroupUser = this.getOne(Wrappers.<KpiGroupUser>lambdaQuery()
  57 + .in(KpiGroupUser::getShopId, shopIds)
  58 + .eq(KpiGroupUser::getPostId, postId)
  59 + .eq(KpiGroupUser::getUserId, userId)
  60 + .ge(KpiGroupUser::getDataDate, startTime)
  61 + .le(KpiGroupUser::getDataDate, endTime)
  62 + .eq(KpiGroupUser::getYn, Boolean.TRUE)
  63 + .orderByDesc(KpiGroupUser::getDataDate)
  64 + .last(" limit 1 ")
  65 + , Boolean.FALSE
  66 + );
  67 + if (PublicUtil.isNotEmpty(kpiGroupUser)) {
  68 + return kpiGroupUser;
  69 + }
  70 + //以岗位去搜索绩效人员最新数据
  71 + return this.getOne(Wrappers.<KpiGroupUser>lambdaQuery()
  72 + .eq(KpiGroupUser::getPostId, postId)
  73 + .eq(KpiGroupUser::getUserId, userId)
  74 + .ge(KpiGroupUser::getDataDate, startTime)
  75 + .le(KpiGroupUser::getDataDate, endTime)
  76 + .eq(KpiGroupUser::getYn, Boolean.TRUE)
  77 + .orderByDesc(KpiGroupUser::getDataDate)
  78 + .last(" limit 1 ")
  79 + , Boolean.FALSE
  80 + );
  81 +
  82 + }
49 83 @Override
50 84 public KpiGroupUser getMonthFirstData(Long kpiGroupId, Long userId, YearMonth yearMonth) {
51 85 return this.baseMapper.getMonthFirstData(kpiGroupId, userId, yearMonth);
... ...
lombok.config 0 → 100644
  1 +config.stopBubbling = true
  2 +lombok.accessors.chain=true
  3 +lombok.equalsandhashcode.callsuper=call
  4 +lombok.tostring.callsuper=call
0 5 \ No newline at end of file
... ...
... ... @@ -12,7 +12,7 @@
12 12 <parent>
13 13 <groupId>cn.fw</groupId>
14 14 <artifactId>fw-common-dependencies</artifactId>
15   - <version>3.5.0</version>
  15 + <version>3.6.0</version>
16 16 </parent>
17 17  
18 18 <modules>
... ... @@ -206,11 +206,34 @@
206 206 <artifactId>junit</artifactId>
207 207 <scope>test</scope>
208 208 </dependency>
  209 + <dependency>
  210 + <groupId>org.jetbrains.kotlin</groupId>
  211 + <artifactId>kotlin-stdlib</artifactId>
  212 + <version>${kotlin.version}</version>
  213 + </dependency>
  214 + <dependency>
  215 + <groupId>org.jetbrains.kotlin</groupId>
  216 + <artifactId>kotlin-reflect</artifactId>
  217 + <version>${kotlin.version}</version>
  218 + </dependency>
  219 + <dependency>
  220 + <groupId>org.jetbrains.kotlin</groupId>
  221 + <artifactId>kotlin-stdlib-jdk8</artifactId>
  222 + <version>${kotlin.version}</version>
  223 + </dependency>
  224 + <dependency>
  225 + <groupId>com.fasterxml.jackson.module</groupId>
  226 + <artifactId>jackson-module-kotlin</artifactId>
  227 + </dependency>
209 228 </dependencies>
210 229  
211 230 <build>
212 231 <plugins>
213 232 <plugin>
  233 + <groupId>org.jetbrains.kotlin</groupId>
  234 + <artifactId>kotlin-maven-plugin</artifactId>
  235 + </plugin>
  236 + <plugin>
214 237 <groupId>org.apache.maven.plugins</groupId>
215 238 <artifactId>maven-compiler-plugin</artifactId>
216 239 <configuration>
... ...