fix:任务创建/修改状态

This commit is contained in:
2026-07-15 08:59:54 +08:00
parent 254797a154
commit 63994ef588
24 changed files with 707 additions and 50 deletions

View File

@@ -1,5 +1,6 @@
/**
*
* 外部引用任务的task接口
* @Author: liyongde
* @Date: 2026/7/14 18:57
*/package cn.code.nl.module.task.api;
*/
package cn.code.nl.module.task.api;

View File

@@ -68,6 +68,9 @@ public class TransportTaskCreateReqDTO {
@Schema(description = "是否自动下发")
private String isAutoIssue;
@Schema(description = "是否创建完成")
private Boolean isCreateFinish;
@Schema(description = "任务类型")
private String taskType;
@@ -87,5 +90,5 @@ public class TransportTaskCreateReqDTO {
private Long sortSeq;
@Schema(description = "扩展参数JSON")
private Map<String, Object> requestParam;
private String requestParam;
}

View File

@@ -8,8 +8,10 @@ import cn.code.nl.framework.common.exception.ErrorCode;
* @Date: 2026/7/14 13:03
*/
public interface ErrorCodeConstants {
ErrorCode TRANSPORT_TASK_NOT_EXISTS = new ErrorCode(1, "搬运任务不存在");
ErrorCode TRANSPORT_TASK_EXISTS_UNFINISHED = new ErrorCode(2, "同业务类型下存在未完结的搬运任务");
ErrorCode TRANSPORT_TASK_STATUS_NOT_ALLOW = new ErrorCode(3, "当前任务状态不允许此操作");
ErrorCode TRANSPORT_TASK_CALLBACK_SEND_FAILED = new ErrorCode(4, "业务回调发送失败");
ErrorCode TRANSPORT_TASK_NOT_EXISTS = new ErrorCode(5001, "搬运任务不存在");
ErrorCode TRANSPORT_TASK_EXISTS_UNFINISHED = new ErrorCode(5002, "同业务类型下存在未完结的搬运任务");
ErrorCode TRANSPORT_TASK_STATUS_NOT_ALLOW = new ErrorCode(5003, "当前任务状态不允许此操作");
ErrorCode TRANSPORT_TASK_CALLBACK_SEND_FAILED = new ErrorCode(5004, "业务回调发送失败");
ErrorCode TRANSPORT_TASK_RUNNING_ALREADY_EXIST = new ErrorCode(5005, "已存在运行中的任务");
}

View File

@@ -1,8 +1,44 @@
package cn.code.nl.module.task.enums;
import lombok.Getter;
/**
*
* 任务状态的枚举
* @Author: liyongde
* @Date: 2026/7/14 16:14
*/public enum TransportTaskStatusEnum {
*/
@Getter
public enum TransportTaskStatusEnum {
CREATED(10, "生成"),
READY(40, "待下发-起点终点确认"),
ISSUING(45, "下发中"),
ISSUED(50, "已下发"),
EXECUTING(60, "执行中"),
PICKED(61, "已取货搬运中"),
FINISHED_CALLBACK_PENDING(67, "外部完成待业务处理"),
CANCEL_EXTERNAL_PENDING(68, "外部取消中"),
CANCEL_CALLBACK_PENDING(69, "外部取消待业务处理"),
FINISHED(70, "完成"),
CANCELLED(80, "取消"),
FAILED(90, "失败");
private final Integer code;
private final String name;
TransportTaskStatusEnum(Integer code, String name) {
this.code = code;
this.name = name;
}
}

View File

@@ -1,4 +1,4 @@
package cn.code.nl.module.task.controller;
package cn.code.nl.module.task.controller.admin.transporttask;
import cn.code.nl.framework.common.pojo.CommonResult;
import cn.code.nl.module.task.dto.AcsFeedbackReqDTO;
@@ -22,7 +22,7 @@ import static cn.code.nl.framework.common.pojo.CommonResult.success;
*/
@Tag(name = "ACS 反馈")
@RestController
@RequestMapping("/api/task/transport")
@RequestMapping("/task/transport")
@Validated
public class AcsFeedbackController {

View File

@@ -1,4 +1,4 @@
package cn.code.nl.module.task.controller;
package cn.code.nl.module.task.controller.admin.transporttask;
import cn.code.nl.framework.common.pojo.CommonResult;
import cn.code.nl.module.task.dto.TaskCallbackResultReqDTO;

View File

@@ -4,6 +4,7 @@ import java.util.*;
import cn.code.nl.framework.common.pojo.PageResult;
import cn.code.nl.framework.mybatis.core.query.LambdaQueryWrapperX;
import cn.code.nl.module.task.enums.TransportTaskStatusEnum;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import cn.code.nl.framework.mybatis.core.mapper.BaseMapperX;
import cn.code.nl.module.task.dal.dataobject.transporttask.TransportTaskDO;
@@ -65,7 +66,7 @@ public interface TransportTaskMapper extends BaseMapperX<TransportTaskDO> {
return selectOne(new LambdaQueryWrapperX<TransportTaskDO>()
.eq(TransportTaskDO::getBizType, bizType)
.eq(TransportTaskDO::getBizId, bizId)
.lt(TransportTaskDO::getTaskStatus, "067"));
.lt(TransportTaskDO::getTaskStatus, TransportTaskStatusEnum.FINISHED_CALLBACK_PENDING.getCode()));
}
/**

View File

@@ -1,15 +1,12 @@
package cn.code.nl.module.task.framework.rpc.config;
import cn.code.nl.module.task.api.TransportTaskApi;
import org.springframework.cloud.openfeign.EnableFeignClients;
import org.springframework.context.annotation.Configuration;
/**
* Task 服务 RPC 配置
* <p>
* 注册 Feign 客户端,使 LMS/WMS 等调用方可通过 @Resource 注入 TransportTaskApi
*/
@Configuration
@EnableFeignClients(clients = {TransportTaskApi.class})
@Configuration(value = "taskRpcConfiguration", proxyBeanMethods = false)
@EnableFeignClients()
public class RpcConfiguration {
}

View File

@@ -1,14 +1,14 @@
package cn.code.nl.module.task.framework.security.config;
import cn.code.nl.framework.security.config.AuthorizeRequestsCustomizer;
import cn.code.nl.module.infra.enums.ApiConstants;
import cn.code.nl.module.task.enums.ApiConstants;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configurers.AuthorizeHttpRequestsConfigurer;
/**
* Infra 模块的 Security 配置
* Task 模块的 Security 配置
*/
@Configuration(proxyBeanMethods = false, value = "taskSecurityConfiguration")
public class SecurityConfiguration {

View File

@@ -1,5 +1,6 @@
/**
*
* 消费者
* @Author: liyongde
* @Date: 2026/7/14 18:47
*/package cn.code.nl.module.task.mq.consumer;
*/
package cn.code.nl.module.task.mq.consumer;

View File

@@ -1,4 +1,4 @@
package cn.code.nl.module.task.dto;
package cn.code.nl.module.task.mq.message;
import lombok.Data;

View File

@@ -1,5 +1,6 @@
/**
*
* 信息体
* @Author: liyongde
* @Date: 2026/7/14 18:47
*/package cn.code.nl.module.task.mq.message;
*/
package cn.code.nl.module.task.mq.message;

View File

@@ -1,4 +1,4 @@
/**
* 消息队列的消息
*/
package cn.code.nl.module.infra.mq.message;
package cn.code.nl.module.task.mq;

View File

@@ -1,6 +1,6 @@
package cn.code.nl.module.task.mq;
package cn.code.nl.module.task.mq.producer;
import cn.code.nl.module.task.dto.TaskEventMessage;
import cn.code.nl.module.task.mq.message.TaskEventMessage;
import lombok.extern.slf4j.Slf4j;
import org.apache.rocketmq.spring.core.RocketMQTemplate;
import org.springframework.stereotype.Component;

View File

@@ -4,13 +4,13 @@ import cn.code.nl.module.task.client.TransportTaskStatusClient;
import cn.code.nl.module.task.dal.dataobject.transporttask.TransportTaskDO;
import cn.code.nl.module.task.dal.mysql.transporttask.TransportTaskMapper;
import cn.code.nl.module.task.dto.AcsFeedbackReqDTO;
import cn.code.nl.module.task.dto.TaskEventMessage;
import cn.code.nl.module.task.mq.message.TaskEventMessage;
import cn.code.nl.module.task.dto.TaskStatusCallbackReqDTO;
import cn.code.nl.module.task.dto.TaskStatusCallbackRespDTO;
import cn.code.nl.module.task.enums.CallbackStatusEnum;
import cn.code.nl.module.task.enums.TaskEventTypeEnum;
import cn.code.nl.module.task.enums.TransportTaskStatusEnum;
import cn.code.nl.module.task.mq.TaskEventProducer;
import cn.code.nl.module.task.mq.producer.TaskEventProducer;
import cn.hutool.core.util.StrUtil;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.extern.slf4j.Slf4j;

View File

@@ -1,5 +1,6 @@
package cn.code.nl.module.task.service.transporttask;
import cn.code.nl.framework.common.exception.ServiceException;
import cn.code.nl.framework.common.pojo.PageResult;
import cn.code.nl.framework.common.util.object.BeanUtils;
import cn.code.nl.module.task.controller.admin.transporttask.vo.TransportTaskPageReqVO;
@@ -43,21 +44,12 @@ public class TransportTaskServiceImpl implements TransportTaskService {
@Override
public Long createTransportTaskByRpc(TransportTaskCreateReqDTO reqDTO) {
// 1. 幂等检查:同 bizType + bizId 下是否有未完结任务
TransportTaskDO existing = transportTaskMapper.selectUnfinishedByBiz(
reqDTO.getBizType(), reqDTO.getBizId());
if (existing != null) {
return existing.getTaskId();
}
// 2. 构建 DO 并保存
// 1. 构建 DO 并保存
TransportTaskDO task = BeanUtils.toBean(reqDTO, TransportTaskDO.class);
// 参数完整 → 待下发(040),否则 → 生成(010)
boolean paramComplete = StrUtil.isNotBlank(reqDTO.getPointCode1())
&& StrUtil.isNotBlank(reqDTO.getPointCode2());
task.setTaskStatus(paramComplete
? String.format("%03d", TransportTaskStatusEnum.READY.getCode())
: String.format("%03d", TransportTaskStatusEnum.CREATED.getCode()));
task.setTaskStatus(reqDTO.getIsCreateFinish()
? String.valueOf(TransportTaskStatusEnum.READY.getCode())
: String.valueOf(TransportTaskStatusEnum.CREATED.getCode()));
task.setCallbackStatus(CallbackStatusEnum.PENDING.getCode());
task.setCallbackRetryCount(0);
task.setCreateMode("RPC");

View File

@@ -79,6 +79,8 @@ spring:
# rocketmq 配置项,对应 RocketMQProperties 配置类
rocketmq:
name-server: 127.0.0.1:9876 # RocketMQ Namesrv
producer:
group: ${spring.application.name}_TASK_DEV_PRODUCER # 生产者分组
spring:
# RabbitMQ 配置项,对应 RabbitProperties 配置类

View File

@@ -64,10 +64,10 @@ mybatis-plus:
map-underscore-to-camel-case: true # 虽然默认为 true ,但是还是显示去指定下。
global-config:
db-config:
id-type: NONE # “智能”模式,基于 IdTypeEnvironmentPostProcessor + 数据源的类型,自动适配成 AUTO、INPUT 模式。
id-type: ASSIGN_ID # 分配 ID默认使用雪花算法。注意Oracle、PostgreSQL、Kingbase、DB2、H2 数据库时,需要去除实体类上的 @KeySequence 注解
# id-type: NONE # “智能”模式,基于 IdTypeEnvironmentPostProcessor + 数据源的类型,自动适配成 AUTO、INPUT 模式。
# id-type: AUTO # 自增 ID适合 MySQL 等直接自增的数据库
# id-type: INPUT # 用户输入 ID适合 Oracle、PostgreSQL、Kingbase、DB2、H2 数据库
# id-type: ASSIGN_ID # 分配 ID默认使用雪花算法。注意Oracle、PostgreSQL、Kingbase、DB2、H2 数据库时,需要去除实体类上的 @KeySequence 注解
logic-delete-value: 1 # 逻辑已删除值(默认为 1)
logic-not-delete-value: 0 # 逻辑未删除值(默认为 0)
banner: false # 关闭控制台的 Banner 打印

View File

@@ -1,8 +1,11 @@
package cn.code.nl.module.task.service.transporttask;
import cn.code.nl.framework.common.pojo.CommonResult;
import cn.code.nl.module.task.api.TransportTaskApi;
import cn.code.nl.module.task.dal.dataobject.transporttask.TransportTaskDO;
import cn.code.nl.module.task.dal.mysql.transporttask.TransportTaskMapper;
import cn.code.nl.module.task.dto.TransportTaskCreateReqDTO;
import jakarta.annotation.Resource;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.InjectMocks;
@@ -22,6 +25,34 @@ class TransportTaskServiceImplTest {
@InjectMocks
private TransportTaskServiceImpl transportTaskService;
/**
* Feign 客户端 —— 真实发起 HTTP 调用,直连本机 Controller
*/
@Mock
private TransportTaskApi transportTaskApi;
/**
* 端到端Feign → Controller → Service → Mapper
*/
@Test
void testApiCreateTask() {
// given
TransportTaskCreateReqDTO req = new TransportTaskCreateReqDTO();
req.setTaskName("测试任务");
req.setOwnerService("LMS");
req.setBizType("INBOUND");
req.setBizId("INB-001");
req.setHandleCode("inboundHandler");
req.setAcsTaskType("MOVE");
req.setAgvSystemType("AGV_TYPE_A");
req.setPointCode1("1");
req.setPointCode2("2");
req.setPointCode3("3");
req.setPointCode4("4");
transportTaskApi.createTransportTask(req);
}
@Test
void testCreateTransportTaskByRpc_shouldReturnTaskId() {
// given