学习

boge-02-flowable进阶_2

Service服务接口 #

ly-20241212142104630

  • 各个Service类 RepositoryService 资源管理类,流程定义、部署、文件 RuntimeService 流程运行管理类,运行过程中(执行) TaskService 任务管理类 HistoryService 历史管理类 ManagerService 引擎管理类

Flowable图标 #

BPMN2.0定义的一些图标

  • 时间

ly-20241212142104849

  • 活动 ly-20241212142104949
  • 网关 ly-20241212142105051

流程部署深入解析 #

  • 使用eclipse打包部署(没有eclipse环境,所以这里只有截图) 将两个流程,打包为bar文件,然后放到项目resources文件夹中 ly-20241212142105247 ly-20241212142105148

  • 这里是为了测试一次部署多个流程(定义,图) 代码如下 ly-20241212142105345

  • 部署完成后查看表结构

    • act_re_procdef

      部署id一样 ly-20241212142105443

    • act_re_deployment ly-20241212142105547

    • 结论:部署和定义是1对多的关系

  • 每次部署所涉及到的资源文件 ly-20241212142105649

  • 涉及到的三张表

    • act_ge_bytearray ly-20241212142105747

    • act_re_procdef category–>xml中的namespace name–>定义时起的名称 key_—>xml中定义的id resource_name—>xml文件名称 dgrm_resource_name–>生成图片名称 suspension_state –> 是否被挂起

      tenant_id – >谁部署的流程

    • act_re_deployment name_部署名

  • 代码 ly-20241212142105845

  • 主要源码 DeployCmd.class ly-20241212142105941

  • DeploymentEntityManagerImpl.java ly-20241212142106041

    ...

boge-02-flowable进阶_1

表结构 #

  • 尽量通过API动数据

  • ACT_RE:repository,包含流程定义和流程静态资源

  • ACT_RU: runtime,包含流程实例、任务、变量等,流程结束会删除

  • ACT_HI: history,包含历史数据,比如历史流程实例、变量、任务等

  • ACT_GE: general,通用数据

  • ACT_ID: identity,组织机构。包含标识的信息,如用户、用户组等等

  • 具体的

    • 流程历史记录

      ly-20241212142103886

    • 流程定义表 ly-20241212142104111

    • 运行实例表 ly-20241212142104209

    • 用户用户组表

      ly-20241212142104309

  • 源码中的体现 ly-20241212142104410

默认的配置文件加载 #

  • 对于

    ProcessEngine defaultProcessEngine = ProcessEngines.getDefaultProcessEngine();
    //-->
    public static ProcessEngine getDefaultProcessEngine() {
            return getProcessEngine(NAME_DEFAULT); //NAME_DEFAULT = "default"
        }
    //-->
    public static ProcessEngine getProcessEngine(String processEngineName) {
            if (!isInitialized()) {
                init();
            }
            return processEngines.get(processEngineName);
        }
    //-->部分
    
        /**
         * Initializes all process engines that can be found on the classpath for resources <code>flowable.cfg.xml</code> (plain Flowable style configuration) and for resources
         * <code>flowable-context.xml</code> (Spring style configuration).
         */
        public static synchronized void init() {
            if (!isInitialized()) {
                if (processEngines == null) {
                    // Create new map to store process-engines if current map is null
                    processEngines = new HashMap<>();
                }
                ClassLoader classLoader = ReflectUtil.getClassLoader();
                Enumeration<URL> resources = null;
                try {
                    resources = classLoader.getResources("flowable.cfg.xml");
                } catch (IOException e) {
                    throw new FlowableIllegalArgumentException("problem retrieving flowable.cfg.xml resources on the classpath: " + System.getProperty("java.class.path"), e);
                }
              //后面还有,每帖出来
            }
        }
    
  • 注意这行classLoader.getResources("flowable.cfg.xml"); 需要在resources根目录下放这么一个文件

    ...

boge-01-flowable基础

Flowable介绍 #

  • flowable的历史

    ly-20241212142101999

  • flowable是BPNM的一个基于java的软件实现,不仅包括BPMN,还有DMN决策表和CMMNCase管理引擎,并且有自己的用户管理、微服务API等

