Kaynağa Gözat

!1213 代码审查修改
Merge pull request !1213 from Lesan/feature/bpm-代码审查

芋道源码 6 ay önce
ebeveyn
işleme
1ae51bde20

+ 1 - 0
yudao-module-bpm/yudao-module-bpm-api/src/main/java/cn/iocoder/yudao/module/bpm/enums/task/BpmReasonEnum.java

@@ -32,6 +32,7 @@ public enum BpmReasonEnum {
     ASSIGN_EMPTY_REJECT("审批人为空,自动不通过"),
     APPROVE_TYPE_AUTO_APPROVE("非人工审核,自动通过"),
     APPROVE_TYPE_AUTO_REJECT("非人工审核,自动不通过"),
+    CANCEL_BY_PROCESS_CLEAN("进程清理自动取消"),
     ;
 
     private final String reason;

+ 13 - 1
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/controller/admin/task/BpmProcessInstanceCopyController.java

@@ -9,7 +9,10 @@ import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
 import cn.iocoder.yudao.module.bpm.controller.admin.base.user.UserSimpleBaseVO;
 import cn.iocoder.yudao.module.bpm.controller.admin.task.vo.cc.BpmProcessInstanceCopyRespVO;
 import cn.iocoder.yudao.module.bpm.controller.admin.task.vo.instance.BpmProcessInstanceCopyPageReqVO;
+import cn.iocoder.yudao.module.bpm.dal.dataobject.definition.BpmProcessDefinitionInfoDO;
 import cn.iocoder.yudao.module.bpm.dal.dataobject.task.BpmProcessInstanceCopyDO;
+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.task.BpmProcessInstanceCopyService;
 import cn.iocoder.yudao.module.bpm.service.task.BpmProcessInstanceService;
 import cn.iocoder.yudao.module.system.api.user.AdminUserApi;
@@ -42,6 +45,8 @@ public class BpmProcessInstanceCopyController {
     private BpmProcessInstanceCopyService processInstanceCopyService;
     @Resource
     private BpmProcessInstanceService processInstanceService;
+    @Resource
+    private BpmProcessDefinitionService processDefinitionService;
 
     @Resource
     private AdminUserApi adminUserApi;
@@ -62,6 +67,8 @@ public class BpmProcessInstanceCopyController {
                 convertSet(pageResult.getList(), BpmProcessInstanceCopyDO::getProcessInstanceId));
         Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(convertListByFlatMap(pageResult.getList(),
                 copy -> Stream.of(copy.getStartUserId(), Long.parseLong(copy.getCreator()))));
+        Map<String, BpmProcessDefinitionInfoDO> processDefinitionInfoMap = processDefinitionService.getProcessDefinitionInfoMap(
+                convertSet(pageResult.getList(), BpmProcessInstanceCopyDO::getProcessDefinitionId));
         return success(convertPage(pageResult, copy -> {
             BpmProcessInstanceCopyRespVO copyVO = BeanUtils.toBean(copy, BpmProcessInstanceCopyRespVO.class);
             MapUtils.findAndThen(userMap, Long.valueOf(copy.getCreator()),
@@ -69,7 +76,12 @@ public class BpmProcessInstanceCopyController {
             MapUtils.findAndThen(userMap, copy.getStartUserId(),
                     user -> copyVO.setCreateUser(BeanUtils.toBean(user, UserSimpleBaseVO.class)));
             MapUtils.findAndThen(processInstanceMap, copyVO.getProcessInstanceId(),
-                    processInstance -> copyVO.setProcessInstanceStartTime(DateUtils.of(processInstance.getStartTime())));
+                    processInstance -> {
+                        copyVO.setSummary(FlowableUtils.getSummary(
+                                processDefinitionInfoMap.get(processInstance.getProcessDefinitionId()),
+                                processInstance.getProcessVariables()));
+                        copyVO.setProcessInstanceStartTime(DateUtils.of(processInstance.getStartTime()));
+                    });
             return copyVO;
         }));
     }

+ 5 - 0
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/controller/admin/task/vo/cc/BpmProcessInstanceCopyRespVO.java

@@ -1,10 +1,12 @@
 package cn.iocoder.yudao.module.bpm.controller.admin.task.vo.cc;
 
+import cn.iocoder.yudao.framework.common.core.KeyValue;
 import cn.iocoder.yudao.module.bpm.controller.admin.base.user.UserSimpleBaseVO;
 import io.swagger.v3.oas.annotations.media.Schema;
 import lombok.Data;
 
 import java.time.LocalDateTime;
+import java.util.List;
 
 @Schema(description = "管理后台 - 流程实例抄送的分页 Item Response VO")
 @Data
@@ -40,4 +42,7 @@ public class BpmProcessInstanceCopyRespVO {
     @Schema(description = "抄送时间", requiredMode = Schema.RequiredMode.REQUIRED)
     private LocalDateTime createTime;
 
+    @Schema(description = "流程摘要", example = "[]")
+    private List<KeyValue<String, String>> summary;
+
 }

+ 3 - 4
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/controller/admin/task/vo/task/BpmTaskRespVO.java

@@ -85,10 +85,6 @@ public class BpmTaskRespVO {
     @Schema(description = "是否填写审批意见", example = "false")
     private Boolean reasonRequire;
 
-    // TODO @lesan:要不放到 processInstance 里面?因为摘要是流程实例的,不是流程任务的
-    @Schema(description = "流程摘要", example = "[]")
-    private List<KeyValue<String, String>> summary; // 只有流程表单,才有摘要!
-
     @Data
     @Schema(description = "流程实例")
     public static class ProcessInstance {
@@ -105,6 +101,9 @@ public class BpmTaskRespVO {
         @Schema(description = "流程定义的编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "2048")
         private String processDefinitionId;
 
+        @Schema(description = "流程摘要", example = "[]")
+        private List<KeyValue<String, String>> summary; // 只有流程表单,才有摘要!
+
         /**
          * 发起人的用户信息
          */

+ 2 - 2
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/convert/task/BpmTaskConvert.java

@@ -54,7 +54,7 @@ public interface BpmTaskConvert {
             AdminUserRespDTO startUser = userMap.get(NumberUtils.parseLong(processInstance.getStartUserId()));
             taskVO.getProcessInstance().setStartUser(BeanUtils.toBean(startUser, UserSimpleBaseVO.class));
             // 摘要
-            taskVO.setSummary(FlowableUtils.getSummary(processDefinitionInfoMap.get(processInstance.getProcessDefinitionId()),
+            taskVO.getProcessInstance().setSummary(FlowableUtils.getSummary(processDefinitionInfoMap.get(processInstance.getProcessDefinitionId()),
                     processInstance.getProcessVariables()));
         });
     }
@@ -80,7 +80,7 @@ public interface BpmTaskConvert {
                 taskVO.setProcessInstance(BeanUtils.toBean(processInstance, BpmTaskRespVO.ProcessInstance.class));
                 taskVO.getProcessInstance().setStartUser(BeanUtils.toBean(startUser, UserSimpleBaseVO.class));
                 // 摘要
-                taskVO.setSummary(FlowableUtils.getSummary(processDefinitionInfoMap.get(processInstance.getProcessDefinitionId()),
+                taskVO.getProcessInstance().setSummary(FlowableUtils.getSummary(processDefinitionInfoMap.get(processInstance.getProcessDefinitionId()),
                         processInstance.getProcessVariables()));
             }
             return taskVO;

+ 6 - 0
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/dal/dataobject/task/BpmProcessInstanceCopyDO.java

@@ -49,6 +49,12 @@ public class BpmProcessInstanceCopyDO extends BaseDO {
      * 关联 ProcessInstance 的 id 属性
      */
     private String processInstanceId;
+    /**
+     * 流程实例的流程定义编号
+     *
+     * 关联 ProcessInstance 的 processDefinitionId 属性
+     */
+    private String processDefinitionId;
     /**
      * 流程分类
      *

+ 33 - 46
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/framework/flowable/core/util/FlowableUtils.java

@@ -27,6 +27,8 @@ import org.flowable.task.api.TaskInfo;
 import java.util.*;
 import java.util.concurrent.Callable;
 
+import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertList;
+
 /**
  * Flowable 相关的工具方法
  *
@@ -193,7 +195,6 @@ public class FlowableUtils {
                 BpmnVariableConstants.PROCESS_INSTANCE_VARIABLE_START_USER_SELECT_ASSIGNEES);
     }
 
-    // TODO @lesan:如果值是 null 的情况,可能要调研下飞书、钉钉,是不是不返回哈!
     /**
      * 获得流程实例的摘要
      *
@@ -206,53 +207,39 @@ public class FlowableUtils {
      */
     public static List<KeyValue<String, String>> getSummary(BpmProcessDefinitionInfoDO processDefinitionInfo,
                                                             Map<String, Object> processVariables) {
-        // TODO @lesan:建议 if return,减少 { 层级
-        if (ObjectUtil.isNotNull(processDefinitionInfo)
-                && BpmModelFormTypeEnum.NORMAL.getType().equals(processDefinitionInfo.getFormType())) {
-            List<KeyValue<String, String>> summaryList = new ArrayList<>();
-            // TODO @lesan:可以使用 CollUtils.convertMap 简化工作量哈。
-            Map<String, BpmFormFieldVO> formFieldsMap = new HashMap<>();
-            processDefinitionInfo.getFormFields().forEach(formFieldStr -> {
-                BpmFormFieldVO formField = JsonUtils.parseObject(formFieldStr, BpmFormFieldVO.class);
+        // 只有流程表单才会显示摘要!
+        if (ObjectUtil.isNull(processDefinitionInfo)
+                || !BpmModelFormTypeEnum.NORMAL.getType().equals(processDefinitionInfo.getFormType())) {
+            return null;
+        }
+        List<KeyValue<String, String>> summaryList;
+        Map<String, BpmFormFieldVO> formFieldsMap = new HashMap<>();
+        processDefinitionInfo.getFormFields().forEach(formFieldStr -> {
+            BpmFormFieldVO formField = JsonUtils.parseObject(formFieldStr, BpmFormFieldVO.class);
+            if (formField != null) {
+                formFieldsMap.put(formField.getField(), formField);
+            }
+        });
+        if (ObjectUtil.isNotNull(processDefinitionInfo.getSummarySetting())
+                && Boolean.TRUE.equals(processDefinitionInfo.getSummarySetting().getEnable())) {
+            // 情况一:当自定义了摘要
+            summaryList = convertList(processDefinitionInfo.getSummarySetting().getSummary(), item -> {
+                BpmFormFieldVO formField = formFieldsMap.get(item);
                 if (formField != null) {
-                    formFieldsMap.put(formField.getField(), formField);
+                    return new KeyValue<String, String>(formField.getTitle(),
+                            processVariables.getOrDefault(item, "").toString());
                 }
+                return null;
             });
-
-            // TODO @lesan:这里也可以 if return,还是为了减少括号哈。这样,就可以写注释,情况一:;情况二:
-            if (ObjectUtil.isNotNull(processDefinitionInfo.getSummarySetting())
-                    && Boolean.TRUE.equals(processDefinitionInfo.getSummarySetting().getEnable())) {
-                // TODO @lesan:这里,也可以通过 CollUtils.convertList 简化哈。
-                for (String item : processDefinitionInfo.getSummarySetting().getSummary()) {
-                    BpmFormFieldVO formField = formFieldsMap.get(item);
-                    if (formField != null) {
-                        summaryList.add(new KeyValue<>(formField.getTitle(),
-                                processVariables.getOrDefault(item, "").toString()));
-                    }
-                }
-            } else {
-                // 默认展示前三个
-                /* TODO @lesan:stream 简化
-                 * summaryList.addAll(formFieldsMap.entrySet().stream()
-                 *         .limit(3)
-                 *         .map(entry -> new KeyValue<>(entry.getValue().getTitle(),
-                 *                 processVariables.getOrDefault(entry.getValue().getField(), "").toString()))
-                 *         .collect(Collectors.toList()));
-                 */
-                int j = 0;
-                for (Map.Entry<String, BpmFormFieldVO> entry : formFieldsMap.entrySet()) {
-                    BpmFormFieldVO formField = entry.getValue();
-                    if (j > 2) {
-                        break;
-                    }
-                    summaryList.add(new KeyValue<>(formField.getTitle(),
-                            processVariables.getOrDefault(formField.getField(), "").toString()));
-                    j++;
-                }
-            }
-            return summaryList;
+        } else {
+            // 情况二:默认摘要展示前三个表单字段
+            summaryList = new ArrayList<>(formFieldsMap.entrySet().stream()
+                    .limit(3)
+                    .map(entry -> new KeyValue<>(entry.getValue().getTitle(),
+                            processVariables.getOrDefault(entry.getValue().getField(), "").toString()))
+                    .toList());
         }
-        return null;
+        return summaryList;
     }
 
     // ========== Task 相关的工具方法 ==========
@@ -317,9 +304,9 @@ public class FlowableUtils {
 
     private static Object getExpressionValue(VariableContainer variableContainer, String expressionString,
                                              ProcessEngineConfigurationImpl processEngineConfiguration) {
-        assert processEngineConfiguration!= null;
+        assert processEngineConfiguration != null;
         ExpressionManager expressionManager = processEngineConfiguration.getExpressionManager();
-        assert expressionManager!= null;
+        assert expressionManager != null;
         Expression expression = expressionManager.createExpression(expressionString);
         return expression.getValue(variableContainer);
     }

+ 1 - 2
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/service/definition/BpmModelServiceImpl.java

@@ -288,8 +288,7 @@ public class BpmModelServiceImpl implements BpmModelService {
         // 2.3 清理所有 Task
         List<Task> tasks = taskService.createTaskQuery()
                 .processDefinitionKey(model.getKey()).list();
-        // TODO @lesan:貌似传递一个 reason 会好点!
-        tasks.forEach(task -> taskService.deleteTask(task.getId()));
+        tasks.forEach(task -> taskService.deleteTask(task.getId(),BpmReasonEnum.CANCEL_BY_PROCESS_CLEAN.getReason()));
     }
 
     @Override

+ 2 - 1
yudao-module-bpm/yudao-module-bpm-biz/src/main/java/cn/iocoder/yudao/module/bpm/service/task/BpmProcessInstanceCopyServiceImpl.java

@@ -77,7 +77,8 @@ public class BpmProcessInstanceCopyServiceImpl implements BpmProcessInstanceCopy
                 .setUserId(userId).setReason(reason).setStartUserId(Long.valueOf(processInstance.getStartUserId()))
                 .setProcessInstanceId(processInstanceId).setProcessInstanceName(processInstance.getName())
                 .setCategory(processDefinition.getCategory()).setTaskId(taskId)
-                .setActivityId(activityId).setActivityName(activityName));
+                .setActivityId(activityId).setActivityName(activityName)
+                .setProcessDefinitionId(processInstance.getProcessDefinitionId()));
         processInstanceCopyMapper.insertBatch(copyList);
     }