Compare commits

..

4 Commits

Author SHA1 Message Date
cbs
248b0bdeba 循环任务 2025-03-04 09:16:34 +08:00
cbs
5c2a8cfe9d 创建订单过滤禁用点位 2025-03-03 09:11:21 +08:00
cbs
b270a21595 创建订单校验物料 2025-03-01 17:05:06 +08:00
cbs
94a34981c6 过滤不能取放的库位 2025-03-01 15:23:08 +08:00
39 changed files with 1382 additions and 259 deletions

View File

@ -237,4 +237,6 @@ public interface ErrorCodeConstants {
// ========== 车辆动作记录 1_002_045_001 ==========
ErrorCode TASK_DETAIL_ACTION_LOG_NOT_EXISTS = new ErrorCode(1_002_045_001, "车辆动作记录不存在");
// ========== 循环任务点位 1_002_046_001==========
ErrorCode TASK_CYCLE_NOT_EXISTS = new ErrorCode(1_002_046_001, "循环任务点位不存在");
}

View File

@ -76,16 +76,28 @@ public class RobotStatusApiImpl implements RobotStatusApi {
String taskStatusKey = RobotTaskChcheConstant.ROBOT_TASK_STATUS + robotStatusDataDTO.getMac();
String cargoDetectedKey = RobotTaskChcheConstant.ROBOT_CARGO_DETECTED + robotStatusDataDTO.getMac();
String pose2dKey = RobotTaskChcheConstant.ROBOT_INFORMATION_POSE_BAT_SOC + robotStatusDataDTO.getMac();
redisUtil.set(taskStatusKey, robotStatusDataDTO.getData().getTask_status(), robotPositionCacheTime);
redisUtil.set(cargoDetectedKey, robotStatusDataDTO.getData().getCargo_detected(), robotPositionCacheTime);
// todo 后续需要改为从车机上报
redisUtil.set(taskStatusKey, "IDLE", robotPositionCacheTime);
redisUtil.set(cargoDetectedKey, false, robotPositionCacheTime);
/*redisUtil.set(taskStatusKey, robotStatusDataDTO.getData().getTask_status(), robotPositionCacheTime);
redisUtil.set(cargoDetectedKey, robotStatusDataDTO.getData().getCargo_detected(), robotPositionCacheTime);*/
Object object = redisUtil.get(pose2dKey);
RobotStatusDataPoseDTO robotStatusDataPoseDTO = JSONUtil.toBean((String) object, RobotStatusDataPoseDTO.class);
if (ObjectUtil.isNotEmpty(robotStatusDataDTO.getData())
&& ObjectUtil.isNotEmpty(robotStatusDataDTO.getData().getPose2d())) {
robotStatusDataPoseDTO.setX(robotStatusDataDTO.getData().getPose2d().getX());
robotStatusDataPoseDTO.setY(robotStatusDataDTO.getData().getPose2d().getY());
robotStatusDataPoseDTO.setYaw(robotStatusDataDTO.getData().getPose2d().getYaw());
}
if (ObjectUtil.isNotEmpty(robotStatusDataDTO.getData())
&& ObjectUtil.isNotEmpty(robotStatusDataDTO.getData().getFloor_zone())) {
robotStatusDataPoseDTO.setFloor(robotStatusDataDTO.getData().getFloor_zone().getFloor());
robotStatusDataPoseDTO.setArea(robotStatusDataDTO.getData().getFloor_zone().getArea());
}
robotStatusDataPoseDTO.setRobotNo(robotNo);
redisUtil.set(pose2dKey, JSON.toJSONString(robotStatusDataPoseDTO), robotPositionCacheTime);
pathPlanningApi.synchronousLineObject(robotStatusDataPoseDTO, PathPlanningTopicConstant.AGV_POSE);

View File

@ -15,6 +15,7 @@ import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotInformationDO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotTaskDO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotTaskDetailDO;
import cn.iocoder.yudao.module.system.dal.mysql.actionlog.RobotTaskDetailActionLogMapper;
import cn.iocoder.yudao.module.system.dal.mysql.cycle.TaskCycleMapper;
import cn.iocoder.yudao.module.system.dal.mysql.houselocation.WareHouseLocationMapper;
import cn.iocoder.yudao.module.system.dal.mysql.robot.RobotInformationMapper;
import cn.iocoder.yudao.module.system.dal.mysql.robot.RobotTaskDetailMapper;
@ -65,6 +66,9 @@ public class RobotTaskStatusApiImpl implements RobotTaskStatusApi {
@Autowired
private ThreadPoolTaskExecutor taskExecutor;
@Resource
private TaskCycleMapper taskCycleMapper;
@Resource
private WareHouseLocationMapper houseLocationMapper;
@ -157,6 +161,7 @@ public class RobotTaskStatusApiImpl implements RobotTaskStatusApi {
robotTaskDO.setEndTime(LocalDateTime.now());
robotTaskDO.setTaskStatus(RobotTaskDetailStatusEnum.DONE.getType());
robotTaskMapper.updateRobot(robotTaskDO);
taskCycleMapper.deletByRobotTaskId(taskDetails.get(0).getRobotTaskId());
}
if (RobotTaskTypeEnum.MOVE.getType().equals(robotTaskDetailDO.getTaskType())) {

View File

@ -0,0 +1,97 @@
package cn.iocoder.yudao.module.system.controller.admin.cycle;
import cn.iocoder.yudao.module.system.controller.admin.cycle.vo.TaskCyclePageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.cycle.vo.TaskCycleRespVO;
import cn.iocoder.yudao.module.system.controller.admin.cycle.vo.TaskCycleSaveReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.cycle.TaskCycleDO;
import cn.iocoder.yudao.module.system.service.cycle.TaskCycleService;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import org.springframework.validation.annotation.Validated;
import org.springframework.security.access.prepost.PreAuthorize;
import io.swagger.v3.oas.annotations.tags.Tag;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.Operation;
import javax.validation.constraints.*;
import javax.validation.*;
import javax.servlet.http.*;
import java.util.*;
import java.io.IOException;
import cn.iocoder.yudao.framework.common.pojo.PageParam;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils;
import cn.iocoder.yudao.framework.apilog.core.annotation.ApiAccessLog;
import static cn.iocoder.yudao.framework.apilog.core.enums.OperateTypeEnum.*;
@Tag(name = "管理后台 - 循环任务点位")
@RestController
@RequestMapping("/robot/task-cycle")
@Validated
public class TaskCycleController {
@Resource
private TaskCycleService taskCycleService;
@PostMapping("/create")
@Operation(summary = "创建循环任务点位")
@PreAuthorize("@ss.hasPermission('robot:task-cycle:create')")
public CommonResult<Long> createTaskCycle(@Valid @RequestBody TaskCycleSaveReqVO createReqVO) {
return success(taskCycleService.createTaskCycle(createReqVO));
}
@PutMapping("/update")
@Operation(summary = "更新循环任务点位")
@PreAuthorize("@ss.hasPermission('robot:task-cycle:update')")
public CommonResult<Boolean> updateTaskCycle(@Valid @RequestBody TaskCycleSaveReqVO updateReqVO) {
taskCycleService.updateTaskCycle(updateReqVO);
return success(true);
}
@DeleteMapping("/delete")
@Operation(summary = "删除循环任务点位")
@Parameter(name = "id", description = "编号", required = true)
@PreAuthorize("@ss.hasPermission('robot:task-cycle:delete')")
public CommonResult<Boolean> deleteTaskCycle(@RequestParam("id") Long id) {
taskCycleService.deleteTaskCycle(id);
return success(true);
}
@GetMapping("/get")
@Operation(summary = "获得循环任务点位")
@Parameter(name = "id", description = "编号", required = true, example = "1024")
@PreAuthorize("@ss.hasPermission('robot:task-cycle:query')")
public CommonResult<TaskCycleRespVO> getTaskCycle(@RequestParam("id") Long id) {
TaskCycleDO taskCycle = taskCycleService.getTaskCycle(id);
return success(BeanUtils.toBean(taskCycle, TaskCycleRespVO.class));
}
@GetMapping("/page")
@Operation(summary = "获得循环任务点位分页")
@PreAuthorize("@ss.hasPermission('robot:task-cycle:query')")
public CommonResult<PageResult<TaskCycleRespVO>> getTaskCyclePage(@Valid TaskCyclePageReqVO pageReqVO) {
PageResult<TaskCycleDO> pageResult = taskCycleService.getTaskCyclePage(pageReqVO);
return success(BeanUtils.toBean(pageResult, TaskCycleRespVO.class));
}
@GetMapping("/export-excel")
@Operation(summary = "导出循环任务点位 Excel")
@PreAuthorize("@ss.hasPermission('robot:task-cycle:export')")
@ApiAccessLog(operateType = EXPORT)
public void exportTaskCycleExcel(@Valid TaskCyclePageReqVO pageReqVO,
HttpServletResponse response) throws IOException {
pageReqVO.setPageSize(PageParam.PAGE_SIZE_NONE);
List<TaskCycleDO> list = taskCycleService.getTaskCyclePage(pageReqVO).getList();
// 导出 Excel
ExcelUtils.write(response, "循环任务点位.xls", "数据", TaskCycleRespVO.class,
BeanUtils.toBean(list, TaskCycleRespVO.class));
}
}

View File

@ -0,0 +1,28 @@
package cn.iocoder.yudao.module.system.controller.admin.cycle.vo;
import lombok.*;
import java.util.*;
import io.swagger.v3.oas.annotations.media.Schema;
import cn.iocoder.yudao.framework.common.pojo.PageParam;
import org.springframework.format.annotation.DateTimeFormat;
import java.time.LocalDateTime;
import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND;
@Schema(description = "管理后台 - 循环任务点位分页 Request VO")
@Data
@EqualsAndHashCode(callSuper = true)
@ToString(callSuper = true)
public class TaskCyclePageReqVO extends PageParam {
@Schema(description = "机器人任务主表id", example = "2231")
private Long robotTaskId;
@Schema(description = "ware_position_map_item的id", example = "923")
private Long mapItemId;
@Schema(description = "创建时间")
@DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
private LocalDateTime[] createTime;
}

View File

@ -0,0 +1,31 @@
package cn.iocoder.yudao.module.system.controller.admin.cycle.vo;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.*;
import java.util.*;
import org.springframework.format.annotation.DateTimeFormat;
import java.time.LocalDateTime;
import com.alibaba.excel.annotation.*;
@Schema(description = "管理后台 - 循环任务点位 Response VO")
@Data
@ExcelIgnoreUnannotated
public class TaskCycleRespVO {
@Schema(description = "主键ID", requiredMode = Schema.RequiredMode.REQUIRED, example = "9553")
@ExcelProperty("主键ID")
private Long id;
@Schema(description = "机器人任务主表id", example = "2231")
@ExcelProperty("机器人任务主表id")
private Long robotTaskId;
@Schema(description = "ware_position_map_item的id", example = "923")
@ExcelProperty("ware_position_map_item的id")
private Long mapItemId;
@Schema(description = "创建时间", requiredMode = Schema.RequiredMode.REQUIRED)
@ExcelProperty("创建时间")
private LocalDateTime createTime;
}

View File

@ -0,0 +1,21 @@
package cn.iocoder.yudao.module.system.controller.admin.cycle.vo;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.*;
import java.util.*;
import javax.validation.constraints.*;
@Schema(description = "管理后台 - 循环任务点位新增/修改 Request VO")
@Data
public class TaskCycleSaveReqVO {
@Schema(description = "主键ID", requiredMode = Schema.RequiredMode.REQUIRED, example = "9553")
private Long id;
@Schema(description = "机器人任务主表id", example = "2231")
private Long robotTaskId;
@Schema(description = "ware_position_map_item的id", example = "923")
private Long mapItemId;
}

View File

@ -110,8 +110,8 @@ public class RobotInformationController {
@Operation(summary = "查询所有车辆")
@PreAuthorize("@ss.hasPermission('robot:information:getAllRobot')")
public CommonResult<List<RobotInformationRespVO>> getAllRobot() {
List<RobotInformationDO> result = informationService.getAllRobot();
return success(BeanUtils.toBean(result, RobotInformationRespVO.class));
List<RobotInformationRespVO> result = informationService.getAllRobotAndErrorMsg();
return success(result);
}
@GetMapping("/list")

View File

@ -58,6 +58,14 @@ public class RobotTaskController {
return success(true);
}
@PutMapping("/close")
@Operation(summary = "更新机器人任务主表")
@PreAuthorize("@ss.hasPermission('robot:task:close')")
public CommonResult<Boolean> closeTask(@Valid @RequestBody RobotTaskSaveReqVO updateReqVO) {
taskService.closeTask(updateReqVO);
return success(true);
}
@DeleteMapping("/delete")
@Operation(summary = "删除机器人任务主表")
@Parameter(name = "id", description = "编号", required = true)

View File

@ -78,4 +78,7 @@ public class RobotInformationRespVO {
@ExcelProperty("区域")
public String area;
@Schema(description = "机器人错误信息")
public String errorMsg;
}

View File

@ -66,11 +66,11 @@ public class RobotTaskDetailAddVO {
@Schema(description = "放货库位的排序")
private Long toLocationNumber;
@Schema(description = "取货库位ware_position_map的id")
private Long fromMapId;
@Schema(description = "取货库位ware_position_map_item的id")
private Long fromMapItemId;
@Schema(description = "放货库位ware_position_map的id")
private Long toMapId;
@Schema(description = "放货库位ware_position_map_item的id")
private Long toMapItemId;
public Long getPriority() {
if (ObjectUtil.isEmpty(priority)) {

View File

@ -88,9 +88,9 @@ public class RobotTaskDetailPageReqVO extends PageParam {
@Schema(description = "放货库位的排序")
private Long toLocationNumber;
@Schema(description = "取货库位ware_position_map的id")
private Long fromMapId;
@Schema(description = "取货库位ware_position_map_item的id")
private Long fromMapItemId;
@Schema(description = "放货库位ware_position_map的id")
private Long toMapId;
@Schema(description = "放货库位ware_position_map_item的id")
private Long toMapItemId;
}

View File

@ -110,11 +110,9 @@ public class RobotTaskDetailRespVO {
@ExcelProperty("放货库位的排序")
private Long toLocationNumber;
@Schema(description = "取货库位ware_position_map的id")
@ExcelProperty("取货库位ware_position_map的id")
private Long fromMapId;
@Schema(description = "取货库位ware_position_map_item的id")
private Long fromMapItemId;
@Schema(description = "放货库位ware_position_map的id")
@ExcelProperty("放货库位ware_position_map的id")
private Long toMapId;
@Schema(description = "放货库位ware_position_map_item的id")
private Long toMapItemId;
}

View File

@ -88,10 +88,10 @@ public class RobotTaskDetailSaveReqVO {
@Schema(description = "放货库位的排序")
private Long toLocationNumber;
@Schema(description = "取货库位ware_position_map的id")
private Long fromMapId;
@Schema(description = "取货库位ware_position_map_item的id")
private Long fromMapItemId;
@Schema(description = "放货库位ware_position_map的id")
private Long toMapId;
@Schema(description = "放货库位ware_position_map_item的id")
private Long toMapItemId;
}

View File

@ -0,0 +1,39 @@
package cn.iocoder.yudao.module.system.dal.dataobject.cycle;
import lombok.*;
import java.util.*;
import java.time.LocalDateTime;
import java.time.LocalDateTime;
import com.baomidou.mybatisplus.annotation.*;
import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
/**
* 循环任务点位 DO
*
* @author 陈宾顺
*/
@TableName("robot_task_cycle")
@KeySequence("robot_task_cycle_seq") // 用于 OraclePostgreSQLKingbaseDB2H2 数据库的主键自增如果是 MySQL 等数据库可不写
@Data
@EqualsAndHashCode(callSuper = true)
@ToString(callSuper = true)
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class TaskCycleDO extends BaseDO {
/**
* 主键ID
*/
@TableId
private Long id;
/**
* 机器人任务主表id
*/
private Long robotTaskId;
/**
* ware_position_map_item的id
*/
private Long mapItemId;
}

View File

@ -129,12 +129,14 @@ public class RobotTaskDetailDO extends BaseDO {
private Integer electricity;
/**
* ware_position_map的id
* ware_position_map_item的id的id
*/
private Long fromMapId;
private Long fromMapItemId;
/**
* ware_position_map的id
* ware_position_map_item的id的id
*/
private Long toMapId;
private Long toMapItemId;
//todo 需要改为ware_position_map_item的id
}

View File

@ -0,0 +1,30 @@
package cn.iocoder.yudao.module.system.dal.mysql.cycle;
import java.util.*;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX;
import cn.iocoder.yudao.module.system.controller.admin.cycle.vo.TaskCyclePageReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.cycle.TaskCycleDO;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
/**
* 循环任务点位 Mapper
*
* @author 陈宾顺
*/
@Mapper
public interface TaskCycleMapper extends BaseMapperX<TaskCycleDO> {
default PageResult<TaskCycleDO> selectPage(TaskCyclePageReqVO reqVO) {
return selectPage(reqVO, new LambdaQueryWrapperX<TaskCycleDO>()
.eqIfPresent(TaskCycleDO::getRobotTaskId, reqVO.getRobotTaskId())
.eqIfPresent(TaskCycleDO::getMapItemId, reqVO.getMapItemId())
.betweenIfPresent(TaskCycleDO::getCreateTime, reqVO.getCreateTime())
.orderByDesc(TaskCycleDO::getId));
}
void deletByRobotTaskId(@Param("robotTaskId") Long robotTaskId);
}

View File

@ -64,7 +64,10 @@ public interface WareHouseLocationMapper extends BaseMapperX<WareHouseLocationDO
@Param("takeType") Integer takeType,
@Param("id") Long id,
@Param("locationIds") List<Long> locationIds,
@Param("mapIds") Set<Long> mapIds);
@Param("mapIds") Set<Long> mapIds,
@Param("takeMapItemIds") List<Long> takeMapItemIds,
@Param("laneIds") List<Long> laneIds,
@Param("areaIds") List<Long> areaIds);
/**
* 普通查询(未删除)
@ -76,13 +79,14 @@ public interface WareHouseLocationMapper extends BaseMapperX<WareHouseLocationDO
/**
* 查询库位
* @param query
* @param locationIds
* @return
* (注意:----------不能修改排序-----------------)
*/
List<WareHouseLocationDO> selectLocations(@Param("query") WareHouseLocationDO query,
@Param("locationIds") List<Long> locationIds,
@Param("mapIds") Set<Long> mapIds);
@Param("mapIds") Set<Long> mapIds,
@Param("laneIds") List<Long> laneIds,
@Param("areaIds") List<Long> areaIds,
@Param("mapItemIds") List<Long> mapItemIds);
void updateLocationLockList( @Param("locationIds") List<Long> locationIds,
@Param("taskId") Long taskId,
@ -114,4 +118,8 @@ public interface WareHouseLocationMapper extends BaseMapperX<WareHouseLocationDO
* @param wareHouseLocationDO
*/
void updateEntity(WareHouseLocationDO wareHouseLocationDO);
void releaseLocationLockList(@Param("locationIds") List<Long> locationIds,
@Param("taskId") Long taskId,
@Param("locationLock") Integer locationLock);
}

View File

@ -65,10 +65,10 @@ public interface RobotInformationMapper extends BaseMapperX<RobotInformationDO>
/**
* 批量更新机器人状态
* @param robotNos
* @param robotNo
* @param robotStatus
*/
void updateRobotListStatus(@Param("robotNos") Set<String> robotNos, @Param("robotStatus") Integer robotStatus);
void updateRobotListStatus(@Param("robotNo") String robotNo, @Param("robotStatus") Integer robotStatus);
/**
* 查询车辆尺寸

View File

@ -92,4 +92,21 @@ public interface RobotTaskDetailMapper extends BaseMapperX<RobotTaskDetailDO> {
*/
List<RobotTaskDetailDO> getChargeTaskDetail();
/**
* 取货中的map_item_id
* @return
*/
List<Long> selectTakeMapItemIds();
/**
* 放货中的map_item_id
* @return
*/
List<Long> selectReleaseMapItemIds();
/**
* 查询需要创建循环任务且已经完成的订单
* @return
*/
List<RobotTaskDetailDO> selectAutoCreateCycleTask();
}

View File

@ -0,0 +1,21 @@
package cn.iocoder.yudao.module.system.enums.robot.charge;
import lombok.AllArgsConstructor;
import lombok.Getter;
/**
* robot_charge_log的task_status
*/
@Getter
@AllArgsConstructor
public enum ChargeTaskStatusEnum {
NEW(0),//未开始
DOING(1),//执行中
DONE(2),//已完成
CLOSE(3), //已取消
ABNORMAL(4); //异常
/**
* 类型
*/
private final Integer type;
}

View File

@ -4,6 +4,7 @@ import cn.iocoder.yudao.framework.tenant.core.job.TenantJob;
import cn.iocoder.yudao.module.system.enums.redis.RobotCacheLockEnum;
import cn.iocoder.yudao.module.system.service.robot.RobotTaskService;
import cn.iocoder.yudao.module.system.service.robot.job.AutoChargeService;
import cn.iocoder.yudao.module.system.service.robot.job.CycleService;
import cn.iocoder.yudao.module.system.service.robot.job.DistributeTasksService;
import cn.iocoder.yudao.module.system.service.robot.job.RobotTaskAutoMoveService;
import cn.iocoder.yudao.module.system.service.robot.pathplanning.RobotPathPlanningService;
@ -39,6 +40,9 @@ public class RobotJob {
@Autowired
private AutoChargeService autoChargeService;
@Autowired
private CycleService cycleService;
@Autowired
private RobotPathPlanningService robotPathPlanningService;
@ -129,4 +133,28 @@ public class RobotJob {
}
}
/**
* 创建循环任务
*/
@XxlJob("CycleTaskJob")
@TenantJob
public void cycleTaskJob() {
RLock lock = redissonUtils.getLock(RobotCacheLockEnum.ROBOT_TASK_ADD_LOCK.getKey());
if (lock.tryLock()){
try {
log.info("----创建循环任务----");
cycleService.cycleTaskJob();
} catch (Exception e) {
log.error("创建循环任务异常 :{}", e);
} finally {
lock.unlock();
}
}else {
log.info("下发任务给路径规划未获取到锁");
throw exception(REDISSON_NOT_OBTAIN_LOCK);
}
}
}

View File

@ -0,0 +1,56 @@
package cn.iocoder.yudao.module.system.service.cycle;
import java.util.*;
import javax.validation.*;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.pojo.PageParam;
import cn.iocoder.yudao.module.system.controller.admin.cycle.vo.TaskCyclePageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.cycle.vo.TaskCycleSaveReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.cycle.TaskCycleDO;
/**
* 循环任务点位 Service 接口
*
* @author 陈宾顺
*/
public interface TaskCycleService {
/**
* 创建循环任务点位
*
* @param createReqVO 创建信息
* @return 编号
*/
Long createTaskCycle(@Valid TaskCycleSaveReqVO createReqVO);
/**
* 更新循环任务点位
*
* @param updateReqVO 更新信息
*/
void updateTaskCycle(@Valid TaskCycleSaveReqVO updateReqVO);
/**
* 删除循环任务点位
*
* @param id 编号
*/
void deleteTaskCycle(Long id);
/**
* 获得循环任务点位
*
* @param id 编号
* @return 循环任务点位
*/
TaskCycleDO getTaskCycle(Long id);
/**
* 获得循环任务点位分页
*
* @param pageReqVO 分页查询
* @return 循环任务点位分页
*/
PageResult<TaskCycleDO> getTaskCyclePage(TaskCyclePageReqVO pageReqVO);
}

View File

@ -0,0 +1,75 @@
package cn.iocoder.yudao.module.system.service.cycle;
import cn.iocoder.yudao.module.system.controller.admin.cycle.vo.TaskCyclePageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.cycle.vo.TaskCycleSaveReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.cycle.TaskCycleDO;
import cn.iocoder.yudao.module.system.dal.mysql.cycle.TaskCycleMapper;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import org.springframework.validation.annotation.Validated;
import org.springframework.transaction.annotation.Transactional;
import java.util.*;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.pojo.PageParam;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
import static cn.iocoder.yudao.module.system.enums.ErrorCodeConstants.TASK_CYCLE_NOT_EXISTS;
/**
* 循环任务点位 Service 实现类
*
* @author 陈宾顺
*/
@Service
@Validated
public class TaskCycleServiceImpl implements TaskCycleService {
@Resource
private TaskCycleMapper taskCycleMapper;
@Override
public Long createTaskCycle(TaskCycleSaveReqVO createReqVO) {
// 插入
TaskCycleDO taskCycle = BeanUtils.toBean(createReqVO, TaskCycleDO.class);
taskCycleMapper.insert(taskCycle);
// 返回
return taskCycle.getId();
}
@Override
public void updateTaskCycle(TaskCycleSaveReqVO updateReqVO) {
// 校验存在
validateTaskCycleExists(updateReqVO.getId());
// 更新
TaskCycleDO updateObj = BeanUtils.toBean(updateReqVO, TaskCycleDO.class);
taskCycleMapper.updateById(updateObj);
}
@Override
public void deleteTaskCycle(Long id) {
// 校验存在
validateTaskCycleExists(id);
// 删除
taskCycleMapper.deleteById(id);
}
private void validateTaskCycleExists(Long id) {
if (taskCycleMapper.selectById(id) == null) {
throw exception(TASK_CYCLE_NOT_EXISTS);
}
}
@Override
public TaskCycleDO getTaskCycle(Long id) {
return taskCycleMapper.selectById(id);
}
@Override
public PageResult<TaskCycleDO> getTaskCyclePage(TaskCyclePageReqVO pageReqVO) {
return taskCycleMapper.selectPage(pageReqVO);
}
}

View File

@ -117,4 +117,11 @@ public interface RobotInformationService extends IService<RobotInformationDO> {
* @return
*/
String getMacByRobotNo(String robotNo);
/**
* 获取机器人全部信息和异常信息
* @return
*/
List<RobotInformationRespVO> getAllRobotAndErrorMsg();
}

View File

@ -30,10 +30,7 @@ import org.springframework.stereotype.Service;
import org.springframework.validation.annotation.Validated;
import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;
@ -513,4 +510,24 @@ public class RobotInformationServiceImpl extends ServiceImpl<RobotInformationMap
}
return "";
}
@Override
public List<RobotInformationRespVO> getAllRobotAndErrorMsg() {
RobotInformationDO query = new RobotInformationDO();
List<RobotInformationDO> robotInformationDOS = informationMapper.queryAllByLimit(query);
if (ObjectUtil.isEmpty(robotInformationDOS)) {
return new ArrayList<>();
}
List<RobotInformationRespVO> list = BeanUtils.toBean(robotInformationDOS, RobotInformationRespVO.class);
for (RobotInformationRespVO v : list) {
String errorMsgKey = RobotTaskChcheConstant.ROBOT_ERROR_MSG + v.getMacAddress();
Object errorMsg = redisUtil.get(errorMsgKey);
if (ObjectUtil.isNotEmpty(errorMsg)) {
v.setErrorMsg(String.valueOf(errorMsg));
}
}
return list;
}
}

