src/main/java/com/zy/asrs/mapper/LocDetlMapper.java
@@ -23,6 +23,8 @@ LocDetl selectItem(@Param("locNo")String locNo, @Param("matnr")String matnr, @Param("batch")String batch); LocDetl selectItemByLocNo(String locNo); int deleteItem(@Param("locNo")String locNo, @Param("matnr")String matnr, @Param("batch")String batch); int updateAnfme(@Param("anfme")Double anfme, @Param("locNo")String locNo, @Param("matnr")String matnr, @Param("batch")String batch); src/main/java/com/zy/asrs/mapper/WrkDetlMapper.java
@@ -6,6 +6,7 @@ import org.apache.ibatis.annotations.Param; import org.springframework.stereotype.Repository; import java.util.Date; import java.util.List; @Mapper @@ -13,6 +14,8 @@ public interface WrkDetlMapper extends BaseMapper<WrkDetl> { List<WrkDetl> selectByWrkNo(Integer wrkNo); WrkDetl selectSingleByWrkNo(Integer workNo); int deleteItem(@Param("wrkNo")Integer wrkNo, @Param("matnr")String matnr, @Param("batch")String batch); @@ -25,4 +28,7 @@ List<WrkDetl> selectPakoutQuery(@Param("staNo")Integer staNo, @Param("matnr")String matnr); List<WrkDetl> selectAndLogByOrderNoGroupByMatnrOfSum(String orderNo); int updateIoTime(@Param("workNo") Integer workNo, @Param("ioTime") Date ioTime); } src/main/java/com/zy/asrs/mapper/WrkMastMapper.java
@@ -2,9 +2,7 @@ import com.baomidou.mybatisplus.mapper.BaseMapper; import com.zy.asrs.entity.WrkMast; import org.apache.ibatis.annotations.Mapper; import org.apache.ibatis.annotations.Param; import org.apache.ibatis.annotations.Select; import org.apache.ibatis.annotations.*; import org.springframework.stereotype.Repository; import java.util.List; @@ -23,4 +21,11 @@ List<WrkMast> selectWrkMastWrkDetlMatnrBatch(@Param("ioType") Integer ioType, @Param("matnr") String matnr , @Param("batch") String batch , @Param("grade") String grade , @Param("crnNo") Integer crnNo); @Insert("insert into asr_wrk_mast_log select * from asr_wrk_mast where wrk_no=#{workNo}") int saveWrkMastLog(Integer workNo); @Insert("insert into asr_wrk_detl_log select * from asr_wrk_detl where wrk_no=#{workNo}") int saveWrkDetlLog(Integer workNo); } src/main/java/com/zy/asrs/service/LocDetlService.java
@@ -15,6 +15,8 @@ LocDetl selectItem(String locNo, String matnr, String batch); LocDetl selectItemByLocNo(String locNo); Page<LocDetl> getStockOut(Page<LocDetl> page); /** src/main/java/com/zy/asrs/service/WrkDetlService.java
@@ -2,6 +2,7 @@ import com.baomidou.mybatisplus.service.IService; import com.zy.asrs.entity.WrkDetl; import com.zy.asrs.entity.WrkMast; import com.zy.common.model.DetlDto; import java.util.Date; @@ -13,6 +14,8 @@ List<WrkDetl> selectByWrkNo(Integer wrkNo); WrkDetl selectSingleByWrkNo(Integer workNo); boolean updateAnfme(Double anfme, Integer wrkNo, String matnr, String batch); List<WrkDetl> selectAndLogByOrderNo(String orderNo); @@ -23,4 +26,7 @@ List<WrkDetl> selectAndLogByOrderNoGroupByMatnrOfSum(String orderNo); boolean updateIoTime(Integer workNo, Date ioTime); } src/main/java/com/zy/asrs/service/impl/LocDetlServiceImpl.java
@@ -118,6 +118,10 @@ return this.baseMapper.selectItem(locNo, matnr, batch); } public LocDetl selectItemByLocNo(String locNo) { return this.baseMapper.selectItemByLocNo(locNo); } @Override public Double getLocDetlSumQty(String locNo) { return this.baseMapper.selectLocDetlSumQty(locNo); src/main/java/com/zy/asrs/service/impl/WorkServiceImpl.java
@@ -240,7 +240,7 @@ // 计算优先级 dto.setPriority(priority); priority++; // 下一个任务优先级递增 priority--; // 下一个任务优先级递增 // 获取库位 LocMast locMast = locMastService.selectById(dto.getLocNo()); @@ -266,6 +266,7 @@ // 生成工作号 int workNo = commonService.getWorkNo(WorkNoType.getWorkNoType(ioType)); String pick = ioType == 101 ? "N":"Y"; // 生成工作档 WrkMast wrkMast = new WrkMast(); @@ -279,7 +280,7 @@ wrkMast.setStaNo(staDesc.getStnNo()); wrkMast.setSourceLocNo(dto.getLocNo()); wrkMast.setFullPlt("Y"); wrkMast.setPicking("N"); wrkMast.setPicking(pick); wrkMast.setExitMk("N"); wrkMast.setEmptyMk("N"); wrkMast.setLinkMis("N"); @@ -906,7 +907,7 @@ } else if (wrkMast.getIoType() > 100 && wrkMast.getWrkSts() != 14) { locNo = wrkMast.getSourceLocNo(); // 出库 ===>> F.在库 if (wrkMast.getIoType() == 101) { if (wrkMast.getIoType() == 101 || wrkMast.getIoType() == 103) { locSts = "F"; // 空板出库 ===>> D.空桶/空栈板 } else if (wrkMast.getIoType() == 110) { src/main/java/com/zy/asrs/service/impl/WrkDetlServiceImpl.java
@@ -57,6 +57,11 @@ } @Override public WrkDetl selectSingleByWrkNo(Integer wrkNo) { return this.baseMapper.selectSingleByWrkNo(wrkNo); } @Override public boolean updateAnfme(Double anfme, Integer wrkNo, String matnr, String batch) { if (anfme <= 0) { return this.baseMapper.deleteItem(wrkNo, matnr, batch) > 0; @@ -84,4 +89,9 @@ public List<WrkDetl> selectAndLogByOrderNoGroupByMatnrOfSum(String orderNo) { return this.baseMapper.selectAndLogByOrderNoGroupByMatnrOfSum(orderNo); } @Override public boolean updateIoTime(Integer workNo, Date ioTime) { return this.baseMapper.updateIoTime(workNo, ioTime) > 0; } } src/main/java/com/zy/common/service/CommonService.java
@@ -597,6 +597,157 @@ return startupDto; } public StartupDto getLocNoRunPick(Integer whsType, Integer staDescId, Integer sourceStaNo, String matnr, String batch, String grade, Integer moveCrnNo, LocTypeDto locTypeDto, int times) { int crnNo = 1;//小车编号备用 RowLastno rowLastno = rowLastnoService.selectById(4); LocMast locMast = null; // 目标库位 StartupDto startupDto = new StartupDto(); int curRow = rowLastno.getCurrentRow(); int sRow = rowLastno.getsRow(); int eRow = rowLastno.geteRow(); int nearRow = 8;//特殊单排 int orbit = 7;//轨道 // 相似工作档案 --- 同天同规格物料 if (!Cools.isEmpty(matnr) && (staDescId == 1 || staDescId == 11 || staDescId == 111) ) { //查询相似工作档案 List<WrkMast> wrkMasts = wrkMastService.selectWrkMastWrkDetlMatnrBatch(1, matnr, batch,null, crnNo); for (WrkMast wrkMast:wrkMasts){ if (Cools.isEmpty(wrkMast.getLocNo())){ continue; } //目标排为轨道外排 if (Utils.getRow(wrkMast.getLocNo()) == orbit || Utils.getRow(wrkMast.getLocNo()) == nearRow){ continue; } //查找此库位的浅库位是否为空 int value = Integer.valueOf(wrkMast.getLocNo().substring(0, 2)) + 1; String loc="0"+value+wrkMast.getLocNo().substring(2); LocMast locMast1=locMastService.selectOne(new EntityWrapper<LocMast>() .eq("loc_no",loc) .eq("loc_sts","O") .eq("loc_type1", locTypeDto.getLocType1()) ); if(Cools.isEmpty(locMast1)){ continue; } locMast=locMast1; break; } } // 靠近摆放规则 --- 同天同规格物料 if (Cools.isEmpty(locMast)) { List<LocDetl> locNos = locDetlService.getSameDetlToday(matnr, batch,sRow, eRow); for (LocDetl locNo : locNos) { //目标排为最外层排 if (Utils.getRow(locNo.getLocNo()) == nearRow || Utils.getRow(locNo.getLocNo()) == orbit){ continue; } LocMast locMast2=locMastService.selectOne(new EntityWrapper<LocMast>() .eq("loc_no",locNo.getLocNo()) .eq("loc_sts","F")); if(Cools.isEmpty(locMast2)){ continue; } int value = Integer.valueOf(locNo.getLocNo().substring(0, 2)) + 1; String loc="0"+value+locNo.getLocNo().substring(2); LocMast locMast1=locMastService.selectOne(new EntityWrapper<LocMast>() .eq("loc_no",loc) .eq("loc_sts","O") .eq("loc_type1", locTypeDto.getLocType1()) ); if(Cools.isEmpty(locMast1)){ continue; } locMast=locMast1; break; } } // 靠近摆放规则 --- 空托 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) { if (Utils.isShallowLoc(slaveProperties, loc.getLocNo())) { continue; } String shallowLocNo = Utils.getShallowLoc(slaveProperties, loc.getLocNo()); // 检测目标库位是否为空库位 LocMast shallowLoc = locMastService.selectById(shallowLocNo); if (shallowLoc != null && shallowLoc.getLocSts().equals("O")) { if (shallowLoc.getLocType1()<locTypeDto.getLocType1()){ continue; } if (basCrnpService.checkSiteError(shallowLoc.getCrnNo(), true)) { locMast = shallowLoc; crnNo = locMast.getCrnNo(); break; } } } } } // 获取目标站 Wrapper<StaDesc> wrapper = new EntityWrapper<StaDesc>() .eq("type_no", staDescId) .eq("stn_no", sourceStaNo) .eq("crn_no", 1); StaDesc staDesc = staDescService.selectOne(wrapper); if (Cools.isEmpty(staDesc)) { log.error("type_no={},stn_no={},crn_no={}", staDescId, sourceStaNo, crnNo); throw new CoolException("入库路径不存在"); } BasDevp staNo = basDevpService.selectById(staDesc.getStnNo()); if (!staNo.getAutoing().equals("Y")) { throw new CoolException("目标站"+staDesc.getCrnStn()+"不可用"); } // 如果没有相近物料,则按规则轮询货架 if (null == locMast) { LocMast locMast1 = new LocMast(); if(times != 0){ locMast1=locMastService.selectOne(new EntityWrapper<LocMast>() .eq("row1", 1) .eq("loc_sts","O") .eq("loc_type1", locTypeDto.getLocType1()) .orderBy("lev1,bay1 ASC")); } else { locMast1=locMastService.selectOne(new EntityWrapper<LocMast>() .eq("row1", 8) .eq("loc_sts","O") .eq("loc_type1", locTypeDto.getLocType1()) .orderBy("lev1,bay1 ASC")); } if(!Cools.isEmpty(locMast1)){ locMast=locMast1; } } // 更新库位排号 rowLastno.setCurrentRow(curRow); rowLastnoService.updateById(rowLastno); // 2.库位当前所属尺寸无空库位时,调整尺寸参数,向上兼容检索库位 if (Cools.isEmpty(locMast)) { times = times - 1; if (times >= 0) { return getLocNoRun4(whsType,staDescId, sourceStaNo, matnr, batch, grade,moveCrnNo,locTypeDto,times); } log.error("系统没有空库位!!! 尺寸规格: {},", JSON.toJSONString(locTypeDto)); throw new CoolException("没有空库位"); } String locNo = locMast.getLocNo(); // 返回找到的库位 startupDto.setWorkNo(0); startupDto.setCrnNo(locMast.getCrnNo()); startupDto.setSourceStaNo(sourceStaNo); startupDto.setLocNo(locNo); return startupDto; } public StartupDto getLocNoRun5(Integer whsType, Integer staDescId, Integer sourceStaNo, String matnr, String batch, String grade, Integer moveCrnNo, LocTypeDto locTypeDto, int times) { if (Cools.isEmpty(matnr)) { //物料号 matnr = ""; src/main/java/com/zy/common/web/WcsController.java
@@ -10,6 +10,7 @@ import com.zy.asrs.entity.*; import com.zy.asrs.entity.param.EmptyPlateOutParam; import com.zy.asrs.entity.param.StatusParam; import com.zy.asrs.mapper.WrkMastMapper; import com.zy.asrs.service.*; import com.zy.common.CodeRes; import com.zy.common.model.LocTypeDto; @@ -57,6 +58,8 @@ private WorkService workService; @Autowired private ApiLogService apiLogService; @Autowired private WrkMastMapper wrkMastMapper; @Value("${wcs-slave.url}") private String url; @Value("${wcs-slave.loc}") @@ -76,7 +79,7 @@ if (param.getFromPort().equals("101")) { //有空板出库时禁止入库 int wrkCount = wrkMastService.selectCount(new EntityWrapper<WrkMast>().eq("io_type",110).eq("sta_no",100).notIn("wrk_sts",7)); int wrkCount = wrkMastService.selectCount(new EntityWrapper<WrkMast>().eq("io_type", 110).eq("sta_no", 100).notIn("wrk_sts", 7)); if(wrkCount > 0){ return Re.error("有空板出库到100站时时禁止入库"); } @@ -97,15 +100,15 @@ if (countLoc > 0 || countWrk > 0) { return Re.error(CodeRes.EXIST_500); } }else { } else { //有满板出库时禁止空板入库 int wrkCount = wrkMastService.selectCount(new EntityWrapper<WrkMast>().eq("sta_no",100).andNew().eq("io_type",101).or().eq("io_type",110)); if(wrkCount > 0){ int wrkCount = wrkMastService.selectCount(new EntityWrapper<WrkMast>().eq("sta_no", 100).andNew().eq("io_type", 101).or().eq("io_type", 110)); if (wrkCount > 0) { return Re.error("有满板出库时禁止空板入库"); } int countLoc = wrkMastService.selectCount(new EntityWrapper<WrkMast>().eq("io_type", 10)); if (countLoc > 0 ) { if (countLoc > 0) { return Re.error("已有空板入库任务禁止在入空板"); } } @@ -195,7 +198,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(1, devpNo, matnrs.get(0), batchs.get(0), null, locTypeDto); if(dto == null){ if (dto == null) { throw new CoolException("没有检索到空库位"); } int workNo = dto.getWorkNo(); @@ -325,14 +328,14 @@ @ResponseBody public Re status(@RequestBody StatusParam statusParam) { WrkMast wrkMast = wrkMastService.selectOne(new EntityWrapper<WrkMast>().eq("wrk_no", statusParam.getTaskId())); if(Cools.isEmpty(wrkMast)&&statusParam.getTaskStatus()!=8){ return Re.error("没有找到:"+statusParam.getTaskId()+"这条任务"); }else if(Cools.isEmpty(wrkMast)&&statusParam.getTaskStatus()==8){ if (Cools.isEmpty(wrkMast) && statusParam.getTaskStatus() != 8) { return Re.error("没有找到:" + statusParam.getTaskId() + "这条任务"); } else if (Cools.isEmpty(wrkMast) && statusParam.getTaskStatus() == 8) { return Re.ok(); }else if(!Cools.isEmpty(wrkMast)&&statusParam.getTaskStatus()==8&&wrkMast.getIoType()==110){ } else if (!Cools.isEmpty(wrkMast) && statusParam.getTaskStatus() == 8 && wrkMast.getIoType() == 110) { return Re.ok(); } /** /* * 任务状态 * 执行过程中 * 的状态。 0- 已 接 @@ -341,41 +344,54 @@ * 任务中断,4-放货 * 完成,8-任务结束 */ if (statusParam.getTaskStatus()==0){ if (statusParam.getTaskStatus() == 0) { //拣料和盘点再入库判断 if((wrkMast.getIoType() == 103 || wrkMast.getIoType() == 107) && wrkMast.getWrkSts() == 14){ if ((wrkMast.getIoType() == 103 || wrkMast.getIoType() == 107) && wrkMast.getWrkSts() == 14) { // LocDetl locDetl = locDetlService.selectItemByLocNo(wrkMast.getSourceLocNo()); // List<WrkDetl> wrkDetl = wrkDetlService.selectByWrkNo(wrkMast.getWrkNo()); String sourcecLocNo = wrkMast.getSourceLocNo(); // // 获取后两位的层数 // String layerStr = sourcecLocNo.substring(sourcecLocNo.length() - 2); // int layer = Integer.parseInt(layerStr); // // 判断层数 // Short locType1 = (short) ((layer == 1) ? 1 : 2); // LocTypeDto locTypeDto = new LocTypeDto(); // locTypeDto.setLocType1(locType1); // StartupDto dto = commonService.getLocNoRunPick(4, 1, 101, wrkDetl.get(0).getMatnr(), wrkDetl.get(0).getBatch(), null, 4, locTypeDto, 2); Date now = new Date(); wrkMast.setIoTime(now); wrkMast.setIoType(wrkMast.getIoType() - 50); // 入出库类型: 103->53,104->54,107->57 wrkMast.setWrkSts(1L);//1.已接收 wrkMast.setSourceStaNo(101); // 源站 wrkMast.setStaNo(null); // 目标站 wrkMast.setLocNo(wrkMast.getSourceLocNo()); // 目标库位 = 出库时的源库位 wrkMast.setSourceLocNo(""); // 源库位清空 wrkMast.setLocNo(sourcecLocNo); // 目标库位 wrkMast.setSourceLocNo(""); wrkMast.setModiTime(now); wrkDetlService.updateIoTime(wrkMast.getWrkNo(), now); // 修改库位状态 Q.拣料/盘点/并板再入库 LocMast locMast = locMastService.selectById(wrkMast.getLocNo()); locMast.setLocSts("Q"); locMast.setModiTime(new Date()); if (!locMastService.updateById(locMast)) { LocMast locMast2 = locMastService.selectById(sourcecLocNo); locMast2.setLocSts("Q"); locMast2.setModiTime(new Date()); if (!locMastService.updateById(locMast2)) { throw new CoolException("修改库位状态失败"); } }else{ } else { wrkMast.setWrkSts(1L);//1.已接收 } }else if (statusParam.getTaskStatus()==1){ } else if (statusParam.getTaskStatus() == 1) { wrkMast.setWrkSts(2L);//2.任务开始 }else if (statusParam.getTaskStatus()==2){ } else if (statusParam.getTaskStatus() == 2) { wrkMast.setWrkSts(3L);//3.取货完成 }else if (statusParam.getTaskStatus()==3){ } else if (statusParam.getTaskStatus() == 3) { wrkMast.setWrkSts(6L);//6.任务中断 } else if (statusParam.getTaskStatus()==4 || statusParam.getTaskStatus()==8){ if(wrkMast.getIoType()==1 || wrkMast.getIoType() == 10 || wrkMast.getIoType() == 11 || wrkMast.getIoType() == 53 ||wrkMast.getIoType() == 57){ } else if (statusParam.getTaskStatus() == 4 || statusParam.getTaskStatus() == 8) { if (wrkMast.getIoType() == 1 || wrkMast.getIoType() == 10 || wrkMast.getIoType() == 11 || wrkMast.getIoType() == 53 || wrkMast.getIoType() == 57) { wrkMast.setWrkSts(4L);//4.入库完成 }else if (wrkMast.getIoType()==103 || wrkMast.getIoType()==107){ } else if (wrkMast.getIoType() == 103 || wrkMast.getIoType() == 107) { wrkMast.setWrkSts(14L);//14.已出库未确认 }else if (wrkMast.getIoType()==101 || wrkMast.getIoType()==110){ } else if (wrkMast.getIoType() == 101 || wrkMast.getIoType() == 110) { wrkMast.setWrkSts(7L);//7.出库完成 } } @@ -384,22 +400,22 @@ } @GetMapping("loc") public void loc(){ List<LocMast> locMasts=locMastService.selectList(new EntityWrapper<LocMast>()); List<HashMap<String,Object>> mapList=new ArrayList<>(); public void loc() { List<LocMast> locMasts = locMastService.selectList(new EntityWrapper<LocMast>()); List<HashMap<String, Object>> mapList = new ArrayList<>(); for (LocMast locMast : locMasts) { if (locMast.getLev1()!=4){ HashMap<String,Object> map=new HashMap<>(); map.put("warehouse","wzzy"); map.put("posiX",locMast.getRow1()); map.put("posiY",locMast.getBay1()); map.put("posiZ",locMast.getLev1()); map.put("cargoNo",locMast.getLocNo()); map.put("type","0"); if (locMast.getLev1() != 4) { HashMap<String, Object> map = new HashMap<>(); map.put("warehouse", "ddth"); map.put("posiX", locMast.getRow1()); map.put("posiY", locMast.getBay1()); map.put("posiZ", locMast.getLev1()); map.put("cargoNo", locMast.getLocNo()); map.put("type", "0"); mapList.add(map); } } if(mapList.size()>0){ if (mapList.size() > 0) { String response = ""; boolean success = false; try { @@ -413,7 +429,7 @@ if (jsonObject.getInteger("returnStatus").equals(0)) { success = true; } else { log.error("wms同步wcs库位失败!!!url:{};request:{};response:{}", url+"/"+loc, JSON.toJSONString(mapList), response); log.error("wms同步wcs库位失败!!!url:{};request:{};response:{}", url + "/" + loc, JSON.toJSONString(mapList), response); throw new CoolException("wms下发任务给wcs失败"); } } catch (Exception e) { @@ -425,14 +441,16 @@ // 保存接口日志 apiLogService.save( "wms同步wcs库位失败", url+"/"+loc, url + "/" + loc, null, "127.0.0.1", JSON.toJSONString(mapList), response, success ); } catch (Exception e) { log.error("", e); } } catch (Exception e) { log.error("", e); } } } } src/main/resources/mapper/LocDetlMapper.xml
@@ -66,6 +66,13 @@ <include refid="batchSeq"></include> </select> <select id="selectItemByLocNo" resultMap="BaseResultMap"> select top 1 * from asr_loc_detl where 1=1 and loc_no = #{locNo} </select> <delete id="deleteItem"> delete from asr_loc_detl where 1=1 src/main/resources/mapper/WrkDetlMapper.xml
@@ -124,4 +124,11 @@ group by awdl.wrk_no, awdl.io_time, awdl.matnr ,awdl.zpallet,awdl.specs,awdl.maktx </select> <update id="updateIoTime"> update asr_wrk_detl set io_time = #{ioTime} where 1=1 and wrk_no = #{workNo} </update> </mapper> src/main/webapp/views/login.html
@@ -56,8 +56,8 @@ <img src="../static/image/logo.png" alt="" style="width: 20%"> </div> <div class="p-sketch-outline"> <h2 class="p-sketch-outline__title">Automatic Storage and Retrieval System</h2> <p class="p-sketch-outline__date">posted: 2018.01.01 / update: 2022.09.21 <!-- <h2 class="p-sketch-outline__title">Automatic Storage and Retrieval System</h2>--> <!-- <p class="p-sketch-outline__date">posted: 2018.01.01 / update: 2022.09.21--> </p> <p class="p-sketch-outline__description">wms made with various simple objects.</p> </div>