package com.zy.core.service;
|
|
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
import com.core.common.Cools;
|
import com.core.exception.CoolException;
|
import com.zy.asrs.domain.param.ManualRollbackTaskParam;
|
import com.zy.asrs.entity.WrkMast;
|
import com.zy.asrs.service.WrkMastLogService;
|
import com.zy.asrs.service.WrkMastService;
|
import com.zy.common.utils.RedisUtil;
|
import com.zy.core.News;
|
import com.zy.core.enums.CrnTaskModeType;
|
import com.zy.core.enums.RedisKeyType;
|
import com.zy.core.enums.WrkStsType;
|
import com.zy.core.model.CommandResponse;
|
import com.zy.core.model.command.CrnCommand;
|
import lombok.extern.slf4j.Slf4j;
|
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.stereotype.Service;
|
import org.springframework.transaction.annotation.Transactional;
|
|
import java.util.Date;
|
import java.util.HashMap;
|
|
@Slf4j
|
@Service
|
public class WrkCommandRollbackService {
|
|
private static final int DEFAULT_AUTO_ROLLBACK_LIMIT = 3;
|
|
@Autowired
|
private WrkMastService wrkMastService;
|
@Autowired
|
private WrkMastLogService wrkMastLogService;
|
@Autowired
|
private RedisUtil redisUtil;
|
|
@Transactional(rollbackFor = Exception.class)
|
public void handleSingleCrnSendResult(CrnCommand command, CommandResponse response, String deviceName) {
|
if (command == null || command.getTaskNo() == null || command.getTaskNo() <= 0) {
|
return;
|
}
|
|
if (CrnTaskModeType.RESET.id.equals(command.getTaskMode())) {
|
return;
|
}
|
|
WrkMast wrkMast = wrkMastService.selectByWorkNo(command.getTaskNo());
|
if (wrkMast == null) {
|
return;
|
}
|
|
if (!isSingleCrnRunStatus(wrkMast.getWrkSts())) {
|
return;
|
}
|
|
if (response != null && Boolean.TRUE.equals(response.getResult())) {
|
clearSendFailState(wrkMast);
|
return;
|
}
|
|
String failMessage = buildFailMessage(deviceName, response);
|
int nextFailCount = (wrkMast.getSendFailCount() == null ? 0 : wrkMast.getSendFailCount()) + 1;
|
int rollbackLimit = getAutoRollbackLimit();
|
boolean manualRequired = nextFailCount >= rollbackLimit;
|
Long updateStatus = manualRequired ? getManualStatus(wrkMast.getWrkSts()) : getRollbackStatus(wrkMast.getWrkSts());
|
if (updateStatus == null) {
|
return;
|
}
|
|
saveWrkLog(wrkMast.getWrkNo());
|
|
wrkMast.setWrkSts(updateStatus);
|
wrkMast.setSendFailCount(nextFailCount);
|
wrkMast.setErrorTime(new Date());
|
wrkMast.setErrorMemo(failMessage);
|
wrkMast.setSystemMsg(failMessage);
|
wrkMast.setModiTime(new Date());
|
wrkMastService.updateById(wrkMast);
|
|
if (manualRequired) {
|
News.taskError(wrkMast.getWrkNo(), "{}下发命令失败,已达到自动回滚上限({}),请在工作档手动回滚。原因: {}", deviceName, rollbackLimit, failMessage);
|
} else {
|
News.taskWarn(wrkMast.getWrkNo(), "{}下发命令失败,任务已自动回滚({}/{}). 原因: {}", deviceName, nextFailCount, rollbackLimit, failMessage);
|
}
|
}
|
|
@Transactional(rollbackFor = Exception.class)
|
public boolean manualRollbackTask(ManualRollbackTaskParam param) {
|
WrkMast wrkMast = findWrkMast(param == null ? null : param.getWrkNo(), param == null ? null : param.getTaskNo());
|
if (wrkMast == null) {
|
throw new CoolException("任务不存在");
|
}
|
|
Long rollbackStatus = getRollbackStatusFromManual(wrkMast.getWrkSts());
|
if (rollbackStatus == null) {
|
throw new CoolException("当前任务不处于待人工回滚状态");
|
}
|
|
saveWrkLog(wrkMast.getWrkNo());
|
|
wrkMast.setWrkSts(rollbackStatus);
|
wrkMast.setSendFailCount(0);
|
wrkMast.setSystemMsg("人工回滚完成,等待重新下发");
|
wrkMast.setModiTime(new Date());
|
wrkMastService.updateById(wrkMast);
|
News.taskInfo(wrkMast.getWrkNo(), "人工回滚完成,任务状态已恢复为待执行");
|
return true;
|
}
|
|
private void clearSendFailState(WrkMast wrkMast) {
|
boolean needUpdate = (wrkMast.getSendFailCount() != null && wrkMast.getSendFailCount() > 0)
|
|| wrkMast.getErrorTime() != null
|
|| !Cools.isEmpty(wrkMast.getErrorMemo());
|
if (!needUpdate) {
|
return;
|
}
|
|
saveWrkLog(wrkMast.getWrkNo());
|
|
wrkMast.setSendFailCount(0);
|
wrkMast.setErrorTime(null);
|
wrkMast.setErrorMemo(null);
|
wrkMast.setSystemMsg("");
|
wrkMast.setModiTime(new Date());
|
wrkMastService.updateById(wrkMast);
|
}
|
|
private WrkMast findWrkMast(Integer wrkNo, String taskNo) {
|
if (wrkNo != null) {
|
return wrkMastService.selectByWorkNo(wrkNo);
|
}
|
if (!Cools.isEmpty(taskNo)) {
|
return wrkMastService.getOne(new QueryWrapper<WrkMast>().eq("wms_wrk_no", taskNo));
|
}
|
return null;
|
}
|
|
private void saveWrkLog(Integer wrkNo) {
|
try {
|
wrkMastLogService.save(wrkNo);
|
} catch (Exception e) {
|
log.warn("保存工作档日志失败, wrkNo={}", wrkNo, e);
|
}
|
}
|
|
private int getAutoRollbackLimit() {
|
Object systemConfigMapObj = redisUtil.get(RedisKeyType.SYSTEM_CONFIG_MAP.key);
|
if (!(systemConfigMapObj instanceof HashMap)) {
|
return DEFAULT_AUTO_ROLLBACK_LIMIT;
|
}
|
|
try {
|
HashMap<String, String> systemConfigMap = (HashMap<String, String>) systemConfigMapObj;
|
return Math.max(1, Integer.parseInt(systemConfigMap.getOrDefault("deviceCommandAutoRollbackLimit", String.valueOf(DEFAULT_AUTO_ROLLBACK_LIMIT))));
|
} catch (Exception ignore) {
|
return DEFAULT_AUTO_ROLLBACK_LIMIT;
|
}
|
}
|
|
private String buildFailMessage(String deviceName, CommandResponse response) {
|
if (response != null && !Cools.isEmpty(response.getMessage())) {
|
return response.getMessage();
|
}
|
return deviceName + "命令下发失败";
|
}
|
|
private boolean isSingleCrnRunStatus(Long wrkSts) {
|
return Long.valueOf(WrkStsType.INBOUND_RUN.sts).equals(wrkSts)
|
|| Long.valueOf(WrkStsType.OUTBOUND_RUN.sts).equals(wrkSts)
|
|| Long.valueOf(WrkStsType.LOC_MOVE_RUN.sts).equals(wrkSts);
|
}
|
|
private Long getRollbackStatus(Long wrkSts) {
|
if (Long.valueOf(WrkStsType.INBOUND_RUN.sts).equals(wrkSts)) {
|
return WrkStsType.INBOUND_DEVICE_RUN.sts;
|
}
|
if (Long.valueOf(WrkStsType.OUTBOUND_RUN.sts).equals(wrkSts)) {
|
return WrkStsType.NEW_OUTBOUND.sts;
|
}
|
if (Long.valueOf(WrkStsType.LOC_MOVE_RUN.sts).equals(wrkSts)) {
|
return WrkStsType.NEW_LOC_MOVE.sts;
|
}
|
return null;
|
}
|
|
private Long getManualStatus(Long wrkSts) {
|
if (Long.valueOf(WrkStsType.INBOUND_RUN.sts).equals(wrkSts)) {
|
return WrkStsType.INBOUND_MANUAL.sts;
|
}
|
if (Long.valueOf(WrkStsType.OUTBOUND_RUN.sts).equals(wrkSts)) {
|
return WrkStsType.OUTBOUND_MANUAL.sts;
|
}
|
if (Long.valueOf(WrkStsType.LOC_MOVE_RUN.sts).equals(wrkSts)) {
|
return WrkStsType.LOC_MOVE_MANUAL.sts;
|
}
|
return null;
|
}
|
|
private Long getRollbackStatusFromManual(Long wrkSts) {
|
if (Long.valueOf(WrkStsType.INBOUND_MANUAL.sts).equals(wrkSts)) {
|
return WrkStsType.INBOUND_DEVICE_RUN.sts;
|
}
|
if (Long.valueOf(WrkStsType.OUTBOUND_MANUAL.sts).equals(wrkSts)) {
|
return WrkStsType.NEW_OUTBOUND.sts;
|
}
|
if (Long.valueOf(WrkStsType.LOC_MOVE_MANUAL.sts).equals(wrkSts)) {
|
return WrkStsType.NEW_LOC_MOVE.sts;
|
}
|
return null;
|
}
|
}
|