- 浏览: 772563 次
- 性别:
- 来自: 广州
文章分类
最新评论
-
corelengine:
好文,支持一下!
在 Spring Web Flow 项目中应用 Hessian 服务 -
corelengine:
感谢分享,不过你的工程太简单了,怎么可以导入eclipse
Spring Web Flow 2.0 入门 例子源码 -
chenrongtao2132:
melody404 写道请教博主一个问题
登录成功以后为什么老 ...
CAS 单点登录安装笔记4 -- asp.net client端的设置 -
chxiaowu:
从头到尾没发现 那里有 cxf bean配置啊。。。。
WebService开发笔记 3 -- 增强访问 WebService 的安全性 -
chxiaowu:
严重: StandardWrapper.Throwable
o ...
WebService开发笔记 3 -- 增强访问 WebService 的安全性
一个Jbpm员工请假流程的实例
http://blog.csdn.net/dust_bug/archive/2006/10/27/1353218.aspx
作者:吴大愚
Email:dywu_xa@sina.com
2006-10-26
适用于jbpm3.1版本
1. 概述
此实例包括的是一个员工请假审批的流程实例,和流程相关的代码以及相应的测试代码。此流程在Eclipse3.1.2 ,JBoss-IDE 1.6环境下测试通过。
说明,这篇文章说使用的流程实例是,学习《一个JBPM工作流管理示例》文章中的流程而来。原文中的流程实例不是jbpm3.1版本,不能适用于jbpm3.1。本人将其改写,并加入自己的设计和实现。原文地址为http://blogger.org.cn/blog/more.asp?name=lhwork&id=16137。可以对照学习。
2. 流程说明
假设应用背景如下:
在某一公司中,部门员工要休假的话需要部门主管的批准。如果休假天数大于10天的话,在部门主管的同意后,还必须老板批准。如果是部门主管要休假只要老板批准即可。在休假被批准之前,申请人可以撤销休假申请。
每次休假申请结束之后,不管通过未通过或是否取消,都必须记录下来。主管在批复申请之后,系统要将批复结果Email给申请人。对于大于10天的申请,如果部门主管已批准同意而上级主管还未批准,这时申请人撤销申请后,系统应发Email通知部门主管申请已撤销。
3. 流程定义
3.1. 原文件
<!---->
3.2. 流程图片
3.3. 说明
3.3.1. 命名规则
start-state的定义为SS_
end-state的定义为ES_
task-node的定义为TN_
fork的定义为Fork_
join的定义为Join_
task的定义为Task_
transition的定义为Tr_
action的定义为Ac_
3.3.2. join节点类型
join结点Join_Request,采用的是Discriminator模式,即只要有一个fork发出的分支到达join,流程就可以向下进行。
Join共有三中模式:
l 默认的是所有fork发出的分支都到达,流程才向下进行;
l 第二种就是Discriminator模式,只要有一个fork发出的分支到达join,流程就可以向下进行;
l 第三种是设置当有n个分支到达之后,流程就可以向下进行。
但jpdl语言在jbpm3.1版本中还不支持对第二,第三两种模式的设置。需要在流程实例化之后,来制定join的模式。具体如何实现,参见后面有关代码部分。
3.3.3. 申请状态
系统存在一个有关申请的状态。系统用流程变量RequestState来存储。共有五个状态。存储在com.myrequest.RequestState.java文件中。
在用户启动此请假流程,完成第一个填写请假申请的任务实例后,此状态置为REQUEST。在完成取消请求任务之后,状态改为CANCEL。等等,读者可以仔细阅读流程定义和对应的代码。
要说明的是所有的状态修改都在完成任务之后的边上执行Action中来修改的。这样虽然增加了很多Action,但是状态修改明确。但对于这样的简单问题,前台代码在实际任务完整之后,就可以调用修改此状态变量。此处将这些修改都放在Action里面,也有一定演示的含义。
3.3.4. 取消请假任务说明
在fork节点后,产生两个并行分支。其中一个TN_RequestCancel任务节点包含一个Task_CancelRequest的任务。当此分支执行到这里时,会把这个任务分配给启动流程的用户。在流程没有结束的时候,如果用户执行这个任务,就表示用户要取消请假申请。在这个取消申请的任务会修改请假状态,在此任务结束后,就会首先到达join节点。表示取消了此次申请操作。
4. 代码说明
4.1. 代码包结构
本实例是在Eclipse3.1.2里面实现的。
在src/java目录下面,有包:
l com.myrequest
n 存放流程的公共信息,包括:
n interface RequestState,用来存放请求状态的5种状态
n interface RequestVariable 存放流程实例的变量名
l com.myrequest.action
n 存放流程中所有的ActionHandler类
n 共有12个类,每个类对应流程中一个action的代码。
l com.myrequest.task
n 存放流程中所有的task的AssignmentHandler分配类
n 共有4个类,对应4个task
l com.myrequest.decision
n 存放流程中所有的decision节点的判断类
n 包括3个类,对应3个Decision节点
在src/test目录下面,有包:
l com.myrequest
n 包含此流程的测试类 MyRequestProcessTest.java
在processes目录下面,有:
l 流程定义文件夹MyRequest,包含:
n Gpd.xml
n Processdefinition.xml
n Processimage.jpg
4.2. 流程代码说明
对流程中使用到的和Action,task,decision相关的类,以及测试类进行说明。
4.2.1. Action代码说明
流程中的Action都使用指定类的形式来完成Action的操作。
例如:
<transition name="Tr_WriteLeave" to="Fork_request"> </transition>
<action class="com.myrequest.action.WriteLeaveActionHandler" name="Ac_WriteLeave"></action>
当流程执行到边Tr_WriteLeave后,就会自动去执行Action里面指定的类WriteLeaveActionHandler。
类WriteLeaveActionHandler实现了接口ActionHandler。此接口就一个函数
public void execute(ExecutionContext executionContext)
当流程执行这个类的时候,就会去调用这个函数。所以我们Action所要完成的工作也都写在这个函数中。
在RequestBeginActionHandler.execute()中,我们只做了将整个流程的请求状态设置为REQEUST状态。
4.2.2. Task代码说明
所有Task都是在Task-node中描述的。Task都是人工任务,也就是说需要先将task分配给那个人,然后由这个人来完成。在人开始任务的时候,可以调用taskInstance的start()操作,表明任务开始。(start()操作是可选的,也可以不调用) 在任务结束后,可以调用taskInstance的end()操作,表示任务实例结束。如果是整个task-node中的最后一个task的end()操作,那么就会这个end操作就会触发流程继续向下走。
例如:
<task name="Task_WriteRequest"></task>
<controller></controller>
<variable name="dayCount" access="read,write,required"></variable>
<assignment class="com.myrequest.task.WriteRequestAssignmentHandler"></assignment>
当流程实例化Task_WriteRequest这个task后,首先会使用WriteRequestAssignmentHandler类来进行任务的分配。WriteRequestAssignmentHandler类实现了AssignmentHandler接口,包含一个
public void assign(Assignable assignable, ExecutionContext executionContext)接口。其中参数assignable就是此任务实例的引用(TaskInstance实现了Assignable接口)。因此我们只要调用assignable.setActorId(String userid),就可以把这个任务分配给userid所代表的用户来执行了。
对于前台,当用户登陆后,通过org.jbpm.db.TaskMgmtSession.findTaskInstances(java.lang.String actorId)就可以得到当前用户所有要执行的任务了,这里的任务是属于多个不同的流程实例的。如果查看数据库就会发现在jbpm_taskInstance表中,每一个taskinstance在actorId_字段记录的是次任务实例分配人员的用户名。这也就是上面所说的findTaskInstances方法如何工作的关键之处。
在WriteRequestAssignmentHandler .assign()里面,我们首先读入流程变量userId,然后将任务分配给这个userId。
如何调用任务实例的end,来表示任务实例的完成呢?真正的系统中应该是在前台,当客户通过web或是客户端触发操作,然后执行对应的任务实例的end操作。但是在我们的代码中只能通过在junit的测试代码中来模拟。具体参见后面讲解测试代码部分。
4.2.3. Decision代码说明
Decision节点可以有多种方式来进行条件判断。
方法一是在每条出边上加一个beanshell的表达式,jbpm引擎会按照流程定义文档中边的顺序一次调用,来判断那个表达式为true,当发现第一个为true的时候,流程就走这条边了。
方法二就是对Decision节点配置一个handler。通过一个类来实现条件判断。
例如:
表示当执行到Deci_IsChiefHere节点后,会自动执行IsChiefHereDecisionHandler类。IsChiefHereDecisionHandler实现了DecisionHandler接口。此接口包含一个方法public String decide(ExecutionContext executionContext) throws Exception 这个方法应该返回一个transition的name,表示选择走那条边。
这IsChiefHereDecisionHandler.decide()操作中,我们首先读取流程变量isChiefHere,然后判断走那条边。
4.3. 流程测试类代码说明
4.3.1. 测试类整体说明
测试类为com.myrequest. MyRequestProcessTest
包含三个设施函数,分别为
l test14DayAndBossNotApprove()
n 测试员工申请14天假期,部门主管批准,但老板不批准
l test4DayAndChiefApprove()
n 测试员工申请14天假期,部门主管批准,(不需要老板批准)
l test14DayAndChiefApproveAndUserCancel()
n 测试员工申请14天假期,部门主管批准,在老板审批前员工自己撤销申请
每个测试前都执行setUp()操作,这个操作用来设置流程中两个变量,一个是用户id,另外一个是部门主管是否在岗的状态。可以修改这两个参数,进行不同的测试。尤其是第二个参数,会影响流程的走向,可以分别设置为true和false以观察流程的走向和结果。
在测试类中还有7个辅助函数。分别为:
l deployProcessDefinition()
n 流程部署
l createProcessInstance()
n 创建流程实例
n 设置join节点的性质为Discriminator模式(参见流程定义部分)
n 设置流程相关变量
n 启动流程
l userWriteRequest(int daycount)
n 模拟申请员工完成Task_WriteRequest任务,参数为请假的天数
l chiefDecide(boolean isApprove)
n 模拟部门主管完成Task_ ChiefDecide任务,参数为部门主管是否批准
l bossDecide(boolean isApprove)
n 模拟老板完成Task_ BossDecide任务,参数为老板是否批准
l userCancel()
n 模拟申请员工完成Task_ CancelRequest任务
l checkTasks()
n 检查整个流程中所有的任务的相关信息
4.3.2. checkTasks()说明
checkTasks()的核心是pi.getTaskMgmtInstance().getTaskInstances();返回流程实例的所有任务实例列表。但要说明的是所返回的任务实例列表和当前流程执行的位置有关,在流程开始处,流程执行中间,和流程执行结束处调用得到的任务实例列表不同。列表包含已经完成的任务实例和当前任务实例。
本来在此方法中还有现实每个任务实例起始时间和结束时间的操作。但发现返回全部为null。这说明在没有使用数据库是,有关时间的属性是不可用的。也就是说,这些时间属性都是记录在数据库jbpm_taskInstance表中的。没有用数据库自然就得不到,它不会保留在内存的流程实例中。要说明的是jbpm_taskInstance表的start字段如果有时间,表示任务实例已经开始执行。如果end字段有时间,表示任务实例已经结束,此任务已经完成。
4.3.3. 测试中有关任务实例获取的说明
因为没有使用数据库,所以不能使用org.jbpm.db.TaskMgmtSession.findTaskInstances(java.lang.String actorId)得到不同用户的当前任务。所以只能便利当前流程实例任务列表,从中找到相应的任务来操作。
如果有人有更好的办法,请留言告知,谢谢:)
5. 实例不足和待学习地方
5.1. 不足
没有使用swimlane,可以添加swimlane来进行任务分配。像websale就是有角色的。主要的原因是对swimlane的使用我还没有搞清楚。我有关swimlane的学习心得会在下一篇对jbpm自带实例websale的分析中来描述。
5.2. 学习点
通过这个实例,我发现org.jbpm.module.exe.ModuleInstance类有很多创建任务实例的方法,例如createTaskInstance(Task task)等等。我一直认为任务的实例化是在流程执行过程中,又工作流引擎来做的工作。不知道在我们写的代码中需要用到创建流程这样的方法吗?如果要用的话,在什么情况下会用到呢?
此外还有很多问题没有搞懂,比如jbpm的模块化思想,它的Ioc实现等等。慢慢学习吧。
6. 完整代码
发表评论
-
JBPM与SPRING事务框架完全整合
2007-12-04 13:43 140JBPM与SPRING事务框架完全整合 作者: beta ... -
ForEachForkActionHandler
2007-10-03 20:20 1184http://wiki.jboss.org/wiki/Wiki ... -
jbpm 使用日记5 一个简单会签示例
2007-09-28 16:10 1659http://www.iteye.com/topic/3358 ... -
JBPM任务回退轻轻松,不用画线.
2007-09-28 12:54 2835JBPM @net -> 论坛 -> JBPM任务 ... -
JBPM流程通过Aciton动态创建TaskInstance来实现“会签”
2007-09-28 12:11 1767JBPM流程通过Aciton动态创建TaskInstanc ... -
jBPM 并发子流程的解决方案与探讨
2007-09-28 11:43 1424jBPM 并发子流程的解决方案与探讨 ... -
Jbpm流程节点动态的创建
2007-09-28 11:32 1716http://jbpm.group.iteye.com/gro ... -
Jbpm 表结构说明
2007-09-28 11:31 2127http://www.blogjava.net/libin27 ... -
事务管理最佳实践全面解析
2007-09-02 16:29 1098事务管理最佳实践全面解析 http://blog.csdn.n ... -
如何将一个分配给了pooledactors的任务回撤
2007-09-02 16:07 1356如何将一个分配给了pooledactors的任务回撤? JBP ... -
SPRING+HIBERNATE3+JBPM+OC4J(初步实现整合)
2007-08-29 12:04 1460http://www.kehui.net/html/artic ... -
主题: jbpm 使用日记5 一个简单会签示例
2007-08-29 11:56 1488http://www.iteye.com/topic/3358 ... -
jBPM 与 spring的整合
2007-08-29 11:49 1411http://forum.springframework.or ... -
Jbpm表结构说明 (转)
2007-08-25 19:38 6440http://blog.csdn.net/airc/archi ... -
jBpm教程jbpm - CSDN tag [RSS 2.0]
2007-08-25 12:17 2290http://tag.csdn.net/tag/jbpm.xm ... -
jBPM在不同的环境进行部署(摘)
2007-08-21 07:27 1881原文:http://www.jboss.com/product ... -
JBPM deploy processdefinition 报错的问题原因及解决办法
2007-08-21 07:21 1550JBPM deploy processdefinition 报 ... -
jBpm的Event介绍
2007-08-20 16:23 1571http://blog.csdn.net/james999/a ... -
jBPM websale代码学习
2007-08-20 16:11 1682http://blog.csdn.net/hongbo7812 ... -
使用jBPM开发企业流程应用之在Tomcat上部署流程引擎及控制台
2007-08-19 13:27 1531使用jBPM开发企业流程应用之在Tomcat上部署流程引擎及 ...
相关推荐
在这个实例中,我们关注的是一个基于Jbpm实现的员工请假流程。这个流程涵盖了从申请到审批的整个过程,展示了Jbpm在实际业务场景中的应用。 首先,`.classpath`和`.project`是Eclipse IDE的配置文件,它们定义了...
这个实例是针对Jbpm3.1版本设计的一个员工请假流程,由吴大愚编写的,旨在帮助用户理解如何利用Jbpm实现企业内部的请假审批流程。 1. **流程概述** 这个流程模拟了一个常见的请假审批过程,员工提交请假申请后,...
在这个“员工请假流程的实例”中,我们看到了如何使用Jbpm来实现一个实际的业务场景。这个流程涉及了员工请假的审批过程,涵盖了不同级别的审批权限和撤销申请的规则。 1. **流程概述** - 该流程设计了一个简单的...
在这个"jbpm4.3 请假流程实例示例"中,我们将深入探讨如何利用jbpm4.3构建一个简单的请假流程,并了解相关的核心概念和技术。 首先,我们要理解什么是业务流程管理(BPM)。BPM是一种方法,它通过自动化和优化企业...
此实例包括的是一个员工请假审批的流程实例,和流程相关的代码以及相应的测试代码。此流程在Eclipse3.1.2 ,JBoss-IDE 1.6环境下测试通过。 说明,这篇文章说使用的流程实例是,学习《一个JBPM工作流管理示例》文章中...
jbpm请假流程实例通常包括以下几个关键步骤: 1. **流程设计**:首先,开发者会使用jbpm提供的流程建模工具(例如:jBPM Designer)来定义请假流程。这涉及到创建各种活动(如:申请、审批、驳回等)、决策节点...
【jbpm4请假实例代码】是一个基于jbpm4工作流引擎的示例应用,它用于演示如何在实际项目中实现员工请假流程的自动化管理。jbpm4是一个开源的工作流管理系统,它提供了强大的业务流程建模、执行和管理功能,使得...
这是一个jbpm员工请假实例PDF文档,里面写得很详细,有图有代码,有文字描述,非常不错!
jbpm4.4 请假流程实例数据库( mysql .sql文件)
【标题】"一个请假流程实例(JBPM项目)"所涉及的知识点主要集中在企业流程管理和Java业务处理平台JBPM上。JBPM是一个开源的工作流管理系统,它允许开发者设计、执行和管理业务流程。在这个实例中,我们将探讨如何使用...
在这个完全版的请假流程JavaWeb项目中,我们将深入探讨如何利用jBPM4.4构建一个完整的业务流程管理系统。 1. **jBPM核心概念** - **流程定义**: jBPM使用BPMN(Business Process Model and Notation)2.0标准来...
这个示例是关于如何在JBoss JBPM4平台上实现一个简单的请假流程,帮助开发者了解如何定义、执行和管理业务流程。 在JBoss JBPM4中,一个流程通常由一系列任务组成,这些任务可以由系统自动执行,也可以由人参与完成...
在这个"JBPM5请假实例,完整版"中,我们将深入探讨如何利用JBPM5来实现一个具体的请假流程,以及在这个过程中可能遇到的关键配置问题。 首先,我们要理解JBPM5的核心功能。JBPM5提供了一个强大的流程建模工具,它...
使用jbpm开源工作流开发的一个请假流程实例,包含SSH,数据库用的是SQLServer,数据访问层Hibernate,中间层Sprinng,表现层Struts2,工作流jbpm。
【jbpm4的员工请假例子原码】是一个基于jbpm4流程引擎的示例项目,展示了如何在企业中实现一个简单的员工请假流程。这个Web项目是完全开源的,可以通过Eclipse这样的集成开发环境来打开和运行,对于学习和理解jbpm4...
【jbpm4.4-请假流程】是一个基于Java开发的流程引擎示例,主要用于演示如何在企业级应用中实现请假流程。jbPM是Java Business Process Management的缩写,它是一个开源的工作流和业务流程管理系统,提供了对BPMN 2.0...