From 34981c30a78e8bbd7791131059a9210f9928b62c Mon Sep 17 00:00:00 2001
From: 刘光辉 <347230014@qq.com>
Date: 星期四, 17 九月 2026 09:24:09 +0800
Subject: [PATCH] Merge remote-tracking branch 'origin/master' into master
---
jnpf-flow-engine/src/main/java/jnpf/workflow/flowable/util/FlowableUtil.java | 250 ++++++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 250 insertions(+), 0 deletions(-)
diff --git a/jnpf-flow-engine/src/main/java/jnpf/workflow/flowable/util/FlowableUtil.java b/jnpf-flow-engine/src/main/java/jnpf/workflow/flowable/util/FlowableUtil.java
new file mode 100644
index 0000000..7163f08
--- /dev/null
+++ b/jnpf-flow-engine/src/main/java/jnpf/workflow/flowable/util/FlowableUtil.java
@@ -0,0 +1,250 @@
+package jnpf.workflow.flowable.util;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Optional;
+import java.util.Set;
+
+import org.flowable.bpmn.model.EndEvent;
+import org.flowable.bpmn.model.FlowElement;
+import org.flowable.bpmn.model.FlowNode;
+import org.flowable.bpmn.model.Gateway;
+import org.flowable.bpmn.model.SequenceFlow;
+import org.flowable.bpmn.model.StartEvent;
+import org.flowable.bpmn.model.SubProcess;
+import org.flowable.bpmn.model.UserTask;
+
+import cn.hutool.core.collection.CollectionUtil;
+import jnpf.workflow.common.model.vo.FlowVo;
+
+/**
+ * BPMN 鎷撴墤鎺ㄥ宸ュ叿锛坆ack/jump/next/prev 绛夋帴鍙g殑鏍稿績锛夈��
+ * 鐢遍粦鐩� jar 鍙嶇紪璇戦�愯淇濈湡杩樺師锛屽嬁鍋�"椤烘墜浼樺寲"銆�
+ */
+public class FlowableUtil {
+
+ public static Collection<FlowElement> getAllElements(Collection<FlowElement> flowElements, Collection<FlowElement> allElements) {
+ allElements = allElements == null ? new ArrayList<>() : allElements;
+ for (FlowElement flowElement : flowElements) {
+ allElements.add(flowElement);
+ if (!(flowElement instanceof SubProcess)) {
+ continue;
+ }
+ allElements = getAllElements(((SubProcess) flowElement).getFlowElements(), allElements);
+ }
+ return allElements;
+ }
+
+ public static List<SequenceFlow> getElementIncomingFlows(FlowElement element) {
+ List<SequenceFlow> flows = null;
+ if (element instanceof FlowNode) {
+ flows = ((FlowNode) element).getIncomingFlows();
+ }
+ return flows;
+ }
+
+ public static List<SequenceFlow> getElementOutgoingFlows(FlowElement element) {
+ List<SequenceFlow> flows = null;
+ if (element instanceof FlowNode) {
+ flows = ((FlowNode) element).getOutgoingFlows();
+ }
+ return flows;
+ }
+
+ public static List<String> getPassActs(FlowElement source, Set<String> passFlows, List<String> passActs) {
+ passFlows = passFlows == null ? new HashSet<>() : passFlows;
+ passActs = passActs == null ? new ArrayList<>() : passActs;
+ List<SequenceFlow> sequenceFlows = getElementIncomingFlows(source);
+ if (null != sequenceFlows && !sequenceFlows.isEmpty()) {
+ for (SequenceFlow sequenceFlow : sequenceFlows) {
+ if (passFlows.contains(sequenceFlow.getId())) {
+ continue;
+ }
+ passFlows.add(sequenceFlow.getId());
+ if (sequenceFlow.getSourceFlowElement() instanceof UserTask) {
+ passActs.add(sequenceFlow.getSourceFlowElement().getId());
+ }
+ if (sequenceFlow.getSourceFlowElement() instanceof StartEvent) {
+ passActs.add(sequenceFlow.getSourceFlowElement().getId());
+ continue;
+ }
+ getPassActs(sequenceFlow.getSourceFlowElement(), passFlows, passActs);
+ }
+ }
+ return passActs;
+ }
+
+ public static List<UserTask> getChildUserTasks(FlowElement source, List<String> runTaskKeyList, Set<String> passFlows, List<UserTask> userTasks) {
+ passFlows = passFlows == null ? new HashSet<>() : passFlows;
+ userTasks = userTasks == null ? new ArrayList<>() : userTasks;
+ List<SequenceFlow> sequenceFlows = getElementOutgoingFlows(source);
+ if (null != sequenceFlows && !sequenceFlows.isEmpty()) {
+ for (SequenceFlow sequenceFlow : sequenceFlows) {
+ if (passFlows.contains(sequenceFlow.getId())) {
+ continue;
+ }
+ passFlows.add(sequenceFlow.getId());
+ if (sequenceFlow.getTargetFlowElement() instanceof UserTask && runTaskKeyList.contains(sequenceFlow.getTargetFlowElement().getId())) {
+ userTasks.add((UserTask) sequenceFlow.getTargetFlowElement());
+ continue;
+ }
+ if (sequenceFlow.getTargetFlowElement() instanceof SubProcess) {
+ FlowElement flowElement = (FlowElement) ((SubProcess) sequenceFlow.getTargetFlowElement()).getFlowElements().toArray()[0];
+ List<UserTask> tasks = getChildUserTasks(flowElement, runTaskKeyList, passFlows, null);
+ if (!tasks.isEmpty()) {
+ userTasks.addAll(tasks);
+ continue;
+ }
+ }
+ getChildUserTasks(sequenceFlow.getTargetFlowElement(), runTaskKeyList, passFlows, userTasks);
+ }
+ }
+ return userTasks;
+ }
+
+ public static List<String> getParentActs(FlowElement source, Set<String> passFlows, List<String> parentActs) {
+ passFlows = passFlows == null ? new HashSet<>() : passFlows;
+ parentActs = parentActs == null ? new ArrayList<>() : parentActs;
+ List<SequenceFlow> sequenceFlows = getElementIncomingFlows(source);
+ if (null != sequenceFlows && !sequenceFlows.isEmpty()) {
+ for (SequenceFlow sequenceFlow : sequenceFlows) {
+ if (passFlows.contains(sequenceFlow.getId())) {
+ continue;
+ }
+ passFlows.add(sequenceFlow.getId());
+ if (sequenceFlow.getSourceFlowElement() instanceof UserTask) {
+ parentActs.add(sequenceFlow.getSourceFlowElement().getId());
+ continue;
+ }
+ if (sequenceFlow.getSourceFlowElement() instanceof StartEvent) {
+ parentActs.add(sequenceFlow.getSourceFlowElement().getId());
+ continue;
+ }
+ getParentActs(sequenceFlow.getSourceFlowElement(), passFlows, parentActs);
+ }
+ }
+ return parentActs;
+ }
+
+ public static List<UserTask> getNextUserTasks(FlowElement source, Set<String> hasSequenceFlow, List<UserTask> userTaskList) {
+ hasSequenceFlow = Optional.ofNullable(hasSequenceFlow).orElse(new HashSet<>());
+ userTaskList = Optional.ofNullable(userTaskList).orElse(new ArrayList<>());
+ List<SequenceFlow> sequenceFlows = getElementOutgoingFlows(source);
+ if (null != sequenceFlows) {
+ for (SequenceFlow sequenceFlow : sequenceFlows) {
+ if (hasSequenceFlow.contains(sequenceFlow.getId())) {
+ continue;
+ }
+ hasSequenceFlow.add(sequenceFlow.getId());
+ FlowElement targetFlowElement = sequenceFlow.getTargetFlowElement();
+ if (targetFlowElement instanceof UserTask) {
+ userTaskList.add((UserTask) targetFlowElement);
+ continue;
+ }
+ getNextUserTasks(targetFlowElement, hasSequenceFlow, userTaskList);
+ }
+ }
+ return userTaskList;
+ }
+
+ public static List<String> getAfter(FlowElement source, Set<String> hasSequenceFlow, List<String> list) {
+ hasSequenceFlow = Optional.ofNullable(hasSequenceFlow).orElse(new HashSet<>());
+ list = Optional.ofNullable(list).orElse(new ArrayList<>());
+ List<SequenceFlow> sequenceFlows = getElementOutgoingFlows(source);
+ if (null != sequenceFlows) {
+ for (SequenceFlow sequenceFlow : sequenceFlows) {
+ if (hasSequenceFlow.contains(sequenceFlow.getId())) {
+ continue;
+ }
+ hasSequenceFlow.add(sequenceFlow.getId());
+ FlowElement targetFlowElement = sequenceFlow.getTargetFlowElement();
+ if (targetFlowElement instanceof UserTask) {
+ list.add(targetFlowElement.getId());
+ } else if (targetFlowElement instanceof EndEvent) {
+ list.add(targetFlowElement.getId());
+ continue;
+ }
+ getAfter(targetFlowElement, hasSequenceFlow, list);
+ }
+ }
+ return list;
+ }
+
+ public static List<SequenceFlow> getOutFlowsWithGateway(FlowElement source, List<SequenceFlow> flows) {
+ flows = flows == null ? new ArrayList<>() : flows;
+ List<SequenceFlow> sequenceFlows = getElementOutgoingFlows(source);
+ if (null != sequenceFlows) {
+ for (SequenceFlow sequenceFlow : sequenceFlows) {
+ flows.add(sequenceFlow);
+ FlowElement targetFlowElement = sequenceFlow.getTargetFlowElement();
+ if (targetFlowElement instanceof UserTask || !(targetFlowElement instanceof Gateway)) {
+ continue;
+ }
+ Gateway gateway = (Gateway) targetFlowElement;
+ List<SequenceFlow> outgoingFlows = gateway.getOutgoingFlows();
+ flows.addAll(outgoingFlows);
+ getOutFlowsWithGateway(gateway, flows);
+ }
+ }
+ return flows;
+ }
+
+ public static List<FlowVo> getOutFlows(FlowElement source, List<FlowVo> flows) {
+ flows = flows == null ? new ArrayList<>() : flows;
+ List<SequenceFlow> sequenceFlows = getElementOutgoingFlows(source);
+ if (null != sequenceFlows) {
+ for (SequenceFlow sequenceFlow : sequenceFlows) {
+ FlowVo vo = new FlowVo();
+ vo.setKey(sequenceFlow.getId());
+ FlowElement targetFlowElement = sequenceFlow.getTargetFlowElement();
+ if (targetFlowElement instanceof Gateway) {
+ Gateway gateway = (Gateway) targetFlowElement;
+ List<FlowVo> list = getOutFlows(gateway, null);
+ vo.setChildren(list);
+ }
+ flows.add(vo);
+ }
+ }
+ return flows;
+ }
+
+ public static List<String> getBefore(FlowElement source, Set<String> passFlows, List<String> keys) {
+ passFlows = passFlows == null ? new HashSet<>() : passFlows;
+ keys = keys == null ? new ArrayList<>() : keys;
+ List<SequenceFlow> sequenceFlows = getElementIncomingFlows(source);
+ if (null != sequenceFlows && !sequenceFlows.isEmpty()) {
+ for (SequenceFlow sequenceFlow : sequenceFlows) {
+ if (passFlows.contains(sequenceFlow.getId())) {
+ continue;
+ }
+ passFlows.add(sequenceFlow.getId());
+ keys.add(sequenceFlow.getSourceFlowElement().getId());
+ if (sequenceFlow.getSourceFlowElement() instanceof StartEvent) {
+ continue;
+ }
+ getBefore(sequenceFlow.getSourceFlowElement(), passFlows, keys);
+ }
+ }
+ return keys;
+ }
+
+ public static String getTaskKeyAfterFlow(FlowElement source) {
+ if (source instanceof SequenceFlow) {
+ SequenceFlow sequenceFlow = (SequenceFlow) source;
+ FlowElement target = sequenceFlow.getTargetFlowElement();
+ if (target instanceof Gateway) {
+ List<SequenceFlow> outgoingFlows = ((Gateway) target).getOutgoingFlows();
+ if (CollectionUtil.isNotEmpty(outgoingFlows)) {
+ SequenceFlow flow = outgoingFlows.get(0);
+ return getTaskKeyAfterFlow(flow);
+ }
+ }
+ if (target instanceof UserTask) {
+ return target.getId();
+ }
+ }
+ return null;
+ }
+}
--
Gitblit v1.8.0