| | |
| | | import javax.servlet.http.HttpServletRequest; |
| | | import java.text.SimpleDateFormat; |
| | | import java.util.*; |
| | | import java.util.concurrent.TimeUnit; |
| | | |
| | | /** |
| | | * Created by vincent on 2022/4/8 |
| | |
| | | private WaitPakinService waitPakinService; |
| | | @Autowired |
| | | private WrkDetlService wrkDetlService; |
| | | @Autowired |
| | | private WrkDetlLogService wrkDetlLogService; |
| | | @Autowired |
| | | private WrkMastService wrkMastService; |
| | | @Autowired |
| | |
| | | HttpServletRequest request) { |
| | | auth(appkey, param, request); |
| | | return R.ok().add(openService.pakinOrderComplete(param)); |
| | | } |
| | | |
| | | /** |
| | | * 托盘入库历史记录重报ERP |
| | | */ |
| | | @PostMapping("/order/pakin/erp/report/v1") |
| | | // @AppAuth(memo = "入库历史重报ERP") |
| | | public synchronized R reportPakinHistoryToErp(@RequestBody(required = false) List<String> barcodes) { |
| | | // auth(appkey, barcodes, request); |
| | | if (Cools.isEmpty(barcodes)) { |
| | | return R.parse(BaseRes.PARAM); |
| | | } |
| | | try { |
| | | return openService.reportPakinHistoryToErp(barcodes); |
| | | } catch (Exception e) { |
| | | return R.error(e.getMessage()); |
| | | } |
| | | } |
| | | |
| | | |
| | |
| | | } |
| | | |
| | | /** |
| | | * 组托信息下发 |
| | | * return |
| | | * 7.3 组托信息下发 |
| | | */ |
| | | @PostMapping("/comb/auth") |
| | | public synchronized R comb(@RequestBody ArrayList<MesToCombParam> param, HttpServletRequest request) { |
| | |
| | | } |
| | | |
| | | /** |
| | | * 出库通知单 |
| | | * 7.11 出库通知单(传递有序无序规则) |
| | | */ |
| | | |
| | | @PostMapping("/outOrder") |
| | | public synchronized R outOrder(@RequestBody ArrayList<OutTaskParam> params, HttpServletRequest request) { |
| | | if (Cools.isEmpty(params)) { |
| | |
| | | } |
| | | log.info("[outOrder] cache: {}", JSON.toJSONString(params)); |
| | | request.setAttribute("cache", params); |
| | | Set<String> orderIds = new LinkedHashSet<>(); |
| | | Map<String, List<OutTaskParam>> linesByBatch = new LinkedHashMap<>(); |
| | | for (OutTaskParam outTaskParam : params) { |
| | | if (Cools.isEmpty(outTaskParam) || Cools.isEmpty(outTaskParam.getOrderId())) { |
| | | return R.error("出库单号不能为空"); |
| | | } |
| | | orderIds.add(outTaskParam.getOrderId()); |
| | | if (Cools.isEmpty(outTaskParam.getBatchSeq())) { |
| | | outTaskParam.setBatchSeq(outTaskParam.getOrderId()); |
| | | } |
| | | if (Cools.isEmpty(outTaskParam.getStationId())) { |
| | | return R.error("托盘「" + outTaskParam.getPalletId() + "」出库口编码不能为空"); |
| | | } |
| | | linesByBatch.computeIfAbsent(outTaskParam.getBatchSeq(), k -> new ArrayList<>()).add(outTaskParam); |
| | | } |
| | | |
| | | Map<String, List<OutTaskParam>> linesByOrder = new LinkedHashMap<>(); |
| | | for (OutTaskParam outTaskParam : params) { |
| | | linesByOrder.computeIfAbsent(outTaskParam.getOrderId(), k -> new ArrayList<>()).add(outTaskParam); |
| | | } |
| | | for (Map.Entry<String, List<OutTaskParam>> entry : linesByOrder.entrySet()) { |
| | | String oid = entry.getKey(); |
| | | for (Map.Entry<String, List<OutTaskParam>> entry : linesByBatch.entrySet()) { |
| | | List<OutTaskParam> lines = entry.getValue(); |
| | | List<Integer> seqs = new ArrayList<>(lines.size()); |
| | | OutTaskParam head = lines.get(0); |
| | | String oid = head.getOrderId(); |
| | | String batchSeq = head.getBatchSeq(); |
| | | boolean hasZero = false; |
| | | boolean hasPositive = false; |
| | | List<Integer> orderedSeqs = new ArrayList<>(lines.size()); |
| | | for (OutTaskParam line : lines) { |
| | | if (line.getSeq() == null) { |
| | | return R.error("出库单「" + oid + "」序号不能为空"); |
| | | return R.error("出库单「" + oid + "」批次「" + batchSeq + "」序号不能为空"); |
| | | } |
| | | seqs.add(line.getSeq()); |
| | | if (line.getSeq() < 0) { |
| | | return R.error("出库单「" + oid + "」批次「" + batchSeq + "」序号不能小于0"); |
| | | } |
| | | if (line.getSeq() == 0) { |
| | | hasZero = true; |
| | | } else { |
| | | hasPositive = true; |
| | | orderedSeqs.add(line.getSeq()); |
| | | } |
| | | } |
| | | Collections.sort(seqs); |
| | | for (int i = 0; i < seqs.size(); i++) { |
| | | if (!String.valueOf(seqs.get(i)).equals(String.valueOf(i + 1))) { |
| | | return R.error("出库单「" + oid + "」序号不连贯"); |
| | | if (hasZero && hasPositive) { |
| | | return R.error("出库单「" + oid + "」批次「" + batchSeq + "」序号不能混用无序和有序"); |
| | | } |
| | | if (!hasZero) { |
| | | Collections.sort(orderedSeqs); |
| | | for (int i = 0; i < orderedSeqs.size(); i++) { |
| | | if (!Objects.equals(orderedSeqs.get(i), i + 1)) { |
| | | return R.error("出库单「" + oid + "」批次「" + batchSeq + "」序号不连贯"); |
| | | } |
| | | } |
| | | } |
| | | } |
| | |
| | | // } |
| | | // } |
| | | |
| | | List<OutTaskParam> errorOutOrders = Lists.newArrayList(); |
| | | List<OutTaskParam> validOutOrders = Lists.newArrayList(); |
| | | List<OutTaskParam> missingStock = Lists.newArrayList(); |
| | | List<OutTaskParam> missingLoc = Lists.newArrayList(); |
| | | for (OutTaskParam outTaskParam : params) { |
| | | // TODO:待測試,校驗庫存信息,不存在則返回 |
| | | int countLoc = locDetlService.selectCount(new EntityWrapper<LocDetl>().eq("zpallet", outTaskParam.getPalletId())); |
| | | if (countLoc == 0){ |
| | | errorOutOrders.add(outTaskParam); |
| | | if (countLoc == 0) { |
| | | missingStock.add(outTaskParam); |
| | | continue; |
| | | } |
| | | validOutOrders.add(outTaskParam); |
| | | } |
| | | for (OutTaskParam outTaskParam : validOutOrders) { |
| | | LocMast locMast = locMastService.selectOne(new EntityWrapper<LocMast>().eq("loc_sts", "F").eq("barcode", outTaskParam.getPalletId())); |
| | | if (locMast == null) { |
| | | throw new CoolException("没有找到托盘码=" + outTaskParam.getPalletId() + "对应的库位"); |
| | | missingLoc.add(outTaskParam); |
| | | } |
| | | } |
| | | |
| | | for (OutTaskParam outTaskParam : validOutOrders) { |
| | | R r = openService.outOrder(outTaskParam,validOutOrders.size()); |
| | | if (!r.get("code").equals(200)){ |
| | | return r; |
| | | if (!missingStock.isEmpty()) { |
| | | List<String> missingPalletIds = new ArrayList<>(missingStock.size()); |
| | | for (OutTaskParam p : missingStock) { |
| | | String pid = p.getPalletId(); |
| | | missingPalletIds.add(Cools.isEmpty(pid) ? "(空)" : pid); |
| | | } |
| | | return R.error("库存中不存在该托盘:" + String.join(",", missingPalletIds)).add(missingStock); |
| | | } |
| | | if(errorOutOrders.size() > 0) { |
| | | return R.error("库存中不存在该托盘").add(errorOutOrders); |
| | | if (!missingLoc.isEmpty()) { |
| | | List<String> badPalletIds = new ArrayList<>(missingLoc.size()); |
| | | for (OutTaskParam p : missingLoc) { |
| | | String pid = p.getPalletId(); |
| | | badPalletIds.add(Cools.isEmpty(pid) ? "(空)" : pid); |
| | | } |
| | | return R.error("没有找到托盘码对应库位:" + String.join(",", badPalletIds)).add(missingLoc); |
| | | } |
| | | |
| | | return R.ok(); |
| | | return openService.outOrderBatch(params); |
| | | } |
| | | |
| | | /** |
| | | * 7.9 出库异常变动上报 |
| | | */ |
| | | @PostMapping("/order/pakout/abnormal/report/v1") |
| | | public synchronized R outOrderAbnormalReport(@RequestBody OutOrderAbnormalReportParam param, HttpServletRequest request) { |
| | | if (request != null) { |
| | | log.info("[outOrderAbnormalReport] cache: {}", param == null ? "null" : JSON.toJSONString(param)); |
| | | request.setAttribute("cache", param); |
| | | } |
| | | if (Cools.isEmpty(param) || Cools.isEmpty(param.getPalletId())) { |
| | | return R.error("palletId不能为空"); |
| | | } |
| | | return openService.outOrderAbnormalReport(param); |
| | | } |
| | | |
| | | /** |
| | | * 7.10 出库异常变动处理 |
| | | */ |
| | | @PostMapping("/order/pakout/abnormal/handle/v1") |
| | | public synchronized R outOrderAbnormalHandle(@RequestBody OutOrderAbnormalHandleParam param, HttpServletRequest request) { |
| | | if (request != null) { |
| | | log.info("[outOrderAbnormalHandle] cache: {}", param == null ? "null" : JSON.toJSONString(param)); |
| | | request.setAttribute("cache", param); |
| | | } |
| | | if (Cools.isEmpty(param) || Cools.isEmpty(param.getPalletId())) { |
| | | return R.error("palletId不能为空"); |
| | | } |
| | | return openService.outOrderAbnormalHandle(param); |
| | | } |
| | | |
| | | /** |
| | |
| | | return R.error("orderNo is empty"); |
| | | } |
| | | return openService.pakoutOrderPause(param); |
| | | } |
| | | |
| | | private String buildOutOrderBatchKey(OutTaskParam param) { |
| | | return param.getOrderId() + "#" + param.getBatchSeq(); |
| | | } |
| | | |
| | | |
| | |
| | | } |
| | | } |
| | | AxisBean inqty = new AxisBean(); |
| | | inqty.setName("入库数量"); |
| | | inqty.setName("入库托盘数"); |
| | | Integer[] array1 = new Integer[data1.size()]; |
| | | inqty.setData(data1.toArray(array1)); |
| | | list.add(inqty); |
| | | AxisBean outqty = new AxisBean(); |
| | | outqty.setName("出库数量"); |
| | | outqty.setName("出库TU"); |
| | | Integer[] array2 = new Integer[data2.size()]; |
| | | outqty.setData(data2.toArray(array2)); |
| | | list.add(outqty); |
| | | } |
| | | map.put("rows",list); |
| | | return R.ok(map); |
| | | } |
| | | |
| | | /** |
| | | * 入出库按小时折线:横轴为「当前整点起向前共 12 小时」滚动窗口,与库表 ymd(yyyy-MM-dd HH)对齐 |
| | | */ |
| | | @GetMapping("/line/charts/hourly") |
| | | public R locIoLineChartsHourly() { |
| | | Map<String, Object> map = new HashMap<>(); |
| | | List<AxisBean> list = new ArrayList<>(); |
| | | |
| | | List<WorkChartAxis> listChart = reportQueryMapper.getChartAxisHourly(); |
| | | if (listChart == null) { |
| | | listChart = Collections.emptyList(); |
| | | } |
| | | |
| | | ArrayList<Integer> data1 = new ArrayList<>(); |
| | | ArrayList<Integer> data2 = new ArrayList<>(); |
| | | List<String> categories = new ArrayList<>(); |
| | | |
| | | final int n = 12; |
| | | SimpleDateFormat sfKey = new SimpleDateFormat("yyyy-MM-dd HH"); |
| | | Calendar calendar = Calendar.getInstance(); |
| | | calendar.set(Calendar.MINUTE, 0); |
| | | calendar.set(Calendar.SECOND, 0); |
| | | calendar.set(Calendar.MILLISECOND, 0); |
| | | calendar.add(Calendar.HOUR_OF_DAY, -(n - 1)); |
| | | |
| | | for (int i = 0; i < n; i++) { |
| | | String key = sfKey.format(calendar.getTime()); |
| | | categories.add(String.valueOf(calendar.get(Calendar.HOUR_OF_DAY))); |
| | | |
| | | int inV = 0; |
| | | int outV = 0; |
| | | for (WorkChartAxis w : listChart) { |
| | | if (w.getYmd() != null && key.equals(w.getYmd().trim())) { |
| | | inV = w.getInqty(); |
| | | outV = w.getOutqty(); |
| | | break; |
| | | } |
| | | } |
| | | data1.add(inV); |
| | | data2.add(outV); |
| | | calendar.add(Calendar.HOUR_OF_DAY, 1); |
| | | } |
| | | |
| | | AxisBean inqty = new AxisBean(); |
| | | inqty.setName("入库托盘数"); |
| | | Integer[] array1 = new Integer[data1.size()]; |
| | | inqty.setData(data1.toArray(array1)); |
| | | list.add(inqty); |
| | | |
| | | AxisBean outqty = new AxisBean(); |
| | | outqty.setName("出库TU"); |
| | | Integer[] array2 = new Integer[data2.size()]; |
| | | outqty.setData(data2.toArray(array2)); |
| | | list.add(outqty); |
| | | |
| | | map.put("categories", categories); |
| | | map.put("rows", list); |
| | | return R.ok(map); |
| | | } |
| | | |
| | |
| | | } |
| | | |
| | | List<WrkDetl> wrkDetls = wrkDetlService.selectByWrkNo(Integer.valueOf(param.getTaskNo())); |
| | | String costTime = resolveCostTime(wrkMast, wrkDetls); |
| | | |
| | | HashMap<String, Object> map = new HashMap<>(); |
| | | map.put("taskNo", param.getTaskNo()); |
| | | map.put("ioType", wrkMast.getIoType()); |
| | | map.put("costTime", costTime); |
| | | map.put("wrkDetls", wrkDetls); |
| | | |
| | | return R.ok().add(map); |
| | | } |
| | | |
| | | private String resolveCostTime(WrkMast wrkMast, List<WrkDetl> wrkDetls) { |
| | | Date createTime = resolveOrderCreateTime(resolveOrderNo(wrkMast, wrkDetls)); |
| | | if (createTime == null) { |
| | | createTime = resolveTaskCreateTime(wrkMast); |
| | | } |
| | | if (createTime == null) { |
| | | return "0"; |
| | | } |
| | | long minutes = TimeUnit.MILLISECONDS.toMinutes(System.currentTimeMillis() - createTime.getTime()); |
| | | if (minutes < 0L) { |
| | | minutes = 0L; |
| | | } |
| | | return String.valueOf(minutes); |
| | | } |
| | | |
| | | private String resolveOrderNo(WrkMast wrkMast, List<WrkDetl> wrkDetls) { |
| | | if (wrkMast != null && !Cools.isEmpty(wrkMast.getUserNo())) { |
| | | return wrkMast.getUserNo(); |
| | | } |
| | | if (Cools.isEmpty(wrkDetls)) { |
| | | return null; |
| | | } |
| | | for (WrkDetl wrkDetl : wrkDetls) { |
| | | if (wrkDetl != null && !Cools.isEmpty(wrkDetl.getOrderNo())) { |
| | | return wrkDetl.getOrderNo(); |
| | | } |
| | | } |
| | | return null; |
| | | } |
| | | |
| | | private Date resolveOrderCreateTime(String orderNo) { |
| | | if (Cools.isEmpty(orderNo)) { |
| | | return null; |
| | | } |
| | | |
| | | Date historyCreateTime = minDate( |
| | | minCreateTime(wrkMastLogService.selectList(new EntityWrapper<WrkMastLog>().eq("user_no", orderNo))), |
| | | minCreateTime(wrkDetlLogService.selectList(new EntityWrapper<WrkDetlLog>().eq("order_no", orderNo))) |
| | | ); |
| | | if (historyCreateTime != null) { |
| | | return historyCreateTime; |
| | | } |
| | | |
| | | return minDate( |
| | | minCreateTime(wrkMastService.selectList(new EntityWrapper<WrkMast>().eq("user_no", orderNo))), |
| | | minCreateTime(wrkDetlService.selectList(new EntityWrapper<WrkDetl>().eq("order_no", orderNo))) |
| | | ); |
| | | } |
| | | |
| | | private Date minDate(Date first, Date second) { |
| | | if (first == null) { |
| | | return second; |
| | | } |
| | | if (second == null) { |
| | | return first; |
| | | } |
| | | return first.before(second) ? first : second; |
| | | } |
| | | |
| | | private Date resolveTaskCreateTime(WrkMast wrkMast) { |
| | | if (wrkMast == null) { |
| | | return null; |
| | | } |
| | | return firstDate(wrkMast.getAppeTime(), wrkMast.getIoTime(), wrkMast.getModiTime()); |
| | | } |
| | | |
| | | private Date firstDate(Date... dates) { |
| | | if (dates == null || dates.length == 0) { |
| | | return null; |
| | | } |
| | | for (Date date : dates) { |
| | | if (date != null) { |
| | | return date; |
| | | } |
| | | } |
| | | return null; |
| | | } |
| | | |
| | | private Date minCreateTime(List<?> list) { |
| | | if (Cools.isEmpty(list)) { |
| | | return null; |
| | | } |
| | | Date min = null; |
| | | for (Object item : list) { |
| | | Date createTime = resolveCreateTime(item); |
| | | if (createTime == null) { |
| | | continue; |
| | | } |
| | | if (min == null || createTime.before(min)) { |
| | | min = createTime; |
| | | } |
| | | } |
| | | return min; |
| | | } |
| | | |
| | | private Date resolveCreateTime(Object item) { |
| | | if (item instanceof WrkMast) { |
| | | WrkMast wrkMast = (WrkMast) item; |
| | | return firstDate(wrkMast.getAppeTime(), wrkMast.getIoTime(), wrkMast.getModiTime()); |
| | | } |
| | | if (item instanceof WrkMastLog) { |
| | | WrkMastLog wrkMastLog = (WrkMastLog) item; |
| | | return firstDate(wrkMastLog.getAppeTime(), wrkMastLog.getIoTime(), wrkMastLog.getModiTime()); |
| | | } |
| | | if (item instanceof WrkDetl) { |
| | | WrkDetl wrkDetl = (WrkDetl) item; |
| | | return firstDate(wrkDetl.getAppeTime(), wrkDetl.getIoTime(), wrkDetl.getModiTime()); |
| | | } |
| | | if (item instanceof WrkDetlLog) { |
| | | WrkDetlLog wrkDetlLog = (WrkDetlLog) item; |
| | | return firstDate(wrkDetlLog.getAppeTime(), wrkDetlLog.getIoTime(), wrkDetlLog.getModiTime()); |
| | | } |
| | | return null; |
| | | } |
| | | } |
| | | |