在JBPM的使用中,很多时候我们要用到监听,前面讲过一个AssignmentHandler,它的作用更多的被用在动态分配任务中。AssignmentHandler虽然也能实现监听,但是有它的不足只出。它只能放到Task节点下,作为任务分配来使用。其它节点就不能用了。其它节点不会触发AssignmentHandler的方法。
在其它节点下监听流程信息,采取用户操作一般使用EventListener,EventListener可以放到任务节点下,不如process根目录,end节点,task,state等节点。当有流程经过这个节点的时候就会出发节点事件所注册的类。
为了给一个流程或一个活动分配一系列的事件监听器,使用on元素来为事件监听器分组并指定事件。
下面看一个我的实例:
<end g="319,369,48,48" name="结束"> <on event="start"> <event-listener class="com.zhjy.bpm.Listener.EndListener"> </event-listener> </on> </end>
这个监听是在End节点中注册一个监听类,这个类是我们自己写的。使用on元素来指定事件,这个需要注意的是on元素event属性可以配置为start或者end,这个为告诉jbpm这个事件是在end的开始执行开始完成执行。
import org.jbpm.api.listener.EventListener; import org.jbpm.api.listener.EventListenerExecution; import org.jbpm.pvm.internal.env.EnvironmentImpl; import com.zhjy.mtdev.plan.PlanState; import com.zhjy.mtdev.plan.service.IPlanService; /** * @Title: TaskListener.java * @author 李守宏 * @date 2012-9-18 下午02:05:00 * @version V1.0 */ public class EndListener implements EventListener { private static final long serialVersionUID = 1L; /* (non-Javadoc) * @see org.jbpm.api.listener.EventListener#notify(org.jbpm.api.listener.EventListenerExecution) */ @Override public void notify(EventListenerExecution execution) throws Exception { IPlanService planService= (IPlanService) EnvironmentImpl.getFromCurrent("planService"); String ownerId = execution.getVariable("planId").toString(); String sign = execution.getVariable("sign").toString(); if("通过".equals(sign)){ planService.updateState(ownerId, PlanState.STORAGE.toString()); }else if("补正".equals(sign)){ planService.updateState(ownerId, PlanState.CORRECT.toString()); }else{ planService.updateState(ownerId, PlanState.REJECT.toString()); } } }
这里的notify方法是必须实现的。流程通过则触发这个事件,然后可以拿到流程执行的相关信息,通过execution可以获取流程信息,流程实例信息,甚至是任务信息,任务信息获取的方式是这样的。
TaskService taskService= (TaskService) EnvironmentImpl.getFromCurrent("taskService"); //获取流程ID String id = execution.getProcessInstance().getId(); List<Task> task = taskService.createTaskQuery().processInstanceId(id).list();
拿到Task列表以后,你就可以拿到很多信息。但是一定注意,在Task中获取已经存在的一个TaskID,然后去完成它会报错的。因为这个监听的过程中旧的任务ID已经不存在新的任务ID还没有生成,task是为空的。这个大家一定要注意,我在这块研究了很长时间。
总之上面说的两种监听,是jbpm常用的获取流程信息的方法,这样被动的监听信息,比主动的获取信息要方便很多,这是对观察者模式的良好应用。监听还可以结合其它技术使用,达到更好的效果比如泳道
SWIMLANE等。达到任务的动态分配效果。