| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238 |
- package com.punchsettle.server.service.manager.impl;
- import java.sql.Timestamp;
- import java.time.DayOfWeek;
- import java.time.LocalDate;
- import java.util.ArrayList;
- import java.util.List;
- import java.util.Map;
- import java.util.Objects;
- import java.util.function.Function;
- import java.util.stream.Collectors;
- import org.springframework.beans.factory.annotation.Autowired;
- import org.springframework.stereotype.Service;
- import org.springframework.transaction.annotation.Transactional;
- import org.springframework.util.CollectionUtils;
- import com.punchsettle.server.atomic.entity.PunchIn;
- import com.punchsettle.server.atomic.entity.PunchInRecord;
- import com.punchsettle.server.atomic.entity.PunchInRecordSettlementRela;
- import com.punchsettle.server.atomic.entity.PunchInSettlement;
- import com.punchsettle.server.atomic.entity.SettlementTask;
- import com.punchsettle.server.atomic.entity.User;
- import com.punchsettle.server.atomic.service.IPunchInRecordService;
- import com.punchsettle.server.atomic.service.IPunchInRecordSettlementRelaService;
- import com.punchsettle.server.atomic.service.IPunchInService;
- import com.punchsettle.server.atomic.service.IPunchInSettlementService;
- import com.punchsettle.server.atomic.service.ISettlementTaskService;
- import com.punchsettle.server.atomic.service.IUserService;
- import com.punchsettle.server.dto.punchin.PunchInQuery;
- import com.punchsettle.server.dto.punchin.PunchInRecordQuery;
- import com.punchsettle.server.dto.task.SettleRewardTaskDto;
- import com.punchsettle.server.service.manager.ISettleManager;
- import com.punchsettle.server.utiis.DateUtils;
- import lombok.extern.slf4j.Slf4j;
- /**
- * @author tyuio
- * @version 1.0.0
- * @description 结算服务类
- * @date 2024/12/12 22:29
- */
- @Slf4j
- @Service
- public class SettleManagerImpl implements ISettleManager {
- @Autowired
- private IPunchInService punchInService;
- @Autowired
- private IPunchInRecordService punchInRecordService;
- @Autowired
- private IUserService userService;
- @Autowired
- private IPunchInSettlementService punchInSettlementService;
- @Autowired
- private ISettlementTaskService settlementTaskService;
- @Autowired
- private IPunchInRecordSettlementRelaService punchInRecordSettlementRelaService;
- @Override
- public void settleReward() {
- }
- @Override
- @Transactional(rollbackFor = Exception.class)
- public void settleReward(SettleRewardTaskDto taskDto) {
- if (Objects.isNull(taskDto) || Objects.isNull(taskDto.getSettleDate())) {
- log.info("结算任务异常,原因:没有指定结算日期");
- return;
- }
- log.info("结算任务开始,结算日期:{}, 结算用户:{}", taskDto.getSettleDate(), taskDto.getUserId());
- Timestamp settleStartTime = new Timestamp(System.currentTimeMillis());
- // 获取昨天的日期,
- LocalDate settleDate = LocalDate.parse(taskDto.getSettleDate());
- String settleDateStr = taskDto.getSettleDate();
- // 判断是否是周末
- boolean weekendFlag =
- DayOfWeek.SATURDAY.equals(settleDate.getDayOfWeek()) || DayOfWeek.SUNDAY.equals(settleDate.getDayOfWeek());
- boolean sundayFlag = DayOfWeek.SUNDAY.equals(settleDate.getDayOfWeek());
- PunchInRecordQuery recordQuery = new PunchInRecordQuery();
- recordQuery.setStartDate(settleDateStr);
- recordQuery.setEndDate(settleDateStr);
- List<PunchInRecord> punchInRecords = punchInRecordService.listByCondition(recordQuery);
- if (CollectionUtils.isEmpty(punchInRecords)) {
- log.info("结算任务结束,原因:没有打卡记录");
- return;
- }
- List<Long> userIds = punchInRecords.stream().map(PunchInRecord::getCreatedBy).collect(Collectors.toList());
- // 读取用户的打卡任务
- PunchInQuery punchInQuery = new PunchInQuery();
- punchInQuery.setUserIds(userIds);
- List<PunchIn> punchIns = punchInService.listByCondition(punchInQuery);
- if (CollectionUtils.isEmpty(punchIns)) {
- log.info("结算任务结束,原因:根据打卡记录没有找到打卡任务");
- return;
- }
- // 读取用户奖励数据
- List<User> users = userService.listByIds(userIds);
- if (CollectionUtils.isEmpty(users)) {
- log.info("结算任务结束,原因:没有找到用户奖励信息");
- return;
- }
- // 获取一周的打卡记录
- Map<Long, List<PunchInRecord>> punchInRecordForWeek = Map.of();
- if (sundayFlag) {
- List<Long> punchInIds = punchIns.stream().map(PunchIn::getId).collect(Collectors.toList());
- PunchInRecordQuery recordForWeekQuery = new PunchInRecordQuery();
- recordForWeekQuery.setPunchInIds(punchInIds);
- recordForWeekQuery.setStartDate(DateUtils.getLastWeekMondayStr());
- recordForWeekQuery.setEndDate(DateUtils.getLastWeekSundayStr());
- List<PunchInRecord> punchInRecordForWeeks = punchInRecordService.listByCondition(recordForWeekQuery);
- if (!CollectionUtils.isEmpty(punchInRecordForWeeks)) {
- punchInRecordForWeek =
- punchInRecordForWeeks.stream().collect(Collectors.groupingBy(PunchInRecord::getPunchInId));
- }
- }
- // 打卡任务容器
- Map<Long, PunchIn> punchInMap =
- punchIns.stream().collect(Collectors.toMap(PunchIn::getId, Function.identity(), (key1, key2) -> key1));
- // 用户-打卡记录分组
- Map<Long, List<PunchInRecord>> userPunchInRecordMap =
- punchInRecords.stream().collect(Collectors.groupingBy(PunchInRecord::getCreatedBy));
- // 用户-奖励分组
- Map<Long, User> userRewardMap = users.stream()
- .collect(Collectors.toMap(User::getId, Function.identity(), (key1, key2) -> key1));
- // 先创建结算任务执行记录
- SettlementTask settlementTask = new SettlementTask();
- settlementTask.setSettleDate(settleDateStr);
- settlementTask.setStartTime(settleStartTime);
- settlementTask.setProcessedNum(userPunchInRecordMap.size());
- settlementTaskService.insert(settlementTask);
- // 结算时间
- Timestamp settlementTime = new Timestamp(System.currentTimeMillis());
- List<PunchInSettlement> addPunchInSettlements = new ArrayList<>();
- List<User> updateUsers = new ArrayList<>();
- List<PunchInRecordSettlementRela> punchInRecordSettlementRelas = new ArrayList<>();
- // 有打卡记录的打卡任务则进行结算
- for (Long userId : userPunchInRecordMap.keySet()) {
- // 获取用户打卡记录
- List<PunchInRecord> punchInRecordList = userPunchInRecordMap.get(userId);
- if (CollectionUtils.isEmpty(punchInRecordList)) {
- log.info("用户{}没有打卡记录,无须结算", userId);
- continue;
- }
- // 获取用户打卡奖励
- User user = userRewardMap.get(userId);
- if (Objects.isNull(user)) {
- log.info("用户{}没有奖励信息,无法结算", userId);
- continue;
- }
- // 根据打卡记录上的打卡任务ID获取具体的打卡任务信息进行结算
- int settleRewardNum = 0;
- for (PunchInRecord punchInRecord : punchInRecordList) {
- PunchIn punchIn = punchInMap.get(punchInRecord.getPunchInId());
- if (Objects.isNull(punchIn)) {
- continue;
- }
- // 周末双倍奖励,否则计算普通奖励
- settleRewardNum += weekendFlag ? punchIn.getRewardNum() * 2 : punchIn.getRewardNum();
- // 周日计算一次全勤双倍奖励
- if (sundayFlag && punchIn.getFullAttendanceFlag()) {
- List<PunchInRecord> tempRecordList = punchInRecordForWeek.get(punchInRecord.getPunchInId());
- if (!CollectionUtils.isEmpty(tempRecordList) && tempRecordList.size() >= 6) {
- settleRewardNum += punchIn.getRewardNum() * 2;
- }
- }
- // 构建结算任务与记录关联信息
- PunchInRecordSettlementRela rela = new PunchInRecordSettlementRela();
- rela.setRecordId(punchInRecord.getId());
- rela.setSettlementId(settlementTask.getId());
- punchInRecordSettlementRelas.add(rela);
- }
- // 计算结算前后,用户奖励数的变化
- int beforeSettleRewardNum = user.getUnclaimedRewardNum();
- int afterSettleRewardNum = beforeSettleRewardNum + settleRewardNum;
- int totalRewardNum = user.getTotalRewardNum() + settleRewardNum;
- // 构造结算信息
- PunchInSettlement addPunchInSettlement = new PunchInSettlement();
- addPunchInSettlement.setSettlementTaskId(settlementTask.getId());
- addPunchInSettlement.setUserId(userId);
- addPunchInSettlement.setSettleRewardNum(settleRewardNum);
- addPunchInSettlement.setSettlementTime(settlementTime);
- addPunchInSettlement.setBeforeSettleRewardNum(beforeSettleRewardNum);
- addPunchInSettlement.setAfterSettleRewardNum(afterSettleRewardNum);
- addPunchInSettlements.add(addPunchInSettlement);
- // 构造用户奖励信息
- User updateUser = new User();
- updateUser.setId(user.getId());
- updateUser.setTotalRewardNum(totalRewardNum);
- updateUser.setUnclaimedRewardNum(afterSettleRewardNum);
- updateUsers.add(updateUser);
- }
- // 更新用户奖励信息
- userService.batchUpdateUser(updateUsers);
- // 新增结算信息
- punchInSettlementService.batchInsert(addPunchInSettlements);
- // 构造并新增关联信息
- punchInRecordSettlementRelaService.batchInsert(punchInRecordSettlementRelas);
- // 构造并新增结算任务信息
- settlementTask.setProcessedSettleNum(addPunchInSettlements.size());
- settlementTask
- .setProcessedUnsettleNum(settlementTask.getProcessedNum() - settlementTask.getProcessedSettleNum());
- settlementTask.setEndTime(new Timestamp(System.currentTimeMillis()));
- settlementTaskService.update(settlementTask);
- log.info("结算任务结束");
- }
- }
|