国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

Activiti 工作流簡介

這篇具有很好參考價(jià)值的文章主要介紹了Activiti 工作流簡介。希望對(duì)大家有所幫助。如果存在錯(cuò)誤或未考慮完全的地方,請(qǐng)大家不吝賜教,您也可以點(diǎn)擊"舉報(bào)違法"按鈕提交疑問。

1、什么是工作流

????????工作流(Workflow),就是通過計(jì)算機(jī)對(duì)業(yè)務(wù)流程自動(dòng)化執(zhí)行管理。它主要解決的是“使在多個(gè)參與者之間按照某種預(yù)定義的規(guī)則自動(dòng)進(jìn)行傳遞文檔、信息或任務(wù)的過程,從而實(shí)現(xiàn)某個(gè)預(yù)期的業(yè)務(wù)目標(biāo),或者促使此目標(biāo)的實(shí)現(xiàn)”。

1.2、工作流系統(tǒng)

????????一個(gè)軟件系統(tǒng)中具有工作流的功能,我們把它稱為工作流系統(tǒng),一個(gè)系統(tǒng)中工作流的功能是什么?就是對(duì)系統(tǒng)的業(yè)務(wù)流程進(jìn)行自動(dòng)化管理,所以工作流是建立在業(yè)務(wù)流程的基礎(chǔ)上,所以一個(gè)軟件的系統(tǒng)核心根本上還是系統(tǒng)的業(yè)務(wù)流程,工作流只是協(xié)助進(jìn)行業(yè)務(wù)流程管理。即使沒有工作流業(yè)務(wù)系統(tǒng)也可以開發(fā)運(yùn)行,只不過有了工作流可以更好的管理業(yè)務(wù)流程,提高系統(tǒng)的可擴(kuò)展性。

1.3、Activiti概述

????????Activiti是一個(gè)工作流引擎, activiti可以將業(yè)務(wù)系統(tǒng)中復(fù)雜的業(yè)務(wù)流程抽取出來,使用專門的建模語言BPMN2.0進(jìn)行定義,業(yè)務(wù)流程按照預(yù)先定義的流程進(jìn)行執(zhí)行,實(shí)現(xiàn)了系統(tǒng)的流程由activiti進(jìn)行管理,減少業(yè)務(wù)系統(tǒng)由于流程變更進(jìn)行系統(tǒng)升級(jí)改造的工作量,從而提高系統(tǒng)的健壯性,同時(shí)也減少了系統(tǒng)開發(fā)維護(hù)成本。

1.4、BPM

????????BPM即業(yè)務(wù)流程管理,是一種規(guī)范化的構(gòu)造端到端的業(yè)務(wù)流程,以持續(xù)的提高組織業(yè)務(wù)效率。 idea插件安裝:https://plugins.jetbrains.com/plugin/7429-actibpm/versions 將下載的jar包插件直接整到idea當(dāng)中,在settings當(dāng)中的插件當(dāng)中,導(dǎo)入本地插件,導(dǎo)入插件之后重啟idea即可。

2、Activiti工作流環(huán)境搭建

引入相關(guān)依賴:(主要MySQL的版本和自己本地需要一致)

<properties>
? ? <slf4j.version>1.6.6</slf4j.version>
? ? <log4j.version>1.2.12</log4j.version>
? ? <activiti.version>7.0.0.Beta1</activiti.version>
</properties>
<dependencies>
? ? <dependency>
? ? ? ? <groupId>org.activiti</groupId>
? ? ? ? <artifactId>activiti-engine</artifactId>
? ? ? ? <version>${activiti.version}</version>
? ? </dependency>
? ? <dependency>
? ? ? ? <groupId>org.activiti</groupId>
? ? ? ? <artifactId>activiti-spring</artifactId>
? ? ? ? <version>${activiti.version}</version>
? ? </dependency>
? ? <!-- bpmn 模型處理 -->
? ? <dependency>
? ? ? ? <groupId>org.activiti</groupId>
? ? ? ? <artifactId>activiti-bpmn-model</artifactId>
? ? ? ? <version>${activiti.version}</version>
? ? </dependency>
? ? <!-- bpmn 轉(zhuǎn)換 -->
? ? <dependency>
? ? ? ? <groupId>org.activiti</groupId>
? ? ? ? <artifactId>activiti-bpmn-converter</artifactId>
? ? ? ? <version>${activiti.version}</version>
? ? </dependency>
? ? <!-- bpmn json數(shù)據(jù)轉(zhuǎn)換 -->
? ? <dependency>
? ? ? ? <groupId>org.activiti</groupId>
? ? ? ? <artifactId>activiti-json-converter</artifactId>
? ? ? ? <version>${activiti.version}</version>
? ? </dependency>
? ? <!-- bpmn 布局 -->
? ? <dependency>
? ? ? ? <groupId>org.activiti</groupId>
? ? ? ? <artifactId>activiti-bpmn-layout</artifactId>
? ? ? ? <version>${activiti.version}</version>
? ? </dependency>
? ? <!-- activiti 云支持 -->
? ? <dependency>
? ? ? ? <groupId>org.activiti.cloud</groupId>
? ? ? ? <artifactId>activiti-cloud-services-api</artifactId>
? ? ? ? <version>${activiti.version}</version>
? ? </dependency>
? ? <!-- mysql驅(qū)動(dòng) -->
? ? <dependency>
? ? ? ? <groupId>mysql</groupId>
? ? ? ? <artifactId>mysql-connector-java</artifactId>
? ? ? ? <version>8.0.23</version>
? ? </dependency>
? ? <!-- mybatis -->
? ? <dependency>
? ? ? ? <groupId>org.mybatis</groupId>
? ? ? ? <artifactId>mybatis</artifactId>
? ? ? ? <version>3.4.5</version>
? ? </dependency>
? ? <!-- 鏈接池 -->
? ? <dependency>
? ? ? ? <groupId>commons-dbcp</groupId>
? ? ? ? <artifactId>commons-dbcp</artifactId>
? ? ? ? <version>1.4</version>
? ? </dependency>
? ? <dependency>
? ? ? ? <groupId>junit</groupId>
? ? ? ? <artifactId>junit</artifactId>
? ? ? ? <version>4.12</version>
? ? </dependency>
? ? <!-- log start -->
? ? <dependency>
? ? ? ? <groupId>log4j</groupId>
? ? ? ? <artifactId>log4j</artifactId>
? ? ? ? <version>${log4j.version}</version>
? ? </dependency>
? ? <dependency>
? ? ? ? <groupId>org.slf4j</groupId>
? ? ? ? <artifactId>slf4j-api</artifactId>
? ? ? ? <version>${slf4j.version}</version>
? ? </dependency>
? ? <dependency>
? ? ? ? <groupId>org.slf4j</groupId>
? ? ? ? <artifactId>slf4j-log4j12</artifactId>
? ? ? ? <version>${slf4j.version}</version>
? ? </dependency>
</dependencies>
?

?使用log4j日志,直接在resources下創(chuàng)建log4j.properties:日志文件路徑根據(jù)實(shí)際路徑修改

