2

体验一把 Flowable 三种常见网关

 1 year ago
source link: https://www.51cto.com/article/721259.html
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

体验一把 Flowable 三种常见网关

作者:江南一点雨 2022-10-25 15:25:22
今天松哥就来和小伙伴们聊一聊这三种网关,一起来体验一把这三种网关各自的特征。

Flowable 中网关类型其实也不少,常见的主要有三种类型,分别是:

这三个里边最常用的当然就是排他网关了,今天松哥就来和小伙伴们聊一聊这三种网关,一起来体验一把这三种网关各自的特征。

1. 排他网关

首先就是排他网关了,这个也叫互斥网关,长得像下图这样:

9427c06210165baf9cd331664576d9b4bdf157.png

排他网关可以有 N 个入口,但是只有一个有效出口。

松哥举一个例子:

假设我有一个请假流程,请假 1 天,组长审批,请假小于 3 天,项目经理审批,请假大于 3 天,总监审批,据此,我们可以绘制如下流程图:

图片

在这个流程图中,当流程从排他网关出来的时候,我们设置一个变量,根据变量的值,来决定下一个走哪一个 Task,例如组长审批,我们做如下配置:

图片

这个流条件表示当 days 这个变量的值小于等于 1 的时候,就会进入到组长审批这个 Task。

按照类似的方式,我们来设置经理审批:

图片

最后,总监审批的条件如下:

图片

最终,我们来看下这个流程对应的 XML 文件,如下:

<process id="demo01" name="测试流程" isExecutable="true">
    <documentation>测试流程</documentation>
    <startEvent id="startEvent1" flowable:formFieldValidation="true"></startEvent>
    <exclusiveGateway id="sid-C4E389D6-C507-4B8E-8469-2288AA5B44A5"></exclusiveGateway>
    <sequenceFlow id="sid-DF97CC8B-3AD5-447D-AE67-1082CAB7B189" sourceRef="startEvent1" targetRef="sid-C4E389D6-C507-4B8E-8469-2288AA5B44A5"></sequenceFlow>
    <userTask id="sid-B4CD08AF-52B5-44F2-AC45-B2F5E154A5F0" name="组长审批" flowable:formFieldValidation="true"></userTask>
    <userTask id="sid-07B7951C-4E76-4639-989C-407C610C5BA8" name="经理审批" flowable:formFieldValidation="true"></userTask>
    <userTask id="sid-1A81B40F-D8D4-4158-B0B9-26DB8FB7DD2E" name="总监审批" flowable:formFieldValidation="true"></userTask>
    <endEvent id="sid-0F56FE56-1A8C-4B47-8F0D-196700DDF7B8"></endEvent>
    <sequenceFlow id="sid-E4B4B580-F078-4BB9-B5D3-966E80737C4C" sourceRef="sid-B4CD08AF-52B5-44F2-AC45-B2F5E154A5F0" targetRef="sid-0F56FE56-1A8C-4B47-8F0D-196700DDF7B8"></sequenceFlow>
    <endEvent id="sid-F05670CB-A8F4-44A3-B53D-46CFB6F65581"></endEvent>
    <sequenceFlow id="sid-3EC62E5D-ACDA-480E-93B4-C24D8F6E9042" sourceRef="sid-07B7951C-4E76-4639-989C-407C610C5BA8" targetRef="sid-F05670CB-A8F4-44A3-B53D-46CFB6F65581"></sequenceFlow>
    <endEvent id="sid-52711414-1769-4EC3-9AE5-6BA426123095"></endEvent>
    <sequenceFlow id="sid-C81500B2-D1EA-429F-8402-A3D8C8CA0E29" sourceRef="sid-1A81B40F-D8D4-4158-B0B9-26DB8FB7DD2E" targetRef="sid-52711414-1769-4EC3-9AE5-6BA426123095"></sequenceFlow>
    <sequenceFlow id="sid-807C7B79-4AFA-4525-847F-4D0FE1C0F0F3" name="小于1天" sourceRef="sid-C4E389D6-C507-4B8E-8469-2288AA5B44A5" targetRef="sid-B4CD08AF-52B5-44F2-AC45-B2F5E154A5F0">
      <conditionExpression xsi:type="tFormalExpression"><![CDATA[${days<=1}]]></conditionExpression>
    </sequenceFlow>
    <sequenceFlow id="sid-3D3DF742-BF47-4536-9EE9-747CD284A1BA" name="1-3天" sourceRef="sid-C4E389D6-C507-4B8E-8469-2288AA5B44A5" targetRef="sid-07B7951C-4E76-4639-989C-407C610C5BA8">
      <conditionExpression xsi:type="tFormalExpression"><![CDATA[${days>1 && days<=3}]]></conditionExpression>
    </sequenceFlow>
    <sequenceFlow id="sid-2AD41E43-AFEC-47A1-B8D1-0B4299434BF8" name="大于3天" sourceRef="sid-C4E389D6-C507-4B8E-8469-2288AA5B44A5" targetRef="sid-1A81B40F-D8D4-4158-B0B9-26DB8FB7DD2E">
      <conditionExpression xsi:type="tFormalExpression"><![CDATA[${days>3}]]></conditionExpression>
    </sequenceFlow>
  </process>

