自动化立体仓库 - WMS系统
lty
2025-07-02 6c15007b12d36d8f6d3e3f8127aa85a21aeb32c4
#锐麒初始化
16个文件已修改
763 ■■■■■ 已修改文件
pom.xml 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/controller/WorkController.java 248 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/service/WorkService.java 24 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/service/impl/BasCrnpServiceImpl.java 68 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/service/impl/WorkServiceImpl.java 157 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/utils/Utils.java 17 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/asrs/utils/VersionUtils.java 4 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/common/service/CommonService.java 176 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/zy/common/web/WcsController.java 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/application.yml 24 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/license.lic 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/static/js/common.js 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/static/js/pakStore/locCheckOut.js 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/static/js/pakStore/stockOut.js 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/views/pakStore/locCheckOut.html 17 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/webapp/views/pakStore/stockOut.html 16 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
pom.xml
@@ -119,7 +119,7 @@
    <build>
        <finalName>tzglasrs</finalName>
        <finalName>rqdzasrs</finalName>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
src/main/java/com/zy/asrs/controller/WorkController.java
@@ -80,73 +80,73 @@
        return R.ok("入库启动成功").add(workService.startupFullPutStore(fullStoreParam,getUserId()));
    }
//    @RequestMapping("/plate/out/start")
//    @ManagerAuth(memo = "出库作业")
//    public R fullStoreTakeStart(@RequestBody StockOutParam param) {
//        workService.startupFullTakeStore(param, getUserId());
//        return R.ok("出库启动成功");
//    }
    @RequestMapping("/plate/out/start")
    @ManagerAuth(memo = "出库作业")
    public R fullStoreTakeStart(@RequestBody StockOutFloorParam param) {
        if (param.getFloor() != null) {
            List<Integer> siteIdList = new ArrayList<>();
            // 第一步:根据楼层选择站点集合
            switch (param.getFloor()) {
                case 1: // 一楼(东区)
                    siteIdList = Arrays.asList(121, 124, 125, 126);
                    break;
                case 2: // 二楼(东区)
                    siteIdList = Arrays.asList(221, 224, 226, 229);
                    break;
                case 3: // 四楼(东区)
                    siteIdList = Arrays.asList(411, 412, 413, 414);
                    break;
                case 4: // 一楼(西区)
                    siteIdList = Arrays.asList(103); // 只有一个站点
                    break;
                case 5: // 二楼(西区)
                    siteIdList = Arrays.asList(201, 204, 206, 209);
                    break;
                case 6: // 四楼(西区)
                    siteIdList = Arrays.asList(401, 402, 403, 404);
                    break;
                default:
                    break;
            }
            // 第二步:根据 locNo 的排号,给每个 locDetl 设置 siteId
            if (param.getLocDetls() != null) {
                for (StockOutFloorParam.LocDetl locDetl : param.getLocDetls()) {
                    String locNo = locDetl.getLocNo(); // 如:0312001
                    if (locNo != null && locNo.length() >= 2) {
                        String rowStr = locNo.substring(0, 2); // 前两位为排号
                        int row = Integer.parseInt(rowStr);
                        Integer siteId = null;
                        // 站点分布规则
                        if (row == 1 || row == 2) {
                            siteId = siteIdList.size() > 0 ? siteIdList.get(0) : null;
                        } else if (row == 3 || row == 4) {
                            siteId = siteIdList.size() > 1 ? siteIdList.get(1) : null;
                        } else if (row == 5 || row == 6) {
                            siteId = siteIdList.size() > 2 ? siteIdList.get(2) : null;
                        } else if (row == 7 || row == 8) {
                            siteId = siteIdList.size() > 3 ? siteIdList.get(3) : null;
                        }
                        // 设置 siteId
                        locDetl.setSiteId(siteId);
                    }
                }
            }
        }
    public R fullStoreTakeStart(@RequestBody StockOutParam param) {
        workService.startupFullTakeStore(param, getUserId());
        return R.ok("出库启动成功");
    }
//    @RequestMapping("/plate/out/start")
//    @ManagerAuth(memo = "出库作业")
//    public R fullStoreTakeStart(@RequestBody StockOutFloorParam param) {
//        if (param.getFloor() != null) {
//            List<Integer> siteIdList = new ArrayList<>();
//
//            // 第一步:根据楼层选择站点集合
//            switch (param.getFloor()) {
//                case 1: // 一楼(东区)
//                    siteIdList = Arrays.asList(121, 124, 125, 126);
//                    break;
//                case 2: // 二楼(东区)
//                    siteIdList = Arrays.asList(221, 224, 226, 229);
//                    break;
//                case 3: // 四楼(东区)
//                    siteIdList = Arrays.asList(411, 412, 413, 414);
//                    break;
//                case 4: // 一楼(西区)
//                    siteIdList = Arrays.asList(103); // 只有一个站点
//                    break;
//                case 5: // 二楼(西区)
//                    siteIdList = Arrays.asList(201, 204, 206, 209);
//                    break;
//                case 6: // 四楼(西区)
//                    siteIdList = Arrays.asList(401, 402, 403, 404);
//                    break;
//                default:
//                    break;
//            }
//
//            // 第二步:根据 locNo 的排号,给每个 locDetl 设置 siteId
//            if (param.getLocDetls() != null) {
//                for (StockOutFloorParam.LocDetl locDetl : param.getLocDetls()) {
//                    String locNo = locDetl.getLocNo(); // 如:0312001
//                    if (locNo != null && locNo.length() >= 2) {
//                        String rowStr = locNo.substring(0, 2); // 前两位为排号
//                        int row = Integer.parseInt(rowStr);
//
//                        Integer siteId = null;
//
//                        // 站点分布规则
//                        if (row == 1 || row == 2) {
//                            siteId = siteIdList.size() > 0 ? siteIdList.get(0) : null;
//                        } else if (row == 3 || row == 4) {
//                            siteId = siteIdList.size() > 1 ? siteIdList.get(1) : null;
//                        } else if (row == 5 || row == 6) {
//                            siteId = siteIdList.size() > 2 ? siteIdList.get(2) : null;
//                        } else if (row == 7 || row == 8) {
//                            siteId = siteIdList.size() > 3 ? siteIdList.get(3) : null;
//                        }
//
//                        // 设置 siteId
//                        locDetl.setSiteId(siteId);
//                    }
//                }
//            }
//        }
//        workService.startupFullTakeStore(param, getUserId());
//        return R.ok("出库启动成功");
//    }
    @RequestMapping("/empty/plate/in/start")
    @ManagerAuth(memo = "空板入库")
@@ -161,75 +161,75 @@
        return R.ok("出库启动成功");
    }