# Set root category priority to INFO and its only appender to CONSOLE.
#log4j.rootCategory=INFO, CONSOLE debug info warn error fatal
log4j.rootCategory=debug, CONSOLE, LOGFILE
# Set the enterprise logger category to FATAL and its only appender to CONSOLE.
log4j.logger.org.apache.axis.enterprise=FATAL, CONSOLE
# CONSOLE is set to be a ConsoleAppender using a PatternLayout.
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.layout=org.apache.log4j.PatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%d{ISO8601} %-6r[%15.15t] %-5p %30.30c %x - %m\n
# LOGFILE is set to be a File appender using a PatternLayout.
log4j.appender.LOGFILE=org.apache.log4j.FileAppender
log4j.appender.LOGFILE.File=E:\\workFile\\log4jLog\\activiti.log
log4j.appender.LOGFILE.Append=true
log4j.appender.LOGFILE.layout=org.apache.log4j.PatternLayout
log4j.appender.LOGFILE.layout.ConversionPattern=%d{ISO8601} %-6r[%15.15t] %-5p %30.30c %x - %m\n

添加activiti配置文件,使用activiti提供的默認(rèn)方式來創(chuàng)建mysql的表。默認(rèn)方式是在 resources 下創(chuàng)建 activiti.cfg.xml 文件,注意:默認(rèn)方式目錄和文件名不能修改,因?yàn)閍ctiviti的源碼中已經(jīng)設(shè)置,到固定的目錄讀取固定文件名的文件。默認(rèn)要在在activiti.cfg.xml中bean的名字叫processEngineConfiguration,名字不可修改,在這里直接連接到本地?cái)?shù)據(jù)庫activiti這個(gè)庫。

工作流,intellij-idea,java,ide

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:tx="http://www.springframework.org/schema/tx"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
                    http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/contex
http://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx.xsd">
    <!-- 默認(rèn)id對(duì)應(yīng)的值 為processEngineConfiguration -->
    <!-- processEngine Activiti的流程引擎 -->
<!--    <bean id="processEngineConfiguration"-->
<!--          class="org.activiti.engine.impl.cfg.StandaloneProcessEngineConfiguration">-->
<!--        <property name="jdbcDriver" value="com.mysql.cj.jdbc.Driver"/>-->
<!--        <property name="jdbcUrl" value="jdbc:mysql:///activiti?autoReconnect=true"/>-->
<!--        <property name="jdbcUsername" value="root"/>-->
<!--        <property name="jdbcPassword" value="123456"/>-->
<!--        <property name="databaseSchemaUpdate" value="true"/>-->
<!--    </bean>-->

    <!-- 這里可以使用 鏈接池 dbcp-->
    <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource">
        <property name="driverClassName" value="com.mysql.cj.jdbc.Driver" />
        <property name="url" value="jdbc:mysql:///activiti?autoReconnect=true" />
        <property name="username" value="root" />
        <property name="password" value="123456" />
        <property name="maxActive" value="3" />
        <property name="maxIdle" value="1" />
    </bean>

    <bean id="processEngineConfiguration"
          class="org.activiti.engine.impl.cfg.StandaloneProcessEngineConfiguration">
        <!-- 引用數(shù)據(jù)源 上面已經(jīng)設(shè)置好了-->
        <property name="dataSource" ref="dataSource" />
        <!-- activiti數(shù)據(jù)庫表處理策略 -->
        <property name="databaseSchemaUpdate" value="true"/>
    </bean>

</beans>

?創(chuàng)建一個(gè)測(cè)試類,調(diào)用activiti的工具類,生成acitivti需要的數(shù)據(jù)庫表。直接使用activiti提供的工具類ProcessEngines,會(huì)默認(rèn)讀取classpath下的activiti.cfg.xml文件,讀取其中的數(shù)據(jù)庫配置,創(chuàng)建 ProcessEngine,在創(chuàng)建ProcessEngine 時(shí)會(huì)自動(dòng)創(chuàng)建表。代碼執(zhí)行完成之后在數(shù)據(jù)庫當(dāng)中進(jìn)行查看對(duì)應(yīng)的表是否都創(chuàng)建出來了。
?

import org.activiti.engine.ProcessEngine;
import org.activiti.engine.ProcessEngineConfiguration;
import org.activiti.engine.ProcessEngines;
import org.junit.jupiter.api.Test;
import org.springframework.boot.test.context.SpringBootTest;

@SpringBootTest
class SpringbootHelloApplicationTests {

    @Test
    void contextLoads() {
        //使用classpath下的activiti.cfg.xml中的配置創(chuàng)建processEngine
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        System.out.println(processEngine);
        // 而除了使用默認(rèn)配置進(jìn)行創(chuàng)建工作流引擎對(duì)象,還可以通過自定義的方式進(jìn)行創(chuàng)建。
        // 自定義配置文件名
        ProcessEngineConfiguration processEngineConfigurationFromResource = ProcessEngineConfiguration.createProcessEngineConfigurationFromResource("activiti.cfg.xml");
        System.out.println(processEngineConfigurationFromResource);
        // 自定義配置文件名 bean對(duì)象id
        ProcessEngineConfiguration processEngineConfigurationFromResource1 = ProcessEngineConfiguration.createProcessEngineConfigurationFromResource("activiti.cfg.xml", "processEngineConfiguration");
        System.out.println(processEngineConfigurationFromResource1);
    }

}

工作流,intellij-idea,java,ide

執(zhí)行完數(shù)據(jù)庫生成25張表。

工作流,intellij-idea,java,ide

?3、Activiti 類、配置文件之間的關(guān)系


3.1、activiti.cfg.xml
????????activiti的引擎配置文件,包括:ProcessEngineConfiguration的定義、數(shù)據(jù)源定義、事務(wù)管理器等,此文件其實(shí)就是一個(gè)spring配置文件。

3.2、流程引擎配置類
????????流程引擎的配置類(ProcessEngineConfiguration),通過ProcessEngineConfiguration可以創(chuàng)建工作流引擎ProceccEngine,常用的兩種方法如下:

????????3.2.1、StandaloneProcessEngineConfiguration
使用StandaloneProcessEngineConfigurationActiviti可以單獨(dú)運(yùn)行,來創(chuàng)建ProcessEngine,Activiti會(huì)自己處理事務(wù)。配置文件方式:通常在activiti.cfg.xml配置文件中定義一個(gè)id為 processEngineConfiguration 的bean,見環(huán)境搭建模塊,就是使用這種方式進(jìn)行配置的。

????????3.2.2、SpringProcessEngineConfiguration
通過org.activiti.spring.SpringProcessEngineConfiguration 與Spring整合。

3.3、Servcie服務(wù)接口
????????Service是工作流引擎提供用于進(jìn)行工作流部署、執(zhí)行、管理的服務(wù)接口,我們使用這些接口可以就是操作服務(wù)對(duì)應(yīng)的數(shù)據(jù)表,并且在這里通過processEngine對(duì)象get對(duì)應(yīng)的service就可以獲取到service對(duì)象了。

工作流,intellij-idea,java,ide

?4、流程的創(chuàng)建與操作

4.1 流程圖的繪制,安裝bpmn插件

工作流,intellij-idea,java,ide?將文件后綴bpmn改為xml,打開文件如下

工作流,intellij-idea,java,ide

?4.2.1 單個(gè)文件部署方式

將上面的流程部署到activiti的數(shù)據(jù)庫中,就是流程定義部署。

/**
     * 單個(gè)文件部署流程
     */
    @Test
    public void develop() {
        // 創(chuàng)建流程對(duì)象
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        // 獲取service對(duì)象
        RepositoryService repositoryService = processEngine.getRepositoryService();
        // 流程部署 設(shè)置名字 將bpmn和png部署進(jìn)去
        Deployment deploy = repositoryService.createDeployment()
                .addClasspathResource("bpmn/hello.bpmn")
                .addClasspathResource("bpmn/hello.png")
                .name("請(qǐng)假流程")
                .deploy();
        System.out.println("id = " + deploy.getId());
        System.out.println("name = " + deploy.getName());
    }

