feat(component): 新增零部件打包管理和外协领料功能
- 实现零部件打包管理控制器,支持打包单的增删改查 - 添加零部件订单信息查询和装箱单详情查看功能 - 实现零部件打包信息的保存、更新和删除操作 - 添加装箱单PDF导出功能 - 实现外协领料控制器,支持SAP领料订单数据查询 - 添加外协领料订单的保存、搜索和详情查看功能 - 实现PDA端外协领料功能和物料扫码提交功能 - 添加出库单审核和库存管理功能 - 实现二维码扫描和批次管理功能
This commit is contained in:
parent
2a8d96a14a
commit
461775b5db
|
|
@ -113,9 +113,7 @@ public class ComponentPackingController {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 添加零部件的打包信息
|
* 添加零部件的打包信息
|
||||||
*
|
* @return {@link InventoryLockVO}
|
||||||
* @param request
|
|
||||||
* @return
|
|
||||||
*/
|
*/
|
||||||
@PostMapping("add")
|
@PostMapping("add")
|
||||||
public ApiResult<Void> savePacking(@Valid @RequestBody ComponentPackingInputQO request) {
|
public ApiResult<Void> savePacking(@Valid @RequestBody ComponentPackingInputQO request) {
|
||||||
|
|
|
||||||
|
|
@ -11,7 +11,6 @@ import com.nflg.wms.admin.repository.InventoryForOutRepository;
|
||||||
import com.nflg.wms.admin.repository.OutMaterialScanRecordRespository;
|
import com.nflg.wms.admin.repository.OutMaterialScanRecordRespository;
|
||||||
import com.nflg.wms.admin.service.BasdeSerialNumberControllerService;
|
import com.nflg.wms.admin.service.BasdeSerialNumberControllerService;
|
||||||
import com.nflg.wms.admin.service.SapService;
|
import com.nflg.wms.admin.service.SapService;
|
||||||
import com.nflg.wms.admin.util.NoUtil;
|
|
||||||
import com.nflg.wms.admin.util.PdfGeneratorUtil;
|
import com.nflg.wms.admin.util.PdfGeneratorUtil;
|
||||||
import com.nflg.wms.admin.util.QRCodeUtil;
|
import com.nflg.wms.admin.util.QRCodeUtil;
|
||||||
import com.nflg.wms.admin.util.ThymeleafUtil;
|
import com.nflg.wms.admin.util.ThymeleafUtil;
|
||||||
|
|
@ -105,6 +104,7 @@ public class OutAssistanceController extends BaseController {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 保存
|
* 保存
|
||||||
|
* @return {@link InventoryLockVO}
|
||||||
*/
|
*/
|
||||||
@Transactional
|
@Transactional
|
||||||
@PostMapping("save")
|
@PostMapping("save")
|
||||||
|
|
@ -119,6 +119,7 @@ public class OutAssistanceController extends BaseController {
|
||||||
VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(materialNos))
|
VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(materialNos))
|
||||||
.throwMessage("以下物料的申请数量超出限制:" + StrUtil.join(",", materialNos));
|
.throwMessage("以下物料的申请数量超出限制:" + StrUtil.join(",", materialNos));
|
||||||
Map<String, List<SubcontractedOrderDTO>> maps = datas.stream().collect(Collectors.groupingBy(SubcontractedOrderDTO::getKey));
|
Map<String, List<SubcontractedOrderDTO>> maps = datas.stream().collect(Collectors.groupingBy(SubcontractedOrderDTO::getKey));
|
||||||
|
List<InventoryLockVO> lockVOS = new ArrayList<>();
|
||||||
maps.forEach((key, items) -> {
|
maps.forEach((key, items) -> {
|
||||||
WmsOutAssistance order = Convert.convert(WmsOutAssistance.class, items.get(0));
|
WmsOutAssistance order = Convert.convert(WmsOutAssistance.class, items.get(0));
|
||||||
order.setNo(serialNumberControllerService.generateSerialNumber(16));
|
order.setNo(serialNumberControllerService.generateSerialNumber(16));
|
||||||
|
|
@ -127,11 +128,35 @@ public class OutAssistanceController extends BaseController {
|
||||||
outAssistanceService.save(order);
|
outAssistanceService.save(order);
|
||||||
items.forEach(item -> {
|
items.forEach(item -> {
|
||||||
WmsOutAssistanceItem data = Convert.convert(WmsOutAssistanceItem.class, item);
|
WmsOutAssistanceItem data = Convert.convert(WmsOutAssistanceItem.class, item);
|
||||||
data.setLeft(data.getNum());
|
RLock lock = redissonClient.getLock(StrUtil.format("lock:inventory:{}:{}:{}", order.getWerks(), order.getLgort1(), item.getMatnr1()));
|
||||||
data.setOrderId(order.getId());
|
try {
|
||||||
outAssistanceItemService.save(data);
|
// 等待5秒获取锁,10秒后自动释放
|
||||||
|
if (lock.tryLock(5, 10, TimeUnit.SECONDS)) {
|
||||||
|
if (inventoryService.getNumOne(order.getWerks(), order.getLgort1(), item.getMatnr1()).compareTo(data.getNum()) < 0) {
|
||||||
|
List<InventoryLockVO> itemLocks = inventoryService.getLockList(order.getWerks(), order.getLgort1(), item.getMatnr1());
|
||||||
|
VUtil.trueThrowBusinessError(CollectionUtil.isEmpty(itemLocks)).throwMessage("库存不足:" + item.getMatnr1());
|
||||||
|
lockVOS.addAll(itemLocks);
|
||||||
|
}else {
|
||||||
|
data.setLeft(data.getNum());
|
||||||
|
data.setOrderId(order.getId());
|
||||||
|
outAssistanceItemService.save(data);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw new NflgException(STATE.BusinessError, "获取锁失败");
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
log.error("保存单据出错", e);
|
||||||
|
throw new NflgException(STATE.BusinessError, e.getMessage());
|
||||||
|
} finally {
|
||||||
|
if (lock.isHeldByCurrentThread()) {
|
||||||
|
lock.unlock();
|
||||||
|
}
|
||||||
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
if (CollectionUtil.isNotEmpty(lockVOS)) {
|
||||||
|
throw new DataAlertException(STATE.OutOfStock, lockVOS);
|
||||||
|
}
|
||||||
return ApiResult.success();
|
return ApiResult.success();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -230,10 +255,10 @@ public class OutAssistanceController extends BaseController {
|
||||||
public ApiResult<Void> submit(@Valid @RequestBody OutProduceSubmitQO request) {
|
public ApiResult<Void> submit(@Valid @RequestBody OutProduceSubmitQO request) {
|
||||||
WmsOutAssistance order = outAssistanceService.lambdaQuery().eq(WmsOutAssistance::getNo, request.getNo()).one();
|
WmsOutAssistance order = outAssistanceService.lambdaQuery().eq(WmsOutAssistance::getNo, request.getNo()).one();
|
||||||
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("订单不存在");
|
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("订单不存在");
|
||||||
Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
// Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
||||||
matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
// matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
||||||
VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
// VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
||||||
.throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
// .throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
||||||
WmsOutAssistanceTicket ticket = new WmsOutAssistanceTicket()
|
WmsOutAssistanceTicket ticket = new WmsOutAssistanceTicket()
|
||||||
.setId(IdUtil.getSnowflakeNextId())
|
.setId(IdUtil.getSnowflakeNextId())
|
||||||
.setNo(serialNumberControllerService.generateSerialNumber(17))
|
.setNo(serialNumberControllerService.generateSerialNumber(17))
|
||||||
|
|
@ -354,36 +379,6 @@ public class OutAssistanceController extends BaseController {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
List<InventoryLockVO> lockVOS = new ArrayList<>();
|
|
||||||
records.stream()
|
|
||||||
.collect(Collectors.groupingBy(OutMaterialScanRecord::getKey10))
|
|
||||||
.forEach((key, vs) -> {
|
|
||||||
OutMaterialScanRecord info = vs.get(0);
|
|
||||||
BigDecimal lockNum = vs.stream().map(OutMaterialScanRecord::getNum).reduce(BigDecimal.ZERO, BigDecimal::add);
|
|
||||||
RLock lock = redissonClient.getLock(StrUtil.format("lock:inventory:{}:{}:{}", info.getFactoryNo(), info.getWarehouseNo(), info.getMaterialNo()));
|
|
||||||
try {
|
|
||||||
// 等待5秒获取锁,10秒后自动释放
|
|
||||||
if (lock.tryLock(5, 10, TimeUnit.SECONDS)) {
|
|
||||||
if (inventoryService.getNumOne(info.getFactoryNo(), info.getWarehouseNo(), info.getMaterialNo()).compareTo(lockNum) < 0) {
|
|
||||||
List<InventoryLockVO> itemLocks = inventoryService.getLockList(info.getFactoryNo(), info.getWarehouseNo(), info.getMaterialNo());
|
|
||||||
VUtil.trueThrowBusinessError(CollectionUtil.isEmpty(itemLocks)).throwMessage("库存不足:" + info.getMaterialNo());
|
|
||||||
lockVOS.addAll(itemLocks);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
throw new NflgException(STATE.BusinessError, "获取锁失败");
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
log.error("保存生产领料单出错", e);
|
|
||||||
throw new NflgException(STATE.BusinessError, e.getMessage());
|
|
||||||
} finally {
|
|
||||||
if (lock.isHeldByCurrentThread()) {
|
|
||||||
lock.unlock();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
if (CollectionUtil.isNotEmpty(lockVOS)) {
|
|
||||||
throw new DataAlertException(STATE.OutOfStock, lockVOS);
|
|
||||||
}
|
|
||||||
outAssistanceItemService.updateBatchById(datas);
|
outAssistanceItemService.updateBatchById(datas);
|
||||||
outAssistanceTicketItemService.saveBatch(ticketItems);
|
outAssistanceTicketItemService.saveBatch(ticketItems);
|
||||||
outAssistanceTicketService.save(ticket);
|
outAssistanceTicketService.save(ticket);
|
||||||
|
|
|
||||||
|
|
@ -11,7 +11,6 @@ import com.nflg.wms.admin.repository.InventoryForOutRepository;
|
||||||
import com.nflg.wms.admin.repository.OutMaterialScanRecordRespository;
|
import com.nflg.wms.admin.repository.OutMaterialScanRecordRespository;
|
||||||
import com.nflg.wms.admin.service.BasdeSerialNumberControllerService;
|
import com.nflg.wms.admin.service.BasdeSerialNumberControllerService;
|
||||||
import com.nflg.wms.admin.service.SapService;
|
import com.nflg.wms.admin.service.SapService;
|
||||||
import com.nflg.wms.admin.util.NoUtil;
|
|
||||||
import com.nflg.wms.admin.util.PdfGeneratorUtil;
|
import com.nflg.wms.admin.util.PdfGeneratorUtil;
|
||||||
import com.nflg.wms.admin.util.QRCodeUtil;
|
import com.nflg.wms.admin.util.QRCodeUtil;
|
||||||
import com.nflg.wms.admin.util.ThymeleafUtil;
|
import com.nflg.wms.admin.util.ThymeleafUtil;
|
||||||
|
|
@ -108,6 +107,7 @@ public class OutCostCenterController extends BaseController {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 保存
|
* 保存
|
||||||
|
* @return {@link InventoryLockVO}
|
||||||
*/
|
*/
|
||||||
@Transactional
|
@Transactional
|
||||||
@PostMapping("save")
|
@PostMapping("save")
|
||||||
|
|
@ -121,6 +121,7 @@ public class OutCostCenterController extends BaseController {
|
||||||
});
|
});
|
||||||
VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(materialNos))
|
VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(materialNos))
|
||||||
.throwMessage("以下物料的申请数量超出限制:" + StrUtil.join(",", materialNos));
|
.throwMessage("以下物料的申请数量超出限制:" + StrUtil.join(",", materialNos));
|
||||||
|
List<InventoryLockVO> lockVOS = new ArrayList<>();
|
||||||
Map<String, List<DepartmentMaterialRequisitionDTO>> maps = datas.stream().collect(Collectors.groupingBy(DepartmentMaterialRequisitionDTO::getKey1));
|
Map<String, List<DepartmentMaterialRequisitionDTO>> maps = datas.stream().collect(Collectors.groupingBy(DepartmentMaterialRequisitionDTO::getKey1));
|
||||||
maps.forEach((key, items) -> {
|
maps.forEach((key, items) -> {
|
||||||
WmsOutCostcenter order = Convert.convert(WmsOutCostcenter.class, items.get(0));
|
WmsOutCostcenter order = Convert.convert(WmsOutCostcenter.class, items.get(0));
|
||||||
|
|
@ -130,11 +131,35 @@ public class OutCostCenterController extends BaseController {
|
||||||
outCostcenterService.save(order);
|
outCostcenterService.save(order);
|
||||||
items.forEach(item -> {
|
items.forEach(item -> {
|
||||||
WmsOutCostcenterItem data = Convert.convert(WmsOutCostcenterItem.class, item);
|
WmsOutCostcenterItem data = Convert.convert(WmsOutCostcenterItem.class, item);
|
||||||
data.setLeft(data.getNum());
|
RLock lock = redissonClient.getLock(StrUtil.format("lock:inventory:{}:{}:{}", order.getWerks(), data.getLgort(), data.getMatnr()));
|
||||||
data.setOrderId(order.getId());
|
try {
|
||||||
outCostcenterItemService.save(data);
|
// 等待5秒获取锁,10秒后自动释放
|
||||||
|
if (lock.tryLock(5, 10, TimeUnit.SECONDS)) {
|
||||||
|
if (inventoryService.getNumOne(order.getWerks(), data.getLgort(), data.getMatnr()).compareTo(data.getNum()) < 0) {
|
||||||
|
List<InventoryLockVO> itemLocks = inventoryService.getLockList(order.getWerks(), data.getLgort(), data.getMatnr());
|
||||||
|
VUtil.trueThrowBusinessError(CollectionUtil.isEmpty(itemLocks)).throwMessage("库存不足:" + data.getMatnr());
|
||||||
|
lockVOS.addAll(itemLocks);
|
||||||
|
} else {
|
||||||
|
data.setLeft(data.getNum());
|
||||||
|
data.setOrderId(order.getId());
|
||||||
|
outCostcenterItemService.save(data);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw new NflgException(STATE.BusinessError, "获取锁失败");
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
log.error("保存单据出错", e);
|
||||||
|
throw new NflgException(STATE.BusinessError, e.getMessage());
|
||||||
|
} finally {
|
||||||
|
if (lock.isHeldByCurrentThread()) {
|
||||||
|
lock.unlock();
|
||||||
|
}
|
||||||
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
if (CollectionUtil.isNotEmpty(lockVOS)) {
|
||||||
|
throw new DataAlertException(STATE.OutOfStock, lockVOS);
|
||||||
|
}
|
||||||
return ApiResult.success();
|
return ApiResult.success();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -232,10 +257,10 @@ public class OutCostCenterController extends BaseController {
|
||||||
public ApiResult<Void> submit(@Valid @RequestBody OutProduceSubmitQO request) {
|
public ApiResult<Void> submit(@Valid @RequestBody OutProduceSubmitQO request) {
|
||||||
WmsOutCostcenter order = outCostcenterService.lambdaQuery().eq(WmsOutCostcenter::getNo, request.getNo()).one();
|
WmsOutCostcenter order = outCostcenterService.lambdaQuery().eq(WmsOutCostcenter::getNo, request.getNo()).one();
|
||||||
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("订单不存在");
|
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("订单不存在");
|
||||||
Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
// Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
||||||
matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
// matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
||||||
VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
// VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
||||||
.throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
// .throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
||||||
WmsOutCostcenterTicket ticket = new WmsOutCostcenterTicket()
|
WmsOutCostcenterTicket ticket = new WmsOutCostcenterTicket()
|
||||||
.setId(IdUtil.getSnowflakeNextId())
|
.setId(IdUtil.getSnowflakeNextId())
|
||||||
.setNo(serialNumberControllerService.generateSerialNumber(15))
|
.setNo(serialNumberControllerService.generateSerialNumber(15))
|
||||||
|
|
@ -253,7 +278,9 @@ public class OutCostCenterController extends BaseController {
|
||||||
.flatMap(Collection::stream)
|
.flatMap(Collection::stream)
|
||||||
.map(QRCodeQO::getContent)
|
.map(QRCodeQO::getContent)
|
||||||
.collect(Collectors.toSet());
|
.collect(Collectors.toSet());
|
||||||
List<WmsQrCodeMaster> qrCodeMasters = CollectionUtil.isEmpty(allQrCodes) ? Collections.emptyList() : qrCodeMasterService.lambdaQuery()
|
List<WmsQrCodeMaster> qrCodeMasters = CollectionUtil.isEmpty(allQrCodes)
|
||||||
|
? Collections.emptyList() :
|
||||||
|
qrCodeMasterService.lambdaQuery()
|
||||||
.eq(WmsQrCodeMaster::getProcessStage, BarCodeProcessStage.InBound.getState())
|
.eq(WmsQrCodeMaster::getProcessStage, BarCodeProcessStage.InBound.getState())
|
||||||
.in(WmsQrCodeMaster::getBarcodeCode, allQrCodes)
|
.in(WmsQrCodeMaster::getBarcodeCode, allQrCodes)
|
||||||
.list();
|
.list();
|
||||||
|
|
@ -348,36 +375,6 @@ public class OutCostCenterController extends BaseController {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
List<InventoryLockVO> lockVOS = new ArrayList<>();
|
|
||||||
records.stream()
|
|
||||||
.collect(Collectors.groupingBy(OutMaterialScanRecord::getKey10))
|
|
||||||
.forEach((key, vs) -> {
|
|
||||||
OutMaterialScanRecord info = vs.get(0);
|
|
||||||
BigDecimal lockNum = vs.stream().map(OutMaterialScanRecord::getNum).reduce(BigDecimal.ZERO, BigDecimal::add);
|
|
||||||
RLock lock = redissonClient.getLock(StrUtil.format("lock:inventory:{}:{}:{}", info.getFactoryNo(), info.getWarehouseNo(), info.getMaterialNo()));
|
|
||||||
try {
|
|
||||||
// 等待5秒获取锁,10秒后自动释放
|
|
||||||
if (lock.tryLock(5, 10, TimeUnit.SECONDS)) {
|
|
||||||
if (inventoryService.getNumOne(info.getFactoryNo(), info.getWarehouseNo(), info.getMaterialNo()).compareTo(lockNum) < 0) {
|
|
||||||
List<InventoryLockVO> itemLocks = inventoryService.getLockList(info.getFactoryNo(), info.getWarehouseNo(), info.getMaterialNo());
|
|
||||||
VUtil.trueThrowBusinessError(CollectionUtil.isEmpty(itemLocks)).throwMessage("库存不足:" + info.getMaterialNo());
|
|
||||||
lockVOS.addAll(itemLocks);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
throw new NflgException(STATE.BusinessError, "获取锁失败");
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
log.error("保存生产领料单出错", e);
|
|
||||||
throw new NflgException(STATE.BusinessError, e.getMessage());
|
|
||||||
} finally {
|
|
||||||
if (lock.isHeldByCurrentThread()) {
|
|
||||||
lock.unlock();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
if (CollectionUtil.isNotEmpty(lockVOS)) {
|
|
||||||
throw new DataAlertException(STATE.OutOfStock, lockVOS);
|
|
||||||
}
|
|
||||||
outCostcenterItemService.updateBatchById(datas);
|
outCostcenterItemService.updateBatchById(datas);
|
||||||
outCostcenterTicketItemService.saveBatch(ticketItems);
|
outCostcenterTicketItemService.saveBatch(ticketItems);
|
||||||
outCostcenterTicketService.save(ticket);
|
outCostcenterTicketService.save(ticket);
|
||||||
|
|
@ -433,17 +430,17 @@ public class OutCostCenterController extends BaseController {
|
||||||
.setFactoryNo(list.get(0).getFactoryNo())
|
.setFactoryNo(list.get(0).getFactoryNo())
|
||||||
.setWarehouseNo(list.get(0).getWarehouseNo())
|
.setWarehouseNo(list.get(0).getWarehouseNo())
|
||||||
.setBinLocation(list.get(0).isQiTao() ? list.get(0).getBinNo() : qrCodeMasters.stream()
|
.setBinLocation(list.get(0).isQiTao() ? list.get(0).getBinNo() : qrCodeMasters.stream()
|
||||||
.filter(qr -> StrUtil.equals(qr.getBarcodeCode(), list.get(0).getUniqNo()))
|
.filter(qr -> StrUtil.equals(qr.getBarcodeCode(), list.get(0).getUniqNo()))
|
||||||
.findFirst()
|
.findFirst()
|
||||||
.map(WmsQrCodeMaster::getBinLocation)
|
.map(WmsQrCodeMaster::getBinLocation)
|
||||||
.orElse("")
|
.orElse("")
|
||||||
)
|
)
|
||||||
.setNum(list.stream().map(OutMaterialScanRecord::getNum).reduce(BigDecimal.ZERO, BigDecimal::add))
|
.setNum(list.stream().map(OutMaterialScanRecord::getNum).reduce(BigDecimal.ZERO, BigDecimal::add))
|
||||||
).toList()
|
).toList()
|
||||||
);
|
);
|
||||||
Map<String, List<OutMaterialScanRecord>> dmaps = records.stream().collect(Collectors.groupingBy(OutMaterialScanRecord::getKey7));
|
Map<String, List<OutMaterialScanRecord>> dmaps = records.stream().collect(Collectors.groupingBy(OutMaterialScanRecord::getKey7));
|
||||||
OptRecordDTO optRecordDTO = new OptRecordDTO();
|
OptRecordDTO optRecordDTO = new OptRecordDTO();
|
||||||
optRecordDTO.setOperationType((short)1)
|
optRecordDTO.setOperationType((short) 1)
|
||||||
.setOrderId(order.getNo());
|
.setOrderId(order.getNo());
|
||||||
optRecordService.add(optRecordDTO);
|
optRecordService.add(optRecordDTO);
|
||||||
C_MaterialOutboundDTO vo = sapService.ZWM00_MB115(new C_MaterialOutboundQO()
|
C_MaterialOutboundDTO vo = sapService.ZWM00_MB115(new C_MaterialOutboundQO()
|
||||||
|
|
|
||||||
|
|
@ -21,7 +21,10 @@ import com.nflg.wms.common.exception.NflgException;
|
||||||
import com.nflg.wms.common.pojo.ApiResult;
|
import com.nflg.wms.common.pojo.ApiResult;
|
||||||
import com.nflg.wms.common.pojo.PageData;
|
import com.nflg.wms.common.pojo.PageData;
|
||||||
import com.nflg.wms.common.pojo.document.OutMaterialScanRecord;
|
import com.nflg.wms.common.pojo.document.OutMaterialScanRecord;
|
||||||
import com.nflg.wms.common.pojo.dto.*;
|
import com.nflg.wms.common.pojo.dto.InventoryForOutDTO;
|
||||||
|
import com.nflg.wms.common.pojo.dto.InventoryInDTO;
|
||||||
|
import com.nflg.wms.common.pojo.dto.InventoryOutDTO;
|
||||||
|
import com.nflg.wms.common.pojo.dto.OptRecordDTO;
|
||||||
import com.nflg.wms.common.pojo.qo.*;
|
import com.nflg.wms.common.pojo.qo.*;
|
||||||
import com.nflg.wms.common.pojo.vo.*;
|
import com.nflg.wms.common.pojo.vo.*;
|
||||||
import com.nflg.wms.common.util.EecExcelUtil;
|
import com.nflg.wms.common.util.EecExcelUtil;
|
||||||
|
|
@ -46,7 +49,6 @@ import java.io.IOException;
|
||||||
import java.math.BigDecimal;
|
import java.math.BigDecimal;
|
||||||
import java.time.Instant;
|
import java.time.Instant;
|
||||||
import java.time.LocalDateTime;
|
import java.time.LocalDateTime;
|
||||||
import java.time.format.DateTimeFormatter;
|
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
@ -384,10 +386,10 @@ public class OutProduceController extends BaseController {
|
||||||
public ApiResult<Void> submit(@Valid @RequestBody OutProduceSubmitQO request) {
|
public ApiResult<Void> submit(@Valid @RequestBody OutProduceSubmitQO request) {
|
||||||
WmsOutProduce order = outProduceService.lambdaQuery().eq(WmsOutProduce::getNo, request.getNo()).one();
|
WmsOutProduce order = outProduceService.lambdaQuery().eq(WmsOutProduce::getNo, request.getNo()).one();
|
||||||
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("订单不存在");
|
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("订单不存在");
|
||||||
Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
// Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
||||||
matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
// matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
||||||
VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
// VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
||||||
.throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
// .throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
||||||
WmsOutProduceTicket ticket = new WmsOutProduceTicket()
|
WmsOutProduceTicket ticket = new WmsOutProduceTicket()
|
||||||
.setId(IdUtil.getSnowflakeNextId())
|
.setId(IdUtil.getSnowflakeNextId())
|
||||||
.setNo(serialNumberControllerService.generateSerialNumber(21))
|
.setNo(serialNumberControllerService.generateSerialNumber(21))
|
||||||
|
|
|
||||||
|
|
@ -162,7 +162,7 @@ public class TransferCompanyController extends BaseController {
|
||||||
throw new NflgException(STATE.BusinessError, "获取锁失败");
|
throw new NflgException(STATE.BusinessError, "获取锁失败");
|
||||||
}
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.error("保存生产领料单出错", e);
|
log.error("保存出错", e);
|
||||||
throw new NflgException(STATE.BusinessError, e.getMessage());
|
throw new NflgException(STATE.BusinessError, e.getMessage());
|
||||||
} finally {
|
} finally {
|
||||||
if (lock.isHeldByCurrentThread()) {
|
if (lock.isHeldByCurrentThread()) {
|
||||||
|
|
@ -288,10 +288,10 @@ public class TransferCompanyController extends BaseController {
|
||||||
public ApiResult<Void> submitForOut(@Valid @RequestBody OutProduceSubmitQO request) {
|
public ApiResult<Void> submitForOut(@Valid @RequestBody OutProduceSubmitQO request) {
|
||||||
WmsTransferCompany order = transferCompanyService.lambdaQuery().eq(WmsTransferCompany::getNo, request.getNo()).one();
|
WmsTransferCompany order = transferCompanyService.lambdaQuery().eq(WmsTransferCompany::getNo, request.getNo()).one();
|
||||||
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("转储单不存在");
|
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("转储单不存在");
|
||||||
Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
// Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
||||||
matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
// matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
||||||
VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
// VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
||||||
.throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
// .throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
||||||
List<WmsTransferCompanyItem> datas = transferCompanyItemService.getList(order.getId());
|
List<WmsTransferCompanyItem> datas = transferCompanyItemService.getList(order.getId());
|
||||||
List<OutMaterialScanRecord> records = new ArrayList<>();
|
List<OutMaterialScanRecord> records = new ArrayList<>();
|
||||||
List<WmsTransferCompanyTicketItem> ticketItems = new ArrayList<>();
|
List<WmsTransferCompanyTicketItem> ticketItems = new ArrayList<>();
|
||||||
|
|
|
||||||
|
|
@ -160,7 +160,7 @@ public class TransferFactoryController extends BaseController {
|
||||||
throw new NflgException(STATE.BusinessError, "获取锁失败");
|
throw new NflgException(STATE.BusinessError, "获取锁失败");
|
||||||
}
|
}
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.error("保存生产领料单出错", e);
|
log.error("保存出错", e);
|
||||||
throw new NflgException(STATE.BusinessError, e.getMessage());
|
throw new NflgException(STATE.BusinessError, e.getMessage());
|
||||||
} finally {
|
} finally {
|
||||||
if (lock.isHeldByCurrentThread()) {
|
if (lock.isHeldByCurrentThread()) {
|
||||||
|
|
@ -287,10 +287,10 @@ public class TransferFactoryController extends BaseController {
|
||||||
public ApiResult<Void> submitForOut(@Valid @RequestBody OutProduceSubmitQO request) {
|
public ApiResult<Void> submitForOut(@Valid @RequestBody OutProduceSubmitQO request) {
|
||||||
WmsTransferFactory order = transferFactoryService.lambdaQuery().eq(WmsTransferFactory::getNo, request.getNo()).one();
|
WmsTransferFactory order = transferFactoryService.lambdaQuery().eq(WmsTransferFactory::getNo, request.getNo()).one();
|
||||||
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("调拨单不存在");
|
VUtil.trueThrowBusinessError(Objects.isNull(order)).throwMessage("调拨单不存在");
|
||||||
Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
// Set<String> matnrs = request.getItems().stream().map(OutProduceSubmitItemQO::getMaterialNo).collect(Collectors.toSet());
|
||||||
matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
// matnrs.removeAll(request.getRecommendBatch().stream().map(InventoryForOutVO::getMaterialNo).collect(Collectors.toSet()));
|
||||||
VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
// VUtil.trueThrowBusinessError(CollectionUtil.isNotEmpty(matnrs))
|
||||||
.throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
// .throwMessage("以下物料无库存,不能出库:" + StrUtil.join(",", matnrs));
|
||||||
List<WmsTransferFactoryItem> datas = transferFactoryItemService.getList(order.getId());
|
List<WmsTransferFactoryItem> datas = transferFactoryItemService.getList(order.getId());
|
||||||
List<OutMaterialScanRecord> records = new ArrayList<>();
|
List<OutMaterialScanRecord> records = new ArrayList<>();
|
||||||
WmsTransferFactoryTicket ticket = new WmsTransferFactoryTicket()
|
WmsTransferFactoryTicket ticket = new WmsTransferFactoryTicket()
|
||||||
|
|
|
||||||
|
|
@ -2,27 +2,38 @@ package com.nflg.wms.admin.service;
|
||||||
|
|
||||||
import cn.hutool.core.collection.CollectionUtil;
|
import cn.hutool.core.collection.CollectionUtil;
|
||||||
import cn.hutool.core.util.IdUtil;
|
import cn.hutool.core.util.IdUtil;
|
||||||
|
import cn.hutool.core.util.StrUtil;
|
||||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||||
|
import com.nflg.wms.common.constant.STATE;
|
||||||
|
import com.nflg.wms.common.exception.DataAlertException;
|
||||||
|
import com.nflg.wms.common.exception.NflgException;
|
||||||
import com.nflg.wms.common.pojo.qo.ComponentPackingEditInputQO;
|
import com.nflg.wms.common.pojo.qo.ComponentPackingEditInputQO;
|
||||||
import com.nflg.wms.common.pojo.qo.ComponentPackingInputQO;
|
import com.nflg.wms.common.pojo.qo.ComponentPackingInputQO;
|
||||||
import com.nflg.wms.common.pojo.qo.ComponentPackingItemEditInputQO;
|
import com.nflg.wms.common.pojo.qo.ComponentPackingItemEditInputQO;
|
||||||
|
import com.nflg.wms.common.pojo.vo.InventoryLockVO;
|
||||||
import com.nflg.wms.common.util.UserUtil;
|
import com.nflg.wms.common.util.UserUtil;
|
||||||
import com.nflg.wms.common.util.VUtil;
|
import com.nflg.wms.common.util.VUtil;
|
||||||
import com.nflg.wms.repository.entity.WmsComponentPacking;
|
import com.nflg.wms.repository.entity.WmsComponentPacking;
|
||||||
import com.nflg.wms.repository.entity.WmsComponentPackingItem;
|
import com.nflg.wms.repository.entity.WmsComponentPackingItem;
|
||||||
import com.nflg.wms.repository.service.IWmsComponentPackingItemService;
|
import com.nflg.wms.repository.service.IWmsComponentPackingItemService;
|
||||||
import com.nflg.wms.repository.service.IWmsComponentPackingService;
|
import com.nflg.wms.repository.service.IWmsComponentPackingService;
|
||||||
|
import com.nflg.wms.repository.service.IWmsInventoryService;
|
||||||
import jakarta.annotation.Resource;
|
import jakarta.annotation.Resource;
|
||||||
import jakarta.validation.Valid;
|
import jakarta.validation.Valid;
|
||||||
import org.springframework.cloud.commons.util.IdUtils;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.redisson.api.RLock;
|
||||||
|
import org.redisson.api.RedissonClient;
|
||||||
import org.springframework.stereotype.Component;
|
import org.springframework.stereotype.Component;
|
||||||
import org.springframework.transaction.annotation.Transactional;
|
import org.springframework.transaction.annotation.Transactional;
|
||||||
|
|
||||||
import java.math.BigDecimal;
|
import java.math.BigDecimal;
|
||||||
import java.time.LocalDateTime;
|
import java.time.LocalDateTime;
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
|
@Slf4j
|
||||||
@Component
|
@Component
|
||||||
public class ComponentPackingControllerService {
|
public class ComponentPackingControllerService {
|
||||||
@Resource
|
@Resource
|
||||||
|
|
@ -34,6 +45,12 @@ public class ComponentPackingControllerService {
|
||||||
@Resource
|
@Resource
|
||||||
private BasdeSerialNumberControllerService basdeSerialNumberControllerService;
|
private BasdeSerialNumberControllerService basdeSerialNumberControllerService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private RedissonClient redissonClient;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private IWmsInventoryService inventoryService;
|
||||||
|
|
||||||
@Transactional
|
@Transactional
|
||||||
public void savePacking(@Valid ComponentPackingInputQO request) {
|
public void savePacking(@Valid ComponentPackingInputQO request) {
|
||||||
WmsComponentPacking wmsComponentPacking = new WmsComponentPacking();
|
WmsComponentPacking wmsComponentPacking = new WmsComponentPacking();
|
||||||
|
|
@ -65,32 +82,57 @@ public class ComponentPackingControllerService {
|
||||||
wmsComponentPacking.setCreateId(UserUtil.getUserId());
|
wmsComponentPacking.setCreateId(UserUtil.getUserId());
|
||||||
wmsComponentPacking.setCreateTime(LocalDateTime.now());
|
wmsComponentPacking.setCreateTime(LocalDateTime.now());
|
||||||
wmsComponentPacking.setFactoryNo(request.getFactoryNo());
|
wmsComponentPacking.setFactoryNo(request.getFactoryNo());
|
||||||
List<WmsComponentPackingItem> wmsComponentPackingItems = request.getItems().stream()
|
List<InventoryLockVO> lockVOS = new ArrayList<>();
|
||||||
.map(item -> new WmsComponentPackingItem()
|
request.getItems().forEach(item -> {
|
||||||
.setId(IdUtil.getSnowflakeNextId())
|
RLock lock = redissonClient.getLock(StrUtil.format("lock:inventory:{}:{}:{}", wmsComponentPacking.getFactoryNo(), item.getLgort(), item.getIdnrk()));
|
||||||
.setItemIndex(item.getIndex())
|
try {
|
||||||
.setVbeln(item.getVbeln())
|
// 等待5秒获取锁,10秒后自动释放
|
||||||
.setPosnr(item.getPosnr())
|
if (lock.tryLock(5, 10, TimeUnit.SECONDS)) {
|
||||||
.setIdnrk(item.getIdnrk())
|
if (inventoryService.getNumOne(wmsComponentPacking.getFactoryNo(), item.getLgort(), item.getIdnrk()).compareTo(item.getMenge()) < 0) {
|
||||||
.setOjtxb(item.getOjtxb())
|
List<InventoryLockVO> itemLocks = inventoryService.getLockList(wmsComponentPacking.getFactoryNo(), item.getLgort(), item.getIdnrk());
|
||||||
.setMeins(item.getMeins())
|
VUtil.trueThrowBusinessError(CollectionUtil.isEmpty(itemLocks)).throwMessage("库存不足:" + item.getIdnrk());
|
||||||
.setMenge(item.getMenge())
|
lockVOS.addAll(itemLocks);
|
||||||
.setAtwrt(item.getAtwrt())
|
} else {
|
||||||
.setZatwrt(item.getZatwrt())
|
wmsComponentPackingItemService.save(
|
||||||
.setZxiah(item.getZxiah())
|
new WmsComponentPackingItem()
|
||||||
.setZtext(item.getZtext())
|
.setId(IdUtil.getSnowflakeNextId())
|
||||||
.setPotx2(item.getPotx2())
|
.setItemIndex(item.getIndex())
|
||||||
.setPmenge(item.getPmenge())
|
.setVbeln(item.getVbeln())
|
||||||
.setLgpbe(item.getLgpbe())
|
.setPosnr(item.getPosnr())
|
||||||
.setLgort(item.getLgort())
|
.setIdnrk(item.getIdnrk())
|
||||||
.setLgobe(item.getLgobe())
|
.setOjtxb(item.getOjtxb())
|
||||||
.setOutQty(new BigDecimal(0))
|
.setMeins(item.getMeins())
|
||||||
.setPackingId(wmsComponentPacking.getId())
|
.setMenge(item.getMenge())
|
||||||
).toList();
|
.setAtwrt(item.getAtwrt())
|
||||||
|
.setZatwrt(item.getZatwrt())
|
||||||
|
.setZxiah(item.getZxiah())
|
||||||
|
.setZtext(item.getZtext())
|
||||||
|
.setPotx2(item.getPotx2())
|
||||||
|
.setPmenge(item.getPmenge())
|
||||||
|
.setLgpbe(item.getLgpbe())
|
||||||
|
.setLgort(item.getLgort())
|
||||||
|
.setLgobe(item.getLgobe())
|
||||||
|
.setOutQty(new BigDecimal(0))
|
||||||
|
.setPackingId(wmsComponentPacking.getId())
|
||||||
|
);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw new NflgException(STATE.BusinessError, "获取锁失败");
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
log.error("保存单据出错", e);
|
||||||
|
throw new NflgException(STATE.BusinessError, e.getMessage());
|
||||||
|
} finally {
|
||||||
|
if (lock.isHeldByCurrentThread()) {
|
||||||
|
lock.unlock();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
if (CollectionUtil.isNotEmpty(lockVOS)) {
|
||||||
|
throw new DataAlertException(STATE.OutOfStock, lockVOS);
|
||||||
|
}
|
||||||
// 直接保存
|
// 直接保存
|
||||||
wmscomponentPackingService.save(wmsComponentPacking);
|
wmscomponentPackingService.save(wmsComponentPacking);
|
||||||
wmsComponentPackingItemService.saveBatch(wmsComponentPackingItems);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Transactional
|
@Transactional
|
||||||
|
|
|
||||||
|
|
@ -3,13 +3,13 @@ package com.nflg.wms.repository.entity;
|
||||||
import com.baomidou.mybatisplus.annotation.IdType;
|
import com.baomidou.mybatisplus.annotation.IdType;
|
||||||
import com.baomidou.mybatisplus.annotation.TableId;
|
import com.baomidou.mybatisplus.annotation.TableId;
|
||||||
import com.baomidou.mybatisplus.annotation.TableName;
|
import com.baomidou.mybatisplus.annotation.TableName;
|
||||||
|
import jakarta.validation.constraints.NotBlank;
|
||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.Setter;
|
import lombok.Setter;
|
||||||
import lombok.ToString;
|
import lombok.ToString;
|
||||||
import lombok.experimental.Accessors;
|
import lombok.experimental.Accessors;
|
||||||
|
|
||||||
import java.io.Serializable;
|
import java.io.Serializable;
|
||||||
import java.time.LocalDate;
|
|
||||||
import java.time.LocalDateTime;
|
import java.time.LocalDateTime;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -157,6 +157,7 @@ public class WmsComponentPacking implements Serializable {
|
||||||
/**
|
/**
|
||||||
* 所属工厂
|
* 所属工厂
|
||||||
*/
|
*/
|
||||||
|
@NotBlank
|
||||||
private String factoryNo;
|
private String factoryNo;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue