package org.springblade.flow.engine.service.impl;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;

import javax.annotation.Resource;

import org.flowable.bpmn.BpmnAutoLayout;
import org.flowable.bpmn.converter.BpmnXMLConverter;
import org.flowable.bpmn.model.BpmnModel;
import org.flowable.bpmn.model.EndEvent;
import org.flowable.bpmn.model.ExclusiveGateway;
import org.flowable.bpmn.model.FlowElement;
import org.flowable.bpmn.model.ParallelGateway;
import org.flowable.bpmn.model.Process;
import org.flowable.bpmn.model.SequenceFlow;
import org.flowable.bpmn.model.StartEvent;
import org.flowable.engine.RepositoryService;
import org.springblade.flow.base.ActionResult;
import org.springblade.flow.base.UserInfo;
import org.springblade.flow.base.entity.DictionaryDataEntity;
import org.springblade.flow.base.service.DictionaryDataService;
import org.springblade.flow.base.util.BpmnModelUtils;
import org.springblade.flow.base.util.FlowCondition;
import org.springblade.flow.base.util.FlowJsonUtil;
import org.springblade.flow.engine.custom.constants.BasicActivitiConstants;
import org.springblade.flow.engine.dto.SequenceFlowDTO;
import org.springblade.flow.engine.entity.FlowEngineEntity;
import org.springblade.flow.engine.entity.FlowEngineVisibleEntity;
import org.springblade.flow.engine.enums.FlowNodeTypeEnum;
import org.springblade.flow.engine.mapper.FlowEngineMapper;
import org.springblade.flow.engine.model.flowengine.FlowEngineListVO;
import org.springblade.flow.engine.model.flowengine.FlowExportModel;
import org.springblade.flow.engine.model.flowengine.FlowTreeModel;
import org.springblade.flow.engine.model.flowengine.PaginationFlowEngine;
import org.springblade.flow.engine.model.flowengine.shuntjson.childnode.ChildNode;
import org.springblade.flow.engine.model.flowengine.shuntjson.childnode.ProperCond;
import org.springblade.flow.engine.model.flowengine.shuntjson.childnode.Properties;
import org.springblade.flow.engine.model.flowengine.shuntjson.nodejson.ChildNodeList;
import org.springblade.flow.engine.model.flowengine.shuntjson.nodejson.ConditionList;
import org.springblade.flow.engine.service.FlowEngineService;
import org.springblade.flow.engine.service.FlowEngineVisibleService;
import org.springblade.flow.exception.WorkFlowException;
import org.springblade.flow.permission.entity.UserEntity;
import org.springblade.flow.util.JsonUtil;
import org.springblade.flow.util.RandomUtil;
import org.springblade.flow.util.StringUtil;
import org.springblade.flow.util.UserProvider;
import org.springblade.flow.util.treeutil.SumTree;
import org.springblade.flow.util.treeutil.newtreeutil.TreeDotUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import com.alibaba.druid.util.StringUtils;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;

/**
 * 流程引擎
 *
 * @author JNPF开发平台组
 * @version V3.1.0
 * @copyright 引迈信息技术有限公司
 * @date 2019年9月27日 上午9:18
 */
