导入jbpm4.3所有包,我用的mysql,c3数据源
jar包加上,可以直接跑测试类,源码带注释,我变懒了。
项目中的CountersignActivity类更新为如下代码,之前的有点问题:
package com.bjhy.oa.service.workflow.util; import java.util.HashMap; import java.util.Map; import org.jbpm.api.ExecutionService; import org.jbpm.api.JbpmException; import org.jbpm.api.TaskService; import org.jbpm.api.activity.ActivityExecution; import org.jbpm.api.task.Task; import org.jbpm.jpdl.internal.activity.JpdlExternalActivity; import org.jbpm.pvm.internal.env.EnvironmentImpl; import org.jbpm.pvm.internal.history.HistoryEvent; import org.jbpm.pvm.internal.history.events.TaskActivityStart; import org.jbpm.pvm.internal.history.model.HistoryTaskImpl; import org.jbpm.pvm.internal.model.Activity; import org.jbpm.pvm.internal.model.ExecutionImpl; import org.jbpm.pvm.internal.model.Transition; import org.jbpm.pvm.internal.script.ScriptManager; import org.jbpm.pvm.internal.session.DbSession; import org.jbpm.pvm.internal.task.TaskImpl; import com.bjhy.oa.service.workflow.util.CountersignUser.Conclusion; /** * 定制会签元素标签 * */ public class CountersignActivity extends JpdlExternalActivity { private static final long serialVersionUID = 1673162002085098868L; /** * 默认的会签信息在上下文中的名字 */ public static final String DEFAULT_COUNTERSIGN_VAR_NAME = "COUNTERSIGN"; /** * 任务的参与者,多个参与者用;号隔开 */ private String assignees; /** * Task的名字,可以不设置,不设置时将采用Activity的名字 */ private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } public String getAssignees() { return assignees; } public void setAssignees(String assignees) { this.assignees = assignees; } /** * 执行表达式语句获取结果 * * @param express * @return * @throws JbpmException */ protected String evaluateExpression(String express) throws JbpmException { if (express != null) { express = express.trim(); if (express.length() > 0) { ScriptManager scriptManager = ScriptManager.getScriptManager(); Object result = scriptManager.evaluateExpression(express, null); if (result != null) { express = result.toString(); } } } return express; } /** * 创建新的任务 * * @return */ private TaskImpl createCounterSignTask(DbSession dbsession, ExecutionImpl execution) { TaskImpl task = dbsession.createTask(); String taskName = name == null ? execution.getActivityName() : name; task.setName(taskName); task.setExecution(execution); task.setProcessInstance(execution.getProcessInstance()); task.setSignalling(false); dbsession.save(task); HistoryEvent.fire(new TaskActivityStart(task), execution); return task; } /** * 创建会签子任务 * * @param dbsession * @param execution * @param task * @param user * @param ht */ public void newCounterSignSubTask(DbSession dbsession, ExecutionImpl execution, TaskImpl task, String user, HistoryTaskImpl ht) { TaskImpl subtask = task.createSubTask(); subtask.setName(task + "_" + user); subtask.setAssignee(user); subtask.setSignalling(false); dbsession.save(subtask); ht.addSubTask(dbsession.get(HistoryTaskImpl.class, subtask.getDbid())); } /** * 实例创建的时候会调用该方法 */ public void execute(ActivityExecution activityExecution) { ExecutionImpl execution = (ExecutionImpl) activityExecution; // 创建当前任务 DbSession dbsession = EnvironmentImpl.getFromCurrent(DbSession.class); ExecutionService executionService = EnvironmentImpl .getFromCurrent(ExecutionService.class); TaskImpl taskImpl = createCounterSignTask(dbsession, execution); HistoryTaskImpl ht = dbsession.get(HistoryTaskImpl.class, taskImpl .getDbid()); CountersignInfo countersignInfo = new CountersignInfo();// 处理会签过程的类 Map<String, CountersignUser> users = new HashMap<String, CountersignUser>(); // 创建子任务 for (String assignee : assignees.split(";")) { newCounterSignSubTask(dbsession, execution, taskImpl, assignee, ht); CountersignUser user = new CountersignUser(assignee); users.put(assignee, user); } countersignInfo.setUsers(users);// 保存所有用户 countersignInfo.setCountersignStrategy(new AllAgreeStrategy());// 设置会签策略 String name = activityExecution.getActivityName(); dbsession.flush(); executionService.setVariable(activityExecution.getId(), name + "_COUNTERSIGN_INFO", countersignInfo); execution.waitForSignal(); } /** * 流程执行的时候会调用该方法 */ public void signal(ActivityExecution activityExecution, String signalName, Map<String, ?> parameters) throws Exception { ExecutionImpl execution = (ExecutionImpl) activityExecution; ExecutionService executionService = EnvironmentImpl .getFromCurrent(ExecutionService.class); TaskService taskService = EnvironmentImpl .getFromCurrent(TaskService.class); String executionId = activityExecution.getId(); Activity activity = execution.getActivity(); Map<String, Object> variables = executionService.getVariables( executionId, executionService.getVariableNames(executionId)); // 获取子任务 Task subTask = (Task) parameters.get("subTask"); Task superTask = ((TaskImpl) subTask).getSuperTask(); taskService.completeTask(subTask.getId());// 结束子任务 // 收集会签意见 String countersignAgree = (String) parameters.get("countersignAgree");// 会签意见内容 Conclusion conclusion = (Conclusion) parameters.get("conclusion");// 会签选择 String assignee = subTask.getAssignee();// 会签人 // 更新集合信息 CountersignInfo countersignInfo = (CountersignInfo) variables .get(superTask.getActivityName() + "_COUNTERSIGN_INFO"); Map<String, CountersignUser> users = countersignInfo.getUsers(); CountersignUser countersignUser = users.get(assignee); countersignUser.setConclusion(conclusion); countersignUser.setCountersignAgree(countersignAgree); boolean allSign = true; // 遍历是否会签完毕 for (CountersignUser item : users.values()) { if (item.getConclusion() == Conclusion.NOSTART) { allSign = false; } } countersignInfo.setAllSign(allSign); // 如果会签完毕,计算结果 if (allSign) { countersignInfo.calculate(); String agree = "同意"; // 如果结果为否决 if (countersignInfo.getConclusion() == Conclusion.DENED) { agree = "不同意"; } variables.put("agree", agree); // 更新集合信息 executionService.setVariables(executionId, variables); // 提交父任务 // 会签完毕,删除父任务 taskService.completeTask(superTask.getId());// 结束子任务 Transition transition = null; if ((signalName == null) || ((Task.STATE_COMPLETED.equals(signalName)) && (activity.getOutgoingTransitions() != null) && (activity .getOutgoingTransitions().size() == 1))) { transition = activity.getOutgoingTransitions().get(0); } else { transition = activity.findOutgoingTransition(signalName); } execution.take(transition); return; } else { // 否则继续等待 execution.waitForSignal(); } } }
CountersignUser类:
/** * 每个会签人的信息(可以根据需求写到数据库中) * */ public class CountersignUser implements Serializable { private static final long serialVersionUID = -555010710697671504L; public enum Conclusion implements Serializable { /** 通过 */ AGREE("同意"), /** 否决 */ DENED("不同意"), /** 弃权 */ ABSTAIN("弃权"), /** 还未查阅 */ NOSTART("未查阅"); private String desc; private Conclusion(String desc){ this.desc = desc; } public String getDesc(){ return desc; } } private Integer id;// 主键id private String assignee;// 参与者名字,唯一的 private Conclusion conclusion = Conclusion.NOSTART;// 每个人的选择 private String countersignAgree;// 意见内容 public CountersignUser() { super(); } public CountersignUser(String assignee) { super(); this.assignee = assignee; } public Integer getId() { return id; } public String getCountersignAgree() { return countersignAgree; } public void setCountersignAgree(String countersignAgree) { this.countersignAgree = countersignAgree; } public void setId(Integer id) { this.id = id; } public String getAssignee() { return assignee; } public void setAssignee(String assignee) { this.assignee = assignee; } public Conclusion getConclusion() { return conclusion; } public void setConclusion(Conclusion conclusion) { this.conclusion = conclusion; } }