| | |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | import java.util.HashMap; |
| | | import java.util.HashSet; |
| | | import java.util.LinkedHashMap; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | | import java.util.Objects; |
| | | import java.util.Set; |
| | | import java.util.stream.Collectors; |
| | | |
| | | import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception; |
| | | import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.*; |
| | |
| | | private CrmContractApi contractApi; |
| | | @Resource |
| | | private ErpAccountService accountService; |
| | | |
| | | @Resource |
| | | private cn.iocoder.yudao.module.mes.api.wms.MesWmStockApi mesWmStockApi; |
| | | |
| | | @Resource |
| | | private AdminUserApi adminUserApi; |
| | |
| | | Long mpsId = mpsApi.createMps(createReqDTO); |
| | | log.info("[createMpsForSaleOrderItem] MPS å建æåï¼mpsId={}, saleOrderItemId={}", mpsId, item.getId()); |
| | | return mpsId; |
| | | } |
| | | |
| | | // ==================== ä»éå®è®¢åçæç产计åï¼ç产车é´è§è§ï¼ ==================== |
| | | |
| | | @Override |
| | | public List<cn.iocoder.yudao.module.erp.controller.admin.sale.vo.order.ErpSaleOrderPendingProductionRespVO> |
| | | getPendingProductionList() { |
| | | // 1. åå
¨é¨å·²å®¡æ ¸çéå®è®¢å |
| | | List<ErpSaleOrderDO> orders = saleOrderMapper.selectList( |
| | | new cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX<ErpSaleOrderDO>() |
| | | .eq(ErpSaleOrderDO::getStatus, ErpAuditStatus.APPROVE.getStatus()) |
| | | .orderByDesc(ErpSaleOrderDO::getId)); |
| | | if (CollUtil.isEmpty(orders)) { |
| | | return Collections.emptyList(); |
| | | } |
| | | Map<Long, ErpSaleOrderDO> orderMap = orders.stream() |
| | | .collect(Collectors.toMap(ErpSaleOrderDO::getId, o -> o, (a, b) -> a)); |
| | | |
| | | // 2. å订åæç» |
| | | List<ErpSaleOrderItemDO> items = saleOrderItemMapper.selectListByOrderIds(orderMap.keySet()); |
| | | if (CollUtil.isEmpty(items)) { |
| | | return Collections.emptyList(); |
| | | } |
| | | |
| | | // 3. å·²æææ MPS çæç»è¦æé¤ï¼é¿å
éå¤å®æç产 |
| | | Set<Long> plannedItemIds = new HashSet<>(); |
| | | List<Long> allItemIds = items.stream().map(ErpSaleOrderItemDO::getId).collect(Collectors.toList()); |
| | | try { |
| | | // 注æï¼è¯¥ API ç´æ¥è¿å Listï¼ä¸æ¯ CommonResult |
| | | List<cn.iocoder.yudao.module.mes.api.mps.dto.MesProMpsRespDTO> existMps = |
| | | mpsApi.getMpsListBySaleOrderItemIds(allItemIds); |
| | | if (CollUtil.isNotEmpty(existMps)) { |
| | | existMps.stream() |
| | | .filter(m -> ObjectUtil.notEqual(m.getStatus(), MPS_STATUS_CANCELED)) |
| | | .map(cn.iocoder.yudao.module.mes.api.mps.dto.MesProMpsRespDTO::getSaleOrderItemId) |
| | | .filter(Objects::nonNull) |
| | | .forEach(plannedItemIds::add); |
| | | } |
| | | } catch (Exception e) { |
| | | log.warn("[getPendingProductionList] æ¥è¯¢å·²æ MPS å¤±è´¥ï¼æå
¨é¨å¯å®æå¤ç", e); |
| | | } |
| | | |
| | | // 4. ç»è£
ï¼å¸¦åºå¯ç¨åºåä¸å»ºè®®ç产æ°é |
| | | List<cn.iocoder.yudao.module.erp.controller.admin.sale.vo.order.ErpSaleOrderPendingProductionRespVO> result |
| | | = new ArrayList<>(); |
| | | for (ErpSaleOrderItemDO item : items) { |
| | | if (plannedItemIds.contains(item.getId())) { |
| | | continue; |
| | | } |
| | | ErpSaleOrderDO order = orderMap.get(item.getOrderId()); |
| | | if (order == null) { |
| | | continue; |
| | | } |
| | | cn.iocoder.yudao.module.erp.controller.admin.sale.vo.order.ErpSaleOrderPendingProductionRespVO vo |
| | | = new cn.iocoder.yudao.module.erp.controller.admin.sale.vo.order.ErpSaleOrderPendingProductionRespVO(); |
| | | vo.setSaleOrderId(order.getId()); |
| | | vo.setSaleOrderNo(order.getNo()); |
| | | vo.setSaleOrderItemId(item.getId()); |
| | | vo.setCustomerId(order.getCustomerId()); |
| | | vo.setCustomerName(getCustomerName(order.getCustomerId())); |
| | | vo.setProductId(item.getProductId()); |
| | | // æç»è¡¨åªå productIdï¼äº§åç¼ç /åç§°/è§æ ¼ä» MDM å |
| | | try { |
| | | MdmItemRespDTO mdmItem = mdmItemApi.getItem(item.getProductId()).getCheckedData(); |
| | | if (mdmItem != null) { |
| | | vo.setProductCode(mdmItem.getCode()); |
| | | vo.setProductName(mdmItem.getName()); |
| | | vo.setProductSpecification(mdmItem.getSpecification()); |
| | | } |
| | | } catch (Exception e) { |
| | | log.warn("[getPendingProductionList] è·åç©æä¿¡æ¯å¤±è´¥ï¼productId={}", item.getProductId(), e); |
| | | } |
| | | vo.setOrderCount(item.getCount()); |
| | | vo.setOrderTime(order.getOrderTime()); |
| | | |
| | | // å½åå¯ç¨åºå |
| | | BigDecimal stock = BigDecimal.ZERO; |
| | | try { |
| | | BigDecimal qty = mesWmStockApi.getStockQuantity(item.getProductId()); |
| | | if (qty != null) { |
| | | stock = qty; |
| | | } |
| | | } catch (Exception e) { |
| | | log.warn("[getPendingProductionList] æ¥è¯¢åºå失败ï¼productId={}", item.getProductId(), e); |
| | | } |
| | | vo.setStockQuantity(stock); |
| | | |
| | | // 建议ç产æ°é = è®¢è´æ°é - å¯ç¨åºåï¼ä¸è¶³ 0 åå 0 |
| | | BigDecimal count = item.getCount() == null ? BigDecimal.ZERO : item.getCount(); |
| | | BigDecimal suggest = count.subtract(stock); |
| | | vo.setSuggestQuantity(suggest.compareTo(BigDecimal.ZERO) > 0 ? suggest : BigDecimal.ZERO); |
| | | |
| | | result.add(vo); |
| | | } |
| | | // æå»ºè®®ç产æ°ééåºï¼æ¥éç产çæåé¢ |
| | | result.sort((a, b) -> b.getSuggestQuantity().compareTo(a.getSuggestQuantity())); |
| | | return result; |
| | | } |
| | | |
| | | @Override |
| | | @Transactional(rollbackFor = Exception.class) |
| | | public int generateMpsFromSaleOrder( |
| | | cn.iocoder.yudao.module.erp.controller.admin.sale.vo.order.ErpSaleOrderGenerateMpsReqVO reqVO) { |
| | | if (reqVO.getItems() == null || reqVO.getItems().isEmpty()) { |
| | | return 0; |
| | | } |
| | | int success = 0; |
| | | for (cn.iocoder.yudao.module.erp.controller.admin.sale.vo.order.ErpSaleOrderGenerateMpsReqVO.Item reqItem |
| | | : reqVO.getItems()) { |
| | | ErpSaleOrderItemDO item = saleOrderItemMapper.selectById(reqItem.getSaleOrderItemId()); |
| | | if (item == null) { |
| | | log.warn("[generateMpsFromSaleOrder] éå®è®¢åæç»ä¸åå¨ï¼id={}", reqItem.getSaleOrderItemId()); |
| | | continue; |
| | | } |
| | | ErpSaleOrderDO order = saleOrderMapper.selectById(item.getOrderId()); |
| | | if (order == null || !ErpAuditStatus.APPROVE.getStatus().equals(order.getStatus())) { |
| | | log.warn("[generateMpsFromSaleOrder] éå®è®¢åæªå®¡æ ¸ï¼è·³è¿ï¼itemId={}", item.getId()); |
| | | continue; |
| | | } |
| | | // å¹çä¿æ¤ï¼å·²æææ MPS åè·³è¿ï¼é¿å
éå¤å®æ |
| | | try { |
| | | List<cn.iocoder.yudao.module.mes.api.mps.dto.MesProMpsRespDTO> existMps = |
| | | mpsApi.getMpsListBySaleOrderItemIds(Collections.singletonList(item.getId())); |
| | | if (CollUtil.isNotEmpty(existMps) |
| | | && existMps.stream().anyMatch(m -> ObjectUtil.notEqual(m.getStatus(), MPS_STATUS_CANCELED))) { |
| | | log.info("[generateMpsFromSaleOrder] æç»({}) å·²å卿æ MPSï¼è·³è¿", item.getId()); |
| | | continue; |
| | | } |
| | | } catch (Exception e) { |
| | | log.warn("[generateMpsFromSaleOrder] å¹çæ ¡éªå¤±è´¥ï¼ç»§ç»çæï¼itemId={}", item.getId(), e); |
| | | } |
| | | try { |
| | | createMpsForSaleOrderItemWithQuantity(order, item, reqItem.getQuantity()); |
| | | success++; |
| | | } catch (Exception e) { |
| | | log.error("[generateMpsFromSaleOrder] çæ MPS 失败ï¼itemId={}", item.getId(), e); |
| | | } |
| | | } |
| | | log.info("[generateMpsFromSaleOrder] å
±çæ MPS {} æ¡", success); |
| | | return success; |
| | | } |
| | | |
| | | /** |
| | | * ææå®æ°é为éå®è®¢åæç»å建 MPS |
| | | * |
| | | * ä¸ createMpsForSaleOrderItem çå·®å«ï¼æ°éç±è½¦é´èªè¡æå®ï¼éå¸¸æ¯ è®¢è´æ°é - å¯ç¨åºåï¼ï¼ |
| | | * è䏿¯ç´æ¥ç¨è®¢åæ°é |
| | | */ |
| | | private Long createMpsForSaleOrderItemWithQuantity(ErpSaleOrderDO saleOrder, ErpSaleOrderItemDO item, |
| | | BigDecimal quantity) { |
| | | String productName = null; |
| | | try { |
| | | MdmItemRespDTO mdmItem = mdmItemApi.getItem(item.getProductId()).getCheckedData(); |
| | | if (mdmItem != null) { |
| | | productName = mdmItem.getName(); |
| | | } |
| | | } catch (Exception e) { |
| | | log.warn("[createMpsForSaleOrderItemWithQuantity] è·åç©æä¿¡æ¯å¤±è´¥ï¼productId={}", item.getProductId(), e); |
| | | } |
| | | |
| | | MesProMpsCreateReqDTO createReqDTO = new MesProMpsCreateReqDTO(); |
| | | createReqDTO.setSaleOrderId(saleOrder.getId()); |
| | | createReqDTO.setSaleOrderNo(saleOrder.getNo()); |
| | | createReqDTO.setSaleOrderItemId(item.getId()); |
| | | createReqDTO.setMdmItemId(item.getProductId()); |
| | | createReqDTO.setProductName(productName); |
| | | createReqDTO.setQuantity(quantity); |
| | | createReqDTO.setClientId(saleOrder.getCustomerId()); |
| | | createReqDTO.setRequestDate(formatRequestDate(saleOrder.getOrderTime())); |
| | | createReqDTO.setRemark("ç±ç产车é´ä»éå®è®¢åçæï¼" + saleOrder.getNo()); |
| | | return mpsApi.createMps(createReqDTO); |
| | | } |
| | | |
| | | /** |
| | | * å客æ·åç§°ï¼å¤±è´¥æ¶è¿å null ä¸å½±å主æµç¨ |
| | | */ |
| | | private String getCustomerName(Long customerId) { |
| | | if (customerId == null) { |
| | | return null; |
| | | } |
| | | try { |
| | | // 该 API ç´æ¥è¿å DTOï¼ä¸æ¯ CommonResult |
| | | cn.iocoder.yudao.module.crm.api.customer.dto.CrmCustomerRespDTO customer = |
| | | customerApi.getCustomer(customerId); |
| | | return customer == null ? null : customer.getName(); |
| | | } catch (Exception e) { |
| | | log.warn("[getCustomerName] è·å客æ·å¤±è´¥ï¼customerId={}", customerId, e); |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | /** |