计划数量为0的修改

This commit is contained in:
秦鸿展
2026-02-09 10:26:07 +08:00
parent f149b7322d
commit 598a8b89e3
2 changed files with 83 additions and 20 deletions
@@ -30,6 +30,7 @@ import lombok.extern.slf4j.Slf4j;
import org.apache.poi.ss.usermodel.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.springframework.web.multipart.MultipartFile;
import java.io.InputStream;
@@ -1176,6 +1177,31 @@ public class StockInOrderApplicationService {
h.getConsignmentNo(), r.getMaterialName(), r.getMaterialCode(), r.getSkuCode(),
r.getWarehouseQuantity(), r.getInboundQuantity());
// 先检查数量,如果数量为空,直接跳过该明细行(不需要检查物料)
BigDecimal quantity = r.getWarehouseQuantity();
if (quantity == null) {
quantity = r.getInboundQuantity();
}
if (quantity == null) {
log.warn("跳过明细行:仓库数量或入库数量不能为空 - 委托编号NO: [{}], 商品名称: [{}], 料号: [{}], SKU码: [{}]",
h.getConsignmentNo(), r.getMaterialName(), r.getMaterialCode(), r.getSkuCode());
continue; // 跳过该明细行,继续处理下一行
}
// 检查是否为容器类型等非物料信息,如果是则跳过
String materialName = r.getMaterialName();
if (StringUtils.isNotBlank(materialName)) {
String lowerName = materialName.trim();
// 常见的容器类型关键词(不区分大小写)
if (lowerName.contains("尺柜") || lowerName.contains("尺集装箱") ||
lowerName.contains("Container") || lowerName.contains("container") ||
(lowerName.contains("") && (lowerName.contains("20") || lowerName.contains("40") || lowerName.contains("45")))) {
log.info("跳过明细行:识别为容器类型信息,非实际物料 - 委托编号NO: [{}], 商品名称: [{}]",
h.getConsignmentNo(), materialName);
continue; // 跳过该明细行,继续处理下一行
}
}
// 根据明细表中的字段查询物料基础信息(优先:料号 > 商品SKU码 > 商品名称)
// 注意:查询时必须加上货主ID条件,确保查询到的是该货主绑定的物料
Long materialBaseInfoId = null;
@@ -1203,13 +1229,17 @@ public class StockInOrderApplicationService {
log.info("通过料号查询到物料基础信息,料号: {}, 物料ID: {}, 货主ID: {}",
r.getMaterialCode(), materialBaseInfoId, shipperId);
} else {
log.warn("通过料号查询到物料基础信息,料号: [{}], 货主ID: [{}]", r.getMaterialCode(), shipperId);
// 如果提供了料号查询不到,直接报错,不允许导入
String errorMsg = String.format("导入失败:该货主下不存在该料号(委托编号NO=%s,货主名称=%s,料号=%s)。请确保该料号已在物料管理中创建,且属于该货主",
h.getConsignmentNo(), order.getShipperName(), r.getMaterialCode());
log.error(errorMsg);
throw new ServiceException(errorMsg);
}
} else {
log.warn("料号为空,跳过料号查询");
log.warn("料号为空,跳过料号查询,将尝试使用SKU码或商品名称查询");
}
// 如果料号查询不到,使用商品SKU码查询
// 只有在料号为空的情况下,才使用商品SKU码查询
if (materialBaseInfoId == null && StringUtils.isNotBlank(r.getSkuCode())) {
MaterialBaseInfoDO queryDO = new MaterialBaseInfoDO();
queryDO.setBarCode(r.getSkuCode());
@@ -1261,26 +1291,40 @@ public class StockInOrderApplicationService {
log.warn("商品名称为空,跳过商品名称查询");
}
// 如果都查询不到,记录警告但不阻止导入(允许后续手动关联)
// 如果都查询不到物料基础信息,阻止导入并抛出异常
if (materialBaseInfoId == null) {
log.warn("未查询到物料基础信息,料号: [{}], SKU码: [{}], 商品名称: [{}],将使用null值,后续可能需要手动关联",
r.getMaterialCode(), r.getSkuCode(), r.getMaterialName());
// 检查是否至少有一个查询条件
boolean hasQueryCondition = StringUtils.isNotBlank(r.getMaterialCode())
|| StringUtils.isNotBlank(r.getSkuCode())
|| StringUtils.isNotBlank(r.getMaterialName());
// 构建错误信息,说明物料在物料管理中不存在
StringBuilder errorMsg = new StringBuilder();
errorMsg.append("导入失败:物料在物料管理中不存在(委托编号NO=").append(h.getConsignmentNo());
errorMsg.append(",货主名称=").append(order.getShipperName());
if (StringUtils.isNotBlank(r.getMaterialCode())) {
errorMsg.append(",料号=").append(r.getMaterialCode());
}
if (StringUtils.isNotBlank(r.getSkuCode())) {
errorMsg.append("SKU码=").append(r.getSkuCode());
}
if (StringUtils.isNotBlank(r.getMaterialName())) {
errorMsg.append(",商品名称=").append(r.getMaterialName());
}
errorMsg.append("");
if (!hasQueryCondition) {
errorMsg.append("。明细行缺少物料标识信息(料号、SKU码或商品名称至少需要填写一个)");
} else {
errorMsg.append("。请确保该物料已在物料管理中创建,且料号、SKU码或商品名称与货主信息匹配");
}
log.error(errorMsg.toString());
throw new ServiceException(errorMsg.toString());
}
// 使用仓库数量或入库数量(优先使用仓库数量,如果为空则使用入库数量)
BigDecimal quantity = r.getWarehouseQuantity();
log.info("数量字段检查 - 仓库数量: [{}], 入库数量: [{}]", r.getWarehouseQuantity(), r.getInboundQuantity());
if (quantity == null) {
quantity = r.getInboundQuantity();
log.info("仓库数量为空,使用入库数量: [{}]", quantity);
}
// 如果数量为空,跳过该明细行,记录警告,继续处理其他行
if (quantity == null) {
log.warn("跳过明细行:仓库数量或入库数量不能为空 - 委托编号NO: [{}], 物料基础信息ID: [{}], 商品名称: [{}], 料号: [{}], SKU码: [{}], 仓库数量: [{}], 入库数量: [{}]",
h.getConsignmentNo(), materialBaseInfoId, r.getMaterialName(), r.getMaterialCode(),
r.getSkuCode(), r.getWarehouseQuantity(), r.getInboundQuantity());
continue; // 跳过该明细行,继续处理下一行
}
// 数量已在前面检查过,这里直接使用
log.info("数量字段检查 - 仓库数量: [{}], 入库数量: [{}], 使用数量: [{}]",
r.getWarehouseQuantity(), r.getInboundQuantity(), quantity);
InMaterialDetailDO d = new InMaterialDetailDO();
d.setMaterialBaseInfoId(materialBaseInfoId);
@@ -1359,6 +1403,16 @@ public class StockInOrderApplicationService {
order.setMaterialDetailList(details);
// 导入入库单时,计划数量取所有明细行的入库数量之和
if (!CollectionUtils.isEmpty(details)) {
BigDecimal totalInboundQuantity = details.stream()
.map(detail -> detail.getInboundQuantity() != null ? detail.getInboundQuantity() : BigDecimal.ZERO)
.reduce(BigDecimal.ZERO, BigDecimal::add);
order.setQuantity(totalInboundQuantity);
log.info("计算计划数量 - 委托编号NO: [{}], 明细行数: {}, 计划数量(入库数量之和): [{}]",
h.getConsignmentNo(), details.size(), totalInboundQuantity);
}
// 在导入时,需要调用shipperParam、supplierParam和setDataDict方法,确保货主信息被正确填充
// 注意:这里只调用shipperParam,因为导入时只提供了货主名称,需要根据名称查找货主ID和编号
try {
@@ -11,7 +11,9 @@ import com.mhd.system.api.model.LoginUser;
import com.mhd.wms.domain.stockInOrder.repository.todo.StockInOrderDO;
import com.mhd.wms.interfaces.dto.stockInOrder.StockInOrderDTO;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;
import java.math.BigDecimal;
import java.util.Date;
/**
@@ -78,6 +80,13 @@ public class StockInOrderAssembler {
if (orderTypeName == null || orderTypeName.trim().length() == 0) {
stockInOrderDO.setOrderTypeName("普通入库单");
}
// 新增入库单时计划数量取所有明细行的入库数量之和
if (!CollectionUtils.isEmpty(stockInOrderDO.getMaterialDetailList())) {
BigDecimal totalInboundQuantity = stockInOrderDO.getMaterialDetailList().stream()
.map(detail -> detail.getInboundQuantity() != null ? detail.getInboundQuantity() : BigDecimal.ZERO)
.reduce(BigDecimal.ZERO, BigDecimal::add);
stockInOrderDO.setQuantity(totalInboundQuantity);
}
}
return stockInOrderDO;
}