package org.springblade.mdm.program.service; import lombok.AllArgsConstructor; import lombok.extern.slf4j.Slf4j; import org.springblade.core.mp.base.BizServiceImpl; import org.springblade.core.tool.utils.Func; import org.springblade.mdm.basesetting.machine.service.MachineService; import org.springblade.mdm.basesetting.machine.entity.Machine; import org.springblade.mdm.program.entity.NcNode; import org.springblade.mdm.program.mapper.NcNodeMapper; import org.springblade.mdm.program.vo.*; import org.springframework.beans.BeanUtils; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import java.util.ArrayList; import java.util.List; import java.util.Objects; import java.util.Optional; /** * 程序节点 * * @author yangys */ @Slf4j @Service @AllArgsConstructor public class NcNodeService extends BizServiceImpl { private final MachineService machineService; public void saveNcCode(NcNodeVO vo) { NcNode ncNode = new NcNode(); BeanUtils.copyProperties(vo, ncNode); ncNode.setId(null); ncNode.setParentIds(buildParentIds(vo.getParentId())); this.save(ncNode); } /** * 构建父id节点 * @param nodeId 节点id * @return */ String buildParentIds(long nodeId){ if(nodeId == 0L){ return "0"; } NcNode pNode = this.baseMapper.selectById(nodeId); return pNode.getParentIds()+","+pNode.getId(); } /** * 更新节点 * @param vo */ public void updateNcNode(NcNodeVO vo) { NcNode ncNode = this.getById(vo.getId()); ncNode.setName(vo.getName()); ncNode.setNodeType(vo.getNodeType()); ncNode.setDescription(vo.getDescription()); ncNode.setRemark(vo.getRemark()); ncNode.setMachineCode(vo.getMachineCode()); ncNode.setParentIds(buildParentIds(vo.getParentId())); this.updateById(ncNode); } /** * 懒加载列表 * @param parentId 父节点ID * @return */ public List lazyList(Long parentId) { // 判断点击搜索但是没有查询条件的情况 if (Func.isEmpty(parentId)) { parentId = 0L; } return baseMapper.lazyList(parentId); } /** * 查询现有固化的程序,暂定条件:零组件号相同,且是同一机床组 * * @param name 程序名称 * @param name * @return */ public NcNode getLastProgramNode(String name) { return this.getBaseMapper().getLastProgramNode(name); } /** * 首页树查询 * @param queryVO * @return */ public List searchList(NcNodeOldQueryVO queryVO) { //1.根据关进字和节点类型查询初始列表,查询的原始列表,需要hasChild字段,所以使用mapper.xml List oriList = this.getBaseMapper().searchList(queryVO); if ("10".equals(queryVO.getNodeType())) { //搜索的根级别,直接返回 return oriList; } List allVos = new ArrayList();//已经加入过的节点,用于去重 List rootVos = new ArrayList(); for(NcNodeVO vo : oriList){ allVos.add(vo); //上级各级的节点 List parents = this.getBaseMapper().searchListInIds(Func.toLongList(vo.getParentIds())); for(NcNodeVO pvo : parents){ if(pvo.getParentId() == 0L){ rootVos.add(pvo); } allVos.add(pvo); } } for(NcNodeVO root : rootVos){ addNodeChildren(root, allVos); } return rootVos; } /** * 首页搜索 新的 * @param queryVO 查询参数 * @return */ public List searchList2(NcNodeQueryVO queryVO) { //1.根据零组件号和创建时间查询初始列表,查询的原始列表,需要hasChild字段,所以使用mapper.xml if(queryVO.getCreateTimeEnd()!=null){ queryVO.setCreateTimeEnd(queryVO.getCreateTimeEnd().plusDays(1)); } List oriList = this.getBaseMapper().searchList2(queryVO); List allVos = new ArrayList<>();//已经加入过的节点,用于去重 List rootVos = new ArrayList<>(); for(NcNodeVO vo : oriList){ allVos.add(vo); //上级各级的节点 List parents = this.getBaseMapper().searchListInIds(Func.toLongList(vo.getParentIds())); for(NcNodeVO pvo : parents){ if(pvo.getParentId() == 0L && !rootVos.contains(pvo)){ rootVos.add(pvo); } if(!allVos.contains(pvo)){ allVos.add(pvo); } } } for(NcNodeVO root : rootVos){ addNodeChildren(root, allVos); } return rootVos; } void addNodeChildren(NcNodeVO node, List allNodes) { for(NcNodeVO vo : allNodes){ if(Objects.equals(vo.getParentId(), node.getId())){ node.addChildren(vo); } } if(node.getChildren()!=null && !node.getChildren().isEmpty()){ for(NcNodeVO child : node.getChildren()){ addNodeChildren(child, allNodes); } } } /** * 获取“程序包名”试切的最新版本 * @param name 节点名称 * @return 最新版本程序报名节点 */ public NcNode getLastEditionTryingProgramPackage(String name){ List pkgList = lambdaQuery().eq(NcNode::getNodeType,NcNode.TYPE_PROGRAM_PACKAGE) .eq(NcNode::getName, name).and(i->{ i.eq(NcNode::getIsCured, 0).or().isNull(NcNode::getIsCured); }).likeRight(NcNode::getParentIds,"0,1,") .eq(NcNode::getIsLastEdition,1).orderByDesc(NcNode::getCreateTime).list();//.eq(NcNode::getProcessEdition,processEdition) if(pkgList.isEmpty()){ return null; }else{ return pkgList.get(0); } } /** * 根据父节点和名称,查询文件界节点列表 * @param name 节点/文件名称 * @param parentId 父节点id */ public NcNode getLastEditionProgramFile(String name,Long parentId) { List nodes = lambdaQuery().eq(NcNode::getNodeType,NcNode.TYPE_PROGRAM_FILE) .eq(NcNode::getName, name).eq(NcNode::getParentId,parentId) .eq(NcNode::getIsLastEdition,1).list(); if(nodes.isEmpty()){ return null; }else { return nodes.get(0); } } /** * 获取试切节点node的历史列表(零组件号,工序号,工序版本,机床组) * @param pkgNode node * @return 历史列表,报错节点本身 */ public List getTryNodeHistory(NcNode pkgNode) { return this.lambdaQuery().eq(NcNode::getDrawingNo,pkgNode.getDrawingNo()) .eq(NcNode::getProcessNo,pkgNode.getProcessNo()) .eq(NcNode::getProcessEdition,pkgNode.getProcessEdition()) .eq(NcNode::getMachineGroupCode,pkgNode.getMachineGroupCode()) .likeLeft(NcNode::getParentIds,"0,1,") .list();//.ne(NcNode::getId,pkgNode.getId()) /* return this.lambdaQuery().eq(NcNode::getParentId,pkgNode.getParentId()) .eq(NcNode::getName,pkgNode.getName()).list();//.ne(NcNode::getId,pkgNode.getId()) */ } /** * 计算历史序号,根据零组件号,工序号,工序版次,机床组查询,查询道则使用该历史编号,查询不到使用新生成的 */ public long calculateHistorySerial(NcNode pkgNode) { NcNode node = this.lambdaQuery().eq(NcNode::getNodeType,NcNode.TYPE_PROGRAM_PACKAGE).eq(NcNode::getDrawingNo,pkgNode.getDrawingNo()) .eq(NcNode::getProcessNo,pkgNode.getProcessNo()).eq(NcNode::getProcessEdition,pkgNode.getProcessEdition()) .eq(NcNode::getMachineGroupCode,pkgNode.getMachineGroupCode()).last("limit 1").one(); if(node != null && node.getHisSerial()!=null){ return node.getHisSerial(); }else{ //以往没有,生成一个新的 return System.currentTimeMillis();//使用当前毫秒数 } } /** * 生成程序包名/程序名称 * @param drawingNo 零组件号 * @param processNo 工序版次 * @return 程序包名/程序名称 */ public static String genProgramName(String drawingNo,String processNo,String processEdition){ return drawingNo+"-"+processNo+"-"+processEdition; } /** * 获取最新版本的 已固化节点 * @param programPkgName * @return */ public NcNode getLastEditionCuredProgramPackage(String programPkgName) { List nodes = lambdaQuery().eq(NcNode::getNodeType,NcNode.TYPE_PROGRAM_PACKAGE) .eq(NcNode::getName, programPkgName).likeRight(NcNode::getParentIds,"0,2,").eq(NcNode::getIsCured,1) //.eq(NcNode::getProcessEdition, processEdition) .eq(NcNode::getIsLastEdition,1).list(); if(nodes.isEmpty()){ return null; }else { return nodes.get(0); } } /** * 获取最新版本的 已固化节点 * @param programPkgName 程序包名 * @param machineCode 机床编号 * @return */ public NcNode getCuredProgramPackage(String programPkgName,String processEdition,String machineCode) { Machine machine = machineService.getByCode(machineCode); List sameGroupMachines = machineService.lambdaQuery().eq(Machine::getMachineGroupCode,machine.getMachineGroupCode()).list(); List machineCodesInGroup = sameGroupMachines.stream().map(Machine::getCode).toList(); List nodes = lambdaQuery().eq(NcNode::getNodeType,NcNode.TYPE_PROGRAM_PACKAGE) .eq(NcNode::getName, programPkgName) .eq(NcNode::getProcessEdition,processEdition) .likeRight(NcNode::getParentIds,"0,2,").eq(NcNode::getIsCured,1) .in(!machineCodesInGroup.isEmpty(),NcNode::getMachineCode,machineCodesInGroup) .eq(NcNode::getIsLastEdition,1).list(); if(nodes.isEmpty()){ return null; }else { return nodes.get(0); } } /** * 获取最新的固化程序,不用工序版次匹配 * @param drawingNo * @param processNo * @param machineCode * @return */ public NcNode getLastCuredProgramWithoutProcessEdition(String drawingNo, String processNo, String machineCode) { Machine machine = machineService.getByCode(machineCode); //List sameGroupMachines = machineService.lambdaQuery().eq(Machine::getMachineGroupCode,machine.getMachineGroupCode()).list(); //List machineCodesInGroup = sameGroupMachines.stream().map(Machine::getCode).toList(); List nodes = lambdaQuery().eq(NcNode::getNodeType,NcNode.TYPE_PROGRAM_PACKAGE) .eq(NcNode::getDrawingNo, drawingNo).eq(NcNode::getProcessNo, processNo) .likeRight(NcNode::getParentIds,"0,2,").eq(NcNode::getIsCured,1) .eq(NcNode::getMachineGroupCode,machine.getMachineGroupCode()) //.in(!machineCodesInGroup.isEmpty(),NcNode::getMachineCode,machineCodesInGroup) .eq(NcNode::getIsLastEdition,1).orderByDesc(NcNode::getCreateTime).list(); if(nodes.isEmpty()){ return null; }else { return nodes.get(0); } } /** * 获取最新版本的 偏离节点 * @param programPkgName 程序包名 * @return 偏离的程序节点 */ public NcNode getLastEditionDeviationProgramPackage(String programPkgName) {//,String processEdition List nodes = lambdaQuery().eq(NcNode::getNodeType,NcNode.TYPE_PROGRAM_PACKAGE) .eq(NcNode::getName, programPkgName) //.eq(NcNode::getProcessEdition, processEdition) .likeRight(NcNode::getParentIds,"0,3,") .eq(NcNode::getIsLastEdition,1).list(); if(nodes.isEmpty()){ return null; }else { return nodes.get(0); } } /** * 根据流程实例id获取node节点,都是程序包节点 * @param processInstanceId 流程实例id * @return 对应额系欸但那 */ public NcNode getByProcessInstanceId(String processInstanceId) { Optional nodeOpt = this.lambdaQuery().eq(NcNode::getProcessInstanceId,processInstanceId).oneOpt(); return nodeOpt.orElse(null); } /** * 物理删除节点id下的子节点(性能考虑,否则数据太多) * @param nodeId 节点id */ public void deleteSubNodes(Long nodeId) { this.baseMapper.deleteSubNodes(nodeId); } /** * 获取程序包下所有层序文件节点 * @param packageNodeId 程序包名 节点id * @return 包下属的程序文件 */ public List getProgramFilesByPackageId(Long packageNodeId) { return this.lambdaQuery().eq(NcNode::getNodeType,NcNode.TYPE_PROGRAM_FILE) .eq(NcNode::getParentId,packageNodeId).eq(NcNode::getIsLastEdition,1).list(); } /** * 升级版本号(+1) * @param nodeId 节点id */ @Transactional public void upgradeVersionNumber(Long nodeId) { NcNode node = this.getById(nodeId); node.upgradeVersionNumber(); this.updateById(node); } /** * 锁定节点 * @param id 程序包节点id */ @Transactional public void lock(Long id) { NcNode node = this.getById(id); node.lock(); this.updateById(node); } @Transactional public void lock(Long id,String remark) { NcNode node = this.getById(id); node.lock(remark); this.updateById(node); } @Transactional public void unlock(Long id) { NcNode node = this.getById(id); node.unlock(); this.updateById(node); } /** * 查询偏离单的序号 * @param programPkgNode 偏离单的程序包名节点 * @return 序号 */ /* public long getDeviationSerialForNode(NcNode programPkgNode) { return lambdaQuery().eq(NcNode::getNodeType,NcNode.TYPE_PROGRAM_PACKAGE) .eq(NcNode::getName,programPkgNode.getName()) .eq(NcNode::getDrawingNo,programPkgNode.getDrawingNo()) .eq(NcNode::getProcessNo,programPkgNode.getProcessNo()) .eq(NcNode::getProcessEdition,programPkgNode.getProcessEdition()) .isNotNull(NcNode::getDeviation) .le(NcNode::getCreateTime,programPkgNode.getCreateTime()) //时间小于等于当前节点 .count(); } */ /** * 根据上级节点id,移动下面的加工机床节点 * @param parentId 上级节点id */ /* public void deleteMachineGroupNodeByParentId(Long parentId) { baseMapper.deleteMachineGroupNodeByParentId(parentId); }*/ /** * 删除所偶非最新版本的数据(hodeHIs里面已经保存过) */ public void deleteOldEditionNodeData() { baseMapper.deleteOldEditionNodeData(); } /** * //更新已固化的,同名、不同机床组的程序为锁定状态 * @param packageNode */ public void lockSameNameOtherMachineGroupProgramPackage(NcNode packageNode) { lambdaUpdate().eq(NcNode::getDrawingNo,packageNode.getDrawingNo()) .eq(NcNode::getProcessNo,packageNode.getProcessNo()) .eq(NcNode::getName,packageNode.getName()) .ne(NcNode::getMachineGroupCode,packageNode.getMachineGroupCode()) .eq(NcNode::getIsCured,1) .eq(NcNode::getIsLastEdition,1) .set(NcNode::getIsLocked,NcNode.LOCKED) .set(NcNode::getRemark,"回传固化同名程序锁定") .update(); } }