引入工作流程activiti 6.0

master
pengqiang 2021-11-09 18:45:12 +08:00
parent 4d1efd344d
commit af57e85f8f
6 changed files with 217 additions and 10 deletions

View File

@ -5,6 +5,7 @@ import cn.palmte.work.bean.ResponseMsg;
import cn.palmte.work.model.ActScriptRepository;
import cn.palmte.work.model.ActTaskDef;
import cn.palmte.work.model.AdminRepository;
import cn.palmte.work.pojo.ActHisTask;
import cn.palmte.work.service.ActTaskDefService;
import cn.palmte.work.service.SysRoleService;
import com.alibaba.fastjson.JSON;
@ -88,4 +89,19 @@ public class ActTaskDefController extends BaseController {
actTaskDefService.completeTask(jsonParam);
return ResponseMsg.buildSuccessMsg("处理成功");
}
/**
*
*
* @param procInsId
* @param model
* @return
*/
@RequestMapping("/hisTaskList/{procInsId}")
public String taskList(@PathVariable String procInsId, Map<String, Object> model) {
List<ActHisTask> list = actTaskDefService.hisTaskList(procInsId);
model.put("taskList", list);
return "/admin/act_his_task_list";
}
}

View File

@ -1,7 +1,11 @@
package cn.palmte.work.model;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Modifying;
import org.springframework.data.jpa.repository.Query;
import javax.transaction.Transactional;
import java.util.Date;
import java.util.List;
public interface ActTaskDefRepository extends JpaRepository<ActTaskDef, Integer> {
@ -13,4 +17,19 @@ public interface ActTaskDefRepository extends JpaRepository<ActTaskDef, Integer>
ActTaskDef findFirstByProcDefIdAndTaskKey(String procDefId, String taskKey);
void deleteByProcDefId(String procDefId);
@Modifying
@Transactional
@Query(value = "update ACT_HI_ACTINST a SET a.ASSIGNEE_=? WHERE PROC_INST_ID_=? AND TASK_ID_=?", nativeQuery = true)
int updateHiActAssign(String assign, String procInsId, String taskId);
@Modifying
@Transactional
@Query(value = "update ACT_HI_TASKINST a SET a.ASSIGNEE_=? WHERE PROC_INST_ID_=? AND ID_=?", nativeQuery = true)
int updateHiTaskAssign(String assign, String procInsId, String taskId);
}

View File

@ -0,0 +1,17 @@
package cn.palmte.work.pojo;
import lombok.Data;
import java.util.Date;
@Data
public class ActHisTask {
private String taskId;
private String actName;
private String assign;
private Date startTime;
private Date endTime;
private String duration;
private String comments;
}

View File