@Service
public class FlowEngineServiceImpl extends ServiceImpl<FlowEngineMapper, FlowEngineEntity>
		implements FlowEngineService {

	@Autowired
	private UserProvider userProvider;
	@Autowired
	private DictionaryDataService dictionaryDataService;
	@Autowired
	private FlowEngineVisibleService flowEngineVisibleService;
	@Resource
	private RepositoryService repositoryService;

	@Override
	public List<FlowEngineEntity> getList(PaginationFlowEngine pagination) {
		QueryWrapper<FlowEngineEntity> queryWrapper = new QueryWrapper<>();
		if (StringUtil.isNotEmpty(pagination.getKeyword())) {
			queryWrapper.lambda().like(FlowEngineEntity::getFullName, pagination.getKeyword());
		}
		if (StringUtil.isNotEmpty(pagination.getFormType())) {
			queryWrapper.lambda().like(FlowEngineEntity::getFormType, pagination.getFormType());
		}
		if (StringUtil.isNotEmpty(pagination.getEnabledMark())) {
			queryWrapper.lambda().like(FlowEngineEntity::getEnabledMark, pagination.getEnabledMark());
		}
		// 排序
		queryWrapper.lambda().orderByAsc(FlowEngineEntity::getSortCode);
		return this.list(queryWrapper);
	}

	@Override
	public List<FlowEngineEntity> getList() {
		QueryWrapper<FlowEngineEntity> queryWrapper = new QueryWrapper<>();
		queryWrapper.lambda().orderByDesc(FlowEngineEntity::getCreatorTime);
		return this.list(queryWrapper);
	}

	@Override
	public List<FlowEngineEntity> getListAll(List<String> id, String visibleType) {
		QueryWrapper<FlowEngineEntity> queryWrapper = new QueryWrapper<>();
		queryWrapper.lambda().eq(FlowEngineEntity::getEnabledMark, 1).eq(FlowEngineEntity::getType, 0);
		if (id.size() > 0) {
			queryWrapper.lambda()
					.and(t -> t.in(FlowEngineEntity::getId, id).or().like(FlowEngineEntity::getVisibleType, visibleType)

					);
		} else if (StringUtil.isNotEmpty(visibleType)) {
			queryWrapper.lambda().eq(FlowEngineEntity::getVisibleType, visibleType);
		}
		queryWrapper.lambda().orderByAsc(FlowEngineEntity::getSortCode);
		return this.list(queryWrapper);
	}

	@Override
	public List<FlowEngineEntity> getFlowFormList() {
		UserInfo userInfo = userProvider.get();
		List<String> id = new ArrayList<>();
		String visibleType = "";
		if (!userInfo.getIsAdministrator()) {
			// 部分看见(岗位和用户)
			id = flowEngineVisibleService.getVisibleFlowList(userInfo.getUserId()).stream().map(t -> t.getFlowId())
					.collect(Collectors.toList());
			visibleType = "0";
		}
		List<FlowEngineEntity> data = getListAll(id, visibleType);
		return data;
	}

	@Override
	public FlowEngineEntity getInfo(String id) throws WorkFlowException {
		QueryWrapper<FlowEngineEntity> queryWrapper = new QueryWrapper<>();
		queryWrapper.lambda().eq(FlowEngineEntity::getId, id);
		FlowEngineEntity flowEngineEntity = this.getOne(queryWrapper);
		if (flowEngineEntity == null) {
			throw new WorkFlowException("未找到流程引擎");
		}
		return flowEngineEntity;
	}

	@Override
	public FlowEngineEntity getInfoByEnCode(String enCode) throws WorkFlowException {
		QueryWrapper<FlowEngineEntity> queryWrapper = new QueryWrapper<>();
		queryWrapper.lambda().eq(FlowEngineEntity::getEnCode, enCode).eq(FlowEngineEntity::getEnabledMark, 1);
		FlowEngineEntity flowEngineEntity = this.getOne(queryWrapper);
		if (flowEngineEntity == null) {
			throw new WorkFlowException("未找到流程引擎");
		}
		return flowEngineEntity;
	}

	@Override
	public boolean isExistByFullName(String fullName, String id) {
		QueryWrapper<FlowEngineEntity> queryWrapper = new QueryWrapper<>();
		queryWrapper.lambda().eq(FlowEngineEntity::getFullName, fullName);
		if (!StringUtils.isEmpty(id)) {
			queryWrapper.lambda().ne(FlowEngineEntity::getId, id);
		}
		return this.count(queryWrapper) > 0 ? true : false;
	}

	@Override
	public boolean isExistByEnCode(String enCode, String id) {
		QueryWrapper<FlowEngineEntity> queryWrapper = new QueryWrapper<>();
		queryWrapper.lambda().eq(FlowEngineEntity::getEnCode, enCode);
		if (!StringUtils.isEmpty(id)) {
			queryWrapper.lambda().ne(FlowEngineEntity::getId, id);
		}
		return this.count(queryWrapper) > 0 ? true : false;
	}

	@Override
	public void delete(FlowEngineEntity entity) {
		this.removeById(entity.getId());
		QueryWrapper<FlowEngineVisibleEntity> queryWrapper = new QueryWrapper<>();
		queryWrapper.lambda().eq(FlowEngineVisibleEntity::getFlowId, entity.getId());
		flowEngineVisibleService.remove(queryWrapper);
	}

	@Transactional(rollbackFor = Exception.class, propagation = Propagation.REQUIRES_NEW)
	@Override
	public void create(FlowEngineEntity entity) {
		ChildNode childNode = JsonUtil.getJsonToBean(entity.getFlowTemplateJson(), ChildNode.class);
		BpmnModel bpmnModel = assembleBpmnModel(childNode, entity);

		// 部署到activiti
		repositoryService.createDeployment().name(entity.getFullName()).category(entity.getCategory())
				.addBpmnModel(entity.getFullName() + BasicActivitiConstants.bpmnSuffix, bpmnModel).deploy();

		List<FlowEngineVisibleEntity> visibleList = visibleList(entity);
		if (entity.getId() == null) {
			entity.setId(RandomUtil.uuId());
		}
		String userId = userProvider.getUserId();
		entity.setCreatorUser(userId);
		entity.setVisibleType(visibleList.size() == 0 ? 0 : 1);
		this.save(entity);
		for (int i = 0; i < visibleList.size(); i++) {
			visibleList.get(i).setId(RandomUtil.uuId());
			visibleList.get(i).setFlowId(entity.getId());
			visibleList.get(i).setSortCode(RandomUtil.parses());
			flowEngineVisibleService.save(visibleList.get(i));
		}
	}

	private BpmnModel assembleBpmnModel(ChildNode childNode, FlowEngineEntity flowEngineEntity) {
		BpmnModel bpmnModel = new BpmnModel();
		BpmnModelUtils.setBpmnModelInfo(bpmnModel, flowEngineEntity);
		// 获取流程节点
		List<ChildNodeList> childNodeListAll = new ArrayList<>();
		// 获取条件节点
		List<ConditionList> conditionListAll = new ArrayList<>();
		// 递归获取条件数据和节点数据
		FlowJsonUtil.getTemplateAll(childNode, childNodeListAll, conditionListAll);

		// 拿到所有有条件的 name值 , 只有 有条件 key value 才存储到DB ,否则也即造成了资源浪费
		Set<String> set = new HashSet<>();
		for (ConditionList conditionList : conditionListAll) {
			List<ProperCond> conditions = conditionList.getConditions();
			for (ProperCond condition : conditions) {
				String field = condition.getField();
				set.add(field);
			}
		}

		Process process = BpmnModelUtils.createProcess(flowEngineEntity, set);

		Map<String, ChildNodeList> childNodeListMap = convertNodeListToMap(childNodeListAll);
		Map<String, ConditionList> conditionListMap = convertConditionListToMap(conditionListAll);
		Map<String, Object> map = new HashMap<>();
		map.putAll(childNodeListMap);
		map.putAll(conditionListMap);
		// 所有的连线都放在此集合
		List<SequenceFlow> sequenceFlows = new ArrayList<>();
		assembleProcess(childNode, process, sequenceFlows, conditionListMap, map);
		bpmnModel.addProcess(process);
		// 自动生成activiti流程图布局
		new BpmnAutoLayout(bpmnModel).execute();
		return bpmnModel;
	}

	private Process assembleProcess(ChildNode childNode, Process process, List<SequenceFlow> sequenceFlows,
			Map<String, ConditionList> conditionListMap, Map map) {
		StartEvent startEvent = BpmnModelUtils.createStartEvent(process);
		String lastNodeId = bpmnModelBuilder(startEvent.getId(), childNode, process, sequenceFlows, map, null, null,
				null, null);
		EndEvent endEvent = BpmnModelUtils.createEndEvent();
		process.addFlowElement(endEvent);
		String[] lastNodeIds = lastNodeId.split(",");
		for (String nodeId : lastNodeIds) {
			boolean contains = nodeId.contains(".");
			if (!contains) {
				process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(nodeId,
						BasicActivitiConstants.endEventId, sequenceFlows));
			} else {
				String[] split = nodeId.split("[.]");
				String flow = split[1];
				FlowElement flowElement = process.getFlowElement(flow);
				if (flowElement == null) {
					process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(split[0],
							BasicActivitiConstants.endEventId, sequenceFlows, split[1], map, process));
				} else {
					process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(split[0],
							BasicActivitiConstants.endEventId, sequenceFlows, null, map, process));
				}
			}
		}

		// 统一移除 并行网关结束 后面有多条连线的情况(实际上正确的方式递归过程中就应该移除)
		List<ParallelGateway> parallelGateways = process.findFlowElementsOfType(ParallelGateway.class);

		List<ParallelGateway> parallelGatewayEndList = new ArrayList<>();
		// 只是 结束的并行网关
		for (ParallelGateway parallelGateway : parallelGateways) {
			if (parallelGateway.getId().startsWith("parallelGateway-end")) {
				parallelGatewayEndList.add(parallelGateway);
			}
		}

		//
		for (ParallelGateway parallelGateway : parallelGatewayEndList) {
			//
			String id = parallelGateway.getId();
			List<SequenceFlow> containsGatewaySequenceFlows = new ArrayList<>();
			for (SequenceFlow sequenceFlow : sequenceFlows) {
				if (sequenceFlow.getSourceRef().equals(id)) {
					containsGatewaySequenceFlows.add(sequenceFlow);
				}
			}

			// 如果线>1条
			if (containsGatewaySequenceFlows.size() > 1) {
				// 取出第一个
				SequenceFlow sequenceFlow = containsGatewaySequenceFlows.get(0);
				containsGatewaySequenceFlows.remove(sequenceFlow);
				// 移除剩下的
				sequenceFlows.remove(containsGatewaySequenceFlows);
				// 流程图中也要完全移除
				for (SequenceFlow containsGatewaySequenceFlow : containsGatewaySequenceFlows) {
					process.removeFlowElement(containsGatewaySequenceFlow.getId());
				}
			}
		}

		List<SequenceFlow> sequenceFlowList = process.findFlowElementsOfType(SequenceFlow.class);
		// 当拼装完所有元素之后 ,为所有的连线开始设置相应的属性
		// 在递归中不好设置各个连线的信息,也可能是自己功力不够,对于递归把控不好,故只能在递归结束之后设置 gr
		for (String nodeId : conditionListMap.keySet()) {
			for (SequenceFlow sequenceFlow : sequenceFlowList) {
				if (nodeId.equals(sequenceFlow.getId())) {
					ConditionList conditionList = conditionListMap.get(nodeId);
					Boolean isDefault = conditionList.getIsDefault();
					if (isDefault) {
						String sourceRef = sequenceFlow.getSourceRef();// 这个id是 排他网关的id
						ExclusiveGateway exclusiveGateway = (ExclusiveGateway) process.getFlowElement(sourceRef);
						exclusiveGateway.setDefaultFlow(sequenceFlow.getId());
					}
				}
			}
		}

		return process;
	}

	/**
	 * 通过nodeId 获取 对应的表示对象
	 * 如果获取出来的
	 * @param nodeId
	 * @param childNodeListMap
	 * @return
	 */
	private ChildNodeList getSequenceFlowOutNode(String nodeId, Map<String, Object> childNodeListMap) {
		Object o1 = childNodeListMap.get(nodeId);
		if (o1 instanceof ConditionList) {
			String prevId = ((ConditionList) o1).getPrevId();
			return getSequenceFlowOutNode(prevId, childNodeListMap);
		} else {
			return (ChildNodeList) o1;
		}
	}

	private String bpmnModelBuilder(String fromId, ChildNode childNode, Process process,
			List<SequenceFlow> sequenceFlows, Map<String, Object> childNodeListMap,
			/* Boolean flag,SequenceFlowDTO sequenceFlowDTO, */List<String> fromList, String sequenceFlowId,
			Set<String> parallelRootNodeIdSet, Map<String, ChildNode> childNodeMap

	) {
		String type = childNode.getType();
		String nodeId = childNode.getNodeId();
		// 写一个集合存储ChildNode对象的List
		if (childNodeMap == null) {
			childNodeMap = new HashMap<>();
			childNodeMap.put(nodeId, childNode);
		} else {
			childNodeMap.put(nodeId, childNode);
		}
		/**
		 条件类型在连续条件分支的时候 很有可能是空
		 如何判断  条件类型是  分支 还是并行呢???
		 判断  ChildNode的  conditionType 是null && 条件节点有值
		 或者 conditionType 是condition && 条件节点有值
		 ..
		 */
		String conditionType = childNode.getConditionType();
		boolean haschildNode = childNode.getChildNode() != null;
		List<ChildNode> conditionNodes = childNode.getConditionNodes();
		boolean hasconditionNodes = conditionNodes != null;

		if (FlowNodeTypeEnum.CONDITION.getType().equals(type)) {
			// 解析连线对象
			// 得到条件上的条件表达式
			List<ProperCond> conditions = childNode.getProperties().getConditions();
			String content = childNode.getContent();
			String conditionExpression = BpmnModelUtils.parseCondition(conditions);
			String priority = childNode.getProperties().getPriority();
			SequenceFlowDTO currentSequenceFlowDTO = new SequenceFlowDTO();
			currentSequenceFlowDTO.setContent(content);
			currentSequenceFlowDTO.setPriority(priority);
			currentSequenceFlowDTO.setConditionExpression(conditionExpression);
			// 从Map中找到 ChildNodeList对象
			ChildNodeList sequenceFlowOutNode = getSequenceFlowOutNode(nodeId, childNodeListMap);
			if (!hasconditionNodes) {
				// 如果没有子节点
				if (!haschildNode) {
					// 判断一下 firstId
					String num = sequenceFlowOutNode.getCustom().getNum();
					if ("0".equals(num)) { // 外层节点的结束 当走到此if 代表整个大递归 结束了,此时应该返回该元素和end元素相连
						if (org.apache.commons.lang3.StringUtils.isBlank(sequenceFlowId)) {
							return fromId;
						} else {
							return fromId + "." + nodeId;
						}
					}
					// 里层节点
					else if ("1".equals(num)) {
						// 如果是排他网关 获取firstId 对应的childNode
						Boolean isInterflow = childNode.getIsInterflow();
						if (isInterflow == null || !isInterflow) {
							if (org.apache.commons.lang3.StringUtils.isBlank(sequenceFlowId)) {
								return fromId;
							} else {
								return fromId + "." + nodeId;
							}

						}
						// 如果是并行网关
						else {

							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							String[] split = parallelGatewayStartId.split(",");
							if (split.length == 1) { // 处于非嵌套并行网关下

								String[] startId = parallelGatewayStartId.split("-");
								String parallelGatewayEndId = startId[0] + "-end-" + startId[2];

								List<ParallelGateway> parallelGateways = process
										.findFlowElementsOfType(ParallelGateway.class);
								List<String> parallelGatewayIdList = new ArrayList<>();
								for (ParallelGateway parallelGateway : parallelGateways) {
									parallelGatewayIdList.add(parallelGateway.getId());
								}

								//
								if (parallelGatewayIdList.contains(parallelGatewayEndId)) {
									process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,
											parallelGatewayEndId, sequenceFlows));
									return parallelGatewayEndId;
								} else {
									ParallelGateway parallelEndGateway = BpmnModelUtils
											.createParallelEndGatewayWithNodeId(startId[2]);
									process.addFlowElement(parallelEndGateway);
									process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,
											parallelEndGateway.getId(), sequenceFlows));
									return parallelEndGateway.getId();
								}
							} else { // 处于嵌套并行网关下

								List<String> asList = Arrays.asList(split);
								ArrayList<String> arrayList = new ArrayList<>(asList);
								Collections.reverse(arrayList);

								List<ParallelGateway> parallelGateways = process
										.findFlowElementsOfType(ParallelGateway.class);
								List<String> parallelGatewayIdList = new ArrayList<>();
								for (ParallelGateway parallelGateway : parallelGateways) {
									parallelGatewayIdList.add(parallelGateway.getId());
								}

								// 最内层的网关id
								String innnerParallelGatewayId = arrayList.get(0);
								String replace = innnerParallelGatewayId.replace("start", "end");
								// 最外层的网关id
								String outParallelGatewayId = arrayList.get(arrayList.size() - 1);
								String replace1 = outParallelGatewayId.replace("start", "end");

								for (int i = 0; i < arrayList.size(); i++) {
									// 最内层并行网关逻辑
									if (innnerParallelGatewayId.equals(arrayList.get(i))) {
										//
										if (parallelGatewayIdList.contains(replace)) {
											process.addFlowElement(BpmnModelUtils
													.createSequenceFlowWithOutNodeId(fromId, replace, sequenceFlows));
										} else {
											ParallelGateway parallelEndGateway = BpmnModelUtils
													.createParallelEndGatewayWithNodeId(replace.split("-")[2]);
											process.addFlowElement(parallelEndGateway);
											process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(
													fromId, parallelEndGateway.getId(), sequenceFlows));
										}
									}
									// 最外层的情况
									else if (outParallelGatewayId.equals(arrayList.get(i))) {

										if (parallelGatewayIdList.contains(replace1)) {
											continue;
										} else {
											//
											ParallelGateway parallelEndGateway = BpmnModelUtils
													.createParallelEndGatewayWithNodeId(replace1.split("-")[2]);
											process.addFlowElement(parallelEndGateway);
											String s = arrayList.get(i - 1);
											String replace3 = s.replace("start", "end");
											process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(
													replace3, parallelEndGateway.getId(), sequenceFlows));
										}
									}
									// 中间情况
									else {
										String current = arrayList.get(i);
										String replace2 = current.replace("start", "end");
										if (parallelGatewayIdList.contains(replace2)) {
											continue;
										} else {
											ParallelGateway parallelEndGateway = BpmnModelUtils
													.createParallelEndGatewayWithNodeId(replace2.split("-")[2]);
											process.addFlowElement(parallelEndGateway);
											String s = arrayList.get(i - 1);
											String replace3 = s.replace("start", "end");
											process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(
													replace3, parallelEndGateway.getId(), sequenceFlows));
										}
									}

								}

								return replace1;
							}