获取Engine对象 #

  • maven依赖

    
        <dependencies>
            <dependency>
                <groupId>mysql</groupId>
                <artifactId>mysql-connector-java</artifactId>
                <version>8.0.29</version>
            </dependency>
            <!-- https://mvnrepository.com/artifact/org.flowable/flowable-engine -->
            <dependency>
                <groupId>org.flowable</groupId>
                <artifactId>flowable-engine</artifactId>
                <version>6.7.2</version>
            </dependency>
            <!-- https://mvnrepository.com/artifact/junit/junit -->
            <dependency>
                <groupId>junit</groupId>
                <artifactId>junit</artifactId>
                <version>4.13.2</version>
                <scope>test</scope>
            </dependency>
        </dependencies>
    
  • 配置并获取ProcessEngine

    ProcessEngineConfiguration configuration=
                    new StandaloneProcessEngineConfiguration();
            //配置
            configuration.setJdbcDriver("com.mysql.cj.jdbc.Driver");
            configuration.setJdbcUsername("root");
            configuration.setJdbcPassword("123456");
            //nullCatalogMeansCurrent=true 设置为只查当前连接的schema库
            configuration.setJdbcUrl("jdbc:mysql://localhost:3306/flowable-learn?" +
                    "useUnicode=true&characterEncoding=utf-8" +
                    "&allowMultiQueries=true" +
                    "&nullCatalogMeansCurrent=true");
            //如果数据库中表结构不存在则新建
            configuration.setDatabaseSchemaUpdate(ProcessEngineConfiguration.DB_SCHEMA_UPDATE_TRUE);
            //构建ProcessEngine
            ProcessEngine processEngine=configuration.buildProcessEngine();
    

日志和表结构介绍 #

  • 添加slf4j依赖

     <!-- https://mvnrepository.com/artifact/org.slf4j/slf4j-reload4j -->
            <dependency>
                <groupId>org.slf4j</groupId>
                <artifactId>slf4j-reload4j</artifactId>
                <version>1.7.36</version>
                <scope>test</scope>
            </dependency>
            <!-- https://mvnrepository.com/artifact/org.apache.logging.log4j/log4j-api -->
            <dependency>
                <groupId>org.apache.logging.log4j</groupId>
                <artifactId>log4j-api</artifactId>
                <version>2.17.2</version>
            </dependency>
    
  • 添加log配置文件

    ...

linux_韩老师_12-20

目录结构 #

  • 目录结构很重要

    • windows下 ly-20241212142133607

    • linux下,从根目录开始分支 /,/root (root用户),/home (创建的用户的目录),/bin(常用的指令),/etc(环境配置)

      ly-20241212142133807

    • 在linux世界里,一切皆文件

      • cpu被映射成文件

        ly-20241212142133880

      • 硬盘 ly-20241212142133952

  • 具体的目录结构

    • /bin 常用,binary的缩写,存放常用的命令 (/usr/bin、/usr/local/bin) ly-20241212142134025

    • /sbin (/usr/sbin、/usr/local/sbin) SuperUser,存放的是系统管理员使用的系统管理程序

    • /home 存放普通用户的主目录

      useradd jack
      
      • 之后看该目录 ly-20241212142134097
      • 删掉 userdel -r jack 目录消失
    • /root 该目录为系统管理员,也称超级管理员的用户的主目录

    • /lib 系统开机所需要的最基本的动态连接共享库,其作用类似于windows里的DLL,几乎所有的应用程序都需要用到这些共享库

    • lost+found 一般为空,非法关机后会存放文件

    • /etc 系统管理所需要的配置文件和子目录,比如mysql的my.conf

    • /usr 用户的应用程序和文件,类似windows的program files

    • /boot 启动Linux时使用的核心文件(破坏则无法启动)

    • /proc (不能动) 虚拟目录,系统内存的映射,访问这个目录获取系统信息

    • /srv (不能动) service的缩写,存放服务启动之后需要提取的数据

    • /sys (不能动) 安装了2.6内核中新出现的文件系统 sysfs

    • /tmp 这个目录用来存放一些临时文件

    • /dev 类似windows设备管理器,将硬件映射成文件

    • /media linux系统会自动识别一些设备,u盘、光驱,将识别的设备映射到该目录下

    • /mnt 为了让用户挂载别的文件系统,比如将外部的存储挂载到该目录 ly-20241212142134167 ly-20241212142134238

      ...

linux_韩老师_07-11