//    @RequestMapping("/locCheck/out/start")
//    @ManagerAuth(memo = "盘点出库")
//    public R locCheckOutStart(@RequestBody StockOutParam param) {
//
//        workService.locCheckOut(param, getUserId());
//        return R.ok("出库启动成功");
//    }
    @RequestMapping("/locCheck/out/start")
    @ManagerAuth(memo = "盘点出库")
    public R locCheckOutStart(@RequestBody StockOutFloorParam param) {
        if (param.getFloor() != null) {
            List<Integer> siteIdList = new ArrayList<>();
    public R locCheckOutStart(@RequestBody StockOutParam param) {
            // 第一步:根据楼层选择站点集合
            switch (param.getFloor()) {
                case 1: // 一楼(东区)
                    siteIdList = Arrays.asList(121, 124, 125, 126);
                    break;
                case 2: // 二楼(东区)
                    siteIdList = Arrays.asList(221, 224, 226, 229);
                    break;
                case 3: // 四楼(东区)
                    siteIdList = Arrays.asList(411, 412, 413, 414);
                    break;
                case 4: // 一楼(西区)
                    siteIdList = Arrays.asList(103); // 只有一个站点
                    break;
                case 5: // 二楼(西区)
                    siteIdList = Arrays.asList(201, 204, 206, 209);
                    break;
                case 6: // 四楼(西区)
                    siteIdList = Arrays.asList(401, 402, 403, 404);
                    break;
                default:
                    break;
            }
            // 第二步:根据 locNo 的排号,给每个 locDetl 设置 siteId
            if (param.getLocDetls() != null) {
                for (StockOutFloorParam.LocDetl locDetl : param.getLocDetls()) {
                    String locNo = locDetl.getLocNo(); // 如:0312001
                    if (locNo != null && locNo.length() >= 2) {
                        String rowStr = locNo.substring(0, 2); // 前两位为排号
                        int row = Integer.parseInt(rowStr);
                        Integer siteId = null;
                        // 站点分布规则
                        if (row == 1 || row == 2) {
                            siteId = siteIdList.size() > 0 ? siteIdList.get(0) : null;
                        } else if (row == 3 || row == 4) {
                            siteId = siteIdList.size() > 1 ? siteIdList.get(1) : null;
                        } else if (row == 5 || row == 6) {
                            siteId = siteIdList.size() > 2 ? siteIdList.get(2) : null;
                        } else if (row == 7 || row == 8) {
                            siteId = siteIdList.size() > 3 ? siteIdList.get(3) : null;
                        }
                        // 设置 siteId
                        locDetl.setSiteId(siteId);
                    }
                }
            }
        }
        workService.locCheckOut(param, getUserId());
        return R.ok("出库启动成功");
    }
//    @RequestMapping("/locCheck/out/start")
//    @ManagerAuth(memo = "盘点出库")
//    public R locCheckOutStart(@RequestBody StockOutFloorParam param) {
//        if (param.getFloor() != null) {
//            List<Integer> siteIdList = new ArrayList<>();
//
//            // 第一步:根据楼层选择站点集合
//            switch (param.getFloor()) {
//                case 1: // 一楼(东区)
//                    siteIdList = Arrays.asList(121, 124, 125, 126);
//                    break;
//                case 2: // 二楼(东区)
//                    siteIdList = Arrays.asList(221, 224, 226, 229);
//                    break;
//                case 3: // 四楼(东区)
//                    siteIdList = Arrays.asList(411, 412, 413, 414);
//                    break;
//                case 4: // 一楼(西区)
//                    siteIdList = Arrays.asList(103); // 只有一个站点
//                    break;
//                case 5: // 二楼(西区)
//                    siteIdList = Arrays.asList(201, 204, 206, 209);
//                    break;
//                case 6: // 四楼(西区)
//                    siteIdList = Arrays.asList(401, 402, 403, 404);
//                    break;
//                default:
//                    break;
//            }
//
//            // 第二步:根据 locNo 的排号,给每个 locDetl 设置 siteId
//            if (param.getLocDetls() != null) {
//                for (StockOutFloorParam.LocDetl locDetl : param.getLocDetls()) {
//                    String locNo = locDetl.getLocNo(); // 如:0312001
//                    if (locNo != null && locNo.length() >= 2) {
//                        String rowStr = locNo.substring(0, 2); // 前两位为排号
//                        int row = Integer.parseInt(rowStr);
//
//                        Integer siteId = null;
//
//                        // 站点分布规则
//                        if (row == 1 || row == 2) {
//                            siteId = siteIdList.size() > 0 ? siteIdList.get(0) : null;
//                        } else if (row == 3 || row == 4) {
//                            siteId = siteIdList.size() > 1 ? siteIdList.get(1) : null;
//                        } else if (row == 5 || row == 6) {
//                            siteId = siteIdList.size() > 2 ? siteIdList.get(2) : null;
//                        } else if (row == 7 || row == 8) {
//                            siteId = siteIdList.size() > 3 ? siteIdList.get(3) : null;
//                        }
//
//                        // 设置 siteId
//                        locDetl.setSiteId(siteId);
//                    }
//                }
//            }
//        }
//        workService.locCheckOut(param, getUserId());
//        return R.ok("出库启动成功");
//    }
    @RequestMapping("/loc/move/start")
    @ManagerAuth(memo = "库位移转")
    public R locMoveStart(@RequestParam String sourceLocNo,
src/main/java/com/zy/asrs/service/WorkService.java
@@ -19,15 +19,15 @@
     */
    String startupFullPutStore(FullStoreParam param, Long userId);
//    /**
//     * 出库作业
//     */
//    void startupFullTakeStore(StockOutParam param, Long userId);
    /**
     * 出库作业
     */
    void startupFullTakeStore(StockOutFloorParam param, Long userId);
    void startupFullTakeStore(StockOutParam param, Long userId);
//    /**
//     * 出库作业
//     */
//    void startupFullTakeStore(StockOutFloorParam param, Long userId);
    /**
@@ -64,15 +64,15 @@
     */
    public WrkMast emptyPlateOut(EmptyPlateOutParam param);
//    /**
//     * 盘点出库
//     */
//    void locCheckOut(StockOutParam param, Long userId);
    /**
     * 盘点出库
     */
    void locCheckOut(StockOutFloorParam param, Long userId);
    void locCheckOut(StockOutParam param, Long userId);
//    /**
//     * 盘点出库
//     */
//    void locCheckOut(StockOutFloorParam param, Long userId);
    /**
     * 库位移转
src/main/java/com/zy/asrs/service/impl/BasCrnpServiceImpl.java
@@ -39,42 +39,42 @@
    @Override
    public boolean checkSiteError(Integer crnNo, boolean pakin) {
        BasCrnp crnp = this.selectById(crnNo);
        if (Cools.isEmpty(crnp)) {
//            log.error("{}号堆垛机不存在", crnNo);
            return false;
        }
        if (crnp.getCrnErr() != null && crnp.getCrnSts() != 3){
            log.error("{}号堆垛机非自动连线状态,无法作业!", crnNo);
            return false;
        }
        if (crnp.getCrnErr() != null) {
            if (crnp.getCrnErr() != 0 && crnp.getCrnErr() != 10 && crnp.getCrnErr() != 6) {
                log.error("{}号堆垛机异常,异常码{}", crnNo, crnp.getCrnErr());
                return false;
            }
        }
        if (pakin) {
            //控制入库暂存数,防止主干道堵塞,2022-10-23 ADD  未实装
//            int maxCount = 2;
//            int storeCount = wrkMastService.getStoreCount(crnNo);
//
//            if(storeCount >= maxCount){
//                log.error("{}号堆垛机暂存数已满!", crnNo);
//        BasCrnp crnp = this.selectById(crnNo);
//        if (Cools.isEmpty(crnp)) {
////            log.error("{}号堆垛机不存在", crnNo);
//            return false;
//        }
//        if (crnp.getCrnErr() != null && crnp.getCrnSts() != 3){
//            log.error("{}号堆垛机非自动连线状态,无法作业!", crnNo);
//            return false;
//        }
//        if (crnp.getCrnErr() != null) {
//            if (crnp.getCrnErr() != 0 && crnp.getCrnErr() != 10 && crnp.getCrnErr() != 6) {
//                log.error("{}号堆垛机异常,异常码{}", crnNo, crnp.getCrnErr());
//                return false;
//            }
            if ("N".equals(crnp.getInEnable())) {
                log.error("{}号堆垛机不可入", crnNo);
                return false;
            }
        } else {
            if ("N".equals(crnp.getOutEnable())) {
                log.error("{}号堆垛机不可出", crnNo);
                return false;
            }
        }
//        }
//
//        if (pakin) {
//            //控制入库暂存数,防止主干道堵塞,2022-10-23 ADD  未实装
////            int maxCount = 2;
////            int storeCount = wrkMastService.getStoreCount(crnNo);
////
////            if(storeCount >= maxCount){
////                log.error("{}号堆垛机暂存数已满!", crnNo);
////                return false;
////            }
//
//            if ("N".equals(crnp.getInEnable())) {
//                log.error("{}号堆垛机不可入", crnNo);
//                return false;
//            }
//        } else {
//            if ("N".equals(crnp.getOutEnable())) {
//                log.error("{}号堆垛机不可出", crnNo);
//                return false;
//            }
//        }
        return true;
    }
src/main/java/com/zy/asrs/service/impl/WorkServiceImpl.java
@@ -7,7 +7,10 @@
import com.core.common.SnowflakeIdWorker;
import com.core.exception.CoolException;
import com.zy.asrs.entity.*;
import com.zy.asrs.entity.param.*;
import com.zy.asrs.entity.param.EmptyPlateOutParam;
import com.zy.asrs.entity.param.FullStoreParam;
import com.zy.asrs.entity.param.LocDetlAdjustParam;
import com.zy.asrs.entity.param.StockOutParam;
import com.zy.asrs.service.*;
import com.zy.asrs.utils.Utils;
import com.zy.common.model.*;
@@ -152,81 +155,31 @@
        return null;
    }
//    @Override
//    @Transactional
//    public void startupFullTakeStore(StockOutFloorParam param, Long userId) {
//        // 目标站点状态检测
//        BasDevp staNo = null;
//        // 获取库位明细
//        List<LocDetlDto> locDetlDtos = new ArrayList<>();
//        for (StockOutFloorParam.LocDetl paramLocDetl : param.getLocDetls()) {
//             staNo = basDevpService.checkSiteStatus(paramLocDetl.getSiteId());
//
//            if (!Cools.isEmpty(paramLocDetl.getLocNo(), paramLocDetl.getMatnr(), paramLocDetl.getCount())) {
//                LocDetl one = locDetlService.selectItem(paramLocDetl.getLocNo(), paramLocDetl);
//                if (null != one) locDetlDtos.add(new LocDetlDto(one, paramLocDetl.getCount()));
//            }
//        }
//        if (!locDetlDtos.isEmpty()) {
//            LocMast locMast = locMastService.selectOne(new EntityWrapper<LocMast>().eq("loc_no", locDetlDtos.get(0).getLocDetl().getLocNo()));
//            if (locMast.getLocSts().equals("F") || locMast.getLocSts().equals("D")) {
//                // 启动出库开始 101.出库
//                stockOut(staNo, locDetlDtos, null, userId);
//            } else {
//                throw new CoolException("所选库位存在状态不为F、D的库位,库位号:" + locMast.getLocNo() + " 、当前状态:" + locMast.getLocSts() + "-" + locMast.getLocSts$());
//            }
//        } else {
//            throw new CoolException("库存不存在");
//        }
//    }
    @Override
    @Transactional
    public void startupFullTakeStore(StockOutFloorParam param, Long userId) {
        // 按 siteId 分组
        Map<Integer, List<LocDetlDto>> siteIdToLocDetlsMap = new HashMap<>();
        for (StockOutFloorParam.LocDetl paramLocDetl : param.getLocDetls()) {
    public void startupFullTakeStore(StockOutParam param, Long userId) {
        // 目标站点状态检测
        BasDevp staNo = basDevpService.checkSiteStatus(param.getOutSite());
        // 获取库位明细
        List<LocDetlDto> locDetlDtos = new ArrayList<>();
        for (StockOutParam.LocDetl paramLocDetl : param.getLocDetls()) {
            if (!Cools.isEmpty(paramLocDetl.getLocNo(), paramLocDetl.getMatnr(), paramLocDetl.getCount())) {
                LocDetl one = locDetlService.selectItem(paramLocDetl.getLocNo(), paramLocDetl);
                if (one != null) {
                    LocDetlDto dto = new LocDetlDto(one, paramLocDetl.getCount());
                    Integer siteId = paramLocDetl.getSiteId();
                    if (siteId != null) {
                        siteIdToLocDetlsMap.computeIfAbsent(siteId, k -> new ArrayList<>()).add(dto);
                    }
                }
                if (null != one) locDetlDtos.add(new LocDetlDto(one, paramLocDetl.getCount()));
            }
        }
        if (siteIdToLocDetlsMap.isEmpty()) {
            throw new CoolException("库存不存在");
        }
        // 遍历分组后的每个 siteId,逐个出库
        for (Map.Entry<Integer, List<LocDetlDto>> entry : siteIdToLocDetlsMap.entrySet()) {
            Integer siteId = entry.getKey();
            List<LocDetlDto> locDetlDtos = entry.getValue();
            // 校验库位状态
            LocMast locMast = locMastService.selectOne(
                    new EntityWrapper<LocMast>().eq("loc_no", locDetlDtos.get(0).getLocDetl().getLocNo())
            );
        if (!locDetlDtos.isEmpty()) {
            LocMast locMast = locMastService.selectOne(new EntityWrapper<LocMast>().eq("loc_no", locDetlDtos.get(0).getLocDetl().getLocNo()));
            if (locMast.getLocSts().equals("F") || locMast.getLocSts().equals("D")) {
                // 校验目标站点
                BasDevp staNo = basDevpService.checkSiteStatus(siteId);
                // 执行出库
                // 启动出库开始 101.出库
                stockOut(staNo, locDetlDtos, null, userId);
            } else {
                throw new CoolException("所选库位存在状态不为F、D的库位,库位号:" +
                        locMast.getLocNo() + " 、当前状态:" + locMast.getLocSts() + "-" + locMast.getLocSts$());
                throw new CoolException("所选库位存在状态不为F、D的库位,库位号:" + locMast.getLocNo() + " 、当前状态:" + locMast.getLocSts() + "-" + locMast.getLocSts$());
            }
        } else {
            throw new CoolException("库存不存在");
        }
    }
    @Override
    @Transactional
@@ -700,77 +653,29 @@
        return wrkMast;
    }
//    @Override
//    @Transactional
//    public void locCheckOut(StockOutParam param, Long userId) {
//        // 目标站点状态检测
//        BasDevp staNo = basDevpService.checkSiteStatus(param.getOutSite());
//        // 获取库位明细
//        List<LocDetlDto> locDetlDtos = new ArrayList<>();
//        for (StockOutParam.LocDetl paramLocDetl : param.getLocDetls()) {
//            if (!Cools.isEmpty(paramLocDetl.getLocNo(), paramLocDetl.getMatnr(), paramLocDetl.getCount())) {
//                LocDetl one = locDetlService.selectItem(paramLocDetl.getLocNo(), paramLocDetl);
//                if (null != one) locDetlDtos.add(new LocDetlDto(one, paramLocDetl.getCount()));
//            }
//        }
//        if (!locDetlDtos.isEmpty()) {
//            LocMast locMast = locMastService.selectOne(new EntityWrapper<LocMast>().eq("loc_no", locDetlDtos.get(0).getLocDetl().getLocNo()));
//            if (locMast.getLocSts().equals("F")) {
//                // 启动出库开始 107.盘点出库
//                stockOut(staNo, locDetlDtos, IoWorkType.CHECK_OUT, userId);
//            } else {
//                throw new CoolException("所选库位存在状态不为F的库位,库位号:" + locMast.getLocNo() + " 、当前状态:" + locMast.getLocSts() + "-" + locMast.getLocSts$());
//            }
//        } else {
//            throw new CoolException("库位物料不存在");
//        }
//    }
    @Override
    @Transactional
    public void locCheckOut(StockOutFloorParam param, Long userId) {
        // 按 siteId 分组
        Map<Integer, List<LocDetlDto>> siteIdToLocDetlsMap = new HashMap<>();
        for (StockOutFloorParam.LocDetl paramLocDetl : param.getLocDetls()) {
    public void locCheckOut(StockOutParam param, Long userId) {
        // 目标站点状态检测
        BasDevp staNo = basDevpService.checkSiteStatus(param.getOutSite());
        // 获取库位明细
        List<LocDetlDto> locDetlDtos = new ArrayList<>();
        for (StockOutParam.LocDetl paramLocDetl : param.getLocDetls()) {
            if (!Cools.isEmpty(paramLocDetl.getLocNo(), paramLocDetl.getMatnr(), paramLocDetl.getCount())) {
                LocDetl one = locDetlService.selectItem(paramLocDetl.getLocNo(), paramLocDetl);
                if (one != null) {
                    LocDetlDto dto = new LocDetlDto(one, paramLocDetl.getCount());
                    Integer siteId = paramLocDetl.getSiteId();
                    if (siteId != null) {
                        siteIdToLocDetlsMap.computeIfAbsent(siteId, k -> new ArrayList<>()).add(dto);
                    }
                }
                if (null != one) locDetlDtos.add(new LocDetlDto(one, paramLocDetl.getCount()));
            }
        }
        if (siteIdToLocDetlsMap.isEmpty()) {
            throw new CoolException("库存不存在");
        }
        // 遍历分组后的每个 siteId,逐个出库
        for (Map.Entry<Integer, List<LocDetlDto>> entry : siteIdToLocDetlsMap.entrySet()) {
            Integer siteId = entry.getKey();
            List<LocDetlDto> locDetlDtos = entry.getValue();
            // 校验库位状态
            LocMast locMast = locMastService.selectOne(
                    new EntityWrapper<LocMast>().eq("loc_no", locDetlDtos.get(0).getLocDetl().getLocNo())
            );
            if (locMast.getLocSts().equals("F") || locMast.getLocSts().equals("D")) {
                // 校验目标站点
                BasDevp staNo = basDevpService.checkSiteStatus(siteId);
                // 执行出库
        if (!locDetlDtos.isEmpty()) {
            LocMast locMast = locMastService.selectOne(new EntityWrapper<LocMast>().eq("loc_no", locDetlDtos.get(0).getLocDetl().getLocNo()));
            if (locMast.getLocSts().equals("F")) {
                // 启动出库开始 107.盘点出库
                stockOut(staNo, locDetlDtos, IoWorkType.CHECK_OUT, userId);
            } else {
                throw new CoolException("所选库位存在状态不为F、D的库位,库位号:" +
                        locMast.getLocNo() + " 、当前状态:" + locMast.getLocSts() + "-" + locMast.getLocSts$());
                throw new CoolException("所选库位存在状态不为F的库位,库位号:" + locMast.getLocNo() + " 、当前状态:" + locMast.getLocSts() + "-" + locMast.getLocSts$());
            }
        } else {
            throw new CoolException("库位物料不存在");
        }
    }
src/main/java/com/zy/asrs/utils/Utils.java
@@ -142,14 +142,13 @@
        int row = getRow(shallowLoc);
        int remainder = (int) Arith.remainder(row, slaveProperties.getGroupCount());
        int targetRow;
//        if (remainder == 2) {
//            targetRow = row - 1;
//        } else if (remainder == 3) {
//            targetRow = row + 1;
//        } else {
//            throw new RuntimeException(shallowLoc + "不是浅库位,系统繁忙");
//        }
        targetRow = row;
        if (remainder == 2) {
            targetRow = row - 1;
        } else if (remainder == 3) {
            targetRow = row + 1;
        } else {
            throw new RuntimeException(shallowLoc + "不是浅库位,系统繁忙");
        }
        return zerofill(String.valueOf(targetRow), 2) + shallowLoc.substring(2);
    }
@@ -281,7 +280,7 @@
    //库位排号分配
    public static int[] LocNecessaryParameters(Integer whsType, Integer curRow, Integer crnNumber) {
        switch (2){
        switch (whsType){
            case 1://经典双伸库位
                return LocNecessaryParametersDoubleExtension(whsType, curRow, crnNumber); //已完善
            case 2://经典单伸库位(2排货架)
src/main/java/com/zy/asrs/utils/VersionUtils.java
@@ -5,6 +5,8 @@
import com.zy.asrs.entity.result.Pakin;
import com.zy.common.model.LocTypeDto;
import java.util.Objects;
/**
 * Created by vincent on 2020/7/14
 */
@@ -28,7 +30,7 @@
     **/
    public static boolean locMoveCheckLocTypeComplete(LocMast loc, LocTypeDto dto) {
        // 如果源库位是高库位,目标库位是低库位
        return loc.getLocType1() >= dto.getLocType1();
        return Objects.equals(loc.getLocType1(), dto.getLocType1());
    }
}
src/main/java/com/zy/common/service/CommonService.java
@@ -123,7 +123,7 @@
    @Transactional
    public StartupDto getLocNo(Integer whsType, Integer staDescId, Integer sourceStaNo, String matnr, String batch, String grade, LocTypeDto locTypeDto) {
         whsType = Utils.GetWhsType(sourceStaNo);
        return getLocNoRun(whsType,staDescId,sourceStaNo,matnr,batch,grade,0,locTypeDto,0);
        return getLocNo(whsType,staDescId,sourceStaNo,matnr,batch,grade,0,locTypeDto,0);
    }
    /**
@@ -136,7 +136,7 @@
     * @return locNo 检索到的库位号
     */
    @Transactional
    public StartupDto getLocNoRun(Integer whsType, Integer staDescId, Integer sourceStaNo, String matnr, String batch, String grade, Integer moveCrnNo, LocTypeDto locTypeDto, int times) {
    public StartupDto getLocNo(Integer whsType, Integer staDescId, Integer sourceStaNo, String matnr, String batch, String grade, Integer moveCrnNo, LocTypeDto locTypeDto, int times) {
        if (Cools.isEmpty(matnr)) {  //物料号
            matnr = "";
        }
@@ -160,7 +160,6 @@
        int eRow = rowLastno.geteRow();
        int crnNumber = rowLastno.getCrnQty();
        int tagId = matService.getTagIdByMatnr(matnr);
        if (Cools.isEmpty(rowLastno)) {
            throw new CoolException("数据异常,请联系管理员");
        }
@@ -169,71 +168,65 @@
        if (!Cools.isEmpty(moveCrnNo) && moveCrnNo!=0){
            crnNumber = moveCrnNo;
            curRow = eRow;
            if (times==0){
                curRow = moveCrnNo*4-1;
            }else {
                curRow = moveCrnNo*4-2;
            }
        }
        //此程序用于优化堆垛机异常时的运行时间
        for (int i = times; i < crnNumber*2; i++) {
        for (int i = times; i < crnNumber; i++) {
            int[] locNecessaryParameters = Utils.LocNecessaryParameters(whsType, curRow, crnNumber);
            curRow = locNecessaryParameters[1];
            crnNo = locNecessaryParameters[2];
            if (basCrnpService.checkSiteError(crnNo, true)) {
                rowCount =  locNecessaryParameters[0];
                nearRow = locNecessaryParameters[3];
                List<LocMast> locMasts = locMastService.selectList(new EntityWrapper<LocMast>().eq("row1", nearRow).eq("loc_sts", "O"));
                int crnCountO = wrkMastService.selectCount(new EntityWrapper<WrkMast>().eq("crn_no", crnNo).le("io_type",100));
                if (locMasts.size()-crnCountO<=0){
                    times++;
                    continue;
                }
                break;
            } else {
                times++;
            }
        }
//        if (nearRow == 0) {
//            throw new CoolException("无可用堆垛机");
//        }
        if (nearRow == 0) {
            throw new CoolException("无可用堆垛机");
        }
        boolean signRule1 = false;
        boolean signRule2 = false;
        if (Utils.BooleanWhsTypeStaIoType(whsType)){
            // 靠近摆放规则 --- 同天同规格物料 //分离版
            if (!Cools.isEmpty(matnr) &&  staDescId == 1){
                signRule1 = false;
            }
            // 靠近摆放规则 --- 同天同规格物料 //互通版
            if (!Cools.isEmpty(matnr) && staDescId == 1) {
                signRule2 = true;
            }
        // 靠近摆放规则 --- 同天同规格物料 //分离版
//        if (!Cools.isEmpty(matnr) &&  (staDescId == 1)){
//            signRule1 = true;
//        }
        // 靠近摆放规则 --- 同天同规格物料 //互通版
        if (!Cools.isEmpty(matnr) && staDescId == 1) {
            signRule2 = true;
        }
            if (!Cools.isEmpty(matnr) &&  (staDescId == 11 || staDescId == 111)) {
                signRule1 = true;
            }
        if (!Cools.isEmpty(matnr) &&  (staDescId == 11 || staDescId == 111)) {
            signRule1 = true;
        }
        if (signRule1){
            if (nearRow!=curRow){
                List<LocMast> locMasts = locMastService.selectList(new EntityWrapper<LocMast>().eq("row1", nearRow).eq("loc_sts", "O"));
                for (LocMast locMast1:locMasts){
                    //获取巷道
                    List<String> groupOutsideLocCrn = Utils.getGroupOutLocCrn(curRow,nearRow,locMast1.getLocNo(), curRow>nearRow);
                    //获取目标库位所在巷道最浅非空库位
                    LocMast locMastF = locMastService.selectLocByLocStsPakInF(curRow,nearRow,groupOutsideLocCrn);
                    if (!Cools.isEmpty(locMastF) && locMastF.getLocSts().equals("F")){
                        LocDetl locDetl = locDetlService.selectOne(new EntityWrapper<LocDetl>().eq("loc_no", locMastF.getLocNo()));
                        if (!Cools.isEmpty(locDetl) && matnr.equals(locDetl.getMatnr()) && batch.equals(Cools.isEmpty(locDetl.getBatch()) ? "" : locDetl.getBatch()) && grade.equals(Cools.isEmpty(locDetl.getBrand()) ? "" : locDetl.getBrand())) {
                            //获取目标库位所在巷道最浅非空库位
                            locMast = locMastService.selectLocByLocStsPakInO(curRow,nearRow,groupOutsideLocCrn);
                            break;
                        }
            List<LocMast> locMasts = locMastService.selectList(new EntityWrapper<LocMast>().eq("row1", nearRow).eq("loc_sts", "O"));
            for (LocMast locMast1:locMasts){
                if (VersionUtils.locMoveCheckLocTypeComplete(locMast1, locTypeDto)) {
                    continue;
                }
                String shallowLoc = Utils.getDeepLoc(slaveProperties,locMast1.getLocNo());
                LocMast locMast2 = locMastService.selectOne(new EntityWrapper<LocMast>().eq("loc_no",shallowLoc));
                if (!Cools.isEmpty(locMast2) && locMast2.getLocSts().equals("F")){
                    LocDetl locDetl = locDetlService.selectOne(new EntityWrapper<LocDetl>().eq("loc_no", locMast2.getLocNo()));
                    if (!Cools.isEmpty(locDetl) && matnr.equals(locDetl.getMatnr())) {
                        locMast = locMast1;
                        break;
                    }
                }
            }
        }else if (signRule2){
            List<String> locNos = locDetlService.getSameDetlToday(matnr, sRow, eRow);
            List<String> locNos = locDetlService.getSameDetlToday(matnr,batch, sRow, eRow);
            for (String locNo : locNos) {
                if (Utils.isShallowLoc(slaveProperties, locNo)) {
                    continue;
@@ -254,7 +247,7 @@
        }
//        // 靠近摆放规则 --- 空托  //分离版
//        if (staDescId == 10 && Utils.BooleanWhsTypeStaIoType(whsType)) {
//        if (staDescId == 10) {
//            List<LocMast> locMasts = locMastService.selectList(new EntityWrapper<LocMast>().eq("row1", nearRow).eq("loc_sts", "O"));
//            for (LocMast locMast1:locMasts){
//                if (VersionUtils.locMoveCheckLocTypeComplete(locMast1, locTypeDto)) {
@@ -270,7 +263,7 @@
//        }
        // 靠近摆放规则 --- 空托 //互通版
        if (staDescId == 10  && Utils.BooleanWhsTypeStaIoType(whsType)) {
        if (staDescId == 10) {
            List<LocMast> locMasts = locMastService.selectList(new EntityWrapper<LocMast>().eq("loc_sts", "D").ge("row1", sRow).le("row1", eRow));
            if (locMasts.size() > 0) {
                for (LocMast loc : locMasts) {
@@ -308,19 +301,17 @@
                log.error("type_no={},stn_no={},crn_no={}", staDescId, sourceStaNo, crnNo);
//                throw new CoolException("入库路径不存在");
                crnNo = 0;
            }else {
                staNo = basDevpService.selectById(staDesc.getCrnStn());
                if (!staNo.getAutoing().equals("Y")) {
                    log.error("目标站"+staDesc.getCrnStn()+"不可用");
//                throw new CoolException("目标站"+staDesc.getCrnStn()+"不可用");
                    crnNo = 0;
                }
                startupDto.setStaNo(staNo.getDevNo());
            }
            staNo = basDevpService.selectById(staDesc.getCrnStn());
            if (!staNo.getAutoing().equals("Y")) {
//                throw new CoolException("目标站"+staDesc.getCrnStn()+"不可用");
                crnNo = 0;
            }
            startupDto.setStaNo(staNo.getDevNo());
        }
        // 更新库位排号
        if (Utils.BooleanWhsTypeSta(whsType, staDescId) && Cools.isEmpty(locMast)) {
        if (Utils.BooleanWhsTypeSta(whsType, staDescId)) {
            rowLastno.setCurrentRow(curRow);
            rowLastnoService.updateById(rowLastno);
        }
@@ -329,87 +320,30 @@
        // 1.按规则查找库位
        if (Cools.isEmpty(locMast) && crnNo != 0) {
            List<LocMast> locMasts = null;
            if(sourceStaNo % 100 > 10){
                locMasts = locMastService.selectList(new EntityWrapper<LocMast>()
                        .eq("row1", nearRow)
                        .eq("loc_sts", "O")
                        .orderBy("lev1",true).orderBy("bay1",false));
            }else{
                 locMasts = locMastService.selectList(new EntityWrapper<LocMast>()
                        .eq("row1", nearRow)
                        .eq("loc_sts", "O")
                        .orderBy("lev1",true).orderBy("bay1",true));
            }
//            List<LocMast> locMasts = locMastService.selectList(new EntityWrapper<LocMast>()
//                    .eq("row1", nearRow)
//                    .eq("loc_sts", "O")
//                    .orderBy("lev1",true).orderBy("bay1",true));
//            for (LocMast locMast1 : locMasts) {
//                if (!VersionUtils.locMoveCheckLocTypeComplete(locMast1, locTypeDto)) {
//                    continue;
//                }
//                if (Utils.BooleanWhsTypeStaIoType(whsType)){
////                    String shallowLoc = Utils.getDeepLoc(slaveProperties, locMast1.getLocNo());
//                    LocMast locMast2 = locMastService.selectOne(new EntityWrapper<LocMast>()
//                            .eq("loc_sts", "O"));
//                    if (!Cools.isEmpty(locMast2)) {
//                        locMast = locMast2;
//                        break;
//                    }
//                } else {
//                    if (!Cools.isEmpty(locMast1)) {
//                        locMast = locMast1;
//                        break;
//                    }
//                }
//            }
            if (Cools.isEmpty(locMast) && Utils.BooleanWhsTypeStaIoType(whsType)){
                if(tagId == 226){
                    List<LocMast> filteredLocMasts = new ArrayList<>();
                    for (LocMast loc : locMasts) {
                        Integer lev = loc.getLev1();
                        if (lev != null && lev >= 6 && lev <= 10) {
                            filteredLocMasts.add(loc);
                        }
                    }
                    locMasts = filteredLocMasts;
            List<LocMast> locMasts = locMastService.selectList(new EntityWrapper<LocMast>().eq("row1", nearRow).eq("loc_sts", "O"));
            for (LocMast locMast1 : locMasts) {
                if (!VersionUtils.locMoveCheckLocTypeComplete(locMast1, locTypeDto)) {
                    continue;
                }
//                if(tagId == 226){  //原材料毛胚等
//                    List<LocMast> filteredLocMasts = new ArrayList<>();
//                    for (LocMast loc : locMasts) {
//                        Integer lev = loc.getLev1();
//                        if (lev != null && lev >= 1 && lev <= 5) {
//                            filteredLocMasts.add(loc);
//                        }
//                    }
//                    locMasts = filteredLocMasts;
//                }
                for (LocMast locMast1 : locMasts) {
                    if (!VersionUtils.locMoveCheckLocTypeComplete(locMast1, locTypeDto)) {
                        continue;
                    }
                    if (!Cools.isEmpty(locMast1)) {
                        locMast = locMast1;
                        break;
                    }
                String shallowLoc = Utils.getDeepLoc(slaveProperties, locMast1.getLocNo());
                LocMast locMast2 = locMastService.selectOne(new EntityWrapper<LocMast>().eq("loc_no", shallowLoc).eq("loc_sts", "O"));
                if (!Cools.isEmpty(locMast2)) {
                    locMast = locMast2;
                    break;
                }
            }
        }
        if (!basCrnpService.checkSiteError(crnNo, true)) {
        if (!Cools.isEmpty(locMast) && !basCrnpService.checkSiteError(crnNo, true)) {
            locMast = null;
        }
        // 递归查询
        if (Cools.isEmpty(locMast) || !locMast.getLocSts().equals("O")) {
            // 当前巷道无空库位时,递归调整至下一巷道,检索全部巷道无果后,跳出递归
            if (times < 1) {
            if (times < rowCount) {
                times = times + 1;
                return getLocNoRun(whsType, staDescId, sourceStaNo, matnr, batch, grade,moveCrnNo+1, locTypeDto, times);
                return getLocNo(1, staDescId, sourceStaNo, matnr, batch, grade,moveCrnNo, locTypeDto, times);
            }
//            // 2.库位当前所属尺寸无空库位时,调整尺寸参数,向上兼容检索库位
//            if (locTypeDto.getLocType1() < 2) {
src/main/java/com/zy/common/web/WcsController.java
@@ -315,7 +315,7 @@
            return R.error("库存没有空板");
        }
        EmptyPlateOutParam emptyPlateOutParam = new EmptyPlateOutParam();
        emptyPlateOutParam.setOutSite(12);
        emptyPlateOutParam.setOutSite(101);
        emptyPlateOutParam.setLocNos(new ArrayList<String>() {{
            add(locMast.getLocNo() + "");
        }});
@@ -333,7 +333,7 @@
        // 检索库位
        List<String> matnrs = waitPakins.stream().map(WaitPakin::getMatnr).distinct().collect(Collectors.toList());
        List<String> batchs = waitPakins.stream().map(WaitPakin::getBatch).distinct().collect(Collectors.toList());
        StartupDto dto = commonService.getLocNo(2, 1, devpNo, matnrs.get(0), batchs.get(0), null, locTypeDto);
        StartupDto dto = commonService.getLocNo(1, 1, devpNo, matnrs.get(0), batchs.get(0), null, locTypeDto);
        int workNo = dto.getWorkNo();
        Date now = new Date();
        // 生成工作档
src/main/resources/application.yml
@@ -10,7 +10,7 @@
    enabled: false
  datasource:
    driver-class-name: com.microsoft.sqlserver.jdbc.SQLServerDriver
    url: jdbc:sqlserver://127.0.0.1:1433;databasename=tzglasrs
    url: jdbc:sqlserver://127.0.0.1:1433;databasename=rqdzasrs
    username: sa
    password: sa@123
  mvc:
@@ -40,7 +40,7 @@
#License相关配置
license:
  subject: tzglasrs
  subject: rqdzasrs
  publicAlias: publicCert
  storePass: public_zhongyang_123456789
  licensePath: license.lic
@@ -49,15 +49,15 @@
# 下位机配置
wcs-slave:
  # 双深
  doubleDeep: false
  doubleDeep: true
  # 双深库位排号
  doubleLocs: 1,4,5,8,9,12,13,16
  doubleLocs: 1,4
  # 一个堆垛机负责的货架排数
  groupCount: 4
  # 左深库位排号
  doubleLocsLeft: 1,5,9,13
  doubleLocsLeft: 1
  # 右深库位排号
  doubleLocsRight: 4,8,12,16
  doubleLocsRight: 4
# wms参数配置
wms-parameter:
  # 自动补空板功能开关
@@ -103,15 +103,13 @@
    lcid: 2052
  #ERP接口
  enabled: true
  enabled: false
  #enabled: false
  #查看ERP中间表间隔
  refreshtime: 0/5 * * * * ?
  db:
    driver_class_name: com.microsoft.sqlserver.jdbc.SQLServerDriver
    url: jdbc:sqlserver://127.0.0.1:1433;databasename=TZGLLK
    username: sa
    password: sa@123
#    url: jdbc:sqlserver://192.168.4.138:1433;databasename=XDLinkLK2
#    username: sa
#    password: sa@123
    url: jdbc:sqlserver://192.168.16.202:9116;databasename=TZGLLK
    username: GLLK
    password: GLLK0626
src/main/resources/license.lic
Binary files differ
src/main/webapp/static/js/common.js
@@ -1,4 +1,4 @@
var baseUrl = "/tzglasrs";
var baseUrl = "/rqdzasrs";
// 详情窗口-高度
var detailHeight = '80%';
src/main/webapp/static/js/pakStore/locCheckOut.js
@@ -48,7 +48,7 @@
                        return;
                    }
                    let param = {
                        floor: staNo,
                        outSite: staNo,
                        locDetls: locDetlData
                    }
                    $.ajax({
src/main/webapp/static/js/pakStore/stockOut.js
@@ -79,7 +79,7 @@
                        return;
                    }
                    let param = {
                        floor: staNo,
                        outSite: staNo,
                        locDetls: locDetlData
                    }
                    $.ajax({
src/main/webapp/views/pakStore/locCheckOut.html
@@ -99,12 +99,7 @@
                <span id="staNoSpan">盘点站:</span>
                <select id="staNoSelect" lay-verify="required">
                    <option value="">请选择站点</option>
<!--                    <option value="1">一楼(东区)</option>-->
<!--                    <option value="2">二楼(东区)</option>-->
                                        <option value="3">四楼(东区)</option>
<!--                    <option value="4">一楼(西区)</option>-->
<!--                    <option value="5">二楼(西区)</option>-->
                    <option value="6">四楼(西区)</option>               </select>
                </select>
                <!-- 2.启动出库 -->
                <button class="layui-btn layui-btn-lg" id="btn-outbound" lay-event="outbound">盘点出库</button>
            </div>
@@ -119,11 +114,11 @@
    <table class="layui-table" id="chooseData" lay-filter="chooseData"></table>
</div>
<!--<script type="text/template" id="takeSiteSelectTemplate">-->
<!--    {{#each data}}-->
<!--    <option value="{{this}}">{{this}}</option>-->
<!--    {{/each}}-->
<!--</script>-->
<script type="text/template" id="takeSiteSelectTemplate">
    {{#each data}}
    <option value="{{this}}">{{this}}</option>
    {{/each}}
</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>
src/main/webapp/views/pakStore/stockOut.html
@@ -99,12 +99,6 @@
                <span id="staNoSpan">出库口:</span>
                <select id="staNoSelect" lay-verify="required">
                    <option value="">请选择站点</option>
                    <option value="1">一楼(东区)</option>
                    <option value="2">二楼(东区)</option>
<!--                    <option value="3">四楼(东区)</option>-->
                    <option value="4">一楼(西区)</option>
                    <option value="5">二楼(西区)</option>
<!--                    <option value="6">四楼(西区)</option>-->
                </select>
                <!-- 2.启动出库 -->
@@ -128,11 +122,11 @@
<script type="text/javascript" src="../../static/js/handlebars/handlebars-v4.5.3.js"></script>
<script type="text/javascript" src="../../static/js/pakStore/stockOut.js" charset="utf-8"></script>
<!--<script type="text/template" id="takeSiteSelectTemplate">-->
<!--    {{#each data}}-->
<!--    <option value="{{siteId}}">{{desc}}</option>-->
<!--    {{/each}}-->
<!--</script>-->
<script type="text/template" id="takeSiteSelectTemplate">
    {{#each data}}
    <option value="{{siteId}}">{{desc}}</option>
    {{/each}}
</script>
</body>
</html>