可以看到,在 sequenceFlow 标签中,有一个 conditionExpression 标签,这个标签的内容就是具体的条件了。

现在,我们部署一下这个流程,然后按照如下方式来启动:

@Test
void test01(){
    Map<String, Object> variables = new HashMap<>();
    variables.put("days", 3);
    ProcessInstance pi = runtimeService.startProcessInstanceByKey("demo01", variables);
    logger.info("id:{},activityId:{}", pi.getId(), pi.getActivityId());
}

注意,这个启动的时候,传入一个 days 变量,系统将来会根据这个变量来决定这个流程要走到哪一个 Task。流程启动成功之后,我们去观察 ACT_RU_TASK 表,就可以看到流程的执行是否和我们所预想的一致。

2. 并行网关

并行网关,从名字上大概也能看出来,这种网关一般用在并行任务上,并行网关如下图:

图片

并行网关一般是成对出现的,一个出现的并行网关用来分流,第二个出现的并行网关用来聚合。

我画一个简单的并行网关的例子,如下图:

图片

小伙伴们看到,这是一个简化的生产笔记本的流程图,当屏幕和键盘都生产好之后,再进行组装,整个流程图中存在两个并行网关(成对出现)。

在这个流程图中,连接线上是不需要设置条件的(不同于拍他网关),这里即使你设置了条件,这个条件也是不会生效的。

我们来看下这个并行网关流程图对应的 XML 文件,如下:

<process id="demo01" name="测试流程" isExecutable="true">
  <documentation>测试流程</documentation>
  <startEvent id="sid-4F7F76BA-526A-4D8C-B45A-02FC1C56CA47" flowable:formFieldValidation="true"></startEvent>
  <sequenceFlow id="sid-11130848-EA1F-458A-A45D-49CBC49428C8" sourceRef="sid-4F7F76BA-526A-4D8C-B45A-02FC1C56CA47" targetRef="sid-6D01D4BE-C475-4270-8745-92752EA2C038"></sequenceFlow>
  <parallelGateway id="sid-6D01D4BE-C475-4270-8745-92752EA2C038"></parallelGateway>
  <userTask id="sid-54DD6BFA-FE6C-4DE7-9038-3DEEAF85002C" name="生产屏幕" flowable:assignee="zhangsan" flowable:formFieldValidation="true">
    <extensionElements>
      <modeler:initiator-can-complete xmlns:modeler="http://flowable.org/modeler"><![CDATA[false]]></modeler:initiator-can-complete>
    </extensionElements>
  </userTask>
  <sequenceFlow id="sid-8DD3383C-45D1-4EAF-9A22-702A5B9D0869" sourceRef="sid-6D01D4BE-C475-4270-8745-92752EA2C038" targetRef="sid-54DD6BFA-FE6C-4DE7-9038-3DEEAF85002C"></sequenceFlow>
  <userTask id="sid-7797ED55-155F-4D17-8EA5-DE40434C421B" name="生产键盘" flowable:assignee="lisi" flowable:formFieldValidation="true">
    <extensionElements>
      <modeler:initiator-can-complete xmlns:modeler="http://flowable.org/modeler"><![CDATA[false]]></modeler:initiator-can-complete>
    </extensionElements>
  </userTask>
  <sequenceFlow id="sid-6E992E8B-CF71-411D-B537-42FEDF4F4209" sourceRef="sid-6D01D4BE-C475-4270-8745-92752EA2C038" targetRef="sid-7797ED55-155F-4D17-8EA5-DE40434C421B"></sequenceFlow>
  <sequenceFlow id="sid-8DCA9516-FFED-4781-9ACC-530DC6E63755" sourceRef="sid-7797ED55-155F-4D17-8EA5-DE40434C421B" targetRef="sid-98D3C336-9AD9-4964-9CCB-496C850EE40F"></sequenceFlow>
  <sequenceFlow id="sid-EE80AE42-D021-4B9F-A91E-BD37C512EE65" sourceRef="sid-54DD6BFA-FE6C-4DE7-9038-3DEEAF85002C" targetRef="sid-98D3C336-9AD9-4964-9CCB-496C850EE40F"></sequenceFlow>
  <userTask id="sid-4FFE361A-E2AF-4481-BACF-1E618E8C4A26" name="组装" flowable:assignee="javaboy" flowable:formFieldValidation="true">
    <extensionElements>
      <modeler:initiator-can-complete xmlns:modeler="http://flowable.org/modeler"><![CDATA[false]]></modeler:initiator-can-complete>
    </extensionElements>
  </userTask>
  <sequenceFlow id="sid-8CABC6E8-E36A-4814-B897-817D4A9F231C" sourceRef="sid-98D3C336-9AD9-4964-9CCB-496C850EE40F" targetRef="sid-4FFE361A-E2AF-4481-BACF-1E618E8C4A26"></sequenceFlow>
  <endEvent id="sid-BF02170B-8138-4867-AE01-E3B29505183D"></endEvent>
  <sequenceFlow id="sid-F72B2A15-913F-436E-8AD7-6A6FB190E197" sourceRef="sid-4FFE361A-E2AF-4481-BACF-1E618E8C4A26" targetRef="sid-BF02170B-8138-4867-AE01-E3B29505183D"></sequenceFlow>
  <parallelGateway id="sid-98D3C336-9AD9-4964-9CCB-496C850EE40F"></parallelGateway>
