package com.chinaztt.mes.warehouse.service.impl; import cn.hutool.core.collection.CollectionUtil; import cn.hutool.core.util.BooleanUtil; import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import com.chinaztt.mes.basic.dto.LocationIfsMoveDTO; import com.chinaztt.mes.basic.entity.Part; import com.chinaztt.mes.basic.entity.Staff; import com.chinaztt.mes.basic.mapper.PartMapper; import com.chinaztt.mes.basic.mapper.StaffMapper; import com.chinaztt.mes.basic.service.LocationService; import com.chinaztt.mes.common.numgen.NumberGenerator; import com.chinaztt.mes.warehouse.dto.ReverseStockApplyDetailDTO; import com.chinaztt.mes.warehouse.entity.ReverseStockApply; import com.chinaztt.mes.warehouse.entity.ReverseStockApplyDetail; import com.chinaztt.mes.warehouse.entity.Stock; import com.chinaztt.mes.warehouse.mapper.ReverseStockApplyDetailMapper; import com.chinaztt.mes.warehouse.mapper.ReverseStockApplyMapper; import com.chinaztt.mes.warehouse.mapper.StockMapper; import com.chinaztt.mes.warehouse.service.ReverseStockApplyDetailService; import com.chinaztt.mes.warehouse.service.ReverseStockApplyService; import com.chinaztt.mes.warehouse.state.constant.ReverseApplyState; import com.chinaztt.mes.warehouse.util.RedisLockHelper; import com.chinaztt.mes.warehouse.util.StockUtils; import com.chinaztt.ztt.common.security.service.ZttUser; import com.chinaztt.ztt.common.security.util.SecurityUtils; import org.apache.commons.lang3.StringUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import java.math.BigDecimal; import java.time.LocalDateTime; import java.util.ArrayList; import java.util.List; import java.util.UUID; /** * @Author: Zero * @Date: 2022/9/16 17:34 * @Description: */ @Service @Transactional(rollbackFor = Exception.class) public class ReverseStockApplyServiceImpl extends ServiceImpl implements ReverseStockApplyService { @Autowired private NumberGenerator numberGenerator; @Autowired private RedisLockHelper redisLockHelper; @Autowired private ReverseStockApplyDetailService reverseStockApplyDetailService; @Autowired private ReverseStockApplyDetailMapper reverseStockApplyDetailMapper; @Autowired private LocationService locationService; @Autowired private StockUtils stockUtils; @Autowired private ReverseStockApplyMapper reverseStockApplyMapper; @Autowired private StaffMapper staffMapper; @Autowired private StockMapper stockMapper; @Autowired private PartMapper partMapper; @Override public Boolean generateApply() { ReverseStockApply reverseStockApply = ReverseStockApply.builder().state(ReverseApplyState.DRAFT.getCode()) .applySerialNo(numberGenerator.generateNumberWithPrefix(ReverseStockApply.DIGIT, ReverseStockApply.PREFIX, ReverseStockApply::getApplySerialNo)).build(); ZttUser currentUser = SecurityUtils.getUser(); Staff staffBySelect = staffMapper.selectOne(Wrappers.lambdaQuery().eq(Staff::getStaffNo, currentUser.getUsername())); if(staffBySelect!=null){ reverseStockApply.setCreateUserName(staffBySelect.getStaffName()); } return save(reverseStockApply); } @Override public String executeReverseMoveLocation(List ids) { try { for (Long id : ids) { Boolean lock = redisLockHelper.lock(String.valueOf(id)); if (BooleanUtil.isFalse(lock)) { throw new RuntimeException("存在正在执行的退料,无法重复执行"); } } List applyDetailList = reverseStockApplyDetailMapper.getApplyDetailByIds(ids); boolean existProcessed = applyDetailList.stream().anyMatch(d -> StringUtils.equals(ReverseApplyState.PROCESSED.getCode(), d.getState())); if (existProcessed) { throw new RuntimeException("存在已执行退料需求"); } boolean existBlankToNo = applyDetailList.stream().anyMatch(d -> StringUtils.isBlank(d.getIfsToLocationNo())); if (existBlankToNo) { throw new RuntimeException("存在至库位为空的退料需求"); } LocationIfsMoveDTO moveDTO = new LocationIfsMoveDTO(); moveDTO.setRECORD_ID(UUID.randomUUID().toString().replace("-", StringUtils.EMPTY)); List dataBeanList = new ArrayList<>(); moveDTO.setBATCH_INFO(dataBeanList); for (ReverseStockApplyDetailDTO detail : applyDetailList) { Stock stock = stockMapper.selectById(detail.getStockId()); if (stock.getOperationStockStatus() == null) { Part part = partMapper.selectById(stock.getPartId()); if (StringUtils.equals("3", part.getMaterialType())) { stock.setOperationStockStatus(Boolean.FALSE); } } if (BooleanUtil.isTrue(stock.getOperationStockStatus())) { continue; } LocationIfsMoveDTO.DataBean bean = new LocationIfsMoveDTO.DataBean(); bean.setPART_NO(detail.getPartNo()); if (BooleanUtil.isTrue(detail.getLotTrackingIfs())) { bean.setLOT_BATCH_NO(detail.getIfsBatchNo()); bean.setWAIV_DEV_REJ_NO(detail.getSn()); } else { bean.setLOT_BATCH_NO("*"); bean.setWAIV_DEV_REJ_NO("*"); } bean.setMOVE_QTY(detail.getReverseQuantity()); bean.setLOCATION_NO(detail.getIfsFromLocationNo()); bean.setTO_LOCATION_NO(detail.getIfsToLocationNo()); dataBeanList.add(bean); } for (ReverseStockApplyDetailDTO detailDTO : applyDetailList) { stockUtils.updateById(detailDTO.getStockId(), detailDTO.getReverseQuantity().negate(), BigDecimal.ZERO, BigDecimal.ZERO, BigDecimal.ZERO, null, "REVERSE"); ZttUser currentUser = SecurityUtils.getUser(); Staff staff = staffMapper.selectOne(Wrappers.lambdaQuery().eq(Staff::getStaffNo, currentUser.getUsername())); if (staff == null) { detailDTO.setExecutor(""); } else { detailDTO.setExecutor(staff.getStaffName()); } detailDTO.setExecuteTime(LocalDateTime.now()); detailDTO.setState(ReverseApplyState.PROCESSED.getCode()); reverseStockApplyDetailService.updateById(detailDTO); } ReverseStockApply stockApply = getById(applyDetailList.get(0).getReverseApplyId()); int count = reverseStockApplyDetailService.count(Wrappers.lambdaQuery().notIn(ReverseStockApplyDetail::getId, ids) .eq(ReverseStockApplyDetail::getState, ReverseApplyState.NEW.getCode()) .eq(ReverseStockApplyDetail::getReverseApplyId, stockApply.getId())); if (count > 0) { stockApply.setState(ReverseApplyState.PROCESSING.getCode()); } else { stockApply.setState(ReverseApplyState.PROCESSED.getCode()); } updateById(stockApply); locationService.moveIfsLocation(moveDTO); return stockApply.getState(); } finally { for (Long id : ids) { redisLockHelper.delLock(String.valueOf(id)); } } } @Override public Boolean deleteApply(List ids) { List reverseStockApplyDetailList = reverseStockApplyDetailMapper.selectList(Wrappers.lambdaQuery().in(ReverseStockApplyDetail::getReverseApplyId, ids)); if (CollectionUtil.isNotEmpty(reverseStockApplyDetailList)) { throw new RuntimeException("存在含有退料详情的申请记录,无法删除"); } reverseStockApplyMapper.deleteBatchIds(ids); return Boolean.TRUE; } }