admin 管理员组

文章数量: 887021


2024年1月15日发(作者:网站特效生成器有哪些官网)

演示部署

下载snaker-web的war包

创建数据库

部署应用

访问应用

下载snaker-web的war包

在网盘下载snaker-web-..*.war文件

创建数据库

选择一款数据库软件,创建snaker的数据库

注意:只需要创建数据库,不需要手动执行脚本

部署应用

将snaker-web-*.*.*.war文件部署至Tomcat(版本>=6即可)的webapps目录下

访问应用

启动Tomcat,访问(*号是当前的版本号)

localhost:8080/snaker-web-*.*.*

测试账号为:

管理员[admin/123456]

测试账号[snaker/123456;test/123456]

如果此处出现问题,请检查数据源配置是否正确,具体配置文件为:

WEB-INF/classes/ties

快速入门

快速入门章节主要介绍流程是如何定义的,以及如何通过常用的api操作来启动、执行直至结束。

流程定义

如何使用Eclipse的设计器插件定义一个流程

如何使用snaker-web项目中的web设计器定义一个流程

流程发布

如何发布定义好的流程

流程启动

如何启动已发布的流程定义

任务执行

如何执行任务

流程定义

使用Eclipse设计器插件

使用web设计器

组件模型属性

使用Eclipse设计器插件

eclipse设计器插件是在eclipse4.3(kepler)版本开发的,经测试,是可以在eclipse4.3+,myeclipse9+上面运行

安装Eclipse插件

在百度网盘上下载snaker-designer-*.*.*.jar插件包,直接copy至eclipse安装目录下的plugins文件夹里即可使用。

考虑到大家下载的eclipse版本可能无法使用设计器,建议直接从百度网盘上下载经过测试的eclipse-kepler版本

Myeclipse安装插件时,可直接把插件包copy至dropins文件夹下面即可

创建流程定义

1)新建流程

依次选择File->New->Other->Snaker,如下图所示:

选择Snaker Process File并输入文件名称,如下图所示:

点击Finish,则打开流程设计器主界面,其中包括两大部分:流程组件、属性Properties视图,如下图所示:

2)定义节点

由于节点定义都是拖拽式的,所以不方便用图形来演示。这里仅仅贴上一个定义好的请假流程图:定义流程的几个注意点:

1)一个流程必须设置name、displayname属性

2)最常用的节点是task,如果是人工任务,则需要设置assignee[参与者]、form[设置表单url],表单url的规则可以表示contextPath下面的绝对路径,也可以表示相对路径[相对路径是用于页面include情况]

3)decision节点用于决策分支,必须设置expr属性,如果有多个选择分支,则建议设置连接线的expr属性,可参考测试用例

4)snaker支持的会签,仅仅是设置task的performType

5)snaker支持三种参与者方式

直接设置静态参与者,即assignee值为用户、部门或角色的标识符

通过运行时动态传递,即assignee值为变量名称,在调用流程引擎的api时,通过map参数传递这个变量值

通过自定义类[继承Assignment类],设置assignmentHandler属性,assign方法返回值就是参与者

6)主办、协办是通过task节点的taskType设置的。snaker既支持单独的节点作为协办节点,也支持主办节点动态的创建协办任务

3)保存定义

流程定义的保存,实际上就是将图形元素转换为xml格式并保存。上面请假流程的xml数据为

/snakerflow/snaker-web/blob/master/src/main/resources/flows/

使用web设计器

web设计器是基于myflow开发的,使用的技术为raphael。

集成web设计器

设计器代码位于snaker-web项目的snaker-websrcmainwebappstylesjssnaker目录下。

如果已有的项目需要集成web版本的设计器,主要是copy这个目录,并且参考snaker-websrcmainwebappWEB-INFcontentsnaker目录下process开头的jsp文件,因为设计器需要页面来编辑和展现。

创建流程定义 使用web设计器的前提是已经成功运行snaker-web应用,具体可参考“1.5演示部署”章节

1)新建流程

以admin账号登录snaker-web,点击左栏菜单:流程管理->流程定义,如下图所示:

![image](/)

点击“设计”按钮,则打开web流程设计器,如下图所示:

![image](/)

web版本的流程设计器布局与样式尽量与eclipse的设计器插件保持一致。其节点和属性参考“组件模型属性”介绍

在流程定义列表页面,点击“初始化”按钮,即可产生6个用于测试的业务流程,如下图所示:

![image](/)