//                            //递归获取该分支的顶级id
//                            String parallelRootNodeId = getParallelRootNodeId(nodeId, childNodeMap,sequenceFlows);
//                            String parallelGatewayStartId="";//顶级分支节点的上一个节点
//                            for (String pNodeId : parallelRootNodeIdSet) {
//                                ChildNodeList childNodeList = (ChildNodeList) childNodeListMap.get(pNodeId);
//                                String flowId = childNodeList.getCustom().getFlowId();
//                                String[] split = flowId.split(",");
//                                for (String s : split) {
//                                    if(parallelRootNodeId.equals(s)){
//                                        parallelGatewayStartId=pNodeId;
//                                    }
//                                }
//                            }
//
//
//
//
//
//
//                            //通过顶级ID 获取到 并行网关的开始节点id
//                            UserTask userTask = (UserTask) process.getFlowElement(parallelRootNodeId);
//                            String id = userTask.getId();
//
//                            String parallelGatewayNodeId="";
//                            for (SequenceFlow sequenceFlow : sequenceFlows) {
//                                if(sequenceFlow.getTargetRef().equals(id)){
//                                    parallelGatewayNodeId=sequenceFlow.getSourceRef();
//                                }
//                            }
//
//                            //
//                            String[] split = parallelGatewayNodeId.split("-");
//
//                            List<ParallelGateway> parallelGateways = process.findFlowElementsOfType(ParallelGateway.class);
//                            //可以得到当前并行网关节点的endId
//                            String parallelGatewayEndId="parallelGateway-end-"+split[2];
//
//                            //
//                            List<String> parallelGatewayIdList=new ArrayList<>();
//                            for (ParallelGateway parallelGateway : parallelGateways) {
//                                parallelGatewayIdList.add(parallelGateway.getId());
//                            }
//
//
//                            if(parallelGatewayIdList.contains(parallelGatewayEndId)){
//                                process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,parallelGatewayEndId,sequenceFlows));
//                                return parallelGatewayEndId;
//                            }
//                            else{
//                                ParallelGateway parallelEndGateway = BpmnModelUtils.createParallelEndGatewayWithNodeId(split[2]);
//                                process.addFlowElement(parallelEndGateway);
//                                process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,parallelEndGateway.getId(),sequenceFlows));
//                                return parallelEndGateway.getId();
//                            }

							/*
							 * List<ParallelGateway> parallelGatewayList =
							 * process.findFlowElementsOfType(ParallelGateway.class); List<ParallelGateway>
							 * parallelStartGatewayList =new ArrayList<>(); List<ParallelGateway>
							 * parallelEndGatewayList =new ArrayList<>(); for (ParallelGateway
							 * parallelGateway : parallelGatewayList) {
							 * if(parallelGateway.getId().contains("end")){ //
							 * parallelEndGatewayList.add(parallelGateway); } else{
							 * parallelStartGatewayList.add(parallelGateway); } }
							 * 
							 * if(parallelStartGatewayList.size()%2!=0){ if(parallelEndGatewayList==null ||
							 * parallelEndGatewayList.isEmpty()){ //代表这是创建的第一个 并行网关的结束 //应该创建并行网关的结束
							 * ParallelGateway parallelGateway = BpmnModelUtils.createParallelEndGateway();
							 * process.addFlowElement(parallelGateway);
							 * process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,
							 * parallelGateway.getId(),sequenceFlows)); return parallelGateway.getId(); }
							 * int startSize = parallelStartGatewayList.size(); int endSize =
							 * parallelEndGatewayList.size(); if(endSize!=startSize){ //应该创建并行网关的结束
							 * ParallelGateway parallelGateway = BpmnModelUtils.createParallelEndGateway();
							 * process.addFlowElement(parallelGateway);
							 * process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,
							 * parallelGateway.getId(),sequenceFlows)); return parallelGateway.getId(); }
							 * else{ ParallelGateway parallelGateway =
							 * parallelEndGatewayList.get(parallelEndGatewayList.size() - 1);
							 * process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,
							 * parallelGateway.getId(),sequenceFlows)); return parallelGateway.getId(); } }
							 * else{ if(parallelEndGatewayList==null || parallelEndGatewayList.isEmpty()){
							 * //代表这是创建的第一个 并行网关的结束 //应该创建并行网关的结束 ParallelGateway parallelGateway =
							 * BpmnModelUtils.createParallelEndGateway();
							 * process.addFlowElement(parallelGateway);
							 * process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,
							 * parallelGateway.getId(),sequenceFlows)); return parallelGateway.getId(); }
							 * int startSize = parallelStartGatewayList.size(); int endSize =
							 * parallelEndGatewayList.size(); if(endSize!=startSize){ //应该创建并行网关的结束
							 * ParallelGateway parallelGateway = BpmnModelUtils.createParallelEndGateway();
							 * process.addFlowElement(parallelGateway);
							 * process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,
							 * parallelGateway.getId(),sequenceFlows)); return parallelGateway.getId(); }
							 * else{ ParallelGateway parallelGateway =
							 * parallelEndGatewayList.get(parallelEndGatewayList.size() - 1);
							 * process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(fromId,
							 * parallelGateway.getId(),sequenceFlows)); return parallelGateway.getId(); } }
							 */

						}
					} else {
						throw new RuntimeException("不识别的外里层节点类型");
					}
				} else {
					String parallelGatewayStartId = childNode.getParallelGatewayStartId();
					if (org.apache.commons.lang3.StringUtils.isNotBlank(parallelGatewayStartId)) {
						// 将此连带下去
						childNode.getChildNode().setParallelGatewayStartId(parallelGatewayStartId);
					}

					// 有子节点
					return bpmnModelBuilder(fromId, childNode.getChildNode(), process, sequenceFlows, childNodeListMap,
							null, sequenceFlowId, parallelRootNodeIdSet, childNodeMap);
				}
			} else {

				if (!haschildNode) {
					// 如果有条件节点 但是没有子节点
					List<String> list = new ArrayList<>();// 逗号隔开各个连接结束节点的节点
					String gatewayId = "";
					// 判断条件节点的前面接什么网关
					if (conditionType == null || FlowCondition.CONDITION.equals(conditionType)) {
						// 先创建排他网关
						ExclusiveGateway exclusiveGateway = BpmnModelUtils.createExclusiveGateway();
						gatewayId = exclusiveGateway.getId();
						process.addFlowElement(exclusiveGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(fromId, gatewayId,
								sequenceFlows, sequenceFlowId, childNodeListMap, process));

						// 遍历条件节点
						for (ChildNode conditionNode : conditionNodes) {
							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							if (org.apache.commons.lang3.StringUtils.isNotBlank(parallelGatewayStartId)) {
								conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
							}
//                            String parallelGatewayStartId = childNode.getParallelGatewayStartId();
//                            if(StringUtils.isBlank(parallelGatewayStartId)){
//                                conditionNode.setParallelGatewayStartId(gatewayId);
//                            }
//                            else{
//                                parallelGatewayStartId+=",";
//                                parallelGatewayStartId+=gatewayId;
//                                conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
//                            }

							sequenceFlowId = conditionNode.getNodeId();
							String lastNodeId = bpmnModelBuilder(gatewayId, conditionNode, process, sequenceFlows,
									childNodeListMap, null, sequenceFlowId, parallelRootNodeIdSet, childNodeMap);
//                        list.add(lastNodeId);
							String[] split = lastNodeId.split(",");
							list.addAll(new ArrayList<>(Arrays.asList(split)));
						}
					}

					else {
						ExclusiveGateway exclusiveGateway = BpmnModelUtils.createExclusiveGateway();
						String exclusiveGatewayId = exclusiveGateway.getId();
						process.addFlowElement(exclusiveGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(fromId, exclusiveGatewayId,
								sequenceFlows, sequenceFlowId, childNodeListMap, process));
						// 并行网关的逻辑
						ParallelGateway parallelGateway = BpmnModelUtils.createParallelStartGateway();
						gatewayId = parallelGateway.getId();
						process.addFlowElement(parallelGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(exclusiveGatewayId,
								gatewayId, sequenceFlows));
						// 为集合添加 并行网关 的previous节点
						if (parallelRootNodeIdSet == null) {
							parallelRootNodeIdSet = new HashSet<>();
							parallelRootNodeIdSet.add(nodeId);
						} else {
							parallelRootNodeIdSet.add(nodeId);
						}
						// 遍历条件节点
						for (ChildNode conditionNode : conditionNodes) {
							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							if (org.apache.commons.lang3.StringUtils.isBlank(parallelGatewayStartId)) {
								conditionNode.setParallelGatewayStartId(gatewayId);
							} else {
								parallelGatewayStartId += ",";
								parallelGatewayStartId += gatewayId;
								conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
							}
							String lastNodeId = bpmnModelBuilder(gatewayId, conditionNode, process, sequenceFlows,
									childNodeListMap, null, null, parallelRootNodeIdSet, childNodeMap);
//                        list.add(lastNodeId);
							String[] split = lastNodeId.split(",");
							list.addAll(new ArrayList<>(Arrays.asList(split)));
						}
					}
					return org.apache.commons.lang3.StringUtils.join(list, ",");
				}
				// 有条件节点, 有子节点
				else {
					// 先遍历子节点
//                    bpmnModelBuilder(fromId,childNode.getChildNode(),process,sequenceFlows,childNodeListMap,false,null,null);
					List<String> list = new ArrayList<>();
//                    Set<String> set = new HashSet<>();// 逗号隔开各个连接结束节点的节点
					String gatewayId = "";
					// 判断条件节点的前面接什么网关
					if (conditionType == null || FlowCondition.CONDITION.equals(conditionType)) {
						// 先创建排他网关
						ExclusiveGateway exclusiveGateway = BpmnModelUtils.createExclusiveGateway();
						gatewayId = exclusiveGateway.getId();
						process.addFlowElement(exclusiveGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(fromId, gatewayId,
								sequenceFlows, sequenceFlowId, childNodeListMap, process));

						// 遍历条件节点
						for (ChildNode conditionNode : conditionNodes) {
							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							if (org.apache.commons.lang3.StringUtils.isNotBlank(parallelGatewayStartId)) {
								conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
							}

//                            String parallelGatewayStartId = childNode.getParallelGatewayStartId();
//                            if(StringUtils.isBlank(parallelGatewayStartId)){
//                                conditionNode.setParallelGatewayStartId(gatewayId);
//                            }
//                            else{
//                                parallelGatewayStartId+=",";
//                                parallelGatewayStartId+=gatewayId;
//                                conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
//                            }

							sequenceFlowId = conditionNode.getNodeId();
							String lastNodeId = bpmnModelBuilder(gatewayId, conditionNode, process, sequenceFlows,
									childNodeListMap, null, sequenceFlowId, parallelRootNodeIdSet, childNodeMap);
							String[] split = lastNodeId.split(",");
							list.addAll(new ArrayList<>(Arrays.asList(split)));
						}
					} else {
						ExclusiveGateway exclusiveGateway = BpmnModelUtils.createExclusiveGateway();
						String exclusiveGatewayId = exclusiveGateway.getId();
						process.addFlowElement(exclusiveGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(fromId, exclusiveGatewayId,
								sequenceFlows, sequenceFlowId, childNodeListMap, process));
						// 并行网关的逻辑
						ParallelGateway parallelGateway = BpmnModelUtils.createParallelStartGateway();
						gatewayId = parallelGateway.getId();
						process.addFlowElement(parallelGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(exclusiveGatewayId,
								gatewayId, sequenceFlows));
						// 为集合添加 并行网关 的previous节点
						if (parallelRootNodeIdSet == null) {
							parallelRootNodeIdSet = new HashSet<>();
							parallelRootNodeIdSet.add(nodeId);
						} else {
							parallelRootNodeIdSet.add(nodeId);
						}
						// 遍历条件节点
						for (ChildNode conditionNode : conditionNodes) {
							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							if (org.apache.commons.lang3.StringUtils.isBlank(parallelGatewayStartId)) {
								conditionNode.setParallelGatewayStartId(gatewayId);
							} else {
								parallelGatewayStartId += ",";
								parallelGatewayStartId += gatewayId;
								conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
							}
							String lastNodeId = bpmnModelBuilder(gatewayId, conditionNode, process, sequenceFlows,
									childNodeListMap, null, null, parallelRootNodeIdSet, childNodeMap);
							String[] split = lastNodeId.split(",");
							list.addAll(new ArrayList<>(Arrays.asList(split)));
						}
					}
					fromList = new ArrayList<>();
					for (String from : list) {
						String[] split = from.split(",");
						fromList.addAll(Arrays.asList(split));
					}
//                    Set<String> set = new HashSet<>(fromList);
//                    fromList=new ArrayList<>(set);
					String one = fromList.get(0);
					fromList.remove(0);
					// 先遍历子节点
					String nodeIds = bpmnModelBuilder(one, childNode.getChildNode(), process, sequenceFlows,
							childNodeListMap, fromList, null, parallelRootNodeIdSet, childNodeMap);
//                    list.add(nodeIds);
//                    String[] split = nodeIds.split(",");
//                    set.addAll(Arrays.asList(split));
					return org.apache.commons.lang3.StringUtils.join(nodeIds, ",");
				}
			}

		}

		// 除了连线 剩下的元素组件都是一种类型
		else {
			ChildNodeList childNodeList = (ChildNodeList) childNodeListMap.get(childNode.getNodeId());
			String userTaskId = "";
			// 用户节点
			if (FlowNodeTypeEnum.APPROVER.getType().equals(type) || FlowNodeTypeEnum.START.getType().equals(type)) {
				userTaskId = BpmnModelUtils.createUserTask(fromId, childNode, process, sequenceFlows, childNodeList);
			}
			// 手工节点(抄送\邮件\站内信\钉钉\短信\微信)
			else if (FlowNodeTypeEnum.COPY.getType().equals(type) || FlowNodeTypeEnum.MAIL.getType().equals(type)
					|| FlowNodeTypeEnum.DING.getType().equals(type) || FlowNodeTypeEnum.WX.getType().equals(type)
					|| FlowNodeTypeEnum.DX.getType().equals(type) || FlowNodeTypeEnum.ZHAN.getType().equals(type)) {
				userTaskId = BpmnModelUtils.createManualTask(fromId, childNode, process, sequenceFlows, childNodeList);
			}
			// 定时器
			else if (FlowNodeTypeEnum.TIMER.getType().equals(type)) {
				userTaskId = BpmnModelUtils.createReceiveTask(fromId, childNode, process, sequenceFlows, childNodeList);
			}
			// 子流程
			else if (FlowNodeTypeEnum.CALL_ACTIVITY.getType().equals(type)) {
				userTaskId = BpmnModelUtils.createCallActivity(fromId, childNode, process, sequenceFlows,
						childNodeList);
			}
			// 业务编排
			else if (FlowNodeTypeEnum.SERVICE_TASK.getType().equals(type)) {
				userTaskId = BpmnModelUtils.createServiceTask(fromId, childNode, process, sequenceFlows, childNodeList);
			}
			// 请求编排
			else if (FlowNodeTypeEnum.HTTP_TASK.getType().equals(type)) {
				userTaskId = BpmnModelUtils.createHttpServiceTask(fromId, childNode, process, sequenceFlows,
						childNodeList);
			}
			// 运维编排
			else if (FlowNodeTypeEnum.SHELL_TASK.getType().equals(type)) {
				userTaskId = BpmnModelUtils.createShellTask(fromId, childNode, process, sequenceFlows, childNodeList);
			}
			// 脚本编排
			else if (FlowNodeTypeEnum.SCRIPT_TASK.getType().equals(type)) {
				userTaskId = BpmnModelUtils.createScriptTask(fromId, childNode, process, sequenceFlows, childNodeList);
			} else {
				throw new WorkFlowException("暂不支持此类型节点");
			}

			// 此flag目前已弃用
//            if(flag){
////              if(StringUtils.isNotBlank(fromId)){
//                  String conditionExpression = sequenceFlowDTO.getConditionExpression();
//                  String content = sequenceFlowDTO.getContent();
//                  String priority = sequenceFlowDTO.getPriority();
//                  SequenceFlow sequenceFlow = BpmnModelUtils.createSequenceFlowWithExpression
//                          (fromId, userTaskId, sequenceFlows, conditionExpression,content);
//                  process.addFlowElement(sequenceFlow) ;
//                  if("2".equals(priority)){
//                      ExclusiveGateway exclusiveGateway = (ExclusiveGateway) process.getFlowElement(fromId);
//                      exclusiveGateway.setDefaultFlow(sequenceFlow.getId());
//                  }
////              }
////              else{
////                  throw  new RuntimeException("不可能走到这种情况");
////              }
//            }
//            else{
			boolean b = fromId.contains(".");
			if (!b) {
				String flow = sequenceFlowId;
				FlowElement flowElement = process.getFlowElement(flow);
				if (flowElement == null) {
					process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(fromId, userTaskId,
							sequenceFlows, sequenceFlowId, childNodeListMap, process));
				} else {
					process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(fromId, userTaskId,
							sequenceFlows, null, childNodeListMap, process));
				}

			} else {
				String[] split = fromId.split("[.]");
				String flow = split[1];
				FlowElement flowElement = process.getFlowElement(flow);
				if (flowElement == null) {
					process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(split[0], userTaskId,
							sequenceFlows, split[1], childNodeListMap, process));
				} else {
					process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(split[0], userTaskId,
							sequenceFlows, null, childNodeListMap, process));
				}

			}
			if (fromList != null && !fromList.isEmpty()) {
				for (String from : fromList) {
					boolean contains = from.contains(".");
					if (!contains) {
						process.addFlowElement(
								BpmnModelUtils.createSequenceFlowWithOutNodeId(from, userTaskId, sequenceFlows));
					} else {
						String[] split = from.split("[.]");

						String flow = split[1];
						FlowElement flowElement = process.getFlowElement(flow);
						if (flowElement == null) {
							process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(split[0], userTaskId,
									sequenceFlows, split[1], childNodeListMap, process));
						} else {
							process.addFlowElement(BpmnModelUtils.createSequenceFlowWithNodeId(split[0], userTaskId,
									sequenceFlows, null, childNodeListMap, process));
						}

					}
				}
			}
