自动化立体仓库 - WMS系统
skyouc
1 天以前 a57445f55e84b7cf6bd26cf152a0ffa7f62f54f2
添加容器管理
商品档案管理
15个文件已修改
12个文件已添加
1140 ■■■■■ 已修改文件
src/main/java/basContainer.sql 18 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/controller/BasContainerController.java 125 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/controller/BasStationController.java 40 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/controller/MobileController.java 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/controller/TaskController.java 47 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/entity/BasContainer.java 88 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/entity/BasStation.java 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/entity/Mat.java 27 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/entity/Task.java 9 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/entity/param/AgvCallParams.java 3 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/enums/CommonEnum.java 25 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/enums/ContainerType.java 27 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/enums/MatTagType.java 20 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/mapper/BasContainerMapper.java 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/service/BasContainerService.java 8 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/service/MobileService.java 8 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/service/impl/BasContainerServiceImpl.java 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/service/impl/MobileServiceImpl.java 163 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/task/handler/WorkMastHandler.java 116 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/common/CodeBuilder.java 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/mapper/BasContainerMapper.xml 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/static/js/basContainer/basContainer.js 249 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/static/js/common.js 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/static/js/mat/mat.js 7 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/static/js/task/task.js 14 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/views/basContainer/basContainer.html 92 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/views/basStation/basStation.html 3 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/basContainer.sql
New file
@@ -0,0 +1,18 @@
-- save basContainer record
-- mysql
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( 'basContainer/basContainer.html', 'basContainer管理', null , '2', null , '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( 'basContainer#view', '查询', '', '3', '0', '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( 'basContainer#btn-add', '新增', '', '3', '1', '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( 'basContainer#btn-edit', '编辑', '', '3', '2', '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( 'basContainer#btn-delete', '删除', '', '3', '3', '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( 'basContainer#btn-export', '导出', '', '3', '4', '1');
-- sqlserver
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'basContainer/basContainer.html', N'basContainer管理', null, '2', null, '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'basContainer#view', N'查询', '90623', '3', '0', '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'basContainer#btn-add', N'新增', '90623', '3', '1', '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'basContainer#btn-edit', N'编辑', '90623', '3', '2', '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'basContainer#btn-delete', N'删除', '90623', '3', '3', '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'basContainer#btn-export', N'导出', '90623', '3', '4', '1');
src/main/java/com/zy/asrs/controller/BasContainerController.java
New file
@@ -0,0 +1,125 @@
package com.zy.asrs.controller;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.mapper.EntityWrapper;
import com.baomidou.mybatisplus.mapper.Wrapper;
import com.baomidou.mybatisplus.plugins.Page;
import com.core.common.DateUtils;
import com.zy.asrs.entity.BasContainer;
import com.zy.asrs.service.BasContainerService;
import com.core.annotations.ManagerAuth;
import com.core.common.BaseRes;
import com.core.common.Cools;
import com.core.common.R;
import com.zy.common.web.BaseController;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import java.util.*;
@RestController
public class BasContainerController extends BaseController {
    @Autowired
    private BasContainerService basContainerService;
    @RequestMapping(value = "/basContainer/{id}/auth")
    @ManagerAuth
    public R get(@PathVariable("id") String id) {
        return R.ok(basContainerService.selectById(String.valueOf(id)));
    }
    @RequestMapping(value = "/basContainer/list/auth")
    @ManagerAuth
    public R list(@RequestParam(defaultValue = "1")Integer curr,
                  @RequestParam(defaultValue = "10")Integer limit,
                  @RequestParam(required = false)String orderByField,
                  @RequestParam(required = false)String orderByType,
                  @RequestParam(required = false)String condition,
                  @RequestParam Map<String, Object> param){
        EntityWrapper<BasContainer> wrapper = new EntityWrapper<>();
        excludeTrash(param);
        convert(param, wrapper);
        allLike(BasContainer.class, param.keySet(), wrapper, condition);
        if (!Cools.isEmpty(orderByField)){wrapper.orderBy(humpToLine(orderByField), "asc".equals(orderByType));}
        return R.ok(basContainerService.selectPage(new Page<>(curr, limit), wrapper));
    }
    private <T> void convert(Map<String, Object> map, EntityWrapper<T> wrapper){
        for (Map.Entry<String, Object> entry : map.entrySet()){
            String val = String.valueOf(entry.getValue());
            if (val.contains(RANGE_TIME_LINK)){
                String[] dates = val.split(RANGE_TIME_LINK);
                wrapper.ge(entry.getKey(), DateUtils.convert(dates[0]));
                wrapper.le(entry.getKey(), DateUtils.convert(dates[1]));
            } else {
                wrapper.like(entry.getKey(), val);
            }
        }
    }
    @RequestMapping(value = "/basContainer/add/auth")
    @ManagerAuth
    public R add(BasContainer basContainer) {
        basContainerService.insert(basContainer);
        return R.ok();
    }
    @RequestMapping(value = "/basContainer/update/auth")
    @ManagerAuth
    public R update(BasContainer basContainer){
        if (Cools.isEmpty(basContainer) || null==basContainer.getId()){
            return R.error();
        }
        basContainerService.updateById(basContainer);
        return R.ok();
    }
    @RequestMapping(value = "/basContainer/delete/auth")
    @ManagerAuth
    public R delete(@RequestParam(value="ids[]") Long[] ids){
         for (Long id : ids){
            basContainerService.deleteById(id);
        }
        return R.ok();
    }
    @RequestMapping(value = "/basContainer/export/auth")
    @ManagerAuth
    public R export(@RequestBody JSONObject param){
        EntityWrapper<BasContainer> wrapper = new EntityWrapper<>();
        List<String> fields = JSONObject.parseArray(param.getJSONArray("fields").toJSONString(), String.class);
        Map<String, Object> map = excludeTrash(param.getJSONObject("basContainer"));
        convert(map, wrapper);
        List<BasContainer> list = basContainerService.selectList(wrapper);
        return R.ok(exportSupport(list, fields));
    }
    @RequestMapping(value = "/basContainerQuery/auth")
    @ManagerAuth
    public R query(String condition) {
        EntityWrapper<BasContainer> wrapper = new EntityWrapper<>();
        wrapper.like("_id", condition);
        Page<BasContainer> page = basContainerService.selectPage(new Page<>(0, 10), wrapper);
        List<Map<String, Object>> result = new ArrayList<>();
        for (BasContainer basContainer : page.getRecords()){
            Map<String, Object> map = new HashMap<>();
            map.put("id", basContainer.getId());
            map.put("value", basContainer.getId());
            result.add(map);
        }
        return R.ok(result);
    }
    @RequestMapping(value = "/basContainer/check/column/auth")
    @ManagerAuth
    public R query(@RequestBody JSONObject param) {
        Wrapper<BasContainer> wrapper = new EntityWrapper<BasContainer>().eq(humpToLine(String.valueOf(param.get("key"))), param.get("val"));
        if (null != basContainerService.selectOne(wrapper)){
            return R.parse(BaseRes.REPEAT).add(getComment(BasContainer.class, String.valueOf(param.get("key"))));
        }
        return R.ok();
    }
}
src/main/java/com/zy/asrs/controller/BasStationController.java
@@ -32,24 +32,26 @@
    @RequestMapping(value = "/basStation/list/auth")
    @ManagerAuth
    public R list(@RequestParam(defaultValue = "1")Integer curr,
                  @RequestParam(defaultValue = "10")Integer limit,
                  @RequestParam(required = false)String orderByField,
                  @RequestParam(required = false)String orderByType,
                  @RequestParam(required = false)String condition,
                  @RequestParam Map<String, Object> param){
    public R list(@RequestParam(defaultValue = "1") Integer curr,
                  @RequestParam(defaultValue = "10") Integer limit,
                  @RequestParam(required = false) String orderByField,
                  @RequestParam(required = false) String orderByType,
                  @RequestParam(required = false) String condition,
                  @RequestParam Map<String, Object> param) {
        EntityWrapper<BasStation> wrapper = new EntityWrapper<>();
        excludeTrash(param);
        convert(param, wrapper);
        allLike(BasStation.class, param.keySet(), wrapper, condition);
        if (!Cools.isEmpty(orderByField)){wrapper.orderBy(humpToLine(orderByField), "asc".equals(orderByType));}
        if (!Cools.isEmpty(orderByField)) {
            wrapper.orderBy(humpToLine(orderByField), "asc".equals(orderByType));
        }
        return R.ok(basStationService.selectPage(new Page<>(curr, limit), wrapper));
    }
    private <T> void convert(Map<String, Object> map, EntityWrapper<T> wrapper){
        for (Map.Entry<String, Object> entry : map.entrySet()){
    private <T> void convert(Map<String, Object> map, EntityWrapper<T> wrapper) {
        for (Map.Entry<String, Object> entry : map.entrySet()) {
            String val = String.valueOf(entry.getValue());
            if (val.contains(RANGE_TIME_LINK)){
            if (val.contains(RANGE_TIME_LINK)) {
                String[] dates = val.split(RANGE_TIME_LINK);
                wrapper.ge(entry.getKey(), DateUtils.convert(dates[0]));
                wrapper.le(entry.getKey(), DateUtils.convert(dates[1]));
@@ -70,10 +72,10 @@
        return R.ok();
    }
    @RequestMapping(value = "/basStation/update/auth")
    @ManagerAuth
    public R update(BasStation basStation){
        if (Cools.isEmpty(basStation) || null==basStation.getId()){
    @RequestMapping(value = "/basStation/update/auth")
    @ManagerAuth
    public R update(BasStation basStation) {
        if (Cools.isEmpty(basStation) || null == basStation.getId()) {
            return R.error();
        }
        basStationService.updateById(basStation);
@@ -82,8 +84,8 @@
    @RequestMapping(value = "/basStation/delete/auth")
    @ManagerAuth
    public R delete(@RequestParam(value="ids[]") Long[] ids){
         for (Long id : ids){
    public R delete(@RequestParam(value = "ids[]") Long[] ids) {
        for (Long id : ids) {
            basStationService.deleteById(id);
        }
        return R.ok();
@@ -91,7 +93,7 @@
    @RequestMapping(value = "/basStation/export/auth")
    @ManagerAuth
    public R export(@RequestBody JSONObject param){
    public R export(@RequestBody JSONObject param) {
        EntityWrapper<BasStation> wrapper = new EntityWrapper<>();
        List<String> fields = JSONObject.parseArray(param.getJSONArray("fields").toJSONString(), String.class);
        Map<String, Object> map = excludeTrash(param.getJSONObject("basStation"));
@@ -107,7 +109,7 @@
        wrapper.like("dev_no", condition);
        Page<BasStation> page = basStationService.selectPage(new Page<>(0, 10), wrapper);
        List<Map<String, Object>> result = new ArrayList<>();
        for (BasStation basStation : page.getRecords()){
        for (BasStation basStation : page.getRecords()) {
            Map<String, Object> map = new HashMap<>();
            map.put("id", basStation.getId());
            map.put("value", basStation.getId());
@@ -120,7 +122,7 @@
    @ManagerAuth
    public R query(@RequestBody JSONObject param) {
        Wrapper<BasStation> wrapper = new EntityWrapper<BasStation>().eq(humpToLine(String.valueOf(param.get("key"))), param.get("val"));
        if (null != basStationService.selectOne(wrapper)){
        if (null != basStationService.selectOne(wrapper)) {
            return R.parse(BaseRes.REPEAT).add(getComment(BasStation.class, String.valueOf(param.get("key"))));
        }
        return R.ok();
src/main/java/com/zy/asrs/controller/MobileController.java
@@ -167,6 +167,16 @@
    }
    @PostMapping("/cache/out/call")
    @ApiOperation("呼叫AGV搬运")
    @ManagerAuth
    public R OutCallAgv(@RequestBody AgvCallParams params) {
        if (Objects.isNull(params)) {
            return R.error("参数不能为空!!");
        }
        return mobileService.OutCallAgv(params, getUserId());
    }
    // 组托 ----------------------------------------------------------------------------------------------------
src/main/java/com/zy/asrs/controller/TaskController.java
@@ -32,25 +32,29 @@
    @RequestMapping(value = "/task/list/auth")
    @ManagerAuth
    public R list(@RequestParam(defaultValue = "1")Integer curr,
                  @RequestParam(defaultValue = "10")Integer limit,
                  @RequestParam(required = false)String orderByField,
                  @RequestParam(required = false)String orderByType,
                  @RequestParam(required = false)String condition,
                  @RequestParam Map<String, Object> param){
    public R list(@RequestParam(defaultValue = "1") Integer curr,
                  @RequestParam(defaultValue = "10") Integer limit,
                  @RequestParam(required = false) String orderByField,
                  @RequestParam(required = false) String orderByType,
                  @RequestParam(required = false) String condition,
                  @RequestParam Map<String, Object> param) {
        EntityWrapper<Task> wrapper = new EntityWrapper<>();
        excludeTrash(param);
        convert(param, wrapper);
        allLike(Task.class, param.keySet(), wrapper, condition);
        if (!Cools.isEmpty(orderByField)){wrapper.orderBy(humpToLine(orderByField), "desc".equals(orderByType));}
        if (Cools.isEmpty(orderByField)) {wrapper.orderDesc(Arrays.asList("wrk_no"));}
        if (!Cools.isEmpty(orderByField)) {
            wrapper.orderBy(humpToLine(orderByField), "desc".equals(orderByType));
        }
        if (Cools.isEmpty(orderByField)) {
            wrapper.orderDesc(Arrays.asList("wrk_no"));
        }
        return R.ok(taskService.selectPage(new Page<>(curr, limit), wrapper));
    }
    private <T> void convert(Map<String, Object> map, EntityWrapper<T> wrapper){
        for (Map.Entry<String, Object> entry : map.entrySet()){
    private <T> void convert(Map<String, Object> map, EntityWrapper<T> wrapper) {
        for (Map.Entry<String, Object> entry : map.entrySet()) {
            String val = String.valueOf(entry.getValue());
            if (val.contains(RANGE_TIME_LINK)){
            if (val.contains(RANGE_TIME_LINK)) {
                String[] dates = val.split(RANGE_TIME_LINK);
                wrapper.ge(entry.getKey(), DateUtils.convert(dates[0]));
                wrapper.le(entry.getKey(), DateUtils.convert(dates[1]));
@@ -67,10 +71,10 @@
        return R.ok();
    }
    @RequestMapping(value = "/task/update/auth")
    @ManagerAuth
    public R update(Task task){
        if (Cools.isEmpty(task) || null==task.getId()){
    @RequestMapping(value = "/task/update/auth")
    @ManagerAuth
    public R update(Task task) {
        if (Cools.isEmpty(task) || null == task.getId()) {
            return R.error();
        }
        taskService.updateById(task);
@@ -79,8 +83,8 @@
    @RequestMapping(value = "/task/delete/auth")
    @ManagerAuth
    public R delete(@RequestParam(value="ids[]") Long[] ids){
         for (Long id : ids){
    public R delete(@RequestParam(value = "ids[]") Long[] ids) {
        for (Long id : ids) {
            taskService.deleteById(id);
        }
        return R.ok();
@@ -90,7 +94,7 @@
    @RequestMapping("/task/control")
    @ManagerAuth(memo = "手动处理工作档")
    public R handControlWrkMast(@RequestParam String workNo,
                                @RequestParam Integer type){
                                @RequestParam Integer type) {
        if (type == 1) {
            taskService.completeWrkMast(workNo, getUserId());
            return R.ok("工作档已完成");
@@ -105,10 +109,9 @@
    }
    @RequestMapping(value = "/task/export/auth")
    @ManagerAuth
    public R export(@RequestBody JSONObject param){
    public R export(@RequestBody JSONObject param) {
        EntityWrapper<Task> wrapper = new EntityWrapper<>();
        List<String> fields = JSONObject.parseArray(param.getJSONArray("fields").toJSONString(), String.class);
        Map<String, Object> map = excludeTrash(param.getJSONObject("task"));
@@ -124,7 +127,7 @@
        wrapper.like("id", condition);
        Page<Task> page = taskService.selectPage(new Page<>(0, 10), wrapper);
        List<Map<String, Object>> result = new ArrayList<>();
        for (Task task : page.getRecords()){
        for (Task task : page.getRecords()) {
            Map<String, Object> map = new HashMap<>();
            map.put("id", task.getId());
            map.put("value", task.getId());
@@ -137,7 +140,7 @@
    @ManagerAuth
    public R query(@RequestBody JSONObject param) {
        Wrapper<Task> wrapper = new EntityWrapper<Task>().eq(humpToLine(String.valueOf(param.get("key"))), param.get("val"));
        if (null != taskService.selectOne(wrapper)){
        if (null != taskService.selectOne(wrapper)) {
            return R.parse(BaseRes.REPEAT).add(getComment(Task.class, String.valueOf(param.get("key"))));
        }
        return R.ok();
src/main/java/com/zy/asrs/entity/BasContainer.java
New file
@@ -0,0 +1,88 @@
package com.zy.asrs.entity;
import com.core.common.Cools;import com.baomidou.mybatisplus.annotations.TableId;
import com.baomidou.mybatisplus.enums.IdType;
import com.fasterxml.jackson.annotation.JsonFormat;
import com.zy.asrs.enums.CommonEnum;
import com.zy.asrs.enums.ContainerType;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import com.baomidou.mybatisplus.annotations.TableName;
import lombok.experimental.Accessors;
import org.springframework.format.annotation.DateTimeFormat;
import java.io.Serializable;
import java.util.Date;
@Data
@Accessors(chain = true)
@TableName("asr_bas_container")
public class BasContainer implements Serializable {
    private static final long serialVersionUID = 1L;
    /**
     * 主键
     */
    @ApiModelProperty(value= "主键")
    @TableId(value = "id", type = IdType.AUTO)
    private Long id;
    /**
     * 容器编码
     */
    @ApiModelProperty(value= "容器编码")
    private String barcode;
    @ApiModelProperty("容器类型")
    private String type;
    @ApiModelProperty("是否混放")
    private Integer flagMix;
    @ApiModelProperty("最大混放种类")
    private Integer mixMax;
    @ApiModelProperty("创建时间")
    @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
    private Date createTime;
    @ApiModelProperty("修改时间")
    @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
    private Date updateTime;
    public BasContainer() {}
    public BasContainer(String barcode) {
        this.barcode = barcode;
    }
    public String getType$() {
        if (Cools.isEmpty(type)) {
            return "料箱";
        }
        if (type.equals(ContainerType.CONTAINER_TYPE_BOX.type)) {
            return ContainerType.CONTAINER_TYPE_BOX.desc;
        } else if (type.equals(ContainerType.CONTAINER_TYPE_SALVER.type)) {
            return ContainerType.CONTAINER_TYPE_SALVER.desc;
        } else if (type.equals(ContainerType.CONTAINER_TYPE_CAGE.type)) {
            return ContainerType.CONTAINER_TYPE_CAGE.desc;
        }
        return null;
    }
    public String getFlagMix$() {
        if (Cools.isEmpty(flagMix)) {
            return null;
        }
        if (flagMix.equals(CommonEnum.COMMON_ENUM_N.type)) {
            return CommonEnum.COMMON_ENUM_N.desc;
        } else if (flagMix.equals(CommonEnum.COMMON_ENUM_Y.type)) {
            return CommonEnum.COMMON_ENUM_Y.desc;
        }
        return null;
    }
}
src/main/java/com/zy/asrs/entity/BasStation.java
@@ -32,7 +32,6 @@
     * 主键
     */
    @ApiModelProperty(value= "主键")
    @TableId(value = "id", type = IdType.AUTO)
    private Long id;
    /**
src/main/java/com/zy/asrs/entity/Mat.java
@@ -7,6 +7,8 @@
import com.baomidou.mybatisplus.enums.IdType;
import com.core.common.Cools;
import com.core.common.SpringUtils;
import com.zy.asrs.enums.ContainerType;
import com.zy.asrs.service.BasContainerService;
import com.zy.asrs.service.TagService;
import com.zy.common.utils.Synchro;
import com.zy.system.entity.User;
@@ -164,7 +166,7 @@
    private String manuDate;
    /**
     * 品项数
     * 品项数/最大组托数量
     */
    @ApiModelProperty(value= "品项数")
    @ExcelProperty(value = "品项数")
@@ -185,6 +187,11 @@
    @ApiModelProperty(value= "重量")
    @ExcelProperty(value = "重量")
    private Double weight;
    @ApiModelProperty(value= "最大组托上限")
    @ExcelProperty(value = "最大组托上限")
    @TableField("up_qty")
    private Double upQty;
    /**
     * 长度
@@ -300,6 +307,10 @@
    @DateTimeFormat(pattern="yyyy-MM-dd HH:mm:ss")
    private Date updateTime;
    @ApiModelProperty("库位类型")
    @TableField("loc_type")
    private Long locType;
    /**
     * 备注
     */
@@ -416,6 +427,20 @@
        return null;
    }
    public String getLocType$(){
        if (Cools.isEmpty(locType)) {
            return "料箱";
        }
        if (locType.equals(ContainerType.CONTAINER_TYPE_BOX.type)) {
            return ContainerType.CONTAINER_TYPE_BOX.desc;
        } else if (locType.equals(ContainerType.CONTAINER_TYPE_SALVER.type)) {
            return ContainerType.CONTAINER_TYPE_SALVER.desc;
        } else if (locType.equals(ContainerType.CONTAINER_TYPE_CAGE.type)) {
            return ContainerType.CONTAINER_TYPE_CAGE.desc;
        }
        return null;
    }
    public String getBeBatch$(){
        if (null == this.beBatch){ return null; }
        switch (this.beBatch){
src/main/java/com/zy/asrs/entity/Task.java
@@ -1,5 +1,6 @@
package com.zy.asrs.entity;
import com.baomidou.mybatisplus.mapper.EntityWrapper;
import com.core.common.Cools;import com.baomidou.mybatisplus.annotations.TableId;
import com.baomidou.mybatisplus.enums.IdType;
import com.baomidou.mybatisplus.annotations.TableField;
@@ -396,8 +397,8 @@
    public String getStaNo$(){
        BasDevpService service = SpringUtils.getBean(BasDevpService.class);
        BasDevp basDevp = service.selectById(this.staNo);
        BasStationService service = SpringUtils.getBean(BasStationService.class);
        BasStation basDevp = service.selectOne(new EntityWrapper<BasStation>().eq("dev_no", this.staNo));
        if (!Cools.isEmpty(basDevp)){
            return String.valueOf(basDevp.getDevNo());
        }
@@ -405,8 +406,8 @@
    }
    public String getSourceStaNo$(){
        BasDevpService service = SpringUtils.getBean(BasDevpService.class);
        BasDevp basDevp = service.selectById(this.sourceStaNo);
        BasStationService service = SpringUtils.getBean(BasStationService.class);
        BasStation basDevp = service.selectOne(new EntityWrapper<BasStation>().eq("dev_no", this.sourceStaNo));
        if (!Cools.isEmpty(basDevp)){
            return String.valueOf(basDevp.getDevNo());
        }
src/main/java/com/zy/asrs/entity/param/AgvCallParams.java
@@ -14,6 +14,9 @@
    @ApiModelProperty("起始位置")
    private String orgSite;
    @ApiModelProperty("源库位")
    private String orgLoc;
    @ApiModelProperty("终点位置")
    private String tarSite;
src/main/java/com/zy/asrs/enums/CommonEnum.java
New file
@@ -0,0 +1,25 @@
package com.zy.asrs.enums;
/**
 * @author Ryan
 * @date 2025/9/25
 * @description: 通用类型枚举
 * @version 1.0
 */
public enum CommonEnum {
    //通用类型
    COMMON_ENUM_Y(0, "否"),
    //通用
    COMMON_ENUM_N(1, "是");
    public Integer type;
    public String desc;
    CommonEnum(Integer type, String desc) {
        this.type = type;
        this.desc = desc;
    }
}
src/main/java/com/zy/asrs/enums/ContainerType.java
New file
@@ -0,0 +1,27 @@
package com.zy.asrs.enums;
public enum ContainerType {
    //料箱
    CONTAINER_TYPE_BOX("12", "料箱"),
    //托盘
    CONTAINER_TYPE_SALVER("14", "托盘"),
    CONTAINER_TYPE_CAGE("13", "笼框"),
    CONTAINER_TYPE_CAR("3", "台车"),
    ;
    public Long type;
    public String desc;
    ContainerType(String type, String desc) {
        this.type = Long.valueOf(type);
        this.desc = desc;
    }
}
src/main/java/com/zy/asrs/enums/MatTagType.java
New file
@@ -0,0 +1,20 @@
package com.zy.asrs.enums;
public enum MatTagType {
    //中件
    MAT_TAGT_YPE_MIDDLE("13", "中件"),
    //小件
    MAT_TAGT_YPE_SMALL("12", "小件"),
    //滤芯
    MAT_TAGT_YPE_XIN("14", "滤芯")
    ;
    public String id;
    public String type;
    MatTagType(String id, String type) {
        this.type = type;
        this.id = id;
    }
}
src/main/java/com/zy/asrs/mapper/BasContainerMapper.java
New file
@@ -0,0 +1,12 @@
package com.zy.asrs.mapper;
import com.zy.asrs.entity.BasContainer;
import com.baomidou.mybatisplus.mapper.BaseMapper;
import org.apache.ibatis.annotations.Mapper;
import org.springframework.stereotype.Repository;
@Mapper
@Repository
public interface BasContainerMapper extends BaseMapper<BasContainer> {
}
src/main/java/com/zy/asrs/service/BasContainerService.java
New file
@@ -0,0 +1,8 @@
package com.zy.asrs.service;
import com.zy.asrs.entity.BasContainer;
import com.baomidou.mybatisplus.service.IService;
public interface BasContainerService extends IService<BasContainer> {
}
src/main/java/com/zy/asrs/service/MobileService.java
@@ -91,4 +91,12 @@
     * @version 1.0
     */
    R getMatsByQRcode(PakinMatsByQRParams params);
    /**
     * @author Ryan
     * @date 2025/9/24
     * @description: 呼叫AGV出库搬运
     * @version 1.0
     */
    R OutCallAgv(AgvCallParams params, Long userId);
}
src/main/java/com/zy/asrs/service/impl/BasContainerServiceImpl.java
New file
@@ -0,0 +1,12 @@
package com.zy.asrs.service.impl;
import com.zy.asrs.mapper.BasContainerMapper;
import com.zy.asrs.entity.BasContainer;
import com.zy.asrs.service.BasContainerService;
import com.baomidou.mybatisplus.service.impl.ServiceImpl;
import org.springframework.stereotype.Service;
@Service("basContainerService")
public class BasContainerServiceImpl extends ServiceImpl<BasContainerMapper, BasContainer> implements BasContainerService {
}
src/main/java/com/zy/asrs/service/impl/MobileServiceImpl.java
@@ -8,6 +8,7 @@
import com.core.exception.CoolException;
import com.zy.asrs.entity.*;
import com.zy.asrs.entity.param.*;
import com.zy.asrs.enums.CommonEnum;
import com.zy.asrs.enums.LocStsType;
import com.zy.asrs.mapper.LocMastMapper;
import com.zy.asrs.mapper.ManLocDetlMapper;
@@ -28,6 +29,8 @@
import org.springframework.transaction.annotation.Transactional;
import javax.annotation.Resource;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.*;
import java.util.stream.Collectors;
@@ -107,6 +110,10 @@
    @Autowired
    private TaskDetlService taskDetlService;
    @Autowired
    private BasStationService basStationService;
    @Autowired
    private BasContainerService basContainerService;
    @Override
    @Transactional
@@ -578,7 +585,6 @@
        }
        Date now = new Date();
        // 无单组托
        if (Cools.isEmpty(param.getOrderNo())) {
            // 生成入库通知档
@@ -595,19 +601,21 @@
                }
            });
            for (DetlDto detlDto : detlDtos) {
                Mat mat = matService.selectByMatnr(detlDto.getMatnr());
                if (Cools.isEmpty(mat)) {
                    throw new CoolException(detlDto.getMatnr() + "商品档案不存在");
                }
                if (mat.getUpQty().compareTo(detlDto.getAnfme()) < 0) {
                    throw new CoolException("物料:" + detlDto.getMatnr() + "单次最大组托上限为:" + mat.getUpQty());
                }
                WaitPakin waitPakin = new WaitPakin();
                BeanUtils.copyProperties(mat, waitPakin);
                waitPakin.setBatch(detlDto.getBatch());
                waitPakin.setZpallet(param.getBarcode());   // 托盘码
                waitPakin.setIoStatus("N");     // 入出状态
                waitPakin.setAnfme(detlDto.getAnfme());  // 数量
                waitPakin.setStatus("Y");    // 状态
                waitPakin.setZpallet(param.getBarcode());
                waitPakin.setIoStatus("N");
                waitPakin.setAnfme(detlDto.getAnfme());
                waitPakin.setStatus("Y");
                waitPakin.setAppeUser(userId);
                waitPakin.setAppeTime(now);
                waitPakin.setModiUser(userId);
@@ -654,11 +662,41 @@
                    detlDtos.add(detlDto);
                }
            });
            BasContainer container = basContainerService.selectOne(new EntityWrapper<BasContainer>().eq("barcode", param.getBarcode()));
            if (Objects.isNull(container)) {
                throw new CoolException("数据错误:容器码不存在!!");
            }
            if (container.getMixMax() < detlDtos.size()) {
                throw new CoolException("超出容器最大混装数量,当前容器最大数量为:" + container.getMixMax() + "!!");
            }
            Set<String> matnrs = detlDtos.stream().map(DetlDto::getMatnr).collect(Collectors.toSet());
            List<Mat> mats = matService.selectList(new EntityWrapper<Mat>().in("matnr", matnrs));
            Set<Long> tagIds = mats.stream().map(Mat::getTagId).collect(Collectors.toSet());
            if (tagIds.size() > 1) {
                throw new CoolException("组托物料类型不一致,只有相同的物料分类才可以组托!!");
            }
            //还可以放入多少种物料
            Integer suplus = container.getMixMax();
            for (DetlDto detlDto : detlDtos) {
                Mat mat = matService.selectByMatnr(detlDto.getMatnr());
                if (Cools.isEmpty(mat)) {
                    throw new CoolException(detlDto.getMatnr() + "商品档案不存在");
                }
                //最多可放数量
                Double singleMax = mat.getUpQty() * suplus;
                if (singleMax.compareTo(detlDto.getAnfme()) < 0) {
                    throw new CoolException("单次最大组托上限为:" + singleMax);
                }
                BigDecimal decimal = new BigDecimal(detlDto.getAnfme() / mat.getUpQty());
                //当前物料需要占用料箱格数
                Integer curr = decimal.setScale(0, RoundingMode.CEILING).intValue();
                suplus = suplus - curr;
                if (suplus == 0 || suplus < 0) {
                    throw new CoolException("物料:" + detlDto.getMatnr() + ", 超出当前托盘装载上限!!");
                }
                WaitPakin waitPakin = new WaitPakin();
                BeanUtils.copyProperties(mat, waitPakin);
//                waitPakin.sync(mat);
@@ -1209,6 +1247,117 @@
    /**
     * @author Ryan
     * @date 2025/9/24
     * @description: AGV呼叫搬运
     * @version 1.0
     */
    @Override
    public R OutCallAgv(AgvCallParams params, Long userId) {
        LocCache locCaches = locCacheService.selectOne(new EntityWrapper<LocCache>()
                .eq("loc_sts", LocStsType.LOC_STS_TYPE_F.type)
                .eq("frozen", 0)
                .orderDesc(Arrays.asList("sort", "first_time"))
                .last("OFFSET 0 ROWS FETCH NEXT 1 ROWS ONLY"));
        if (Objects.isNull(locCaches)) {
            throw new CoolException("暂无满足需求库位!");
        }
        BasStation station = basStationService.selectOne(new EntityWrapper<BasStation>()
                .eq("loc_sts", LocStsType.LOC_STS_TYPE_O.type)
                .eq("dev_no", params.getTarSite()));
        if (Objects.isNull(station)) {
            throw new CoolException("站点正在执行任务!!");
        }
        generateOutTask(station, locCaches, userId);
        return R.ok();
    }
    /**
     * @author Ryan
     * @date 2025/9/25
     * @description: 呼叫AGV生成出库任务
     * @version 1.0
     */
    @Transactional(rollbackFor = Exception.class)
    public void generateOutTask(BasStation station, LocCache loc, Long userId) {
        // 获取工作号
        int workNo = commonService.getWorkNo(WorkNoType.PICK.type);
        // 保存工作档
        Task task = new Task();
        task.setWrkNo(workNo)
                .setIoTime(new Date())
                .setWrkSts(11L) // 工作状态:11.生成出库ID
                .setIoType(101) // 入出库状态: 11.库格移载
                .setTaskType("agv")
                .setIoPri(10D)
                .setFullPlt("Y") // 满板:Y
                .setPicking("N") // 拣料
                .setExitMk("N")// 退出
                .setStaNo(station.getDevNo())
                .setSourceLocNo(loc.getLocNo())
                .setEmptyMk(loc.getLocSts().equals("D") ? "Y" : "N")// 空板
                .setBarcode(loc.getBarcode())// 托盘码
                .setLinkMis("N")
                .setAppeUser(userId)
                .setAppeTime(new Date())
                .setModiUser(userId)
                .setModiTime(new Date());
        if (!taskService.insert(task)) {
            throw new CoolException("保存工作档失败");
        }
        List<LocDetl> detls = locDetlService.selectList(new EntityWrapper<LocDetl>().eq("loc_id", loc.getId()));
        if (Objects.isNull(detls) || detls.isEmpty()) {
            throw new CoolException("数据错误:库位明细为空!!");
        }
        List<TaskDetl> taskDetls = new ArrayList<>();
        detls.forEach(pakin -> {
            TaskDetl wrkDetl = new TaskDetl();
            BeanUtils.copyProperties(pakin, wrkDetl);
            wrkDetl.setWrkNo(workNo)
                    .setIoTime(new Date())
                    .setOrderNo(pakin.getOrderNo())
                    .setAnfme(pakin.getAnfme())
                    .setZpallet(pakin.getZpallet())
                    .setBatch(pakin.getBatch())
                    .setMatnr(pakin.getMatnr())
                    .setMaktx(pakin.getMaktx())
                    .setAppeUser(userId)
                    .setUnit(pakin.getUnit())
                    .setModel(pakin.getModel())
                    .setAppeTime(new Date())
                    .setModiUser(userId);
            taskDetls.add(wrkDetl);
        });
        //保存工作档明细
        if (!taskDetlService.insertBatch(taskDetls)) {
            throw new CoolException("保存工作档明细失败");
        }
        loc.setLocSts(LocStsType.LOC_STS_TYPE_R.type);
        loc.setModiUser(userId);
        loc.setModiTime(new Date());
        if (!locCacheService.updateById(loc)) {
            throw new CoolException("更新库位状态信息!!");
        }
        // 修改目标站点信息
        if (station.getLocSts().equals("O")) {
            station.setLocSts("S"); // S.入库预约
            station.setModiTime(new Date());
            station.setModiUser(userId);
            if (!basStationService.updateById(station)) {
                throw new CoolException("更新目标库位状态失败");
            }
        } else {
            throw new CoolException("移转失败,目标库位状态:" + station.getLocSts());
        }
    }
    /**
     * @author Ryan
     * @date 2025/9/22
     * @description: 生成AGV搬运任务
     * @version 1.0
@@ -1225,7 +1374,7 @@
        Task task = new Task();
        task.setWrkNo(workNo)
                .setIoTime(new Date())
                .setWrkSts(11L) // 工作状态:11.生成出库ID
                .setWrkSts(1L) // 工作状态:11.生成出库ID
                .setIoType(11) // 入出库状态: 11.库格移载
                .setTaskType("agv")
                .setIoPri(10D)
src/main/java/com/zy/asrs/task/handler/WorkMastHandler.java
@@ -6,8 +6,10 @@
import com.zy.asrs.entity.*;
import com.zy.asrs.enums.LocStsType;
import com.zy.asrs.service.*;
import com.zy.asrs.service.impl.BasStationServiceImpl;
import com.zy.asrs.service.impl.LocCacheServiceImpl;
import com.zy.asrs.service.impl.OrderPakinServiceImpl;
import com.zy.asrs.service.impl.TaskDetlServiceImpl;
import com.zy.asrs.task.AbstractHandler;
import com.zy.asrs.task.core.ReturnT;
import lombok.extern.slf4j.Slf4j;
@@ -50,6 +52,10 @@
    private OrderPakinService orderPakinService;
    @Autowired
    private TaskService taskService;
    @Autowired
    private TaskDetlService taskDetlService;
    @Autowired
    private BasStationServiceImpl basStationService;
    public ReturnT<String> start(WrkMast wrkMast) {
        // 4.入库完成
@@ -471,18 +477,16 @@
                                if (!orderDetlPakoutService.increaseQtyByOrderNo(wrkDetl.getOrderNo(), wrkDetl.getMatnr(),
                                        orderDetlPakout.getBatch(), wrkDetl.getBrand(), wrkDetl.getStandby1(), wrkDetl.getStandby2(), wrkDetl.getStandby3(),
                                        wrkDetl.getBoxType1(), wrkDetl.getBoxType2(), wrkDetl.getBoxType3(), wrkDetl.getAnfme())) {
//                                    exceptionHandle("全板出库 ===>> 更新订单完成数量失败;[workNo={0}],[locNo={1}]",
//                                            wrkMast.getWrkNo(), wrkMast.getLocNo());
                                    TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                                    return FAIL.setMsg("全板出库 ===>> 更新订单完成数量失败; [workNo=" + wrkMast.getWrkNo() + "],[locNo=" + wrkMast.getSourceLocNo() + "]");
                                }
                            }
                        } catch (Exception ignore) {
                        }
                    }
                    // 删除工作档源库位的库存明细
                    if (!locDetlService.delete(new EntityWrapper<LocDetl>().eq("loc_no", wrkMast.getSourceLocNo()))) {
//                        exceptionHandle("全板出库 ===>> 删除库存明细失败;[workNo={0}],[sourceLocNo={1}]", wrkMast.getWrkNo(), wrkMast.getSourceLocNo());
                        TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                        return FAIL.setMsg("全板出库 ===>> 删除库存明细失败; [workNo=" + wrkMast.getWrkNo() + "],[locNo=" + wrkMast.getSourceLocNo() + "]");
                    }
@@ -493,7 +497,6 @@
                        locMast.setModiTime(now);
                        locMast.setIoTime(now);
                        if (!locMastService.updateById(locMast)) {
//                            exceptionHandle("全板出库 ===>> 修改源库位状态失败;[workNo={0}],[sourceLocNo={1}]", wrkMast.getWrkNo(), wrkMast.getSourceLocNo());
                            TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                            return FAIL.setMsg("全板出库 ===>> 修改源库位状态失败; [workNo=" + wrkMast.getWrkNo() + "],[locNo=" + wrkMast.getSourceLocNo() + "]");
                        }
@@ -575,13 +578,103 @@
     * @version 1.0
     */
    @Transactional(rollbackFor = Exception.class)
    public ReturnT<String> AgvStart(Task wrkMast) {
    public ReturnT<String> AgvStart(Task task) {
        // 4.入库完成
        if (task.getWrkSts() == 4) {
            return agvDoIn(task);
            // 14.出库完成
        } else if (task.getWrkSts() == 14) {
            return agvDoOut(task);
        }
        return SUCCESS;
    }
    /**
     * @author Ryan
     * @date 2025/9/25
     * @description: AGV出库任务
     * @version 1.0
     */
    public ReturnT<String> agvDoOut(Task task) {
        if (task.getIoType().equals(101)) {
            Date now = new Date();
            LocCache locMast = locCacheService.selectOne(new EntityWrapper<LocCache>().eq("loc_no" ,task.getSourceLocNo()));
            if (Objects.isNull(locMast)) {
                throw new RuntimeException("数据错误:库位信息不能为空!!");
            }
            List<TaskDetl> wrkDetls101 = taskDetlService.selectList(new EntityWrapper<TaskDetl>().eq("wrk_no", task.getWrkNo()));
            if (wrkDetls101.isEmpty()) {
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                return FAIL.setMsg("全板出库 ===>> 工作明细档为空; [workNo=" + task.getWrkNo() + "],[locNo=" + task.getSourceLocNo() + "]");
            }
            for (TaskDetl wrkDetl : wrkDetls101) {
                // 更新订单完成数量
                OrderDetlPakout orderDetlPakout = orderDetlPakoutService.selectItem(wrkDetl.getOrderNo(), wrkDetl.getMatnr(), wrkDetl.getBatch(), wrkDetl.getBrand(), wrkDetl.getStandby1(), wrkDetl.getStandby2(), wrkDetl.getStandby3(),
                        wrkDetl.getBoxType1(), wrkDetl.getBoxType2(), wrkDetl.getBoxType3());
                if (orderDetlPakout == null) {
                    orderDetlPakout = orderDetlPakoutService.selectItem(wrkDetl.getOrderNo(), wrkDetl.getMatnr(), wrkDetl.getBatch(), wrkDetl.getBrand(), wrkDetl.getStandby1(), wrkDetl.getStandby2(), wrkDetl.getStandby3(),
                            wrkDetl.getBoxType1(), wrkDetl.getBoxType2(), wrkDetl.getBoxType3());
                }
                try {
                    if (!Cools.isEmpty(orderDetlPakout)) {
                        if (!orderDetlPakoutService.increaseQtyByOrderNo(wrkDetl.getOrderNo(), wrkDetl.getMatnr(),
                                orderDetlPakout.getBatch(), wrkDetl.getBrand(), wrkDetl.getStandby1(), wrkDetl.getStandby2(), wrkDetl.getStandby3(),
                                wrkDetl.getBoxType1(), wrkDetl.getBoxType2(), wrkDetl.getBoxType3(), wrkDetl.getAnfme())) {
                            TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                            return FAIL.setMsg("全板出库 ===>> 更新订单完成数量失败; [workNo=" + task.getWrkNo() + "],[locNo=" + task.getSourceLocNo() + "]");
                        }
                    }
                } catch (Exception ignore) {
                }
            }
            // 删除工作档源库位的库存明细
            if (!locDetlService.delete(new EntityWrapper<LocDetl>().eq("loc_no", task.getSourceLocNo()))) {
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                return FAIL.setMsg("全板出库 ===>> 删除库存明细失败; [workNo=" + task.getWrkNo() + "],[locNo=" + task.getSourceLocNo() + "]");
            }
            // 修改源库位状态 R ===>> O
            if (locMast.getLocSts().equals(LocStsType.LOC_STS_TYPE_R.type)) {
                locMast.setLocSts(LocStsType.LOC_STS_TYPE_O.type);
                locMast.setBarcode("");
                locMast.setModiTime(now);
                locMast.setIoTime(now);
                if (!locCacheService.updateById(locMast)) {
                    TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                    return FAIL.setMsg("全板出库 ===>> 修改源库位状态失败; [workNo=" + task.getWrkNo() + "],[locNo=" + task.getSourceLocNo() + "]");
                }
            } else {
                throw new CoolException("当前库位状态" + locMast.getLocSts() + ", 无法执行出库操作!!");
            }
            BasStation devNo = basStationService.selectOne(new EntityWrapper<BasStation>().eq("dev_no", task.getStaNo()));
            if (Objects.isNull(devNo)) {
                throw new CoolException("站点:" + task.getSourceStaNo() + ", 不存在!!");
            }
            devNo.setLocSts(LocStsType.LOC_STS_TYPE_F.type);
            devNo.setModiTime(new Date());
            if (!basStationService.updateById(devNo)) {
                throw new CoolException("站点信息修改失败!!");
            }
//            task.setWrkSts(15L);
//            if (!taskService.updateById(task)) {
//                throw new CoolException("任务状态修改失败!!");
//            }
        } else {
        }
        return SUCCESS;
    }
    @Transactional(rollbackFor = Exception.class)
    public ReturnT<String> agvDoIn(Task wrkMast) {
        LocCache locCache = locCacheService.selectOne(new EntityWrapper<LocCache>().eq("loc_no", wrkMast.getLocNo()));
        if (Objects.isNull(locCache)) {
            throw new CoolException("数据错误,库位不存在!!");
        }
        if (!locCache.getLocSts().equals(LocStsType.LOC_STS_TYPE_S.type)) {
            throw new CoolException("当前库位状态为:" +  LocStsType.LOC_STS_TYPE_S.type +  "." +  LocStsType.LOC_STS_TYPE_S.desc  + ",不是出库预约状态");
            throw new CoolException("当前库位状态为:" + LocStsType.LOC_STS_TYPE_S.type + "." + LocStsType.LOC_STS_TYPE_S.desc + ",不是出库预约状态");
        }
        List<WaitPakin> apallet = waitPakinService.selectList(new EntityWrapper<WaitPakin>().eq("zpallet", wrkMast.getBarcode()));
        if (Objects.isNull(apallet)) {
@@ -626,17 +719,6 @@
        if (Objects.isNull(pakins) || pakins.isEmpty()) {
            throw new CoolException("单据不存在!!");
        }
//        pakins.forEach(orderPakin -> {
//            orderPakin.setSettle(4L);
//            if (!orderPakinService.updateById(orderPakin)) {
//                throw new CoolException("单据修改失败!!");
//            }
//            List<OrderDetlPakin> detlPakins = orderDetlPakinService.selectList(new EntityWrapper<OrderDetlPakin>().eq("order_id", orderPakin.getId()));
//            if (Objects.isNull(detlPakins) || detlPakins.isEmpty()) {
//                throw new CoolException("单据明细不存在!!");
//            }
//        });
        return SUCCESS;
    }
src/main/java/com/zy/common/CodeBuilder.java
@@ -20,7 +20,7 @@
        generator.url="127.0.0.1:1433;databasename=jsxswms";
        generator.username="sa";
        generator.password="Skyouc#23";
        generator.table="agv_task_detl_log";
        generator.table="asr_bas_container";
        generator.packagePath="com.zy.asrs";
        generator.build();
    }
src/main/resources/mapper/BasContainerMapper.xml
New file
@@ -0,0 +1,12 @@
<?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="com.zy.asrs.mapper.BasContainerMapper">
    <!-- 通用查询映射结果 -->
    <resultMap id="BaseResultMap" type="com.zy.asrs.entity.BasContainer">
        <id column="Id" property="Id" />
        <result column="barcode" property="barcode" />
    </resultMap>
</mapper>
src/main/webapp/static/js/basContainer/basContainer.js
New file
@@ -0,0 +1,249 @@
var pageCurr;
layui.config({
    base: baseUrl + "/static/layui/lay/modules/"
}).use(['table','laydate', 'form', 'admin'], function(){
    var table = layui.table;
    var $ = layui.jquery;
    var layer = layui.layer;
    var layDate = layui.laydate;
    var form = layui.form;
    var admin = layui.admin;
    // 数据渲染
    tableIns = table.render({
        elem: '#basContainer',
        headers: {token: localStorage.getItem('token')},
        url: baseUrl+'/basContainer/list/auth',
        page: true,
        limit: 15,
        limits: [15, 30, 50, 100, 200, 500],
        toolbar: '#toolbar',
        cellMinWidth: 50,
        height: 'full-120',
        cols: [[
            {type: 'checkbox'}
            ,{field: 'barcode', align: 'center',title: '容器编码'}
            ,{field: 'type$', align: 'center',title: '容器类型'}
            ,{field: 'flagMix$', align: 'center',title: '是否混放'}
            ,{field: 'mixMax', align: 'center',title: '混放种类'}
            ,{field: 'createTime', align: 'center',title: '创建时间'}
            ,{field: 'updateTime', align: 'center',title: '修改时间'}
            ,{fixed: 'right', title:'操作', align: 'center', toolbar: '#operate', width:120}
        ]],
        request: {
            pageName: 'curr',
            pageSize: 'limit'
        },
        parseData: function (res) {
            return {
                'code': res.code,
                'msg': res.msg,
                'count': res.data.total,
                'data': res.data.records
            }
        },
        response: {
            statusCode: 200
        },
        done: function(res, curr, count) {
            if (res.code === 403) {
                top.location.href = baseUrl+"/";
            }
            pageCurr=curr;
            limit();
        }
    });
    // 监听排序事件
    table.on('sort(basContainer)', function (obj) {
        var searchData = {};
        $.each($('#search-box [name]').serializeArray(), function() {
            searchData[this.name] = this.value;
        });
        searchData['orderByField'] = obj.field;
        searchData['orderByType'] = obj.type;
        tableIns.reload({
            where: searchData,
            page: {curr: 1}
        });
    });
    // 监听头工具栏事件
    table.on('toolbar(basContainer)', function (obj) {
        var checkStatus = table.checkStatus(obj.config.id).data;
        switch(obj.event) {
            case 'addData':
                showEditModel();
                break;
            case 'deleteData':
               if (checkStatus.length === 0) {
                   layer.msg('请选择要删除的数据', {icon: 2});
                   return;
               }
               del(checkStatus.map(function (d) {
                   return d.id;
               }));
               break;
            case 'exportData':
                admin.confirm('确定导出Excel吗', {shadeClose: true}, function(){
                    var titles=[];
                    var fields=[];
                    obj.config.cols[0].map(function (col) {
                        if (col.type === 'normal' && col.hide === false && col.toolbar == null) {
                            titles.push(col.title);
                            fields.push(col.field);
                        }
                    });
                    var exportData = {};
                    $.each($('#search-box [name]').serializeArray(), function() {
                        exportData[this.name] = this.value;
                    });
                    var param = {
                        'basContainer': exportData,
                        'fields': fields
                    };
                    $.ajax({
                        url: baseUrl+"/basContainer/export/auth",
                        headers: {'token': localStorage.getItem('token')},
                        data: JSON.stringify(param),
                        dataType:'json',
                        contentType:'application/json;charset=UTF-8',
                        method: 'POST',
                        success: function (res) {
                            layer.closeAll();
                            if (res.code === 200) {
                                table.exportFile(titles,res.data,'xls');
                            } else if (res.code === 403) {
                                top.location.href = baseUrl+"/";
                            } else {
                                layer.msg(res.msg, {icon: 2})
                            }
                        }
                    });
                });
                break;
        }
    });
    // 监听行工具事件
    table.on('tool(basContainer)', function(obj){
        var data = obj.data;
        switch (obj.event) {
            case 'edit':
                showEditModel(data);
                break;
            case "del":
                del([data.id]);
                break;
        }
    });
    /* 弹窗 - 新增、修改 */
    function showEditModel(mData) {
        admin.open({
            type: 1,
            area: '600px',
            title: (mData ? '修改' : '添加') + '订单状态',
            content: $('#editDialog').html(),
            success: function (layero, dIndex) {
                layDateRender(mData);
                form.val('detail', mData);
                form.on('submit(editSubmit)', function (data) {
                    var loadIndex = layer.load(2);
                    $.ajax({
                        url: baseUrl+"/basContainer/"+(mData?'update':'add')+"/auth",
                        headers: {'token': localStorage.getItem('token')},
                        data: data.field,
                        method: 'POST',
                        success: function (res) {
                            layer.close(loadIndex);
                            if (res.code === 200){
                                layer.close(dIndex);
                                layer.msg(res.msg, {icon: 1});
                                tableReload();
                            } else if (res.code === 403){
                                top.location.href = baseUrl+"/";
                            }else {
                                layer.msg(res.msg, {icon: 2});
                            }
                        }
                    })
                    return false;
                });
                $(layero).children('.layui-layer-content').css('overflow', 'visible');
                layui.form.render('select');
            }
        });
    }
    /* 删除 */
    function del(ids) {
        layer.confirm('确定要删除选中数据吗?', {
            skin: 'layui-layer-admin',
            shade: .1
        }, function (i) {
            layer.close(i);
            var loadIndex = layer.load(2);
            $.ajax({
                url: baseUrl+"/basContainer/delete/auth",
                headers: {'token': localStorage.getItem('token')},
                data: {ids: ids},
                method: 'POST',
                success: function (res) {
                    layer.close(loadIndex);
                    if (res.code === 200){
                        layer.msg(res.msg, {icon: 1});
                        tableReload();
                    } else if (res.code === 403){
                        top.location.href = baseUrl+"/";
                    } else {
                        layer.msg(res.msg, {icon: 2});
                    }
                }
            })
        });
    }
    // 搜索
    form.on('submit(search)', function (data) {
        pageCurr = 1;
        tableReload(false);
    });
    // 重置
    form.on('submit(reset)', function (data) {
        pageCurr = 1;
        clearFormVal($('#search-box'));
        tableReload(false);
    });
    // 时间选择器
    function layDateRender(data) {
        setTimeout(function () {
            layDate.render({
                elem: '.layui-laydate-range'
                ,type: 'datetime'
                ,range: true
            });
        }, 300);
    }
    layDateRender();
});
// 关闭动作
$(document).on('click','#data-detail-close', function () {
    parent.layer.closeAll();
});
function tableReload(child) {
    var searchData = {};
    $.each($('#search-box [name]').serializeArray(), function() {
        searchData[this.name] = this.value;
    });
    tableIns.reload({
        where: searchData,
        page: {curr: pageCurr}
     });
}
src/main/webapp/static/js/common.js
@@ -183,9 +183,7 @@
    {field: 'matnr', align: 'center',title: '商品编号(品号)', width: 180}
    // {field: 'id', align: 'center',title: 'ID'}
    // ,{field: 'uuid', align: 'center',title: '编号'}
    // ,{field: 'tagId$', align: 'center',title: '所属归类'}
    ,{field: 'maktx', align: 'center',title: '商品名称(品名)', width: 200}
    // ,{field: 'name', align: 'center',title: '别名'}
    ,{field: 'specs', align: 'center',title: '规格'}
    ,{field: 'model', align: 'center',title: '代码', hide: true}
    ,{field: 'color', align: 'center',title: '颜色', hide: true}
src/main/webapp/static/js/mat/mat.js
@@ -5,9 +5,10 @@
    var cols = [
        {type: 'checkbox'}
        ,{field: 'tagId$', align: 'center',title: '归类', templet: '#tagTpl'}
        ,{field: 'store_max', align: 'center',title: '库存上限'}
        ,{field: 'store_min', align: 'center',title: '库存下限'}
        ,{field: 'store_max_date', align: 'center',title: '库龄上限(天)'}
        ,{field: 'locType$', align: 'center',title: '库位类型'}
        // ,{field: 'store_max', align: 'center',title: '库存上限'}
        // ,{field: 'store_min', align: 'center',title: '库存下限'}
        // ,{field: 'store_max_date', align: 'center',title: '库龄上限(天)'}
    ];
    cols.push.apply(cols, matCols);
    cols.push(
src/main/webapp/static/js/task/task.js
@@ -22,23 +22,23 @@
        height: 'full-120',
        cols: [[
            {type: 'checkbox'}
            , {field: 'wrkNo', align: 'center', title: '工作号', sort: true, width: 115}
            , {field: 'wrkNo', align: 'center', title: '工作号', sort: true, width: 105}
            , {field: 'ioTime$', align: 'center', title: '工作时间', width: 160}
            , {field: 'wrkSts$', align: 'center', title: '工作状态', width: 150}
            , {field: 'ioType$', align: 'center', title: '入出库类型', width: 150}
            , {field: 'ioPri', align: 'center', title: '优先级'}
            , {field: 'ioPri', align: 'center', title: '优先级', width: 80}
            , {field: 'taskType$', align: 'center', title: '任务类型'}
            , {field: 'crnNo$', align: 'center', title: '堆垛机', hide: true}
            , {field: 'sourceStaNo$', align: 'center', title: '源站'}
            , {field: 'staNo$', align: 'center', title: '目标站'}
            , {field: 'sourceLocNo', align: 'center', title: '源库位'}
            , {field: 'locNo', align: 'center', title: '目标库位'}
            , {field: 'barcode', align: 'center', title: '条码'}
            , {field: 'staNo$', align: 'center', title: '目标站', width: 120}
            , {field: 'sourceLocNo', align: 'center', title: '源库位', width: 120}
            , {field: 'locNo', align: 'center', title: '目标库位', width: 120}
            , {field: 'barcode', align: 'center', title: '条码', width: 110}
            , {field: 'preHave', align: 'center', title: '先入品', hide: true}
            , {field: 'takeNone', align: 'center', title: '空操作', hide: true}
            , {field: 'modiUser$', align: 'center', title: '修改人员', hide: true}
            , {field: 'modiTime$', align: 'center', title: '修改时间', hide: true, width: 160}
            , {fixed: 'right', title: '操作', align: 'center', toolbar: '#operate', width: 250}
            , {fixed: 'right', title: '操作', align: 'center', toolbar: '#operate', width: 200}
        ]],
        request: {
            pageName: 'curr',
src/main/webapp/views/basContainer/basContainer.html
New file
@@ -0,0 +1,92 @@
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <title></title>
    <meta name="renderer" content="webkit">
    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
    <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
    <link rel="stylesheet" href="../../static/layui/css/layui.css" media="all">
    <link rel="stylesheet" href="../../static/css/admin.css?v=318" media="all">
    <link rel="stylesheet" href="../../static/css/cool.css" media="all">
</head>
<body>
<div class="layui-fluid">
    <div class="layui-card">
        <div class="layui-card-body">
            <div class="layui-form toolbar" id="search-box">
                <div class="layui-form-item">
                    <div class="layui-inline">
                        <div class="layui-input-inline">
                            <input class="layui-input" type="text" name="id" placeholder="编号" autocomplete="off">
                        </div>
                    </div>
                     <div class="layui-inline" style="width: 300px">
                        <div class="layui-input-inline">
                            <input class="layui-input layui-laydate-range" name="create_time" type="text" placeholder="起始时间 - 终止时间" autocomplete="off" style="width: 300px">
                        </div>
                    </div>
                    <div class="layui-inline">
                        <div class="layui-input-inline">
                            <input class="layui-input" type="text" name="condition" placeholder="请输入" autocomplete="off">
                        </div>
                    </div>
                    <div class="layui-inline">&emsp;
                        <button class="layui-btn icon-btn" lay-filter="search" lay-submit>
                            <i class="layui-icon">&#xe615;</i>搜索
                        </button>
                        <button class="layui-btn icon-btn" lay-filter="reset" lay-submit>
                            <i class="layui-icon">&#xe666;</i>重置
                        </button>
                    </div>
                </div>
            </div>
            <table class="layui-hide" id="basContainer" lay-filter="basContainer"></table>
        </div>
    </div>
</div>
<script type="text/html" id="toolbar">
    <div class="layui-btn-container">
        <button class="layui-btn layui-btn-sm" id="btn-add" lay-event="addData">新增</button>
        <button class="layui-btn layui-btn-sm layui-btn-danger" id="btn-delete" lay-event="deleteData">删除</button>
        <button class="layui-btn layui-btn-primary layui-btn-sm" id="btn-export" lay-event="exportData" style="float: right">导出</button>
    </div>
</script>
<script type="text/html" id="operate">
    <a class="layui-btn layui-btn-primary layui-btn-xs btn-edit" lay-event="edit">修改</a>
    <a class="layui-btn layui-btn-danger layui-btn-xs btn-edit" lay-event="del">删除</a>
</script>
<script type="text/javascript" src="../../static/js/jquery/jquery-3.3.1.min.js"></script>
<script type="text/javascript" src="../../static/layui/layui.js" charset="utf-8"></script>
<script type="text/javascript" src="../../static/js/common.js" charset="utf-8"></script>
<script type="text/javascript" src="../../static/js/cool.js" charset="utf-8"></script>
<script type="text/javascript" src="../../static/js/basContainer/basContainer.js" charset="utf-8"></script>
</body>
<!-- 表单弹窗 -->
<script type="text/html" id="editDialog">
    <form id="detail" lay-filter="detail" class="layui-form admin-form model-form">
        <input name="id" type="hidden">
        <div class="layui-row">
            <div class="layui-col-md12">
                <div class="layui-form-item">
                    <label class="layui-form-label">容器编码: </label>
                    <div class="layui-input-block">
                        <input class="layui-input" name="barcode" placeholder="请输入容器编码">
                    </div>
                </div>
             </div>
        </div>
        <hr class="layui-bg-gray">
        <div class="layui-form-item text-right">
            <button class="layui-btn" lay-filter="editSubmit" lay-submit="">保存</button>
            <button class="layui-btn layui-btn-primary" type="button" ew-event="closeDialog">取消</button>
        </div>
    </form>
</script>
</html>
src/main/webapp/views/basStation/basStation.html
@@ -73,6 +73,9 @@
        <div class="layui-row">
            <div class="layui-col-md12">
                <div class="layui-form-item">
                    <input class="layui-input" name="id" style="display: none">
                </div>
                <div class="layui-form-item">
                    <label class="layui-form-label layui-form-required">编号: </label>
                    <div class="layui-input-block">
                        <input class="layui-input" name="devNo" placeholder="请输入编号" lay-vertype="tips"