注意:流程的状态表示当前流程是否可用,版本号用于管理同名流程的多版本管理

![image](/)

上图中的四个图标按顺序分别表示:启动流程、编辑、重新设计、禁用。点击重新设计,可打开已经定义好的业务流程,如下图所示:

![image](/)

2)定义节点

web设计器定义流程时注意以下两点:

1)web流程设计器还是适用于开发人员,不适合业务人员。如果面向业务人员,需要多设计器进行改造

2)设计器中连接线需要先点击连接线图标,再选择节点1、节点2,这样才能连接两个节点。连接线的删除是通过del键盘去操作的

3)保存定义 也是将图形元素转换为xml格式,并保存至数据库中,参见wf_process的content字段。

组件模型属性

组件模型 属性 描述

通用属性 name 组件名称,模型内名称唯一

displayName 组件中文显示名称,方便阅读

preInterceptors 前置拦截器

postInterceptors 后置拦截器

Process expireTime 期望完成时间,设置表达式变量由参数传递

instanceUrl 流程定义列表页面直接启动流程实例的URL

instanceNoClass 流程实例编号生成类

Transition expr 决策选择Decision节点的输出变迁表达式

Task form 用户参与的表单任务对应的URL

assignee 任务参与者变量

assignmentHandler 任务参与者处理类

taskType 任务类型(主办/协办)

performType 任务参与类型(针对多个参与者),ANY为其中一个参与者完成即往下流转;ALL为所有参与者完成才往下流转

reminderTime 任务提醒时间

reminderRepeat 提示重复次数

expireTime 期望完成时间

autoExecute 超时是否自动执行

callback 自动执行的回调设置

Custom clazz 自定义节点的Java类路径,两种方式:

1.实现IHandler接口,实现接口时不需要设置下面三个属性。

2.无接口实现的普通java类,需要设置下面方法名称、参数属性

methodName 定义需要执行的java类的方法名称

args 定义传递的参数表达式

流程部署

deploy

