From 9907ec6c7c6e66cc906560a74432f3cae2b4fefc Mon Sep 17 00:00:00 2001 From: HuangHuiKang Date: Tue, 9 Jun 2026 17:57:54 +0800 Subject: [PATCH] =?UTF-8?q?fix:=E4=BF=AE=E6=94=B9=E6=B7=BB=E5=8A=A0?= =?UTF-8?q?=E5=85=A5=E5=BA=93=E5=8D=95=E6=8D=AE=E7=9B=B8=E5=85=B3=E5=AE=A1?= =?UTF-8?q?=E6=89=B9=E6=8E=A5=E5=8F=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../module/erp/enums/ErpAuditStatus.java | 22 +- .../module/erp/enums/ErrorCodeConstants.java | 8 + .../admin/stock/ErpStockInController.java | 244 ++++----- .../vo/in/ErpStockInApproveRecordRespVO.java | 44 ++ .../stock/vo/in/ErpStockInAuditReqVO.java | 22 + .../stock/vo/in/ErpStockInPageReqVO.java | 20 +- .../admin/stock/vo/in/ErpStockInRespVO.java | 51 +- .../stock/vo/in/ErpStockInSaveReqVO.java | 37 +- .../stock/vo/in/ErpStockInSubmitReqVO.java | 21 + .../stock/ErpStockInApproveRecordDO.java | 39 ++ .../dal/dataobject/stock/ErpStockInDO.java | 14 +- .../dataobject/stock/ErpStockInItemDO.java | 12 + .../stock/ErpStockInApproveRecordMapper.java | 23 + .../erp/dal/mysql/stock/ErpStockInMapper.java | 21 +- .../erp/service/stock/ErpStockInService.java | 66 +-- .../service/stock/ErpStockInServiceImpl.java | 464 +++++++++++------- 16 files changed, 716 insertions(+), 392 deletions(-) create mode 100644 yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInApproveRecordRespVO.java create mode 100644 yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInAuditReqVO.java create mode 100644 yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInSubmitReqVO.java create mode 100644 yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInApproveRecordDO.java create mode 100644 yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/mysql/stock/ErpStockInApproveRecordMapper.java diff --git a/yudao-module-erp/yudao-module-erp-api/src/main/java/cn/iocoder/yudao/module/erp/enums/ErpAuditStatus.java b/yudao-module-erp/yudao-module-erp-api/src/main/java/cn/iocoder/yudao/module/erp/enums/ErpAuditStatus.java index ea178cb91..233f21087 100644 --- a/yudao-module-erp/yudao-module-erp-api/src/main/java/cn/iocoder/yudao/module/erp/enums/ErpAuditStatus.java +++ b/yudao-module-erp/yudao-module-erp-api/src/main/java/cn/iocoder/yudao/module/erp/enums/ErpAuditStatus.java @@ -6,36 +6,22 @@ import lombok.RequiredArgsConstructor; import java.util.Arrays; -/** - * ERP 审核状态枚举 - * - * TODO 芋艿:目前只有待审批、已审批两个状态,未来接入工作流后,会丰富下:待提交(草稿)=》已提交(待审核)=》审核通过、审核不通过;另外,工作流需要支持“反审核”,把工作流退回到原点; - * - * @author 芋道源码 - */ @RequiredArgsConstructor @Getter public enum ErpAuditStatus implements IntArrayValuable { - DRAFT(0, "草稿"), // 审核中 - UN_APPROVE(1, "驳回"), // 审核通过 - PROCESS(10, "未审核"), // 审核中 - APPROVE(20, "已审核"); // 审核通过 + DRAFT(0, "待提交"), + UN_APPROVE(1, "已驳回"), + PROCESS(10, "审核中"), + APPROVE(20, "审核通过"); public static final int[] ARRAYS = Arrays.stream(values()).mapToInt(ErpAuditStatus::getStatus).toArray(); - /** - * 状态 - */ private final Integer status; - /** - * 状态名 - */ private final String name; @Override public int[] array() { return ARRAYS; } - } diff --git a/yudao-module-erp/yudao-module-erp-api/src/main/java/cn/iocoder/yudao/module/erp/enums/ErrorCodeConstants.java b/yudao-module-erp/yudao-module-erp-api/src/main/java/cn/iocoder/yudao/module/erp/enums/ErrorCodeConstants.java index 30f4c5977..4352aaf5b 100644 --- a/yudao-module-erp/yudao-module-erp-api/src/main/java/cn/iocoder/yudao/module/erp/enums/ErrorCodeConstants.java +++ b/yudao-module-erp/yudao-module-erp-api/src/main/java/cn/iocoder/yudao/module/erp/enums/ErrorCodeConstants.java @@ -109,6 +109,14 @@ public interface ErrorCodeConstants { ErrorCode STOCK_IN_APPROVE_FAIL = new ErrorCode(1_030_401_003, "审核失败,只有未审核的入库单才能审核"); ErrorCode STOCK_IN_NO_EXISTS = new ErrorCode(1_030_401_004, "生成入库单失败,请重新提交"); ErrorCode STOCK_IN_UPDATE_FAIL_APPROVE = new ErrorCode(1_030_401_005, "其它入库单({})已审核,无法修改"); + ErrorCode STOCK_IN_UPDATE_FAIL_PROCESS = new ErrorCode(1_030_401_006, "其它入库单({})审核中,无法修改"); + ErrorCode STOCK_IN_DELETE_FAIL_PROCESS = new ErrorCode(1_030_401_007, "其它入库单({})审核中,无法删除"); + ErrorCode STOCK_IN_SUBMIT_FAIL_STATUS = new ErrorCode(1_030_401_008, "提交审核失败,只有待提交或已驳回的入库单才能提交"); + ErrorCode STOCK_IN_SUBMIT_FAIL_USER = new ErrorCode(1_030_401_009, "提交审核失败,只有创建人才能提交审核"); + ErrorCode STOCK_IN_SUBMIT_FAIL_AUDIT_USER_EMPTY = new ErrorCode(1_030_401_010, "提交审核失败,请选择审核人"); + ErrorCode STOCK_IN_AUDIT_FAIL_STATUS = new ErrorCode(1_030_401_011, "审核失败,只有审核中的入库单才能审核"); + ErrorCode STOCK_IN_AUDIT_FAIL_USER = new ErrorCode(1_030_401_012, "审核失败,当前用户不是指定审核人"); + ErrorCode STOCK_IN_AUDIT_FAIL_RESULT = new ErrorCode(1_030_401_013, "审核失败,审核结果只支持通过或驳回"); ErrorCode STOCK_ALERADY_IN = new ErrorCode(1_030_401_005, "模具({})已经入库,无法继续操作入库"); ErrorCode STOCK_ALERADY_OUT = new ErrorCode(1_030_401_005, "模具({})已经出库,无法继续操作出库"); diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/ErpStockInController.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/ErpStockInController.java index 71fd2e819..7e662284d 100644 --- a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/ErpStockInController.java +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/ErpStockInController.java @@ -6,17 +6,23 @@ import cn.iocoder.yudao.framework.common.pojo.CommonResult; import cn.iocoder.yudao.framework.common.pojo.PageParam; import cn.iocoder.yudao.framework.common.pojo.PageResult; import cn.iocoder.yudao.framework.common.util.collection.MapUtils; +import cn.iocoder.yudao.framework.common.util.number.NumberUtils; import cn.iocoder.yudao.framework.common.util.object.BeanUtils; import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils; import cn.iocoder.yudao.framework.ratelimiter.core.annotation.RateLimiter; +import cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils; import cn.iocoder.yudao.module.common.dal.dataobject.mold.MoldBrandDO; import cn.iocoder.yudao.module.erp.controller.admin.product.vo.product.ErpProductRespVO; +import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInApproveRecordRespVO; +import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInAuditReqVO; import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInPageReqVO; import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInRespVO; import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInSaveReqVO; +import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInSubmitReqVO; import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.StockInTypeEnum; import cn.iocoder.yudao.module.erp.dal.dataobject.purchase.ErpSupplierDO; import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockDO; +import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInApproveRecordDO; import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInDO; import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInItemDO; import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpWarehouseDO; @@ -46,15 +52,17 @@ import javax.validation.Valid; import java.io.IOException; import java.math.BigDecimal; import java.util.ArrayList; +import java.util.Collections; import java.util.List; import java.util.Map; import java.util.Objects; import java.util.concurrent.TimeUnit; +import java.util.stream.Stream; import static cn.iocoder.yudao.framework.apilog.core.enums.OperateTypeEnum.EXPORT; import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success; import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertList; -import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertMultiMap; +import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertListByFlatMap; import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertSet; @Tag(name = "管理后台 - ERP 其它入库单") @@ -75,12 +83,10 @@ public class ErpStockInController { private ErpWarehouseService warehouseService; @Resource private WarehouseAreaService warehouseAreaService; - @Resource private MoldBrandService moldBrandService; @Resource private MoldService moldService; - @Resource private AdminUserApi adminUserApi; @@ -105,11 +111,36 @@ public class ErpStockInController { @RateLimiter(count = 1, timeUnit = TimeUnit.SECONDS) public CommonResult updateStockInStatus(@RequestParam("id") Long id, @RequestParam("status") Integer status, - @RequestParam(name = "status",required = false) Integer bizType) { - stockInService.updateStockInStatus(id, status,bizType); + @RequestParam(name = "bizType", required = false) Integer bizType) { + stockInService.updateStockInStatus(id, status, bizType); + return success(true); + } + + @PutMapping("/submit") + @Operation(summary = "提交其它入库单审核") + @PreAuthorize("@ss.hasPermission('erp:stock-in:update')") + @RateLimiter(count = 1, timeUnit = TimeUnit.SECONDS) + public CommonResult submitStockInAudit(@Valid @RequestBody ErpStockInSubmitReqVO submitReqVO) { + stockInService.submitStockInAudit(submitReqVO); return success(true); } + @PutMapping("/audit") + @Operation(summary = "审核其它入库单") + @PreAuthorize("@ss.hasPermission('erp:stock-in:update-status')") + @RateLimiter(count = 1, timeUnit = TimeUnit.SECONDS) + public CommonResult auditStockIn(@Valid @RequestBody ErpStockInAuditReqVO auditReqVO) { + stockInService.auditStockIn(auditReqVO); + return success(true); + } + + @GetMapping("/approve-record-list") + @Operation(summary = "获得其它入库单审核记录") + @PreAuthorize("@ss.hasPermission('erp:stock-in:query')") + public CommonResult> getApproveRecordList(@RequestParam("id") Long id) { + return success(buildApproveRecordRespList(stockInService.getStockInApproveRecordList(id))); + } + @DeleteMapping("/delete") @Operation(summary = "删除其它入库单") @Parameter(name = "ids", description = "编号数组", required = true) @@ -128,67 +159,17 @@ public class ErpStockInController { if (stockIn == null) { return success(null); } - List stockInItemList = stockInService.getStockInItemListByInId(id); - Map warehouseMap = warehouseService.getWarehouseMap( - convertSet(stockInItemList, ErpStockInItemDO::getWarehouseId)); - Map areaMap = warehouseAreaService.getWarehouseAreaMap( - convertSet(stockInItemList, ErpStockInItemDO::getAreaId)); - if (Objects.equals(stockIn.getInType(), "模具入库")) { - Map moldMap = moldBrandService.getMoldVOMap( - convertSet(stockInItemList, ErpStockInItemDO::getMoldSetId)); - Map> moldListMap = moldService.getMoldListMapByBrandIds( - convertSet(stockInItemList, ErpStockInItemDO::getMoldSetId)); - return success(BeanUtils.toBean(stockIn, ErpStockInRespVO.class, stockInVO -> { - stockInVO.setItems(convertList(stockInItemList, source -> { - ErpStockInRespVO.Item item = BeanUtils.toBean(source, ErpStockInRespVO.Item.class); - item.setMoldSetId(source.getMoldSetId()); - item.setMoldSetName(source.getMoldSetName()); - ErpStockDO stock = stockService.getStock(source.getMoldSetId(), source.getWarehouseId()); - item.setStockCount(stock != null ? stock.getCount() : BigDecimal.ZERO); - item.setMoldList(moldListMap.getOrDefault(source.getMoldSetId(), new ArrayList<>())); - fillWarehouseInfo(item, source, warehouseMap, areaMap); - MapUtils.findAndThen(moldMap, source.getMoldSetId(), mold -> item.setMoldSetName(mold.getName()) - .setProductName(mold.getName()) - .setProductBarCode(mold.getCode())); - return item; - })); - stockInVO.setMoldSetNames(CollUtil.join(stockInVO.getItems(), ",", ErpStockInRespVO.Item::getMoldSetName)); - stockInVO.setProductNames(stockInVO.getMoldSetNames()); - })); - } else { - Map productMap = productService.getProductVOMap( - convertSet(stockInItemList, ErpStockInItemDO::getProductId)); - return success(BeanUtils.toBean(stockIn, ErpStockInRespVO.class, stockInVO -> - stockInVO.setItems(BeanUtils.toBean(stockInItemList, ErpStockInRespVO.Item.class, item -> { - ErpStockDO stock = stockService.getStock(item.getProductId(), item.getWarehouseId()); - item.setStockCount(stock != null ? stock.getCount() : BigDecimal.ZERO); - if (StringUtils.isBlank(item.getWarehouseName())) { - MapUtils.findAndThen(warehouseMap, item.getWarehouseId(), warehouse -> item.setWarehouseName(warehouse.getName())); - } - if (StringUtils.isBlank(item.getAreaName())) { - MapUtils.findAndThen(areaMap, item.getAreaId(), area -> item.setAreaName(area.getAreaName())); - } - MapUtils.findAndThen(productMap, item.getProductId(), product -> item.setProductName(product.getName()) - .setProductBarCode(product.getBarCode()).setProductUnitName(product.getUnitName())); - })))); - } - + return success(buildStockInRespVO(stockIn, + stockInService.getStockInItemListByInId(id), + stockInService.getStockInApproveRecordList(id))); } @GetMapping("/page") @Operation(summary = "获得其它入库单分页") @PreAuthorize("@ss.hasPermission('erp:stock-in:query')") public CommonResult> getStockInPage(@Valid ErpStockInPageReqVO pageReqVO) { - if(StringUtils.isEmpty(pageReqVO.getInType())){ - List list = new ArrayList<>(); - list.add(StockInTypeEnum.产品入库.getValue()); - list.add(StockInTypeEnum.其他入库.getValue()); - list.add(StockInTypeEnum.原料入库.getValue()); - list.add(StockInTypeEnum.备件入库.getValue()); - pageReqVO.setInTypeList(list); - } - PageResult pageResult = stockInService.getStockInPage(pageReqVO); - return success(buildStockInVOPageResult(pageResult)); + fillPageReqDefault(pageReqVO); + return success(buildStockInVOPageResult(stockInService.getStockInPage(pageReqVO))); } @GetMapping("/export-excel") @@ -196,68 +177,108 @@ public class ErpStockInController { @PreAuthorize("@ss.hasPermission('erp:stock-in:export')") @ApiAccessLog(operateType = EXPORT) public void exportStockInExcel(@Valid ErpStockInPageReqVO pageReqVO, - HttpServletResponse response) throws IOException { + HttpServletResponse response) throws IOException { + fillPageReqDefault(pageReqVO); pageReqVO.setPageSize(PageParam.PAGE_SIZE_NONE); List list = buildStockInVOPageResult(stockInService.getStockInPage(pageReqVO)).getList(); - // 导出 Excel ExcelUtils.write(response, "其它入库单.xls", "数据", ErpStockInRespVO.class, list); } + private void fillPageReqDefault(ErpStockInPageReqVO pageReqVO) { + if (Boolean.TRUE.equals(pageReqVO.getRelatedToMe())) { + pageReqVO.setCurrentUserId(SecurityFrameworkUtils.getLoginUserId()); + } + if (StringUtils.isEmpty(pageReqVO.getInType())) { + List list = new ArrayList<>(); + list.add(StockInTypeEnum.产品入库.getValue()); + list.add(StockInTypeEnum.其他入库.getValue()); + list.add(StockInTypeEnum.原料入库.getValue()); + list.add(StockInTypeEnum.备件入库.getValue()); + pageReqVO.setInTypeList(list); + } + } + private PageResult buildStockInVOPageResult(PageResult pageResult) { if (CollUtil.isEmpty(pageResult.getList())) { return PageResult.empty(pageResult.getTotal()); } - List stockInItemList = stockInService.getStockInItemListByInIds( - convertSet(pageResult.getList(), ErpStockInDO::getId)); - Map> stockInItemMap = convertMultiMap(stockInItemList, ErpStockInItemDO::getInId); - Map productMap = productService.getProductVOMap( - convertSet(stockInItemList, ErpStockInItemDO::getProductId)); - Map supplierMap = supplierService.getSupplierMap( - convertSet(pageResult.getList(), ErpStockInDO::getSupplierId)); + List list = convertList(pageResult.getList(), stockIn -> buildStockInRespVO( + stockIn, stockInService.getStockInItemListByInId(stockIn.getId()), Collections.emptyList())); + return new PageResult<>(list, pageResult.getTotal()); + } + + private ErpStockInRespVO buildStockInRespVO(ErpStockInDO stockIn, List stockInItemList, + List approveRecords) { + ErpStockInRespVO stockInVO = BeanUtils.toBean(stockIn, ErpStockInRespVO.class); Map warehouseMap = warehouseService.getWarehouseMap( convertSet(stockInItemList, ErpStockInItemDO::getWarehouseId)); Map areaMap = warehouseAreaService.getWarehouseAreaMap( convertSet(stockInItemList, ErpStockInItemDO::getAreaId)); - Map userMap = adminUserApi.getUserMap( - convertSet(pageResult.getList(), stockIn -> Long.parseLong(stockIn.getCreator()))); - Map moldMap = moldBrandService.getMoldVOMap( - convertSet(stockInItemList, ErpStockInItemDO::getMoldSetId)); - Map> moldListMap = moldService.getMoldListMapByBrandIds( - convertSet(stockInItemList, ErpStockInItemDO::getMoldSetId)); + Map userMap = adminUserApi.getUserMap(convertListByFlatMap( + Collections.singletonList(stockIn), item -> Stream.of(NumberUtils.parseLong(item.getCreator()), + item.getStockUserId(), item.getAuditUserId()))); + MapUtils.findAndThen(userMap, NumberUtils.parseLong(stockIn.getCreator()), user -> stockInVO.setCreatorName(user.getNickname())); + MapUtils.findAndThen(userMap, stockIn.getStockUserId(), user -> stockInVO.setStockUserName(user.getNickname())); + MapUtils.findAndThen(userMap, stockIn.getAuditUserId(), user -> stockInVO.setAuditUserName(user.getNickname())); - return BeanUtils.toBean(pageResult, ErpStockInRespVO.class, stockIn -> { - if (Objects.equals(stockIn.getInType(), "模具入库")) { - List itemDOS = stockInItemMap.get(stockIn.getId()); - stockIn.setItems(convertList(itemDOS, source -> { - ErpStockInRespVO.Item item = BeanUtils.toBean(source, ErpStockInRespVO.Item.class); - item.setMoldSetId(source.getMoldSetId()); - item.setMoldSetName(source.getMoldSetName()); - item.setMoldList(moldListMap.getOrDefault(source.getMoldSetId(), new ArrayList<>())); - fillWarehouseInfo(item, source, warehouseMap, areaMap); - MapUtils.findAndThen(moldMap, source.getMoldSetId(), mold -> item.setMoldSetName(mold.getName()) - .setProductName(mold.getName()) - .setProductBarCode(mold.getCode())); - return item; - })); - stockIn.setMoldSetNames(CollUtil.join(stockIn.getItems(), ",", ErpStockInRespVO.Item::getMoldSetName)); - stockIn.setProductNames(stockIn.getMoldSetNames()); - } else { - stockIn.setItems(BeanUtils.toBean(stockInItemMap.get(stockIn.getId()), ErpStockInRespVO.Item.class, - item -> MapUtils.findAndThen(productMap, item.getProductId(), product -> item.setProductName(product.getName()) - .setProductBarCode(product.getBarCode()).setProductUnitName(product.getUnitName())))); - stockIn.getItems().forEach(item -> { - if (StringUtils.isBlank(item.getWarehouseName())) { - MapUtils.findAndThen(warehouseMap, item.getWarehouseId(), warehouse -> item.setWarehouseName(warehouse.getName())); - } - if (StringUtils.isBlank(item.getAreaName())) { - MapUtils.findAndThen(areaMap, item.getAreaId(), area -> item.setAreaName(area.getAreaName())); - } + if (Objects.equals(stockIn.getInType(), "模具入库")) { + Map moldMap = moldBrandService.getMoldVOMap( + convertSet(stockInItemList, ErpStockInItemDO::getMoldSetId)); + Map> moldListMap = moldService.getMoldListMapByBrandIds( + convertSet(stockInItemList, ErpStockInItemDO::getMoldSetId)); + stockInVO.setItems(convertList(stockInItemList, source -> { + ErpStockInRespVO.Item item = BeanUtils.toBean(source, ErpStockInRespVO.Item.class); + ErpStockDO stock = stockService.getStock(source.getMoldSetId(), source.getWarehouseId()); + item.setStockCount(stock != null ? stock.getCount() : BigDecimal.ZERO); + item.setMoldList(moldListMap.getOrDefault(source.getMoldSetId(), new ArrayList<>())); + fillWarehouseInfo(item, source, warehouseMap, areaMap); + MapUtils.findAndThen(moldMap, source.getMoldSetId(), mold -> { + item.setMoldSetName(mold.getName()); + item.setProductName(mold.getName()); + item.setProductBarCode(mold.getCode()); }); - stockIn.setProductNames(CollUtil.join(stockIn.getItems(), ",", ErpStockInRespVO.Item::getProductName)); + return item; + })); + stockInVO.setMoldSetNames(CollUtil.join(stockInVO.getItems(), ",", ErpStockInRespVO.Item::getMoldSetName)); + stockInVO.setProductNames(stockInVO.getMoldSetNames()); + } else { + Map productMap = productService.getProductVOMap( + convertSet(stockInItemList, ErpStockInItemDO::getProductId)); + stockInVO.setItems(BeanUtils.toBean(stockInItemList, ErpStockInRespVO.Item.class, item -> { + ErpStockDO stock = stockService.getStock(item.getProductId(), item.getWarehouseId()); + item.setStockCount(stock != null ? stock.getCount() : BigDecimal.ZERO); + if (StringUtils.isBlank(item.getWarehouseName())) { + MapUtils.findAndThen(warehouseMap, item.getWarehouseId(), warehouse -> item.setWarehouseName(warehouse.getName())); + } + if (StringUtils.isBlank(item.getAreaName())) { + MapUtils.findAndThen(areaMap, item.getAreaId(), area -> item.setAreaName(area.getAreaName())); + } + MapUtils.findAndThen(productMap, item.getProductId(), product -> { + item.setProductName(product.getName()); + item.setProductBarCode(product.getBarCode()); + item.setProductUnitName(product.getUnitName()); + }); + })); + stockInVO.setProductNames(CollUtil.join(stockInVO.getItems(), ",", ErpStockInRespVO.Item::getProductName)); + } - } - MapUtils.findAndThen(supplierMap, stockIn.getSupplierId(), supplier -> stockIn.setSupplierName(supplier.getName())); - MapUtils.findAndThen(userMap, Long.parseLong(stockIn.getCreator()), user -> stockIn.setCreatorName(user.getNickname())); + if (stockIn.getSupplierId() != null) { + Map supplierMap = supplierService.getSupplierMap(Collections.singleton(stockIn.getSupplierId())); + MapUtils.findAndThen(supplierMap, stockIn.getSupplierId(), supplier -> stockInVO.setSupplierName(supplier.getName())); + } + stockInVO.setApproveRecords(buildApproveRecordRespList(approveRecords)); + return stockInVO; + } + + private List buildApproveRecordRespList(List records) { + if (CollUtil.isEmpty(records)) { + return new ArrayList<>(); + } + Map userMap = adminUserApi.getUserMap(convertListByFlatMap(records, + record -> Stream.of(NumberUtils.parseLong(record.getCreator()), record.getTargetUserId()))); + return BeanUtils.toBean(records, ErpStockInApproveRecordRespVO.class, record -> { + MapUtils.findAndThen(userMap, NumberUtils.parseLong(record.getCreator()), user -> record.setCreatorName(user.getNickname())); + MapUtils.findAndThen(userMap, record.getTargetUserId(), user -> record.setTargetUserName(user.getNickname())); }); } @@ -281,24 +302,25 @@ public class ErpStockInController { createReqVO.setInType(StockInTypeEnum.生产入库.getValue()); return success(stockInService.createStockIn(createReqVO)); } + @GetMapping("/pageMesStockIn") @Operation(summary = "获得生产入库单分页") @PreAuthorize("@ss.hasPermission('erp:stock-in:query')") public CommonResult> pageMesStockIn(@Valid ErpStockInPageReqVO pageReqVO) { pageReqVO.setInType(StockInTypeEnum.生产入库.getValue()); - PageResult pageResult = stockInService.getStockInPage(pageReqVO); - return success(buildStockInVOPageResult(pageResult)); + fillPageReqDefault(pageReqVO); + return success(buildStockInVOPageResult(stockInService.getStockInPage(pageReqVO))); } + @GetMapping("/pageComponent") @Operation(summary = "获得备件入库单分页") @PreAuthorize("@ss.hasPermission('erp:stock-in:query')") public CommonResult> pageComponent(@Valid ErpStockInPageReqVO pageReqVO) { pageReqVO.setInType(StockInTypeEnum.生产入库.getValue()); - PageResult pageResult = stockInService.getStockInPage(pageReqVO); - return success(buildStockInVOPageResult(pageResult)); + fillPageReqDefault(pageReqVO); + return success(buildStockInVOPageResult(stockInService.getStockInPage(pageReqVO))); } - @PutMapping("/update-mold-status") @Operation(summary = "更新模具入库单的状态") @PreAuthorize("@ss.hasPermission('erp:stock-out:update-status')") diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInApproveRecordRespVO.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInApproveRecordRespVO.java new file mode 100644 index 000000000..0acbf076d --- /dev/null +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInApproveRecordRespVO.java @@ -0,0 +1,44 @@ +package cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in; + +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.Data; + +import java.time.LocalDateTime; + +@Schema(description = "管理后台 - ERP 其它入库单审核记录 Response VO") +@Data +public class ErpStockInApproveRecordRespVO { + + @Schema(description = "编号", example = "1") + private Long id; + + @Schema(description = "入库单编号", example = "1") + private Long stockInId; + + @Schema(description = "操作类型", example = "SUBMIT") + private String actionType; + + @Schema(description = "变更前状态", example = "0") + private Integer fromStatus; + + @Schema(description = "变更后状态", example = "10") + private Integer toStatus; + + @Schema(description = "目标审核人编号", example = "1") + private Long targetUserId; + + @Schema(description = "目标审核人名称", example = "李四") + private String targetUserName; + + @Schema(description = "备注", example = "请审核") + private String remark; + + @Schema(description = "操作人", example = "1") + private String creator; + + @Schema(description = "操作人名称", example = "张三") + private String creatorName; + + @Schema(description = "创建时间") + private LocalDateTime createTime; +} diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInAuditReqVO.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInAuditReqVO.java new file mode 100644 index 000000000..710b36c5a --- /dev/null +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInAuditReqVO.java @@ -0,0 +1,22 @@ +package cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in; + +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.Data; + +import javax.validation.constraints.NotNull; + +@Schema(description = "管理后台 - ERP 其它入库单审核 Request VO") +@Data +public class ErpStockInAuditReqVO { + + @Schema(description = "入库编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "11756") + @NotNull(message = "入库编号不能为空") + private Long id; + + @Schema(description = "审核结果 20-通过 1-驳回", requiredMode = Schema.RequiredMode.REQUIRED, example = "20") + @NotNull(message = "审核结果不能为空") + private Integer status; + + @Schema(description = "审核备注", example = "审核通过") + private String remark; +} diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInPageReqVO.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInPageReqVO.java index 44972ce91..4c69306c2 100644 --- a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInPageReqVO.java +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInPageReqVO.java @@ -34,23 +34,33 @@ public class ErpStockInPageReqVO extends PageParam { @InEnum(ErpAuditStatus.class) private Integer status; - @Schema(description = "入库类型", example = "随便") + @Schema(description = "入库类型", example = "其它入库") private String inType; - @Schema(description = "入库类型", example = "随便") + + @Schema(description = "入库类型集合") private List inTypeList; @Schema(description = "备注", example = "随便") private String remark; - @Schema(description = "创建者") + @Schema(description = "创建人") private String creator; + @Schema(description = "审核人编号", example = "1") + private Long auditUserId; + + @Schema(description = "仅看当前登录人提交和待审批的数据", example = "true") + private Boolean relatedToMe; + + @Schema(hidden = true) + private Long currentUserId; + @Schema(description = "产品编号", example = "1") private Long productId; @Schema(description = "仓库编号", example = "1") private Long warehouseId; - @Schema(description = "id集合导出用") + @Schema(description = "id 集合,导出使用") private String ids; -} \ No newline at end of file +} diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInRespVO.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInRespVO.java index d35ea8ad2..c1914b8ae 100644 --- a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInRespVO.java +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInRespVO.java @@ -1,8 +1,8 @@ package cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in; import cn.iocoder.yudao.framework.excel.core.annotations.DictFormat; -import cn.iocoder.yudao.module.common.dal.dataobject.mold.MoldDO; import cn.iocoder.yudao.framework.excel.core.convert.DictConvert; +import cn.iocoder.yudao.module.common.dal.dataobject.mold.MoldDO; import com.alibaba.excel.annotation.ExcelIgnoreUnannotated; import com.alibaba.excel.annotation.ExcelProperty; import io.swagger.v3.oas.annotations.media.Schema; @@ -29,6 +29,7 @@ public class ErpStockInRespVO { @Schema(description = "供应商编号", example = "3113") private Long supplierId; + @Schema(description = "供应商名称", example = "芋道") @ExcelProperty("供应商名称") private String supplierName; @@ -37,11 +38,26 @@ public class ErpStockInRespVO { @ExcelProperty("入库时间") private LocalDateTime inTime; + @Schema(description = "经办人编号", example = "1888") + private Long stockUserId; + + @Schema(description = "经办人名称", example = "张三") + private String stockUserName; + + @Schema(description = "是否需要审核", example = "true") + private Boolean needAudit; + + @Schema(description = "审核人编号", example = "1888") + private Long auditUserId; + + @Schema(description = "审核人名称", example = "李四") + private String auditUserName; + @Schema(description = "合计数量", requiredMode = Schema.RequiredMode.REQUIRED, example = "15663") @ExcelProperty("合计数量") private BigDecimal totalCount; - @Schema(description = "合计金额,单位:元", requiredMode = Schema.RequiredMode.REQUIRED, example = "24906") + @Schema(description = "合计金额", requiredMode = Schema.RequiredMode.REQUIRED, example = "24906") @ExcelProperty("合计金额") private BigDecimal totalPrice; @@ -54,7 +70,7 @@ public class ErpStockInRespVO { @ExcelProperty("备注") private String remark; - @Schema(description = "入库类型", example = "随便") + @Schema(description = "入库类型", example = "其它入库") @ExcelProperty("入库类型") private String inType; @@ -63,6 +79,7 @@ public class ErpStockInRespVO { @Schema(description = "创建人", example = "芋道") private String creator; + @Schema(description = "创建人名称", example = "芋道") private String creatorName; @@ -80,6 +97,9 @@ public class ErpStockInRespVO { @Schema(description = "模具组名称") private String moldSetNames; + @Schema(description = "审核记录") + private List approveRecords; + @Data public static class Item { @@ -101,22 +121,31 @@ public class ErpStockInRespVO { @Schema(description = "产品编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "3113") private Long productId; - @Schema(description = "产品单价", requiredMode = Schema.RequiredMode.REQUIRED, example = "100.00") + @Schema(description = "产品单价", example = "100.00") private BigDecimal productPrice; @Schema(description = "产品数量", requiredMode = Schema.RequiredMode.REQUIRED, example = "100.00") private BigDecimal count; + @Schema(description = "包装方案 ID", example = "1") + private Long packagingSchemeId; + + @Schema(description = "单位输入方式", example = "包") + private String inputUnitType; + + @Schema(description = "录入数量", example = "10.00") + private BigDecimal inputCount; + @Schema(description = "备注", example = "随便") private String remark; - // ========== 关联字段 ========== - - @Schema(description = "产品名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "巧克力") + @Schema(description = "产品名称", example = "巧克力") private String productName; - @Schema(description = "产品条码", requiredMode = Schema.RequiredMode.REQUIRED, example = "A9985") + + @Schema(description = "产品条码", example = "A9985") private String productBarCode; - @Schema(description = "产品单位名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "盒") + + @Schema(description = "产品单位名称", example = "盒") private String productUnitName; @Schema(description = "仓库名称", example = "A仓") @@ -125,12 +154,10 @@ public class ErpStockInRespVO { @Schema(description = "库区名称", example = "A-01") private String areaName; - @Schema(description = "库存数量", requiredMode = Schema.RequiredMode.REQUIRED, example = "100.00") + @Schema(description = "库存数量", example = "100.00") private BigDecimal stockCount; @Schema(description = "子模具详情") private List moldList; - } - } diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInSaveReqVO.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInSaveReqVO.java index 66029415a..794323a8d 100644 --- a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInSaveReqVO.java +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInSaveReqVO.java @@ -1,6 +1,5 @@ package cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in; -import cn.iocoder.yudao.module.erp.dal.dataobject.product.ErpProductDO; import io.swagger.v3.oas.annotations.media.Schema; import lombok.Data; @@ -15,7 +14,7 @@ import java.util.List; @Data public class ErpStockInSaveReqVO { - @Schema(description = "入库编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "11756") + @Schema(description = "入库编号", example = "11756") private Long id; @Schema(description = "供应商编号", example = "3113") @@ -25,9 +24,18 @@ public class ErpStockInSaveReqVO { @NotNull(message = "入库时间不能为空") private LocalDateTime inTime; - @Schema(description = "入库类型", example = "随便") + @Schema(description = "入库类型", example = "其它入库") private String inType; + @Schema(description = "经办人编号", example = "1888") + private Long stockUserId; + + @Schema(description = "是否需要审核", example = "true") + private Boolean needAudit; + + @Schema(description = "审核人编号", example = "1888") + private Long auditUserId; + @Schema(description = "备注", example = "随便") private String remark; @@ -39,29 +47,26 @@ public class ErpStockInSaveReqVO { @Valid private List items; - @Schema(description = "仓库编号", example = "3113") private Long warehouseId; - @Data public static class Item { - @Schema(description = "????????????????", example = "11756") + @Schema(description = "子项 id", example = "11756") private Long id; - @Schema(description = "??? ID?????????", example = "101") + @Schema(description = "模具组 id", example = "101") private Long moldSetId; - @Schema(description = "仓库编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "3113") -// @NotNull(message = "仓库编号不能为空") + @Schema(description = "仓库编号", example = "3113") private Long warehouseId; @Schema(description = "库区编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "3113") @NotNull(message = "库区编号不能为空") private Long areaId; - @Schema(description = "产品编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "3113") + @Schema(description = "产品编号", example = "3113") private Long productId; @Schema(description = "产品单价", example = "100.00") @@ -71,11 +76,19 @@ public class ErpStockInSaveReqVO { @NotNull(message = "产品数量不能为空") private BigDecimal count; + @Schema(description = "包装方案 ID", example = "1") + private Long packagingSchemeId; + + @Schema(description = "单位输入方式", example = "包") + private String inputUnitType; + + @Schema(description = "录入数量", example = "10.00") + private BigDecimal inputCount; + @Schema(description = "备注", example = "随便") private String remark; - @Schema(description = "设备id", example = "100.00") + @Schema(description = "设备 id", example = "100") private Long deviceId; } - } diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInSubmitReqVO.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInSubmitReqVO.java new file mode 100644 index 000000000..cb33ae648 --- /dev/null +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/controller/admin/stock/vo/in/ErpStockInSubmitReqVO.java @@ -0,0 +1,21 @@ +package cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in; + +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.Data; + +import javax.validation.constraints.NotNull; + +@Schema(description = "管理后台 - ERP 其它入库单提交审核 Request VO") +@Data +public class ErpStockInSubmitReqVO { + + @Schema(description = "入库编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "11756") + @NotNull(message = "入库编号不能为空") + private Long id; + + @Schema(description = "审核人编号", example = "1888") + private Long auditUserId; + + @Schema(description = "提交备注", example = "请审核") + private String remark; +} diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInApproveRecordDO.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInApproveRecordDO.java new file mode 100644 index 000000000..e4bca8c91 --- /dev/null +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInApproveRecordDO.java @@ -0,0 +1,39 @@ +package cn.iocoder.yudao.module.erp.dal.dataobject.stock; + +import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO; +import com.baomidou.mybatisplus.annotation.KeySequence; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.EqualsAndHashCode; +import lombok.NoArgsConstructor; +import lombok.ToString; + +@TableName("erp_stock_in_approve_record") +@KeySequence("erp_stock_in_approve_record_seq") +@Data +@EqualsAndHashCode(callSuper = true) +@ToString(callSuper = true) +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class ErpStockInApproveRecordDO extends BaseDO { + + @TableId + private Long id; + + private Long stockInId; + + private String actionType; + + private Integer fromStatus; + + private Integer toStatus; + + private Long targetUserId; + + private String remark; + +} diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInDO.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInDO.java index d3fae3243..45ef22015 100644 --- a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInDO.java +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInDO.java @@ -44,6 +44,10 @@ public class ErpStockInDO extends BaseDO { * 入库时间 */ private LocalDateTime inTime; + /** + * 经办人编号 + */ + private Long stockUserId; /** * 合计数量 */ @@ -58,6 +62,14 @@ public class ErpStockInDO extends BaseDO { * 枚举 {@link cn.iocoder.yudao.module.erp.enums.ErpAuditStatus} */ private Integer status; + /** + * 是否需要审核 + */ + private Boolean needAudit; + /** + * 审核人编号 + */ + private Long auditUserId; /** * 备注 */ @@ -71,4 +83,4 @@ public class ErpStockInDO extends BaseDO { */ private String fileUrl; -} \ No newline at end of file +} diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInItemDO.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInItemDO.java index 69d8de4a7..b1f859d48 100644 --- a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInItemDO.java +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/dataobject/stock/ErpStockInItemDO.java @@ -66,6 +66,18 @@ public class ErpStockInItemDO extends BaseDO { * 产品数量 */ private BigDecimal count; + /** + * 包装方案 ID + */ + private Long packagingSchemeId; + /** + * 单位输入方式(托/包/个) + */ + private String inputUnitType; + /** + * 录入数量 + */ + private BigDecimal inputCount; /** * 合计金额,单位:元 */ diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/mysql/stock/ErpStockInApproveRecordMapper.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/mysql/stock/ErpStockInApproveRecordMapper.java new file mode 100644 index 000000000..62668b516 --- /dev/null +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/mysql/stock/ErpStockInApproveRecordMapper.java @@ -0,0 +1,23 @@ +package cn.iocoder.yudao.module.erp.dal.mysql.stock; + +import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX; +import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX; +import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInApproveRecordDO; +import org.apache.ibatis.annotations.Mapper; + +import java.util.List; + +@Mapper +public interface ErpStockInApproveRecordMapper extends BaseMapperX { + + default List selectListByStockInId(Long stockInId) { + return selectList(new LambdaQueryWrapperX() + .eq(ErpStockInApproveRecordDO::getStockInId, stockInId) + .orderByAsc(ErpStockInApproveRecordDO::getId)); + } + + default int deleteByStockInId(Long stockInId) { + return delete(ErpStockInApproveRecordDO::getStockInId, stockInId); + } + +} diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/mysql/stock/ErpStockInMapper.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/mysql/stock/ErpStockInMapper.java index c47b360e8..a7ce57747 100644 --- a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/mysql/stock/ErpStockInMapper.java +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/dal/mysql/stock/ErpStockInMapper.java @@ -14,11 +14,6 @@ import java.util.Arrays; import java.util.List; import java.util.stream.Collectors; -/** - * ERP 其它入库单 Mapper - * - * @author 芋道源码 - */ @Mapper public interface ErpStockInMapper extends BaseMapperX { @@ -32,15 +27,17 @@ public interface ErpStockInMapper extends BaseMapperX { .inIfPresent(ErpStockInDO::getInType, reqVO.getInTypeList()) .likeIfPresent(ErpStockInDO::getRemark, reqVO.getRemark()) .eqIfPresent(ErpStockInDO::getCreator, reqVO.getCreator()) + .eqIfPresent(ErpStockInDO::getAuditUserId, reqVO.getAuditUserId()) .orderByDesc(ErpStockInDO::getId); + query.and(Boolean.TRUE.equals(reqVO.getRelatedToMe()) && reqVO.getCurrentUserId() != null, + w -> w.eq(ErpStockInDO::getCreator, String.valueOf(reqVO.getCurrentUserId())) + .or().eq(ErpStockInDO::getAuditUserId, reqVO.getCurrentUserId())); if (reqVO.getWarehouseId() != null || reqVO.getProductId() != null) { query.leftJoin(ErpStockInItemDO.class, ErpStockInItemDO::getInId, ErpStockInDO::getId) .eq(reqVO.getWarehouseId() != null, ErpStockInItemDO::getWarehouseId, reqVO.getWarehouseId()) .eq(reqVO.getProductId() != null, ErpStockInItemDO::getProductId, reqVO.getProductId()) - .groupBy(ErpStockInDO::getId); // 避免 1 对多查询,产生相同的 1 + .groupBy(ErpStockInDO::getId); } - - // 单独处理 ids 条件 if (StringUtils.isNotBlank(reqVO.getIds())) { List idList = Arrays.stream(reqVO.getIds().split(",")) .map(String::trim) @@ -48,19 +45,17 @@ public interface ErpStockInMapper extends BaseMapperX { .collect(Collectors.toList()); query.in(ErpStockInDO::getId, idList); } - - - return selectJoinPage(reqVO, ErpStockInDO.class, query); } default int updateByIdAndStatus(Long id, Integer status, ErpStockInDO updateObj) { return update(updateObj, new LambdaUpdateWrapper() - .eq(ErpStockInDO::getId, id).eq(ErpStockInDO::getStatus, status)); + .eq(ErpStockInDO::getId, id) + .eq(ErpStockInDO::getStatus, status)); } default ErpStockInDO selectByNo(String no) { return selectOne(ErpStockInDO::getNo, no); } -} \ No newline at end of file +} diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/service/stock/ErpStockInService.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/service/stock/ErpStockInService.java index cd41b5b91..a045fd403 100644 --- a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/service/stock/ErpStockInService.java +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/service/stock/ErpStockInService.java @@ -1,8 +1,11 @@ package cn.iocoder.yudao.module.erp.service.stock; import cn.iocoder.yudao.framework.common.pojo.PageResult; +import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInAuditReqVO; import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInPageReqVO; import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInSaveReqVO; +import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInSubmitReqVO; +import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInApproveRecordDO; import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInDO; import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInItemDO; @@ -10,76 +13,29 @@ import javax.validation.Valid; import java.util.Collection; import java.util.List; -/** - * ERP 其它入库单 Service 接口 - * - * @author 芋道源码 - */ public interface ErpStockInService { - /** - * 创建其它入库单 - * - * @param createReqVO 创建信息 - * @return 编号 - */ Long createStockIn(@Valid ErpStockInSaveReqVO createReqVO); - /** - * 更新其它入库单 - * - * @param updateReqVO 更新信息 - */ void updateStockIn(@Valid ErpStockInSaveReqVO updateReqVO); - /** - * 更新其它入库单的状态 - * - * @param id 编号 - * @param status 状态 - */ - void updateStockInStatus(Long id, Integer status,Integer bizType); + void updateStockInStatus(Long id, Integer status, Integer bizType); + + void submitStockInAudit(@Valid ErpStockInSubmitReqVO submitReqVO); + + void auditStockIn(@Valid ErpStockInAuditReqVO auditReqVO); - /** - * 删除其它入库单 - * - * @param ids 编号数组 - */ void deleteStockIn(List ids); - /** - * 获得其它入库单 - * - * @param id 编号 - * @return 其它入库单 - */ ErpStockInDO getStockIn(Long id); - /** - * 获得其它入库单分页 - * - * @param pageReqVO 分页查询 - * @return 其它入库单分页 - */ PageResult getStockInPage(ErpStockInPageReqVO pageReqVO); - // ==================== 入库项 ==================== - - /** - * 获得其它入库单项列表 - * - * @param inId 入库编号 - * @return 其它入库单项列表 - */ List getStockInItemListByInId(Long inId); - /** - * 获得其它入库单项 List - * - * @param inIds 入库编号数组 - * @return 其它入库单项 List - */ List getStockInItemListByInIds(Collection inIds); + List getStockInApproveRecordList(Long stockInId); + void updateMoldStatus(Long id, Integer status); -} \ No newline at end of file +} diff --git a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/service/stock/ErpStockInServiceImpl.java b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/service/stock/ErpStockInServiceImpl.java index 0f1d4d077..f22987be1 100644 --- a/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/service/stock/ErpStockInServiceImpl.java +++ b/yudao-module-erp/yudao-module-erp-biz/src/main/java/cn/iocoder/yudao/module/erp/service/stock/ErpStockInServiceImpl.java @@ -3,19 +3,23 @@ package cn.iocoder.yudao.module.erp.service.stock; import cn.hutool.core.collection.CollUtil; import cn.iocoder.yudao.framework.common.pojo.PageResult; import cn.iocoder.yudao.framework.common.util.number.MoneyUtils; +import cn.iocoder.yudao.framework.common.util.number.NumberUtils; import cn.iocoder.yudao.framework.common.util.object.BeanUtils; +import cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils; import cn.iocoder.yudao.module.common.controller.admin.mold.vo.MoldBrandSaveReqVO; import cn.iocoder.yudao.module.common.dal.dataobject.mold.MoldBrandDO; +import cn.iocoder.yudao.module.common.enums.MoldBrandStatusEnum; +import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInAuditReqVO; import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInPageReqVO; import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInSaveReqVO; -import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.out.ErpStockOutSaveReqVO; +import cn.iocoder.yudao.module.erp.controller.admin.stock.vo.in.ErpStockInSubmitReqVO; import cn.iocoder.yudao.module.erp.dal.dataobject.product.ErpProductDO; -import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockDO; +import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInApproveRecordDO; import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInDO; import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockInItemDO; -import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpStockOutDO; import cn.iocoder.yudao.module.erp.dal.dataobject.stock.ErpWarehouseDO; import cn.iocoder.yudao.module.erp.dal.dataobject.warehousearea.WarehouseAreaDO; +import cn.iocoder.yudao.module.erp.dal.mysql.stock.ErpStockInApproveRecordMapper; import cn.iocoder.yudao.module.erp.dal.mysql.stock.ErpStockInItemMapper; import cn.iocoder.yudao.module.erp.dal.mysql.stock.ErpStockInMapper; import cn.iocoder.yudao.module.erp.dal.mysql.stock.ErpStockMapper; @@ -27,40 +31,62 @@ import cn.iocoder.yudao.module.erp.service.product.ErpProductService; import cn.iocoder.yudao.module.erp.service.purchase.ErpSupplierService; import cn.iocoder.yudao.module.erp.service.stock.bo.ErpStockRecordCreateReqBO; import cn.iocoder.yudao.module.erp.service.warehousearea.WarehouseAreaService; -import com.baomidou.mybatisplus.core.toolkit.Wrappers; +import cn.iocoder.yudao.module.system.api.user.AdminUserApi; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import org.springframework.validation.annotation.Validated; import javax.annotation.Resource; import java.math.BigDecimal; -import java.util.*; +import java.util.Collection; +import java.util.Collections; +import java.util.List; +import java.util.Map; +import java.util.Objects; import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception; -import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.*; -import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.*; - -// TODO 芋艿:记录操作日志 -/** - * ERP 其它入库单 Service 实现类 - * - * @author 芋道源码 - */ +import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertList; +import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertMap; +import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertSet; +import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.diffList; +import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.getSumValue; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_ALERADY_IN; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_APPROVE_FAIL; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_AUDIT_FAIL_RESULT; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_AUDIT_FAIL_STATUS; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_AUDIT_FAIL_USER; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_DELETE_FAIL_APPROVE; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_DELETE_FAIL_PROCESS; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_NOT_EXISTS; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_NO_EXISTS; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_PROCESS_FAIL; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_SUBMIT_FAIL_AUDIT_USER_EMPTY; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_SUBMIT_FAIL_STATUS; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_SUBMIT_FAIL_USER; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_UPDATE_FAIL_APPROVE; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.STOCK_IN_UPDATE_FAIL_PROCESS; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.WAREHOUSE_AREA_NOT_EXISTS; +import static cn.iocoder.yudao.module.erp.enums.ErrorCodeConstants.WAREHOUSE_LOCATION_WAREHOUSE_AREA_NOT_MATCH; + @Service @Validated public class ErpStockInServiceImpl implements ErpStockInService { + private static final String ACTION_SUBMIT = "SUBMIT"; + private static final String ACTION_APPROVE = "APPROVE"; + private static final String ACTION_REJECT = "REJECT"; + private static final String ACTION_AUTO_APPROVE = "AUTO_APPROVE"; + @Resource private ErpStockInMapper stockInMapper; @Resource private ErpStockInItemMapper stockInItemMapper; - + @Resource + private ErpStockInApproveRecordMapper stockInApproveRecordMapper; @Resource private ErpStockMapper erpStockMapper; - @Resource private ErpNoRedisDAO noRedisDAO; - @Resource private ErpProductService productService; @Resource @@ -73,154 +99,325 @@ public class ErpStockInServiceImpl implements ErpStockInService { private MoldBrandService moldBrandService; @Resource private WarehouseAreaService warehouseAreaService; + @Resource + private AdminUserApi adminUserApi; @Override @Transactional(rollbackFor = Exception.class) public Long createStockIn(ErpStockInSaveReqVO createReqVO) { - // 1.1 校验入库项的有效性 - List stockInItems = validateStockInItems(createReqVO.getItems(),createReqVO.getInType()); - // 1.2 校验供应商 - //supplierService.validateSupplier(createReqVO.getSupplierId()); - // 1.3 生成入库单号,并校验唯一性 + List stockInItems = validateStockInItems(createReqVO.getItems(), createReqVO.getInType()); + if (createReqVO.getStockUserId() != null) { + adminUserApi.validateUser(createReqVO.getStockUserId()); + } + if (createReqVO.getAuditUserId() != null) { + adminUserApi.validateUser(createReqVO.getAuditUserId()); + } String no = noRedisDAO.generate(ErpNoRedisDAO.STOCK_IN_NO_PREFIX); if (stockInMapper.selectByNo(no) != null) { throw exception(STOCK_IN_NO_EXISTS); } - // 2.1 插入入库单 + boolean needAudit = !Boolean.FALSE.equals(createReqVO.getNeedAudit()); + Integer status = needAudit ? ErpAuditStatus.DRAFT.getStatus() : ErpAuditStatus.APPROVE.getStatus(); ErpStockInDO stockIn = BeanUtils.toBean(createReqVO, ErpStockInDO.class, in -> in - .setNo(no).setStatus(ErpAuditStatus.PROCESS.getStatus()) + .setNo(no) + .setNeedAudit(needAudit) + .setStatus(status) .setTotalCount(getSumValue(stockInItems, ErpStockInItemDO::getCount, BigDecimal::add)) .setTotalPrice(getSumValue(stockInItems, ErpStockInItemDO::getTotalPrice, BigDecimal::add, BigDecimal.ZERO))); stockInMapper.insert(stockIn); - // 2.2 插入入库单项 - stockInItems.forEach(o -> { - o.setInId(stockIn.getId()); - o.setCount(o.getCount()); - }); + stockInItems.forEach(item -> item.setInId(stockIn.getId())); stockInItemMapper.insertBatch(stockInItems); -// for (ErpStockInItemDO item : stockInItems) { -// MoldDO moldDO = moldService.getMold(item.getProductId()); -// moldDO.setStatus(ErpAuditStatus.PROCESS.getStatus()); // 未审核 -// moldService.updateMold(BeanUtils.toBean(moldDO, MoldSaveReqVO.class)); -// } + + if (!needAudit) { + applyStockInEffect(stockIn, stockInItems, null); + createApproveRecord(stockIn.getId(), ACTION_AUTO_APPROVE, null, + ErpAuditStatus.APPROVE.getStatus(), null, "无需审核,系统自动入库"); + } return stockIn.getId(); } @Override @Transactional(rollbackFor = Exception.class) public void updateStockIn(ErpStockInSaveReqVO updateReqVO) { - // 1.1 校验存在 ErpStockInDO stockIn = validateStockInExists(updateReqVO.getId()); if (ErpAuditStatus.APPROVE.getStatus().equals(stockIn.getStatus())) { throw exception(STOCK_IN_UPDATE_FAIL_APPROVE, stockIn.getNo()); } - // 1.2 校验供应商 - //supplierService.validateSupplier(updateReqVO.getSupplierId()); - // 1.3 校验入库项的有效性 - List stockInItems = validateStockInItems(updateReqVO.getItems(),updateReqVO.getInType()); - - // 2.1 更新入库单 + if (ErpAuditStatus.PROCESS.getStatus().equals(stockIn.getStatus())) { + throw exception(STOCK_IN_UPDATE_FAIL_PROCESS, stockIn.getNo()); + } + if (updateReqVO.getStockUserId() != null) { + adminUserApi.validateUser(updateReqVO.getStockUserId()); + } + if (updateReqVO.getAuditUserId() != null) { + adminUserApi.validateUser(updateReqVO.getAuditUserId()); + } + List stockInItems = validateStockInItems(updateReqVO.getItems(), updateReqVO.getInType()); + boolean needAudit = !Boolean.FALSE.equals(updateReqVO.getNeedAudit()); ErpStockInDO updateObj = BeanUtils.toBean(updateReqVO, ErpStockInDO.class, in -> in + .setNeedAudit(needAudit) .setTotalCount(getSumValue(stockInItems, ErpStockInItemDO::getCount, BigDecimal::add)) - .setTotalPrice(getSumValue(stockInItems, ErpStockInItemDO::getTotalPrice, BigDecimal::add))); + .setTotalPrice(getSumValue(stockInItems, ErpStockInItemDO::getTotalPrice, BigDecimal::add, BigDecimal.ZERO))); stockInMapper.updateById(updateObj); - // 2.2 更新入库单项 updateStockInItemList(updateReqVO.getId(), stockInItems); - - } @Override @Transactional(rollbackFor = Exception.class) - public void updateStockInStatus(Long id, Integer status,Integer bizType) { - boolean approve = ErpAuditStatus.APPROVE.getStatus().equals(status); + public void updateStockInStatus(Long id, Integer status, Integer bizType) { ErpStockInDO stockIn = validateStockInExists(id); - if (stockIn.getStatus().equals(status)) { + boolean approve = ErpAuditStatus.APPROVE.getStatus().equals(status); + if (approve) { + if (!ErpAuditStatus.PROCESS.getStatus().equals(stockIn.getStatus())) { + throw exception(STOCK_IN_APPROVE_FAIL); + } + } else { + if (!ErpAuditStatus.APPROVE.getStatus().equals(stockIn.getStatus())) { + throw exception(STOCK_IN_PROCESS_FAIL); + } + } + int updateCount = stockInMapper.updateByIdAndStatus(id, stockIn.getStatus(), new ErpStockInDO().setStatus(status)); + if (updateCount == 0) { throw exception(approve ? STOCK_IN_APPROVE_FAIL : STOCK_IN_PROCESS_FAIL); } + List stockInItems = stockInItemMapper.selectListByInId(id); + if (approve) { + applyStockInEffect(stockIn, stockInItems, bizType); + } else { + cancelStockInEffect(stockIn, stockInItems, bizType); + } + } - int updateCount = stockInMapper.updateByIdAndStatus(id, stockIn.getStatus(), - new ErpStockInDO().setStatus(status)); + @Override + @Transactional(rollbackFor = Exception.class) + public void submitStockInAudit(ErpStockInSubmitReqVO submitReqVO) { + ErpStockInDO stockIn = validateStockInExists(submitReqVO.getId()); + Long loginUserId = SecurityFrameworkUtils.getLoginUserId(); + if (!Objects.equals(NumberUtils.parseLong(stockIn.getCreator()), loginUserId)) { + throw exception(STOCK_IN_SUBMIT_FAIL_USER); + } + if (!ErpAuditStatus.DRAFT.getStatus().equals(stockIn.getStatus()) + && !ErpAuditStatus.UN_APPROVE.getStatus().equals(stockIn.getStatus())) { + throw exception(STOCK_IN_SUBMIT_FAIL_STATUS); + } + Long auditUserId = submitReqVO.getAuditUserId() != null ? submitReqVO.getAuditUserId() : stockIn.getAuditUserId(); + if (auditUserId == null) { + throw exception(STOCK_IN_SUBMIT_FAIL_AUDIT_USER_EMPTY); + } + adminUserApi.validateUser(auditUserId); + Integer fromStatus = stockIn.getStatus(); + ErpStockInDO updateObj = new ErpStockInDO() + .setAuditUserId(auditUserId) + .setNeedAudit(true) + .setStatus(ErpAuditStatus.PROCESS.getStatus()); + int updateCount = stockInMapper.updateByIdAndStatus(stockIn.getId(), fromStatus, updateObj); if (updateCount == 0) { - throw exception(approve ? STOCK_IN_APPROVE_FAIL : STOCK_IN_PROCESS_FAIL); + throw exception(STOCK_IN_SUBMIT_FAIL_STATUS); + } + createApproveRecord(stockIn.getId(), ACTION_SUBMIT, fromStatus, + ErpAuditStatus.PROCESS.getStatus(), auditUserId, submitReqVO.getRemark()); + } + + @Override + @Transactional(rollbackFor = Exception.class) + public void auditStockIn(ErpStockInAuditReqVO auditReqVO) { + ErpStockInDO stockIn = validateStockInExists(auditReqVO.getId()); + if (!ErpAuditStatus.PROCESS.getStatus().equals(stockIn.getStatus())) { + throw exception(STOCK_IN_AUDIT_FAIL_STATUS); + } + Long loginUserId = SecurityFrameworkUtils.getLoginUserId(); + if (!Objects.equals(stockIn.getAuditUserId(), loginUserId)) { + throw exception(STOCK_IN_AUDIT_FAIL_USER); + } + if (!ErpAuditStatus.APPROVE.getStatus().equals(auditReqVO.getStatus()) + && !ErpAuditStatus.UN_APPROVE.getStatus().equals(auditReqVO.getStatus())) { + throw exception(STOCK_IN_AUDIT_FAIL_RESULT); } - List stockInItems = stockInItemMapper.selectListByInId(id); + Integer fromStatus = stockIn.getStatus(); + int updateCount = stockInMapper.updateByIdAndStatus(stockIn.getId(), fromStatus, + new ErpStockInDO().setStatus(auditReqVO.getStatus())); + if (updateCount == 0) { + throw exception(STOCK_IN_AUDIT_FAIL_STATUS); + } + + List stockInItems = stockInItemMapper.selectListByInId(stockIn.getId()); + if (ErpAuditStatus.APPROVE.getStatus().equals(auditReqVO.getStatus())) { + applyStockInEffect(stockIn, stockInItems, null); + } + Long targetUserId = NumberUtils.parseLong(stockIn.getCreator()); + createApproveRecord(stockIn.getId(), ErpAuditStatus.APPROVE.getStatus().equals(auditReqVO.getStatus()) + ? ACTION_APPROVE : ACTION_REJECT, + fromStatus, auditReqVO.getStatus(), targetUserId, auditReqVO.getRemark()); + } + + @Override + @Transactional(rollbackFor = Exception.class) + public void deleteStockIn(List ids) { + List stockIns = stockInMapper.selectBatchIds(ids); + if (CollUtil.isEmpty(stockIns)) { + return; + } + stockIns.forEach(stockIn -> { + if (ErpAuditStatus.APPROVE.getStatus().equals(stockIn.getStatus())) { + throw exception(STOCK_IN_DELETE_FAIL_APPROVE, stockIn.getNo()); + } + if (ErpAuditStatus.PROCESS.getStatus().equals(stockIn.getStatus())) { + throw exception(STOCK_IN_DELETE_FAIL_PROCESS, stockIn.getNo()); + } + }); + stockIns.forEach(stockIn -> { + stockInMapper.deleteById(stockIn.getId()); + stockInItemMapper.deleteByInId(stockIn.getId()); + stockInApproveRecordMapper.deleteByStockInId(stockIn.getId()); + }); + } + + private ErpStockInDO validateStockInExists(Long id) { + ErpStockInDO stockIn = stockInMapper.selectById(id); + if (stockIn == null) { + throw exception(STOCK_IN_NOT_EXISTS); + } + return stockIn; + } + + @Override + public ErpStockInDO getStockIn(Long id) { + return stockInMapper.selectById(id); + } + + @Override + public PageResult getStockInPage(ErpStockInPageReqVO pageReqVO) { + return stockInMapper.selectPage(pageReqVO); + } + + @Override + public List getStockInItemListByInId(Long inId) { + return stockInItemMapper.selectListByInId(inId); + } + + @Override + public List getStockInItemListByInIds(Collection inIds) { + if (CollUtil.isEmpty(inIds)) { + return Collections.emptyList(); + } + return stockInItemMapper.selectListByInIds(inIds); + } + + @Override + public List getStockInApproveRecordList(Long stockInId) { + return stockInApproveRecordMapper.selectListByStockInId(stockInId); + } + + @Override + public void updateMoldStatus(Long id, Integer status) { + ErpStockInDO stockIn = validateStockInExists(id); + stockIn.setStatus(status); + stockInMapper.updateById(stockIn); + } + + private void applyStockInEffect(ErpStockInDO stockIn, List stockInItems, Integer bizType) { + operateStockInEffect(stockIn, stockInItems, true, bizType); + } + + private void cancelStockInEffect(ErpStockInDO stockIn, List stockInItems, Integer bizType) { + operateStockInEffect(stockIn, stockInItems, false, bizType); + } + + private void operateStockInEffect(ErpStockInDO stockIn, List stockInItems, + boolean approve, Integer bizType) { stockInItems.forEach(stockInItem -> { BigDecimal count = approve ? stockInItem.getCount() : stockInItem.getCount().negate(); - if (Objects.equals(stockIn.getInType(), "模具入库")) { + if (Objects.equals(stockIn.getInType(), "妯″叿鍏ュ簱")) { MoldBrandDO moldDO = moldBrandService.getMoldBrand(stockInItem.getMoldSetId()); + Integer recordBizType = bizType != null ? bizType + : (approve ? ErpStockRecordBizTypeEnum.OTHER_IN.getType() + : ErpStockRecordBizTypeEnum.OTHER_IN_CANCEL.getType()); stockRecordService.createStockRecord(new ErpStockRecordCreateReqBO( stockInItem.getProductId(), moldDO.getId(), stockInItem.getWarehouseId(), count, - ErpStockRecordBizTypeEnum.OTHER_IN.getType(), stockInItem.getInId(), stockInItem.getId(), stockIn.getNo(), stockIn.getInTime())); + recordBizType, stockInItem.getInId(), stockInItem.getId(), stockIn.getNo(), stockIn.getInTime())); + if (approve && itemNeedUpdateMoldStatus(moldDO)) { + moldDO.setStatus(MoldBrandStatusEnum.STANDBY.getStatus()); + moldBrandService.updateMoldBrand(BeanUtils.toBean(moldDO, MoldBrandSaveReqVO.class)); + } } else { ErpProductDO productDO = productService.getProduct(stockInItem.getProductId()); + Integer recordBizType = bizType != null ? bizType + : (approve ? ErpStockRecordBizTypeEnum.getTypeByName(stockIn.getInType()) + : ErpStockRecordBizTypeEnum.getTypeByName(stockIn.getInType(), 10)); stockRecordService.createStockRecord(new ErpStockRecordCreateReqBO( stockInItem.getProductId(), productDO.getCategoryId(), stockInItem.getWarehouseId(), count, - ErpStockRecordBizTypeEnum.getTypeByName(stockIn.getInType(), status), stockInItem.getInId(), stockInItem.getId(), stockIn.getNo(), stockIn.getInTime())); + recordBizType, stockInItem.getInId(), stockInItem.getId(), stockIn.getNo(), stockIn.getInTime())); } }); + } - if (Objects.equals(stockIn.getInType(), "模具入库")) { - for (ErpStockInItemDO item : stockInItems) { - if (item.getMoldSetId() != null) { - MoldBrandDO moldDO = moldBrandService.getMoldBrand(item.getMoldSetId()); - if (Objects.equals(moldDO.getStatus(), 1)) { - throw exception(STOCK_ALERADY_IN, moldDO.getCode() + "-" + moldDO.getName()); - } - moldDO.setStatus(1); - moldBrandService.updateMoldBrand(BeanUtils.toBean(moldDO, MoldBrandSaveReqVO.class)); - } - } + private boolean itemNeedUpdateMoldStatus(MoldBrandDO moldDO) { + if (Objects.equals(moldDO.getStatus(), MoldBrandStatusEnum.STANDBY.getStatus())) { + throw exception(STOCK_ALERADY_IN, moldDO.getCode() + "-" + moldDO.getName()); } + return true; + } + + private void createApproveRecord(Long stockInId, String actionType, Integer fromStatus, + Integer toStatus, Long targetUserId, String remark) { + stockInApproveRecordMapper.insert(ErpStockInApproveRecordDO.builder() + .stockInId(stockInId) + .actionType(actionType) + .fromStatus(fromStatus) + .toStatus(toStatus) + .targetUserId(targetUserId) + .remark(remark) + .build()); } - private List validateStockInItems(List list,String outType) { + private List validateStockInItems(List list, String inType) { validateWarehouseAreas(list); - if (Objects.equals(outType, "模具入库")) { - List moldList = moldBrandService.validMoldList( - convertSet(list, ErpStockInSaveReqVO.Item::getMoldSetId)); + if (Objects.equals(inType, "妯″叿鍏ュ簱")) { + List moldList = moldBrandService.validMoldList(convertSet(list, ErpStockInSaveReqVO.Item::getMoldSetId)); Map moldMap = convertMap(moldList, MoldBrandDO::getId); Map warehouseMap = convertMap( warehouseService.getWarehouseList(convertSet(list, ErpStockInSaveReqVO.Item::getWarehouseId)), ErpWarehouseDO::getId); Map areaMap = warehouseAreaService.getWarehouseAreaMap( convertSet(list, ErpStockInSaveReqVO.Item::getAreaId)); - return convertList(list, o -> { - MoldBrandDO moldBrand = moldMap.get(o.getMoldSetId()); + return convertList(list, item -> { + MoldBrandDO moldBrand = moldMap.get(item.getMoldSetId()); return ErpStockInItemDO.builder() - .id(null) + .id(item.getId()) .moldSetId(moldBrand.getId()) .moldSetName(moldBrand.getName()) - .warehouseId(o.getWarehouseId()) - .warehouseName(warehouseMap.containsKey(o.getWarehouseId()) ? warehouseMap.get(o.getWarehouseId()).getName() : null) - .areaId(o.getAreaId()) - .areaName(areaMap.containsKey(o.getAreaId()) ? areaMap.get(o.getAreaId()).getAreaName() : null) + .warehouseId(item.getWarehouseId()) + .warehouseName(warehouseMap.containsKey(item.getWarehouseId()) ? warehouseMap.get(item.getWarehouseId()).getName() : null) + .areaId(item.getAreaId()) + .areaName(areaMap.containsKey(item.getAreaId()) ? areaMap.get(item.getAreaId()).getAreaName() : null) .productId(moldBrand.getId()) .productUnitId(null) - .productPrice(o.getProductPrice()) - .count(o.getCount()) - .totalPrice(MoneyUtils.priceMultiply(o.getProductPrice(), o.getCount())) - .remark(o.getRemark()) - .deviceId(o.getDeviceId()) + .productPrice(item.getProductPrice()) + .count(item.getCount()) + .packagingSchemeId(item.getPackagingSchemeId()) + .inputUnitType(item.getInputUnitType()) + .inputCount(item.getInputCount()) + .totalPrice(MoneyUtils.priceMultiply(item.getProductPrice(), item.getCount())) + .remark(item.getRemark()) + .deviceId(item.getDeviceId()) .build(); }); - } else { - List productList = productService.validProductList( - convertSet(list, ErpStockInSaveReqVO.Item::getProductId)); - Map productMap = convertMap(productList, ErpProductDO::getId); - Map warehouseMap = convertMap( - warehouseService.getWarehouseList(convertSet(list, ErpStockInSaveReqVO.Item::getWarehouseId)), - ErpWarehouseDO::getId); - Map areaMap = warehouseAreaService.getWarehouseAreaMap( - convertSet(list, ErpStockInSaveReqVO.Item::getAreaId)); - return convertList(list, o -> BeanUtils.toBean(o, ErpStockInItemDO.class, item -> item - .setWarehouseName(warehouseMap.containsKey(item.getWarehouseId()) ? warehouseMap.get(item.getWarehouseId()).getName() : null) - .setAreaName(areaMap.containsKey(item.getAreaId()) ? areaMap.get(item.getAreaId()).getAreaName() : null) - .setProductUnitId(productMap.get(item.getProductId()).getUnitId()) - .setTotalPrice(MoneyUtils.priceMultiply(item.getProductPrice(), item.getCount())))); } + + List productList = productService.validProductList(convertSet(list, ErpStockInSaveReqVO.Item::getProductId)); + Map productMap = convertMap(productList, ErpProductDO::getId); + Map warehouseMap = convertMap( + warehouseService.getWarehouseList(convertSet(list, ErpStockInSaveReqVO.Item::getWarehouseId)), + ErpWarehouseDO::getId); + Map areaMap = warehouseAreaService.getWarehouseAreaMap( + convertSet(list, ErpStockInSaveReqVO.Item::getAreaId)); + return convertList(list, item -> BeanUtils.toBean(item, ErpStockInItemDO.class, target -> target + .setWarehouseName(warehouseMap.containsKey(target.getWarehouseId()) ? warehouseMap.get(target.getWarehouseId()).getName() : null) + .setAreaName(areaMap.containsKey(target.getAreaId()) ? areaMap.get(target.getAreaId()).getAreaName() : null) + .setProductUnitId(productMap.get(target.getProductId()).getUnitId()) + .setTotalPrice(MoneyUtils.priceMultiply(target.getProductPrice(), target.getCount())))); } private void validateWarehouseAreas(List list) { @@ -246,9 +443,9 @@ public class ErpStockInServiceImpl implements ErpStockInService { && newList.stream().anyMatch(item -> item.getMoldSetId() != null); if (moldStockIn) { stockInItemMapper.deleteByInId(id); - newList.forEach(o -> { - o.setId(null); - o.setInId(id); + newList.forEach(item -> { + item.setId(null); + item.setInId(id); }); stockInItemMapper.insertBatch(newList); return; @@ -256,9 +453,9 @@ public class ErpStockInServiceImpl implements ErpStockInService { List oldList = stockInItemMapper.selectListByInId(id); List> diffList = diffList(oldList, newList, - (oldVal, newVal) -> oldVal.getId().equals(newVal.getId())); + (oldVal, newVal) -> Objects.equals(oldVal.getId(), newVal.getId())); if (CollUtil.isNotEmpty(diffList.get(0))) { - diffList.get(0).forEach(o -> o.setInId(id)); + diffList.get(0).forEach(item -> item.setInId(id)); stockInItemMapper.insertBatch(diffList.get(0)); } if (CollUtil.isNotEmpty(diffList.get(1))) { @@ -268,68 +465,5 @@ public class ErpStockInServiceImpl implements ErpStockInService { stockInItemMapper.deleteBatchIds(convertList(diffList.get(2), ErpStockInItemDO::getId)); } } - - @Override - @Transactional(rollbackFor = Exception.class) - public void deleteStockIn(List ids) { - // 1. 校验不处于已审批 - List stockIns = stockInMapper.selectBatchIds(ids); - if (CollUtil.isEmpty(stockIns)) { - return; - } - stockIns.forEach(stockIn -> { - if (ErpAuditStatus.APPROVE.getStatus().equals(stockIn.getStatus())) { - throw exception(STOCK_IN_DELETE_FAIL_APPROVE, stockIn.getNo()); - } - }); - - // 2. 遍历删除,并记录操作日志 - stockIns.forEach(stockIn -> { - // 2.1 删除入库单 - stockInMapper.deleteById(stockIn.getId()); - // 2.2 删除入库单项 - stockInItemMapper.deleteByInId(stockIn.getId()); - }); - } - - private ErpStockInDO validateStockInExists(Long id) { - ErpStockInDO stockIn = stockInMapper.selectById(id); - if (stockIn == null) { - throw exception(STOCK_IN_NOT_EXISTS); - } - return stockIn; - } - - @Override - public ErpStockInDO getStockIn(Long id) { - return stockInMapper.selectById(id); - } - - @Override - public PageResult getStockInPage(ErpStockInPageReqVO pageReqVO) { - return stockInMapper.selectPage(pageReqVO); - } - - // ==================== 入库项 ==================== - - @Override - public List getStockInItemListByInId(Long inId) { - return stockInItemMapper.selectListByInId(inId); - } - - @Override - public List getStockInItemListByInIds(Collection inIds) { - if (CollUtil.isEmpty(inIds)) { - return Collections.emptyList(); - } - return stockInItemMapper.selectListByInIds(inIds); - } - - @Override - public void updateMoldStatus(Long id, Integer status) { - ErpStockInDO stockIn = validateStockInExists(id); - stockIn.setStatus(status); - stockInMapper.updateById(stockIn); - } - } +