@ -3,26 +3,31 @@ package cn.palmte.work.service;
import cn.palmte.work.config.activiti.ActConstant;
import cn.palmte.work.config.activiti.DeleteTaskCommand;
import cn.palmte.work.config.activiti.JumpCommand;
import cn.palmte.work.model.ActScript;
import cn.palmte.work.model.ActScriptRepository;
import cn.palmte.work.model.ActTaskDef;
import cn.palmte.work.model.ActTaskDefRepository;
import cn.palmte.work.model.*;
import cn.palmte.work.pojo.ActHisTask;
import cn.palmte.work.utils.InterfaceUtil;
import com.alibaba.fastjson.JSONObject;
import org.activiti.bpmn.model.FlowNode;
import org.activiti.engine.*;
import org.activiti.engine.task.IdentityLink;
import org.activiti.engine.task.Task;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.data.jpa.repository.Modifying;
import org.springframework.stereotype.Service;
import top.jfunc.common.db.QueryHelper;
import top.jfunc.common.db.bean.Record;
import top.jfunc.common.db.utils.Pagination;
import javax.annotation.Resource;
import javax.persistence.EntityManager;
import javax.transaction.Transactional;
import java.lang.reflect.Method;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
@Service
@ -51,6 +56,8 @@ public class ActTaskDefService {
@Autowired
private ActScriptRepository actScriptRepository;
@Autowired
Pagination pagination;
public List<ActTaskDef> findByProcDefId(String procDefId) {
List<ActTaskDef> list = actTaskDefRepository.findByProcDefId(procDefId);
@ -130,30 +137,35 @@ public class ActTaskDefService {
}
/**
*
*
* @param json
*/
public void completeTask(JSONObject json) {
String taskId = json.getString("taskId");
String procInstId = json.getString("procInsId");
String procInsId = json.getString("procInsId");
String message = json.getString("message");
int type = json.getInteger("type");
taskService.addComment(taskId, procInstId, message);
String userId = InterfaceUtil.getAdminId() + "";
taskService.addComment(taskId, procInsId, message);
actTaskDefRepository.updateHiTaskAssign(userId, procInsId, taskId);
actTaskDefRepository.updateHiActAssign(userId, procInsId, taskId);
Task currentTask = taskService.createTaskQuery().taskId(taskId).singleResult();
ActTaskDef actTaskDef = findFirstByProcDefIdAndTaskKey(currentTask.getProcessDefinitionId(), currentTask.getTaskDefinitionKey());
if (ActConstant.TYPE_APPROVE == type) {
taskService.setAssignee(taskId, userId);
//审批通过
taskService.complete(taskId);
//执行配置的审批通过脚本
int endScript = actTaskDef.getEndScript();
if (endScript != 0) {
invokeEventScript(endScript, procInstId);
invokeEventScript(endScript, procInsId);
} else {
logger.info("未配置审批通过脚本 task:{}", actTaskDef.getTaskName());
}
@ -166,7 +178,7 @@ public class ActTaskDefService {
//执行配置的驳回脚本
int rollbackScript = actTaskDef.getRollbackScript();
if (rollbackScript != 0) {
invokeEventScript(rollbackScript, procInstId);
invokeEventScript(rollbackScript, procInsId);
} else {
logger.info("未配置驳回脚本 task:{}", actTaskDef.getTaskName());
}
@ -174,6 +186,7 @@ public class ActTaskDefService {
}
/**
*
*
@ -237,4 +250,58 @@ public class ActTaskDefService {
taskService.saveTask(singleResult);
}
public List<ActHisTask> hisTaskList(String procIncId) {
String select = "select ht.ID_ as hisInstanceId, ht.PROC_DEF_ID_ as procDefinitionId, ht.PROC_INST_ID_ as procInstanceId, ht.EXECUTION_ID_ as executionId," +
" ht.ACT_ID_ as actId, ht.TASK_ID_ as taskId, ht.CALL_PROC_INST_ID_ as callProcInstanceId, ht.ACT_NAME_ as actName, " +
"ht.ACT_TYPE_ as actType, ht.ASSIGNEE_ as assignee, ht.START_TIME_ as startTime, ht.END_TIME_ as endTime, " +
"ht.DURATION_ as duration, ht.DELETE_REASON_ as deleteReason, ht.TENANT_ID_ as tenantId, hc.MESSAGE_ AS comments";
QueryHelper queryHelper = new QueryHelper(select, " ACT_HI_ACTINST ht " +
" LEFT JOIN ACT_HI_COMMENT hc on ht.TASK_ID_ = hc.TASK_ID_ and hc.type_='comment' ");
queryHelper.addCondition("ht.TASK_ID_ is not null");
queryHelper.addCondition("ht.PROC_INST_ID_ =?", procIncId);
queryHelper.addOrderProperty("ht.start_time_", true);
List<ActHisTask> taskList = pagination.find(queryHelper.getSql(), ActHisTask.class);
for (ActHisTask actHisTask : taskList) {
if (StringUtils.isBlank(actHisTask.getAssign())) {
Task task = taskService.createTaskQuery().taskId(actHisTask.getTaskId()).singleResult();
if (task != null) {
if (StringUtils.isNotBlank(task.getAssignee())) {
actHisTask.setAssign(task.getAssignee());
} else {
List<IdentityLink> identityLinkList = taskService.getIdentityLinksForTask(task.getId());
if (identityLinkList != null && !identityLinkList.isEmpty()) {
String name = "";
for (IdentityLink identityLink : identityLinkList) {
if ("assignee".equals(identityLink.getType()) || "candidate".equals(identityLink.getType())) {
String assigneeUserId = identityLink.getUserId();
if (StringUtils.isNotBlank(name)) {
name = name + ",";
}
name += accountService.getNameById(Integer.parseInt(assigneeUserId));
}
}
actHisTask.setAssign(name);
}
}
}
}
String duration = actHisTask.getDuration();
/*Date startTime = actHisTask.getStartTime();
Date endTime = actHisTask.getEndTime();*/
if (StringUtils.isNotBlank(duration)) {
Long ztime = Long.parseLong(duration);
Long day = ztime / (1000 * 60 * 60 * 24);
Long hour = (ztime % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60);
Long minute = (ztime % (1000 * 60 * 60 * 24)) % (1000 * 60 * 60) / (1000 * 60);
Long second = (ztime % (1000 * 60 * 60 * 24)) % (1000 * 60 * 60) % (1000 * 60) / 1000;
actHisTask.setDuration(day + "天" + hour + "时" + minute + "分" + second + "秒");
} else {
actHisTask.setDuration("正在处理。。。");
}
}
return taskList;
}
}

View File

@ -0,0 +1,81 @@
<#assign base=request.contextPath />
<#import "../common/defaultLayout.ftl" as defaultLayout>
<@defaultLayout.layout>
<link rel="stylesheet" href="${base}/assets/css/amazeui.switch.css"/>
<div class="admin-content">
<div class="am-cf am-padding" style="padding:1rem 1.6rem 1.6rem 1rem;margin:0px;">
<!-- padding:1px 2px 3px 4px;上、右、下,和左 -->
<div class="am-fl am-cf"><strong class="am-text-primary am-text-lg">工作流程</strong> /
<small>审批过程</small>
</div>
</div>
<div class="am-g">
<div class="am-u-sm-12 am-scrollable-horizontal">
<!-- padding:1px 2px 3px 4px;上、右、下,和左 -->
<table class="am-table am-table-striped am-table-hover table-main">
<thead>
<tr class="am-text-nowrap">
<th class="table-title">序号</th>
<th class="table-title">任务节点</th>
<th class="table-title">办理人</th>
<th class="table-date">审批开始时间</th>
<th class="table-date">审批结束时间</th>
<th class="table-date">用时</th>
<th class="table-set am-text-center">审批意见</th>
</tr>
</thead>
<tbody>
<#if (taskList)?exists>
<#list taskList as list>
<tr>
<td>${list_index+1!}</td>
<td>${list.actName!}</td>
<td>${list.assign!}</td>
<td>${list.startTime?datetime}</td>
<td><#if list.endTime??>
${list.endTime?datetime}
</#if></td>
<td>${list.duration!}</td>
<td>${list.comments!}</td>
</tr>
</#list>
</#if>
</tbody>
</table>
<div class="am-cf">
<!-- 分页 -->
<#if (pager.list)?exists && (pager.list?size>0) >
<div class="am-fr">
<#include "../common/common_pager.ftl">
</div>
<#else>
<div class="am-kai" align="center">
<h3>没有找到任何记录!</h3>
</div>
</#if>
</div>
</div>
</div>
<div class="am-margin">
<#--<button type="submit" class="am-btn am-btn-primary am-btn-xs">提交保存</button>-->
<button type="button" class="am-btn am-btn-warning am-btn-xs"
onclick="location.href='${base}/actProcIns/list'">返回
</button>
</div>
</div>
</@defaultLayout.layout>
<script src="${base}/assets/js/amazeui.switch.js"></script>
<script type="text/javascript">
var urlBase = "${base}";
var url;
$(function () {
});
</script>

View File

@ -67,9 +67,16 @@
class="am-btn am-btn-default am-btn-xs am-text-secondary"
onclick="window.open('${base}/actProcIns/procInsPng/${list.procInsId!}')">
<span class="am-icon-pencil-square-o"></span>
流程图
流程图
</button>
<button type="button"
class="am-btn am-btn-default am-btn-xs am-text-secondary"
onclick="location.href='${base}/actTaskDef/hisTaskList/${list.procInsId}'">
<span class="am-icon-pencil-square-o"></span>
审批过程
</button>
</#if>
</td>