一步一步学JBPM(12)——JBPM流程历史追踪

来源:互联网 发布:javascript数组方法 编辑:程序博客网 时间:2024/06/16 17:45

JBPM的使用过程中,由于JBPM完全屏蔽了流程内部的细节。所以有时候很难从全局上掌握流行的运行情况。比如你提交一个请求,只知道请求提交了,通常你是不知道提交到那里,也不知道你的请求目前在那个位置。这样必须专门通过程序去查看流程的整体运行情况。查看的方式越简单明了越好。

 

我采用图片的方式,能够显示出流程进过的历史和当前任务所在的节点。方便用户查询。

这个技术分成两个重要部分。第一个是查询当前流程的流程定义图片,将其转换成输出流。第二点是将查询任务经过的节点和当前节点,得到他们的坐标。在html中使用图像标注出来。

 

一:获得流程定义图片。

[java] view plaincopy
  1. public InputStream findProcessInstancePic(String processInstanceId) {  
  2.   
  3.         ProcessInstance processInstance = executionService  
  4.                 .findProcessInstanceById(processInstanceId);  
  5.   
  6.         String processDefinitionId = processInstance.getProcessDefinitionId();  
  7.   
  8.         ProcessDefinition processDefinition = repositoryService  
  9.                 .createProcessDefinitionQuery()  
  10.                 .processDefinitionId(processDefinitionId).uniqueResult();  
  11.         return repositoryService.getResourceAsStream(  
  12.                 processDefinition.getDeploymentId(),  
  13.                 processDefinition.getImageResourceName());  
  14. }  

这个方法是通过流程实例ID获取流程定义,然后将流程定义对应的图片得到。返回输出流。流程定义图片是部署流程的时候和流程定义一起部署到JBPM中的。得到图片以后,在界面使用img标签显示出图片。

[html] view plaincopy
  1. </center>  
  2.         <img src="${ctx}/service/processInstance/pic.do?processInstanceId=${id }" style="position:absolute;left:0px;top:0px;"/>  
  3.         <c:if test="${activityCoordinates!=null }">  
  4.         <div  
  5.             style="position:absolute;border:3px solid red;left:${activityCoordinates.x }px;top:${activityCoordinates.y }px;width:${activityCoordinates.width }px;height:${activityCoordinates.height}px;"></div>  
  6.         </c:if>  
  7.         <c:if test="${ac!=null }">  
  8.         <c:forEach items="${ac }" var="a">  
  9.             <div  
  10.             style="position:absolute;border:3px solid blue;left:${a.x }px;top:${a.y }px;width:${a.width }px;height:${a.height}px;"></div>  
  11.           
  12.         </c:forEach>  
  13.         </c:if>  
  14.     </body>  
  15.   
  16. </html>  

其中

[html] view plaincopy
  1. <imgsrcimgsrc="${ctx}/service/processInstance/pic.do?processInstanceId=${id }"style="position:absolute;left:0px;top:0px;"/>  

请求一个controller显示图片。

controller代码如下:

[java] view plaincopy
  1. /** 
  2.      * 显示流程图片 
  3.      *  
  4.      * @param request 
  5.      * @param response 
  6.      * @param id 
  7.      */  
  8.     @RequestMapping("/service/processInstance/pic.do")  
  9.     public void pic(HttpServletRequest request, HttpServletResponse response,  
  10.             String processInstanceId) {  
  11.         InputStream inputStream = workflowManager  
  12.                 .findProcessInstancePic(processInstanceId);  
  13.         PrintWriter pw = null;  
  14.         if (inputStream == null) {  
  15.             try {  
  16.                 pw = response.getWriter();  
  17.                 pw.write("error");  
  18.             } catch (IOException e) {  
  19.                 e.printStackTrace();  
  20.             } finally {  
  21.                 pw.close();  
  22.             }  
  23.         } else {  
  24.             byte[] b = new byte[1024];  
  25.             int len = -1;  
  26.             ServletOutputStream sos = null;  
  27.             try {  
  28.                 sos = response.getOutputStream();  
  29.                 while ((len = inputStream.read(b, 01024)) != -1) {  
  30.                     sos.write(b, 0, len);  
  31.                 }  
  32.             } catch (IOException e) {  
  33.                 e.printStackTrace();  
  34.             } finally {  
  35.                 if (sos != null) {  
  36.                     try {  
  37.                         sos.close();  
  38.                     } catch (IOException e) {  
  39.                         // TODO Auto-generated catch block  
  40.                         e.printStackTrace();  
  41.                     }  
  42.                 }  
  43.   
  44.             }  
  45.   
  46.         }  
  47.   
  48.     }  