//            }
			// 从Map中找到 ChildNodeList对象
			ChildNodeList nodeList = (ChildNodeList) childNodeListMap.get(nodeId);
			// 如果没有条件节点
			if (!hasconditionNodes) {
				// 如果没有子节点
				if (!haschildNode) {
					// 判断一下 firstId
					String num = nodeList.getCustom().getNum();
					if ("0".equals(num)) { // 外层节点的结束 当走到此if 代表整个大递归 结束了,此时应该返回该元素和end元素相连
						if (org.apache.commons.lang3.StringUtils.isBlank(sequenceFlowId)) {
							return userTaskId;
						} else {
							return userTaskId + "." + sequenceFlowId;
						}
					}
					// 里层节点
					else if ("1".equals(num)) {
						// 如果是排他网关 获取firstId 对应的childNode
						Boolean isInterflow = childNode.getIsInterflow();
//                        if( isInterflow==null ||!isInterflow){
						if (org.apache.commons.lang3.StringUtils.isBlank(childNode.getParallelGatewayStartId())) {
							if (org.apache.commons.lang3.StringUtils.isBlank(sequenceFlowId)) {
								return userTaskId;
							} else {
								return userTaskId + "." + sequenceFlowId;
							}
//                            String firstId = nodeList.getCustom().getFirstId();
//                            if(StringUtils.isBlank(firstId)){//当走到此if, 代表 里层节点也遍历完毕, 应该是此元素和end元素进行相连
//                                return userTaskId;
//                            }
							//
//                            else{
//                                //当前这个元素id 和  外层节点元素相连
//                                process.addFlowElement(BpmnModelUtils.createSequenceFlow(userTaskId,firstId,sequenceFlows));
//                                return "end";//代表里层节点循环完毕
//                            }
						}
						// 如果是并行网关
						else {

							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							String[] split = parallelGatewayStartId.split(",");
							if (split.length == 1) { // 处于非嵌套并行网关下

								String[] startId = parallelGatewayStartId.split("-");
								String parallelGatewayEndId = startId[0] + "-end-" + startId[2];

								List<ParallelGateway> parallelGateways = process
										.findFlowElementsOfType(ParallelGateway.class);
								List<String> parallelGatewayIdList = new ArrayList<>();
								for (ParallelGateway parallelGateway : parallelGateways) {
									parallelGatewayIdList.add(parallelGateway.getId());
								}

								//
								if (parallelGatewayIdList.contains(parallelGatewayEndId)) {
									process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,
											parallelGatewayEndId, sequenceFlows));
									return parallelGatewayEndId;
								} else {
									ParallelGateway parallelEndGateway = BpmnModelUtils
											.createParallelEndGatewayWithNodeId(startId[2]);
									process.addFlowElement(parallelEndGateway);
									process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,
											parallelEndGateway.getId(), sequenceFlows));
									return parallelEndGateway.getId();
								}
							} else { // 处于嵌套并行网关下

								List<String> asList = Arrays.asList(split);
								ArrayList<String> arrayList = new ArrayList<>(asList);
								Collections.reverse(arrayList);

								List<ParallelGateway> parallelGateways = process
										.findFlowElementsOfType(ParallelGateway.class);
								List<String> parallelGatewayIdList = new ArrayList<>();
								for (ParallelGateway parallelGateway : parallelGateways) {
									parallelGatewayIdList.add(parallelGateway.getId());
								}

								// 最内层的网关id
								String innnerParallelGatewayId = arrayList.get(0);
								String replace = innnerParallelGatewayId.replace("start", "end");
								// 最外层的网关id
								String outParallelGatewayId = arrayList.get(arrayList.size() - 1);
								String replace1 = outParallelGatewayId.replace("start", "end");

								for (int i = 0; i < arrayList.size(); i++) {
									// 最内层并行网关逻辑
									if (innnerParallelGatewayId.equals(arrayList.get(i))) {
										//
										if (parallelGatewayIdList.contains(replace)) {
											process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(
													userTaskId, replace, sequenceFlows));
										} else {
											ParallelGateway parallelEndGateway = BpmnModelUtils
													.createParallelEndGatewayWithNodeId(replace.split("-")[2]);
											process.addFlowElement(parallelEndGateway);
											process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(
													userTaskId, parallelEndGateway.getId(), sequenceFlows));
										}
									}
									// 最外层的情况
									else if (outParallelGatewayId.equals(arrayList.get(i))) {

										if (parallelGatewayIdList.contains(replace1)) {
											continue;
										} else {
											//
											ParallelGateway parallelEndGateway = BpmnModelUtils
													.createParallelEndGatewayWithNodeId(replace1.split("-")[2]);
											process.addFlowElement(parallelEndGateway);
											String s = arrayList.get(i - 1);
											String replace2 = s.replace("start", "end");
											process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(
													replace2, parallelEndGateway.getId(), sequenceFlows));
										}
									}
									// 中间情况
									else {
										String current = arrayList.get(i);
										String replace2 = current.replace("start", "end");
										if (parallelGatewayIdList.contains(replace2)) {
											continue;
										} else {
											ParallelGateway parallelEndGateway = BpmnModelUtils
													.createParallelEndGatewayWithNodeId(replace2.split("-")[2]);
											process.addFlowElement(parallelEndGateway);
											String s = arrayList.get(i - 1);
											String replace3 = s.replace("start", "end");
											process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(
													replace3, parallelEndGateway.getId(), sequenceFlows));
										}
									}

								}

								return replace1;
							}