之后直接啟動(dòng)這個(gè)測(cè)試方法進(jìn)行流程部署,可以觀察日志,整個(gè)部署的過程當(dāng)中總共操作了三張表

  1. act_re_deployment 流程定義部署表,每部署一次增加一條記錄
  2. act_re_procdef 流程定義表,部署每個(gè)新的流程定義都會(huì)在這張表中增加一條記錄
  3. act_ge_bytearray 流程資源表

????????act_re_deployment 和 act_re_procdef一對(duì)多關(guān)系,一次部署在流程部署表生成一條記錄,但一次部署可以部署多個(gè)流程定義,每個(gè)流程定義在流程定義表生成一條記錄。每一個(gè)流程定義在act_ge_bytearray會(huì)存在兩個(gè)資源記錄,bpmn和png。

4.2.2 使用壓縮包的方式

/**
     * 壓縮包的方式部署
     */
    @Test
    public void devoZip(){
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RepositoryService repositoryService = processEngine.getRepositoryService();
        InputStream inputStream = this.getClass().getClassLoader().getResourceAsStream("bpmn/hello.zip");
        ZipInputStream zipInputStream = new ZipInputStream(inputStream);
        Deployment deploy = repositoryService.createDeployment().addZipInputStream(zipInputStream).deploy();
        System.out.println("id = " + deploy.getId());
        System.out.println("name = " + deploy.getName());
    }

4.3 開始流程

????????啟動(dòng)一個(gè)流程表示發(fā)起一個(gè)新的請(qǐng)假申請(qǐng),這就相當(dāng)于java類與java對(duì)象的關(guān)系,類定義好后需要new創(chuàng)建一個(gè)對(duì)象使用,當(dāng)然可以new多個(gè)對(duì)象。對(duì)于請(qǐng)出差申請(qǐng)流程,發(fā)起一個(gè)請(qǐng)假申請(qǐng)單需要啟動(dòng)一個(gè)流程實(shí)例,請(qǐng)假申請(qǐng)單發(fā)起請(qǐng)假也需要啟動(dòng)一個(gè)流程實(shí)例。

流程實(shí)例的key查看數(shù)據(jù)庫

工作流,intellij-idea,java,ide

/**
     * 開始流程
     */
    @Test
    public void start(){
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RuntimeService runtimeService = processEngine.getRuntimeService();
        // 根據(jù)流程id啟動(dòng)流程 act_re_procdef表里的key
        ProcessInstance instance = runtimeService.startProcessInstanceByKey("myProcess_1");
        System.out.println("流程id = " + instance.getProcessDefinitionId());
        System.out.println("實(shí)例id = " + instance.getId());
        System.out.println("活動(dòng)id = " + instance.getActivityId());
    }

工作流,intellij-idea,java,ide

?流程開始成功。

4.4 任務(wù)查詢

????????流程啟動(dòng)后,任務(wù)的負(fù)責(zé)人就可以查詢自己當(dāng)前需要處理的任務(wù),查詢出來的任務(wù)都是該用戶的待辦任務(wù)。

/**
     * 查找任務(wù)
     */
    @Test
    public void findTask(){
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();

        // act_ru_task表里的assignee字段就是處理人 可以手動(dòng)設(shè)置
        List<Task> list = taskService.createTaskQuery().processDefinitionKey("myProcess_1").taskAssignee("cxb").list();
        for (Task task : list){
            System.out.println("流程id = " + task.getProcessInstanceId());
            System.out.println("任務(wù)id = " + task.getId());
            System.out.println("任務(wù)負(fù)責(zé)人 = " + task.getAssignee());
            System.out.println("任務(wù)名稱 = " + task.getName());
        }
    }

而對(duì)應(yīng)的查詢語句也是:根據(jù)流程的Key以及負(fù)責(zé)人去task當(dāng)中查詢?nèi)蝿?wù)。

SELECT DISTINCT RES.* FROM ACT_RU_TASK RES INNER JOIN ACT_RE_PROCDEF D ON RES.PROC_DEF_ID_ = D.ID_ 
WHERE RES.ASSIGNEE_ = 'yueyue' AND D.KEY_ = 'myLeave' ORDER BY RES.ID_ ASC LIMIT 2147483647 OFFSET 0 

工作流,intellij-idea,java,ide

這里設(shè)置處理人。

?工作流,intellij-idea,java,ide

?4.5 任務(wù)推動(dòng)

????????在前面我們可以獲取到負(fù)責(zé)人所有的任務(wù),并且可以獲取到相對(duì)應(yīng)的任務(wù)id,這里只需要獲取id進(jìn)行推動(dòng)流程即可。

/**
     * 任務(wù)推動(dòng)
     */
    @Test
    public void next(){
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();

        taskService.complete("5005");
        // 獲取單個(gè)流程數(shù)據(jù)進(jìn)行操作,替換掉上面的2505
        // Task task = taskService.createTaskQuery().processDefinitionKey("myProcess_1").taskAssignee("zhangsan").singleResult();
        // taskService.complete(task.getId());
        System.out.println("任務(wù)完成");
    }

工作流,intellij-idea,java,ide

?????????任務(wù)推動(dòng)之后還是和查詢?nèi)蝿?wù)一致的查詢語句獲取當(dāng)前負(fù)責(zé)人的數(shù)據(jù),也可以直接查看 act_ru_task這張表的流程數(shù)據(jù)推動(dòng)了沒,而之前的流程會(huì)保存在 act_hi_taskinst 這張表當(dāng)中。而這里對(duì)后續(xù)的幾個(gè)流程的推動(dòng)也是相同的道理,就不繼續(xù)進(jìn)行流程推動(dòng)了,當(dāng)最后一步的流程走完之后,整個(gè)流程已經(jīng)結(jié)束,在act_ru_task這張表就不會(huì)存在當(dāng)前這個(gè)流程的數(shù)據(jù)了。


4.6 流程定義信息查詢

????????查詢流程相關(guān)信息,包含流程定義,流程部署,流程定義版本

/**
     * 流程定義信息查詢
     */
    @Test
    public void processInfo() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RepositoryService repositoryService = processEngine.getRepositoryService();
        ProcessDefinitionQuery processDefinitionQuery = repositoryService.createProcessDefinitionQuery();
        List<ProcessDefinition> list = processDefinitionQuery.processDefinitionKey("myProcess_1").orderByProcessDefinitionVersion().desc().list();
        for (ProcessDefinition definition : list) {
            System.out.println("id = " + definition.getId());
            System.out.println("name = " + definition.getName());
            System.out.println("key = " + definition.getKey());
            System.out.println("version = " + definition.getVersion());
        }
    }

工作流,intellij-idea,java,ide

?4.7 流程刪除

/**
     * 刪除流程
     */
    @Test
    public void deleteProcess() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RepositoryService repositoryService = processEngine.getRepositoryService();
//        repositoryService.deleteDeployment("1");
        // 如果該流程定義下存在已經(jīng)運(yùn)行的流程,使用普通刪除報(bào)錯(cuò),可用級(jí)聯(lián)刪除方法將流程及相關(guān)記錄全部刪除。
        // 先刪除沒有完成流程節(jié)點(diǎn),最后就可以完全刪除流程定義信息
         repositoryService.deleteDeployment("1", true);
    }

