要实现JBPM的任务回退很简单,只要对JBPM中的2个表进行修改,这2个表分别是:
jbpm_token和jbpm_taskinstance,对应类是org.jbpm.graph.exe.Token和
org.jbpm.taskmgmt.exe.TaskInstance.
修改方法:
将已经完成的任务实例jbpm_taskinstance表中的2个字段修改:issuspended_=0和
isopen_=0,将start_=null和end_=null这2个字段改不改都可以 我自己是另外用一个业务表来记录任务处理时间的
这样就能将已经完成的实例重开
还要修改的表就是jbpm_token中的node_字段,这里要将你所回退到的节点的ID写进去,进行数据库的更新。
这2个表对应的2个方法分别是getTokenForUpdate和getTaskInstanceForUpdate。
jbpm没将任务回退直接写成Java方法,估计是怕不同人有不同的需求,感觉如果将jbpm的表结构如果能全了解,那样要根据自己需求自己扩展就很简单了。
多分支回退功能实现思路
在流程派发界面增加一个“回退按钮”,回退按钮仅能实现逐步回退,即回退到上一步;
如想实现多步回退,建议采用决策节点进行实现;
点击按钮后,系统进行如下判断:
首先需要了解当前节点的上一节点类型{
根据当前节点id(nodeid)查询JBPM_TRANSITION表,获得from信息;{
select name_,from_ as 上一节点id from JBPM_TRANSITION where PROCESSDEFINITION_ = ? and TO_ = ?[当前节点id]
}
select class_ from JBPM_NODE where id_ = 上一节点id
}
如果是开始节点(node class is R)则不允许
如果是普通节点(node class is K){
@todo:
1,将当前任务实例设置成完成状态(update JBPM_TASKINSTANCE set END_ = GETDATE(),ISOPEN_=0,ISSIGNALLING_=0 where id_ = ?;)
2,将上一节点对应的任务实例设置成未完成状态(
根据节点id获得任务id;
update JBPM_TASKINSTANCE set END_ = null,ISOPEN_=1,ISSIGNALLING_=1 where TOKEN_=? and TASK_ = ?;
)
3,将token移动到上一节点上(update JBPM_TOKEN set NODE_ = 1492 where ID_ = ?[tokenid];)
4,保存退回意见;操作JBPM_VARIABLEINSTANCE表{
INSERT INTO JBPM_VARIABLEINSTANCE
([CLASS_] -- 固定值
,[NAME_] --固定值
,[TOKEN_] --token id
,[PROCESSINSTANCE_] -- 流程实例id
,[STRINGVALUE_] -- name_ == 'operatorId' ? '当前登录人id' : '审批意见'
,[TASKINSTANCE_]) -- 当前任务实例id
VALUES
('S','operatorId',?,?,?,?) --记录操作人
,('S','comment',?,?,?,?) --记录操作人填写的审批意见
}
}
如果是汇聚节点(node class is J){
@todo:
1,查询汇聚节点的来源节点(select name_,from_ from JBPM_TRANSITION where PROCESSDEFINITION_ = ? and TO_ = ?)
2,将"必须执行"的节点结果集显示在界面上供用户选择(支持多选){
1,根据from_获得task_id(select * from JBPM_TASK where TASKNODE_ = ?[from_];)
2,检查节点是否必须执行(select if_must_approve[1必须0不必须] from wf_taskuser where task_id_ = ? and prcessinstance_id_ = ?)
}
3,用户选择预回退的节点后点击确认操作,系统做如下处理{
1,将当前任务实例设置成完成状态[同上]
2,获得所选节点信息
3,将获得的所有节点信息对应的任务实例设置成未完成状态[同上]
4,将token[子token]移动到每个所选节点上(update JBPM_TOKEN set NODE_ = ?[所选节点id],ISABLETOREACTIVATEPARENT_ = 1 where ID_ = ?[子tokenID];)
5,保存退回意见[同上]
}
}
如果是分支节点(node class is F){
@todo:
如果是汇聚节点,那么此操作一定发生在分支上且是其中一分支发起的回退操作;
首先系统提示操作者,此回退操作会自动设置所有分支中的任务实例状态为已完成;
确定操作后,token会回到汇聚节点处;
1,提示用户此操作的下场是什么
2,根据token查询所有子token(select ID_ from JBPM_TOKEN where PARENT_ = ?)
3,查询所有子token对应的任务实例(select * from JBPM_TASKINSTANCE where TOKEN_ in (select ID_ from JBPM_TOKEN where PARENT_ = ?))
4,将所有任务实例设置成完成状态
5,找到分支节点的上一节点并将对应的任务实例设置成未完成状态{
1,select from_ as 上一节点id from JBPM_TRANSITION where PROCESSDEFINITION_ = ? and TO_ = ?[当前节点id];
2,update from_对应的任务实例为未完成状态[同上]
}
6,将token(父亲)移动到分支节点的上一个节点上{
1,找到分支节点的上一节点[同上]
2,update JBPM_TOKEN set NODE_ = ?[from_] where ID_ = ?[tokenid];
}
6,保存退回意见[同上]
}
如果是决策节点(node class is D){
@todo:
1,将当前任务实例设置成完成状态
2,找到决策节点的上一节点并将对应的任务实例设置成未完成状态
3,将token移动到决策节点的上一节点
4,保存退回意见
}