网络连接 #

  • 网络连接的三种模式 同一个教室的三个主机 ly-20241212142132441 此时三个同学可以正常通讯
    • 桥接模式 ly-20241212142132642 这是张三的虚拟机和外部互通;但是如果这样设置,ip会不够用;
    • NAT模式 ly-20241212142132718 如图,虚拟机可以跟虚拟的网卡(192.168.100.99)互通,且通过这个虚拟网卡,及(192.168.0.50代理),与外界(192.168.0.X)互通 NAT模式,网络地址转换模式,虚拟系统和外部系统通讯,不造成IP冲突 ly-20241212142132796 注意,这里外部其他主机(除0.50和100.99)是访问不到100.88的
    • 主机模式:独立的系统

虚拟机克隆 #

  • 方式1,直接拷贝整个文件夹 ly-20241212142132865
  • 方式2,使用VMWare 克隆前先把克隆目标关闭 克隆虚拟机当前状态–创建完整克隆

虚拟机快照 #

  • 为什么需要虚拟机快照 ly-20241212142132937

  • 快照a ly-20241212142133013 之后创建了文件夹hello 然后拍摄快照b 之后创建了文件夹hello2 然后拍摄快照c

  • 目前

  • 回到快照A ly-20241212142133231 之后会重启,效果(两个文件夹都没有了)

  • 如果恢复到B,然后再创建一个快照,就会变成 ly-20241212142133305

虚拟机迁移 #

  • 直接剪切、删除,即可 ly-20241212142133375

vmtools工具 #

  • 如下步骤,注意,这里只是在有界面的情况下进行安装 ly-20241212142133446
  • 安装完毕后
    • 在vm上面设置 ly-20241212142133522
    • 共享文件夹在linux中的路径 /mnt/hgfs/myshare

Flowable-05-spring-boot

入门 #

需要两个依赖

<properties>

        <flowable.version>6.7.2</flowable.version>
    </properties>
    <dependencies>
        <dependency>
            <groupId>org.flowable</groupId>
            <artifactId>flowable-spring-boot-starter</artifactId>
            <version>${flowable.version}</version>
        </dependency>

        <!-- https://mvnrepository.com/artifact/com.h2database/h2 -->
        <dependency>
            <groupId>com.h2database</groupId>
            <artifactId>h2</artifactId>
            <version>2.1.212</version>
        </dependency>

    </dependencies>

结合Spring:

只需将依赖项添加到类路径并使用*@SpringBootApplication*注释,幕后就会发生很多事情:

  • 自动创建内存数据源(因为 H2 驱动程序位于类路径中)并传递给 Flowable 流程引擎配置

  • 已创建并公开了 Flowable ProcessEngine、CmmnEngine、DmnEngine、FormEngine、ContentEngine 和 IdmEngine bean

  • 所有 Flowable 服务都暴露为 Spring bean

  • Spring Job Executor 已创建

  • 将自动部署流程文件夹中的任何 BPMN 2.0 流程定义。创建一个文件夹processes并将一个虚拟进程定义(名为one-task-process.bpmn20.xml)添加到此文件夹。该文件的内容如下所示。

    <?xml version="1.0" encoding="UTF-8"?>
    <definitions
            xmlns="http://www.omg.org/spec/BPMN/20100524/MODEL"
            xmlns:flowable="http://flowable.org/bpmn"
            targetNamespace="Examples">
    
        <process id="oneTaskProcess" name="The One Task Process">
            <startEvent id="theStart" />
            <sequenceFlow id="flow1" sourceRef="theStart" targetRef="theTask" />
            <userTask id="theTask" name="my task" flowable:assignee="kermit" />
            <sequenceFlow id="flow2" sourceRef="theTask" targetRef="theEnd" />
            <endEvent id="theEnd" />
        </process>
    
    </definitions>
    
  • 案例文件夹中的任何 CMMN 1.1 案例定义都将自动部署。

    ...

Flowable-04-spring