工作流,intellij-idea,java,ide

?4.8 下載資源文件

????????首先可以知道資源文件存在 act_ge_bytearray 這張表當(dāng)中,而對(duì)于流程的數(shù)據(jù)bpmn和png文件的DEPLOYMENT_ID這個(gè)字段是相同的,因此只需要獲取到這個(gè)id就能得到相對(duì)應(yīng)的數(shù)據(jù),這個(gè)id如何獲取呢?在前面4.6獲取流程信息當(dāng)中就可以獲取到這個(gè)id,因此把之前獲取全部改為獲取單個(gè),就能拿到這個(gè)id了。而后續(xù)根據(jù)repositoryService來進(jìn)行獲取需要兩個(gè)參數(shù),一個(gè)就是這個(gè)id,另外一個(gè)就是文件的路徑,文件的路徑可以在 act_re_procdef 當(dāng)中進(jìn)行獲取。
?

/**
     * 下載資源文件
     * @throws IOException
     */
    @Test
    public void getBolb() throws IOException {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RepositoryService repositoryService = processEngine.getRepositoryService();
        ProcessDefinitionQuery processDefinitionQuery = repositoryService.createProcessDefinitionQuery();
        ProcessDefinition definition = processDefinitionQuery.processDefinitionKey("myProcess_1").orderByProcessDefinitionVersion().desc().singleResult();

        // 獲取流程id 文件名
        String deploymentId = definition.getDeploymentId();
        String diagramResourceName = definition.getDiagramResourceName();
        String resourceName = definition.getResourceName();

        // 得到input流
        InputStream pngInput = repositoryService.getResourceAsStream(deploymentId, diagramResourceName);
        InputStream bpmnInput = repositoryService.getResourceAsStream(deploymentId, resourceName);

        File pngFile = new File("d:/leave.png");
        File bpmnFile = new File("d:/leave.bpmn");

        FileOutputStream pngOutputStream = new FileOutputStream(pngFile);
        FileOutputStream bpmnOutputStream = new FileOutputStream(bpmnFile);

        // 輸入輸出轉(zhuǎn)換
        IOUtils.copy(pngInput, pngOutputStream);
        IOUtils.copy(bpmnInput, bpmnOutputStream);

        pngInput.close();
        pngOutputStream.close();
        bpmnInput.close();
        bpmnOutputStream.close();
    }

并且這里使用到的IOUtils工具類是apache提供的,需要引入新的依賴

<dependency>
            <groupId>commons-io</groupId>
            <artifactId>commons-io</artifactId>
            <version>2.6</version>
        </dependency>

4.9 流程歷史信息查看

????????即使流程定義已經(jīng)刪除了,流程執(zhí)行的歷史信息通過前面的分析,依然保存在activiti的act_hi_*相關(guān)的表中。所以我們還是可以查詢流程執(zhí)行的歷史信息,可以通過HistoryService來查看相關(guān)的歷史記錄。

/**
     * 查看流程歷史信息
     */
    @Test
    public void findHistory() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        HistoryService historyService = processEngine.getHistoryService();
        // 設(shè)置查詢條件進(jìn)行查詢
        List<HistoricActivityInstance> list = historyService.createHistoricActivityInstanceQuery()
                .orderByHistoricActivityInstanceStartTime().asc()
                .processInstanceId("12501").list();
        for (HistoricActivityInstance historiy : list) {
            System.out.println("activiti id = " + historiy.getActivityId());
            System.out.println("activiti name = " + historiy.getActivityName());
            System.out.println("process definition id = " + historiy.getProcessDefinitionId());
            System.out.println("process instance id = " + historiy.getProcessInstanceId());
            System.out.println("start time = " + new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(historiy.getStartTime()));
            System.out.println("===============================================");
        }
    }

工作流,intellij-idea,java,ide

4.10、給流程實(shí)例添加Businesskey(業(yè)務(wù)標(biāo)識(shí))

????????啟動(dòng)流程實(shí)例時(shí),指定的businesskey,就會(huì)在act_ru_execution #流程實(shí)例的執(zhí)行表中存儲(chǔ)businesskey。
Businesskey:業(yè)務(wù)標(biāo)識(shí),通常為業(yè)務(wù)表的主鍵,業(yè)務(wù)標(biāo)識(shí)和流程實(shí)例一一對(duì)應(yīng)。業(yè)務(wù)標(biāo)識(shí)來源于業(yè)務(wù)系統(tǒng)。存儲(chǔ)業(yè)務(wù)標(biāo)識(shí)就是根據(jù)業(yè)務(wù)標(biāo)識(shí)來關(guān)聯(lián)查詢業(yè)務(wù)系統(tǒng)的數(shù)據(jù)。

/**
     * 增加業(yè)務(wù)標(biāo)識(shí)
     */
    @Test
    public void addLeaveKey() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RuntimeService runtimeService = processEngine.getRuntimeService();
        ProcessInstance myLevel = runtimeService.startProcessInstanceByKey("myProcess_1", "1001");
        System.out.println(myLevel.getBusinessKey());
    }

工作流,intellij-idea,java,ide

4.11 流程的掛起與激活

4.11.1、全部流程實(shí)例掛起

????????操作流程定義為掛起狀態(tài),該流程定義下邊所有的流程實(shí)例全部暫停:流程定義為掛起狀態(tài)該流程定義將不允許啟動(dòng)新的流程實(shí)例,同時(shí)該流程定義下所有的流程實(shí)例將全部掛起暫停執(zhí)行。

/**
     * 全部流程實(shí)例掛起
     */
    @Test
    public void suspendAll() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RepositoryService repositoryService = processEngine.getRepositoryService();

        ProcessDefinition definition = repositoryService.createProcessDefinitionQuery().processDefinitionKey("myProcess_1").singleResult();
        // 是否暫停
        boolean suspended = definition.isSuspended();
        String id = definition.getId();
        if (suspended) {
            repositoryService.activateProcessDefinitionById(id, true, null);
            System.out.println("id = " + id + " 激活");
        } else {
            repositoryService.suspendProcessDefinitionById(id, true, null);
            System.out.println("id = " + id + " 掛起");
        }
    }

4.11.2、單個(gè)流程實(shí)例掛起

?????????操作流程實(shí)例對(duì)象,針對(duì)單個(gè)流程執(zhí)行掛起操作,某個(gè)流程實(shí)例掛起則此流程不再繼續(xù)執(zhí)行,完成該流程實(shí)例的當(dāng)前任務(wù)將報(bào)異常。

    @Test
    public void suspendOne() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RuntimeService runtimeService = processEngine.getRuntimeService();

        ProcessInstance processInstance = runtimeService.createProcessInstanceQuery().processInstanceId("12501").singleResult();
        boolean suspended = processInstance.isSuspended();
        String id = processInstance.getId();

        if (suspended) {
            runtimeService.activateProcessInstanceById(id);
            System.out.println("id = " + id + " 激活");
        } else {
            runtimeService.suspendProcessInstanceById(id);
            System.out.println("id = " + id + " 掛起");
        }
    }

4.11.3 流程實(shí)例推動(dòng)

????????在前面我們對(duì)一個(gè)整個(gè)的流程以及單個(gè)流程進(jìn)行了激活和掛起操作,之后可以編寫一段代碼來進(jìn)行推動(dòng)流程操作,主要是用來當(dāng)流程被掛起后流程還能否被繼續(xù)推動(dòng)。很顯然,當(dāng)掛起的流程去進(jìn)行流程推動(dòng)是不允許推動(dòng)流程的,必須是流程是激活狀態(tài)下才能夠被推動(dòng)。

