|
@@ -1,30 +1,273 @@
|
|
package com.xjrsoft.module.job;
|
|
package com.xjrsoft.module.job;
|
|
|
|
|
|
|
|
+import cn.hutool.core.util.IdUtil;
|
|
|
|
+import cn.hutool.extra.spring.SpringUtil;
|
|
|
|
+import com.alibaba.fastjson.JSONObject;
|
|
|
|
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
|
|
|
+import com.xjrsoft.common.utils.WeChatUtil;
|
|
|
|
+import com.xjrsoft.module.attendance.entity.AttendanceRuleDetails;
|
|
|
|
+import com.xjrsoft.module.attendance.entity.AttendanceUserRelation;
|
|
|
|
+import com.xjrsoft.module.attendance.mapper.AttendanceUserRelationMapper;
|
|
|
|
+import com.xjrsoft.module.attendance.service.IAttendanceRuleCategoryService;
|
|
|
|
+import com.xjrsoft.module.concat.service.IXjrUserService;
|
|
|
|
+import com.xjrsoft.module.organization.dto.WeChatSendMessageDto;
|
|
|
|
+import com.xjrsoft.module.organization.service.IWeChatService;
|
|
|
|
+import com.xjrsoft.module.system.entity.WechatMessageLog;
|
|
|
|
+import com.xjrsoft.module.system.service.IWechatMessageLogService;
|
|
|
|
+import com.xjrsoft.module.teacher.entity.XjrUser;
|
|
import org.junit.jupiter.api.Test;
|
|
import org.junit.jupiter.api.Test;
|
|
|
|
+import org.springframework.beans.factory.annotation.Autowired;
|
|
|
|
+import org.springframework.boot.test.context.SpringBootTest;
|
|
|
|
|
|
-import java.time.LocalDate;
|
|
|
|
import java.time.LocalDateTime;
|
|
import java.time.LocalDateTime;
|
|
-import java.time.LocalTime;
|
|
|
|
-
|
|
|
|
-import static org.junit.jupiter.api.Assertions.*;
|
|
|
|
|
|
+import java.time.format.DateTimeFormatter;
|
|
|
|
+import java.time.temporal.ChronoUnit;
|
|
|
|
+import java.util.ArrayList;
|
|
|
|
+import java.util.Collections;
|
|
|
|
+import java.util.Date;
|
|
|
|
+import java.util.HashMap;
|
|
|
|
+import java.util.List;
|
|
|
|
+import java.util.Map;
|
|
|
|
+import java.util.Set;
|
|
|
|
+import java.util.stream.Collectors;
|
|
|
|
|
|
/**
|
|
/**
|
|
* @author dzx
|
|
* @author dzx
|
|
* @date 2024/6/4
|
|
* @date 2024/6/4
|
|
*/
|
|
*/
|
|
|
|
+@SpringBootTest
|
|
class AttenDanceWarnNoticeTaskTest {
|
|
class AttenDanceWarnNoticeTaskTest {
|
|
|
|
|
|
|
|
|
|
|
|
+ @Autowired
|
|
|
|
+ private IAttendanceRuleCategoryService categoryService;
|
|
|
|
+
|
|
|
|
+ @Autowired
|
|
|
|
+ private IXjrUserService userService;
|
|
|
|
+
|
|
|
|
+ @Autowired
|
|
|
|
+ private AttendanceUserRelationMapper relationMapper;
|
|
|
|
+
|
|
|
|
+ @Autowired
|
|
|
|
+ private IWeChatService weChatService;
|
|
|
|
+
|
|
|
|
+ @Autowired
|
|
|
|
+ private WeChatUtil weChatUtil;
|
|
|
|
+
|
|
|
|
+ @Autowired
|
|
|
|
+ private IWechatMessageLogService wechatMessageLogService;
|
|
|
|
+
|
|
@Test
|
|
@Test
|
|
- void test(){
|
|
|
|
|
|
+ public void RefreshConnectionPool() {
|
|
|
|
+ String active = SpringUtil.getActiveProfile();
|
|
|
|
+ if(!"dev".equals(active)){
|
|
|
|
+ return;
|
|
|
|
+ }
|
|
|
|
+ //获取当前时间
|
|
LocalDateTime now = LocalDateTime.now();
|
|
LocalDateTime now = LocalDateTime.now();
|
|
- System.out.println(now.getDayOfWeek().name());
|
|
|
|
|
|
+ DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
|
|
|
|
+ String timeStr = now.format(formatter);
|
|
|
|
+
|
|
|
|
+ //查询今天所有的考勤规则
|
|
|
|
+ List<AttendanceRuleDetails> ruleDetailsList = categoryService.getTodayRules();
|
|
|
|
+ Map<Long, AttendanceRuleDetails> ruleDetailsMap = new HashMap<>();
|
|
|
|
+ for (AttendanceRuleDetails ruleDetail : ruleDetailsList) {
|
|
|
|
+ ruleDetailsMap.put(ruleDetail.getAttendanceRuleCategoryId(), ruleDetail);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ //查询出所有人的考勤规则
|
|
|
|
+ List<AttendanceUserRelation> relationList = relationMapper.selectList(
|
|
|
|
+ new QueryWrapper<AttendanceUserRelation>().lambda()
|
|
|
|
+ .eq(AttendanceUserRelation::getDeleteMark, 0)
|
|
|
|
+ );
|
|
|
|
+ Map<Long, AttendanceRuleDetails> allTodyRule = new HashMap<>();
|
|
|
|
+ for (AttendanceUserRelation userRelation : relationList) {
|
|
|
|
+ allTodyRule.put(userRelation.getUserId(), ruleDetailsMap.get(userRelation.getAttendanceRuleCategoryId()));
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ Map<Long, AttendanceUserRelation> allUserStatus = new HashMap<>();
|
|
|
|
+ for (AttendanceUserRelation userRelation : relationList) {
|
|
|
|
+ allUserStatus.put(userRelation.getUserId(), userRelation);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ //根据规则中的用户id查询出所有绑定了微信的学生和教师
|
|
|
|
+ if(allTodyRule.isEmpty()){
|
|
|
|
+ System.out.println("未能查询出规则,不进行推送");
|
|
|
|
+ return;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ //获取最近的时间
|
|
|
|
+ LocalDateTime recentlyTime = getRecentlyTime(ruleDetailsList, now);
|
|
|
|
+ if(!recentlyTime.isEqual(now)){
|
|
|
|
+ System.out.println("未到时间,不进行推送");
|
|
|
|
+// return;
|
|
|
|
+ }
|
|
|
|
+ String wechatTemplate = weChatUtil.getAttenDanceWarnTemplate();
|
|
|
|
+// WechatMessageLog log = wechatMessageLogService.getOne(
|
|
|
|
+// new QueryWrapper<WechatMessageLog>().lambda()
|
|
|
|
+// .select(WechatMessageLog.class, x -> VoToColumnUtil.fieldsToColumns(WechatMessageLog.class).contains(x.getProperty()))
|
|
|
|
+// .eq(WechatMessageLog::getSendTime, recentlyTime)
|
|
|
|
+// .eq(WechatMessageLog::getTemplateId, wechatTemplate)
|
|
|
|
+// );
|
|
|
|
+// if(log != null){//已经推送过,不再进行推送
|
|
|
|
+//// return;
|
|
|
|
+// }
|
|
|
|
+
|
|
|
|
+ //判断所有当前时间下,哪几条规则需要进行提醒
|
|
|
|
+ Map<Long, Integer> ruleDetailsJudgeMap = judgeExecuteNotice(now, ruleDetailsList, recentlyTime);
|
|
|
|
+
|
|
|
|
+ WechatMessageLog messageLog = new WechatMessageLog();
|
|
|
|
+ messageLog.setTemplateId(wechatTemplate);
|
|
|
|
+ messageLog.setSendTime(recentlyTime);
|
|
|
|
+
|
|
|
|
+ List<XjrUser> userList = getUserList(allTodyRule.keySet());
|
|
|
|
+ for (XjrUser xjrUser : userList) {
|
|
|
|
+ AttendanceRuleDetails ruleDetails = allTodyRule.get(xjrUser.getId());
|
|
|
|
+ Integer status = ruleDetailsJudgeMap.get(ruleDetails.getId());
|
|
|
|
+ if(status == 0){
|
|
|
|
+ continue;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ WeChatSendMessageDto weChatSendMessageDto = new WeChatSendMessageDto();
|
|
|
|
+ weChatSendMessageDto.setUserId(xjrUser.getOpenId());
|
|
|
|
+ weChatSendMessageDto.setTemplateId(wechatTemplate);
|
|
|
|
+ weChatSendMessageDto.setMsgId(IdUtil.getSnowflakeNextId() + "");
|
|
|
|
+ JSONObject paramJson = new JSONObject();
|
|
|
|
+
|
|
|
|
+ JSONObject thing8 = new JSONObject();
|
|
|
|
+ thing8.put("value", xjrUser.getName());
|
|
|
|
+ paramJson.put("thing8", thing8);
|
|
|
|
+
|
|
|
|
+ JSONObject time9 = new JSONObject();
|
|
|
|
+ time9.put("value", timeStr);
|
|
|
|
+ paramJson.put("time9", time9);
|
|
|
|
+
|
|
|
|
+ JSONObject const12 = new JSONObject();
|
|
|
|
+ if(status == 1){
|
|
|
|
+ const12.put("value", "未打卡");
|
|
|
|
+ }else{
|
|
|
|
+ const12.put("value", "待打卡");
|
|
|
|
+ }
|
|
|
|
+ //查询这个用户最新的考勤状态
|
|
|
|
+ AttendanceUserRelation userRelation = allUserStatus.get(xjrUser.getId());
|
|
|
|
+ if(userRelation != null
|
|
|
|
+ && userRelation.getAttendanceTime() !=null
|
|
|
|
+ && userRelation.getAttendanceTime().toLocalDate().isEqual(now.toLocalDate())
|
|
|
|
+ && "到校".equals(userRelation.getAttendanceStatus())){
|
|
|
|
+ const12.put("value", "已打卡");
|
|
|
|
+ }
|
|
|
|
+ paramJson.put("const12", const12);
|
|
|
|
+
|
|
|
|
+ weChatSendMessageDto.setContent(paramJson);
|
|
|
|
+ weChatService.sendTemplateMessage(weChatSendMessageDto);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ messageLog.setCreateDate(new Date());
|
|
|
|
+ messageLog.setContent("消息推送人数:" + userList.size());
|
|
|
|
+ wechatMessageLogService.save(messageLog);
|
|
|
|
+
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ /**
|
|
|
|
+ * 判断所有规则,哪些需要发送
|
|
|
|
+ * @param judgeTime
|
|
|
|
+ * @param ruleDetailsList
|
|
|
|
+ * @return 0:不需要提醒,1:未打卡,2:待打卡
|
|
|
|
+ */
|
|
|
|
+ Map<Long, Integer> judgeExecuteNotice(LocalDateTime judgeTime, List<AttendanceRuleDetails> ruleDetailsList, LocalDateTime recentlyTime){
|
|
|
|
+ Map<Long, Integer> result = new HashMap<>();
|
|
|
|
+ for (AttendanceRuleDetails ruleDetails : ruleDetailsList) {
|
|
|
|
+ if(ruleDetails.getIsAllowInOutSchool() != null && ruleDetails.getIsAllowInOutSchool() == 1
|
|
|
|
+ && ruleDetails.getIsAttendance() != null && ruleDetails.getIsAttendance() == 1){
|
|
|
|
+ if(ruleDetails.getAmStartTime() != null){
|
|
|
|
+ LocalDateTime amStartTime = judgeTime.with(ruleDetails.getAmStartTime().toLocalTime());
|
|
|
|
+ if(recentlyTime.isEqual(amStartTime)){
|
|
|
|
+ Long amBetween = ChronoUnit.MINUTES.between(judgeTime, amStartTime);
|
|
|
|
+ if(judgeTime.isBefore(amStartTime) && amBetween >= ruleDetails.getAgoMinutes() - 1 && amBetween <= ruleDetails.getAgoMinutes() + 1){//相差分钟数小于0
|
|
|
|
+ result.put(ruleDetails.getId(), 1);
|
|
|
|
+ }else if(judgeTime.isAfter(amStartTime) && amBetween >= ruleDetails.getOverMinutes() - 1 && amBetween <= ruleDetails.getOverMinutes() + 1){
|
|
|
|
+ result.put(ruleDetails.getId(), 2);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ if(ruleDetails.getPmStartTime() != null){
|
|
|
|
+ LocalDateTime pmStartTime = judgeTime.with(ruleDetails.getPmStartTime().toLocalTime());
|
|
|
|
+ if(recentlyTime.isEqual(pmStartTime)){
|
|
|
|
+ Long pmBetween = ChronoUnit.MINUTES.between(judgeTime, pmStartTime);
|
|
|
|
+ if(judgeTime.isBefore(pmStartTime) && pmBetween >= ruleDetails.getAgoMinutes() - 1 && pmBetween <= ruleDetails.getAgoMinutes() + 1){
|
|
|
|
+ result.put(ruleDetails.getId(), 1);
|
|
|
|
+ }else if(judgeTime.isAfter(pmStartTime) && pmBetween >= ruleDetails.getOverMinutes() - 1 && pmBetween <= ruleDetails.getOverMinutes() + 1){
|
|
|
|
+ result.put(ruleDetails.getId(), 2);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ if(ruleDetails.getEveningStartTime() != null){
|
|
|
|
+ LocalDateTime eveningStartTime = judgeTime.with(ruleDetails.getEveningStartTime().toLocalTime());
|
|
|
|
+ if(recentlyTime.isEqual(eveningStartTime)){
|
|
|
|
+ Long eveningBetween = ChronoUnit.MINUTES.between(judgeTime, eveningStartTime);
|
|
|
|
+ if(judgeTime.isBefore(eveningStartTime) && eveningBetween >= ruleDetails.getAgoMinutes() - 1 && eveningBetween <= ruleDetails.getAgoMinutes() + 1){
|
|
|
|
+ result.put(ruleDetails.getId(), 1);
|
|
|
|
+ }else if(judgeTime.isAfter(eveningStartTime) && eveningBetween >= ruleDetails.getOverMinutes() - 1 && eveningBetween <= ruleDetails.getOverMinutes() + 1){
|
|
|
|
+ result.put(ruleDetails.getId(), 2);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ if(!result.containsKey(ruleDetails.getId())){
|
|
|
|
+ result.put(ruleDetails.getId(), 0);
|
|
|
|
+ }
|
|
|
|
+ }else{
|
|
|
|
+ result.put(ruleDetails.getId(), 0);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ return result;
|
|
|
|
+ }
|
|
|
|
+ /**
|
|
|
|
+ * 查询出所有用户信息(openId不为空的)
|
|
|
|
+ * @param userIds 需要插叙的userid
|
|
|
|
+ * @return 用户信息
|
|
|
|
+ */
|
|
|
|
+ List<XjrUser> getUserList(Set<Long> userIds){
|
|
|
|
+ return userService.list(
|
|
|
|
+ new QueryWrapper<XjrUser>().lambda()
|
|
|
|
+ .in(XjrUser::getId, userIds)
|
|
|
|
+// .isNotNull(XjrUser::getOpenId)
|
|
|
|
+ );
|
|
|
|
+ }
|
|
|
|
|
|
- LocalTime amStartTime = LocalTime.of(8,0,0);
|
|
|
|
- System.out.println(now.with(amStartTime));
|
|
|
|
|
|
+ LocalDateTime getRecentlyTime(List<AttendanceRuleDetails> ruleDetails, LocalDateTime now){
|
|
|
|
+ List<LocalDateTime> result = new ArrayList<>();
|
|
|
|
+ for (AttendanceRuleDetails ruleDetail : ruleDetails) {
|
|
|
|
+ if(ruleDetail.getIsAllowInOutSchool() != null && ruleDetail.getIsAllowInOutSchool() == 1
|
|
|
|
+ && ruleDetail.getIsAttendance() != null && ruleDetail.getIsAttendance() == 1){
|
|
|
|
+ if(ruleDetail.getAmStartTime() != null){
|
|
|
|
+ LocalDateTime amStartTime = now.with(ruleDetail.getAmStartTime().toLocalTime());
|
|
|
|
+ result.add(amStartTime);
|
|
|
|
+ }
|
|
|
|
+ if(ruleDetail.getPmStartTime() != null){
|
|
|
|
+ LocalDateTime pmStartTime = now.with(ruleDetail.getPmStartTime().toLocalTime());
|
|
|
|
+ result.add(pmStartTime);
|
|
|
|
+ }
|
|
|
|
|
|
- System.out.println(1L == 1);
|
|
|
|
|
|
+ if(ruleDetail.getEveningStartTime() != null){
|
|
|
|
+ LocalDateTime eveningStartTime = now.with(ruleDetail.getEveningStartTime().toLocalTime());
|
|
|
|
+ result.add(eveningStartTime);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ if(result.isEmpty()){
|
|
|
|
+ return null;
|
|
|
|
+ }
|
|
|
|
+ Map<Long, LocalDateTime> timeMap = new HashMap<>();
|
|
|
|
+ for (LocalDateTime localDateTime : result) {
|
|
|
|
+ long between = ChronoUnit.SECONDS.between(now, localDateTime);
|
|
|
|
+ timeMap.put(Math.abs(between), localDateTime);
|
|
|
|
+ }
|
|
|
|
+ List<Long> collect = timeMap.keySet().stream().collect(Collectors.toList());
|
|
|
|
+ Collections.sort(collect, Long::compare);
|
|
|
|
|
|
|
|
+ return timeMap.get(collect.get(0));
|
|
}
|
|
}
|
|
|
|
|
|
}
|
|
}
|