工作流的 code review

pull/2/head
YunaiV 2021-11-07 20:25:31 +08:00
parent baab642d28
commit 1bc4bdac0c
7 changed files with 32 additions and 20 deletions

View File

@ -28,6 +28,7 @@ public class LeaveApplyEndProcessor implements ExecutionListener {
final Object approved = delegateExecution.getVariable("approved"); final Object approved = delegateExecution.getVariable("approved");
OALeaveDO updateDo = new OALeaveDO(); OALeaveDO updateDo = new OALeaveDO();
updateDo.setId(Long.valueOf(businessKey)); updateDo.setId(Long.valueOf(businessKey));
// TODO @jason代码的格式哈。} else { 。另外,这里可以简化成,二元表达式
if (Objects.equals(approved, true)) { if (Objects.equals(approved, true)) {
updateDo.setStatus(FlowStatusEnum.PASS.getStatus()); updateDo.setStatus(FlowStatusEnum.PASS.getStatus());
}else{ }else{

View File

@ -26,11 +26,9 @@ import org.springframework.transaction.annotation.Transactional;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import javax.annotation.Resource; import javax.annotation.Resource;
import javax.validation.constraints.NotNull;
import java.util.*; import java.util.*;
import static cn.iocoder.yudao.adminserver.modules.bpm.enums.oa.OAErrorCodeConstants.*; import static cn.iocoder.yudao.adminserver.modules.bpm.enums.oa.OAErrorCodeConstants.*;
import static cn.iocoder.yudao.adminserver.modules.system.enums.SysErrorCodeConstants.POST_CODE_DUPLICATE;
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception; import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
/** /**
@ -116,6 +114,7 @@ public class OALeaveServiceImpl implements OALeaveService {
} }
} }
// TODO @jason要不请假不支持删除只支持取消
@Override @Override
public void deleteLeave(Long id) { public void deleteLeave(Long id) {
// 校验存在 // 校验存在

View File

@ -6,7 +6,7 @@ import cn.iocoder.yudao.framework.common.pojo.PageResult;
import javax.servlet.http.HttpServletResponse; import javax.servlet.http.HttpServletResponse;
import java.util.List; import java.util.List;
// TODO @jason前缀
/** /**
* *
*/ */
@ -25,14 +25,13 @@ public interface TaskService {
*/ */
void claimTask(String taskId); void claimTask(String taskId);
// TODO @jason可以把实现方法的注释统一写到接口里
/** /**
* *
* @param taskReq * @param taskReq
*/ */
void completeTask(TaskReqVO taskReq); void completeTask(TaskReqVO taskReq);
/** /**
* id, * id,
* @param taskQuery taskId * @param taskQuery taskId
@ -45,7 +44,6 @@ public interface TaskService {
*/ */
List<TaskStepVO> getHistorySteps(String processInstanceId); List<TaskStepVO> getHistorySteps(String processInstanceId);
/** /**
* formKey, formKey * formKey, formKey
* @param taskQuery ,taskId * @param taskQuery ,taskId

View File

@ -174,21 +174,24 @@ public class TaskServiceImpl implements TaskService {
public void getHighlightImg(String processInstanceId, HttpServletResponse response) { public void getHighlightImg(String processInstanceId, HttpServletResponse response) {
// 查询历史 // 查询历史
//TODO 云扬四海 貌似流程结束后,点击审批进度会报错 //TODO 云扬四海 貌似流程结束后,点击审批进度会报错
// TODO @Li一些 historyService 的查询,貌似比较通用,是不是抽一些小方法出来
HistoricProcessInstance hpi = historyService.createHistoricProcessInstanceQuery().processInstanceId(processInstanceId).singleResult(); HistoricProcessInstance hpi = historyService.createHistoricProcessInstanceQuery().processInstanceId(processInstanceId).singleResult();
// 如果有结束时间 // 如果有结束时间 TODO @Li如果查询不到是不是抛出一个业务异常比较好哈
if (hpi == null) { if (hpi == null) {
return; return;
} }
// 没有结束时间。说明流程在执行过程中 // 没有结束时间。说明流程在执行过程中
// TODO @Li一些 runtimeService 的查询,貌似比较通用,是不是抽一些小方法出来
ProcessInstance pi = runtimeService.createProcessInstanceQuery().processInstanceId(processInstanceId).singleResult(); ProcessInstance pi = runtimeService.createProcessInstanceQuery().processInstanceId(processInstanceId).singleResult();
BpmnModel bpmnModel = repositoryService.getBpmnModel(pi.getProcessDefinitionId()); BpmnModel bpmnModel = repositoryService.getBpmnModel(pi.getProcessDefinitionId()); // TODO @Li这块和下面的逻辑比较相关可以在后面一点查询。
List<String> highLightedActivities = new ArrayList<>(); List<String> highLightedActivities = new ArrayList<>();
List<HistoricActivityInstance> historicActivityInstances = historyService.createHistoricActivityInstanceQuery().processInstanceId(processInstanceId) List<HistoricActivityInstance> historicActivityInstances = historyService.createHistoricActivityInstanceQuery().processInstanceId(processInstanceId)
.orderByHistoricActivityInstanceId().asc().list(); .orderByHistoricActivityInstanceId().asc().list(); // TODO @Li这块和下面的逻辑比较相关可以在后面一点查询。
// 获取所有活动节点 // 获取所有活动节点
List<HistoricActivityInstance> finishedInstances = historyService.createHistoricActivityInstanceQuery() List<HistoricActivityInstance> finishedInstances = historyService.createHistoricActivityInstanceQuery()
.processInstanceId(processInstanceId).finished().list(); .processInstanceId(processInstanceId).finished().list();
// TODO @LihighLightedActivities 结果,可以使用 CollUtils.buildList() 方法。即使不用,也应该用 stream。简洁很重要。
for (HistoricActivityInstance hai : finishedInstances) { for (HistoricActivityInstance hai : finishedInstances) {
highLightedActivities.add(hai.getActivityId()); highLightedActivities.add(hai.getActivityId());
} }
@ -199,6 +202,7 @@ public class TaskServiceImpl implements TaskService {
List<String> highLightedFlowIds = getHighLightedFlows(bpmnModel, historicActivityInstances); List<String> highLightedFlowIds = getHighLightedFlows(bpmnModel, historicActivityInstances);
//设置"宋体" //设置"宋体"
// TODO @LiService 返回 bytes最终 Controller 去写
try (InputStream inputStream = processDiagramGenerator.generateDiagram(bpmnModel, highLightedActivities, highLightedFlowIds, try (InputStream inputStream = processDiagramGenerator.generateDiagram(bpmnModel, highLightedActivities, highLightedFlowIds,
"宋体", "宋体", "宋体")){ "宋体", "宋体", "宋体")){
String picName = hpi.getProcessDefinitionName()+".svg"; String picName = hpi.getProcessDefinitionName()+".svg";
@ -207,9 +211,9 @@ public class TaskServiceImpl implements TaskService {
} catch (IOException e) { } catch (IOException e) {
log.error(ExceptionUtils.getStackTrace(e)); log.error(ExceptionUtils.getStackTrace(e));
} }
} }
// TODO @Li参考 ServletUtils 方法。如果没有满足的,可以在写一个。
private void responseImage(HttpServletResponse response, InputStream inputStream, String picName) throws IOException { private void responseImage(HttpServletResponse response, InputStream inputStream, String picName) throws IOException {
response.setContentType("application/octet-stream;charset=UTF-8"); response.setContentType("application/octet-stream;charset=UTF-8");
response.setHeader("Content-Disposition", "attachment; filename=" + URLEncoder.encode(picName, "UTF-8")); response.setHeader("Content-Disposition", "attachment; filename=" + URLEncoder.encode(picName, "UTF-8"));
@ -220,6 +224,8 @@ public class TaskServiceImpl implements TaskService {
} }
response.flushBuffer(); response.flushBuffer();
} }
// TODO @Li这个方法的可读性还有一定的优化空间可以思考下哈。
/** /**
* 线 https://blog.csdn.net/qiuxinfa123/article/details/119579863 * 线 https://blog.csdn.net/qiuxinfa123/article/details/119579863
* @see * @see
@ -244,6 +250,7 @@ public class TaskServiceImpl implements TaskService {
} }
} }
// TODO @Li这两个变量直接放到循环里。这种优化一般不需要做的对性能影响超级小。
FlowNode currentFlowNode; FlowNode currentFlowNode;
FlowNode targetFlowNode; FlowNode targetFlowNode;
// 遍历已完成的活动实例从每个实例的outgoingFlows中找到已执行的 // 遍历已完成的活动实例从每个实例的outgoingFlows中找到已执行的
@ -252,11 +259,10 @@ public class TaskServiceImpl implements TaskService {
currentFlowNode = (FlowNode) bpmnModel.getMainProcess().getFlowElement(currentActivityInstance.getActivityId(), true); currentFlowNode = (FlowNode) bpmnModel.getMainProcess().getFlowElement(currentActivityInstance.getActivityId(), true);
List<SequenceFlow> sequenceFlows = currentFlowNode.getOutgoingFlows(); List<SequenceFlow> sequenceFlows = currentFlowNode.getOutgoingFlows();
/** // 遍历outgoingFlows并找到已流转的 满足如下条件认为已已流转:
* outgoingFlows // 1.当前节点是并行网关或兼容网关则通过outgoingFlows能够在历史活动中找到的全部节点均为已流转
* 1.outgoingFlows // 2.当前节点是以上两种类型之外的通过outgoingFlows查找到的时间最早的流转节点视为有效流转
* 2.outgoingFlows // TODO @Li“parallelGateway” 和 "inclusiveGateway",有对应的枚举么?如果木有,可以自己枚举哈
*/
if ("parallelGateway".equals(currentActivityInstance.getActivityType()) || "inclusiveGateway".equals(currentActivityInstance.getActivityType())) { if ("parallelGateway".equals(currentActivityInstance.getActivityType()) || "inclusiveGateway".equals(currentActivityInstance.getActivityType())) {
// 遍历历史活动节点,找到匹配流程目标节点的 // 遍历历史活动节点,找到匹配流程目标节点的
for (SequenceFlow sequenceFlow : sequenceFlows) { for (SequenceFlow sequenceFlow : sequenceFlows) {
@ -266,6 +272,7 @@ public class TaskServiceImpl implements TaskService {
} }
} }
} else { } else {
// TODO @Li如果是为了获取到时间更早的一个是不是遍历的过程中就可以解决
List<Map<String, Object>> tempMapList = new ArrayList<>(); List<Map<String, Object>> tempMapList = new ArrayList<>();
for (SequenceFlow sequenceFlow : sequenceFlows) { for (SequenceFlow sequenceFlow : sequenceFlows) {
for (HistoricActivityInstance historicActivityInstance : historicActivityInstances) { for (HistoricActivityInstance historicActivityInstance : historicActivityInstances) {
@ -283,6 +290,7 @@ public class TaskServiceImpl implements TaskService {
long earliestStamp = 0L; long earliestStamp = 0L;
String highLightedFlowId = null; String highLightedFlowId = null;
for (Map<String, Object> map : tempMapList) { for (Map<String, Object> map : tempMapList) {
// TODO @Li可以使用 MapUtil 去 get 值
long highLightedFlowStartTime = Long.valueOf(map.get("highLightedFlowStartTime").toString()); long highLightedFlowStartTime = Long.valueOf(map.get("highLightedFlowStartTime").toString());
if (earliestStamp == 0 || earliestStamp >= highLightedFlowStartTime) { if (earliestStamp == 0 || earliestStamp >= highLightedFlowStartTime) {
highLightedFlowId = map.get("highLightedFlowId").toString(); highLightedFlowId = map.get("highLightedFlowId").toString();

View File

@ -56,6 +56,7 @@ public interface SysUserMapper extends BaseMapperX<SysUserDO> {
return selectList(new QueryWrapperX<SysUserDO>().like("username", username)); return selectList(new QueryWrapperX<SysUserDO>().like("username", username));
} }
// TODO jason变量平铺比较好
default List<SysUserDO> selectListByBaseVO(SysUserBaseVO reqVO) { default List<SysUserDO> selectListByBaseVO(SysUserBaseVO reqVO) {
return selectList(new QueryWrapperX<SysUserDO>().likeIfPresent("username", reqVO.getUsername()) return selectList(new QueryWrapperX<SysUserDO>().likeIfPresent("username", reqVO.getUsername())
.likeIfPresent("nickname", reqVO.getNickname()) .likeIfPresent("nickname", reqVO.getNickname())

View File

@ -19,6 +19,7 @@
<properties> <properties>
<activiti.version>7.1.0.M6</activiti.version> <activiti.version>7.1.0.M6</activiti.version>
</properties> </properties>
<!-- TODO @jason后续弄到 yudao-dependencies 里 -->
<dependencyManagement> <dependencyManagement>
<dependencies> <dependencies>
<dependency> <dependency>

View File

@ -1,5 +1,6 @@
package cn.iocoder.yudao.framework.activiti.config; package cn.iocoder.yudao.framework.activiti.config;
import lombok.AllArgsConstructor;
import org.activiti.api.runtime.shared.identity.UserGroupManager; import org.activiti.api.runtime.shared.identity.UserGroupManager;
import org.activiti.image.ProcessDiagramGenerator; import org.activiti.image.ProcessDiagramGenerator;
import org.activiti.image.impl.DefaultProcessDiagramGenerator; import org.activiti.image.impl.DefaultProcessDiagramGenerator;
@ -14,24 +15,27 @@ import org.springframework.stereotype.Component;
public class YudaoActivitiConfiguration { public class YudaoActivitiConfiguration {
// TODO @Li可以说明下 ProcessDiagramGenerator 作用
@Bean @Bean
public ProcessDiagramGenerator processDiagramGenerator (){ public ProcessDiagramGenerator processDiagramGenerator (){
return new DefaultProcessDiagramGenerator(); return new DefaultProcessDiagramGenerator();
} }
/**
* ProcessEngineConfigurationConfigurer 使 MyBatis SqlSessionFactory
*/
@Component @Component
@AllArgsConstructor
public static class SqlSessionFactoryProcessEngineConfigurationConfigurer public static class SqlSessionFactoryProcessEngineConfigurationConfigurer
implements ProcessEngineConfigurationConfigurer { implements ProcessEngineConfigurationConfigurer {
private final SqlSessionFactory sqlSessionFactory; private final SqlSessionFactory sqlSessionFactory;
public SqlSessionFactoryProcessEngineConfigurationConfigurer(SqlSessionFactory sessionFactory) {
this.sqlSessionFactory = sessionFactory;
}
@Override @Override
public void configure(SpringProcessEngineConfiguration springProcessEngineConfiguration) { public void configure(SpringProcessEngineConfiguration springProcessEngineConfiguration) {
springProcessEngineConfiguration.setSqlSessionFactory(sqlSessionFactory); springProcessEngineConfiguration.setSqlSessionFactory(sqlSessionFactory);
} }
} }