二:显示流程坐标。

首先根据流程实例ID查询出该流程实例进过的节点的名称。然后再在流程定义中查询这些节点的坐标。

[java] view plaincopy
  1. public ActivityCoordinates findActivityCoordinates(String id) {  
  2.   
  3.         ProcessInstance processInstance = executionService  
  4.                 .findProcessInstanceById(id);  
  5.         if (null==processInstance||processInstance.isSuspended()) {  
  6.             return null;  
  7.         }  
  8.         Set<String> activityNames = processInstance.findActiveActivityNames();  
  9.   
  10.         return repositoryService.getActivityCoordinates(processInstance  
  11.                 .getProcessDefinitionId(), activityNames.iterator().next());  
  12.   
  13.     }  

[java] view plaincopy
  1. @Override  
  2.     public List<ActivityCoordinates> findHistoryActivityInfo(String processId) {  
  3.         List<ActivityCoordinates> activityCoordinates = new ArrayList<ActivityCoordinates>();  
  4.         List<HistoryActivityInstance> hisIns = historyService.createHistoryActivityInstanceQuery().processInstanceId(processId).list();  
  5.           
  6.         ProcessInstance processInstance = executionService.findProcessInstanceById(processId);  
  7.         if (null==processInstance||processInstance.isSuspended()) {  
  8.             return null;  
  9.         }  
  10.         for(Iterator<HistoryActivityInstance> iter = hisIns.iterator();iter.hasNext() ; ){  
  11.             activityCoordinates.add(repositoryService.getActivityCoordinates(processInstance.getProcessDefinitionId(), iter.next().getActivityName()));  
  12.         }  
  13.         return activityCoordinates;  
  14.     }  

其中第一个方法是返回当前节点坐标,第二个方法是返回进过节点坐标(包括当前节点,这就需要去掉当前的节点),这个操作在controller中完成,然后返回到页面中。


[java] view plaincopy
  1. /** 
  2.      * 显示流程坐标 
  3.      *  
  4.      * @param request 
  5.      * @param id 
  6.      * @return 
  7.      */  
  8.     @RequestMapping("service/processInstance/view.do")  
  9.     public String view(HttpServletRequest request, String id) {  
  10.   
  11.         // 流程图活动坐标  
  12.         ActivityCoordinates activityCoordinates = workflowManager  
  13.                 .findActivityCoordinates(id);  
  14.         List<ActivityCoordinates> ac = null;  
  15.         if(activityCoordinates != null){  
  16.              ac = workflowManager.findHistoryActivityInfo(id);  
  17.               
  18.             ac.remove(activityCoordinates);  
  19.   
  20.         }  
  21.           
  22.         request.setAttribute("ac", ac);  
  23.         request.setAttribute("activityCoordinates", activityCoordinates);  
  24.         request.setAttribute("id", id);  
  25.         return "/mtdev/module/myflow/image";  
  26.     }  

jsp界面和上面的一样。这里的关键是使用div在图片上标记出节点。给div加上边框,看起来就和图片合在一起一样。

 

下面是效果图。

更好更多地JBPM博客地址:http://blog.csdn.net/lsh6688/article/category/1189610

0 0