//                                    String s = arrayList.get(i);
//                                    String[] split1 = s.split("-");
//                                    String parallelGatewayEndId=split1[0]+"-end-"+split1[2];
							//
//                                    if(parallelGatewayIdList.contains(parallelGatewayEndId)){
//                                        process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,parallelGatewayEndId,sequenceFlows));
//                                    }
//                                    else{
//                                        ParallelGateway parallelEndGateway = BpmnModelUtils.createParallelEndGatewayWithNodeId(split1[2]);
//                                        process.addFlowElement(parallelEndGateway);
//                                        process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,parallelEndGateway.getId(),sequenceFlows));
//                                        return parallelEndGateway.getId();
//                                    }

//                                for (int i = split.length - 1; i >= 0; i--) {
//
//                                    //
//                                    String startId =split[i];
//                                    String[] split1 = startId.split("-");
//                                    String parallelGatewayEndId=split1[0]+"-end-"+split1[2];
//
//                                    List<ParallelGateway> parallelGateways = process.findFlowElementsOfType(ParallelGateway.class);
//                                    List<String> parallelGatewayIdList=new ArrayList<>();
//                                    for (ParallelGateway parallelGateway : parallelGateways) {
//                                        parallelGatewayIdList.add(parallelGateway.getId());
//                                    }
//
//
//                                    //
//                                    if(parallelGatewayIdList.contains(parallelGatewayEndId)){
//                                        process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,parallelGatewayEndId,sequenceFlows));
////                                        return parallelGatewayEndId;
//                                    }
//                                    else{
//                                        ParallelGateway parallelEndGateway = BpmnModelUtils.createParallelEndGatewayWithNodeId(startId[2]);
//                                        process.addFlowElement(parallelEndGateway);
//                                        process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,parallelEndGateway.getId(),sequenceFlows));
//                                        return parallelEndGateway.getId();
//                                    }
//
//                                }

