Commit b98421dfc620046a01949c6836db8914012fee01

Authored by YunaiV
1 parent 040a1bcf

【代码评审】工作流:抄送的实现逻辑

yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/convert/task/BpmTaskConvert.java
@@ -113,6 +113,7 @@ public interface BpmTaskConvert { @@ -113,6 +113,7 @@ public interface BpmTaskConvert {
113 } 113 }
114 if (BpmTaskStatusEnum.RUNNING.getStatus().equals(taskStatus)){ 114 if (BpmTaskStatusEnum.RUNNING.getStatus().equals(taskStatus)){
115 // 设置表单权限 TODO @芋艿 是不是还要加一个全局的权限 基于 processInstance 的权限;回复:可能不需要,但是发起人,需要有个权限配置 115 // 设置表单权限 TODO @芋艿 是不是还要加一个全局的权限 基于 processInstance 的权限;回复:可能不需要,但是发起人,需要有个权限配置
  116 + // TODO @jason:貌似这么返回,主要解决当前审批 task 的表单权限,但是不同抄送人的表单权限,可能不太对。例如说,对 A 抄送人是隐藏某个字段。
116 taskVO.setFieldsPermission(BpmnModelUtils.parseFormFieldsPermission(bpmnModel, task.getTaskDefinitionKey())); 117 taskVO.setFieldsPermission(BpmnModelUtils.parseFormFieldsPermission(bpmnModel, task.getTaskDefinitionKey()));
117 // 操作按钮设置 118 // 操作按钮设置
118 taskVO.setButtonsSetting(BpmnModelUtils.parseButtonsSetting(bpmnModel, task.getTaskDefinitionKey())); 119 taskVO.setButtonsSetting(BpmnModelUtils.parseButtonsSetting(bpmnModel, task.getTaskDefinitionKey()));
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/framework/flowable/core/enums/BpmConstants.java renamed to yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/framework/flowable/core/enums/BpmnVariableConstants.java
@@ -3,11 +3,11 @@ package cn.iocoder.yudao.module.bpm.framework.flowable.core.enums; @@ -3,11 +3,11 @@ package cn.iocoder.yudao.module.bpm.framework.flowable.core.enums;
3 import org.flowable.engine.runtime.ProcessInstance; 3 import org.flowable.engine.runtime.ProcessInstance;
4 4
5 /** 5 /**
6 - * BPM 通用常量 6 + * BPM Variable 通用常量
7 * 7 *
8 * @author 芋道源码 8 * @author 芋道源码
9 */ 9 */
10 -public class BpmConstants { 10 +public class BpmnVariableConstants {
11 11
12 /** 12 /**
13 * 流程实例的变量 - 状态 13 * 流程实例的变量 - 状态
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/framework/flowable/core/enums/SimpleModelConstants.java
1 package cn.iocoder.yudao.module.bpm.framework.flowable.core.enums; 1 package cn.iocoder.yudao.module.bpm.framework.flowable.core.enums;
2 2
  3 +// TODO @jason:要不合并到 BpmnModelConstants 那
3 /** 4 /**
4 * 仿钉钉快搭 JSON 常量信息 5 * 仿钉钉快搭 JSON 常量信息
5 * 6 *
@@ -7,12 +8,6 @@ package cn.iocoder.yudao.module.bpm.framework.flowable.core.enums; @@ -7,12 +8,6 @@ package cn.iocoder.yudao.module.bpm.framework.flowable.core.enums;
7 */ 8 */
8 public interface SimpleModelConstants { 9 public interface SimpleModelConstants {
9 10
10 - // TODO @芋艿:审批方式的名字,可能要看下;  
11 - /**  
12 - * 审批方式属性  
13 - */  
14 - String APPROVE_METHOD_ATTRIBUTE = "approveMethod";  
15 -  
16 // TODO @芋艿:条件表达式的字段名 11 // TODO @芋艿:条件表达式的字段名
17 12
18 /** 13 /**
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/framework/flowable/core/custom/delegate/BpmCopyTaskDelegate.java renamed to yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/framework/flowable/core/listener/BpmCopyTaskDelegate.java
1 -package cn.iocoder.yudao.module.bpm.framework.flowable.core.custom.delegate; 1 +package cn.iocoder.yudao.module.bpm.framework.flowable.core.listener;
2 2
3 import cn.hutool.core.collection.CollUtil; 3 import cn.hutool.core.collection.CollUtil;
4 import cn.iocoder.yudao.module.bpm.framework.flowable.core.candidate.BpmTaskCandidateInvoker; 4 import cn.iocoder.yudao.module.bpm.framework.flowable.core.candidate.BpmTaskCandidateInvoker;
@@ -11,13 +11,19 @@ import org.springframework.stereotype.Component; @@ -11,13 +11,19 @@ import org.springframework.stereotype.Component;
11 11
12 import java.util.Set; 12 import java.util.Set;
13 13
  14 +import static cn.iocoder.yudao.module.bpm.framework.flowable.core.listener.BpmCopyTaskDelegate.BEAN_NAME;
  15 +
14 /** 16 /**
15 * 处理抄送用户的 {@link JavaDelegate} 的实现类 17 * 处理抄送用户的 {@link JavaDelegate} 的实现类
16 * 18 *
  19 + * 目前只有快搭模式的【抄送节点】使用
  20 + *
17 * @author jason 21 * @author jason
18 */ 22 */
19 -@Component  
20 -public class BpmCopyTaskDelegate implements JavaDelegate { 23 +@Component(BEAN_NAME)
  24 +public class BpmCopyTaskDelegate implements JavaDelegate {
  25 +
  26 + public static final String BEAN_NAME = "bpmCopyTaskDelegate";
21 27
22 @Resource 28 @Resource
23 private BpmTaskCandidateInvoker taskCandidateInvoker; 29 private BpmTaskCandidateInvoker taskCandidateInvoker;
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/framework/flowable/core/util/FlowableUtils.java
@@ -3,7 +3,7 @@ package cn.iocoder.yudao.module.bpm.framework.flowable.core.util; @@ -3,7 +3,7 @@ package cn.iocoder.yudao.module.bpm.framework.flowable.core.util;
3 import cn.hutool.core.util.ObjectUtil; 3 import cn.hutool.core.util.ObjectUtil;
4 import cn.iocoder.yudao.framework.tenant.core.context.TenantContextHolder; 4 import cn.iocoder.yudao.framework.tenant.core.context.TenantContextHolder;
5 import cn.iocoder.yudao.framework.tenant.core.util.TenantUtils; 5 import cn.iocoder.yudao.framework.tenant.core.util.TenantUtils;
6 -import cn.iocoder.yudao.module.bpm.framework.flowable.core.enums.BpmConstants; 6 +import cn.iocoder.yudao.module.bpm.framework.flowable.core.enums.BpmnVariableConstants;
7 import org.flowable.common.engine.api.delegate.Expression; 7 import org.flowable.common.engine.api.delegate.Expression;
8 import org.flowable.common.engine.api.variable.VariableContainer; 8 import org.flowable.common.engine.api.variable.VariableContainer;
9 import org.flowable.common.engine.impl.el.ExpressionManager; 9 import org.flowable.common.engine.impl.el.ExpressionManager;
@@ -91,7 +91,7 @@ public class FlowableUtils { @@ -91,7 +91,7 @@ public class FlowableUtils {
91 * @return 状态 91 * @return 状态
92 */ 92 */
93 private static Integer getProcessInstanceStatus(Map<String, Object> processVariables) { 93 private static Integer getProcessInstanceStatus(Map<String, Object> processVariables) {
94 - return (Integer) processVariables.get(BpmConstants.PROCESS_INSTANCE_VARIABLE_STATUS); 94 + return (Integer) processVariables.get(BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_STATUS);
95 } 95 }
96 96
97 /** 97 /**
@@ -115,7 +115,7 @@ public class FlowableUtils { @@ -115,7 +115,7 @@ public class FlowableUtils {
115 * @return 过滤后的表单 115 * @return 过滤后的表单
116 */ 116 */
117 public static Map<String, Object> filterProcessInstanceFormVariable(Map<String, Object> processVariables) { 117 public static Map<String, Object> filterProcessInstanceFormVariable(Map<String, Object> processVariables) {
118 - processVariables.remove(BpmConstants.PROCESS_INSTANCE_VARIABLE_STATUS); 118 + processVariables.remove(BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_STATUS);
119 return processVariables; 119 return processVariables;
120 } 120 }
121 121
@@ -128,7 +128,7 @@ public class FlowableUtils { @@ -128,7 +128,7 @@ public class FlowableUtils {
128 @SuppressWarnings("unchecked") 128 @SuppressWarnings("unchecked")
129 public static Map<String, List<Long>> getStartUserSelectAssignees(ProcessInstance processInstance) { 129 public static Map<String, List<Long>> getStartUserSelectAssignees(ProcessInstance processInstance) {
130 return (Map<String, List<Long>>) processInstance.getProcessVariables().get( 130 return (Map<String, List<Long>>) processInstance.getProcessVariables().get(
131 - BpmConstants.PROCESS_INSTANCE_VARIABLE_START_USER_SELECT_ASSIGNEES); 131 + BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_START_USER_SELECT_ASSIGNEES);
132 } 132 }
133 133
134 // ========== Task 相关的工具方法 ========== 134 // ========== Task 相关的工具方法 ==========
@@ -140,7 +140,7 @@ public class FlowableUtils { @@ -140,7 +140,7 @@ public class FlowableUtils {
140 * @return 状态 140 * @return 状态
141 */ 141 */
142 public static Integer getTaskStatus(TaskInfo task) { 142 public static Integer getTaskStatus(TaskInfo task) {
143 - return (Integer) task.getTaskLocalVariables().get(BpmConstants.TASK_VARIABLE_STATUS); 143 + return (Integer) task.getTaskLocalVariables().get(BpmnVariableConstants.TASK_VARIABLE_STATUS);
144 } 144 }
145 145
146 /** 146 /**
@@ -150,7 +150,7 @@ public class FlowableUtils { @@ -150,7 +150,7 @@ public class FlowableUtils {
150 * @return 审批原因 150 * @return 审批原因
151 */ 151 */
152 public static String getTaskReason(TaskInfo task) { 152 public static String getTaskReason(TaskInfo task) {
153 - return (String) task.getTaskLocalVariables().get(BpmConstants.TASK_VARIABLE_REASON); 153 + return (String) task.getTaskLocalVariables().get(BpmnVariableConstants.TASK_VARIABLE_REASON);
154 } 154 }
155 155
156 /** 156 /**
@@ -174,8 +174,8 @@ public class FlowableUtils { @@ -174,8 +174,8 @@ public class FlowableUtils {
174 * @return 过滤后的表单 174 * @return 过滤后的表单
175 */ 175 */
176 public static Map<String, Object> filterTaskFormVariable(Map<String, Object> taskLocalVariables) { 176 public static Map<String, Object> filterTaskFormVariable(Map<String, Object> taskLocalVariables) {
177 - taskLocalVariables.remove(BpmConstants.TASK_VARIABLE_STATUS);  
178 - taskLocalVariables.remove(BpmConstants.TASK_VARIABLE_REASON); 177 + taskLocalVariables.remove(BpmnVariableConstants.TASK_VARIABLE_STATUS);
  178 + taskLocalVariables.remove(BpmnVariableConstants.TASK_VARIABLE_REASON);
179 return taskLocalVariables; 179 return taskLocalVariables;
180 } 180 }
181 181
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/framework/flowable/core/util/SimpleModelUtils.java
@@ -11,6 +11,7 @@ import cn.iocoder.yudao.module.bpm.controller.admin.definition.vo.model.simple.B @@ -11,6 +11,7 @@ import cn.iocoder.yudao.module.bpm.controller.admin.definition.vo.model.simple.B
11 import cn.iocoder.yudao.module.bpm.controller.admin.definition.vo.model.simple.BpmSimpleModelNodeVO.RejectHandler; 11 import cn.iocoder.yudao.module.bpm.controller.admin.definition.vo.model.simple.BpmSimpleModelNodeVO.RejectHandler;
12 import cn.iocoder.yudao.module.bpm.enums.definition.*; 12 import cn.iocoder.yudao.module.bpm.enums.definition.*;
13 import cn.iocoder.yudao.module.bpm.framework.flowable.core.enums.BpmnModelConstants; 13 import cn.iocoder.yudao.module.bpm.framework.flowable.core.enums.BpmnModelConstants;
  14 +import cn.iocoder.yudao.module.bpm.framework.flowable.core.listener.BpmCopyTaskDelegate;
14 import cn.iocoder.yudao.module.bpm.framework.flowable.core.simplemodel.SimpleModelConditionGroups; 15 import cn.iocoder.yudao.module.bpm.framework.flowable.core.simplemodel.SimpleModelConditionGroups;
15 import org.flowable.bpmn.BpmnAutoLayout; 16 import org.flowable.bpmn.BpmnAutoLayout;
16 import org.flowable.bpmn.model.Process; 17 import org.flowable.bpmn.model.Process;
@@ -277,20 +278,22 @@ public class SimpleModelUtils { @@ -277,20 +278,22 @@ public class SimpleModelUtils {
277 private static List<FlowElement> buildFlowNode(BpmSimpleModelNodeVO node, BpmSimpleModelNodeType nodeType) { 278 private static List<FlowElement> buildFlowNode(BpmSimpleModelNodeVO node, BpmSimpleModelNodeType nodeType) {
278 List<FlowElement> list = new ArrayList<>(); 279 List<FlowElement> list = new ArrayList<>();
279 switch (nodeType) { 280 switch (nodeType) {
280 - case START_NODE: {  
281 - // @芋艿 改成 convert 是不是好理解一点 281 + case START_NODE: { // 开始节点
282 StartEvent startEvent = convertStartNode(node); 282 StartEvent startEvent = convertStartNode(node);
283 list.add(startEvent); 283 list.add(startEvent);
284 break; 284 break;
285 } 285 }
286 - case APPROVE_NODE: {  
287 - // TODO @芋艿 改成 convertXXXNode, , 方面里面使用 buildBpmnXXXNode. 是否更好理解  
288 - // 转换审批节点 286 + case END_NODE: { // 结束节点
  287 + EndEvent endEvent = convertEndNode(node);
  288 + list.add(endEvent);
  289 + break;
  290 + }
  291 + case APPROVE_NODE: { // 审批节点
289 List<FlowElement> flowElements = convertApproveNode(node); 292 List<FlowElement> flowElements = convertApproveNode(node);
290 list.addAll(flowElements); 293 list.addAll(flowElements);
291 break; 294 break;
292 } 295 }
293 - case COPY_NODE: { 296 + case COPY_NODE: { // 抄送节点
294 ServiceTask serviceTask = convertCopyNode(node); 297 ServiceTask serviceTask = convertCopyNode(node);
295 list.add(serviceTask); 298 list.add(serviceTask);
296 break; 299 break;
@@ -316,11 +319,6 @@ public class SimpleModelUtils { @@ -316,11 +319,6 @@ public class SimpleModelUtils {
316 list.add(inclusiveGateway); 319 list.add(inclusiveGateway);
317 break; 320 break;
318 } 321 }
319 - case END_NODE: {  
320 - EndEvent endEvent = convertEndNode(node);  
321 - list.add(endEvent);  
322 - break;  
323 - }  
324 default: { 322 default: {
325 // TODO 其它节点类型的实现 323 // TODO 其它节点类型的实现
326 } 324 }
@@ -389,13 +387,11 @@ public class SimpleModelUtils { @@ -389,13 +387,11 @@ public class SimpleModelUtils {
389 serviceTask.setId(node.getId()); 387 serviceTask.setId(node.getId());
390 serviceTask.setName(node.getName()); 388 serviceTask.setName(node.getName());
391 serviceTask.setImplementationType(ImplementationType.IMPLEMENTATION_TYPE_DELEGATEEXPRESSION); 389 serviceTask.setImplementationType(ImplementationType.IMPLEMENTATION_TYPE_DELEGATEEXPRESSION);
392 - serviceTask.setImplementation("${bpmCopyTaskDelegate}"); 390 + serviceTask.setImplementation("${" + BpmCopyTaskDelegate.BEAN_NAME + "}");
393 391
394 // 添加抄送候选人元素 392 // 添加抄送候选人元素
395 addCandidateElements(node.getCandidateStrategy(), node.getCandidateParam(), serviceTask); 393 addCandidateElements(node.getCandidateStrategy(), node.getCandidateParam(), serviceTask);
396 -  
397 // 添加表单字段权限属性元素 394 // 添加表单字段权限属性元素
398 - // TODO @芋艿:这块关注下哈;  
399 addFormFieldsPermission(node.getFieldsPermission(), serviceTask); 395 addFormFieldsPermission(node.getFieldsPermission(), serviceTask);
400 return serviceTask; 396 return serviceTask;
401 } 397 }
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/service/task/BpmProcessInstanceServiceImpl.java
1 -package cn.iocoder.yudao.module.bpm.service.task; import cn.hutool.core.collection.CollUtil; import cn.hutool.core.util.ArrayUtil; import cn.hutool.core.util.StrUtil; import cn.iocoder.yudao.framework.common.pojo.PageResult; import cn.iocoder.yudao.framework.common.util.date.DateUtils; import cn.iocoder.yudao.framework.common.util.object.PageUtils; import cn.iocoder.yudao.module.bpm.api.task.dto.BpmProcessInstanceCreateReqDTO; import cn.iocoder.yudao.module.bpm.controller.admin.task.vo.instance.BpmProcessInstanceCancelReqVO; import cn.iocoder.yudao.module.bpm.controller.admin.task.vo.instance.BpmProcessInstanceCreateReqVO; import cn.iocoder.yudao.module.bpm.controller.admin.task.vo.instance.BpmProcessInstancePageReqVO; import cn.iocoder.yudao.module.bpm.convert.task.BpmProcessInstanceConvert; import cn.iocoder.yudao.module.bpm.enums.task.BpmProcessInstanceStatusEnum; import cn.iocoder.yudao.module.bpm.enums.task.BpmReasonEnum; import cn.iocoder.yudao.module.bpm.framework.flowable.core.candidate.strategy.BpmTaskCandidateStartUserSelectStrategy; import cn.iocoder.yudao.module.bpm.framework.flowable.core.enums.BpmConstants; import cn.iocoder.yudao.module.bpm.framework.flowable.core.event.BpmProcessInstanceEventPublisher; import cn.iocoder.yudao.module.bpm.framework.flowable.core.util.FlowableUtils; import cn.iocoder.yudao.module.bpm.service.definition.BpmProcessDefinitionService; import cn.iocoder.yudao.module.bpm.service.message.BpmMessageService; import cn.iocoder.yudao.module.system.api.user.AdminUserApi; import cn.iocoder.yudao.module.system.api.user.dto.AdminUserRespDTO; import jakarta.annotation.Resource; import jakarta.validation.Valid; import lombok.extern.slf4j.Slf4j; import org.flowable.bpmn.model.BpmnModel; import org.flowable.bpmn.model.UserTask; import org.flowable.engine.HistoryService; import org.flowable.engine.RuntimeService; import org.flowable.engine.history.HistoricProcessInstance; import org.flowable.engine.history.HistoricProcessInstanceQuery; import org.flowable.engine.repository.ProcessDefinition; import org.flowable.engine.runtime.ProcessInstance; import org.springframework.context.annotation.Lazy; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import org.springframework.validation.annotation.Validated; import java.util.*; import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception; import static cn.iocoder.yudao.module.bpm.enums.ErrorCodeConstants.*; /** * 流程实例 Service 实现类 * * ProcessDefinition & ProcessInstance & Execution & Task 的关系: * 1. <a href="https://blog.csdn.net/bobozai86/article/details/105210414" /> * * HistoricProcessInstance & ProcessInstance 的关系: * 1. <a href=" https://my.oschina.net/843294669/blog/71902" /> * * 简单来说,前者 = 历史 + 运行中的流程实例,后者仅是运行中的流程实例 * * @author 芋道源码 */ @Service @Validated @Slf4j public class BpmProcessInstanceServiceImpl implements BpmProcessInstanceService { @Resource private RuntimeService runtimeService; @Resource private HistoryService historyService; @Resource private BpmProcessDefinitionService processDefinitionService; @Resource @Lazy // 避免循环依赖 private BpmTaskService taskService; @Resource private BpmMessageService messageService; @Resource private AdminUserApi adminUserApi; @Resource private BpmProcessInstanceEventPublisher processInstanceEventPublisher; // ========== Query 查询相关方法 ========== @Override public ProcessInstance getProcessInstance(String id) { return runtimeService.createProcessInstanceQuery() .includeProcessVariables() .processInstanceId(id) .singleResult(); } @Override public List<ProcessInstance> getProcessInstances(Set<String> ids) { return runtimeService.createProcessInstanceQuery().processInstanceIds(ids).list(); } @Override public HistoricProcessInstance getHistoricProcessInstance(String id) { return historyService.createHistoricProcessInstanceQuery().processInstanceId(id).includeProcessVariables().singleResult(); } @Override public List<HistoricProcessInstance> getHistoricProcessInstances(Set<String> ids) { return historyService.createHistoricProcessInstanceQuery().processInstanceIds(ids).list(); } @Override public PageResult<HistoricProcessInstance> getProcessInstancePage(Long userId, BpmProcessInstancePageReqVO pageReqVO) { // 通过 BpmProcessInstanceExtDO 表,先查询到对应的分页 HistoricProcessInstanceQuery processInstanceQuery = historyService.createHistoricProcessInstanceQuery() .includeProcessVariables() .processInstanceTenantId(FlowableUtils.getTenantId()) .orderByProcessInstanceStartTime().desc(); if (userId != null) { // 【我的流程】菜单时,需要传递该字段 processInstanceQuery.startedBy(String.valueOf(userId)); } else if (pageReqVO.getStartUserId() != null) { // 【管理流程】菜单时,才会传递该字段 processInstanceQuery.startedBy(String.valueOf(pageReqVO.getStartUserId())); } if (StrUtil.isNotEmpty(pageReqVO.getName())) { processInstanceQuery.processInstanceNameLike("%" + pageReqVO.getName() + "%"); } if (StrUtil.isNotEmpty(pageReqVO.getProcessDefinitionId())) { processInstanceQuery.processDefinitionId("%" + pageReqVO.getProcessDefinitionId() + "%"); } if (StrUtil.isNotEmpty(pageReqVO.getCategory())) { processInstanceQuery.processDefinitionCategory(pageReqVO.getCategory()); } if (pageReqVO.getStatus() != null) { processInstanceQuery.variableValueEquals(BpmConstants.PROCESS_INSTANCE_VARIABLE_STATUS, pageReqVO.getStatus()); } if (ArrayUtil.isNotEmpty(pageReqVO.getCreateTime())) { processInstanceQuery.startedAfter(DateUtils.of(pageReqVO.getCreateTime()[0])); processInstanceQuery.startedBefore(DateUtils.of(pageReqVO.getCreateTime()[1])); } // 查询数量 long processInstanceCount = processInstanceQuery.count(); if (processInstanceCount == 0) { return PageResult.empty(processInstanceCount); } // 查询列表 List<HistoricProcessInstance> processInstanceList = processInstanceQuery.listPage(PageUtils.getStart(pageReqVO), pageReqVO.getPageSize()); return new PageResult<>(processInstanceList, processInstanceCount); } // ========== Update 写入相关方法 ========== @Override @Transactional(rollbackFor = Exception.class) public String createProcessInstance(Long userId, @Valid BpmProcessInstanceCreateReqVO createReqVO) { // 获得流程定义 ProcessDefinition definition = processDefinitionService.getProcessDefinition(createReqVO.getProcessDefinitionId()); // 发起流程 return createProcessInstance0(userId, definition, createReqVO.getVariables(), null, createReqVO.getStartUserSelectAssignees()); } @Override public String createProcessInstance(Long userId, @Valid BpmProcessInstanceCreateReqDTO createReqDTO) { // 获得流程定义 ProcessDefinition definition = processDefinitionService.getActiveProcessDefinition(createReqDTO.getProcessDefinitionKey()); // 发起流程 return createProcessInstance0(userId, definition, createReqDTO.getVariables(), createReqDTO.getBusinessKey(), createReqDTO.getStartUserSelectAssignees()); } private String createProcessInstance0(Long userId, ProcessDefinition definition, Map<String, Object> variables, String businessKey, Map<String, List<Long>> startUserSelectAssignees) { // 1.1 校验流程定义 if (definition == null) { throw exception(PROCESS_DEFINITION_NOT_EXISTS); } if (definition.isSuspended()) { throw exception(PROCESS_DEFINITION_IS_SUSPENDED); } // 1.2 校验发起人自选审批人 validateStartUserSelectAssignees(definition, startUserSelectAssignees); // 2. 创建流程实例 if (variables == null) { variables = new HashMap<>(); } FlowableUtils.filterProcessInstanceFormVariable(variables); // 过滤一下,避免 ProcessInstance 系统级的变量被占用 variables.put(BpmConstants.PROCESS_INSTANCE_VARIABLE_STATUS, // 流程实例状态:审批中 BpmProcessInstanceStatusEnum.RUNNING.getStatus()); if (CollUtil.isNotEmpty(startUserSelectAssignees)) { variables.put(BpmConstants.PROCESS_INSTANCE_VARIABLE_START_USER_SELECT_ASSIGNEES, startUserSelectAssignees); } ProcessInstance instance = runtimeService.createProcessInstanceBuilder() .processDefinitionId(definition.getId()) .businessKey(businessKey) .name(definition.getName().trim()) .variables(variables) .start(); return instance.getId(); } private void validateStartUserSelectAssignees(ProcessDefinition definition, Map<String, List<Long>> startUserSelectAssignees) { // 1. 获得发起人自选审批人的 UserTask 列表 BpmnModel bpmnModel = processDefinitionService.getProcessDefinitionBpmnModel(definition.getId()); List<UserTask> userTaskList = BpmTaskCandidateStartUserSelectStrategy.getStartUserSelectUserTaskList(bpmnModel); if (CollUtil.isEmpty(userTaskList)) { return; } // 2. 校验发起人自选审批人的 UserTask 是否都配置了 userTaskList.forEach(userTask -> { List<Long> assignees = startUserSelectAssignees != null ? startUserSelectAssignees.get(userTask.getId()) : null; if (CollUtil.isEmpty(assignees)) { throw exception(PROCESS_INSTANCE_START_USER_SELECT_ASSIGNEES_NOT_CONFIG, userTask.getName()); } Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(assignees); assignees.forEach(assignee -> { if (userMap.get(assignee) == null) { throw exception(PROCESS_INSTANCE_START_USER_SELECT_ASSIGNEES_NOT_EXISTS, userTask.getName(), assignee); } }); }); } @Override public void cancelProcessInstanceByStartUser(Long userId, @Valid BpmProcessInstanceCancelReqVO cancelReqVO) { // 1.1 校验流程实例存在 ProcessInstance instance = getProcessInstance(cancelReqVO.getId()); if (instance == null) { throw exception(PROCESS_INSTANCE_CANCEL_FAIL_NOT_EXISTS); } // 1.2 只能取消自己的 if (!Objects.equals(instance.getStartUserId(), String.valueOf(userId))) { throw exception(PROCESS_INSTANCE_CANCEL_FAIL_NOT_SELF); } // 2. 取消流程 updateProcessInstanceCancel(cancelReqVO.getId(), BpmReasonEnum.CANCEL_PROCESS_INSTANCE_BY_START_USER.format(cancelReqVO.getReason())); } @Override public void cancelProcessInstanceByAdmin(Long userId, BpmProcessInstanceCancelReqVO cancelReqVO) { // 1.1 校验流程实例存在 ProcessInstance instance = getProcessInstance(cancelReqVO.getId()); if (instance == null) { throw exception(PROCESS_INSTANCE_CANCEL_FAIL_NOT_EXISTS); } // 2. 取消流程 AdminUserRespDTO user = adminUserApi.getUser(userId); updateProcessInstanceCancel(cancelReqVO.getId(), BpmReasonEnum.CANCEL_PROCESS_INSTANCE_BY_ADMIN.format(user.getNickname(), cancelReqVO.getReason())); } private void updateProcessInstanceCancel(String id, String reason) { // 1. 更新流程实例 status runtimeService.setVariable(id, BpmConstants.PROCESS_INSTANCE_VARIABLE_STATUS, BpmProcessInstanceStatusEnum.CANCEL.getStatus()); runtimeService.setVariable(id, BpmConstants.PROCESS_INSTANCE_VARIABLE_REASON, reason); // 2. 结束流程 taskService.moveTaskToEnd(id); } @Override public void updateProcessInstanceReject(ProcessInstance processInstance, String reason) { runtimeService.setVariable(processInstance.getProcessInstanceId(), BpmConstants.PROCESS_INSTANCE_VARIABLE_STATUS, BpmProcessInstanceStatusEnum.REJECT.getStatus()); runtimeService.setVariable(processInstance.getProcessInstanceId(), BpmConstants.PROCESS_INSTANCE_VARIABLE_REASON, BpmReasonEnum.REJECT_TASK.format(reason)); } // ========== Event 事件相关方法 ========== @Override public void processProcessInstanceCompleted(ProcessInstance instance) { // 注意:需要基于 instance 设置租户编号,避免 Flowable 内部异步时,丢失租户编号 FlowableUtils.execute(instance.getTenantId(), () -> { // 1.1 获取当前状态 Integer status = (Integer) instance.getProcessVariables().get(BpmConstants.PROCESS_INSTANCE_VARIABLE_STATUS); String reason = (String) instance.getProcessVariables().get(BpmConstants.PROCESS_INSTANCE_VARIABLE_REASON); // 1.2 当流程状态还是审批状态中,说明审批通过了,则变更下它的状态 // 为什么这么处理?因为流程完成,并且完成了,说明审批通过了 if (Objects.equals(status, BpmProcessInstanceStatusEnum.RUNNING.getStatus())) { status = BpmProcessInstanceStatusEnum.APPROVE.getStatus(); runtimeService.setVariable(instance.getId(), BpmConstants.PROCESS_INSTANCE_VARIABLE_STATUS, status); } // 2. 发送对应的消息通知 if (Objects.equals(status, BpmProcessInstanceStatusEnum.APPROVE.getStatus())) { messageService.sendMessageWhenProcessInstanceApprove(BpmProcessInstanceConvert.INSTANCE.buildProcessInstanceApproveMessage(instance)); } else if (Objects.equals(status, BpmProcessInstanceStatusEnum.REJECT.getStatus())) { messageService.sendMessageWhenProcessInstanceReject( BpmProcessInstanceConvert.INSTANCE.buildProcessInstanceRejectMessage(instance, reason)); } // 3. 发送流程实例的状态事件 processInstanceEventPublisher.sendProcessInstanceResultEvent( BpmProcessInstanceConvert.INSTANCE.buildProcessInstanceStatusEvent(this, instance, status)); }); } }  
2 \ No newline at end of file 1 \ No newline at end of file
  2 +package cn.iocoder.yudao.module.bpm.service.task; import cn.hutool.core.collection.CollUtil; import cn.hutool.core.util.ArrayUtil; import cn.hutool.core.util.StrUtil; import cn.iocoder.yudao.framework.common.pojo.PageResult; import cn.iocoder.yudao.framework.common.util.date.DateUtils; import cn.iocoder.yudao.framework.common.util.object.PageUtils; import cn.iocoder.yudao.module.bpm.api.task.dto.BpmProcessInstanceCreateReqDTO; import cn.iocoder.yudao.module.bpm.controller.admin.task.vo.instance.BpmProcessInstanceCancelReqVO; import cn.iocoder.yudao.module.bpm.controller.admin.task.vo.instance.BpmProcessInstanceCreateReqVO; import cn.iocoder.yudao.module.bpm.controller.admin.task.vo.instance.BpmProcessInstancePageReqVO; import cn.iocoder.yudao.module.bpm.convert.task.BpmProcessInstanceConvert; import cn.iocoder.yudao.module.bpm.enums.task.BpmProcessInstanceStatusEnum; import cn.iocoder.yudao.module.bpm.enums.task.BpmReasonEnum; import cn.iocoder.yudao.module.bpm.framework.flowable.core.candidate.strategy.BpmTaskCandidateStartUserSelectStrategy; import cn.iocoder.yudao.module.bpm.framework.flowable.core.enums.BpmnVariableConstants; import cn.iocoder.yudao.module.bpm.framework.flowable.core.event.BpmProcessInstanceEventPublisher; import cn.iocoder.yudao.module.bpm.framework.flowable.core.util.FlowableUtils; import cn.iocoder.yudao.module.bpm.service.definition.BpmProcessDefinitionService; import cn.iocoder.yudao.module.bpm.service.message.BpmMessageService; import cn.iocoder.yudao.module.system.api.user.AdminUserApi; import cn.iocoder.yudao.module.system.api.user.dto.AdminUserRespDTO; import jakarta.annotation.Resource; import jakarta.validation.Valid; import lombok.extern.slf4j.Slf4j; import org.flowable.bpmn.model.BpmnModel; import org.flowable.bpmn.model.UserTask; import org.flowable.engine.HistoryService; import org.flowable.engine.RuntimeService; import org.flowable.engine.history.HistoricProcessInstance; import org.flowable.engine.history.HistoricProcessInstanceQuery; import org.flowable.engine.repository.ProcessDefinition; import org.flowable.engine.runtime.ProcessInstance; import org.springframework.context.annotation.Lazy; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import org.springframework.validation.annotation.Validated; import java.util.*; import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception; import static cn.iocoder.yudao.module.bpm.enums.ErrorCodeConstants.*; /** * 流程实例 Service 实现类 * * ProcessDefinition & ProcessInstance & Execution & Task 的关系: * 1. <a href="https://blog.csdn.net/bobozai86/article/details/105210414" /> * * HistoricProcessInstance & ProcessInstance 的关系: * 1. <a href=" https://my.oschina.net/843294669/blog/71902" /> * * 简单来说,前者 = 历史 + 运行中的流程实例,后者仅是运行中的流程实例 * * @author 芋道源码 */ @Service @Validated @Slf4j public class BpmProcessInstanceServiceImpl implements BpmProcessInstanceService { @Resource private RuntimeService runtimeService; @Resource private HistoryService historyService; @Resource private BpmProcessDefinitionService processDefinitionService; @Resource @Lazy // 避免循环依赖 private BpmTaskService taskService; @Resource private BpmMessageService messageService; @Resource private AdminUserApi adminUserApi; @Resource private BpmProcessInstanceEventPublisher processInstanceEventPublisher; // ========== Query 查询相关方法 ========== @Override public ProcessInstance getProcessInstance(String id) { return runtimeService.createProcessInstanceQuery() .includeProcessVariables() .processInstanceId(id) .singleResult(); } @Override public List<ProcessInstance> getProcessInstances(Set<String> ids) { return runtimeService.createProcessInstanceQuery().processInstanceIds(ids).list(); } @Override public HistoricProcessInstance getHistoricProcessInstance(String id) { return historyService.createHistoricProcessInstanceQuery().processInstanceId(id).includeProcessVariables().singleResult(); } @Override public List<HistoricProcessInstance> getHistoricProcessInstances(Set<String> ids) { return historyService.createHistoricProcessInstanceQuery().processInstanceIds(ids).list(); } @Override public PageResult<HistoricProcessInstance> getProcessInstancePage(Long userId, BpmProcessInstancePageReqVO pageReqVO) { // 通过 BpmProcessInstanceExtDO 表,先查询到对应的分页 HistoricProcessInstanceQuery processInstanceQuery = historyService.createHistoricProcessInstanceQuery() .includeProcessVariables() .processInstanceTenantId(FlowableUtils.getTenantId()) .orderByProcessInstanceStartTime().desc(); if (userId != null) { // 【我的流程】菜单时,需要传递该字段 processInstanceQuery.startedBy(String.valueOf(userId)); } else if (pageReqVO.getStartUserId() != null) { // 【管理流程】菜单时,才会传递该字段 processInstanceQuery.startedBy(String.valueOf(pageReqVO.getStartUserId())); } if (StrUtil.isNotEmpty(pageReqVO.getName())) { processInstanceQuery.processInstanceNameLike("%" + pageReqVO.getName() + "%"); } if (StrUtil.isNotEmpty(pageReqVO.getProcessDefinitionId())) { processInstanceQuery.processDefinitionId("%" + pageReqVO.getProcessDefinitionId() + "%"); } if (StrUtil.isNotEmpty(pageReqVO.getCategory())) { processInstanceQuery.processDefinitionCategory(pageReqVO.getCategory()); } if (pageReqVO.getStatus() != null) { processInstanceQuery.variableValueEquals(BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_STATUS, pageReqVO.getStatus()); } if (ArrayUtil.isNotEmpty(pageReqVO.getCreateTime())) { processInstanceQuery.startedAfter(DateUtils.of(pageReqVO.getCreateTime()[0])); processInstanceQuery.startedBefore(DateUtils.of(pageReqVO.getCreateTime()[1])); } // 查询数量 long processInstanceCount = processInstanceQuery.count(); if (processInstanceCount == 0) { return PageResult.empty(processInstanceCount); } // 查询列表 List<HistoricProcessInstance> processInstanceList = processInstanceQuery.listPage(PageUtils.getStart(pageReqVO), pageReqVO.getPageSize()); return new PageResult<>(processInstanceList, processInstanceCount); } // ========== Update 写入相关方法 ========== @Override @Transactional(rollbackFor = Exception.class) public String createProcessInstance(Long userId, @Valid BpmProcessInstanceCreateReqVO createReqVO) { // 获得流程定义 ProcessDefinition definition = processDefinitionService.getProcessDefinition(createReqVO.getProcessDefinitionId()); // 发起流程 return createProcessInstance0(userId, definition, createReqVO.getVariables(), null, createReqVO.getStartUserSelectAssignees()); } @Override public String createProcessInstance(Long userId, @Valid BpmProcessInstanceCreateReqDTO createReqDTO) { // 获得流程定义 ProcessDefinition definition = processDefinitionService.getActiveProcessDefinition(createReqDTO.getProcessDefinitionKey()); // 发起流程 return createProcessInstance0(userId, definition, createReqDTO.getVariables(), createReqDTO.getBusinessKey(), createReqDTO.getStartUserSelectAssignees()); } private String createProcessInstance0(Long userId, ProcessDefinition definition, Map<String, Object> variables, String businessKey, Map<String, List<Long>> startUserSelectAssignees) { // 1.1 校验流程定义 if (definition == null) { throw exception(PROCESS_DEFINITION_NOT_EXISTS); } if (definition.isSuspended()) { throw exception(PROCESS_DEFINITION_IS_SUSPENDED); } // 1.2 校验发起人自选审批人 validateStartUserSelectAssignees(definition, startUserSelectAssignees); // 2. 创建流程实例 if (variables == null) { variables = new HashMap<>(); } FlowableUtils.filterProcessInstanceFormVariable(variables); // 过滤一下,避免 ProcessInstance 系统级的变量被占用 variables.put(BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_STATUS, // 流程实例状态:审批中 BpmProcessInstanceStatusEnum.RUNNING.getStatus()); if (CollUtil.isNotEmpty(startUserSelectAssignees)) { variables.put(BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_START_USER_SELECT_ASSIGNEES, startUserSelectAssignees); } ProcessInstance instance = runtimeService.createProcessInstanceBuilder() .processDefinitionId(definition.getId()) .businessKey(businessKey) .name(definition.getName().trim()) .variables(variables) .start(); return instance.getId(); } private void validateStartUserSelectAssignees(ProcessDefinition definition, Map<String, List<Long>> startUserSelectAssignees) { // 1. 获得发起人自选审批人的 UserTask 列表 BpmnModel bpmnModel = processDefinitionService.getProcessDefinitionBpmnModel(definition.getId()); List<UserTask> userTaskList = BpmTaskCandidateStartUserSelectStrategy.getStartUserSelectUserTaskList(bpmnModel); if (CollUtil.isEmpty(userTaskList)) { return; } // 2. 校验发起人自选审批人的 UserTask 是否都配置了 userTaskList.forEach(userTask -> { List<Long> assignees = startUserSelectAssignees != null ? startUserSelectAssignees.get(userTask.getId()) : null; if (CollUtil.isEmpty(assignees)) { throw exception(PROCESS_INSTANCE_START_USER_SELECT_ASSIGNEES_NOT_CONFIG, userTask.getName()); } Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(assignees); assignees.forEach(assignee -> { if (userMap.get(assignee) == null) { throw exception(PROCESS_INSTANCE_START_USER_SELECT_ASSIGNEES_NOT_EXISTS, userTask.getName(), assignee); } }); }); } @Override public void cancelProcessInstanceByStartUser(Long userId, @Valid BpmProcessInstanceCancelReqVO cancelReqVO) { // 1.1 校验流程实例存在 ProcessInstance instance = getProcessInstance(cancelReqVO.getId()); if (instance == null) { throw exception(PROCESS_INSTANCE_CANCEL_FAIL_NOT_EXISTS); } // 1.2 只能取消自己的 if (!Objects.equals(instance.getStartUserId(), String.valueOf(userId))) { throw exception(PROCESS_INSTANCE_CANCEL_FAIL_NOT_SELF); } // 2. 取消流程 updateProcessInstanceCancel(cancelReqVO.getId(), BpmReasonEnum.CANCEL_PROCESS_INSTANCE_BY_START_USER.format(cancelReqVO.getReason())); } @Override public void cancelProcessInstanceByAdmin(Long userId, BpmProcessInstanceCancelReqVO cancelReqVO) { // 1.1 校验流程实例存在 ProcessInstance instance = getProcessInstance(cancelReqVO.getId()); if (instance == null) { throw exception(PROCESS_INSTANCE_CANCEL_FAIL_NOT_EXISTS); } // 2. 取消流程 AdminUserRespDTO user = adminUserApi.getUser(userId); updateProcessInstanceCancel(cancelReqVO.getId(), BpmReasonEnum.CANCEL_PROCESS_INSTANCE_BY_ADMIN.format(user.getNickname(), cancelReqVO.getReason())); } private void updateProcessInstanceCancel(String id, String reason) { // 1. 更新流程实例 status runtimeService.setVariable(id, BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_STATUS, BpmProcessInstanceStatusEnum.CANCEL.getStatus()); runtimeService.setVariable(id, BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_REASON, reason); // 2. 结束流程 taskService.moveTaskToEnd(id); } @Override public void updateProcessInstanceReject(ProcessInstance processInstance, String reason) { runtimeService.setVariable(processInstance.getProcessInstanceId(), BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_STATUS, BpmProcessInstanceStatusEnum.REJECT.getStatus()); runtimeService.setVariable(processInstance.getProcessInstanceId(), BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_REASON, BpmReasonEnum.REJECT_TASK.format(reason)); } // ========== Event 事件相关方法 ========== @Override public void processProcessInstanceCompleted(ProcessInstance instance) { // 注意:需要基于 instance 设置租户编号,避免 Flowable 内部异步时,丢失租户编号 FlowableUtils.execute(instance.getTenantId(), () -> { // 1.1 获取当前状态 Integer status = (Integer) instance.getProcessVariables().get(BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_STATUS); String reason = (String) instance.getProcessVariables().get(BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_REASON); // 1.2 当流程状态还是审批状态中,说明审批通过了,则变更下它的状态 // 为什么这么处理?因为流程完成,并且完成了,说明审批通过了 if (Objects.equals(status, BpmProcessInstanceStatusEnum.RUNNING.getStatus())) { status = BpmProcessInstanceStatusEnum.APPROVE.getStatus(); runtimeService.setVariable(instance.getId(), BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_STATUS, status); } // 2. 发送对应的消息通知 if (Objects.equals(status, BpmProcessInstanceStatusEnum.APPROVE.getStatus())) { messageService.sendMessageWhenProcessInstanceApprove(BpmProcessInstanceConvert.INSTANCE.buildProcessInstanceApproveMessage(instance)); } else if (Objects.equals(status, BpmProcessInstanceStatusEnum.REJECT.getStatus())) { messageService.sendMessageWhenProcessInstanceReject( BpmProcessInstanceConvert.INSTANCE.buildProcessInstanceRejectMessage(instance, reason)); } // 3. 发送流程实例的状态事件 processInstanceEventPublisher.sendProcessInstanceResultEvent( BpmProcessInstanceConvert.INSTANCE.buildProcessInstanceStatusEvent(this, instance, status)); }); } }
3 \ No newline at end of file 3 \ No newline at end of file
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/service/task/BpmTaskServiceImpl.java
@@ -19,7 +19,7 @@ import cn.iocoder.yudao.module.bpm.enums.task.BpmCommentTypeEnum; @@ -19,7 +19,7 @@ import cn.iocoder.yudao.module.bpm.enums.task.BpmCommentTypeEnum;
19 import cn.iocoder.yudao.module.bpm.enums.task.BpmReasonEnum; 19 import cn.iocoder.yudao.module.bpm.enums.task.BpmReasonEnum;
20 import cn.iocoder.yudao.module.bpm.enums.task.BpmTaskSignTypeEnum; 20 import cn.iocoder.yudao.module.bpm.enums.task.BpmTaskSignTypeEnum;
21 import cn.iocoder.yudao.module.bpm.enums.task.BpmTaskStatusEnum; 21 import cn.iocoder.yudao.module.bpm.enums.task.BpmTaskStatusEnum;
22 -import cn.iocoder.yudao.module.bpm.framework.flowable.core.enums.BpmConstants; 22 +import cn.iocoder.yudao.module.bpm.framework.flowable.core.enums.BpmnVariableConstants;
23 import cn.iocoder.yudao.module.bpm.framework.flowable.core.util.BpmnModelUtils; 23 import cn.iocoder.yudao.module.bpm.framework.flowable.core.util.BpmnModelUtils;
24 import cn.iocoder.yudao.module.bpm.framework.flowable.core.util.FlowableUtils; 24 import cn.iocoder.yudao.module.bpm.framework.flowable.core.util.FlowableUtils;
25 import cn.iocoder.yudao.module.bpm.service.definition.BpmModelService; 25 import cn.iocoder.yudao.module.bpm.service.definition.BpmModelService;
@@ -446,7 +446,7 @@ public class BpmTaskServiceImpl implements BpmTaskService { @@ -446,7 +446,7 @@ public class BpmTaskServiceImpl implements BpmTaskService {
446 } else if (BpmTaskSignTypeEnum.AFTER.getType().equals(scopeType)) { 446 } else if (BpmTaskSignTypeEnum.AFTER.getType().equals(scopeType)) {
447 // 只有 parentTask 处于 APPROVING 的情况下,才可以继续 complete 完成 447 // 只有 parentTask 处于 APPROVING 的情况下,才可以继续 complete 完成
448 // 否则,一个未审批的 parentTask 任务,在加签出来的任务都被减签的情况下,就直接完成审批,这样会存在问题 448 // 否则,一个未审批的 parentTask 任务,在加签出来的任务都被减签的情况下,就直接完成审批,这样会存在问题
449 - Integer status = (Integer) parentTask.getTaskLocalVariables().get(BpmConstants.TASK_VARIABLE_STATUS); 449 + Integer status = (Integer) parentTask.getTaskLocalVariables().get(BpmnVariableConstants.TASK_VARIABLE_STATUS);
450 if (ObjectUtil.notEqual(status, BpmTaskStatusEnum.APPROVING.getStatus())) { 450 if (ObjectUtil.notEqual(status, BpmTaskStatusEnum.APPROVING.getStatus())) {
451 return; 451 return;
452 } 452 }
@@ -531,7 +531,7 @@ public class BpmTaskServiceImpl implements BpmTaskService { @@ -531,7 +531,7 @@ public class BpmTaskServiceImpl implements BpmTaskService {
531 * @param status 状态 531 * @param status 状态
532 */ 532 */
533 private void updateTaskStatus(String id, Integer status) { 533 private void updateTaskStatus(String id, Integer status) {
534 - taskService.setVariableLocal(id, BpmConstants.TASK_VARIABLE_STATUS, status); 534 + taskService.setVariableLocal(id, BpmnVariableConstants.TASK_VARIABLE_STATUS, status);
535 } 535 }
536 536
537 /** 537 /**
@@ -543,7 +543,7 @@ public class BpmTaskServiceImpl implements BpmTaskService { @@ -543,7 +543,7 @@ public class BpmTaskServiceImpl implements BpmTaskService {
543 */ 543 */
544 private void updateTaskStatusAndReason(String id, Integer status, String reason) { 544 private void updateTaskStatusAndReason(String id, Integer status, String reason) {
545 updateTaskStatus(id, status); 545 updateTaskStatus(id, status);
546 - taskService.setVariableLocal(id, BpmConstants.TASK_VARIABLE_REASON, reason); 546 + taskService.setVariableLocal(id, BpmnVariableConstants.TASK_VARIABLE_REASON, reason);
547 } 547 }
548 548
549 @Override 549 @Override
@@ -692,7 +692,7 @@ public class BpmTaskServiceImpl implements BpmTaskService { @@ -692,7 +692,7 @@ public class BpmTaskServiceImpl implements BpmTaskService {
692 // 疑问:为什么不通过 updateTaskStatusWhenCanceled 监听取消,而是直接提前调用呢? 692 // 疑问:为什么不通过 updateTaskStatusWhenCanceled 监听取消,而是直接提前调用呢?
693 // 回答:详细见 updateTaskStatusWhenCanceled 的方法,加签的场景 693 // 回答:详细见 updateTaskStatusWhenCanceled 的方法,加签的场景
694 taskList.forEach(task -> { 694 taskList.forEach(task -> {
695 - Integer otherTaskStatus = (Integer) task.getTaskLocalVariables().get(BpmConstants.TASK_VARIABLE_STATUS); 695 + Integer otherTaskStatus = (Integer) task.getTaskLocalVariables().get(BpmnVariableConstants.TASK_VARIABLE_STATUS);
696 if (BpmTaskStatusEnum.isEndStatus(otherTaskStatus)) { 696 if (BpmTaskStatusEnum.isEndStatus(otherTaskStatus)) {
697 return; 697 return;
698 } 698 }
@@ -884,7 +884,7 @@ public class BpmTaskServiceImpl implements BpmTaskService { @@ -884,7 +884,7 @@ public class BpmTaskServiceImpl implements BpmTaskService {
884 884
885 @Override 885 @Override
886 public void processTaskCreated(Task task) { 886 public void processTaskCreated(Task task) {
887 - Integer status = (Integer) task.getTaskLocalVariables().get(BpmConstants.TASK_VARIABLE_STATUS); 887 + Integer status = (Integer) task.getTaskLocalVariables().get(BpmnVariableConstants.TASK_VARIABLE_STATUS);
888 if (status != null) { 888 if (status != null) {
889 log.error("[updateTaskStatusWhenCreated][taskId({}) 已经有状态({})]", task.getId(), status); 889 log.error("[updateTaskStatusWhenCreated][taskId({}) 已经有状态({})]", task.getId(), status);
890 return; 890 return;
@@ -908,7 +908,7 @@ public class BpmTaskServiceImpl implements BpmTaskService { @@ -908,7 +908,7 @@ public class BpmTaskServiceImpl implements BpmTaskService {
908 } 908 }
909 909
910 // 2. 更新 task 状态 + 原因 910 // 2. 更新 task 状态 + 原因
911 - Integer status = (Integer) task.getTaskLocalVariables().get(BpmConstants.TASK_VARIABLE_STATUS); 911 + Integer status = (Integer) task.getTaskLocalVariables().get(BpmnVariableConstants.TASK_VARIABLE_STATUS);
912 if (BpmTaskStatusEnum.isEndStatus(status)) { 912 if (BpmTaskStatusEnum.isEndStatus(status)) {
913 log.error("[updateTaskStatusWhenCanceled][taskId({}) 处于结果({}),无需进行更新]", taskId, status); 913 log.error("[updateTaskStatusWhenCanceled][taskId({}) 处于结果({}),无需进行更新]", taskId, status);
914 return; 914 return;