From 1519a7c81e6566dd0cbc6acfb1b5e92c3aaba7df Mon Sep 17 00:00:00 2001 From: xiangpei <xiangpei@timesnew.cn> Date: 星期日, 02 三月 2025 10:53:57 +0800 Subject: [PATCH] 赋码定时任务只判断超时,且用红码时间判断 --- business/src/main/java/com/ycl/task/FlowableTask.java | 186 ++++++++++++++++++++++++++++++++++++++++++---- 1 files changed, 170 insertions(+), 16 deletions(-) diff --git a/business/src/main/java/com/ycl/task/FlowableTask.java b/business/src/main/java/com/ycl/task/FlowableTask.java index 7336100..02c1455 100644 --- a/business/src/main/java/com/ycl/task/FlowableTask.java +++ b/business/src/main/java/com/ycl/task/FlowableTask.java @@ -1,24 +1,36 @@ package com.ycl.task; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; +import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper; import com.baomidou.mybatisplus.extension.conditions.update.LambdaUpdateChainWrapper; +import com.ycl.common.enums.business.ProcessLogEventTypeEnum; +import com.ycl.domain.entity.ProcessCoding; +import com.ycl.domain.entity.ProcessLog; import com.ycl.domain.entity.ProjectInfo; import com.ycl.domain.entity.ProjectProcess; import com.ycl.factory.FlowServiceFactory; +import com.ycl.mapper.ProcessCodingMapper; +import com.ycl.mapper.ProcessLogMapper; import com.ycl.mapper.ProjectInfoMapper; import com.ycl.mapper.ProjectProcessMapper; -import com.ycl.service.ProjectProcessService; +import com.ycl.service.ProcessCodingService; +import com.ycl.service.ProcessLogService; import lombok.extern.slf4j.Slf4j; +import org.apache.commons.lang3.StringUtils; import org.flowable.task.api.Task; import org.flowable.task.api.TaskInfo; +import org.flowable.task.api.history.HistoricTaskInstance; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; import org.springframework.util.CollectionUtils; -import java.util.Date; -import java.util.List; -import java.util.Map; +import java.util.*; +import java.util.function.Function; import java.util.stream.Collectors; + +import static com.ycl.common.constant.ProcessOverTimeConstants.*; +import static com.ycl.common.enums.business.ProcessLogEventTypeEnum.CANCEL_HANGUP; +import static com.ycl.common.enums.business.ProcessLogEventTypeEnum.HANGUP; @Slf4j @Component("flowableTask") @@ -27,28 +39,170 @@ private ProjectProcessMapper projectProcessMapper; @Autowired private ProjectInfoMapper projectInfoMapper; + @Autowired + private ProcessCodingMapper processCodingMapper; + @Autowired + private ProcessLogService processLogService; + @Autowired + private ProcessLogMapper processLogMapper; /** * 璧嬬爜浠诲姟 + * 涓や釜閫昏緫 鏀归」鐩爜銆佹敼鑺傜偣棰滆壊 */ public void expireTask() { log.info("寮�濮嬭祴鐮�"); - List<Task> taskList = taskService.createTaskQuery().list(); - if (!CollectionUtils.isEmpty(taskList)) { - Date now = new Date(); - // 鎸夎秴鏃剁姸鎬佸垎缁勪换鍔� - Map<Boolean, List<String>> processInstanceMap = taskList.stream() - .collect(Collectors.groupingBy( - task -> task.getDueDate() != null && now.after(task.getDueDate()), - Collectors.mapping(TaskInfo::getProcessInstanceId, Collectors.toList()) - )); - // 澶勭悊瓒呮椂鍜屾湭瓒呮椂鐨勯」鐩� - updateProjectCoding(processInstanceMap.get(true), "red"); // 瓒呮椂椤圭洰 - updateProjectCoding(processInstanceMap.get(false), "green"); // 鏈秴鏃堕」鐩� + //褰撳墠姝e湪杩愯鐨勬墍鏈変换鍔¤妭鐐� + List<Task> taskList = taskService.createTaskQuery().active().list(); + if (CollectionUtils.isEmpty(taskList)) return; + //鎺掗櫎鎺夎妭鐐规寕璧风殑浠诲姟 + List<String> allHangupTask = processLogMapper.getAllHangup(); + taskList = taskList.stream() + .filter(task -> !allHangupTask.contains(task.getId())) + .collect(Collectors.toList()); + //TODO锛氱瓫閫夊嚭娴佺▼瀹炰緥id锛岀敤浣滈」鐩寕璧� + Set<String> proInsIds = taskList.stream() + .map(TaskInfo::getProcessInstanceId) + .collect(Collectors.toSet()); + //TODO:鏌ヨ椤圭洰鎸傝捣鏃ュ織 + + List<String> taskIds = taskList.stream().map(TaskInfo::getId).collect(Collectors.toList()); + //鏌ヨ鑺傜偣鎸傝捣鏃ュ織 + Map<String, List<ProcessLog>> hangupLogMap = new LambdaQueryChainWrapper<>(processLogMapper) + .in(ProcessLog::getEventType, HANGUP, CANCEL_HANGUP) + .in(ProcessLog::getProcessInsId, taskIds) + .list() + .stream() + .collect(Collectors.groupingBy(ProcessLog::getTaskId)); + + //闇�瑕佺洃鎺х殑璧嬬爜浠诲姟 + List<ProcessCoding> processCodingList = new LambdaQueryChainWrapper<>(processCodingMapper) + .in(ProcessCoding::getTaskId, taskIds) + .list(); + Map<String, ProcessCoding> taskMap = new HashMap<>(); + Map<String, Date> startTaskMap = new HashMap<>(); + if (!CollectionUtils.isEmpty(processCodingList)) { + //key涓簍askId value涓烘湰浣撳璞� + taskMap = processCodingList.stream().collect(Collectors.toMap(ProcessCoding::getTaskId, Function.identity())); + //鎷垮埌寮�濮嬭鏃剁殑鑺傜偣闆嗗悎 key:taskId value:寮�濮嬫椂闂� + startTaskMap = getStartTaskList(processCodingList); } + //鎻愬墠鍑嗗鎺ユ敹鏁版嵁鐨刴ap key:娴佺▼瀹炰緥id value:闇�瑕佹敼鍙樼殑棰滆壊 + Map<String, List<String>> map = new HashMap<>(); + List<ProcessCoding> list = new ArrayList<>(); + map.put(GREEN, new ArrayList<>()); + map.put(RED, new ArrayList<>()); + map.put(YELLOW, new ArrayList<>()); + Date now = new Date(); + //閬嶅巻鎵�鏈変唬鍔炵殑鑺傜偣 + for (Task task : taskList) { + String taskId = task.getId(); + ProcessCoding processCoding = taskMap.get(taskId); + if (processCoding == null) { + //涓嶉渶瑕佺洃鎺х殑浠诲姟鑺傜偣椤圭洰鐮佺洿鎺ユ敼涓虹豢鑹� + map.get(GREEN).add(task.getProcessInstanceId()); + continue; + } + //鍒ゆ柇璧嬬爜缁熶竴鐢ㄧ浣滀负鍗曚綅锛屼笖鍙渶鐢ㄧ孩鐮佹椂闂村垽鏂秴鏃讹紝閫氳繃瓒呮椂鍘绘敼鍙橀」鐩殑璧嬬爜鐘舵�侊紝鑺傜偣鏈韩鏃犺祴鐮佺姸鎬� + Date startTime = startTaskMap.get(processCoding.getStartTaskId()); + try { + Long redTime = getTime(processCoding.getRedTime()); +// Long yellowTime = getTime(processCoding.getYellowTime()); +// Long overtime = getTime(processCoding.getOvertime()); + if (startTime == null) continue; + //鑺傜偣澶勭悊鏃堕棿 + long durationTime = (now.getTime() - startTime.getTime()) / 1000; + //TODO锛氬噺鍘绘祦绋嬫寕璧锋椂闀� + + //鍑忓幓鑺傜偣鎸傝捣鏃堕暱 + durationTime = subNodeHangupTime(hangupLogMap, task, durationTime); + + String status = GREEN; // 榛樿鐘舵�佷负缁胯壊 + String overtimeStatus = NORMAL; + if (redTime != null && redTime != 0 && durationTime >= redTime) { + status = RED; // 濡傛灉瓒呰繃绾㈣壊鏃堕棿闃堝�硷紝鍒欒〃鏄庤浠诲姟瓒呮椂 + overtimeStatus = OVERTIME; + } +// else if (yellowTime != null && yellowTime != 0 && durationTime >= yellowTime) { +// status = YELLOW; // 鍚﹀垯锛屽鏋滆秴杩囬粍鑹叉椂闂撮槇鍊硷紝鍒欑姸鎬佷负榛勮壊 +// } +// //澶勭悊鍔炵悊鏈熼檺 +// String overtimeStatus = NORMAL; +// if (overtime != null && overtime != 0 && durationTime >= overtime) { +// overtimeStatus = OVERTIME; // 濡傛灉瓒呰繃鍔炵悊鏈熼檺 +// } else if (overtime != null && overtime != 0 && durationTime >= (overtime - 12 * 60 * 60)) { +// overtimeStatus = WILLOVERTIME; // 濡傛灉涓存湡(鍥哄畾瓒呮椂鍓�12灏忔椂涓轰复鏈�) +// } +// else if (overtime != null && overtime != 0 && durationDay >= (overtime - 60)) { +// overtimeStatus = WILLOVERTIME; // 濡傛灉涓存湡(鍥哄畾瓒呮椂鍓�12灏忔椂涓轰复鏈�) +// } + map.get(status).add(task.getProcessInstanceId()); + processCoding.setStatus(status); + processCoding.setOvertimeStatus(overtimeStatus); + processCoding.setStartTaskTime(task.getCreateTime()); + list.add(processCoding); + } catch (Exception e) { + log.error(e.getMessage(), "璧嬬爜鏃堕棿鏍煎紡鏈夎"); + } + } + //鏇存柊椤圭洰鐮� + map.forEach((key, value) -> updateProjectCoding(value, key)); + //鏇存柊鑺傜偣鐘舵�� 鑷畾涔夌殑mybatis鏂规硶 + if (!CollectionUtils.isEmpty(list)) processCodingMapper.updateBatch(list); + log.info("缁撴潫璧嬬爜"); } + //鍑忓幓鑺傜偣鎸傝捣鏃堕暱 + private long subNodeHangupTime(Map<String, List<ProcessLog>> hangupLogMap, Task task, long durationTime) { + List<ProcessLog> processLogs = hangupLogMap.get(task.getId()); + if (!CollectionUtils.isEmpty(processLogs)) { + long hangupTime = 0; + //鍒嗙粍鍒嗕负鎸傝捣鍜屽彇娑堟寕璧� + Map<ProcessLogEventTypeEnum, List<ProcessLog>> logEventTypeMap = processLogs.stream() + .sorted(Comparator.comparing(ProcessLog::getGmtCreate)) + .collect(Collectors.groupingBy(ProcessLog::getEventType)); + List<ProcessLog> cancelHangup = logEventTypeMap.get(CANCEL_HANGUP); + for (int i = 0; i < cancelHangup.size(); i++) { + ProcessLog processLog = cancelHangup.get(i); + hangupTime += processLog.getGmtCreate().getTime() - logEventTypeMap.get(HANGUP).get(i).getGmtCreate().getTime(); + } + durationTime = durationTime - hangupTime; + } + return durationTime; + } + + private Long getTime(String timeStr) { + Long time = null; + if (StringUtils.isNotBlank(timeStr)) { + String[] timeArr = timeStr.split("-"); + // 瑙f瀽澶╂暟鍜屽皬鏃舵暟 + int days = Integer.parseInt(timeArr[0]); + int hours = 0; + if (timeArr.length > 1) { + hours = Integer.parseInt(timeArr[1]); + } + time = (days * 24L + hours) * 3600L; +// //鍒�-绉� +// time= (days * 60L) + hours; + } + return time; + } + + private Map<String, Date> getStartTaskList(List<ProcessCoding> processCodingList) { + //鏌ュ嚭浠诲姟璁℃椂璧峰鑺傜偣闆嗗悎 + List<String> startTaskIds = processCodingList.stream().map(ProcessCoding::getStartTaskId).collect(Collectors.toList()); + //鏌ュ嚭璧峰璁℃椂鑺傜偣鏁版嵁 + Map<String, Date> startDateMap = new HashMap<>(); + List<HistoricTaskInstance> hisStartTasks = historyService.createHistoricTaskInstanceQuery().taskIds(startTaskIds).list(); + if (!CollectionUtils.isEmpty(hisStartTasks)) { + hisStartTasks.forEach(hisTask -> { + startDateMap.put(hisTask.getId(), hisTask.getStartTime()); + }); + } + return startDateMap; + } + /** * 璧嬬爜 * -- Gitblit v1.8.0