先学习使用flowable-ui的Demo
这个可以帮助我们生成bpmn20.xml文件
也就是使用flowable自带的flowable-ui制作流程图
使用docker运行
docker run -p 8080:8080 flowable/flowable-ui
运行成功后访问
http://localhost:8080/flowable-ui
user: admin
password: test
创建流程得到bpmn20.xml
导出xml
<?xml version="1.0" encoding="UTF-8"?>
<definitions xmlns="http://www.omg.org/spec/BPMN/20100524/MODEL" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:flowable="http://flowable.org/bpmn" xmlns:bpmndi="http://www.omg.org/spec/BPMN/20100524/DI" xmlns:omgdc="http://www.omg.org/spec/DD/20100524/DC" xmlns:omgdi="http://www.omg.org/spec/DD/20100524/DI" typeLanguage="http://www.w3.org/2001/XMLSchema" expressionLanguage="http://www.w3.org/1999/XPath" targetNamespace="http://www.flowable.org/processdef" exporter="Flowable Open Source Modeler" exporterVersion="6.8.0">
<process id="leave_approve" name="请假审批" isExecutable="true">
<documentation>请假审批</documentation>
<startEvent id="startEvent1" flowable:formFieldValidation="true"></startEvent>
<userTask id="sid-7361D568-A832-478D-B31E-770B6508F0EC" name="学生" flowable:formFieldValidation="true"></userTask>
<sequenceFlow id="sid-7EDC7758-DF02-4ED4-9EA8-1E169B31107E" sourceRef="startEvent1" targetRef="sid-7361D568-A832-478D-B31E-770B6508F0EC"></sequenceFlow>
<userTask id="sid-D858C90B-1391-4E58-A715-13FCBBD13498" name="老师" flowable:formFieldValidation="true"></userTask>
<sequenceFlow id="sid-96173B13-7480-43F0-9B3E-EC1CA76D5446" name="请假" sourceRef="sid-7361D568-A832-478D-B31E-770B6508F0EC" targetRef="sid-D858C90B-1391-4E58-A715-13FCBBD13498"></sequenceFlow>
<sequenceFlow id="sid-624203DD-6504-480B-8558-8D3E929D50AB" name="审批" sourceRef="sid-D858C90B-1391-4E58-A715-13FCBBD13498" targetRef="sid-9263F9A7-58B4-4C62-8ECF-93B4FD76626F"></sequenceFlow>
<userTask id="sid-E27E9FD3-50EE-44B5-BE83-D199A794394E" name="校长" flowable:formFieldValidation="true"></userTask>
<exclusiveGateway id="sid-DB230500-F8E7-4796-866E-80AE4F5759D5"></exclusiveGateway>
<sequenceFlow id="sid-FC660276-FC1E-4D66-8E70-0D32D2843014" name="审批" sourceRef="sid-E27E9FD3-50EE-44B5-BE83-D199A794394E" targetRef="sid-DB230500-F8E7-4796-866E-80AE4F5759D5"></sequenceFlow>
<endEvent id="sid-D9764532-4C6A-4087-A440-B3F3F032A077"></endEvent>
<exclusiveGateway id="sid-9263F9A7-58B4-4C62-8ECF-93B4FD76626F"></exclusiveGateway>
<sequenceFlow id="sid-3918DA4F-F9CA-4A67-847F-D7934807ECED" name="拒绝" sourceRef="sid-9263F9A7-58B4-4C62-8ECF-93B4FD76626F" targetRef="sid-7361D568-A832-478D-B31E-770B6508F0EC">
<conditionExpression xsi:type="tFormalExpression"><![CDATA[${action='N'}]]></conditionExpression>
</sequenceFlow>
<sequenceFlow id="sid-91377CDC-8D11-4E59-BE0D-C186C658D62E" name="同意" sourceRef="sid-DB230500-F8E7-4796-866E-80AE4F5759D5" targetRef="sid-D9764532-4C6A-4087-A440-B3F3F032A077">
<conditionExpression xsi:type="tFormalExpression"><![CDATA[${action='Y'}]]></conditionExpression>
</sequenceFlow>
<sequenceFlow id="sid-84B59206-7F5E-43C5-BDB8-EB7D0F822160" name="拒绝" sourceRef="sid-DB230500-F8E7-4796-866E-80AE4F5759D5" targetRef="sid-7361D568-A832-478D-B31E-770B6508F0EC">
<conditionExpression xsi:type="tFormalExpression"><![CDATA[${action='N'}]]></conditionExpression>
</sequenceFlow>
<sequenceFlow id="sid-65EE4768-D3FD-49E8-8A1E-190A06207DF9" name="同意" sourceRef="sid-9263F9A7-58B4-4C62-8ECF-93B4FD76626F" targetRef="sid-E27E9FD3-50EE-44B5-BE83-D199A794394E">
<conditionExpression xsi:type="tFormalExpression"><![CDATA[${action='Y'}]]></conditionExpression>
</sequenceFlow>
</process>
<bpmndi:BPMNDiagram id="BPMNDiagram_leave_approve">
<bpmndi:BPMNPlane bpmnElement="leave_approve" id="BPMNPlane_leave_approve">
<bpmndi:BPMNShape bpmnElement="startEvent1" id="BPMNShape_startEvent1">
<omgdc:Bounds height="30.0" width="30.0" x="100.0" y="163.0"></omgdc:Bounds>
</bpmndi:BPMNShape>
<bpmndi:BPMNShape bpmnElement="sid-7361D568-A832-478D-B31E-770B6508F0EC" id="BPMNShape_sid-7361D568-A832-478D-B31E-770B6508F0EC">
<omgdc:Bounds height="80.0" width="100.0" x="175.0" y="138.0"></omgdc:Bounds>
</bpmndi:BPMNShape>
<bpmndi:BPMNShape bpmnElement="sid-D858C90B-1391-4E58-A715-13FCBBD13498" id="BPMNShape_sid-D858C90B-1391-4E58-A715-13FCBBD13498">
<omgdc:Bounds height="80.0" width="100.0" x="320.0" y="138.0"></omgdc:Bounds>
</bpmndi:BPMNShape>
<bpmndi:BPMNShape bpmnElement="sid-E27E9FD3-50EE-44B5-BE83-D199A794394E" id="BPMNShape_sid-E27E9FD3-50EE-44B5-BE83-D199A794394E">
<omgdc:Bounds height="80.0" width="100.0" x="550.0" y="138.0"></omgdc:Bounds>
</bpmndi:BPMNShape>
<bpmndi:BPMNShape bpmnElement="sid-DB230500-F8E7-4796-866E-80AE4F5759D5" id="BPMNShape_sid-DB230500-F8E7-4796-866E-80AE4F5759D5">
<omgdc:Bounds height="40.0" width="40.0" x="695.0" y="158.0"></omgdc:Bounds>
</bpmndi:BPMNShape>
<bpmndi:BPMNShape bpmnElement="sid-D9764532-4C6A-4087-A440-B3F3F032A077" id="BPMNShape_sid-D9764532-4C6A-4087-A440-B3F3F032A077">
<omgdc:Bounds height="28.0" width="28.0" x="780.0" y="164.0"></omgdc:Bounds>
</bpmndi:BPMNShape>
<bpmndi:BPMNShape bpmnElement="sid-9263F9A7-58B4-4C62-8ECF-93B4FD76626F" id="BPMNShape_sid-9263F9A7-58B4-4C62-8ECF-93B4FD76626F">
<omgdc:Bounds height="40.0" width="40.0" x="465.0" y="158.0"></omgdc:Bounds>
</bpmndi:BPMNShape>
<bpmndi:BPMNEdge bpmnElement="sid-96173B13-7480-43F0-9B3E-EC1CA76D5446" id="BPMNEdge_sid-96173B13-7480-43F0-9B3E-EC1CA76D5446" flowable:sourceDockerX="50.0" flowable:sourceDockerY="40.0" flowable:targetDockerX="50.0" flowable:targetDockerY="40.0">
<omgdi:waypoint x="274.9499999999907" y="178.0"></omgdi:waypoint>
<omgdi:waypoint x="319.9999999999807" y="178.0"></omgdi:waypoint>
</bpmndi:BPMNEdge>
<bpmndi:BPMNEdge bpmnElement="sid-FC660276-FC1E-4D66-8E70-0D32D2843014" id="BPMNEdge_sid-FC660276-FC1E-4D66-8E70-0D32D2843014" flowable:sourceDockerX="50.0" flowable:sourceDockerY="40.0" flowable:targetDockerX="20.5" flowable:targetDockerY="20.5">
<omgdi:waypoint x="649.9499999999977" y="178.21623376623376"></omgdi:waypoint>
<omgdi:waypoint x="695.4130434782554" y="178.41304347826085"></omgdi:waypoint>
</bpmndi:BPMNEdge>
<bpmndi:BPMNEdge bpmnElement="sid-91377CDC-8D11-4E59-BE0D-C186C658D62E" id="BPMNEdge_sid-91377CDC-8D11-4E59-BE0D-C186C658D62E" flowable:sourceDockerX="20.5" flowable:sourceDockerY="20.5" flowable:targetDockerX="14.0" flowable:targetDockerY="14.0">
<omgdi:waypoint x="734.5591869398207" y="178.3782051282051"></omgdi:waypoint>
<omgdi:waypoint x="780.0002755524838" y="178.08885188426407"></omgdi:waypoint>
</bpmndi:BPMNEdge>
<bpmndi:BPMNEdge bpmnElement="sid-84B59206-7F5E-43C5-BDB8-EB7D0F822160" id="BPMNEdge_sid-84B59206-7F5E-43C5-BDB8-EB7D0F822160" flowable:sourceDockerX="20.5" flowable:sourceDockerY="20.5" flowable:targetDockerX="50.0" flowable:targetDockerY="40.0">
<omgdi:waypoint x="715.5" y="158.5"></omgdi:waypoint>
<omgdi:waypoint x="715.5" y="65.5"></omgdi:waypoint>
<omgdi:waypoint x="225.0" y="65.5"></omgdi:waypoint>
<omgdi:waypoint x="225.0" y="138.0"></omgdi:waypoint>
</bpmndi:BPMNEdge>
<bpmndi:BPMNEdge bpmnElement="sid-65EE4768-D3FD-49E8-8A1E-190A06207DF9" id="BPMNEdge_sid-65EE4768-D3FD-49E8-8A1E-190A06207DF9" flowable:sourceDockerX="20.5" flowable:sourceDockerY="20.5" flowable:targetDockerX="50.0" flowable:targetDockerY="40.0">
<omgdi:waypoint x="504.5247370727428" y="178.41666666666663"></omgdi:waypoint>
<omgdi:waypoint x="549.9999999999953" y="178.21812227074236"></omgdi:waypoint>
</bpmndi:BPMNEdge>
<bpmndi:BPMNEdge bpmnElement="sid-3918DA4F-F9CA-4A67-847F-D7934807ECED" id="BPMNEdge_sid-3918DA4F-F9CA-4A67-847F-D7934807ECED" flowable:sourceDockerX="20.5" flowable:sourceDockerY="20.5" flowable:targetDockerX="50.0" flowable:targetDockerY="40.0">
<omgdi:waypoint x="485.5" y="197.4418389319552"></omgdi:waypoint>
<omgdi:waypoint x="485.5" y="294.5"></omgdi:waypoint>
<omgdi:waypoint x="225.0" y="294.5"></omgdi:waypoint>
<omgdi:waypoint x="225.0" y="217.95000000000002"></omgdi:waypoint>
</bpmndi:BPMNEdge>
<bpmndi:BPMNEdge bpmnElement="sid-7EDC7758-DF02-4ED4-9EA8-1E169B31107E" id="BPMNEdge_sid-7EDC7758-DF02-4ED4-9EA8-1E169B31107E" flowable:sourceDockerX="15.0" flowable:sourceDockerY="15.0" flowable:targetDockerX="50.0" flowable:targetDockerY="40.0">
<omgdi:waypoint x="129.9499984899576" y="178.0"></omgdi:waypoint>
<omgdi:waypoint x="174.9999999999917" y="178.0"></omgdi:waypoint>
</bpmndi:BPMNEdge>
<bpmndi:BPMNEdge bpmnElement="sid-624203DD-6504-480B-8558-8D3E929D50AB" id="BPMNEdge_sid-624203DD-6504-480B-8558-8D3E929D50AB" flowable:sourceDockerX="50.0" flowable:sourceDockerY="40.0" flowable:targetDockerX="20.5" flowable:targetDockerY="20.5">
<omgdi:waypoint x="419.94999999999806" y="178.21623376623378"></omgdi:waypoint>
<omgdi:waypoint x="465.4130434782609" y="178.4130434782609"></omgdi:waypoint>
</bpmndi:BPMNEdge>
</bpmndi:BPMNPlane>
</bpmndi:BPMNDiagram>
</definitions>
后台系统搭建
maven引入
<dependency>
<groupId>org.flowable</groupId>
<artifactId>flowable-engine</artifactId>
<version>6.4.2</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.29</version>
</dependency>
数据库信息配置
server.port=8081
## ==============================
## MySQL connection config
## ==============================
spring.datasource.url=jdbc:mysql://localhost:3306/flowable_db?useUnicode=true&characeterEncoding=utf-8&serverTimezone=UTC
spring.datasource.username=root
spring.datasource.password=*****
Flowable引擎在使用前需要先通过配置来初始化ProcessEngine。
初始化ProcessEngineConfiguration一般有两种方式:
1.通过Spinrg配置文件进行依赖注入,通过flowable.cfg.xml文件来初始化ProcessEngineConfiguration(这里的文件名必须为flowable.cfg.xml,否则Flowable识别不到)
2.通过编写程序的方式来构造ProcessEngineConfiguration对象
ProcessEngineConfiguration在初始化过程中会同时初始化数据库,如果数据库已经存在,则不会做创建更新操作,如果数据库不存在,则会默认执行数据库创建脚本
flowable.cfg.xml文件
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
<!-- 生成流程图参数 -->
<bean id="processDiagramGenerator" class="org.flowable.image.impl.DefaultProcessDiagramGenerator" />
<bean id="processEngineConfiguration" class="org.flowable.engine.impl.cfg.StandaloneProcessEngineConfiguration">
<property name="jdbcUrl" value="jdbc:mysql://localhost:3306/flowable_db?useUnicode=true&characeterEncoding=utf-8&serverTimezone=UTC" />
<property name="jdbcDriver" value="com.mysql.jdbc.Driver" />
<property name="jdbcUsername" value="root" />
<property name="jdbcPassword" value="***" />
<property name="databaseSchemaUpdate" value="true" />
<property name="asyncExecutorActivate" value="false" />
<!-- 流程部署时自动生成对应的图片 -->
<property name="createDiagramOnDeploy" value="true" />
<!-- 生成流程图参数 -->
<property name="processDiagramGenerator" ref="processDiagramGenerator" />
<!-- 流程图字体 -->
<property name="activityFontName" value="宋体" />
<property name="labelFontName" value="宋体" />
<property name="annotationFontName" value="宋体" />
</bean>
</beans>
执行下面的程序自动生成相关的表
package com.example.flowabledemo;
import org.flowable.engine.ProcessEngine;
import org.flowable.engine.ProcessEngines;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
public class FlowabledemoApplication {
public static void main(String[] args) {
SpringApplication.run(FlowabledemoApplication.class, args);
//如果配置文件位于resources/flowable.cfg.xml,则可以这样获取引擎
//获取引擎时就会自动在数据库中创建相关的表
ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
}
}
生成好了数据表
Flowable数据库解释
数据库
1、Flowable的所有数据库表都以ACT_开头。第二部分是说明表用途的两字符标示符。服务API的命名也大略符合这个规则。
2、ACT_RE_: 'RE’代表repository。带有这个前缀的表包含“静态”信息,例如流程定义与流程资源(图片、规则等)。
3、ACT_RU_: 'RU’代表runtime。这些表存储运行时信息,例如流程实例(process instance)、用户任务(user task)、变量(variable)、作业(job)等。Flowable只在流程实例运行中保存运行时数据,并在流程实例结束时删除记录。这样保证运行时表小和快。
4、ACT_HI_: 'HI’代表history。这些表存储历史数据,例如已完成的流程实例、变量、任务等。
5、ACT_GE_: 通用数据。在多处使用。
1)通用数据表(2个)
act_ge_bytearray:二进制数据表,如流程定义、流程模板、流程图的字节流文件;
act_ge_property:属性数据表(不常用);
2)历史表(8个,HistoryService接口操作的表)
act_hi_actinst:历史节点表,存放流程实例运转的各个节点信息(包含开始、结束等非任务节点);
act_hi_attachment:历史附件表,存放历史节点上传的附件信息(不常用);
act_hi_comment:历史意见表;
act_hi_detail:历史详情表,存储节点运转的一些信息(不常用);
act_hi_identitylink:历史流程人员表,存储流程各节点候选、办理人员信息,常用于查询某人或部门的已办任务;
act_hi_procinst:历史流程实例表,存储流程实例历史数据(包含正在运行的流程实例);
act_hi_taskinst:历史流程任务表,存储历史任务节点;
act_hi_varinst:流程历史变量表,存储流程历史节点的变量信息;
3)用户相关表(4个,IdentityService接口操作的表)
act_id_group:用户组信息表,对应节点选定候选组信息;
act_id_info:用户扩展信息表,存储用户扩展信息;
act_id_membership:用户与用户组关系表;
act_id_user:用户信息表,对应节点选定办理人或候选人信息;
4)流程定义、流程模板相关表(3个,RepositoryService接口操作的表)
act_re_deployment:部属信息表,存储流程定义、模板部署信息;
act_re_procdef:流程定义信息表,存储流程定义相关描述信息,但其真正内容存储在act_ge_bytearray表中,以字节形式存储;
act_re_model:流程模板信息表,存储流程模板相关描述信息,但其真正内容存储在act_ge_bytearray表中,以字节形式存储;
5)流程运行时表(6个,RuntimeService接口操作的表)
act_ru_task:运行时流程任务节点表,存储运行中流程的任务节点信息,重要,常用于查询人员或部门的待办任务时使用;
act_ru_event_subscr:监听信息表,不常用;
act_ru_execution:运行时流程执行实例表,记录运行中流程运行的各个分支信息(当没有子流程时,其数据与act_ru_task表数据是一一对应的);
act_ru_identitylink:运行时流程人员表,重要,常用于查询人员或部门的待办任务时使用;
act_ru_job:运行时定时任务数据表,存储流程的定时任务信息;
act_ru_variable:运行时流程变量数据表,存储运行中的流程各节点的变量信息;
# 流程引擎API与服务
引擎API是与Flowable交互的最常用手段。总入口点是ProcessEngine。
1、RepositoryService很可能是使用Flowable引擎要用的第一个服务。这个服务提供了管理与控制部署(deployments)与流程定义(processdefinitions)的操作。管理静态信息,
2、RuntimeService用于启动流程定义的新流程实例。
3、IdentityService很简单。它用于管理(创建,更新,删除,查询……)组与用户。
4、FormService是可选服务。也就是说Flowable没有它也能很好地运行,而不必牺牲任何功能。
5、HistoryService暴露Flowable引擎收集的所有历史数据。要提供查询历史数据的能力。
6、ManagementService通常在用Flowable编写用户应用时不需要使用。它可以读取数据库表与表原始数据的信息,也提供了对作业(job)的查询与管理操作。
7、DynamicBpmnService可用于修改流程定义中的部分内容,而不需要重新部署它。例如可以修改流程定义中一个用户任务的办理人设置,或者修改一个服务任务中的类名。
部署流程
随便写一个test
public class FlowAbleCreateTest {
@Test
public void deploymentProcess() {
//获取ProcessEngine
ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
//获取RepositoryService
RepositoryService repositoryService = processEngine.getRepositoryService();
//部署流程
Deployment deployment = repositoryService.createDeployment()
.addClasspathResource("./请假审批.bpmn20.xml") //部署资源
.name("请假审批") //部署名称
.deploy();
System.out.println("部署名:"+deployment.getName());
System.out.println("部署id:"+deployment.getId());
}
}
完成上面的部署后相关数据保存到如下3张表中:
1.流程部署表:每部署一次增加一条记录
2.流程定义表:部署每个新的流程就会在这张表中增加一条记录
-- 注意,KEY_ 这个字段是用来唯一识别不同流程的关键字
3.流程资源表
act_re_deployment和act_re_procdef一对多关系,一次部署在流程部署表生成一条记录,
但一次部署可以部署多个流程定义,每个流程定义在流程定义表生成一条记录。
每一个流程定义在act_ge_bytearray会存在两个资源记录,bpmn和png。
建议:一次部署一个流程,这样部署表和流程定义表是一对一有关系,方便读取流程部署及流程定义信息。
启动流程
@Test
public void runtimeProcess() {
//获取ProcessEngine
ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
//获取RuntimeService
RuntimeService runtimeService = processEngine.getRuntimeService();
//根据流程key启动对应的流程,创建流程实例
ProcessInstance processInstance = runtimeService.startProcessInstanceByKey("leave_approve");
//流程部署id:1
System.out.println("流程部署id:" + processInstance.getDeploymentId());
//流程定义id:evectionProcess:1:4
System.out.println("流程定义id:" + processInstance.getProcessDefinitionId());
//流程实例id:2501
System.out.println("流程实例id:" + processInstance.getId());
}
完成上面的启动流程后相关数据保存到如下7张表中:
act_hi_actinst 流程实例执行历史信息
act_hi_identitylink 流程参与用户的历史信息
act_hi_procinst 流程实例的历史信息
act_hi_taskinst 流程任务的历史信息
act_ru_execution 流程执行信息
act_ru_identitylink 流程的正在参与用户信息
act_ru_task 流程当前任务信息
更多详情:https://static.kancloud.cn/king_om/liuchengyiqin001/3023127