ProcessEngineFactoryBean #

  • 将ProcessEngine配置为常规的SpringBean

    <bean id="processEngineConfiguration" class="org.flowable.spring.SpringProcessEngineConfiguration">
        ...
    </bean>
    
    <bean id="processEngine" class="org.flowable.spring.ProcessEngineFactoryBean">
      <property name="processEngineConfiguration" ref="processEngineConfiguration" />
    </bean>
    
  • 使用transaction

    <beans xmlns="http://www.springframework.org/schema/beans"
           xmlns:context="http://www.springframework.org/schema/context"
           xmlns:tx="http://www.springframework.org/schema/tx"
           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
                               http://www.springframework.org/schema/context
                                 http://www.springframework.org/schema/context/spring-context-2.5.xsd
                               http://www.springframework.org/schema/tx
                                 http://www.springframework.org/schema/tx/spring-tx-3.0.xsd">
    
      <bean id="dataSource" class="org.springframework.jdbc.datasource.SimpleDriverDataSource">
        <property name="driverClass" value="org.h2.Driver" />
        <property name="url" value="jdbc:h2:mem:flowable;DB_CLOSE_DELAY=1000" />
        <property name="username" value="sa" />
        <property name="password" value="" />
      </bean>
    
      <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
        <property name="dataSource" ref="dataSource" />
      </bean>
    
      <bean id="processEngineConfiguration" class="org.flowable.spring.SpringProcessEngineConfiguration">
        <property name="dataSource" ref="dataSource" />
        <property name="transactionManager" ref="transactionManager" />
        <property name="databaseSchemaUpdate" value="true" />
        <property name="asyncExecutorActivate" value="false" />
      </bean>
    
      <bean id="processEngine" class="org.flowable.spring.ProcessEngineFactoryBean">
        <property name="processEngineConfiguration" ref="processEngineConfiguration" />
      </bean>
    
      <bean id="repositoryService" factory-bean="processEngine" factory-method="getRepositoryService" />
      <bean id="runtimeService" factory-bean="processEngine" factory-method="getRuntimeService" />
      <bean id="taskService" factory-bean="processEngine" factory-method="getTaskService" />
      <bean id="historyService" factory-bean="processEngine" factory-method="getHistoryService" />
      <bean id="managementService" factory-bean="processEngine" factory-method="getManagementService" />
    
    ...
    
  • 还包括了其他的一些bean

    <beans>
      ...
      <tx:annotation-driven transaction-manager="transactionManager"/>
    
      <bean id="userBean" class="org.flowable.spring.test.UserBean">
        <property name="runtimeService" ref="runtimeService" />
      </bean>
    
      <bean id="printer" class="org.flowable.spring.test.Printer" />
    
    </beans>
    
  • 使用

    ...

Flowable-03-api

流程引擎API和服务 #

引擎API是与Flowable交互的常见方式,主要起点是ProcessEngine,可以通过配置(Configuration章节)中描述的多种方式创建。

从ProcessEngine获取包含工作流/BPM方法的各种服务。ProcessEngine和服务对象是线程安全的

ly-20241212142116684

下面是通过processEngine获取各种服务的方法

ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();

RuntimeService runtimeService = processEngine.getRuntimeService();
RepositoryService repositoryService = processEngine.getRepositoryService();
TaskService taskService = processEngine.getTaskService();
ManagementService managementService = processEngine.getManagementService();
IdentityService identityService = processEngine.getIdentityService();
HistoryService historyService = processEngine.getHistoryService();
FormService formService = processEngine.getFormService();
DynamicBpmnService dynamicBpmnService = processEngine.getDynamicBpmnService();

ProcessEngines.getDefaultProcessEngine()在第一次调用时初始化并构建流程引擎,然后返回相同的流程引擎

ProcessEngines类将扫描所有flowable.cfg.xml和flowable-context.xml文件。

对于所有 flowable.cfg.xml 文件,流程引擎将以典型的 Flowable 方式构建:ProcessEngineConfiguration.createProcessEngineConfigurationFromInputStream(inputStream).buildProcessEngine()。

对于所有 flowable-context.xml 文件,流程引擎将以 Spring 方式构建:首先创建 Spring 应用程序上下文,然后从该应用程序上下文中获取流程引擎。

The RepositoryService is probably the first service needed when working with the Flowable engine.

该服务**(RepositoryService)提供用于管理和操作部署deployments**和流程定义的操作

  • 查询引擎已知的部署和流程定义
  • 暂停和激活作为一个整体或特定流程定义的部署。挂起意味着不能对它们执行进一步的操作,而激活则相反并再次启用操作
  • 检索各种资源,例如引擎自动生成的部署或流程图中包含的文件
  • 检索流程定义的 POJO 版本,该版本可用于使用 Java 而不是 XML 来内省流程

RepositoryService主要是关于静态信息(不会改变的数据,或者至少不会改变太多),而RuntimeService处理启动流程定义的新流程实例

...

Flowable-02-Configuration

创建流程引擎 #