具體的實(shí)例id和assignee值根據(jù)自己數(shù)據(jù)庫的值來進(jìn)行處理。

/**
     * 流程實(shí)例推動(dòng)
     */
    @Test
    public void complete() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();
        Task task = taskService.createTaskQuery().processInstanceId("15001").taskAssignee("cxb").singleResult();
        System.out.println("id = " + task.getId());
        System.out.println("name = " + task.getName());
        System.out.println("assignee = " + task.getAssignee());
        taskService.complete(task.getId());
    }

5、個(gè)人任務(wù)

5.1、分配任務(wù)責(zé)任人

5.1.1、固定負(fù)責(zé)人

????????在進(jìn)行業(yè)務(wù)流程建模時(shí)指定固定的任務(wù)負(fù)責(zé)人,直接在bpmn當(dāng)中指定assignee。

5.1.2、表達(dá)式分配

????????由于固定分配方式,任務(wù)只管一步一步執(zhí)行任務(wù),執(zhí)行到每一個(gè)任務(wù)將按照 bpmn 的配置去分配任務(wù)負(fù)責(zé)人。和前面一樣進(jìn)行指定,使用${變量名}的方式進(jìn)行指定。而指定之后的這些變量在流程啟動(dòng)的時(shí)候可以通過一個(gè)map對(duì)象來進(jìn)行賦值。

/**
     * 表達(dá)式分配
     */
    @Test
    public void startDistribution () {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RuntimeService runtimeService = processEngine.getRuntimeService();
        // 根據(jù)流程id啟動(dòng)流程
        Map<String, Object> map = new HashMap();
        map.put("assignee", "huangyueyue");
        map.put("director", "yueyueniao");
        map.put("manager", "zhangsan");
        ProcessInstance instance = runtimeService.startProcessInstanceByKey("myProcess_1", map);
    }

工作流,intellij-idea,java,ide

?5.1.3、監(jiān)聽器分配

????????任務(wù)監(jiān)聽器的Event的選項(xiàng)包含:

  • Create:任務(wù)創(chuàng)建后觸發(fā)
  • Assignment:任務(wù)分配后觸發(fā)
  • Delete:任務(wù)完成后觸發(fā)
  • All:所有事件發(fā)生都觸發(fā)

定義任務(wù)監(jiān)聽類,且類必須實(shí)現(xiàn) org.activiti.engine.delegate.TaskListener 接口

package com.cxb.springboot.listener;

import org.activiti.engine.delegate.DelegateTask;
import org.activiti.engine.delegate.TaskListener;

public class MyTaskListener implements TaskListener {
    @Override
    public void notify(DelegateTask delegateTask) {
        if (delegateTask.getName().equals("請(qǐng)假申請(qǐng)") &&
                delegateTask.getEventName().equals("create")) {
            // 這里指定任務(wù)負(fù)責(zé)人
            delegateTask.setAssignee("黃閱閱");
        }
    }
}

<userTask activiti:exclusive="true" id="_3" name="請(qǐng)假申請(qǐng)">
      <extensionElements>
        <activiti:taskListener class="com.cxb.springboot.listener.MyTaskListener" event="all"/>
      </extensionElements>
    </userTask>

工作流,intellij-idea,java,ide

?5.2、查詢?nèi)蝿?wù)

????????在前面就已經(jīng)可以通過流程key和負(fù)責(zé)人就可以查詢出這個(gè)人負(fù)責(zé)的流程單,而實(shí)際應(yīng)用時(shí),查詢待辦任務(wù)可能要顯示出業(yè)務(wù)系統(tǒng)的一些相關(guān)信息。這里可以通過 businessKey(業(yè)務(wù)標(biāo)識(shí) )關(guān)聯(lián)查詢業(yè)務(wù)系統(tǒng)的數(shù)據(jù)。

工作流,intellij-idea,java,ide

/**
     * 查詢?nèi)蝿?wù)
     */
    @Test
    public void findProcessInstance() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();
        RuntimeService runtimeService = processEngine.getRuntimeService();
        Task task = taskService.createTaskQuery()
                .processDefinitionKey("myProcess_1")
                .taskAssignee("cxb")
                .singleResult();
        String processInstanceId = task.getProcessInstanceId();
        ProcessInstance processInstance = runtimeService.createProcessInstanceQuery()
                .processInstanceId(processInstanceId)
                .singleResult();
        String businessKey = processInstance.getBusinessKey();
        System.out.println("businessKey==" + businessKey);
    }

?查詢業(yè)務(wù)標(biāo)識(shí)碼工作流,intellij-idea,java,ide

?5.3、任務(wù)推動(dòng)

????????在之前可以通過TaskService這個(gè)類的complate方法推動(dòng)任務(wù)的流動(dòng),而在這里我們還需要對(duì)當(dāng)前用戶是否擁有推動(dòng)該流程的權(quán)限,只需要先通過查詢當(dāng)前負(fù)責(zé)人的所有流程進(jìn)行判斷即可。有該流程即可推動(dòng),反之無法推動(dòng)流程。

@Test
    public void completeTask() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();
        Task task = taskService.createTaskQuery()
                .taskId("20005")
                .taskAssignee("cxb")
                .singleResult();
        if (task != null) {
            taskService.complete("20005");
            System.out.println("完成任務(wù)");
        }
    }

工作流,intellij-idea,java,ide

6、流程變量與組任務(wù)

6.1、流程變量概述

6.1.1、流程變量是什么

????????流程變量在 activiti 中是一個(gè)非常重要的角色,流程運(yùn)轉(zhuǎn)有時(shí)需要靠流程變量,業(yè)務(wù)系統(tǒng)和 activiti 結(jié)合時(shí)少不了流程變量,流程變量就是 activiti 在管理工作流時(shí)根據(jù)管理需要而設(shè)置的變量。

????????雖然流程變量中可以存儲(chǔ)業(yè)務(wù)數(shù)據(jù)可以通過activiti的api查詢流程變量從而實(shí)現(xiàn)查詢業(yè)務(wù)數(shù)據(jù),但是不建議這樣使用,因?yàn)闃I(yè)務(wù)數(shù)據(jù)查詢由業(yè)務(wù)系統(tǒng)負(fù)責(zé),activiti設(shè)置流程變量是為了流程執(zhí)行需要而創(chuàng)建。

6.1.2、流程變量作用域

????????流程變量的作用域可以是一個(gè)流程實(shí)例,或一個(gè)任務(wù),或一個(gè)執(zhí)行實(shí)例

1、global變量

????????流程變量的默認(rèn)作用域是流程實(shí)例。當(dāng)一個(gè)流程變量的作用域?yàn)榱鞒虒?shí)例時(shí),可以稱為 global 變量。
????????global 變量中變量名不允許重復(fù),設(shè)置相同名稱的變量,后設(shè)置的值會(huì)覆蓋前設(shè)置的變量值。
2、local變量

????????任務(wù)和執(zhí)行實(shí)例僅僅是針對(duì)一個(gè)任務(wù)和一個(gè)執(zhí)行實(shí)例范圍,范圍沒有流程實(shí)例大, 稱為 local 變量。
????????Local 變量由于在不同的任務(wù)或不同的執(zhí)行實(shí)例中,作用域互不影響,變量名可以相同沒有影響。
????????Local 變量名也可以和 global 變量名相同,沒有影響。

