| package com.ruoyi.system.service.impl; | 
|   | 
| import cn.hutool.core.bean.BeanUtil; | 
| import com.baomidou.mybatisplus.core.metadata.IPage; | 
| import com.baomidou.mybatisplus.extension.plugins.pagination.Page; | 
| import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; | 
| import com.ruoyi.common.exception.ServiceException; | 
| import com.ruoyi.common.utils.SecurityUtils; | 
| import com.ruoyi.system.constants.ApprovalApplicationCodePrefix; | 
| import com.ruoyi.system.dto.asset.OaApprovalApplicationChangeDTO; | 
| import com.ruoyi.system.emums.ApprovalStatusEnum; | 
| import com.ruoyi.system.emums.ApprovalTypeEnum; | 
| import com.ruoyi.system.mapper.OaApprovalApplicationChangeMapper; | 
| import com.ruoyi.system.model.OaApprovalApplicationAssetItem; | 
| import com.ruoyi.system.model.OaApprovalApplicationChange; | 
| import com.ruoyi.system.model.OaApprovalApplications; | 
| import com.ruoyi.system.model.OaApprovalFlowNode; | 
| import com.ruoyi.system.query.OaApprovalApplicationChangePageQuery; | 
| import com.ruoyi.system.service.AssetMainService; | 
| import com.ruoyi.system.service.OaApprovalApplicationAssetItemService; | 
| import com.ruoyi.system.service.OaApprovalApplicationChangeService; | 
| import com.ruoyi.system.service.OaApprovalApplicationsService; | 
| import com.ruoyi.system.service.OaApprovalFlowNodeService; | 
| import com.ruoyi.system.service.OaApprovalTodoService; | 
| import com.ruoyi.system.vo.asset.AssetMainVO; | 
| import com.ruoyi.system.vo.asset.OaApprovalApplicationChangeDetailVO; | 
| import com.ruoyi.system.vo.asset.OaApprovalApplicationChangePageVO; | 
| import lombok.RequiredArgsConstructor; | 
| import org.springframework.stereotype.Service; | 
| import org.springframework.transaction.annotation.Transactional; | 
| import org.springframework.util.CollectionUtils; | 
|   | 
| import java.time.LocalDate; | 
| import java.time.format.DateTimeFormatter; | 
| import java.util.Collections; | 
| import java.util.List; | 
| import java.util.Objects; | 
| import java.util.stream.Collectors; | 
|   | 
| /** | 
|  * <p> | 
|  * 资产变更审批明细表 服务实现类 | 
|  * </p> | 
|  * | 
|  * @author WuGuanFengYue | 
|  * @since 2025-09-15 | 
|  */ | 
| @Service | 
| @RequiredArgsConstructor | 
| public class OaApprovalApplicationChangeServiceImpl extends ServiceImpl<OaApprovalApplicationChangeMapper, OaApprovalApplicationChange> implements OaApprovalApplicationChangeService { | 
|   | 
|     private final OaApprovalApplicationsService oaApprovalApplicationsService; | 
|     private final OaApprovalFlowNodeService oaApprovalFlowNodeService; | 
|     private final OaApprovalTodoService oaApprovalTodoService; | 
|     private final OaApprovalApplicationAssetItemService oaApprovalApplicationAssetItemService; | 
|     private final AssetMainService assetMainService; | 
|   | 
|     @Override | 
|     @Transactional(rollbackFor = Exception.class) | 
|     public void submitChange(OaApprovalApplicationChangeDTO dto) { | 
|         //校验资产状态 | 
|         oaApprovalApplicationAssetItemService.validateAssetStatus(dto.getAssetMainIds()); | 
|         // 1. 构建并保存审批主表 | 
|         OaApprovalApplications applications = buildOaApprovalApplications(dto); | 
|   | 
|         // 2. 获取流程首节点,设置当前节点,并保存 | 
|         OaApprovalFlowNode firstFlowNode = getFirstFlowNode(ApprovalTypeEnum.ASSET_CHANGE.getCode()); | 
|         applications.setCurrentFlowNodeId(firstFlowNode.getId()); | 
|         oaApprovalApplicationsService.save(applications); | 
|   | 
|         // 3. 创建待办 | 
|         oaApprovalTodoService.createApprovalTodos(applications.getId(), applications.getApplicationCode(), firstFlowNode, dto.getOwnershipDeptId()); | 
|   | 
|         // 4. 保存变更明细 | 
|         OaApprovalApplicationChange detail = buildOaApprovalApplicationChange(dto, applications.getId()); | 
|         this.save(detail); | 
|   | 
|         // 5. 保存关联的资产项 | 
|         List<OaApprovalApplicationAssetItem> items = dto.getAssetMainIds().stream() | 
|                 .map(i -> { | 
|                     OaApprovalApplicationAssetItem item = new OaApprovalApplicationAssetItem(); | 
|                     item.setApprovalApplicationId(applications.getId()); | 
|                     item.setAssetMainId(i); | 
|                     return item; | 
|                 }) | 
|                 .collect(Collectors.toList()); | 
|         oaApprovalApplicationAssetItemService.saveBatch(items); | 
|     } | 
|   | 
|     private OaApprovalApplications buildOaApprovalApplications(OaApprovalApplicationChangeDTO dto) { | 
|         OaApprovalApplications applications = BeanUtil.copyProperties(dto, OaApprovalApplications.class); | 
|         applications.setApplicationCode(oaApprovalApplicationsService.generateApplicationCode(ApprovalApplicationCodePrefix.ASSET_CHANGE)); | 
|         applications.setApprovalId(ApprovalTypeEnum.ASSET_CHANGE.getCode()); | 
|         applications.setApplicationDate(LocalDate.now()); | 
|         applications.setApprovalStatus(ApprovalStatusEnum.PENDING.getCode()); | 
|         applications.setApplicantUserId(SecurityUtils.getUserId().intValue()); | 
|         applications.setApplicantName(SecurityUtils.getLoginUser().getUser().getNickName()); | 
|         applications.setDeptId(Integer.parseInt(SecurityUtils.getLoginUser().getUser().getDeptId())); | 
|         applications.setDeptName(SecurityUtils.getLoginUser().getUser().getDeptName()); | 
|         return applications; | 
|     } | 
|   | 
|     private OaApprovalApplicationChange buildOaApprovalApplicationChange(OaApprovalApplicationChangeDTO dto, Integer applicationId) { | 
|         OaApprovalApplicationChange change = BeanUtil.copyProperties(dto, OaApprovalApplicationChange.class); | 
|         change.setApprovalApplicationId(applicationId); | 
|         return change; | 
|     } | 
|   | 
|     private OaApprovalFlowNode getFirstFlowNode(Integer approvalId) { | 
|         List<OaApprovalFlowNode> flowNodes = oaApprovalFlowNodeService.lambdaQuery() | 
|                 .eq(OaApprovalFlowNode::getApprovalId, approvalId) | 
|                 .eq(OaApprovalFlowNode::getStatus, 1) | 
|                 .orderByAsc(OaApprovalFlowNode::getSortOrder) | 
|                 .list(); | 
|         if (CollectionUtils.isEmpty(flowNodes)) { | 
|             throw new ServiceException("未找到有效的审批流程配置"); | 
|         } | 
|         return flowNodes.get(0); | 
|     } | 
|   | 
|     /** | 
|      * 生成申请单号:BG + yyyyMMdd + 3位序号 | 
|      */ | 
|     private String generateApplicationCode(String prefix) { | 
|         String dateStr = LocalDate.now().format(DateTimeFormatter.ofPattern("yyyyMMdd")); | 
|         prefix = prefix + dateStr; | 
|         Long count = oaApprovalApplicationsService.lambdaQuery() | 
|                 .like(OaApprovalApplications::getApplicationCode, prefix) | 
|                 .count(); | 
|         return prefix + String.format("%03d", count + 1); | 
|     } | 
|   | 
|     @Override | 
|     public IPage<OaApprovalApplicationChangePageVO> getChangePageList(OaApprovalApplicationChangePageQuery pageQuery) { | 
|         Page<OaApprovalApplicationChangePageVO> page = new Page<>(pageQuery.getPageNum(), pageQuery.getPageSize()); | 
|         return this.baseMapper.selectChangePage(page, pageQuery); | 
|     } | 
|   | 
|     @Override | 
|     public OaApprovalApplicationChangeDetailVO getChangeDetail(Integer id) { | 
|         OaApprovalApplications app = oaApprovalApplicationsService.getById(id); | 
|         if (app == null) { | 
|             throw new ServiceException("审批主记录不存在"); | 
|         } | 
|         OaApprovalApplicationChange detail = this.lambdaQuery().eq(OaApprovalApplicationChange::getApprovalApplicationId, app.getId()).one(); | 
|         if (detail == null) { | 
|             throw new ServiceException("记录不存在"); | 
|         } | 
|         oaApprovalApplicationsService.assembleApplicationDetail(app); | 
|         List<Integer> assetMainIds = oaApprovalApplicationAssetItemService.lambdaQuery() | 
|                 .eq(OaApprovalApplicationAssetItem::getApprovalApplicationId, app.getId()) | 
|                 .list().stream().map(OaApprovalApplicationAssetItem::getAssetMainId) | 
|                 .distinct().collect(Collectors.toList()); | 
|   | 
|         List<AssetMainVO> assetMainVOS = assetMainIds.isEmpty() ? Collections.emptyList() : assetMainService.getListByIds(assetMainIds); | 
|         OaApprovalApplicationChangeDetailVO vo = BeanUtil.copyProperties(app, OaApprovalApplicationChangeDetailVO.class); | 
|         vo.setTitle(detail.getTitle()); | 
|         vo.setAssetTypeId(detail.getAssetTypeId()); | 
|         vo.setAddressType(detail.getAddressType()); | 
|         vo.setUseDeptId(detail.getUseDeptId()); | 
|         vo.setWarehouseId(detail.getWarehouseId()); | 
|         vo.setAddress(detail.getAddress()); | 
|         vo.setOwnershipDeptId(detail.getOwnershipDeptId()); | 
|         vo.setUserName(detail.getUserName()); | 
|         vo.setChangeTime(detail.getChangeTime()); | 
|         vo.setItems(assetMainVOS); | 
|         return vo; | 
|     } | 
|   | 
|     @Transactional(rollbackFor = Exception.class) | 
|     @Override | 
|     public void deleteByApplicationId(Integer id) { | 
|         OaApprovalApplications applications = oaApprovalApplicationsService.getById(id); | 
|         if (Objects.isNull(applications)) { | 
|             throw new ServiceException("申请记录不存在"); | 
|         } | 
|         if (!applications.getApprovalStatus().equals(ApprovalStatusEnum.REFUSED.getCode())) { | 
|             throw new ServiceException("该申请不能删除"); | 
|         } | 
|         this.lambdaUpdate().eq(OaApprovalApplicationChange::getApprovalApplicationId, id).remove(); | 
|         oaApprovalApplicationAssetItemService.lambdaUpdate().eq(OaApprovalApplicationAssetItem::getApprovalApplicationId, id).remove(); | 
|         oaApprovalApplicationsService.removeById(id); | 
|     } | 
| } |