//                            //递归获取该分支的顶级id
//                            String parallelRootNodeId = getParallelRootNodeId(nodeId, childNodeMap,sequenceFlows);
//                            String parallelGatewayStartId="";//当前节点顶级分支节点的上一个节点id
//                            for (String pNodeId : parallelRootNodeIdSet) {
//                                ChildNodeList childNodeList = (ChildNodeList) childNodeListMap.get(pNodeId);
//                                String flowId = childNodeList.getCustom().getFlowId();
//                                String[] split = flowId.split(",");
//                                for (String s : split) {
//                                    if(parallelRootNodeId.equals(s)){
//                                        parallelGatewayStartId=pNodeId;
//                                    }
//                                }
//                            }
//                            //当前节点顶级分支节点的上一个节点对象
//                            ChildNode prevChildNode = childNodeMap.get(parallelGatewayStartId);
//                            Boolean prevChildNodeIsInterflow = prevChildNode.getIsInterflow();
//
//                            //
//                            UserTask userTask = (UserTask) process.getFlowElement(parallelRootNodeId);
//                            String id = userTask.getId();
//                            String parallelGatewayNodeId="";
//                            for (SequenceFlow sequenceFlow : sequenceFlows) {
//                                if(sequenceFlow.getTargetRef().equals(id)){
//                                    parallelGatewayNodeId=sequenceFlow.getSourceRef();
//                                }
//                            }
//
//                            String[] split = parallelGatewayNodeId.split("-");
//
//                            List<ParallelGateway> parallelGateways = process.findFlowElementsOfType(ParallelGateway.class);
//                            //可以得到当前并行网关节点的endId
//                            String parallelGatewayEndId="parallelGateway-end-"+split[2];
//
//                            //
//                            List<String> parallelGatewayIdList=new ArrayList<>();
//                            for (ParallelGateway parallelGateway : parallelGateways) {
//                                parallelGatewayIdList.add(parallelGateway.getId());
//                            }
//
//
//
//                            //如果为true 则代表当前节点 处于 嵌套并行网关的情况下
//                            if(prevChildNodeIsInterflow){
//                                //获取当前节点顶级节点的 id 的 上一个节点的 顶级id的  节点
//                                String prevChildNodeNodeId = prevChildNode.getNodeId();
//
//                                String prevParallelRootNodeId = getParallelRootNodeId(prevChildNodeNodeId, childNodeMap,sequenceFlows);
//
//                                UserTask prevUserTask = (UserTask) process.getFlowElement(prevParallelRootNodeId);
//                                String  prevUserTaskId = prevUserTask.getId();
//                                String prevParallelGatewayNodeId="";
//                                for (SequenceFlow sequenceFlow : sequenceFlows) {
//                                    if(sequenceFlow.getTargetRef().equals(prevUserTaskId)){
//                                        prevParallelGatewayNodeId=sequenceFlow.getSourceRef();
//                                    }
//                                }
//
//                                String[] tempSplit = prevParallelGatewayNodeId.split("-");
//
//                                List<ParallelGateway> prevParallelGateways = process.findFlowElementsOfType(ParallelGateway.class);
//                                //可以得到当前并行网关节点的endId
//                                String prevParallelGatewayEndId="parallelGateway-end-"+tempSplit[2];
//
//                                //
//                                List<String> prevParallelGatewayIdList=new ArrayList<>();
//                                for (ParallelGateway parallelGateway : prevParallelGateways) {
//                                    prevParallelGatewayIdList.add(parallelGateway.getId());
//                                }
//
//
//                                //先判断内层结束是否创建
//                                if(parallelGatewayIdList.contains(parallelGatewayEndId)){
//
//                                    process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,parallelGatewayEndId,sequenceFlows));
//
//                                    //
//                                    if(prevParallelGatewayIdList.contains(prevParallelGatewayEndId)){
//                                        //如果存在 ,那么 需要是内层的连接外层的
//                                        process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(parallelGatewayEndId,prevParallelGatewayEndId,sequenceFlows));
//                                        //同时 return 最外层的 并行网关结束节点id
//                                        return prevParallelGatewayEndId;
//                                    }
//                                    else{
//                                        //如果不存在 先创建内层的
//                                        ParallelGateway parallelEndGateway = BpmnModelUtils.createParallelEndGatewayWithNodeId(split[2]);
//                                        process.addFlowElement(parallelEndGateway);
//                                        process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,parallelEndGateway.getId(),sequenceFlows));
//                                        //
//                                        //判断上一个节点的并行网关的结束是否存在
//                                        if(prevParallelGatewayIdList.contains(prevParallelGatewayEndId)){
//                                            //如果存在 ,那么 需要是内层的连接外层的
//                                            process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(parallelGatewayEndId,prevParallelGatewayEndId,sequenceFlows));
//                                            //同时 return 最外层的 并行网关结束节点id
//                                            return prevParallelGatewayEndId;
//                                        }
//
//
//
//                                    }
//
//                                }
//
//                                //内层元素还没有创建
//                                else{
//
//                                }
//
//
//
//
//
//
//
//                            }
//                            //单个并行网关的结束
//                            else{
//                                if(parallelGatewayIdList.contains(parallelGatewayEndId)){
//                                    process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,parallelGatewayEndId,sequenceFlows));
//                                    return parallelGatewayEndId;
//                                }
//                                else{
//                                    ParallelGateway parallelEndGateway = BpmnModelUtils.createParallelEndGatewayWithNodeId(split[2]);
//                                    process.addFlowElement(parallelEndGateway);
//                                    process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,parallelEndGateway.getId(),sequenceFlows));
//                                    return parallelEndGateway.getId();
//                                }
//                            }

						}
					} else {
						throw new RuntimeException("不识别的外里层节点类型");
					}
				} else {
					// 有子节点
					String parallelGatewayStartId = childNode.getParallelGatewayStartId();
					if (org.apache.commons.lang3.StringUtils.isNotBlank(parallelGatewayStartId)) {
						// 将此连带下去
						childNode.getChildNode().setParallelGatewayStartId(parallelGatewayStartId);
					}
					return bpmnModelBuilder(userTaskId, childNode.getChildNode(), process, sequenceFlows,
							childNodeListMap, null, null, parallelRootNodeIdSet, childNodeMap);
				}
			} else {
				// 如果有条件节点 但是没有子节点
				if (!haschildNode) {
					String gatewayId = "";
					List<String> list = new ArrayList<>();// 逗号隔开各个连接结束节点的节点
					// 判断条件节点的前面接什么网关
					if (conditionType == null || FlowCondition.CONDITION.equals(conditionType)) {
						// 先创建排他网关
						ExclusiveGateway exclusiveGateway = BpmnModelUtils.createExclusiveGateway();
						gatewayId = exclusiveGateway.getId();
						process.addFlowElement(exclusiveGateway);
						process.addFlowElement(
								BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId, gatewayId, sequenceFlows));

						// 遍历条件节点
						for (ChildNode conditionNode : conditionNodes) {

							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							if (org.apache.commons.lang3.StringUtils.isNotBlank(parallelGatewayStartId)) {
								conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
							}
//                            if(StringUtils.isBlank(parallelGatewayStartId)){
//                                conditionNode.setParallelGatewayStartId(gatewayId);
//                            }
//                            else{
//                                parallelGatewayStartId+=",";
//                                parallelGatewayStartId+=gatewayId;
//                                conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
//                            }

							sequenceFlowId = conditionNode.getNodeId();
							String lastNodeId = bpmnModelBuilder(gatewayId, conditionNode, process, sequenceFlows,
									childNodeListMap, null, sequenceFlowId, parallelRootNodeIdSet, childNodeMap);
							String[] split = lastNodeId.split(",");
							list.addAll(new ArrayList<>(Arrays.asList(split)));
						}
					}

					else {
						ExclusiveGateway exclusiveGateway = BpmnModelUtils.createExclusiveGateway();
						String exclusiveGatewayId = exclusiveGateway.getId();
						process.addFlowElement(exclusiveGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,
								exclusiveGatewayId, sequenceFlows));
						// 并行网关的逻辑
						ParallelGateway parallelGateway = BpmnModelUtils.createParallelStartGateway();
						gatewayId = parallelGateway.getId();
						process.addFlowElement(parallelGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(exclusiveGatewayId,
								gatewayId, sequenceFlows));

						// 为集合添加 并行网关 的previous节点
						if (parallelRootNodeIdSet == null) {
							parallelRootNodeIdSet = new HashSet<>();
							parallelRootNodeIdSet.add(nodeId);
						} else {
							parallelRootNodeIdSet.add(nodeId);
						}
						// 遍历条件节点
						for (ChildNode conditionNode : conditionNodes) {
							//
							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							if (org.apache.commons.lang3.StringUtils.isBlank(parallelGatewayStartId)) {
								conditionNode.setParallelGatewayStartId(gatewayId);
							} else {
								parallelGatewayStartId += ",";
								parallelGatewayStartId += gatewayId;
								conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
							}
//                            sequenceFlowId=conditionNode.getNodeId();
							String lastNodeId = bpmnModelBuilder(gatewayId, conditionNode, process, sequenceFlows,
									childNodeListMap, null, null, parallelRootNodeIdSet, childNodeMap);
							String[] split = lastNodeId.split(",");
							list.addAll(new ArrayList<>(Arrays.asList(split)));
						}
					}

					return org.apache.commons.lang3.StringUtils.join(list, ",");
				}
				// 有条件节点, 有子节点
				else {
					String gatewayId = "";
					List<String> list = new ArrayList<>();
//                    Set<String> set = new HashSet<>();// 逗号隔开各个连接结束节点的节点
					// 判断条件节点的前面接什么网关
					if (conditionType == null || FlowCondition.CONDITION.equals(conditionType)) {
						// 先创建排他网关
						ExclusiveGateway exclusiveGateway = BpmnModelUtils.createExclusiveGateway();
						gatewayId = exclusiveGateway.getId();
						process.addFlowElement(exclusiveGateway);
						process.addFlowElement(
								BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId, gatewayId, sequenceFlows));

						// 遍历条件节点
						for (ChildNode conditionNode : conditionNodes) {
							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							if (org.apache.commons.lang3.StringUtils.isNotBlank(parallelGatewayStartId)) {
								conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
							}
//                            String parallelGatewayStartId = childNode.getParallelGatewayStartId();
//                            if(StringUtils.isBlank(parallelGatewayStartId)){
//                                conditionNode.setParallelGatewayStartId(gatewayId);
//                            }
//                            else{
//                                parallelGatewayStartId+=",";
//                                parallelGatewayStartId+=gatewayId;
//                                conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
//                            }

							sequenceFlowId = conditionNode.getNodeId();
							String lastNodeId = bpmnModelBuilder(gatewayId, conditionNode, process, sequenceFlows,
									childNodeListMap, null, sequenceFlowId, parallelRootNodeIdSet, childNodeMap);
							String[] split = lastNodeId.split(",");
							list.addAll(new ArrayList<>(Arrays.asList(split)));
						}

					} else {
						ExclusiveGateway exclusiveGateway = BpmnModelUtils.createExclusiveGateway();
						String exclusiveGatewayId = exclusiveGateway.getId();
						process.addFlowElement(exclusiveGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(userTaskId,
								exclusiveGatewayId, sequenceFlows));
						// 并行网关的逻辑
						ParallelGateway parallelGateway = BpmnModelUtils.createParallelStartGateway();
						gatewayId = parallelGateway.getId();
						process.addFlowElement(parallelGateway);
						process.addFlowElement(BpmnModelUtils.createSequenceFlowWithOutNodeId(exclusiveGatewayId,
								gatewayId, sequenceFlows));

						// 为集合添加 并行网关 的previous节点
						if (parallelRootNodeIdSet == null) {
							parallelRootNodeIdSet = new HashSet<>();
							parallelRootNodeIdSet.add(nodeId);
						} else {
							parallelRootNodeIdSet.add(nodeId);
						}

						// 遍历条件节点
						for (ChildNode conditionNode : conditionNodes) {
							String parallelGatewayStartId = childNode.getParallelGatewayStartId();
							if (org.apache.commons.lang3.StringUtils.isBlank(parallelGatewayStartId)) {
								conditionNode.setParallelGatewayStartId(gatewayId);
							} else {
								parallelGatewayStartId += ",";
								parallelGatewayStartId += gatewayId;
								conditionNode.setParallelGatewayStartId(parallelGatewayStartId);
							}
							String lastNodeId = bpmnModelBuilder(gatewayId, conditionNode, process, sequenceFlows,
									childNodeListMap, null, null, parallelRootNodeIdSet, childNodeMap);
							String[] split = lastNodeId.split(",");
							list.addAll(new ArrayList<>(Arrays.asList(split)));
						}
					}

					fromList = new ArrayList<>();
					for (String from : list) {
						String[] split = from.split(",");
						fromList.addAll(Arrays.asList(split));
					}