View File

@ -3,6 +3,7 @@ package cn.iocoder.yudao.module.system.service.robot;
import cn.hutool.core.util.ObjectUtil;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskDetailAddVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskDetailPageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskDetailRespVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskDetailSaveReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotTaskDetailDO;
import cn.iocoder.yudao.module.system.dal.mysql.robot.RobotTaskDetailMapper;
@ -86,6 +87,8 @@ public class RobotTaskDetailServiceImpl implements RobotTaskDetailService {
@Override
@Transactional(rollbackFor = Exception.class)
public void insertRobotDetailList(List<RobotTaskDetailAddVO> taskDetailList) {
taskDetailMapper.insertBatchList(taskDetailList);
List<RobotTaskDetailDO> bean = BeanUtils.toBean(taskDetailList, RobotTaskDetailDO.class);
taskDetailMapper.insertBatch(bean);
// taskDetailMapper.insertBatchList(taskDetailList);
}
}

View File

@ -6,6 +6,7 @@ import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.pojo.PageParam;
import cn.iocoder.yudao.module.system.controller.admin.robot.detail.RobotTaskDetailLogResoVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.detail.RobotTaskDetailLogVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskDetailAddVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskPageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskRespVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskSaveReqVO;
@ -75,4 +76,13 @@ public interface RobotTaskService extends IService<RobotTaskDO> {
* @return
*/
PageResult<RobotTaskDetailLogResoVO> logPage( RobotTaskDetailLogVO pageReqVO);
/**
* 添加循环任务点位
* @param id
* @param taskDetailList
*/
void addCycle(Long id, List<RobotTaskDetailAddVO> taskDetailList);
void closeTask(@Valid RobotTaskSaveReqVO updateReqVO);
}