Flowable 流程引擎通过一个名为 flowable.cfg.xml 的 XML 文件进行配置

  • 现在类路径下放置floable.cfg.xml文件

    <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="processEngineConfiguration" class="org.flowable.engine.impl.cfg.StandaloneProcessEngineConfiguration">
    
        <property name="jdbcUrl" value="jdbc:h2:mem:flowable;DB_CLOSE_DELAY=1000" />
        <property name="jdbcDriver" value="org.h2.Driver" />
        <property name="jdbcUsername" value="sa" />
        <property name="jdbcPassword" value="" />
    
        <property name="databaseSchemaUpdate" value="true" />
    
        <property name="asyncExecutorActivate" value="false" />
    
        <property name="mailServerHost" value="mail.my-corp.com" />
        <property name="mailServerPort" value="5025" />
      </bean>
    
    </beans>
    
  • 然后使用静态方法进行获取ProcessEngine

    ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
    
  • 还有其他配置,这里不一一列举,详见文档地址 https://www.flowable.com/open-source/docs/bpmn/ch03-Configuration

  • 大致目录如下 ly-20241212142116369 ly-20241212142116576

Flowable-01-GettingStarted

入门 #

什么是流动性 #

Flowable 是一个用 Java 编写的轻量级业务流程引擎。Flowable 流程引擎允许您部署 BPMN 2.0 流程定义(用于定义流程的行业 XML 标准)、创建这些流程定义的流程实例、运行查询、访问活动或历史流程实例和相关数据等等。

可以使用 Flowable REST API 通过 HTTP 进行通信。还有几个 Flowable 应用程序(Flowable Modeler、Flowable Admin、Flowable IDM 和 Flowable Task)提供开箱即用的示例 UI,用于处理流程和任务。

Flowable和Activiti #

Flowable是Activiti的一个分支

构建命令行命令 #

创建流程引擎 #

请假流程如下

  • 员工要求休假数次
  • 经理批准或拒绝请求
  • 之后将模拟再某个外部系统中注册请求,并向员工发送一封包含结果的邮件

创建一个空的Mave项目,并添加依赖

    <dependencies>
        <dependency>
            <groupId>org.flowable</groupId>
            <artifactId>flowable-engine</artifactId>
            <version>6.6.0</version>
        </dependency>
        <dependency>
            <groupId>com.h2database</groupId>
            <artifactId>h2</artifactId>
            <version>1.3.176</version>
        </dependency> 

        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>8.0.29</version> <!--当版本号>=8.0.22时会报date转字符串的错误-->
        </dependency>
    </dependencies>

添加一个带有Main方法的类

这里实例化一个ProcessEngine实例,一般只需要实例化一次,是通过ProcessEngineConfiguration创建的,用来配置和调整流程引擎的配置

  • ProcessEngineConfiguration也可以使用配置 XML 文件创建
  • ProcessEngineConfiguration需要的最低配置是与数据库的 JDBC 连接
package org.flowable;

import org.flowable.engine.ProcessEngine;
import org.flowable.engine.ProcessEngineConfiguration;
import org.flowable.engine.impl.cfg.StandaloneProcessEngineConfiguration;

public class HolidayRequest {
    public static void main(String[] args) {

        //这里改用mysql,注意后面的nullCatalogMeansCurrent=true
        //注意,pom需要添加mysql驱动依赖
        ProcessEngineConfiguration cfg = new StandaloneProcessEngineConfiguration()
                .setJdbcUrl("jdbc:mysql://localhost:3306/flowable_official?useUnicode=true" +
                        "&characterEncoding=utf-8&serverTimezone=Asia/Shanghai&allowMultiQueries=true"
                        +"&nullCatalogMeansCurrent=true"
                )
                .setJdbcUsername("root")
                .setJdbcPassword("123456")
                .setJdbcDriver("com.mysql.cj.jdbc.Driver")
                .setDatabaseSchemaUpdate(ProcessEngineConfiguration.DB_SCHEMA_UPDATE_TRUE);
        /* //这是官网,用的h2
        ProcessEngineConfiguration cfg = new StandaloneProcessEngineConfiguration()
                .setJdbcUrl("jdbc:h2:mem:flowable;DB_CLOSE_DELAY=-1")
                .setJdbcUsername("sa")
                .setJdbcPassword("")
                .setJdbcDriver("org.h2.Driver")
                .setDatabaseSchemaUpdate(ProcessEngineConfiguration.DB_SCHEMA_UPDATE_TRUE);*/

        ProcessEngine processEngine = cfg.buildProcessEngine();
    }
}

运行后会出现slf4j的警告,添加依赖并编写配置文件即可

...