6.2、使用global變量控制流程

?????????還是和前面的整個(gè)流程一樣,現(xiàn)在對(duì)流程的分支進(jìn)行控制,通過流程變量來進(jìn)行控制,當(dāng)天數(shù)大于或等于三天還需要通過經(jīng)理審批,反之直接通過主管審批就結(jié)束了整個(gè)流程。工作流,intellij-idea,java,ide

?????????這里的話使用的UEL表達(dá)式使用的是uel-method來進(jìn)行賦值,所以在這里需要一個(gè)實(shí)體類來進(jìn)行值的給予,先定義一個(gè)類。該類當(dāng)中必須包含這個(gè)day變量,也就是在bpmn文件當(dāng)中指定的變量,以及該類必須實(shí)例化。并且加上getset方法。

public class Leave implements Serializable {
    private Double day;
}

6.2.1、啟動(dòng)流程時(shí)設(shè)置變量

????????在啟動(dòng)流程時(shí)設(shè)置流程變量,變量的作用域是整個(gè)流程實(shí)例。通過Map<key,value>設(shè)置流程變量,map中可以設(shè)置多個(gè)變量,這個(gè)key就是流程變量的名字。后續(xù)通過TaskService的compele方法來進(jìn)行推動(dòng)流程實(shí)例的代碼就不給出了,直接獲取taskid進(jìn)行推動(dòng),查看流程的走向。

 /**
     * 單個(gè)文件部署流程
     */
    @Test
    public void developGlobal() {
        // 創(chuàng)建流程對(duì)象
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        // 獲取service對(duì)象
        RepositoryService repositoryService = processEngine.getRepositoryService();
        // 流程部署 設(shè)置名字 將bpmn和png部署進(jìn)去
        Deployment deploy = repositoryService.createDeployment()
                .addClasspathResource("bpmn/hello-global.bpmn")
                .addClasspathResource("bpmn/hello-global.png")
                .name("請(qǐng)假流程全局設(shè)置變量")
                .deploy();
        System.out.println("id = " + deploy.getId());
        System.out.println("name = " + deploy.getName());
    }

    /**
     * 啟動(dòng)流程時(shí)設(shè)置變量
     */
    @Test
    public void startSetGlobal() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RuntimeService runtimeService = processEngine.getRuntimeService();
        Leave leave = new Leave();
        leave.setDay(4d);
        Map map = new HashMap();
        map.put("leave", leave);
        map.put("assignee", "yueyueniao");
        map.put("director", "張三");
        map.put("manager", "黃閱閱");
        ProcessInstance processInstance = runtimeService.startProcessInstanceByKey("myProcess_1", map);
        System.out.println(processInstance);
    }

6.2.2 任務(wù)辦理時(shí)設(shè)置變量

????????在完成任務(wù)時(shí)設(shè)置流程變量,該流程變量只有在該任務(wù)完成后其它結(jié)點(diǎn)才可使用該變量,它的作用域是整個(gè)流程實(shí)例,如果設(shè)置的流程變量的key在流程實(shí)例中已存在相同的名字則后設(shè)置的變量替換前邊設(shè)置的變量。這樣對(duì)前面6.2.1的代碼當(dāng)中往map對(duì)象當(dāng)中添加leave的代碼注掉。

/**
     * 任務(wù)辦理時(shí)設(shè)置變量
     */
    @Test
    public void completeSet() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();
        Leave leave = new Leave();
        leave.setDay(4d);
        Map map = new HashMap();
        map.put("leave", leave);
        Task task = taskService.createTaskQuery().processDefinitionKeyLike("myLeaveGlabal").taskAssignee("張三").singleResult();
        if (task != null) {
            taskService.complete(task.getId(), map);
        }
    }

?6.2.3 通過當(dāng)前流程實(shí)例設(shè)置

????????通過流程實(shí)例id設(shè)置全局變量,該流程實(shí)例必須未執(zhí)行完成。

    @Test
    public void setGlobalVariableByExecutionId() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RuntimeService runtimeService = processEngine.getRuntimeService();
        Leave leave = new Leave();
        leave.setDay(4d);
        runtimeService.setVariable("75001", "leave", leave);
    }

6.2.4 通過當(dāng)前任務(wù)設(shè)置

    @Test
    public void setGlobalVariableByTaskId() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();
        Leave leave = new Leave();
        leave.setDay(4d);
        taskService.setVariable("75001", "leave", leave);
    }

6.3 組任務(wù)辦理流程***

1)查詢組任務(wù)
指定候選人,查詢?cè)摵蜻x人當(dāng)前的待辦任務(wù)。候選人不能立即辦理任務(wù)。

2)拾取任務(wù)
該組任務(wù)的所有候選人都能拾取。將候選人的組任務(wù),變成個(gè)人任務(wù)。原來候選人就變成了該任務(wù)的負(fù)責(zé)人。如果拾取后不想辦理該任務(wù),需要將已經(jīng)拾取的個(gè)人任務(wù)歸還到組里邊,將個(gè)人任務(wù)變成了組任務(wù)。

3)查詢個(gè)人任務(wù)
查詢方式同個(gè)人任務(wù)部分,根據(jù)assignee查詢用戶負(fù)責(zé)的個(gè)人任務(wù)。

4)辦理個(gè)人任務(wù)
首先創(chuàng)建一個(gè)bpmn文件,在user當(dāng)中可以對(duì)candidateUsers進(jìn)行設(shè)置多個(gè)人員,之間用都好進(jìn)行隔開,而對(duì)應(yīng)的xml如下:

    <userTask activiti:candidateUsers="zhangsan,lisi" activiti:exclusive="true" id="_3" name="申請(qǐng)-group"/>
    <userTask activiti:candidateUsers="wangwu,zhaoliu" activiti:exclusive="true" id="_4" name="審核-group"/>

之后將該bpmn進(jìn)行部署,并且啟動(dòng)任務(wù)。

6.3.1 查詢組任務(wù)

????????根據(jù)候選人查詢組任務(wù),可以看到這個(gè)task在act_ru_task這張表當(dāng)中的assignee卻是一個(gè)null,也就是該用戶雖然可以查詢出該任務(wù),卻無法對(duì)該任務(wù)進(jìn)行處理。

    @Test
    public void findGroup() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();
        List<Task> list = taskService.createTaskQuery().processDefinitionKey("myLeaveGroup").taskCandidateUser("zhangsan").list();
        for (Task task : list) {
            System.out.println("instance id = " + task.getProcessInstanceId());
            System.out.println("id = " + task.getId());
            System.out.println("assignee = " + task.getAssignee());
            System.out.println("name = " + task.getName());
        }
    }

6.3.2 拾取任務(wù)

????????候選人員拾取組任務(wù)后該任務(wù)變?yōu)樽约旱膫€(gè)人任務(wù)。用戶拾取任務(wù)之后,對(duì)應(yīng)的act_ru_task表對(duì)應(yīng)的行數(shù)據(jù)的assignee就會(huì)變成相對(duì)應(yīng)的人員。

    @Test
    public void getTask() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();

        Task task = taskService.createTaskQuery().taskId("87505").taskCandidateUser("zhangsan").singleResult();
        if (task != null) {
            taskService.claim("87505", "zhangsan");
            System.out.println("用戶拾取");
        }
    }

6.3.3 歸還組任務(wù)

