add(mes): 添加物料BOM信息批量新增功能(新增BOM对话框:根据结构BOM批量新增物料BOM)

- 在 IProdMaterialBomService 接口中新增 insertBatchByBoList 方法
- 在 ProdMaterialBomController 中添加 addBatchMaterialBom 控制器方法
- 在 ProdMaterialBomServiceImpl 中实现 insertBatchByBoList 方法的逻辑
- 按层级分组处理,确保父节点先于子节点插入
- 增加了异常处理和数据完整性校验
master
zch 2 weeks ago
parent bffd1aefa4
commit 32f318be93

@ -107,9 +107,20 @@ public class ProdMaterialBomController extends BaseController {
/**
* BOM
*/
@GetMapping("getProdMaterialBomList")
@GetMapping("/getProdMaterialBomList")
public R<List<ProdMaterialBomVo>> getProdMaterialBomlist(ProdMaterialBomBo bo) {
List<ProdMaterialBomVo> list = prodMaterialBomService.queryList(bo);
return R.ok(list);
}
/**
* BOM
*/
@SaCheckPermission("mes:materialBom:add")
@Log(title = "物料BOM信息", businessType = BusinessType.INSERT)
@RepeatSubmit()
@PostMapping("/addBatchMaterialBom")
public R<Void> addBatchMaterialBom(@RequestBody List<ProdMaterialBomBo> boList) {
return toAjax(prodMaterialBomService.insertBatchByBoList(boList));
}
}

@ -56,4 +56,12 @@ public interface IProdMaterialBomService {
* @return
*/
Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid);
/**
* BOM
*
* @param boList BOM
* @return
*/
Boolean insertBatchByBoList(List<ProdMaterialBomBo> boList);
}

@ -15,6 +15,14 @@ import org.dromara.mes.service.IProdMaterialBomService;
import java.util.List;
import java.util.Map;
import java.util.Collection;
import java.util.stream.Collectors;
import java.util.ArrayList;
import java.util.HashMap;
import org.springframework.transaction.annotation.Transactional;
import cn.hutool.core.collection.CollUtil;
import org.dromara.common.core.exception.ServiceException;
/**
* BOMService
@ -154,4 +162,100 @@ public class ProdMaterialBomServiceImpl implements IProdMaterialBomService {
}
}
/**
* BOM
* @param boList BOM
* @return true
*/
@Override
@Transactional(rollbackFor = Exception.class)
public Boolean insertBatchByBoList(List<ProdMaterialBomBo> boList) {
if (CollUtil.isEmpty(boList)) {
return false;
}
try {
// 按层级分组根据parentId分组
Map<Long, List<ProdMaterialBomBo>> levelMap = new HashMap<>();
// 1. 首先找出所有顶级节点
List<ProdMaterialBomBo> topNodes = boList.stream()
.filter(bo -> bo.getParentId() == null || bo.getParentId() == 0)
.collect(Collectors.toList());
// 2. 其他节点按parentId分组
Map<Long, List<ProdMaterialBomBo>> childrenMap = boList.stream()
.filter(bo -> bo.getParentId() != null && bo.getParentId() != 0)
.collect(Collectors.groupingBy(bo -> Math.abs(bo.getParentId())));
// 存储临时ID到实际ID的映射
Map<Long, Long> idMapping = new HashMap<>();
// 3. 先处理顶级节点
for (ProdMaterialBomBo topNode : topNodes) {
Long tempId = Math.abs(topNode.getMaterialBomId());
topNode.setMaterialBomId(null); // 清除临时ID
topNode.setParentId(0L); // 确保顶级节点parentId为0
topNode.setAncestors("0"); // 顶级节点的ancestors为"0"
// 插入顶级节点
ProdMaterialBom add = MapstructUtils.convert(topNode, ProdMaterialBom.class);
if (baseMapper.insert(add) <= 0) {
throw new ServiceException("插入顶级节点失败");
}
// 记录映射关系
idMapping.put(tempId, add.getMaterialBomId());
}
// 4. 处理子节点,直到所有节点都处理完
while (!childrenMap.isEmpty()) {
// 找出当前可以处理的节点父节点已经在idMapping中的节点
List<Long> processableParentIds = new ArrayList<>(childrenMap.keySet());
boolean processed = false;
for (Long parentTempId : processableParentIds) {
// 检查父节点是否已处理
if (idMapping.containsKey(parentTempId)) {
List<ProdMaterialBomBo> children = childrenMap.remove(parentTempId);
// 处理同一父节点的所有子节点
for (ProdMaterialBomBo child : children) {
Long childTempId = Math.abs(child.getMaterialBomId());
child.setMaterialBomId(null); // 清除临时ID
// 设置实际的父节点ID
Long actualParentId = idMapping.get(parentTempId);
child.setParentId(actualParentId);
// 设置祖级列表
ProdMaterialBom parent = baseMapper.selectById(actualParentId);
child.setAncestors(parent.getAncestors() + "," + actualParentId);
// 插入子节点
ProdMaterialBom add = MapstructUtils.convert(child, ProdMaterialBom.class);
if (baseMapper.insert(add) <= 0) {
throw new ServiceException("插入子节点失败");
}
// 记录映射关系
idMapping.put(childTempId, add.getMaterialBomId());
}
processed = true;
}
}
// 如果一轮循环没有处理任何节点,说明数据有问题
if (!processed && !childrenMap.isEmpty()) {
throw new ServiceException("存在无法处理的节点,可能是父节点丢失");
}
}
return true;
} catch (Exception e) {
throw new ServiceException("批量插入失败: " + e.getMessage());
}
}
}

Loading…
Cancel
Save