s().deploy(StreamHelper

.getStreamFromClasspath("flows/")

部署后的版本号默认为0,如果存在同名的流程定义,则新的流程定义版本号依次加1,并不会影响其它已经运行的流程实例。

redeploy

s().redeploy(processId, StreamHelper

.getStreamFromClasspath("flows/")

重新部署流程会影响已经运行的流程实例

undeploy

s().undeploy(processId)

卸载流程只会更新状态state值,不会删除数据

流程启动

可根据流程定义的id或者name启动流程实例。如果相同的流程名称存在不同的版本,并使用name启动实例时,会以最新的版本号来启动,其它低版本运行中的流程实例不会受到影响,这样就允许流程的多个版本同时运行。

根据id启动实例

nstanceById(processId);

nstanceById(processId, operator);

nstanceById(processId, operator, args);

startInstanceById方法的参数为:流程定义id、操作人operator、参数列表args

根据name启动实例

nstanceByName(name)

nstanceByName(name, version)

nstanceByName(name, version, operator)

nstanceByName(name, version, operator, args)

startInstanceByName方法的参数为:流程名称name、版本号version、操作人operator、参数列表args

任务执行

执行任务是工作流平台中最常见的操作,其处理逻辑包括两部分:

完成当前任务

按照流程定义驱动产生新的任务

执行任务的调用方法如下:

eTask(taskId);

eTask(taskId, operator);

eTask(taskId, operator, args);

executeTask参数分别表示:任务标识taskId、操作人operator、参数列表args

应用整合

为了方便整合,snaker提供了应用示例提供参考

snaker-springmvc

/yuqs/snaker-springmvc

基于SpringMVC、Spring3、Hibernate3、Snaker的快速整合示例,仅仅包括流程管理的功能,所有涉及到操作人员的部分全部使用admin,如果整合到具体项目时,一定要替换成系统当前登录的用户

snaker-struts2

/yuqs/snaker-struts2

基于Struts2、Spring3、Mybatis、Snaker的快速整合示例,仅仅包括流程管理的功能,所有涉及到操作人员的部分全部使用admin,如果整合到具体项目时,一定要替换成系统当前登录的用户

snaker-web

/yuqs/snaker-web

基于SpringMVC、Spring3、Hibernate3、Shiro、Snaker搭建的基础演示应用,包含:用户管理、部门管理、角色管理、权限管理、资源管理、菜单管理、流程管理、数据字典等常用功能模块

jfaker

/yuqs/jfaker

基于JFinal、Shiro、Snaker搭建的基础演示应用,包含:用户管理、部门管理、角色管理、权限管理、资源管理、菜单管理、流程管理、数据字典等常用功能模块

目前Snaker可独立运行,以API方式整合,同时也支持spring、jfinal、nutz三个平台,并且能够将事务托管给平台管理。其它情况下,需要自定义扩展。

API

API方式的事务由snaker自身管理,保证每次api调用事务的正确性。

snaker提供的测试用例目前就采用这种方式。

spring

与spring整合过程,需要配置服务、事务,以保证事务交给spring管理。可以参考snaker-web项目

jfinal

与Jfinal整合类似于API方式

nutz

与Nutz整合类似于API方式

API整合

如果使用api集成,需要在中配置DBAccess、Transaction、Dialect

import urce;

import Engine;

import lper;

import uration;

public class SnakerHelper {

private static final SnakerEngine engine;

static {

//使用项目中已有的DataSource、SessionFactory、SqlSessionFactory对象

//传递至initAccessDBObject方法中都可以

DataSource dataSource = aSource();

engine = new Configuration()

.initAccessDBObject(dataSource)

.buildSnakerEngine();

}

public static SnakerEngine getEngine() {

return engine;

}

}

initAccessDBObject方法传递的参数值与配置的数据库访问对应关系:

参数类型 访问对象 事务管理拦截器 依赖库

DataSource JdbcAccess DataSourceTransactionInterceptor

SessionFactory HibernateAccess Hibernate3TransactionInterceptor hibernate-*-

SqlSessionFactory MybatisAccess MybatisTransactionInterceptor

initAccessDBObject方法也可以不调用,而使用ties中的jdbc.或hibernate.来初始化DataSource、SessionFactory、SqlSessionFactory。但在实际的项目,还是建议使用该项目已有的DataSource、SessionFactory、SqlSessionFactory

Spring整合

增加maven依赖或jar

配置DBAccess

配置服务类

配置事务管理

增加maven依赖或jar

maven坐标如下:

flow

snaker-spring

*.*.*

如果非maven项目,需要到百度网盘下载jar包

配置DBAccess

访问类型

springjdbc

hibernate

hibernate

mybatis

类路径

JdbcAccess

ate3Access

ate4Access

sAccess

如配置Hibernate方式的DBAccess:

配置服务类

配置事务管理

需要将流程引擎的事务托管给spring统一管理

详细说明

本章主要详细介绍Snaker使用过程中各种常用的操作

表定义

表关系图

表详细说明

字段详细说明

表关系图

Snaker流程引擎核心共7张表,关系图如下所示

表详细说明:

表名称 描述

wf_process 流程定义表

wf_order 活动实例表

wf_task 活动任务表

wf_task_actor 活动任务参与者表

wf_hist_order 历史实例表

wf_hist_task 历史任务表

wf_hist_task_actor 历史任务参与者表

wf_surrogate 委托代理管理表

wf_cc_order 抄送实例表

字段详细说明:

wf_process:

字段名称 字段描述

id 主键ID

name 流程名称

display_Name 流程显示名称

type 流程类型

instance_Url 实例url

state 流程是否可用

content 流程模型定义

version 版本

create_Time 创建时间

creator 创建人

wf_order:

字段名称 字段描述

id 主键ID

parent_Id 父流程ID

process_Id 流程定义ID

creator 发起人

create_Time 发起时间

expire_Time 期望完成时间

last_Update_Time 上次更新时间

last_Updator 上次更新人

priority 优先级

parent_Node_Name 父流程依赖的节点名称

order_No 流程实例编号

variable 附属变量json存储

version 版本

wf_hist_order:

字段名称 字段描述

id 主键ID

parent_Id 父流程ID

process_Id 流程定义ID

creator 发起人

create_Time 发起时间

expire_Time 期望完成时间

end_Time 完成时间

priority 优先级

order_No 流程实例编号

variable 附属变量json存储

order_State 状态

wf_task:

字段名称 字段描述

id 主键ID

order_Id 流程实例ID

task_Name 任务名称

display_Name 任务显示名称

task_Type 任务类型

perform_Type 参与类型

operator 任务处理人

create_Time 任务创建时间

finish_Time 任务完成时间

expire_Time 任务期望完成时间

action_Url 任务处理的url

parent_Task_Id 父任务ID

variable 附属变量json存储

version 版本

wf_hist_task:

字段名称 字段描述

id 主键ID

order_Id 流程实例ID

task_Name 任务名称

display_Name 任务显示名称

task_Type 任务类型

perform_Type 参与类型

operator 任务处理人

create_Time 任务创建时间

finish_Time 任务完成时间

expire_Time 任务期望完成时间

action_Url 任务处理的url

parent_Task_Id 父任务ID

variable 附属变量json存储

task_State 任务状态

wf_task_actor:

字段名称 字段描述

task_Id 任务ID

actor_Id 参与者ID

wf_hist_task_actor:

字段名称 字段描述

task_Id 任务ID

actor_Id 参与者ID

wf_surrogate:

字段名称 字段描述

id 主键ID

process_Name 流程名称

operator 授权人

surrogate 代理人

odate 操作时间

sdate 开始时间

edate 结束时间

state 状态

wf_cc_order:

字段名称 字段描述

order_Id 流程实例ID

actor_Id 参与者ID

create_Time 抄送时间

finish_Time 完成时间

creator 发起人

status 状态

数据库支持

目前snaker默认支持

h2

db2

mysql

mssql

oracle

postgres

数据库,并支持自行扩展其它数据库。

snaker2.4版本之前,需要在中配置数据库发言

snaker2.4+版本,已经根据数据库连接自动获取发言,不需要手动配置。如果实现其它数据库,则需要实现Dialect方言接口,并配置发言。

t

由于流程引擎的数据库操作都是标准的sql语法,自定义发言是为了分页查询。

流程引擎API

流程引擎作为所有服务的入口,提供获取服务的方法,同时也提供最常用的api。

Engine

获取定义服务

获取实例服务

获取任务服务

获取查询服务

获取管理服务

启动流程

执行任务

驳回、任意跳转任务

创建自由任务

获取定义服务

s();

获取实例服务

();

获取任务服务

();

获取查询服务

();

获取管理服务

r();

启动流程

流程实例由引擎API的方法完成,方法的参数一般为流程定义的id或者是name、version。

根据流程定义id启动实例

nstanceById(String id);

nstanceById(String id, String operator);

nstanceById(String id, String operator, Map args);

根据流程定义name、version启动实例

nstanceByName(String name);

nstanceByName(String name, Integer version);

nstanceByName(String name, Integer version, String operator);

nstanceByName(String name, Integer version, String operator, Map args);

启动实例方法会返回一个Order对象,并且能够根据模型创建相应的任务Task

执行任务

执行任务由引擎API的方法完成,方法的参数一般为任务的id,操作人operator,变量数据args。

eTask(String taskId);

eTask(String taskId, String operator);

eTask(String taskId, String operator, Map args);

执行任务方法会返回一个Task集合,并且能够根据模型创建下一步任务Task

驳回、任意跳转任务

任务驳回有两种场景:驳回至上一步;驳回至任意节点。

eAndJumpTask(String taskId, String operator, Map args, String nodeName);

方法的参数nodeName决定驳回的方式:

nodeName为空时,则驳回至上一步,不需要传递参与者数据

nodeName不为空,则表示任意跳转,此时需要传递参与者数据。

创建自由任务

FreeTask(String orderId, String operator, Map args, TaskModel model);

创建自由任务时,需要新建任务模型对象TaskModel,再根据此模型创建对应的任务数据。

流程定义

流程定义服务作为工作流平台中最频繁调用的服务,并且流程定义是业务流程的静态逻辑数据,所以一般使用缓存,以减少数据库io访问次数。

snaker在设计流程定义服务时,通过实现缓存管理器包装接口来实现流程定义的缓存。默认使用内存缓存方式,同时也支持ehcache缓存框架。只需要依赖snaker-ehcache包即可。

ssService

anagerAware

发布

重新发布

卸载

更新类别

查询接口

快速入门章节的流程定义已经介绍如何通过设计器创建新的流程,本章节主要介绍对已经创建好的流程定义,如何操作。

流程发布统一使用InputStream输入流作为流程定义的数据。可借助

Helper

流帮助类完成,方法如下定义:

InputStream的方法名称

getStreamFromString

getStreamFromFile

getStreamFromClasspath

getStreamFromUrl

描述

根据字符串获取输入流

根据文件对象获取输入流

根据类路径下的资源文件名称获取输入流

根据url远程资源获取输入流

注意:snaker的流程定义编码格式统一使用UTF-8

发布

deploy(InputStream inputStream)

s().deploy(StreamHelper

.getStreamFromClasspath("flows/")

发布后的版本号默认为0,如果存在同名的流程定义,则新的流程定义版本号依次加1,并不会影响其它已经运行的流程实例。

重新发布

redeploy(String processId, InputStream inputStream)

s().redeploy(processId, StreamHelper

.getStreamFromClasspath("flows/")

重新发布流程会影响已经运行的流程实例

卸载

undeploy(String processId)

s().undeploy(processId)

卸载流程只会更新状态state值,不会删除物理数据

更新类别

updateType(String processId, String type)

s().updateType(processId, type)

更新类别主要用于业务流程较多,并且存在分类情况时使用

查询接口

Process getProcessById(String id)

Process getProcessByName(String name)

Process getProcessByVersion(String name, Integer version)

public List getProcesss(QueryFilter filter)

public List getProcesss(Page page, QueryFilter filter)

模型操作

通过流程定义章节的查询接口可以轻松获取到Process实体对象,该实体中的model属性就是流程图的对象表达形式了,可通过getModel方法获取ProcessModel。

el()

流程模型

流程模型

Start节点

name获取节点

类型获取所有节点

所有任务节点

后续一级节点集合

sModel

流程模型、流程定义的XML文件、流程图三种表现形式可互相转换,流程模型对象不仅包含了自身的属性(如:name displayName instanceUrl expireTime instanceNoClass ),同时也包含了所有节点模型对象以及它们的关系。

Start节点

odel

Start节点作为流程启动的入口,只有输出路由,其输入路由为空,可通过getInputs方法进行验证

name获取节点

NodeModel getNode(String nodeName)

根据节点的name属性获取到节点模型对象

类型获取所有节点

List getModels(Class clazz)

根据节点类型获取所有该类型的模型对象集合。常用于如下方式:

List taskModels = els()

所有任务节点

List getTaskModels()

该方法获取有序的所有任务模型集合

后续一级节点集合

List getNextModels(Class clazz)

获取某个节点的后续一级节点集合,getNextModels是NodeModel的方法

流程实例

流程实例服务主要配合引擎完成实例的开始、结束状态。

Service

完成实例

完成实例

强制终止

唤醒实例

流程实例的完成,是通过complete方法处理的。

void complete(String orderId)

一般情况下,该方法不需要显示调用,流程引擎在执行最后一个任务,流向End节点时,会自动触发完成实例的动作。

如果你手动调用complete方法,会造成实例数据与任务数据不一致的情况,仅仅是结束了实例,但是该实例下的所有活动任务依然存在。

强制终止

如果需要把一个活动的流程实例结束掉,并且同时结束该实例下的所有活动任务,那么可以调用terminate方法进行处理。

void terminate(String orderId)

void terminate(String orderId, String operator)

如果不传递operator,那么会存在权限不够,活动任务无法结束的情况。此时建议您传递超级权限去终止。

唤醒实例

如果一个已经结束的实例,希望重新激活至最后一步,该如何操作呢。那么调用resume方法即可实现此功能。

Order resume(String orderId)

唤醒实例后,会重新产生一个活动实例的数据记录Order,同时会唤醒最后一个历史任务为活动任务记录。

活动任务

任务服务主要配合流程引擎在调度过程中任务数据的操作。

ervice

转派

撤回

提取

驳回跳转

唤醒

更新

转派

任务转派是向指定人创建新的任务。转派api支持主办、协办两种任务类型

createNewTask(String taskId, int taskType, actors)

taskType:0 主办任务类型

taskType:1 协办任务类型

撤回

根据历史任务id,撤回由该历史任务派发的所有活动任务,如果无活动任务,则不允许撤回,抛出unchecked异常:SnakerException

withdrawTask(String taskId, String operator)

提取

任务提取一般发生在参与者为部门、角色等组的情况下,该组的某位成员提取任务后,不允许其它成员处理该任务。

take(String taskId, String operator)

驳回、跳转

任务驳回、跳转请参考流程引擎API章节

唤醒

如果一个已经结束的任务,希望重新激活为活动状态,该如何操作呢。那么调用resume方法即可实现此功能。

Task resume(String taskId, String operator)

更新

如果一个活动任务,需要更新部分字段,则可以使用更新方法完成。

updateTask(Task task)

可更新任务对象的finish_Time、operator、expire_Time、variable

流程变量

数据存储

设计方法

Snaker的流程变量

变量数据获取

流程引擎在设计的过程中,需要考虑数据的分类存储

数据存储

业务数据

一般保存在业务表中

流程数据

一般保存在流程引擎的表中,如`wf_process` `wf_order` `wf_task`等

关联数据

流程变量保存的就是关联数据

设计方法

变量表

目前主流的流程引擎如Jbpm、Activiti都常用变量表方式,其优点是支持丰富的变量类型,变量值无长度限制,支持查询。缺点是很多使用者过于依赖变量表,将大部分业务数据保存在变量表中,数据过多时性能急剧下降。

变量字段

变量字段方式适用于中小型流程平台,只支持少量字段的存储,强制用户适用业务表保存业务数据,流程变量仅保存少量的关联数据。变量数据随实例、任务记录一次查询即可获得。但是缺点也很明显,不支持关联数据的查询,如果需要查询,只能将关联数据在业务表重复保存一份。

snaker的流程变量

snaker使用变量字段保存关联数据的方式,并支持在运行时动态添加全局变量数据

全局变量

全局变量的作用域是流程实例从启动至结束的所有过程

局部变量

局部变量的作用域是任务执行的单个过程

动态添加全局变量数据,可通过addVariable方法完成。

().addVariable(String orderId, Map args)

变量数据获取

变量数据取可通过实例对象Order HistoryOrder、任务对象Task HistoryTask的getVariableMap()方法获取

任务参与者

snaker的任务支持静态配置、动态传递、自定义类处理、动态设置、组等方式。

参与者设置

动态添加、删除参与者

组支持

参与者设置

直接设置静态参与者,即assignee值为用户、部门或角色的标识符

通过运行时动态传递,即assignee值为变量名称,在调用流程引擎的api时,通过map参数传递这个变量值

通过自定义类[继承Assignment类],设置assignmentHandler属性,assign方法返回值就是参与者

动态添加、删除参与者

向指定任务动态添加参与者,同时支持设置参与类型

performType为0,则仅仅向wf_task_actor表中增加一条参与者信息 performType为1,则会在wf_task表中增加一条任务数据。

().addTaskActor(String taskId, actors)

().addTaskActor(String taskId, Integer performType, actors)

对指定任务动态删除其中的参与者

().removeTaskActor(String taskId, actors)

组支持

由于snaker引擎与用户权限完全解耦的,所以对于组的支持,仅仅是你设置组作为参与者,你就要自定义一个任务的访问策略,能够根据操作人得到所有的组集合,这样流程引擎才能允许该操作人处理任务。

自定义任务访问策略类

public class CustomAccessStrategy extends GeneralAccessStrategy {

protected List ensureGroup(String operator) {

//此处根据实际项目获取操作人对应的组列表

return ups();

}

}

配置

在中增加下面的配置

节点拦截器

snaker的拦截器支持所有的节点前后拦截,并且支持全局、局部拦截器。拦截器统一实现SnakerInterceptor接口

Interceptor

全局拦截器

局部拦截器

全局拦截器

全局拦截器会拦截所有新产生的任务对象。自定义的全局拦截器需要配置到中。如默认支持的日志拦截器

局部拦截器

局部拦截器支持节点执行的前置、后置拦截。需要配置到task节点模型的preInterceptors[前置拦截]、postInterceptors[后置拦截]属性

委托代理

委托代理主要用于流程平台中,主办人由于出差、休假等原因无法处理任务时,通过委托其它人员去处理此人的某类业务流程的待办任务。

表结构

表结构

委托代理配置

管理委托代理

委托代理表主要保存委托代理的记录信息

wf_surrogate

委托代理配置

需要在中配置委托代理的拦截器

管理委托代理

委托代理的数据管理由管理服务类完成

erService

管理服务接口针对委托代理提供以下方法:

void saveOrUpdate(Surrogate surrogate)

void deleteSurrogate(String id)

Surrogate getSurrogate(String id)

List getSurrogate(QueryFilter filter)

String getSurrogate(String operator, String processName)

List getSurrogate(Page page, QueryFilter filter)

决策表达式

决策表达式主要用于decision(选择分支)节点,该节点支持三种路由选择方式

decision的expr

transition的expr

自定义类

decision的expr

decision节点的expr有两种方式来设置

1.表达式中增加判断逻辑,如:${day > 3 ? 't1' : 't2'},此时根据day的值决定走t1、或t2的路由,用于设置范围值的情况

2.表达式仅仅是一个变量,如:${tname},此时,传递tname的值为路由name即可,用于设置具体值的情况(如:同意、不同意)

transition的expr

如果decision节点的expr为空,可设置输出路由的expr,必须返回boolean类型

路由1设置expr的值为:${content==1},

路由2设置expr的值为${content > 1}。

自定义类

自定义类需要实现DecisionHandler接口的decide方法

onHandler

该方法返回字符串即表示输出路由的name

Snaker默认支持Juel、SringEL两种表达式引擎,需要在中配置。配置如下:

并且支持自定义表达式,实现Expression接口,同样修改一下配合即可。

Juel表达式引擎常用语法

String expr1 = "${content}";

Map args1 = new HashMap();

("content", 1);

n(eval(, expr1, args1));

String expr2 = "${content == 1 ? 'v1' : 'v2'}";

Map args2 = new HashMap();

//此处不仅支持数字类型,也支持字符串类型,但是值必须可转换为数字

("content", "2");

n(eval(, expr2, args2));

String expr3 = "${content > 1 ? 'v1' : 'v2'}";

Map args3 = new HashMap();

//此处只要是数字类型即可,如1或0.5等

("content", 4.2);

n(eval(, expr3, args3));

//juel支持表达式为字符串类型而参数为数字类型

String expr4 = "${content == '1' ? 'v1' : 'v2'}";

Map args4 = new HashMap();

//此处不仅可以写字符串"1",也可以写char类型'1',写数字类型1,浮点类型1.00

("content", 1);

n(eval(, expr4, args4));

//逻辑表达式与,使用&&表示

String expr5 = "${content > 1 && content <= 10 ? 'v1' : 'v2'}";

Map args5 = new HashMap();

//此处不仅可以写字符串"1",也可以写char类型'1',写数字类型1,浮点类型1.00

("content", "11");

n(eval(, expr5, args5));

//逻辑表达式或,使用||表示

String expr6 = "${content < 1 || content > 10 ? 'v1' : 'v2'}";

Map args6 = new HashMap();

//此处不仅可以写字符串"1",也可以写char类型'1',写数字类型1,浮点类型1.00

("content", "1");

n(eval(, expr6, args6));

//逻辑表达式

String expr7 = "${content < 1 || content > 10 ? 'v1' : (content == 8 ? 'v2' : 'v3')}";

Map args7 = new HashMap();

//此处不仅可以写字符串"1",也可以写char类型'1',写数字类型1,浮点类型1.00

("content", "8");

n(eval(, expr7, args7));

Spring EL表达式引擎常用语法

String expr1 = "#content";

Map args1 = new HashMap();

("content", "v2");

n(expr1 + "====>" + eval(, expr1, args1));

String expr2 = "#content == 1 ? 'v1' : 'v2'";

Map args2 = new HashMap();

//此处仅支持数字类型

("content", 2.1);

n(expr2 + "====>" + eval(, expr2, args2));

String expr3 = "#content > 1 ? 'v1' : 'v2'";

Map args3 = new HashMap();

//此处只要是数字类型即可,如1或0.5等

("content", 4.2);

n(expr3 + "====>" + eval(, expr3, args3));

//spel支持表达式为字符串类型而参数为数字类型

String expr4 = "#content == '1' ? 'v1' : 'v2'";

Map args4 = new HashMap();

//此处仅支持字符串"1"

("content", "1");

n(expr4 + "====>" + eval(, expr4, args4));

//逻辑表达式与,使用and表示

String expr5 = "#content > 1 and #content <= 10 ? 'v1' : 'v2'";

Map args5 = new HashMap();

//此处仅支持数字类型

("content", 11);

n(expr5 + "====>" + eval(, expr5, args5));

//逻辑表达式或,使用||表示

String expr6 = "#content < 1 or #content > 10 ? 'v1' : 'v2'";

Map args6 = new HashMap();

//此处不仅可以写字符串"1",也可以写char类型'1',写数字类型1,浮点类型1.00

("content", 1);

n(expr6 + "====>" + eval(, expr6, args6));

//逻辑表达式

String expr7 = "(#content < 1 or #content > 10) ? 'v1' : (#content == 8 ? 'v2' : 'v3')";

Map args7 = new HashMap();

//此处不仅可以写字符串"1",也可以写char类型'1',写数字类型1,浮点类型1.00

("content", 8);

n(expr7 + "====>" + eval(, expr7, args7));

子流程

子流程的作用是将一个复杂的业务流程进行细化拆分,提高流程的复用性。

子流程模型

父子流程的关联

子流程模型

子流程模型类型为SubProcessModel,其主要属性为processName,根据流程的name进行关联,由于流程定义支持一个name多个版本同时运行,那么子流程关联只设置name,即表示与最新版本的子流程关联。

父子流程的关联

对于表结构的设计中,父子流程的关联字段为

wf_order[parent_Id、parent_Node_Name]

wf_hist_order[parent_Id]

时限控制

时限控制常用于流程平台中的超时处理(提醒、自动执行等)、以及任务监控的查询统计等功能。

依赖包

依赖包

配置

实现提醒接口

snaker默认支持quartz定时器调度框架,只需要依赖snaker-quartz的包即可。

配置

在中配置时限控制的拦截器、定时调度的实现类

如果使用其它定时调度框架,需要实现IScheduler接口,并替换QuartzScheduler类配置

以上两步已经完成了时限的配置工作,下面就可以针对提醒、超时自动执行做自定义扩展了。

超时提醒

编写自定义的提醒类,实现IReminder接口。并配置到中即可。

任务节点配置超时提醒属性:reminderTime、reminderRepeat。

reminderTime是一个变量,表示提醒开始时间,当你调用api时需要传递此变量值,值的类型为date。

reminderRepeat是一个数字,表示重复提醒间隔时间,以分钟为单位

默认提醒一次就结束,如果希望提醒多次,可通过ties中配置属性,该值是个数字,表示提醒次数。

节假日配置

#是否启用节假日,默认为false

endar=true/false

#节日配置,格式为yyyy-MM-dd,...

ys=2014-12-26,2014-12-27

#工作日设置,格式为1,7,表示周一至周日

=1,2,3,4,5

#工作时间设置,格式为8:00-18:00

me=8:00-18:00

超时自动完成

任务节点配置超时处理属性:expireTime、autoExecute、callback

expireTime是一个变量,表示期望完成时间,当你调用api时需要传递此变量值,值的类型为date。

autoExecute的值为Y/N,表示超时是否自动执行

callback是一个字符串,表示自动执行的回调类路径配置

编写回调类

通过实现JobCallback接口

lback

实例抄送

实例的抄送类似于邮箱里面的抄送功能,一般用于将该流程实例抄送给领导查阅。

表结构

表结构

创建抄送

更新状态

抄送记录表主要保存抄送的记录信息

wf_cc_order

创建抄送

根据实例id、创建人、抄送人创建抄送记录

().createCCOrder(String orderId, String creator, actorIds)

更新状态

更新状态用于更新抄送记录为已经阅读

().updateCCStatus(String orderId, actorIds)

会签任务

snaker的会签目前相对比较简单,仅仅是根据任务节点的performType属性值确定是否产生多个相同任务。

performType的值有两种,分别是ANY、ALL。

ANY 多个参与者时,任何一个完成任务即继续流转

ALL 多个参与者时,所有都需要完成任务才能继续流转

会签任务节点

动态加签

会签百分比

串行会签

会签任务节点

只需要在流程定义时,将任务节点的属性performType值设置为ALL即可,当调用api时传递多个参与者时,则自动派发与参与者数量相同的任务。会签任务必须等待所有参与者完成后,才继续流转

动态加签

可调用任务服务的addTaskActor方法实现动态加签。

().addTaskActor(String taskId, 1, actorIds)

会签百分比

暂未实现

串行会签

暂未实现

Fork/Join

snaker流程引擎中的所有节点模型都支持fork/join的并行流转。

建议fork/join配对使用,否则会造成流程数据不一致。

测试用例中的forkjoin流程图如下所示:

自定义节点

snaker的自定义节点可完成流程的全自动编排。只需要在自定义节点模型中配置处理类即可。

自定义节点的处理类有两种方式:

实现IHandler接口

只需要配置clazz属性即可

普通java类

需要设置clazz methodName args var

自定义节点的执行不需要外部触发,只要抵达节点立即执行绑定的类进行处理。并记录历史任务,处理类返回值保存在历史任务的变量字段中

级联删除

级联删除主要用于流程定义、流程实例的数据。一般情况下,不建议在正式环境里使用此功能,顾名思义,会删除所有的关联数据,谨慎使用。

流程定义

s().cascadeRemove(String processId)


本文标签: 流程 任务 需要 定义 节点