????????直接通過assignee進(jìn)行查詢,查詢到數(shù)據(jù)再將assignee置空也就表示歸還了任務(wù)。同理任務(wù)的交接就不用設(shè)置為空了,直接設(shè)置給另一個(gè)用戶即可。

    @Test
    public void returnTask() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();

        Task task = taskService.createTaskQuery().taskId("87505").taskAssignee("zhangsan").singleResult();
        if (task != null) {
            taskService.setAssignee("87505", null);
            System.out.println("用戶歸還");
        }
    }

7、網(wǎng)關(guān)

7.1 排他網(wǎng)關(guān)

????????排他網(wǎng)關(guān),用來在流程中實(shí)現(xiàn)決策。 當(dāng)流程執(zhí)行到這個(gè)網(wǎng)關(guān),所有分支都會(huì)判斷條件是否為true,如果為true則執(zhí)行該分支,注意:排他網(wǎng)關(guān)只會(huì)選擇一個(gè)為true的分支執(zhí)行。如果有兩個(gè)分支條件都為true,排他網(wǎng)關(guān)會(huì)選擇id值較小的一條分支去執(zhí)行。

工作流,intellij-idea,java,ide

?在這里對(duì)A流程后設(shè)置一個(gè)排他網(wǎng)關(guān)進(jìn)行流程分支,這兩條分支線也就對(duì)應(yīng)兩個(gè)uel表達(dá)式進(jìn)行判斷,而后就可以直接把這個(gè)流程進(jìn)行部署,部署之后在啟動(dòng)流程的時(shí)候就給這個(gè)day進(jìn)行設(shè)置值,直接進(jìn)行推動(dòng)流程,查看流程的流轉(zhuǎn)。

    @Test
    public void startSet() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        RuntimeService runtimeService = processEngine.getRuntimeService();
        Leave leave = new Leave();
        leave.setDay(-4d);
        Map map = new HashMap();
        map.put("leave", leave);
        ProcessInstance processInstance = runtimeService.startProcessInstanceByKey("gateway-pt", map);
    }

    @Test
    public void compete() {
        ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
        TaskService taskService = processEngine.getTaskService();
        Task task = taskService.createTaskQuery().processDefinitionKey("gateway-pt").taskAssignee("張三").singleResult();
        if (task != null) {
            taskService.complete(task.getId());
        }
    }

7.2 并行網(wǎng)關(guān)

????????并行網(wǎng)關(guān)允許將流程分成多條分支,也可以把多條分支匯聚到一起,并行網(wǎng)關(guān)的功能是基于進(jìn)入和外出順序流的:

????????fork分支:并行后的所有外出順序流,為每個(gè)順序流都創(chuàng)建一個(gè)并發(fā)分支。

????????join匯聚:所有到達(dá)并行網(wǎng)關(guān),在此等待的進(jìn)入分支, 直到所有進(jìn)入順序流的分支都到達(dá)以后, 流程就會(huì)通過匯聚網(wǎng)關(guān)。

工作流,intellij-idea,java,ide

????????并行網(wǎng)關(guān)的測(cè)試代碼和前面排他網(wǎng)關(guān)的代碼基本一致,在首先進(jìn)行部署之后啟動(dòng)流程,給流程設(shè)置一個(gè)天數(shù),而之后推動(dòng)任務(wù)之后,首先進(jìn)入到并行網(wǎng)關(guān),這里并不會(huì)進(jìn)行判斷,這里的意思是表示B和C都可以進(jìn)行對(duì)該任務(wù)流程進(jìn)行操作,并且只有到B和C都做了相關(guān)的操作流程才會(huì)繼續(xù)往后流轉(zhuǎn),后面接的排他網(wǎng)關(guān)直接通過最開始設(shè)置的值再進(jìn)行判斷做流程的流轉(zhuǎn)。


7.3 包含網(wǎng)關(guān)

????????包含網(wǎng)關(guān)可以看做是排他網(wǎng)關(guān)和并行網(wǎng)關(guān)的結(jié)合體。和排他網(wǎng)關(guān)一樣,可以在外出順序流上定義條件,包含網(wǎng)關(guān)會(huì)解析它們。 但是主要的區(qū)別是包含網(wǎng)關(guān)可以選擇多于一條順序流,這和并行網(wǎng)關(guān)一樣。

? ? ? ? 1、分支:所有外出順序流的條件都會(huì)被解析,結(jié)果為true的順序流會(huì)以并行方式繼續(xù)執(zhí)行, 會(huì)為每個(gè)順序流創(chuàng)建一個(gè)分支。
? ? ? ? 2、匯聚:所有并行分支到達(dá)包含網(wǎng)關(guān),會(huì)進(jìn)入等待狀態(tài), 直到每個(gè)包含流程token的進(jìn)入順序流的分支都到達(dá)。 這是與并行網(wǎng)關(guān)的最大不同。換句話說,包含網(wǎng)關(guān)只會(huì)等待被選中執(zhí)行了的進(jìn)入順序流。 在匯聚之后,流程會(huì)穿過包含網(wǎng)關(guān)繼續(xù)執(zhí)行。
????????和之前的網(wǎng)關(guān)一樣進(jìn)行部署推動(dòng)流程,可以發(fā)現(xiàn)在進(jìn)入到包含網(wǎng)關(guān)的時(shí)候,網(wǎng)關(guān)會(huì)對(duì)條件進(jìn)行判斷再進(jìn)行流轉(zhuǎn)。二里面的包含又相當(dāng)于并行網(wǎng)關(guān),當(dāng)并行的流程都執(zhí)行完成之后再由包含網(wǎng)關(guān)進(jìn)行匯聚。之后走排他網(wǎng)關(guān)進(jìn)行判斷流轉(zhuǎn)。

7.4 事件網(wǎng)關(guān)

????????事件網(wǎng)關(guān)允許根據(jù)事件判斷流向。網(wǎng)關(guān)的每個(gè)外出順序流都要連接到一個(gè)中間捕獲事件。 當(dāng)流程到達(dá)一個(gè)基于事件網(wǎng)關(guān),網(wǎng)關(guān)會(huì)進(jìn)入等待狀態(tài):會(huì)暫停執(zhí)行。與此同時(shí),會(huì)為每個(gè)外出順序流創(chuàng)建相對(duì)的事件訂閱。

????????事件網(wǎng)關(guān)的外出順序流和普通順序流不同,這些順序流不會(huì)真的"執(zhí)行", 相反它們讓流程引擎去決定執(zhí)行到事件網(wǎng)關(guān)的流程需要訂閱哪些事件。 要考慮以下條件:

? ? ? ? 1、事件網(wǎng)關(guān)必須有兩條或以上外出順序流;
? ? ? ? 2、事件網(wǎng)關(guān)后,只能使用intermediateCatchEvent類型(activiti不支持基于事件網(wǎng)關(guān)后連接ReceiveTask)
? ? ? ? 3、連接到事件網(wǎng)關(guān)的中間捕獲事件必須只有一個(gè)入口順序流。

參考文章來源地址http://www.zghlxwxcb.cn/news/detail-764180.html

到了這里,關(guān)于Activiti 工作流簡介的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點(diǎn)僅代表作者本人,不代表本站立場(chǎng)。本站僅提供信息存儲(chǔ)空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請(qǐng)注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實(shí)不符,請(qǐng)點(diǎn)擊違法舉報(bào)進(jìn)行投訴反饋,一經(jīng)查實(shí),立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費(fèi)用

