多路聚合(Multiple Merge)
Description : A point in a workow process where two or more branches reconverge without
synchronization. If more than one branch gets activated, possibly concurrently, the activity
following the merge is started for every activation of every incoming branch.
描述: 多路合并是指在流程中某点,两条或更多分支无同步再收敛。若多于一个分支被激活,可能同时被激活,任务后的合并对于每条流入的激活分支都响应一次。
java 代码
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- package org.jbpm.jpdl.patterns;
-
- import junit.framework.TestCase;
-
- import org.jbpm.graph.def.ProcessDefinition;
- import org.jbpm.graph.exe.Token;
- import org.jbpm.graph.node.Merge;
-
-
-
-
- public class Wfp08MultiMergeTest extends TestCase {
-
- private static ProcessDefinition multiMergeProcessDefinition = createMultiMergeProcessDefinition();
-
- public static ProcessDefinition createMultiMergeProcessDefinition() {
- ProcessDefinition processDefinition = ProcessDefinition.parseXmlString(
- "<process-definition>" +
- " <start-state name='start'>" +
- " <transition to='a' />" +
- " </start-state>" +
- " <state name='a'>" +
- " <transition to='multichoice' />" +
- " </state>" +
- " <fork name='multichoice'>" +
- " <script>" +
- " <variable name='transitionNames' access='write' />" +
- " <expression>" +
- " transitionNames = new ArrayList();" +
- " if ( scenario == 1 ) {" +
- " transitionNames.add( \"to b\" );" +
- " } else if ( scenario == 2 ) {" +
- " transitionNames.add( \"to c\" );" +
- " } else if ( scenario >= 3 ) {" +
- " transitionNames.add( \"to b\" );" +
- " transitionNames.add( \"to c\" );" +
- " }" +
- " </expression>" +
- " </script>" +
- " <transition name='to b' to='b' />" +
- " <transition name='to c' to='c' />" +
- " </fork>" +
- " <state name='b'>" +
- " <transition to='multimerge' />" +
- " </state>" +
- " <state name='c'>" +
- " <transition to='multimerge' />" +
- " </state>" +
- " <merge name='multimerge'>" +
- " <transition to='d' />" +
- " </merge>" +
- " <state name='d' />" +
- "</process-definition>"
- );
-
- return processDefinition;
- }
-
- public void testMultiMergeScenario1() {
- ProcessDefinition pd = multiMergeProcessDefinition;
- Token root = Wfp06MultiChoiceTest.executeScenario(pd,1);
- Token tokenB = root.getChild("to b");
- tokenB.signal();
- assertSame( pd.getNode("d"), tokenB.getNode() );
- }
-
- public void testMultiMergeScenario2() {
- ProcessDefinition pd = multiMergeProcessDefinition;
- Token root = Wfp06MultiChoiceTest.executeScenario(pd,2);
- Token tokenC = root.getChild("to c");
- tokenC.signal();
- assertSame( pd.getNode("d"), tokenC.getNode() );
- }
-
- private static ProcessDefinition synchronizingMultiMergeProcessDefinition = createSynchronizingMultiMergeProcessDefinition();
-
- public static ProcessDefinition createSynchronizingMultiMergeProcessDefinition() {
- ProcessDefinition pd = createMultiMergeProcessDefinition();
-
-
- Merge merge = (Merge) pd.getNode("multimerge");
- merge.setSynchronized( true );
-
- return pd;
- }
-
- public void testMultiMergeScenario3() {
- ProcessDefinition pd = synchronizingMultiMergeProcessDefinition;
- Token root = Wfp06MultiChoiceTest.executeScenario(pd,3);
- Token tokenB = root.getChild("to b");
- Token tokenC = root.getChild("to c");
-
- tokenB.signal();
- assertSame( pd.getNode("multimerge"), tokenB.getNode() );
- assertSame( pd.getNode("c"), tokenC.getNode() );
-
- tokenC.signal();
- assertSame( pd.getNode("d"), tokenB.getNode() );
- assertSame( pd.getNode("d"), tokenC.getNode() );
- }
-
- public void testMultiMergeScenario4() {
- ProcessDefinition pd = synchronizingMultiMergeProcessDefinition;
- Token root = Wfp06MultiChoiceTest.executeScenario(pd,4);
- Token tokenB = root.getChild("to b");
- Token tokenC = root.getChild("to c");
-
- tokenC.signal();
- assertSame( pd.getNode("b"), tokenB.getNode() );
- assertSame( pd.getNode("multimerge"), tokenC.getNode() );
-
- tokenB.signal();
- assertSame( pd.getNode("d"), tokenB.getNode() );
- assertSame( pd.getNode("d"), tokenC.getNode() );
- }
-
- public void testMultiMergeScenario5() {
- ProcessDefinition pd = multiMergeProcessDefinition;
- Token root = Wfp06MultiChoiceTest.executeScenario(pd,5);
- Token tokenB = root.getChild("to b");
- Token tokenC = root.getChild("to c");
-
- tokenB.signal();
- assertSame( pd.getNode("d"), tokenB.getNode() );
- assertSame( pd.getNode("c"), tokenC.getNode() );
-
- tokenC.signal();
- assertSame( pd.getNode("d"), tokenB.getNode() );
- assertSame( pd.getNode("d"), tokenC.getNode() );
- }
-
- public void testMultiMergeScenario6() {
- ProcessDefinition pd = multiMergeProcessDefinition;
- Token root = Wfp06MultiChoiceTest.executeScenario(pd,6);
- Token tokenB = root.getChild("to b");
- Token tokenC = root.getChild("to c");
-
- tokenC.signal();
- assertSame( pd.getNode("b"), tokenB.getNode() );
- assertSame( pd.getNode("d"), tokenC.getNode() );
-
- tokenB.signal();
- assertSame( pd.getNode("d"), tokenB.getNode() );
- assertSame( pd.getNode("d"), tokenC.getNode() );
- }
- }
流程定义文件:
xml 代码
- <process-definition>
- <start-state name='start'>
- <transition to='a' />
- </start-state>
- <state name='a'>
- <transition to='multichoice' />
- </state>
- <fork name='multichoice'>
- <script>
- <variable name='transitionNames' access='write' />
- <expression>
- transitionNames = new ArrayList();
- if ( scenario == 1 ) {
- transitionNames.add( \"to b\" );
- } else if ( scenario == 2 ) {
- transitionNames.add( \"to c\" );
- } else if ( scenario >= 3 ) {
- transitionNames.add( \"to b\" );
- transitionNames.add( \"to c\" );
- }
- </expression>
- </script>
- <transition name='to b' to='b' />
- <transition name='to c' to='c' />
- </fork>
- <state name='b'>
- <transition to='multimerge' />
- </state>
- <state name='c'>
- <transition to='multimerge' />
- </state>
- <merge name='multimerge'>
- <transition to='d' />
- </merge>
- <state name='d' />
- </process-definition>
testMultiMergeScenario1()
节点流程执行顺序:
start -> a --> multichoice --> b --> multimerge --> d
testMultiMergeScenario2()
节点流程执行顺序:
start -> a --> multichoice --> c --> multimerge--> d
testMultiMergeScenario3()
注意该方法,在multimerge 会同步等待
节点流程执行顺序:
start -> a --> multichoice --> b --> multimerge--> d
multichoice --> c --> multimerge--> d
testMultiMergeScenario4()
注意该方法,在multimerge 会同步等待
节点流程执行顺序:
start -> a --> multichoice --> b --> multimerge--> d
multichoice --> c --> multimerge--> d
testMultiMergeScenario5()
节点流程执行顺序:
start -> a --> multichoice --> b --> multimerge--> d
multichoice --> c --> multimerge--> d
testMultiMergeScenario6()
节点流程执行顺序:
start -> a --> multichoice --> b --> multimerge--> d
multichoice --> c --> multimerge--> d
注意该类中同步设置.
Merge merge = (Merge) pd.getNode("multimerge");
merge.setSynchronized( true );