//                    Set<String> set = new HashSet<>(fromList);
//                    fromList=new ArrayList<>(set);
					String one = fromList.get(0);
					fromList.remove(0);
					// 先遍历子节点
					String nodeIds = bpmnModelBuilder(one, childNode.getChildNode(), process, sequenceFlows,
							childNodeListMap, fromList, null, parallelRootNodeIdSet, childNodeMap);
//                    list.add(nodeIds);
//                    String[] split = nodeIds.split(",");
//                    set.addAll(Arrays.asList(split));
					return org.apache.commons.lang3.StringUtils.join(nodeIds, ",");
				}
			}
		}
	}

	/**
	 * 将List转为Map 为了拿到最外层id
	 * @param childNodeLists
	 * @return
	 */
	private Map<String, ChildNodeList> convertNodeListToMap(List<ChildNodeList> childNodeLists) {
		Map<String, ChildNodeList> childNodeListMap = new HashMap<>();
		for (ChildNodeList childNodeList : childNodeLists) {
			String nodeId = childNodeList.getCustom().getNodeId();
			childNodeListMap.put(nodeId, childNodeList);
		}
		return childNodeListMap;
	}

	private Map<String, ConditionList> convertConditionListToMap(List<ConditionList> conditionLists) {
		Map<String, ConditionList> childNodeListMap = new HashMap<>();
		for (ConditionList conditionList : conditionLists) {
			String nodeId = conditionList.getNodeId();
			childNodeListMap.put(nodeId, conditionList);
		}
		return childNodeListMap;
	}

	@Override
	public boolean updateVisible(String id, FlowEngineEntity entity) {

		ChildNode childNode = JsonUtil.getJsonToBean(entity.getFlowTemplateJson(), ChildNode.class);
		BpmnModel bpmnModel = assembleBpmnModel(childNode, entity);
		BpmnXMLConverter bpmnXMLConverter = new BpmnXMLConverter();
		byte[] bytes = bpmnXMLConverter.convertToXML(bpmnModel);
		// 部署到activiti
		repositoryService.createDeployment().name(entity.getFullName()).category(entity.getCategory())
				.addBpmnModel(entity.getFullName() + BasicActivitiConstants.bpmnSuffix, bpmnModel).deploy();

		List<FlowEngineVisibleEntity> visibleList = visibleList(entity);
		entity.setId(id);
		entity.setLastModifyTime(new Date());
		entity.setLastModifyUser(userProvider.getUserId());
		entity.setVisibleType(visibleList.size() == 0 ? 0 : 1);
		boolean flag = this.updateById(entity);
		if (flag == true) {
			QueryWrapper<FlowEngineVisibleEntity> queryWrapper = new QueryWrapper<>();
			queryWrapper.lambda().eq(FlowEngineVisibleEntity::getFlowId, entity.getId());
			flowEngineVisibleService.remove(queryWrapper);
			for (int i = 0; i < visibleList.size(); i++) {
				visibleList.get(i).setId(RandomUtil.uuId());
				visibleList.get(i).setFlowId(entity.getId());
				visibleList.get(i).setSortCode(Long.parseLong(i + ""));
				flowEngineVisibleService.save(visibleList.get(i));
			}
		}
		return flag;
	}

	@Override
	public void update(String id, FlowEngineEntity entity) {
		entity.setId(id);
		entity.setLastModifyTime(new Date());
		entity.setLastModifyUser(userProvider.getUserId());
		this.updateById(entity);
	}

	@Override
	public boolean first(String id) {
		boolean isOk = false;
		// 获取要上移的那条数据的信息
		FlowEngineEntity upEntity = this.getById(id);
		Long upSortCode = upEntity.getSortCode() == null ? 0 : upEntity.getSortCode();
		// 查询上几条记录
		QueryWrapper<FlowEngineEntity> queryWrapper = new QueryWrapper<>();
		queryWrapper.lambda().lt(FlowEngineEntity::getSortCode, upSortCode)
				.eq(FlowEngineEntity::getCategory, upEntity.getCategory()).orderByDesc(FlowEngineEntity::getSortCode);
		List<FlowEngineEntity> downEntity = this.list(queryWrapper);
		if (downEntity.size() > 0) {
			// 交换两条记录的sort值
			Long temp = upEntity.getSortCode();
			upEntity.setSortCode(downEntity.get(0).getSortCode());
			downEntity.get(0).setSortCode(temp);
			updateById(downEntity.get(0));
			updateById(upEntity);
			isOk = true;
		}
		return isOk;
	}

	@Override
	public boolean next(String id) {
		boolean isOk = false;
		// 获取要下移的那条数据的信息
		FlowEngineEntity downEntity = this.getById(id);
		Long upSortCode = downEntity.getSortCode() == null ? 0 : downEntity.getSortCode();
		// 查询下几条记录
		QueryWrapper<FlowEngineEntity> queryWrapper = new QueryWrapper<>();
		queryWrapper.lambda().gt(FlowEngineEntity::getSortCode, upSortCode)
				.eq(FlowEngineEntity::getCategory, downEntity.getCategory()).orderByAsc(FlowEngineEntity::getSortCode);
		List<FlowEngineEntity> upEntity = this.list(queryWrapper);
		if (upEntity.size() > 0) {
			// 交换两条记录的sort值
			Long temp = downEntity.getSortCode();
			downEntity.setSortCode(upEntity.get(0).getSortCode());
			upEntity.get(0).setSortCode(temp);
			updateById(upEntity.get(0));
			updateById(downEntity);
			isOk = true;
		}
		return isOk;
	}

	@Override
	public List<FlowEngineListVO> getTreeList(PaginationFlowEngine pagination, boolean isList,
			List<UserEntity> userList) {
		List<FlowEngineEntity> data = new ArrayList<>();
		if (isList) {
			data = getList(pagination);
		} else {
			data = getFlowFormList();
		}
		List<DictionaryDataEntity> dictionList = dictionaryDataService.getList("507f4f5df86b47588138f321e0b0dac7");
		List<FlowTreeModel> modelAll = new LinkedList<>();
		for (DictionaryDataEntity entity : dictionList) {
			FlowTreeModel model = new FlowTreeModel();
			model.setFullName(entity.getFullName());
			model.setId(entity.getId());
			long num = data.stream().filter(t -> entity.getEnCode().equals(t.getCategory())).count();
			model.setNum(num);
			if (num > 0) {
				modelAll.add(model);
			}
		}
		for (FlowEngineEntity entity : data) {
			FlowTreeModel model = JsonUtil.getJsonToBean(entity, FlowTreeModel.class);
			DictionaryDataEntity dataEntity = dictionList.stream()
					.filter(t -> t.getEnCode().equals(entity.getCategory())).findFirst().orElse(null);
			if (dataEntity != null) {
				model.setParentId(dataEntity.getId());
				UserEntity creatorUser = userList.stream().filter(t -> t.getId().equals(model.getCreatorUser()))
						.findFirst().orElse(null);
				if (creatorUser != null) {
					model.setCreatorUser(creatorUser.getRealName() + "/" + creatorUser.getAccount());
				} else {
					model.setCreatorUser("");
				}
				modelAll.add(model);
			}
		}
		List<SumTree<FlowTreeModel>> trees = TreeDotUtils.convertListToTreeDot(modelAll);
		List<FlowEngineListVO> list = JsonUtil.getJsonToList(trees, FlowEngineListVO.class);
		return list;
	}

	private List<FlowEngineVisibleEntity> visibleList(FlowEngineEntity entity) {
		List<FlowEngineVisibleEntity> visibleList = new ArrayList<>();
		if (entity.getFlowTemplateJson() != null) {
			ChildNode childNode = JsonUtil.getJsonToBean(entity.getFlowTemplateJson(), ChildNode.class);
			Properties properties = childNode.getProperties();
			// 可见的用户
			for (String user : properties.getInitiator()) {
				FlowEngineVisibleEntity visible = new FlowEngineVisibleEntity();
				visible.setOperatorId(user);
				visible.setOperatorType("user");
				visibleList.add(visible);
			}
			// 可见的部门
			for (String position : properties.getInitiatePos()) {
				FlowEngineVisibleEntity visible = new FlowEngineVisibleEntity();
				visible.setOperatorId(position);
				visible.setOperatorType("position");
				visibleList.add(visible);
			}
			// 可见的角色
			List<String> roleList = properties.getInitiateRole() != null ? properties.getInitiateRole()
					: new ArrayList<>();
			for (String role : roleList) {
				FlowEngineVisibleEntity visible = new FlowEngineVisibleEntity();
				visible.setOperatorId(role);
				visible.setOperatorType("role");
				visibleList.add(visible);
			}
		}
		return visibleList;
	}

	@Override
	public FlowExportModel exportData(String id) throws WorkFlowException {
		FlowEngineEntity entity = getInfo(id);
		List<FlowEngineVisibleEntity> visibleList = flowEngineVisibleService.getVisibleFlowList(entity.getId());
		FlowExportModel model = new FlowExportModel();
		model.setFlowEngine(entity);
		model.setVisibleList(visibleList);
		return model;
	}

	@Override
	@Transactional
	public ActionResult ImportData(FlowEngineEntity entity, List<FlowEngineVisibleEntity> visibleList)
			throws WorkFlowException {
		if (entity != null) {
			if (isExistByFullName(entity.getFullName(), null)) {
				return ActionResult.fail("流程名称不能重复");
			}
			if (isExistByEnCode(entity.getEnCode(), null)) {
				return ActionResult.fail("流程编码不能重复");
			}
			try {
				this.save(entity);
				if (visibleList != null) {
					for (int i = 0; i < visibleList.size(); i++) {
						flowEngineVisibleService.save(visibleList.get(i));
					}
				}
			} catch (Exception e) {
				throw new WorkFlowException("数据已存在");
			}
			return ActionResult.success("导入成功");
		}
		return ActionResult.fail("导入数据格式不正确");
	}
}