</process>

现在我们把这个流程部署并启动。

流程启动成功之后,我们发现在 ACT_RU_TASK 表中有两个需要执行的 Task,如下图:

图片

这两个 Task,如果只执行掉其中一个,那么还剩下另外一个 Task,如果两个都执行了,那么你就会看到一个新的 Task,如下图(两个并行任务执行完成后,进入到下一个任务):

图片

好啦,这就是并行网关。

3. 包容网关

包容网关,有时候也叫相容网关、兼容网关等,如下图:

d2c788e930d25fda38c0432eb295a6cc0308bd.png

包容谁呢?包容排他网关和并行网关。也就是说,这种包容网关可以根据实际条件转为排他网关或者并行网关。

举个栗子:

假如说报销金额大于 500,zhangsan 审批,报销金额大于 1000,则需要 zhangsan 和 lisi 同时审批,且 zhangsan 和 lisi 审批无先后顺序。

据此,我绘制如下流程图:

图片

在报销金额大于 500 上设置如下条件:

图片

大于 1000 上设置如下条件:

030993f95235562d2a1548a6611758cce15731.png

接下来我们来部署好这个流程。

部署好之后,我们首先来启动流程,第一次启动的时候,我们设置报销金额为 666,如下:

@Test
void test01(){
    Map<String, Object> variables = new HashMap<>();
    variables.put("money", 666);
    ProcessInstance pi = runtimeService.startProcessInstanceByKey("demo01", variables);
    logger.info("id:{},activityId:{}", pi.getId(), pi.getActivityId());
}

流程启动之后,我们在 ACT_RU_TASK 表中可以看到,该 zhangsan 审批了,如下:

图片

zhangsan 审批之后,就是 wangwu 审批了,我就不演示了。

假设我们启动流程的时候,报销金额为 2000,如下:

@Test
void test01(){
    Map<String, Object> variables = new HashMap<>();
    variables.put("money", 2000);
    ProcessInstance pi = runtimeService.startProcessInstanceByKey("demo01", variables);
    logger.info("id:{},activityId:{}", pi.getId(), pi.getActivityId());
}

那么此时你就会看到,在 ACT_RU_TASK 表中,出现了两条记录,分别是 zhangsan 审批和 lisi 审批,此时这两个审批就是一个并行任务了:

图片

接下来就按并行任务的模式来,这两个人都审批了,才会进入到 wangwu 审批。

这就是兼容网关的特点,即根据实际情况,会变成排他网关或者并行网关。

好啦,三种常见的网关就和小伙伴们分享完啦,感兴趣的小伙伴赶紧试一试吧~

责任编辑:武晓燕 来源: 江南一点雨

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK