连线
之前我们做的流程图都是一条线下去,没有任何分支:
有时候一件任务可能要分情况,有些情况需要走一个复杂流程,
有些情况需要走简单流程,就如同一条河的分支一样。例如,
员工请一天以内的假是部门经理直接审批通过,如果要请一天
以上的假期,则需要再由总经理审批之后才能通过,此时就要
分情况。这种情况在流程系统中叫做“连线”。
例图:
我们接下来用一个代码实例来学习“连线”。
首先在我们之前的测试工程的src/main/java下创建一个包:
然后在该包下创建一个流程图:
我们在流程图编辑区域绘制流程图:
然后编辑各个Task节点的名称:
点击空白处,编辑整个流程的信息:
如何判断一个任务完成之后,怎么判断该走哪一个线?
我们点击下面的一条线,填写该线的信息:
另外一个Name类似:
但是这还不是控制分流的地方,我们点击Properties选项
的Main Config来设置:
我们在Condition中防止一个判断语句即可。流程图通过
判断语句来确认自己该走哪一个流程。
保存该流程图。可以看到也生产了png图片:
为了防止我们的bpmn和png格式的文件在src/main/java下编译之后消失,
我们要指定该文件夹下编译之后存在所有格式的文件(原来是只存在java文件):
接下来我们创建一个测试类:
(1)执行部署deploymentProcessDefinition_inputStream方法对我们的流程进行部署:
部署之后,我们可以在部署对象表act_re_deployment中查看到我们的流程信息:
然后可以在流程定义表act_re_procdef中查看我们流程的所有基础信息:
可以在资源文件表act_ge_bytearray中看到我们的资源信息:
看一下我们的bpmn文件,以XML格式打开,我们可以看到,当部门经理
审批完之后,有SequenceFlow进行分支选择,每一个SequenceFlow中都
包裹了自己的流程定义信息:
(2)接下来我们通过我们的Key来启动我们的流程实例,执行startProcessInstance方法:
启动之后,查看正在运行的流程实例表act_ru_execution,可以看到我们的实例:
查看流程实例的历史表act_hi_procinst,也可以看到我们的实例刚刚启动后的历史信息:
查看正在执行的任务表act_ru_task,可以看到我们的待办任务:
可以看到,该部门经理赵六审批了。
查看历史任务表act_hi_taskinst,只有我们刚刚的需要赵六执行的任务信息:
查看活动历史表act_hi_actinst,有start节点和第一个task任务的信息:
(3)查看赵六的待办任务,执行findMyPersonalTask方法:
所以待会我们就要完成id为1604的任务
(4)完成任务
我们完成任务后,可以指定连线信息,这样就可以指定接下来的流程是走“重要”还是“不重要”。
所以我们要修改我们的completeMyPersonalTask方法:
按照我们上面的流程图,我们走“不重要”的时候,是直接到结束节点的,也就是
说我们的流程现在结束了,查看正在运行的流程实例表act_ru_execution发现没有了:
查看流程实例的历史表act_hi_procinst发现End的时间已经有了,说明实例结束了:
查看活动历史表act_hi_actinst,发现刚好走了start节点、审批【部门经理】和End节点:
审批【总经理】和End节点:
最后,我们想查看正在执行的流程变量,可以去act_ru_variables表中查看。
想看历史的流程变量,可以去act_hi_varinst表中查看:
至此,我们的“连线”知识点介绍完毕。
附录:
Activiti流程系统常用表
之前我们做的流程图都是一条线下去,没有任何分支:
有时候一件任务可能要分情况,有些情况需要走一个复杂流程,
有些情况需要走简单流程,就如同一条河的分支一样。例如,
员工请一天以内的假是部门经理直接审批通过,如果要请一天
以上的假期,则需要再由总经理审批之后才能通过,此时就要
分情况。这种情况在流程系统中叫做“连线”。
例图:
我们接下来用一个代码实例来学习“连线”。
首先在我们之前的测试工程的src/main/java下创建一个包:
然后在该包下创建一个流程图:
我们在流程图编辑区域绘制流程图:
然后编辑各个Task节点的名称:
点击空白处,编辑整个流程的信息:
如何判断一个任务完成之后,怎么判断该走哪一个线?
我们点击下面的一条线,填写该线的信息:
另外一个Name类似:
但是这还不是控制分流的地方,我们点击Properties选项
的Main Config来设置:
我们在Condition中防止一个判断语句即可。流程图通过
判断语句来确认自己该走哪一个流程。
保存该流程图。可以看到也生产了png图片:
为了防止我们的bpmn和png格式的文件在src/main/java下编译之后消失,
我们要指定该文件夹下编译之后存在所有格式的文件(原来是只存在java文件):
接下来我们创建一个测试类:
package cn.com.sequenceFlow;
import java.io.InputStream;
import java.util.List;
import org.activiti.engine.ProcessEngine;
import org.activiti.engine.ProcessEngines;
import org.activiti.engine.RepositoryService;
import org.activiti.engine.RuntimeService;
import org.activiti.engine.TaskService;
import org.activiti.engine.repository.Deployment;
import org.activiti.engine.repository.DeploymentBuilder;
import org.activiti.engine.runtime.ProcessInstance;
import org.activiti.engine.task.Task;
import org.junit.Test;
public class SequenceFlowTest {
//获取流程引擎对象
//getDefaultProcessEngine方法内部会自动读取名为activiti.cfg.xml文件的配置信息
ProcessEngine processEngine=ProcessEngines.getDefaultProcessEngine();
/**部署流程定义*/
@Test
public void deploymentProcessDefinition_inputStream(){
//获得上传文件的输入流
InputStream inputStreamBpmn=this.getClass().getResourceAsStream("SequenceFlow.bpmn");
InputStream inputStreamPng=this.getClass().getResourceAsStream("SequenceFlow.png");
//获取仓库服务,从类路径下完成部署
RepositoryService repositoryService=processEngine.getRepositoryService();
DeploymentBuilder deploymentBuilder=repositoryService.createDeployment();//创建一个部署对象
deploymentBuilder.name("连线");//添加部署的名称
deploymentBuilder.addInputStream("SequenceFlow.bpmn", inputStreamBpmn);
deploymentBuilder.addInputStream("SequenceFlow.png", inputStreamPng);
Deployment deployment=deploymentBuilder.deploy();//完成部署
//打印我们的流程信息
System.out.println("部署Id:"+deployment.getId());
System.out.println("部署名称Name:"+deployment.getName());
}
/**启动流程引擎*/
@Test
public void startProcessInstance(){
//获取流程启动Service
RuntimeService runtimeService=processEngine.getRuntimeService();
//使用流程定义的key,key对应bpmn文件对应的id,
//(也是act_re_procdef表中对应的KEY_字段),默认是按照最新版本启动
String processDefinitionkey="sequenceFlow";//流程定义的key就是sequenceFlow
//获取流程实例对象
ProcessInstance processInstance=runtimeService.startProcessInstanceByKey(processDefinitionkey);
System.out.println("流程实例ID:"+processInstance.getId());//流程实例ID
System.out.println("流程定义ID:"+processInstance.getProcessDefinitionId());//流程定义ID
}
/**查询当前的个人任务(实际就是查询act_ru_task表)*/
@Test
public void findMyPersonalTask(){
String assignee="赵六";
//获取事务Service
TaskService taskService=processEngine.getTaskService();
List<Task> taskList=taskService.createTaskQuery()//创建任务查询对象
.taskAssignee(assignee)//指定个人任务查询,指定办理人
.list();//获取该办理人下的事务列表
if(taskList!=null&&taskList.size()>0){
for(Task task:taskList){
System.out.println("任务ID:"+task.getId());
System.out.println("任务名称:"+task.getName());
System.out.println("任务的创建时间:"+task.getCreateTime());
System.out.println("任务办理人:"+task.getAssignee());
System.out.println("流程实例ID:"+task.getProcessInstanceId());
System.out.println("执行对象ID:"+task.getExecutionId());
System.out.println("流程定义ID:"+task.getProcessDefinitionId());
System.out.println("#############################################");
}
}
}
/**完成我的任务*/
@Test
public void completeMyPersonalTask(){
String taskId="";//上一次我们查询的任务ID
TaskService taskService=processEngine.getTaskService();
taskService.complete(taskId);//完成taskId对应的任务
System.out.println("完成ID为"+taskId+"的任务");
}
}
(1)执行部署deploymentProcessDefinition_inputStream方法对我们的流程进行部署:
部署之后,我们可以在部署对象表act_re_deployment中查看到我们的流程信息:
然后可以在流程定义表act_re_procdef中查看我们流程的所有基础信息:
可以在资源文件表act_ge_bytearray中看到我们的资源信息:
看一下我们的bpmn文件,以XML格式打开,我们可以看到,当部门经理
审批完之后,有SequenceFlow进行分支选择,每一个SequenceFlow中都
包裹了自己的流程定义信息:
(2)接下来我们通过我们的Key来启动我们的流程实例,执行startProcessInstance方法:
启动之后,查看正在运行的流程实例表act_ru_execution,可以看到我们的实例:
查看流程实例的历史表act_hi_procinst,也可以看到我们的实例刚刚启动后的历史信息:
查看正在执行的任务表act_ru_task,可以看到我们的待办任务:
可以看到,该部门经理赵六审批了。
查看历史任务表act_hi_taskinst,只有我们刚刚的需要赵六执行的任务信息:
查看活动历史表act_hi_actinst,有start节点和第一个task任务的信息:
(3)查看赵六的待办任务,执行findMyPersonalTask方法:
所以待会我们就要完成id为1604的任务
(4)完成任务
我们完成任务后,可以指定连线信息,这样就可以指定接下来的流程是走“重要”还是“不重要”。
所以我们要修改我们的completeMyPersonalTask方法:
/**完成我的任务*/
@Test
public void completeMyPersonalTask(){
String taskId="1604";//上一次我们查询的任务ID
//完成任务的同时,设置流程变量,使用流程变量用来制定完成任务后,下一个连线,
//对应sequenceFlow.bpmn文件中${message=='不重要'}
Map<String,Object> variables=new HashMap<String,Object>();
variables.put("message", "不重要");
TaskService taskService=processEngine.getTaskService();
taskService.complete(taskId,variables);//完成taskId对应的任务,并附带流程变量
System.out.println("完成ID为"+taskId+"的任务");
}
我们上面的代码是设置的走“不重要”的流程。执行completeMyPersonalTask方法:
按照我们上面的流程图,我们走“不重要”的时候,是直接到结束节点的,也就是
说我们的流程现在结束了,查看正在运行的流程实例表act_ru_execution发现没有了:
查看流程实例的历史表act_hi_procinst发现End的时间已经有了,说明实例结束了:
查看活动历史表act_hi_actinst,发现刚好走了start节点、审批【部门经理】和End节点:
我们重新部署一个流程,版本未2,部署/启动/完成第一个任务的提交之后,流程先到项目经理赵六这里。
我们给赵六的完成方法中的流程变量message设置“重要”:
/**完成我的任务*/
@Test
public void completeMyPersonalTask(){
String taskId="2002";//上一次我们查询的任务ID
//完成任务的同时,设置流程变量,使用流程变量用来制定完成任务后,下一个连线,
//对应sequenceFlow.bpmn文件中${message=='重要'}
Map<String,Object> variables=new HashMap<String,Object>();
variables.put("message", "重要");
TaskService taskService=processEngine.getTaskService();
taskService.complete(taskId,variables);//完成taskId对应的任务,并附带流程变量
System.out.println("完成ID为"+taskId+"的任务");
}
执行该方法。
此时任务流转到总经理田七这里,查看田七的任务,是有的:
此时对于总经理,只需要审批完成任务即可:
/**完成我的任务*/
@Test
public void completeMyPersonalTask(){
String taskId="2003";//任务ID
TaskService taskService=processEngine.getTaskService();
taskService.complete(taskId);//完成taskId对应的任务
System.out.println("完成ID为"+taskId+"的任务");
}
完成后整个流程结束。
再去查看一下活动历史表act_hi_actinst,发现刚好走了start节点、审批【部门经理】、审批【总经理】和End节点:
最后,我们想查看正在执行的流程变量,可以去act_ru_variables表中查看。
想看历史的流程变量,可以去act_hi_varinst表中查看:
至此,我们的“连线”知识点介绍完毕。
附录:
Activiti流程系统常用表
转载请注明出处:http://blog.csdn.net/acmman/article/details/66473148