相關(guān)文章

  • 【工作流Activiti7】3、Activiti7 回退與會(huì)簽

    【工作流Activiti7】3、Activiti7 回退與會(huì)簽

    1.? 回退(駁回) 回退的思路就是動(dòng)態(tài)更改節(jié)點(diǎn)的流向。先遇水搭橋,最后再過河拆橋。 具體操作如下: 取得當(dāng)前節(jié)點(diǎn)的信息 取得當(dāng)前節(jié)點(diǎn)的上一個(gè)節(jié)點(diǎn)的信息 保存當(dāng)前節(jié)點(diǎn)的流向 新建流向,由當(dāng)前節(jié)點(diǎn)指向上一個(gè)節(jié)點(diǎn) 將當(dāng)前節(jié)點(diǎn)的流向設(shè)置為上面新建的流向 當(dāng)前節(jié)點(diǎn)完

    2023年04月20日
    瀏覽(24)
  • Spring Boot + Activiti 結(jié)合,實(shí)現(xiàn)工作流

    Spring Boot + Activiti 結(jié)合,實(shí)現(xiàn)工作流

    Activiti是一個(gè)工作流引擎,Activiti可以將業(yè)務(wù)系統(tǒng)中復(fù)雜的業(yè)務(wù)流程抽取出來,使用專門的建模語言BPMN2.0進(jìn)行定義,業(yè)務(wù)流程按照預(yù)先定義的流程進(jìn)行執(zhí)行,實(shí)現(xiàn)了系統(tǒng)的流程由Activiti進(jìn)行管理,減少業(yè)務(wù)系統(tǒng)由于流程變更進(jìn)行系統(tǒng)升級(jí)改造的工作量,Activiti流程就是數(shù)據(jù)庫表

    2023年04月13日
    瀏覽(27)
  • Activiti7 工作流非原流程終止

    Activiti7 工作流非原流程終止

    正常工作流,需要經(jīng)過 node1、node2 才能結(jié)束。 現(xiàn)在要求已經(jīng)開啟的流程,目前停留在 node1,可以提前終止。 一般根據(jù)實(shí)際需要,可以有幾種做法: 新繪制流程圖,新增 node1 結(jié)束的流程分支,替換原流程 SQL 的方式,將該流程的數(shù)據(jù),手動(dòng)修改為終止的狀態(tài) 代碼動(dòng)態(tài)修改流程

    2023年04月16日
    瀏覽(43)
  • 若依框架SpringBoot+Activiti工作流的使用

    若依框架SpringBoot+Activiti工作流的使用

    使用簡介:本技術(shù)點(diǎn)主要是針對(duì)類審批的業(yè)務(wù)流程的建模,可以有:任務(wù)發(fā)布(即流程開始)到一級(jí)一級(jí)的審批到最終結(jié)束(即流程結(jié)束)一整套完備的模型 1、idea下載activiti插件 ider以前版本下載actiBPM,但是新版ider這個(gè)插件已經(jīng)被淘汰,已經(jīng)被下面這個(gè)替代 ? ? 2、單獨(dú)起

    2024年02月11日
    瀏覽(30)
  • 【業(yè)務(wù)功能篇36】Springboot+activiti7 工作流引擎

    【業(yè)務(wù)功能篇36】Springboot+activiti7 工作流引擎

    業(yè)務(wù)場(chǎng)景:前段時(shí)間總結(jié)的有一個(gè)告警工單流程,我們都是直接自己建表,狀態(tài)節(jié)點(diǎn),操作節(jié)點(diǎn),都是自定義設(shè)計(jì)的,而到后面會(huì)有很多的工單流程,比如創(chuàng)建一個(gè)遺留問題電子流,指定處理人進(jìn)行分析閉環(huán),等等多種電子流,后期重復(fù)的開發(fā)工作以及維護(hù)工作會(huì)越來越多。

    2024年02月12日
    瀏覽(20)
  • Activiti7工作流引擎:在線流程編輯器Activiti Modoler5.x

    Activiti7工作流引擎:在線流程編輯器Activiti Modoler5.x

    有的時(shí)候我們的流程圖需要業(yè)務(wù)人員自己繪制,然后使用自己繪制的流程圖,此時(shí)就需要一個(gè)在線流程圖編輯器需要集成到我們的web系統(tǒng)中。Activiti Modoler是Activiti官方推出的在線流程編輯器。 https://github.com/Activiti/Activiti/tree/5.x 將整個(gè)項(xiàng)目下載下來。不同版本的目錄結(jié)構(gòu)區(qū)別

    2024年02月09日
    瀏覽(19)
  • SpringBoot整合Activiti實(shí)現(xiàn)工作流的低代碼系統(tǒng)(附源碼+文檔)

    SpringBoot整合Activiti實(shí)現(xiàn)工作流的低代碼系統(tǒng)(附源碼+文檔)

    activiti工作流引擎項(xiàng)目,企業(yè)erp、oa、hr、crm等企事業(yè)辦公系統(tǒng)輕松落地,一套完整并且實(shí)際運(yùn)用在多套項(xiàng)目中的案例,滿足日常業(yè)務(wù)流程審批需求。 springboot+vue+activiti集成了activiti在線編輯器,流行的前后端分離部署開發(fā)模式,快速開發(fā)平臺(tái),可插拔工作流服務(wù)。工作流表單

    2024年04月09日
    瀏覽(20)
  • 后端面試話術(shù)集錦第 九 篇:Activiti工作流面試話術(shù)

    這是后端面試集錦第九篇博文—— Activiti 工作流面試話術(shù)??? 工作流這塊兒,實(shí)際在工作中使用的時(shí)候, Activiti 用的居多,當(dāng)然還有一些其他的工作流引擎。 在網(wǎng)上看了也大概看了一下,其他的像 JBPM 以及 workflow 等用的情況來講不是很多。 所以說 Activiti 目前來講用的比

    2024年02月10日
    瀏覽(22)
  • SpringBoot整合Activiti實(shí)現(xiàn)工作流的低代碼系統(tǒng)(附源碼和配套文檔)

    SpringBoot整合Activiti實(shí)現(xiàn)工作流的低代碼系統(tǒng)(附源碼和配套文檔)

    activiti工作流引擎項(xiàng)目,企業(yè)erp、oa、hr、crm等企事業(yè)辦公系統(tǒng)輕松落地,一套完整并且實(shí)際運(yùn)用在多套項(xiàng)目中的案例,滿足日常業(yè)務(wù)流程審批需求。 springboot+vue+activiti集成了activiti在線編輯器,流行的前后端分離部署開發(fā)模式,快速開發(fā)平臺(tái),可插拔工作流服務(wù)。工作流表單

    2024年03月15日
    瀏覽(21)
  • 【業(yè)務(wù)功能篇38】上篇:Springboot+activiti7 工作流引擎 增加網(wǎng)關(guān)組件、Assignment分配權(quán)限

    【業(yè)務(wù)功能篇38】上篇:Springboot+activiti7 工作流引擎 增加網(wǎng)關(guān)組件、Assignment分配權(quán)限

    在前面的一篇文章中,簡單舉例了一個(gè) 工單電子流,【業(yè)務(wù)功能篇36】Springboot+activiti7 工作流引擎_studyday1的博客-CSDN博客僅有一個(gè)子任務(wù),這種一般是針對(duì)比較簡單的一個(gè)遺留問題記錄場(chǎng)景,今天再介紹一個(gè),相對(duì)比較復(fù)雜的流程,多個(gè)處理,審批節(jié)點(diǎn)任務(wù),通過排他網(wǎng)關(guān)組

    2024年02月13日
    瀏覽(20)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請(qǐng)作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包