activiti5,jbpm等jbpm4工作流开发实例在什么开发场景下需要用到

随笔 - 1078&
文章 - 0&评论 - 0&trackbacks - 0
& & 从本篇文章我们开始介绍工作流框架activiti的相关知识,不过在介绍activiti的知识之前,我们很有必要对工作流的一些基本概念进行了解。
工作流重要概念
& & Workflow(工作流)是&业务过程的部分或整体在计算机应用环境下的自动化,是对工作流程及其各操作步骤之间业务规则的抽象、概括描述&,它主要解决的是&使在多个参与者之间按照一种提前定义好的规则流程来传递与执行文档、信息或任务的过程,让这个过程可以自动进行或者部分自动执行,从而完成预期的业务目标&。
& & 提到工作流就不能不提到工作流管理联盟(WfMC,WorkflowManagementCoalition),它是一个由涉及工作流和业务流程管理的推广学者(adopters)、开发工程师、顾问、分析师、大学和研究团体的全球性组织,它的成立,标志着工作流技术开始进入相对成熟的阶段。该组织创建并完善了工作流管理系统的相关术语、体系结构及应用编程接口等方面制定了一系列标准,是唯一的致力于工作流标准的专业组织。
& & 接下来要说的是工作流管理系统(WorkflowManagement System,WfMS),它完成了工作量的定义和管理,并按照在系统中预先定义好的工作流规则进行工作流实例的执行的软件系统,这里要说明一下的是,并不是我们企业自己的系统应用了工作流就是工作流管理系统了,工作流管理系统不是企业的业务系统,而是为企业的业务系统的运行提供了一个软件的支撑环境。WfMS被用来定义、管理和执行工作流程,它的目标是管理工作的流程以确保工作在正确的时间被期望的人员所执行。同时也可以在自动化进行的业务过程中插入人工的执行和干预。
WfMS与工作流框架
& & WfMS我一般习惯于称它为工作流框架,常见的工作流框Activiti、JBPM、OSWorkflow、ActiveBPEL、YAWL等。
工作流引擎
& & 个人觉得直接理解工作流引擎概念有点难度,我们可以先通过了解工作流引擎的职责再反过来理解工作流引擎,工作流引擎一般都做两件事情:
& & 1.定义流程,也就是给我们提供某种规范来定义规则,以及如何定义一个流程的这种规范,同事我们可以根据工作流引擎提供的相关概念来定义更为复杂的流程,这就是工作流引擎做的第一件事叫做定义流程。
& & 2.执行流程,也就是工作流引擎需要解释这个规则,还要负责流程,它相当于流程的调度者,监控每个流程的执行情况,并将流程操作发往下一步,或者根据条件休眠或终止流程的这么一个过程就叫做执行流程。
& & 了解完工作流引擎的这两个职责,我相信对于什么是工作流引擎一定已经有了一定的认识了,我们在用一句稍微有点官方的话来总结一下工作流引擎,工作流引擎为我们提供相关规则概念的定义,给我们提供了相关的API来调用这个引擎去执行流程。流程的操作实际上就是工作流引擎提供相关的api我们去调用它。
工作流框架与工作流引擎
& & 上面我们提及了常见了几个工作流框架,其中现在的Activiti和JBPM5.0之前的版本都是基于ProcessEngine 工作流引擎的工作流框架;JBPM5.0开始是基于DroolsFlow为工作流引擎的工作流框架;其中OSWorkflow是以工作流引擎命名的工作流框架,所以OSWorkflow是基于OSWorkflow工作流引擎的工作流框架;ActiveBPEL是基于工作流BPEL引擎的工作流框架&&.
& & 到这里关于工作流的相关概念就介绍完了,接下来我们先了解一下我们的主角activiti的前世今生。
Activiti前世今生
& & Activiti 的创始人是& Tom Baeyens&说到Tom Baeyens&就不能不提他与jbpm的渊源。TomBaeyens 是 jBPM 的创始人,在 2002年,Tom Baeyens创建了基于状态机原理的jBPM流程引擎。jBPM经过了JBoss和Redhat公司之后,发展到了 jBPM 4。由于jBPM使用的是 GPL开源协议,并且与JBoss和Redhat公司的其他产品线结合的越来越紧密,对jBPM在更广泛的范围使用形成了阻碍。JBoss内部对jBPM未来版本的实现产生了严重的意见分歧,在2005年 Tom Baeyens离开了JBoss公司加入了Alfresco 公司,创建了使用Apache based-license V2的、独立于Alfresco产品的开源流程产品Activiti 。Activiti在2010年3月份开始启动,到了2010年12月份正式发布第一个版本,新的基于jBPM4的开源工作流系统Activiti 5.0& !所以说Activiti5是在jBPM 3、jBPM&4的基础上发展而来的,是原jBPM 的延续。
Activiti&与jBPM&5的比较
& & jBPM 5则与之前的jBPM3、jBPM 4没有太大关联,且舍弃了备受推崇的PVM(流程虚拟机)思想,转而选择jBoss自身产品DroolsFlow作为流程引擎的核心实现,工作流最为重要的&人机交互&任务(类似于审批活动)则由单独的一块&Human Task Service&附加到DroolsFlow上实现,任务的查询、处理等行为通过Apache Mina异步通信机制完成。
Hibernate3
持久化标准
MyBatis机制/事务控制
Bitronix,基于JTA事务管理
数据库连接方式
Jdbc/DataSource
Jdbc/DataSource
支持数据库
Oracle、SQL Server、等多数数据库
Oracle、SQL Server、MySQL等多数数据库
Command模式、观察者模式等
内部服务通讯
Service间通过API调用
基于Apache Mina异步通讯
SOAP、Mule、RESTful
支持的流程格式
BPMN2、xPDL、jPDL等
目前仅只支持BPMN2 xml
PVM(流程虚拟机)
jBPM3、jBPM4
Drools Flow
& & 从表格中的比较我们可以看出,Activiti最大的优势是采用了PVM(流程虚拟机),支持除了BPMN2.0规范之外的流程格式,与外部服务有良好的集成能力,延续了jBPM3、jBPM4良好的社区支持,服务接口清晰,链式API更为优雅;劣势是持久化层没有遵循JPA规范。
& & jBPM最大的优势是采用了ApacheMina异步通信技术,采用JPA/JTA持久化方面的标准,以功能齐全的Guvnor作为流程仓库,有RedHat(jBoss.org被红帽收购)的专业化支持;但其劣势也很明显,对自身技术依赖过紧且目前仅支持BPMN2。
& & 我们对Activiti和jBPM进行比较目的是为了让我们可以对他们的特性更加的了解,只有了解了他们的特性以后,这样当我们遇到具体的项目时就可以根据需要来选用适合的工作流框架。
& & 我们这篇文章主要介绍了工作流相关的基本概念,同时又了解了Activiti的前世今生,最后将Activiti与jBPM进行了比较。
阅读(...) 评论()2445人阅读
工具(15)
activiti5 工作流的入门,最近工作需要,学习了一下工作流,使用的是activiti 它的前身是jBPM。
在入门阶段,我推荐可以看/activiti-basic.html
这里面的7个视频从安装插件到部署一个最简单的工作流都讲解了。视频长度也不长,学习周期很短,而且对入门的帮组很大。
如果对上面的视频已经掌握了,那就按网络上面比较火的咖啡兔的demo,他在git提供了maven和no-maven的demo代码,可以下载下来跑跑看。
接着可以结合activiti的文档pdf和咖啡兔的demo来查看工作流的一些功能,比如流程图导出,任务完成,流程实例启动等。
总结一下activiti的几个重点:
1.Activiti Modeler
Activiti Modeler是一个BPMN web建模组件,它是Activiti
Explorer web应用的一部分。我们也可以自己把这个部分集成到自己的系统中,至于如何集成咖啡兔的文章有专门讲述:http://www.kafeitu.me/activiti//integrate-activiti-modeler.html
2.Activiti
REST 就是Activiti 结合RestLet提供url来给用户去操作工作流的方法,以json方式传递数据,可以参考文档。说白了就是直接提供给url来调用activiti的api。
在activiti开发过程中api的几个最主要的服务类:
RepositoryService它提供了管理和控制发布 包和流程定义的操作。
RuntimeService它负责启动一个流程定义的新实例,也可以用来获取和保存流程变量,也能查询流程实例和执行
TaskService查询分配给用户或组的任务
IdentityService它可以管理(创建,更新,删除,查询...)群组和用户
FormService这个服务提供了启动表单和任务表单两个概念。 启动表单会在流程实例启动之前展示给 用户, 任务表单会在用户完成任务时展示
HistoryService提供了Activiti引擎手机的所有历史数据
4.bpmn2.0标准
bpmn我们说画的流程图都是基于它的标准,所以要如何画流程图,有哪些标签都可以查看bpmn来实现。
BPMN 2.0根节点是definitions节点。一个空的流程定义:
&definitions&
xmlns:activiti=&&&
targetNamespace=&Examples&&&
&process id=&myProcess& name=&My First Process&&&
&/process&&
&/definitions&
在下面的文章,我会把在工作过程中遇到的一些问题或者代码贴出来。
&&相关文章推荐
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
访问:46743次
排名:千里之外
原创:26篇
(7)(1)(1)(2)(2)(11)(6)(5)Jbpm4或Activiti5的流程任务分发与汇总 - man1900 - ITeye博客
博客分类:
应用场景:在企业或事业单位,经常需要把一个任务分派给多条线去处理,每条线可以由一个或多个步骤构成,多条线的任务完成后需要再汇总一起于某个任务上。如下例子为一个公文下发流程,这个流程就涉及到任务的两级分发。
图一 原流程定义图
图二 执行过程中流程图
以上黄色的代表任务分发,紫黄代表任务汇总。 解决方法一: 我们可以把多个任务线用子流程去实现也可以,这样在分发那里会产生多个子流程,子流程完成后,需要汇总。但若有多级分发与汇总,则需要子流程再嵌套子流程。 解决方法二:
把分发的任务线当作普通的任务来实现,该产生多少个任务可由分发任务决定,这些任务的名称是一样的,但任务实例id不一样,执行人不一样。 在jbpm4或Activiti5上,动态创建子流程及对子流程的处理上,相对要完成的工作多一些,主要是activity或jbpm4上没有提供这块api。而动态创建任务在jbpm4或activiti5上也是没有提供的,只有activiti5上提供了一个taskService.newTask,而该方法产生的新任务则跟流程定义无关,则表示该任务完成后,不能产生后续的任务。在此,我们先提供activiti5的解决办法。Jbpm4的解决方法可以参照该方式实现,以下为解决方案的步骤: 1.
第二种解决方案的关键点在于如何动态创建任务,在这里,我们绕过activiti的API直接对activiti5表进行生成处理,让他生成我们需要流程数据。 如下所示:
* 按任务Id,复制另一会签任务出来
* @param orgTaskId
* @param assignee
public ProcessTask newTask(String orgTaskId,String assignee)
String newExecutionId=UniqueIdUtil.getNextId();
String newTaskId=UniqueIdUtil.getNextId();
TaskEntity taskEntity=getTask(orgTaskId);
ExecutionEntity executionEntity=
if(taskEntity.getExecution()!=null){
executionEntity=taskEntity.getExecution();
executionEntity=getExecution(taskEntity.getExecutionId());
ProcessExecution newExecution=new ProcessExecution(executionEntity);
newExecution.setId(newExecutionId);
ProcessTask newTask=new ProcessTask(taskEntity);
newTask.setId(newTaskId);
newTask.setExecutionId(newExecutionId);
newTask.setCreateTime(new Date());
newTask.setAssignee(assignee);
newTask.setOwner(assignee);
ProcessTaskHistory newTaskHistory=new ProcessTaskHistory(taskEntity);
newTaskHistory.setAssignee(assignee);
newTaskHistory.setStartTime(new Date());
newTaskHistory.setId(newTaskId);
newTaskHistory.setOwner(assignee);
executionDao.add(newExecution);
taskDao.insertTask(newTask);
taskHistoryDao.add(newTaskHistory);
return newT
说明:以上代码写在BpmService类里,关键是从原来的任务中复制一份新的数据出来,同时需要复制其Execution的记录以及执行历史的记录。
需要记录分发与汇总的节点
所以在流程节点的设置上,我们提供了以下的配置实体。
public class BpmNodeSet extends BaseModel
* 在线表单
public static Short FORM_TYPE_ONLINE=0;
public static Short FORM_TYPE_URL=1;
* 普通任务节点
public static Short NODE_TYPE_NORMAL=0;
* 分发任务节点
public static Short NODE_TYPE_FORK=1;
protected Long setId;
// 流程定义ID
protected Long defId;
protected String nodeN
// Activiti流程定义ID
protected String actDefId;
protected String nodeId;
// 表单类型(0:在线表单,1:URL表单)
protected Short formType=-1;
// 表单URL
protected String formU
// 表单定义ID
protected Long formDefId;
// 表单名称
protected String formDefN
* 任务类型:
* 0=普通任务
* 1=分发任务
protected Short nodeT
* 当任务类型=1时,可以指定汇总任务Key
protected String joinTaskK
* 当任务类型=1时,指定的汇总任务名称
protected String joinTaskN
然后在任务的创建及完成的事件里加上监听若当前的任务为分发任务,则动态产生分发的任务。若为汇总任务,则只产生最后一个汇总,以免得由Activiti产生多个汇总任务。 在监听事件创建分发任务(TaskCreateListener.java类)
BpmNodeSet bpmNodeSet=bpmNodeSetService.getByActDefIdNodeId(actDefId, nodeId);
if(bpmNodeSet!=null && BpmNodeSet.NODE_TYPE_FORK.equals(bpmNodeSet.getNodeType())){//当前任务为分发任务
Map&String,List&String&& nodeUserMap=taskUserAssignService.getNodeUserMap();
//若当前的线程里包含了该任务对应的执行人员列表,则任务的分发用户来自于此
if(nodeUserMap!=null && nodeUserMap.get(nodeId)!=null){
List&String& userIds=nodeUserMap.get(nodeId);
bpmService.newForkTasks((TaskEntity)delegateTask, userIds);
//产生分发记录,以方便后续的任务汇总处理
taskForkService.newTaskForks(delegateTask,bpmNodeSet.getJoinTaskName(), bpmNodeSet.getJoinTaskKey(), userIds.size());
ForkUser forkUser=taskUserAssignService.getForkUser();
if(forkUser!=null){
bpmService.newForkTasks((TaskEntity)delegateTask, forkUser.getForkUserIdsAsList());
以上代码中,分发任务的创建对应的人员来自表单中指定的人员。 任务汇总时,我们需要记录完成的情况,若为汇总节点,我们会根据汇总完成的情况,进行处理,若汇总的任务尚没有全部完成,后续产生的汇总任务我们则采用删除策略,该方法定义在BpmService类中。
* 检查及删除重复的汇总任务
* @param processInstanceId
public void deleteRepeatJoinTask(String processInstanceId){
List&TaskEntity& taskList=getTasks(processInstanceId);
for(TaskEntity task:taskList){
//判断后续的节点是否为汇总节点,若是,则需要检查是否需要产生后续的任务
BpmNodeSet joinNodeSet=bpmNodeSetService.getByActDefIdJoinTaskKey(task.getProcessDefinitionId(), task.getTaskDefinitionKey());
if(joinNodeSet!=null){
TaskFork taskFork=taskForkService.getByInstIdJoinTaskKey(task.getProcessInstanceId(), task.getTaskDefinitionKey());
if(taskFork!=null){
if(taskFork.getFininshCount()&taskFork.getForkCount()-1){
taskService.deleteTask(task.getId());
//更新完成任务的个数
taskFork.setFininshCount(taskFork.getFininshCount()+1);
taskForkService.update(taskFork);
taskForkService.delById(taskFork.getTaskForkId());
最终实现的效果可以如下所示:
更多资讯请加QQ了解
可以用泳道和foreach-join实现这个的确可以实现
扩展他们本身的api实现的能说具体点吗?哪个API?具体怎么实现的,请不吝赐教,小弟感激了。
浏览: 321879 次
来自: 广州
这是主流程调用子流程报的错大神指导原因吗?
pageoffice也是office在线编辑的吧,J.Offi ...
你好,想问下,串行的多实例任务能做到回退么
参考这个实现思路,可以弄个自定义的表单设计器http://wi ...
都进不去啊Activiti在强大的表达式之上做了更高的构建我们从成立jBPM直到jBPM4设计流程虚拟机构建。在Activiti我们现在有非常熟练的和有才能的人和公司构建下一个通用的BPM技术。BPMN2.0将是BPM的未来并且我们有专门技术带来这些特征进开发人员友好开发。Activiti的关注点在于BPMN2.0能够使我们实现未来的BPM和工作流解决方案。
给出我们构建jBPM4做的努力并且我们有值得骄傲的成果,我们遗憾jBPM4由JBoss表示停止使用。
Activiti不会遭受单独公司的易损点。我们非常高兴Alfresco给我们机会打算开发Activiti为一个Apache项目。Apache基金会的核心价值是项目的连续性和保证他待在真正的社区里。所以其中的要求是多个公司必须积极参与社区项目。从一开始,SpringSoure就加入了这个项目所以我们在我们的路上非常良好确保Activiti有很长的生命而不由单个个人或公司控制。

我要回帖

更多关于 activiti工作流引擎 的文章

 

随机推荐