View File

@ -3,33 +3,50 @@ package cn.iocoder.yudao.module.system.service.robot;
import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.json.JSONUtil;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.util.date.DateUtils;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
import cn.iocoder.yudao.framework.mybatis.core.util.MyBatisUtils;
import cn.iocoder.yudao.module.mqtt.enums.path.TaskTypeEnum;
import cn.iocoder.yudao.module.system.api.robot.dto.RobotStatusDataPoseDTO;
import cn.iocoder.yudao.module.system.constant.robot.RobotTaskChcheConstant;
import cn.iocoder.yudao.module.system.controller.admin.robot.detail.RobotTaskDetailLogResoVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.detail.RobotTaskDetailLogVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.task.TaskPPDistribution;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.*;
import cn.iocoder.yudao.module.system.dal.dataobject.cycle.TaskCycleDO;
import cn.iocoder.yudao.module.system.dal.dataobject.housearea.HouseAreaDO;
import cn.iocoder.yudao.module.system.dal.dataobject.houselane.WareHouseLaneDO;
import cn.iocoder.yudao.module.system.dal.dataobject.houselocation.WareHouseLocationDO;
import cn.iocoder.yudao.module.system.dal.dataobject.information.DeviceInformationDO;
import cn.iocoder.yudao.module.system.dal.dataobject.positionmap.PositionMapDO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotChargeLogDO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotInformationDO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotTaskDO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotTaskDetailDO;
import cn.iocoder.yudao.module.system.dal.mysql.cycle.TaskCycleMapper;
import cn.iocoder.yudao.module.system.dal.mysql.housearea.HouseAreaMapper;
import cn.iocoder.yudao.module.system.dal.mysql.houselane.WareHouseLaneMapper;
import cn.iocoder.yudao.module.system.dal.mysql.houselocation.WareHouseLocationMapper;
import cn.iocoder.yudao.module.system.dal.mysql.information.DeviceInformationMapper;
import cn.iocoder.yudao.module.system.dal.mysql.robot.RobotChargeLogMapper;
import cn.iocoder.yudao.module.system.dal.mysql.robot.RobotInformationMapper;
import cn.iocoder.yudao.module.system.dal.mysql.robot.RobotTaskDetailMapper;
import cn.iocoder.yudao.module.system.dal.mysql.robot.RobotTaskMapper;
import cn.iocoder.yudao.module.system.enums.common.ZeroOneEnum;
import cn.iocoder.yudao.module.system.enums.device.DeviceUseStatusEnum;
import cn.iocoder.yudao.module.system.enums.redis.RobotCacheLockEnum;
import cn.iocoder.yudao.module.system.enums.robot.*;
import cn.iocoder.yudao.module.system.enums.robot.charge.ChargeTaskStatusEnum;
import cn.iocoder.yudao.module.system.service.robot.job.RobotCommonTaskService;
import cn.iocoder.yudao.module.system.util.redis.RedisUtil;
import cn.iocoder.yudao.module.system.util.redis.RedissonUtils;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.segments.MergeSegments;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.google.common.collect.Lists;
@ -48,6 +65,7 @@ import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.function.Function;
import java.util.stream.Collectors;
import java.util.stream.Stream;
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception0;
@ -100,9 +118,25 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
@Value("${zn.task-no:ZN}")
private String taskNo;
@Value("${zn.do_cycle:true}")
private Boolean doCycle;
@Value("${zn.task.check_sku_info:true}")
private Boolean checkSkuInfo;
@Resource
private WareHouseLaneMapper houseLaneMapper;
@Resource
private HouseAreaMapper houseAreaMapper;
@Resource
private TaskCycleMapper taskCycleMapper;
@Resource
private DeviceInformationMapper deviceInformationMapper;
@Override
@Transactional(rollbackFor = Exception.class)
public Long createTask(RobotTaskSaveReqVO createReqVO) throws InterruptedException {
@ -140,6 +174,7 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
/**
* 校验
*
* @param createReqVO
*/
private void doTaskCheck(RobotTaskSaveReqVO createReqVO) {
@ -189,6 +224,7 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
/**
* 添加任务
*
* @param createReqVO
*/
@Transactional(rollbackFor = Exception.class)
@ -196,12 +232,27 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
RobotTaskDO task = BeanUtils.toBean(createReqVO, RobotTaskDO.class);
taskMapper.insert(task);
List<Long> laneIds = new ArrayList<>();
List<Long> areaIds = new ArrayList<>();
if (ObjectUtil.isNotEmpty(task.getSkuInfo()) && checkSkuInfo) {
List<WareHouseLaneDO> wareHouseLaneDOS = houseLaneMapper.selectList(new LambdaQueryWrapper<WareHouseLaneDO>()
.eq(WareHouseLaneDO::getLaneMsg, task.getSkuInfo()));
if (ObjectUtil.isNotEmpty(wareHouseLaneDOS)) {
laneIds = wareHouseLaneDOS.stream().map(WareHouseLaneDO::getId).collect(Collectors.toList());
}
List<HouseAreaDO> houseAreaDOS = houseAreaMapper.selectList(new LambdaQueryWrapper<HouseAreaDO>()
.eq(HouseAreaDO::getSkuInfo, task.getSkuInfo()));
if (ObjectUtil.isNotEmpty(houseAreaDOS)) {
areaIds = houseAreaDOS.stream().map(HouseAreaDO::getId).collect(Collectors.toList());
}
}
//查找库位
List<Long> locationIds = new ArrayList<>();
if (MoveAllEnum.NO.getType().equals(createReqVO.getDoMoveAll())) {
locationIds = setSingleLocationIdNo(createReqVO.getTaskDetailList(),task);
locationIds = setSingleLocationIdNo(createReqVO.getTaskDetailList(), task, laneIds, areaIds);
} else {
locationIds = setAllLocationIdNo(createReqVO,task.getId());
locationIds = setAllLocationIdNo(createReqVO, task.getId(), laneIds, areaIds, task.getSkuInfo());
}
// 插入
@ -216,21 +267,165 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
locationMapper.updateLocationLockList(list, task.getId(), LocationLockEnum.NO.getType());
});
if (doCycle && ObjectUtil.isNotEmpty(createReqVO.getDoCycle())
&& ZeroOneEnum.ONE.getType().equals(createReqVO.getDoCycle().intValue())) {
addCycle(task.getId(), createReqVO.getTaskDetailList());
}
return RESULT;
}
@Transactional(rollbackFor = Exception.class)
public void addCycle(Long id, List<RobotTaskDetailAddVO> taskDetailList) {
List<TaskCycleDO> cycleDOList = new ArrayList<>();
List<Long> laneIds = new ArrayList<>();
List<Long> areaIds = new ArrayList<>();
List<Long> locationIds = new ArrayList<>();
for (RobotTaskDetailAddVO detailAddVO : taskDetailList) {
if (ReleaseTakeEnum.TO_LANE.getType().equals(detailAddVO.getTakeType())) {
laneIds.add(detailAddVO.getTakeId());
} else if (ReleaseTakeEnum.TO_AREA.getType().equals(detailAddVO.getTakeType())) {
areaIds.add(detailAddVO.getTakeId());
} else if (ReleaseTakeEnum.TO_LOCATION.getType().equals(detailAddVO.getTakeType())) {
locationIds.add(detailAddVO.getTakeId());
}
if (ReleaseTakeEnum.TO_LANE.getType().equals(detailAddVO.getReleaseType())) {
laneIds.add(detailAddVO.getTakeId());
} else if (ReleaseTakeEnum.TO_AREA.getType().equals(detailAddVO.getReleaseType())) {
areaIds.add(detailAddVO.getTakeId());
} else if (ReleaseTakeEnum.TO_LOCATION.getType().equals(detailAddVO.getReleaseType())) {
locationIds.add(detailAddVO.getTakeId());
}
}
LambdaQueryWrapper<WareHouseLocationDO> wrapper = new LambdaQueryWrapper<>();
if (ObjectUtil.isNotEmpty(laneIds)) {
wrapper.or(w -> w.in(WareHouseLocationDO::getLaneId, laneIds));
}
if (ObjectUtil.isNotEmpty(areaIds)) {
wrapper.or(w -> w.in(WareHouseLocationDO::getAreaId, areaIds));
}
if (ObjectUtil.isNotEmpty(locationIds)) {
wrapper.or(w -> w.in(WareHouseLocationDO::getId, locationIds));
}
List<WareHouseLocationDO> wareHouseLocationDOS = locationMapper.selectList(wrapper);
wareHouseLocationDOS
.stream()
.map(WareHouseLocationDO::getMapItemId)
.forEach(mapItemId -> {
TaskCycleDO build = TaskCycleDO.builder().robotTaskId(id).mapItemId(mapItemId).build();
cycleDOList.add(build);
});
taskCycleMapper.insertBatch(cycleDOList);
}
/**
* 关闭任务
*
* @param updateReqVO
*/
@Override
public void closeTask(RobotTaskSaveReqVO updateReqVO) {
// 校验存在
validateTaskExists(updateReqVO.getId());
if (ObjectUtil.isEmpty(updateReqVO.getId())) {
throw exception(TASK_CHECK_ID_EXCEPTION);
}
// 更新
//修改优先级需要订单状态为未开始/处理中
RobotTaskDO robotTaskDO = taskMapper.selectById(updateReqVO.getId());
List<RobotTaskDetailDO> taskDetailDOS = taskDetailMapper.queryByTaskId(updateReqVO.getId());
//修改订单状态
/*if (ObjectUtil.isNotEmpty(updateReqVO.getTaskStatus())
&& RobotTaskStatusEnum.DONE.getType().equals(robotTaskDO.getTaskStatus())
&& !robotTaskDO.getTaskStatus().equals(updateReqVO.getTaskStatus())) {
throw exception(TASK_CHECK_TASK_STATUS);
}*/
List<Long> locationIds = new ArrayList<>();
Set<String> robotNos = new HashSet<>();
for (RobotTaskDetailDO taskDetailDO : taskDetailDOS) {
if (!(RobotTaskDetailStatusEnum.NEW.getType().equals(taskDetailDO.getTaskStatus())
&& RobotTaskDetailStatusEnum.DOING.getType().equals(taskDetailDO.getTaskStatus()))) {
continue;
}
//后期需做状态映射
taskDetailDO.setTaskStatus(updateReqVO.getTaskStatus());
// todo 关闭需要下发任务给车机 还需要考虑下处理中的任务怎么处理
// todo 清楚交管
if (ObjectUtil.isNotEmpty(taskDetailDO.getFromLocationId())) {
locationIds.add(taskDetailDO.getFromLocationId());
}
if (ObjectUtil.isNotEmpty(taskDetailDO.getToLocationId())) {
locationIds.add(taskDetailDO.getToLocationId());
}
if (ObjectUtil.isNotEmpty(taskDetailDO.getRobotNo())
&& RobotTaskDetailStatusEnum.DOING.getType().equals(taskDetailDO.getTaskStatus())) {
robotNos.add(taskDetailDO.getRobotNo());
}
}
RobotTaskDO updateObj = BeanUtils.toBean(updateReqVO, RobotTaskDO.class);
taskMapper.updateById(updateObj);
taskDetailMapper.updateBatch(taskDetailDOS);
if (ObjectUtil.isNotEmpty(locationIds)) {
locationMapper.releaseLocationLockList(locationIds, robotTaskDO.getId()
, LocationLockEnum.YES.getType());
}
// todo 执行中的需要锁车 需要添加执行中的判断
if (ObjectUtil.isNotEmpty(robotNos)) {
List<RobotInformationDO> robotInformationDOS = informationMapper.selectList(new LambdaQueryWrapper<RobotInformationDO>()
.eq(RobotInformationDO::getRobotStatus, RobotStatusEnum.DOING.getType())
.in(RobotInformationDO::getRobotNo, robotNos));
// informationMapper.updateRobotTaskModel(robotNos,RobotTaskModelEnum.REJECTION.getType());
}
}
/**
* 设置放货和取货的id
*
* @param createReqVO
* @param taskId
*/
@Transactional(rollbackFor = Exception.class)
public List<Long> setAllLocationIdNo(RobotTaskSaveReqVO createReqVO, Long taskId) {
public List<Long> setAllLocationIdNo(RobotTaskSaveReqVO createReqVO, Long taskId,
List<Long> laneIds, List<Long> areaIds, String skuInfo) {
List<RobotTaskDetailAddVO> taskDetailList = createReqVO.getTaskDetailList();
List<RobotTaskDetailAddVO> newTaskDetailList = new ArrayList<>();
List<Long> toLocationIds = new ArrayList<>(); //被此次任务锁定的空库位id
List<Long> fromLocationIds = new ArrayList<>(); //被此次任务锁定的有货库位id
List<Long> mapItemIds = new ArrayList<>();
if (doCycle) {
List<TaskCycleDO> taskCycleDOS = taskCycleMapper.selectList(new LambdaQueryWrapper<TaskCycleDO>());
if (ObjectUtil.isNotEmpty(taskCycleDOS)) {
mapItemIds = taskCycleDOS.stream().map(TaskCycleDO::getMapItemId).collect(Collectors.toList());
}
}
List<WareHouseLocationDO> wareHouseLocationDOS = locationMapper.selectList(new LambdaQueryWrapper<WareHouseLocationDO>()
.eq(WareHouseLocationDO::getLocationEnable, LocationEnableEnum.NO.getType()));
if (ObjectUtil.isNotEmpty(wareHouseLocationDOS)) {
List<Long> mapItemList = wareHouseLocationDOS.stream().map(WareHouseLocationDO::getMapItemId)
.collect(Collectors.toList());
mapItemIds.addAll(mapItemList);
}
//被此次任务锁定的空库位id
List<Long> toLocationIds = new ArrayList<>();
//被此次任务锁定的有货库位id
List<Long> fromLocationIds = new ArrayList<>();
for (RobotTaskDetailAddVO robotTaskVo : taskDetailList) {
Set<Long> mapIds = new HashSet<>();
if (ObjectUtil.isNotEmpty(robotTaskVo.getRobotNo())) {
@ -260,7 +455,8 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
.build();
}
List<WareHouseLocationDO> stockList = locationMapper.selectLocations(query,toLocationIds,mapIds);
List<WareHouseLocationDO> stockList = locationMapper.selectLocations(query, toLocationIds, mapIds,
new ArrayList<>(), new ArrayList<>(), new ArrayList<>());
if (ObjectUtil.isEmpty(stockList)) {
log.error("取货线库/区域为空或者已锁定或者机器人取放货区域受限制 :{}", robotTaskVo.toString());
throw new RuntimeException("取货线库/区域为空或者已锁定或者机器人取放货区域受限制");
@ -274,6 +470,10 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
//查找空库位
WareHouseLocationDO releaseQuery = null;
if (ReleaseTakeEnum.TO_LANE.getType().equals(robotTaskVo.getReleaseType())) {
if (ObjectUtil.isEmpty(laneIds) && ObjectUtil.isNotEmpty(skuInfo)) {
log.error("查不到此物料对应的线库区域 :{}", robotTaskVo.getReleaseId());
throw new RuntimeException("查不到此物料对应的线库区域 " + skuInfo);
}
releaseQuery = WareHouseLocationDO.builder()
.laneId(robotTaskVo.getReleaseId())
.locationEnable(LocationEnableEnum.YES.getType())
@ -281,6 +481,10 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
.locationUseStatus(LocationUseStatusEnum.NO.getType())
.build();
} else if (ReleaseTakeEnum.TO_AREA.getType().equals(robotTaskVo.getReleaseType())) {
if (ObjectUtil.isEmpty(areaIds) && ObjectUtil.isNotEmpty(skuInfo)) {
log.error("查不到此物料对应的区域库位 :{}", robotTaskVo.getReleaseId());
throw new RuntimeException("查不到此物料对应的区域库位 " + skuInfo);
}
releaseQuery = WareHouseLocationDO.builder()
.areaId(robotTaskVo.getReleaseId())
.locationEnable(LocationEnableEnum.YES.getType())
@ -289,11 +493,13 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
.build();
}
List<WareHouseLocationDO> releaseStockList = locationMapper.selectLocations(releaseQuery,toLocationIds,mapIds);
List<WareHouseLocationDO> releaseStockList = locationMapper.selectLocations(releaseQuery, toLocationIds, mapIds,
laneIds, areaIds, mapItemIds);
if (ObjectUtil.isEmpty(releaseStockList) || releaseStockList.size() < stockList.size()) {
log.error("放货线库/区域库位数量不足或者机器人取放货区域受限制 :{}", robotTaskVo.toString());
throw new RuntimeException("放货线库/区域库位数量不足或者机器人取放货区域受限制");
}
Collections.reverse(releaseStockList);
//赋值数据
List<RobotTaskDetailAddVO> addTaskDetailList = getTaskDatail(stockList, releaseStockList, toLocationIds,
robotTaskVo, taskId, fromLocationIds);
@ -311,6 +517,7 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
/**
* 赋值数据
*
* @param stockList
* @param releaseStockList
* @param toLocationIds
@ -337,7 +544,8 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
robotTaskDetailAddVo.setFromLaneId(stockList.get(i).getLaneId());
robotTaskDetailAddVo.setToLaneId(releaseStockList.get(i).getLaneId());
robotTaskDetailAddVo.setFromLocationNumber(stockList.get(i).getLocationNumber());
robotTaskDetailAddVo.setFromMapId(stockList.get(i).getMapId());
robotTaskDetailAddVo.setFromMapItemId(stockList.get(i).getMapItemId());
robotTaskDetailAddVo.setToMapItemId(releaseStockList.get(i).getMapItemId());
robotTaskDetailAddVo.setRobotTaskId(taskId);
robotTaskDetailAddVo.setPriority(robotTaskVo.getPriority());
robotTaskDetailAddVo.setFromLocationStorey(stockList.get(i).getLocationStorey());
@ -352,40 +560,72 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
/**
* 设置放货和取货的id
*
* @param taskDetailList
* @return
*/
@Transactional(rollbackFor = Exception.class)
public List<Long> setSingleLocationIdNo(List<RobotTaskDetailAddVO> taskDetailList, RobotTaskDO task){
public List<Long> setSingleLocationIdNo(List<RobotTaskDetailAddVO> taskDetailList, RobotTaskDO task,
List<Long> laneIds, List<Long> areaIds) {
//取货中的map_item_id 此集合不能执行放货的任务
List<Long> takeMapItemIds = taskDetailMapper.selectTakeMapItemIds();
if (ObjectUtil.isEmpty(takeMapItemIds)) {
takeMapItemIds = new ArrayList<>();
}
//放货中的map_item_id 此集合不能执行取货的任务
List<Long> releaseMapItemIds = taskDetailMapper.selectReleaseMapItemIds();
if (ObjectUtil.isEmpty(releaseMapItemIds)) {
releaseMapItemIds = new ArrayList<>();
}
if (doCycle) {
List<TaskCycleDO> taskCycleDOS = taskCycleMapper.selectList(new LambdaQueryWrapper<TaskCycleDO>());
if (ObjectUtil.isNotEmpty(taskCycleDOS)) {
List<Long> mapItemIds =
taskCycleDOS.stream().map(TaskCycleDO::getMapItemId).collect(Collectors.toList());
takeMapItemIds.addAll(mapItemIds);
releaseMapItemIds.addAll(mapItemIds);
}
}
List<WareHouseLocationDO> wareHouseLocationDOS = locationMapper.selectList(new LambdaQueryWrapper<WareHouseLocationDO>()
.eq(WareHouseLocationDO::getLocationEnable, LocationEnableEnum.NO.getType()));
if (ObjectUtil.isNotEmpty(wareHouseLocationDOS)) {
List<Long> mapItemList = wareHouseLocationDOS.stream().map(WareHouseLocationDO::getMapItemId)
.collect(Collectors.toList());
releaseMapItemIds.addAll(mapItemList);
}
List<Long> locationIds = new ArrayList<>();
for (RobotTaskDetailAddVO robotTaskVo : taskDetailList) {
robotTaskVo.setRobotTaskId(task.getId());
robotTaskVo.setPriority(task.getPriority());
RobotTaskTypeEnum robotTaskType = RobotTaskTypeEnum.getRobotTaskType(robotTaskVo.getTaskType());
switch (robotTaskType) {
case TAKE_RELEASE:
doTakeRelease(robotTaskVo,locationIds);
doTakeRelease(robotTaskVo, locationIds, takeMapItemIds, releaseMapItemIds, laneIds, areaIds, task.getSkuInfo());
break;
case PARK:
doPark(robotTaskVo,locationIds);
doPark(robotTaskVo, locationIds, takeMapItemIds, releaseMapItemIds);
break;
case CHARGE:
doCharge(robotTaskVo);
doCharge(robotTaskVo, takeMapItemIds, releaseMapItemIds);
break;
case MOVE:
doMove(robotTaskVo,locationIds);
doMove(robotTaskVo, locationIds, takeMapItemIds, releaseMapItemIds);
break;
case TAKE:
doTake(robotTaskVo,locationIds);
doTake(robotTaskVo, locationIds, takeMapItemIds, releaseMapItemIds);
break;
case RELEASE:
doRelease(robotTaskVo,locationIds);
doRelease(robotTaskVo, locationIds, takeMapItemIds, releaseMapItemIds, laneIds, areaIds, task.getSkuInfo());
break;
case SCAN:
doScan(robotTaskVo,locationIds);
//暂无此功能
doScan(robotTaskVo, locationIds, takeMapItemIds, releaseMapItemIds);
break;
case DETECTING_TRAYS:
doDetectingTrays(robotTaskVo,locationIds);
//暂无此功能
doDetectingTrays(robotTaskVo, locationIds, takeMapItemIds, releaseMapItemIds);
break;
default:
log.error("任务类型不存在 ");
@ -397,73 +637,88 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
/**
* 检测托盘类型
*
* @param robotTaskVo
*/
@Transactional(rollbackFor = Exception.class)
public void doDetectingTrays(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds) {
setToLocation(robotTaskVo,getMapIdsByRobotNo(robotTaskVo.getRobotNo()),new ArrayList<>());
locationIds.add(robotTaskVo.getToLocationId());
public void doDetectingTrays(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds, List<Long> takeMapItemIds,
List<Long> releaseMapItemIds) {
/*setToLocation(robotTaskVo,getMapIdsByRobotNo(robotTaskVo.getRobotNo()),new ArrayList<>());
locationIds.add(robotTaskVo.getToLocationId());*/
}
/**
* 扫描码
*
* @param robotTaskVo
*/
@Transactional(rollbackFor = Exception.class)
public void doScan(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds) {
setToLocation(robotTaskVo,getMapIdsByRobotNo(robotTaskVo.getRobotNo()),new ArrayList<>());
locationIds.add(robotTaskVo.getToLocationId());
public void doScan(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds, List<Long> takeMapItemIds,
List<Long> releaseMapItemIds) {
/*setToLocation(robotTaskVo,getMapIdsByRobotNo(robotTaskVo.getRobotNo()),new ArrayList<>());
locationIds.add(robotTaskVo.getToLocationId());*/
}
/**
* 仅放货
*
* @param robotTaskVo
*/
@Transactional(rollbackFor = Exception.class)
public void doRelease(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds) {
setToLocation(robotTaskVo,getMapIdsByRobotNo(robotTaskVo.getRobotNo()),locationIds);
public void doRelease(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds, List<Long> takeMapItemIds,
List<Long> releaseMapItemIds, List<Long> laneIds, List<Long> areaIds, String skuInfo) {
setToLocation(robotTaskVo, getMapIdsByRobotNo(robotTaskVo.getRobotNo()), locationIds, takeMapItemIds, releaseMapItemIds, laneIds, areaIds, skuInfo);
locationIds.add(robotTaskVo.getToLocationId());
}
/**
* 仅取货
*
* @param robotTaskVo
*/
@Transactional(rollbackFor = Exception.class)
public void doTake(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds) {
public void doTake(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds, List<Long> takeMapItemIds,
List<Long> releaseMapItemIds) {
Set<Long> mapIds = new HashSet<>();
if (ObjectUtil.isNotEmpty(robotTaskVo.getRobotNo())) {
mapIds = getMapIdsByRobotNo(robotTaskVo.getRobotNo());
}
setFromLocation(robotTaskVo,mapIds,locationIds);
setFromLocation(robotTaskVo, mapIds, locationIds, takeMapItemIds, releaseMapItemIds);
locationIds.add(robotTaskVo.getFromLocationId());
}
/**
* 移动
*
* @param robotTaskVo
*/
@Transactional(rollbackFor = Exception.class)
public void doMove(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds) {
setToLocation(robotTaskVo,getMapIdsByRobotNo(robotTaskVo.getRobotNo()),locationIds);
public void doMove(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds, List<Long> takeMapItemIds,
List<Long> releaseMapItemIds) {
setToLocation(robotTaskVo, getMapIdsByRobotNo(robotTaskVo.getRobotNo()), locationIds, takeMapItemIds, releaseMapItemIds,
null, null, null);
locationIds.add(robotTaskVo.getToLocationId());
}
/**
* 充电
*
* @param robotTaskVo
*/
@Transactional(rollbackFor = Exception.class)
public void doCharge(RobotTaskDetailAddVO robotTaskVo) {
public void doCharge(RobotTaskDetailAddVO robotTaskVo, List<Long> takeMapItemIds,
List<Long> releaseMapItemIds) {
}
/**
* 停车
*
* @param robotTaskVo
*/
@Transactional(rollbackFor = Exception.class)
public void doPark(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds) {
public void doPark(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds, List<Long> takeMapItemIds,
List<Long> releaseMapItemIds) {
// todo 停车后续停到等待点
/*setToLocation(robotTaskVo,getMapIdsByRobotNo(robotTaskVo.getRobotNo()),locationIds);
locationIds.add(robotTaskVo.getToLocationId());*/
@ -471,6 +726,7 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
/**
* 查询此机器人对应的楼层/区域(json)
*
* @param robotNo
* @return
*/
@ -491,7 +747,9 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
* 设置停车/目标库位/扫描库位
*/
@Transactional(rollbackFor = Exception.class)
public void setToLocation(RobotTaskDetailAddVO robotTaskVo, Set<Long> mapIds, List<Long> locationIds){
public void setToLocation(RobotTaskDetailAddVO robotTaskVo, Set<Long> mapIds, List<Long> locationIds,
List<Long> takeMapItemIds, List<Long> releaseMapItemIds,
List<Long> laneIds, List<Long> areaIds, String skuInfo) {
if (ReleaseTakeEnum.TO_LOCATION.getType().equals(robotTaskVo.getReleaseType())) {
WareHouseLocationDO query = WareHouseLocationDO.builder().id(robotTaskVo.getReleaseId()).build();
WareHouseLocationDO locationDO = locationMapper.queryAllByLimit(query);
@ -500,15 +758,30 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
robotTaskVo.setToLocationStorey(locationDO.getLocationStorey());
robotTaskVo.setToLaneId(locationDO.getLaneId());
robotTaskVo.setToLocationNumber(locationDO.getLocationNumber());
robotTaskVo.setToMapId(locationDO.getMapId());
robotTaskVo.setToMapItemId(locationDO.getMapItemId());
if (ObjectUtil.isNotEmpty(mapIds) && !mapIds.contains(locationDO.getMapId())) {
log.error("机器人不能在此放货库位放货 :{}, 机器人编号 :{}", locationDO.getLocationNo(), robotTaskVo.getRobotNo());
throw new RuntimeException("机器人不能在此放货库位放货 " + robotTaskVo.getReleaseId());
}
if (ObjectUtil.isNotEmpty(takeMapItemIds) && takeMapItemIds.contains(locationDO.getMapItemId())) {
log.error("此点位存在取货任务 :{}", locationDO.getLocationNo());
throw new RuntimeException("此库位存在取货任务 " + locationDO.getLocationNo());
}
releaseMapItemIds.add(locationDO.getMapItemId());
} else {
if (ReleaseTakeEnum.TO_LANE.getType().equals(robotTaskVo.getReleaseType()) && ObjectUtil.isEmpty(laneIds)
&& ObjectUtil.isNotEmpty(skuInfo)) {
log.error("查不到此物料对应的线库区域 :{}", robotTaskVo.getReleaseId());
throw new RuntimeException("查不到此物料对应的线库区域 " + skuInfo);
}
if (ReleaseTakeEnum.TO_AREA.getType().equals(robotTaskVo.getReleaseType()) && ObjectUtil.isEmpty(areaIds)
&& ObjectUtil.isNotEmpty(skuInfo)) {
log.error("查不到此物料对应的区域库位 :{}", robotTaskVo.getReleaseId());
throw new RuntimeException("查不到此物料对应的区域库位 " + skuInfo);
}
WareHouseLocationDO wareHouseLocationDO =
locationMapper.selectByTypeAndId(LocationUseStatusEnum.NO.getType(), robotTaskVo.getReleaseType()
,robotTaskVo.getReleaseId(),locationIds,mapIds);
, robotTaskVo.getReleaseId(), locationIds, mapIds, takeMapItemIds, laneIds, areaIds);
if (ObjectUtil.isEmpty(wareHouseLocationDO)) {
log.error("放货库位为空或者已锁定或者机器人取放货区域受限制 :{}", robotTaskVo.getReleaseId());
throw new RuntimeException("放货库位为空或者已锁定或者机器人取放货区域受限制 " + robotTaskVo.getReleaseId());
@ -518,18 +791,21 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
robotTaskVo.setToLocationStorey(wareHouseLocationDO.getLocationStorey());
robotTaskVo.setToLaneId(wareHouseLocationDO.getLaneId());
robotTaskVo.setToLocationNumber(wareHouseLocationDO.getLocationNumber());
robotTaskVo.setToMapId(wareHouseLocationDO.getMapId());
robotTaskVo.setToMapItemId(wareHouseLocationDO.getMapItemId());
releaseMapItemIds.add(wareHouseLocationDO.getMapItemId());
}
}
/**
* 设置取货库位
*
* @param robotTaskVo
* @param mapIds
* @param locationIds
*/
@Transactional(rollbackFor = Exception.class)
public void setFromLocation(RobotTaskDetailAddVO robotTaskVo, Set<Long> mapIds, List<Long> locationIds) {
public void setFromLocation(RobotTaskDetailAddVO robotTaskVo, Set<Long> mapIds, List<Long> locationIds,
List<Long> takeMapItemIds, List<Long> releaseMapItemIds) {
if (ReleaseTakeEnum.TO_LOCATION.getType().equals(robotTaskVo.getTakeType())) {
WareHouseLocationDO query = WareHouseLocationDO.builder().id(robotTaskVo.getTakeId()).build();
WareHouseLocationDO locationDO = locationMapper.queryAllByLimit(query);
@ -538,15 +814,20 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
robotTaskVo.setFromLocationStorey(locationDO.getLocationStorey());
robotTaskVo.setFromLaneId(locationDO.getLaneId());
robotTaskVo.setFromLocationNumber(locationDO.getLocationNumber());
robotTaskVo.setFromMapId(locationDO.getMapId());
robotTaskVo.setFromMapItemId(locationDO.getMapItemId());
if (ObjectUtil.isNotEmpty(mapIds) && !mapIds.contains(locationDO.getMapId())) {
log.error("机器人不能在此取货库位取货 :{}, 机器人编号 :{}", locationDO.getLocationNo(), robotTaskVo.getRobotNo());
throw new RuntimeException("机器人不能在此取货库位取货 " + robotTaskVo.getTakeId());
}
if (ObjectUtil.isNotEmpty(releaseMapItemIds) && releaseMapItemIds.contains(locationDO.getMapItemId())) {
log.error("此取货库位存在放货任务 :{}", locationDO.getLocationNo());
throw new RuntimeException("此取货库位存在放货任务 " + locationDO.getLocationNo());
}
takeMapItemIds.add(locationDO.getMapItemId());
} else {
WareHouseLocationDO wareHouseLocationDO =
locationMapper.selectByTypeAndId(LocationUseStatusEnum.YES.getType(), robotTaskVo.getTakeType(),
robotTaskVo.getTakeId(),locationIds,mapIds);
robotTaskVo.getTakeId(), locationIds, mapIds, releaseMapItemIds, new ArrayList<>(), new ArrayList<>());
if (ObjectUtil.isEmpty(wareHouseLocationDO)) {
log.error("取货库位为空或者已锁定或者机器人取放货区域受限制 :{}", robotTaskVo.getTakeId());
throw new RuntimeException("取货库位为空或者已锁定或者机器人取放货区域受限制 " + robotTaskVo.getTakeId());
@ -556,27 +837,31 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
robotTaskVo.setFromLocationStorey(wareHouseLocationDO.getLocationStorey());
robotTaskVo.setFromLaneId(wareHouseLocationDO.getLaneId());
robotTaskVo.setFromLocationNumber(wareHouseLocationDO.getLocationNumber());
robotTaskVo.setFromMapId(wareHouseLocationDO.getMapId());
robotTaskVo.setFromMapItemId(wareHouseLocationDO.getMapItemId());
takeMapItemIds.add(wareHouseLocationDO.getMapItemId());
}
}
/**
* 取放
*
* @param robotTaskVo
*/
@Transactional(rollbackFor = Exception.class)
public void doTakeRelease(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds) {
public void doTakeRelease(RobotTaskDetailAddVO robotTaskVo, List<Long> locationIds,
List<Long> takeMapItemIds, List<Long> releaseMapItemIds,
List<Long> laneIds, List<Long> areaIds, String skuInfo) {
Set<Long> mapIds = new HashSet<>();
if (ObjectUtil.isNotEmpty(robotTaskVo.getRobotNo())) {
mapIds = getMapIdsByRobotNo(robotTaskVo.getRobotNo());
}
//校验放货库位
setToLocation(robotTaskVo, mapIds,locationIds);
setToLocation(robotTaskVo, mapIds, locationIds, takeMapItemIds, releaseMapItemIds, laneIds, areaIds, skuInfo);
locationIds.add(robotTaskVo.getToLocationId());
//校验取货库位
setFromLocation(robotTaskVo,mapIds,locationIds);
setFromLocation(robotTaskVo, mapIds, locationIds, takeMapItemIds, releaseMapItemIds);
locationIds.add(robotTaskVo.getFromLocationId());
//验证取货库位是否存在未完成的任务
@ -593,10 +878,7 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
@Override
@Transactional(rollbackFor = Exception.class)
public void updateTask(RobotTaskSaveReqVO updateReqVO) {
RLock lock = redissonUtils.getLock(RobotCacheLockEnum.ROBOT_TASK_DISTRIBUTE_LOCK.getKey());
String msg = "";
if (lock.tryLock()){
try {
// 校验存在
validateTaskExists(updateReqVO.getId());
if (ObjectUtil.isEmpty(updateReqVO.getId())) {
@ -608,77 +890,19 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
List<RobotTaskDetailDO> taskDetailDOS = taskDetailMapper.queryByTaskId(updateReqVO.getId());
if (ObjectUtil.isNotEmpty(updateReqVO.getPriority())
&& !updateReqVO.getPriority().equals(robotTaskDO.getPriority())) {
if (!RobotTaskStatusEnum.NEW.getType().equals(robotTaskDO.getTaskStatus())
/*if (!RobotTaskStatusEnum.NEW.getType().equals(robotTaskDO.getTaskStatus())
&& !RobotTaskStatusEnum.DOING.getType().equals(robotTaskDO.getTaskStatus())) {
throw exception(TASK_CHECK_TASK_PRIORITY);
}
}*/
for (RobotTaskDetailDO taskDetailDO : taskDetailDOS) {
taskDetailDO.setPriority(updateReqVO.getPriority());
}
}
//修改订单状态
if (ObjectUtil.isNotEmpty(updateReqVO.getTaskStatus())
&& RobotTaskStatusEnum.DONE.getType().equals(robotTaskDO.getTaskStatus())
&& !robotTaskDO.getTaskStatus().equals(updateReqVO.getTaskStatus())) {
throw exception(TASK_CHECK_TASK_STATUS);
}
List<Long> locationIds = new ArrayList<>();
Set<String> robotNos = new HashSet<>();
if (ObjectUtil.isNotEmpty(updateReqVO.getTaskStatus())
&& RobotTaskStatusEnum.CLOSE.getType().equals(updateReqVO.getTaskStatus())
&& !robotTaskDO.getTaskStatus().equals(updateReqVO.getTaskStatus())) {
for (RobotTaskDetailDO taskDetailDO : taskDetailDOS) {
if (!(RobotTaskDetailStatusEnum.NEW.getType().equals(taskDetailDO.getTaskStatus())
&& RobotTaskDetailStatusEnum.DOING.getType().equals(taskDetailDO.getTaskStatus()))) {
continue;
}
//后期需做状态映射
taskDetailDO.setTaskStatus(updateReqVO.getTaskStatus());
// todo 关闭需要下发任务给车机 还需要考虑下处理中的任务怎么处理
// todo 清楚交管
if (ObjectUtil.isNotEmpty(taskDetailDO.getFromLocationId())) {
locationIds.add(taskDetailDO.getFromLocationId());
}
if (ObjectUtil.isNotEmpty(taskDetailDO.getToLocationId())) {
locationIds.add(taskDetailDO.getToLocationId());
}
if (ObjectUtil.isNotEmpty(taskDetailDO.getRobotNo())) {
robotNos.add(taskDetailDO.getRobotNo());
}
}
}
RobotTaskDO updateObj = BeanUtils.toBean(updateReqVO, RobotTaskDO.class);
taskMapper.updateById(updateObj);
taskDetailMapper.updateBatch(taskDetailDOS);
if (ObjectUtil.isNotEmpty(locationIds)) {
locationMapper.updateLocationLockList(locationIds,robotTaskDO.getId()
,LocationLockEnum.YES.getType());
}
// todo 执行中的需要锁车 需要添加执行中的判断
if (ObjectUtil.isNotEmpty(robotNos)) {
// informationMapper.updateRobotTaskModel(robotNos,RobotTaskModelEnum.REJECTION.getType());
}
} catch (Exception e) {
log.error("更新任务失败 :{}",e.getMessage());
msg = e.getMessage();
} finally {
lock.unlock();
}
} else {
throw exception(REDISSON_NOT_OBTAIN_LOCK);
}
if (ObjectUtil.isNotEmpty(msg)) {
throw exception0(TASK_CHECK_UPDATE_STATUS.getCode(), msg);
}
}
@Override
@ -733,6 +957,7 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
/**
* PP分配的任务
*
* @param message
*/
@Override
@ -747,24 +972,21 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
String robotDoingActionKey = RobotTaskChcheConstant.ROBOT_QUERY_DOING_ACTION + mac;
redisUtil.del(robotDoingActionKey);
List<TaskPPDistribution> list = Arrays.asList(distribution);
List<Long> detailIds = new ArrayList<>();
Map<Long, String> deviceNoMap = new HashMap<>();
RobotChargeLogDO robotChargeLogs = null;
Set<String> robotNos = new HashSet<>();
robotNos.add(distribution.getRobotNo());
/**
* 充电
*/
if (TaskTypeEnum.CHARGE.getType().equals(distribution.getType())) {
robotChargeLogs = chargeLogMapper.selectById(distribution.getId());
robotChargeLogs.setTaskStatus(RobotTaskDetailStatusEnum.DOING.getType());
robotChargeLogs.setTaskStatus(ChargeTaskStatusEnum.DOING.getType());
chargeLogMapper.updateBatch(robotChargeLogs);
robotInformationMapper.updateRobotListStatus(robotNos,RobotStatusEnum.CHARGE.getType());
robotInformationMapper.updateRobotListStatus(distribution.getRobotNo(), RobotStatusEnum.CHARGE.getType());
if (ObjectUtil.isNotEmpty(robotChargeLogs.getTaskDetailId())) {
deviceNoMap.put(robotChargeLogs.getTaskDetailId(), robotChargeLogs.getDeviceNo());
detailIds.add(robotChargeLogs.getTaskDetailId());
@ -775,7 +997,8 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
* 任务
*/
if (TaskTypeEnum.TASK.getType().equals(distribution.getType())) {
robotInformationMapper.updateRobotListStatus(robotNos,RobotStatusEnum.DOING.getType());
chargeDone(distribution.getRobotNo());
robotInformationMapper.updateRobotListStatus(distribution.getRobotNo(), RobotStatusEnum.DOING.getType());
detailIds.add(distribution.getId());
}
@ -808,8 +1031,56 @@ public class RobotTaskServiceImpl extends ServiceImpl<RobotTaskMapper,RobotTaskD
robotCommonTaskService.sendChargeTaskToRobot(distribution, robotChargeLogs);
}
/**
* 机器人完成充电
*
* @param robotNo
*/
private void chargeDone(String robotNo) {
RobotInformationDO robotInformationDO = robotInformationMapper.selectOne(new LambdaQueryWrapperX<RobotInformationDO>()
.eq(RobotInformationDO::getRobotNo, robotNo));
if (!RobotStatusEnum.CHARGE.getType().equals(robotInformationDO.getRobotStatus())) {
return;
}
RobotChargeLogDO robotChargeLogDO = chargeLogMapper.selectOne(new LambdaQueryWrapperX<RobotChargeLogDO>()
.eq(RobotChargeLogDO::getRobotNo, robotNo)
.orderByDesc(RobotChargeLogDO::getCreateTime)
.last("limit 1"));
if (ObjectUtil.isEmpty(robotChargeLogDO)) {
return;
}
log.info("开始结束充电,并接任务 :{}", robotNo);
robotChargeLogDO.setEndTime(LocalDateTime.now());
String pose2dKey = RobotTaskChcheConstant.ROBOT_INFORMATION_POSE_BAT_SOC + robotInformationDO.getMacAddress();
Object object = redisUtil.get(pose2dKey);
RobotStatusDataPoseDTO robotStatusDataPoseDTO = JSONUtil.toBean((String) object, RobotStatusDataPoseDTO.class);
if (ObjectUtil.isNotEmpty(object) && ObjectUtil.isNotEmpty(robotStatusDataPoseDTO)) {
robotChargeLogDO.setEndElectricity(Integer.valueOf(robotStatusDataPoseDTO.getBat_soc()));
}
robotChargeLogDO.setTaskStatus(ChargeTaskStatusEnum.DONE.getType());
chargeLogMapper.updateBatch(robotChargeLogDO);
if (ObjectUtil.isEmpty(robotChargeLogDO.getTaskDetailId())) {
return;
}
RobotTaskDetailDO taskDetail = taskDetailMapper.selectById(robotChargeLogDO.getTaskDetailId());
taskDetail.setTaskStatus(RobotTaskDetailStatusEnum.DONE.getType());
taskDetailMapper.updateBatch(taskDetail);
RobotTaskDO robotTask = taskMapper.selectById(taskDetail.getRobotTaskId());
robotTask.setTaskStatus(RobotTaskStatusEnum.DONE.getType());
taskMapper.updateBatch(robotTask);
DeviceInformationDO deviceInformationDO = deviceInformationMapper.selectOne(new LambdaQueryWrapperX<DeviceInformationDO>()
.eq(DeviceInformationDO::getDeviceNo, robotChargeLogDO.getDeviceNo()));
deviceInformationDO.setDeviceUseStatus(DeviceUseStatusEnum.IDLE.getType());
deviceInformationMapper.updateBatch(deviceInformationDO);
log.info("充电桩设置为空闲 :{}", deviceInformationDO.getDeviceNo());
}
/**
* 任务日志分页
*
* @param pageReqVO
* @return
*/

View File

@ -0,0 +1,5 @@
package cn.iocoder.yudao.module.system.service.robot.job;
public interface CycleService {
void cycleTaskJob();
}

View File

@ -0,0 +1,220 @@
package cn.iocoder.yudao.module.system.service.robot.job;
import cn.hutool.core.util.ObjectUtil;
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
import cn.iocoder.yudao.framework.common.util.date.DateUtils;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import cn.iocoder.yudao.framework.tenant.core.context.TenantContextHolder;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskDetailAddVO;
import cn.iocoder.yudao.module.system.controller.admin.robot.vo.RobotTaskRespVO;
import cn.iocoder.yudao.module.system.dal.dataobject.houselocation.WareHouseLocationDO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotTaskDO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotTaskDetailDO;
import cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotWarnCodeMappingDO;
import cn.iocoder.yudao.module.system.dal.mysql.houselocation.WareHouseLocationMapper;
import cn.iocoder.yudao.module.system.dal.mysql.robot.RobotTaskDetailMapper;
import cn.iocoder.yudao.module.system.dal.mysql.robot.RobotTaskMapper;
import cn.iocoder.yudao.module.system.enums.redis.RobotCacheLockEnum;
import cn.iocoder.yudao.module.system.enums.robot.LocationLockEnum;
import cn.iocoder.yudao.module.system.enums.robot.RobotTaskDetailStatusEnum;
import cn.iocoder.yudao.module.system.enums.robot.RobotTaskStatusEnum;
import cn.iocoder.yudao.module.system.service.robot.RobotTaskDetailService;
import cn.iocoder.yudao.module.system.service.robot.RobotTaskService;
import cn.iocoder.yudao.module.system.util.redis.RedisUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.google.common.collect.Lists;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;
import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
import static com.baomidou.mybatisplus.core.toolkit.IdWorker.getId;
@Service
@Slf4j
public class CycleServiceImpl implements CycleService {
@Resource
private RobotTaskMapper taskMapper;
@Resource
private RobotTaskDetailMapper taskDetailMapper;
@Value("${zn.do_cycle:true}")
private Boolean doCycle;
@Value("${zn.task-no:ZN}")
private String taskNo;
@Resource
private RedisUtil redisUtil;
@Resource
private WareHouseLocationMapper locationMapper;
@Resource
private RobotTaskService robotTaskService;
/**
* 创建循环任务
*/
@Override
public void cycleTaskJob() {
TenantContextHolder.setTenantId(1L);
if (!doCycle) {
log.info("循环任务关闭了--不自动创建循环任务");
}
List<RobotTaskDetailDO> detailDOS = taskDetailMapper.selectAutoCreateCycleTask();
if (ObjectUtil.isEmpty(detailDOS)) {
log.info("---不存在需要自动创建循环的任务--");
return;
}
Set<Long> taskIds = detailDOS.stream().map(RobotTaskDetailDO::getRobotTaskId).collect(Collectors.toSet());
List<RobotTaskDO> taskList = taskMapper.selectList(new LambdaQueryWrapper<RobotTaskDO>()
.in(RobotTaskDO::getId, taskIds));
Map<Long, List<RobotTaskDetailDO>> taskIdMap =
detailDOS.stream().collect(Collectors.groupingBy(RobotTaskDetailDO::getRobotTaskId));
String incrementByKey = redisUtil.getIncrementByKey(RobotCacheLockEnum.TASK_NO.getKey());
List<RobotTaskDO> taskDOList = new ArrayList<>();
List<RobotTaskDetailDO> taskDetailList = new ArrayList<>();
for (RobotTaskDO v : taskList) {
RobotTaskDO taskData = getTaskData(incrementByKey, v);
List<RobotTaskDetailDO> taskDetailDOS = getTaskDetailData(taskData,taskIdMap,v.getId());
taskDOList.add(taskData);
taskDetailList.addAll(taskDetailDOS);
}
taskMapper.insertBatch(taskDOList);
taskDetailMapper.insertBatch(taskDetailList);
List<Long> fromLocationIds = taskDetailList.stream().map(RobotTaskDetailDO::getFromLocationId).collect(Collectors.toList());
List<Long> toLocationIds = taskDetailList.stream().map(RobotTaskDetailDO::getToLocationId).collect(Collectors.toList());
List<Long> locationIds = new ArrayList<>();
locationIds.addAll(fromLocationIds);
locationIds.addAll(toLocationIds);
List<List<Long>> fromPartition = Lists.partition(locationIds, 100);
fromPartition.forEach(list -> {
locationMapper.updateLocationLockList(list, -1l, LocationLockEnum.NO.getType());
});
List<RobotTaskDetailAddVO> bean = BeanUtils.toBean(taskDetailList, RobotTaskDetailAddVO.class);
Map<Long, List<RobotTaskDetailAddVO>> taskDetailMap =
bean.stream().collect(Collectors.groupingBy(RobotTaskDetailAddVO::getRobotTaskId));
taskDetailMap.forEach((k,v) ->{
robotTaskService.addCycle(k,v);
});
}
private List<RobotTaskDetailDO> getTaskDetailData(RobotTaskDO taskData, Map<Long,
List<RobotTaskDetailDO>> taskIdMap, Long id) {
List<RobotTaskDetailDO> taskDetailDOList = new ArrayList<>();
List<RobotTaskDetailDO> taskDetailDOS = taskIdMap.get(id);
for (RobotTaskDetailDO v : taskDetailDOS) {
RobotTaskDetailDO build = RobotTaskDetailDO.builder()
.robotTaskId(taskData.getId())
.taskType(v.getTaskType())
.releaseType(v.getTakeType())
.takeType(v.getReleaseType())
.releaseId(v.getTakeId())
.takeId(v.getReleaseId())
.fromLocationNo(v.getToLocationNo())
.fromLocationId(v.getToLocationId())
.fromLaneId(v.getToLaneId())
.toLaneId(v.getFromLaneId())
.toLocationNo(v.getFromLocationNo())
.toLocationId(v.getFromLocationId())
.fromLocationStorey(v.getToLocationStorey())
.toLocationStorey(v.getFromLocationStorey())
.priority(v.getPriority())
.taskStatus(RobotTaskDetailStatusEnum.NEW.getType())
.taskStage(0l)
.needLock(v.getNeedLock())
.startTime(null)
.endTime(null)
.fromLocationNumber(v.getToLocationNumber())
.toLocationNumber(v.getFromLocationNumber())
.fromMapItemId(v.getToMapItemId())
.toMapItemId(v.getFromMapItemId())
.build();
taskDetailDOList.add(build);
}
return taskDetailDOList;
}
/**
* 设置任务主表数据
* @param incrementByKey
* @param v
* @return
*/
public RobotTaskDO getTaskData(String incrementByKey, RobotTaskDO v ) {
String taskNoStr = taskNo + DateUtils.getYearMonthDay() + incrementByKey;
RobotTaskDO task = new RobotTaskDO();
BeanUtils.copyProperties(v, task);
task.setRemainingCycleNumber(v.getRemainingCycleNumber() - 1);
task.setTaskNo(taskNoStr);
task.setTaskStatus(RobotTaskStatusEnum.NEW.getType());
task.setTaskStage(0l);
task.setStartTime(null);
task.setEndTime(null);
task.setCreateTime(LocalDateTime.now());
task.setUpdateTime(LocalDateTime.now());
task.setId(getId());
return task;
}
}

View File

@ -192,7 +192,7 @@ public class DistributeTasksServiceImpl implements DistributeTasksService {
//不拼接
List<Long> singleTaskIds =taskDOList.stream()
.filter(v -> MontageTaskEnum.YES.getType().equals(v.getMontageTask()))
.filter(v -> MontageTaskEnum.NO.getType().equals(v.getMontageTask()))
.map(RobotTaskDO::getId)
.collect(Collectors.toList());
@ -366,9 +366,6 @@ public class DistributeTasksServiceImpl implements DistributeTasksService {
if (ObjectUtil.isNotEmpty(updateTaskDetails)) {
robotTaskDetailMapper.updateBatch(updateTaskDetails);
}
if (ObjectUtil.isNotEmpty(robotNos)) {
robotInformationMapper.updateRobotListStatus(robotNos, RobotStatusEnum.DOING.getType());
}
}
/**
@ -664,7 +661,7 @@ public class DistributeTasksServiceImpl implements DistributeTasksService {
taskNigth.setCommand_type(CommandTypeEnum.MOVE_POSES.getType());
List<Pose2ds> pose2dsNight = new ArrayList<>();
WareHouseLocationDO ware = WareHouseLocationDO.builder()
/* WareHouseLocationDO ware = WareHouseLocationDO.builder()
.laneId(-2l)
.build();
List<WareHouseLocationDO> releaseStockList =
@ -672,7 +669,7 @@ public class DistributeTasksServiceImpl implements DistributeTasksService {
for (WareHouseLocationDO wareHouseLocationDO : releaseStockList) {
Pose2ds pose = positionMapItemMapper.selectByLocationId(wareHouseLocationDO.getId());
pose2dsNight.add(pose);
}
}*/
// taskNigth.setPose2ds(pose2dsNight);

View File

@ -192,7 +192,7 @@ public class RobotTaskAutoMoveServiceImpl implements RobotTaskAutoMoveService {
List<List<Long>> fromPartition = Lists.partition(locationIds, 100);
fromPartition.forEach(list-> {
locationMapper.updateLocationLockList(list,0l,LocationLockEnum.NO.getType());
// locationMapper.updateLocationLockList(list,0l,LocationLockEnum.NO.getType());
});
// todo 搬运任务下发给机器人

View File

@ -254,7 +254,7 @@ public class RobotPathPlanningServiceImpl implements RobotPathPlanningService {
} else if (ObjectUtil.isNotEmpty(taskDetailDO.getFromLocationId())
&& ObjectUtil.isEmpty(taskDetailDO.getFromLaneId())) {
//取的是普通点位
pathPlanning.setTakeGroupId("POINT_" + taskDetailDO.getFromMapId());
pathPlanning.setTakeGroupId("POINT_" + taskDetailDO.getFromMapItemId());
pathPlanning.setTakeLocationNumber(Math.abs(locationNumberReduce - taskDetailDO.getFromLocationNumber()));
pathPlanning.setTakePointId(locationDOMap.get(taskDetailDO.getFromLocationId()).getMapItemId());
}
@ -270,7 +270,7 @@ public class RobotPathPlanningServiceImpl implements RobotPathPlanningService {
} else if (ObjectUtil.isNotEmpty(taskDetailDO.getToLocationId())
&& ObjectUtil.isEmpty(taskDetailDO.getToLaneId())) {
//放的是普通点位
pathPlanning.setReleaseGroupId("POINT_" + taskDetailDO.getToMapId());
pathPlanning.setReleaseGroupId("POINT_" + taskDetailDO.getToMapItemId());
pathPlanning.setReleaseLocationNumber(taskDetailDO.getToLocationNumber());
pathPlanning.setReleasePointId(locationDOMap.get(taskDetailDO.getToLocationId()).getMapItemId());
}
@ -340,8 +340,8 @@ public class RobotPathPlanningServiceImpl implements RobotPathPlanningService {
|| RobotTaskTypeEnum.RELEASE.getType().equals(detail.getTaskType())) {
laneIds.add(detail.getFromLaneId());
laneIds.add(detail.getToLaneId());
mapIds.add(detail.getFromMapId());
mapIds.add(detail.getToMapId());
mapIds.add(detail.getFromMapItemId());
mapIds.add(detail.getToMapItemId());
}
}
}
@ -352,8 +352,8 @@ public class RobotPathPlanningServiceImpl implements RobotPathPlanningService {
&& !laneIds.contains(v.getToLaneId())
&& !RobotTaskTypeEnum.PARK.getType().equals(v.getTaskType()) //停车在充电的任务做
&& !RobotTaskTypeEnum.CHARGE.getType().equals(v.getTaskType()) //停车在充电的任务做
&& !mapIds.contains(v.getFromMapId())
&& !mapIds.contains(v.getToMapId()))
&& !mapIds.contains(v.getFromMapItemId())
&& !mapIds.contains(v.getToMapItemId()))
.collect(Collectors.toList());
if (ObjectUtil.isEmpty(detailDOS)) {
@ -375,15 +375,15 @@ public class RobotPathPlanningServiceImpl implements RobotPathPlanningService {
//取货点位--最小
Map<Long, Long> fromLocationMap = detailDOS.stream()
.filter(v -> ObjectUtil.isNotEmpty(v.getFromMapId()))
.collect(Collectors.groupingBy(RobotTaskDetailDO::getFromMapId,
.filter(v -> ObjectUtil.isNotEmpty(v.getFromMapItemId()))
.collect(Collectors.groupingBy(RobotTaskDetailDO::getFromMapItemId,
Collectors.collectingAndThen(Collectors.minBy(Comparator.comparingLong(RobotTaskDetailDO::getFromLocationNumber)),
a -> a.isPresent() ? a.get().getFromLocationNumber() : null)));
//放货点位--最大
Map<Long, Long> toLocationMap = detailDOS.stream()
.filter(v -> ObjectUtil.isNotEmpty(v.getToMapId()))
.collect(Collectors.groupingBy(RobotTaskDetailDO::getToMapId,
.filter(v -> ObjectUtil.isNotEmpty(v.getToMapItemId()))
.collect(Collectors.groupingBy(RobotTaskDetailDO::getToMapItemId,
Collectors.collectingAndThen(Collectors.maxBy(Comparator.comparingLong(RobotTaskDetailDO::getToLocationNumber)),
a -> a.isPresent() ? a.get().getToLocationNumber() : null)));
@ -392,14 +392,14 @@ public class RobotPathPlanningServiceImpl implements RobotPathPlanningService {
for (RobotTaskDetailDO v : detailDOS) {
RobotTaskDetailDO fromLane = ObjectUtil.isNotEmpty(v.getFromLaneId()) ? fromLaneMap.get(v.getFromLaneId()) : null;
RobotTaskDetailDO toLane = ObjectUtil.isNotEmpty(v.getToLaneId()) ? toLaneMap.get(v.getToLaneId()) : null;
Long fromLocation = ObjectUtil.isNotEmpty(v.getFromMapId()) ? fromLocationMap.get(v.getFromMapId()) : null;
Long toLocation = ObjectUtil.isNotEmpty(v.getToMapId()) ? toLocationMap.get(v.getToMapId()) : null;
Long fromLocation = ObjectUtil.isNotEmpty(v.getFromMapItemId()) ? fromLocationMap.get(v.getFromMapItemId()) : null;
Long toLocation = ObjectUtil.isNotEmpty(v.getToMapItemId()) ? toLocationMap.get(v.getToMapItemId()) : null;
//校验放货线库有取的任务
RobotTaskDetailDO fromLaneDoRelease = ObjectUtil.isNotEmpty(v.getToLaneId()) ? fromLaneMap.get(v.getToLaneId()) : null;
//校验放的普通库位有取的任务
Long toHaveFrom = ObjectUtil.isNotEmpty(v.getToMapId()) ? fromLocationMap.get(v.getToMapId()) : null;
Long toHaveFrom = ObjectUtil.isNotEmpty(v.getToMapItemId()) ? fromLocationMap.get(v.getToMapItemId()) : null;
//校验取货库位有放的任务
Long fromHaveTo = ObjectUtil.isNotEmpty(v.getFromMapId()) ? toLocationMap.get(v.getFromMapId()) : null;
Long fromHaveTo = ObjectUtil.isNotEmpty(v.getFromMapItemId()) ? toLocationMap.get(v.getFromMapItemId()) : null;
//取放模式
if (RobotTaskTypeEnum.TAKE_RELEASE.getType().equals(v.getTaskType())) {
@ -694,7 +694,7 @@ public class RobotPathPlanningServiceImpl implements RobotPathPlanningService {
taskNigth.setCommand_type(CommandTypeEnum.MOVE_POSES.getType());
List<Pose2ds> pose2dsNight = new ArrayList<>();
WareHouseLocationDO ware = WareHouseLocationDO.builder()
/*WareHouseLocationDO ware = WareHouseLocationDO.builder()
.laneId(-2l)
.build();
List<WareHouseLocationDO> releaseStockList =
@ -702,7 +702,7 @@ public class RobotPathPlanningServiceImpl implements RobotPathPlanningService {
for (WareHouseLocationDO wareHouseLocationDO : releaseStockList) {
Pose2ds pose = positionMapItemMapper.selectByLocationId(wareHouseLocationDO.getId());
pose2dsNight.add(pose);
}
}*/
// taskNigth.setPose2ds(pose2dsNight);

View File

@ -250,4 +250,6 @@ zn:
robot_chearg: #机器人充电的配置
release_location_number_config: 50 #同一组序号,越大越先执行
priority_config: 50 #优先级
task: #任务相关的配置
check_sku_info: true #校验物料信息

View File

@ -496,47 +496,90 @@
#{id}
</foreach>
</update>
<update id="releaseLocationLockList">
update
ware_house_location
set
location_lock = #{locationLock}
where
task_id = #{taskId}
and location_lock = '0'
and id in
<foreach collection="locationIds" item="id" index="index" open="(" close=")"
separator=",">
#{id}
</foreach>
</update>
<select id="selectByTypeAndId" resultMap="BaseResultMap">
select
<include refid="base_sql"></include>
from
ware_house_location
ware_house_location t1
<where>
<if test= " locationUseStatus != null ">
AND location_use_status = #{locationUseStatus}
AND t1.location_use_status = #{locationUseStatus}
</if>
<if test= "takeType != null and takeType == '1'.toString()">
AND id = #{id}
AND t1.id = #{id}
</if>
<if test= "takeType != null and takeType == '2'.toString()">
AND lane_id = #{id}
AND t1.lane_id = #{id}
</if>
<if test= "takeType != null and takeType == '3'.toString()">
AND area_id = #{id}
AND t1.area_id = #{id}
</if>
<if test= " locationIds != null and locationIds.size() > 0">
AND id not in
AND t1.id not in
<foreach collection="locationIds" item="id" index="index" open="(" close=")"
separator=",">
#{id}
</foreach>
</if>
<if test= " mapIds != null and mapIds.size() > 0">
AND map_id in
AND t1.map_id in
<foreach collection="mapIds" item="mapId" index="index" open="(" close=")"
separator=",">
#{mapId}
</foreach>
</if>
<if test= '"1"=="1"'>
AND location_enable = '1'
AND location_lock = '1'
AND location_type = '0'
AND t1.location_enable = '1'
AND t1.location_lock = '1'
AND t1.location_type = '0'
</if>
<if test= "locationUseStatus != null and locationUseStatus == '0'.toString()">
AND ((t1.lane_id > 0
and t1.location_number &lt; (SELECT IFNULL(min( t2.location_number ) ,10000000000) from ware_house_location t2
where t1.lane_id = t2.lane_id
AND t2.location_type = '0'
AND (t2.location_use_status = '1' or t2.location_enable = '0' or t2.location_lock = '0'))
) or t1.lane_id is null)
</if>
<if test= " takeMapItemIds != null and takeMapItemIds.size() > 0">
AND t1.map_item_id not in
<foreach collection="takeMapItemIds" item="mapItemId" index="index" open="(" close=")"
separator=",">
#{mapItemId}
</foreach>
</if>
<if test= " laneIds != null and laneIds.size() > 0">
AND t1.lane_id in
<foreach collection="laneIds" item="laneId" index="index" open="(" close=")"
separator=",">
#{laneId}
</foreach>
</if>
<if test= " areaIds != null and areaIds.size() > 0">
AND t1.area_id in
<foreach collection="areaIds" item="areaId" index="index" open="(" close=")"
separator=",">
#{areaId}
</foreach>
</if>
</where>
order by location_number desc , location_storey asc
order by t1.location_number desc , t1.location_storey asc
limit 1
</select>
@ -642,8 +685,29 @@
#{mapId}
</foreach>
</if>
<if test="laneIds != null and laneIds.size() > 0">
and lane_id in
<foreach collection="laneIds" item="item" index="index" open="(" close=")"
separator=",">
#{item}
</foreach>
</if>
<if test="areaIds != null and areaIds.size() > 0">
and area_id in
<foreach collection="areaIds" item="item" index="index" open="(" close=")"
separator=",">
#{item}
</foreach>
</if>
<if test="mapItemIds != null and mapItemIds.size() > 0">
and map_item_id not in
<foreach collection="mapItemIds" item="item" index="index" open="(" close=")"
separator=",">
#{item}
</foreach>
</if>
</where>
order by id asc
order by location_number asc
</select>
<select id="getLocationByName" resultType="cn.iocoder.yudao.module.system.controller.admin.houselocation.vo.WareHouseLocationRespVO">
<choose>

View File

@ -267,11 +267,7 @@
set
robot_status = #{robotStatus}
where
robot_no in
<foreach collection="robotNos" item="robotNo" index="index" open="(" close=")"
separator=",">
#{robotNo}
</foreach>
robot_no = #{robotNo}
</update>
<!--通过主键删除-->

View File

@ -17,8 +17,8 @@
<result property="toLaneId" column="to_lane_id" jdbcType="INTEGER"/>
<result property="fromLocationNumber" column="from_location_number" jdbcType="INTEGER"/>
<result property="toLocationNumber" column="to_location_number" jdbcType="INTEGER"/>
<result property="fromMapId" column="from_map_id" jdbcType="INTEGER"/>
<result property="toMapId" column="to_map_id" jdbcType="INTEGER"/>
<result property="fromMapItemId" column="from_map_item_id" jdbcType="INTEGER"/>
<result property="toMapItemId" column="to_map_item_id" jdbcType="INTEGER"/>
<result property="toLocationNo" column="to_location_no" jdbcType="VARCHAR"/>
<result property="toLocationId" column="to_location_id" jdbcType="INTEGER"/>
<result property="fromLocationStorey" column="from_location_storey" jdbcType="INTEGER"/>
@ -69,8 +69,8 @@
priority,
from_location_number,
to_location_number,
from_map_id,
to_map_id
from_map_item_id,
to_map_item_id
</sql>
@ -197,20 +197,55 @@
and t2.task_type = '3'
</select>
<select id="selectTakeMapItemIds" resultType="java.lang.Long">
select
t2.map_item_id
from
robot_task_detail t1, ware_house_location t2
where
t1.from_location_id = t2.id
and t1.task_status in ('0','1')
</select>
<select id="selectReleaseMapItemIds" resultType="java.lang.Long">
select
t2.map_item_id
from
robot_task_detail t1, ware_house_location t2
where
t1.to_location_id = t2.id
and t1.task_status in ('0','1')
</select>
<select id="selectAutoCreateCycleTask"
resultType="cn.iocoder.yudao.module.system.dal.dataobject.robot.RobotTaskDetailDO">
select
t1.*
from
robot_task_detail t1, robot_task t2
where
t2.id = t1.robot_task_id
and t2.remaining_cycle_number > 1
and t2.task_status = '2'
and t1.task_status = '2'
and t1.deleted = '0'
and t2.deleted = '0'
</select>
<!--keyProperty="id" useGeneratedKeys="true"-->
<insert id="insertBatchList" >
insert into robot_task_detail(robot_task_id, task_type, release_type, take_type, release_id, take_id,
from_location_no, from_location_id, to_location_no, to_location_id, robot_no,from_location_storey,
to_location_storey,priority,from_lane_id,to_lane_id,from_location_number,to_location_number,
from_map_id,to_map_id)
from_map_item_id,to_map_item_id)
values
<foreach collection="taskDetailList" item="entity" separator=",">
(#{entity.robotTaskId}, #{entity.taskType}, #{entity.releaseType}, #{entity.takeType}, #{entity.releaseId},
#{entity.takeId}, #{entity.fromLocationNo}, #{entity.fromLocationId}, #{entity.toLocationNo},
#{entity.toLocationId}, #{entity.robotNo}, #{entity.fromLocationStorey}, #{entity.toLocationStorey}
, #{entity.priority}, #{entity.fromLaneId}, #{entity.toLaneId}, #{entity.fromLocationNumber},
#{entity.toLocationNumber}, #{entity.fromMapId}, #{entity.toMapId})
#{entity.toLocationNumber}, #{entity.fromMapItemId}, #{entity.toMapItemId})
</foreach>
</insert>

View File

@ -0,0 +1,15 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="cn.iocoder.yudao.module.system.dal.mysql.cycle.TaskCycleMapper">
<!--
一般情况下,尽可能使用 Mapper 进行 CRUD 增删改查即可。
无法满足的场景,例如说多表关联查询,才使用 XML 编写 SQL。
代码生成器暂时只生成 Mapper XML 文件本身,更多推荐 MybatisX 快速开发插件来生成查询。
文档可见https://www.iocoder.cn/MyBatis/x-plugins/
-->
<delete id="deletByRobotTaskId">
delete from robot_task_cycle where robot_task_id = #{robotTaskId}
</delete>
</mapper>