JBPM 5.5:父/子流程事件中关联可重用子流程节点与子流程实例
在JBPM 5.5中关联父流程节点与子流程实例的验证方案
没问题,这在JBPM 5.5里完全可以做到!你可以通过事件监听器里的上下文数据,精准关联父流程的可重用子流程节点和对应的子流程实例,我分两种场景给你具体实现方案:
场景1:在父流程的beforeNodeTriggered事件中验证
当父流程的可重用子流程节点(R1/R2)即将触发时,这个事件会被触发,你可以直接从事件对象中获取节点信息和关联的子流程实例:
实现步骤
- 实现
ProcessEventListener接口,重写beforeNodeTriggered方法 - 判断当前节点实例是否为
ReusableSubProcessInstance类型(可重用子流程节点的实例类型) - 获取父流程节点的唯一ID(R1是1,R2是2)和即将启动的子流程实例ID(1111/2222)
- 做对应匹配验证
代码示例
public class ParentSubProcessValidationListener implements ProcessEventListener { @Override public void beforeNodeTriggered(ProcessNodeTriggeredEvent event) { NodeInstance nodeInstance = event.getNodeInstance(); // 过滤出可重用子流程节点实例 if (nodeInstance instanceof ReusableSubProcessInstance) { ReusableSubProcessInstance subProcessNode = (ReusableSubProcessInstance) nodeInstance; // 获取父流程节点的唯一ID String parentNodeUniqueId = subProcessNode.getNode().getId(); // 获取关联的子流程实例ID String subProcessInstanceId = subProcessNode.getProcessInstance().getId(); // 执行匹配验证 validateAssociation(parentNodeUniqueId, subProcessInstanceId); } } private void validateAssociation(String parentNodeId, String subProcessInstanceId) { if ("1".equals(parentNodeId) && "1111".equals(subProcessInstanceId)) { System.out.println("验证通过:父流程节点R1触发了子流程实例CP1(ID:1111)"); } else if ("2".equals(parentNodeId) && "2222".equals(subProcessInstanceId)) { System.out.println("验证通过:父流程节点R2触发了子流程实例CP2(ID:2222)"); } else { System.err.println("警告:节点与子流程实例不匹配,节点ID:" + parentNodeId + ",子流程实例ID:" + subProcessInstanceId); } } // 实现其他ProcessEventListener的空方法(必须) @Override public void afterNodeTriggered(ProcessNodeTriggeredEvent event) {} @Override public void beforeNodeLeft(ProcessNodeLeftEvent event) {} @Override public void afterNodeLeft(ProcessNodeLeftEvent event) {} @Override public void beforeProcessStarted(ProcessStartedEvent event) {} @Override public void afterProcessStarted(ProcessStartedEvent event) {} @Override public void beforeProcessCompleted(ProcessCompletedEvent event) {} @Override public void afterProcessCompleted(ProcessCompletedEvent event) {} }
场景2:在子流程的beforeProcessStarted事件中验证
当子流程(CP1/CP2)即将启动时,这个事件会触发,你可以通过子流程实例反向关联到父流程的触发节点:
实现步骤
- 实现
ProcessEventListener接口,重写beforeProcessStarted方法 - 获取当前子流程实例的父流程实例
- 遍历父流程的节点实例,找到关联当前子流程的
ReusableSubProcessInstance - 获取父节点ID和子流程实例ID,执行匹配验证
代码示例
public class SubProcessParentNodeValidationListener implements ProcessEventListener { @Override public void beforeProcessStarted(ProcessStartedEvent event) { ProcessInstance subProcessInstance = event.getProcessInstance(); ProcessInstance parentProcessInstance = subProcessInstance.getParentProcessInstance(); // 确保子流程有父流程(避免独立启动的情况) if (parentProcessInstance != null) { // 遍历父流程的所有节点实例,找到触发当前子流程的节点 for (NodeInstance nodeInstance : parentProcessInstance.getNodeInstances()) { if (nodeInstance instanceof ReusableSubProcessInstance) { ReusableSubProcessInstance triggerNode = (ReusableSubProcessInstance) nodeInstance; // 验证该节点是否关联当前子流程实例 if (triggerNode.getProcessInstance().getId().equals(subProcessInstance.getId())) { String parentNodeId = triggerNode.getNode().getId(); String subProcessId = subProcessInstance.getId(); validateAssociation(parentNodeId, subProcessId); break; // 找到匹配节点后退出循环 } } } } } private void validateAssociation(String parentNodeId, String subProcessInstanceId) { if ("1".equals(parentNodeId) && "1111".equals(subProcessInstanceId)) { System.out.println("验证通过:子流程实例CP1(ID:1111)由父流程节点R1触发"); } else if ("2".equals(parentNodeId) && "2222".equals(subProcessInstanceId)) { System.out.println("验证通过:子流程实例CP2(ID:2222)由父流程节点R2触发"); } else { System.err.println("警告:子流程实例与触发节点不匹配,子流程ID:" + subProcessInstanceId + ",触发节点ID:" + parentNodeId); } } // 实现其他ProcessEventListener的空方法(必须) @Override public void afterProcessStarted(ProcessStartedEvent event) {} @Override public void beforeNodeTriggered(ProcessNodeTriggeredEvent event) {} @Override public void afterNodeTriggered(ProcessNodeTriggeredEvent event) {} @Override public void beforeNodeLeft(ProcessNodeLeftEvent event) {} @Override public void afterNodeLeft(ProcessNodeLeftEvent event) {} @Override public void beforeProcessCompleted(ProcessCompletedEvent event) {} @Override public void afterProcessCompleted(ProcessCompletedEvent event) {} }
额外注意事项
- 监听器注册:你需要把这些监听器注册到对应的流程中,可以通过流程定义的XML配置(在
<process>标签下添加<event-listener>),或者通过代码动态注册 - ID一致性:确保代码中使用的节点唯一ID(1/2)和子流程实例ID(1111/2222)与实际流程定义/运行时的ID完全一致
- 动态实例ID:如果子流程实例ID是动态生成的而非固定值,建议在父流程节点中通过变量传递预期的子流程标识,再在监听器中做匹配
内容的提问来源于stack exchange,提问作者BeingVikram
相关产品推荐
相关产品推荐

