From f901de1209277caa00fb13329a4a58fbe5ad1995 Mon Sep 17 00:00:00 2001
From: chenchuchuan <13554600537@163.com>
Date: Mon, 12 Oct 2026 10:49:07 +0800
Subject: [PATCH 1/2] =?UTF-8?q?refactor(flow):=20=E7=AE=80=E5=8C=96=20reso?=
=?UTF-8?q?lveTitleCached=20=E6=96=B9=E6=B3=95=E7=AD=BE=E5=90=8D?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
- 移除 workOrder 和 taskKey 冗余参数,方法仅接收 taskInstanceExt
- 简化空判断逻辑,直接从 taskInstanceExt 读取落库 title
- 控制器中移除不再需要的 FlowWorkOrder 查询调用
- 更新所有调用点适配新的方法签名
---
.../flow/controller/FlowOperationController.java | 39 ++++++++--------------
.../apelet/common/flow/service/FlowApiService.java | 6 ++--
.../flow/service/impl/FlowApiServiceImpl.java | 11 +++---
3 files changed, 20 insertions(+), 36 deletions(-)
diff --git a/common/common-flow/src/main/java/apelet/common/flow/controller/FlowOperationController.java b/common/common-flow/src/main/java/apelet/common/flow/controller/FlowOperationController.java
index d6ac6aa..eeda8f5 100644
--- a/common/common-flow/src/main/java/apelet/common/flow/controller/FlowOperationController.java
+++ b/common/common-flow/src/main/java/apelet/common/flow/controller/FlowOperationController.java
@@ -219,13 +219,12 @@ public class FlowOperationController {
if (StrUtil.isNotBlank(flowTaskExt.getVariableListJson())) {
taskInfoVo.setVariableList(JSON.parseArray(flowTaskExt.getVariableListJson(), JSONObject.class));
}
- FlowWorkOrder workOrder = flowWorkOrderService.getFlowWorkOrderByProcessInstanceId(processInstanceId);
// 单条详情:只查一次节点扩展(复用批量接口传单元素集合),无 N+1 风险。
String taskKey = taskInfoVo.getTaskKey();
- FlowTaskInstanceExt taskInstanceExt = workOrder == null || StrUtil.isBlank(taskKey) ? null
+ FlowTaskInstanceExt taskInstanceExt = StrUtil.isBlank(taskKey) ? null
: flowTaskInstanceExtService.getMapByProcessInstanceIds(CollUtil.newHashSet(processInstanceId))
.get(processInstanceId + ":" + taskKey);
- taskInfoVo.setTitle(flowApiService.resolveTitleCached(workOrder, taskKey, taskInstanceExt));
+ taskInfoVo.setTitle(flowApiService.resolveTitleCached(taskInstanceExt));
}
return ResponseResult.success(taskInfoVo);
}
@@ -835,24 +834,16 @@ public class FlowOperationController {
pageData.getDataList().forEach(instance -> resultList.add(BeanUtil.beanToMap(instance)));
List taskInstanceList = pageData.getDataList();
if (CollUtil.isNotEmpty(taskInstanceList)) {
- Set instanceIdSet = taskInstanceList.stream()
- .map(HistoricTaskInstance::getProcessInstanceId).collect(Collectors.toSet());
+ Set instanceIdSet = taskInstanceList.stream().map(HistoricTaskInstance::getProcessInstanceId).collect(Collectors.toSet());
List instanceList = flowApiService.getHistoricProcessInstanceList(instanceIdSet);
- Set loginNameSet = instanceList.stream()
- .map(HistoricProcessInstance::getStartUserId).collect(Collectors.toSet());
- List userInfoList = flowCustomExtFactory
- .getFlowIdentityExtHelper().getUserInfoListByUsernameSet(loginNameSet);
- Map userInfoMap =
- userInfoList.stream().collect(Collectors.toMap(FlowUserInfoVo::getLoginName, c -> c));
- Map instanceMap =
- instanceList.stream().collect(Collectors.toMap(HistoricProcessInstance::getId, c -> c));
- List workOrderList =
- flowWorkOrderService.getInList(INSTANCE_ID, instanceIdSet);
- Map workOrderMap =
- workOrderList.stream().collect(Collectors.toMap(FlowWorkOrder::getProcessInstanceId, c -> c));
+ Set loginNameSet = instanceList.stream().map(HistoricProcessInstance::getStartUserId).collect(Collectors.toSet());
+ List userInfoList = flowCustomExtFactory.getFlowIdentityExtHelper().getUserInfoListByUsernameSet(loginNameSet);
+ Map userInfoMap = userInfoList.stream().collect(Collectors.toMap(FlowUserInfoVo::getLoginName, c -> c));
+ Map instanceMap = instanceList.stream().collect(Collectors.toMap(HistoricProcessInstance::getId, c -> c));
+ List workOrderList = flowWorkOrderService.getInList(INSTANCE_ID, instanceIdSet);
+ Map workOrderMap = workOrderList.stream().collect(Collectors.toMap(FlowWorkOrder::getProcessInstanceId, c -> c));
// 节点标题按实例批量预载(一次 IN 查询覆盖整页),避免逐行查询造成 N+1。
- Map taskInstanceExtMap =
- flowTaskInstanceExtService.getMapByProcessInstanceIds(instanceIdSet);
+ Map taskInstanceExtMap = flowTaskInstanceExtService.getMapByProcessInstanceIds(instanceIdSet);
resultList.forEach(result -> {
String instanceId = result.get(INSTANCE_ID).toString();
HistoricProcessInstance instance = instanceMap.get(instanceId);
@@ -869,15 +860,13 @@ public class FlowOperationController {
// 标题只认 zz_flow_task_instance_ext 的落库值:没有标题行就是空
Object taskDefinitionKey = result.get("taskDefinitionKey");
String taskKey = taskDefinitionKey == null ? null : taskDefinitionKey.toString();
- result.put("title", flowApiService.resolveTitleCached(flowWorkOrder, taskKey,
+ result.put("title", flowApiService.resolveTitleCached(
taskKey == null ? null : taskInstanceExtMap.get(instanceId + ":" + taskKey)));
}
});
- Set taskIdSet =
- taskInstanceList.stream().map(HistoricTaskInstance::getId).collect(Collectors.toSet());
+ Set taskIdSet = taskInstanceList.stream().map(HistoricTaskInstance::getId).collect(Collectors.toSet());
List commentList = flowTaskCommentService.getFlowTaskCommentListByTaskIds(taskIdSet);
- Map> commentMap =
- commentList.stream().collect(Collectors.groupingBy(FlowTaskComment::getTaskId));
+ Map> commentMap = commentList.stream().collect(Collectors.groupingBy(FlowTaskComment::getTaskId));
resultList.forEach(result -> {
List comments = commentMap.get(result.get("id").toString());
if (CollUtil.isNotEmpty(comments)) {
@@ -956,7 +945,7 @@ public class FlowOperationController {
data.put("flowStatus", workOrder.getFlowStatus());
// 流程实例列表使用起始节点的标题;标题只认落库值,没有标题行就是空
String initTaskKey = initTaskKeyMap.get(instance.getProcessDefinitionId());
- data.put("title", flowApiService.resolveTitleCached(workOrder, initTaskKey,
+ data.put("title", flowApiService.resolveTitleCached(
initTaskKey == null ? null : taskInstanceExtMap.get(instance.getId() + ":" + initTaskKey)));
}
resultList.add(data);
diff --git a/common/common-flow/src/main/java/apelet/common/flow/service/FlowApiService.java b/common/common-flow/src/main/java/apelet/common/flow/service/FlowApiService.java
index 6676520..ca43961 100644
--- a/common/common-flow/src/main/java/apelet/common/flow/service/FlowApiService.java
+++ b/common/common-flow/src/main/java/apelet/common/flow/service/FlowApiService.java
@@ -671,12 +671,10 @@ public interface FlowApiService {
* 本方法只读落库值,不做实时解析兜底:没有标题行就返回 null,列表上该行标题为空。
* 因此存量数据(改造前已跑的实例)标题会为空,需要回填后才有。
*
- * @param workOrder 流程工单对象,为空时返回 null。
- * @param taskKey BPMN 节点Id,用于定位标题行,为空时返回 null。
- * @param taskInstanceExt 节点扩展对象(调用方批量预载,避免逐行查询),可为空。
+ * @param taskInstanceExt 节点扩展对象(调用方按 (实例, 节点) 批量预载,避免逐行查询),可为空。
* @return 落库的标题;没有标题行返回 null。
*/
- String resolveTitleCached(FlowWorkOrder workOrder, String taskKey, FlowTaskInstanceExt taskInstanceExt);
+ String resolveTitleCached(FlowTaskInstanceExt taskInstanceExt);
/**
* 生成指定节点的标题并落库到 zz_flow_task_instance_ext。
diff --git a/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowApiServiceImpl.java b/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowApiServiceImpl.java
index bbc5930..a91968d 100644
--- a/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowApiServiceImpl.java
+++ b/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowApiServiceImpl.java
@@ -1024,7 +1024,7 @@ public class FlowApiServiceImpl implements FlowApiService {
}
// 标题只以 zz_flow_task_instance_ext 的落库值为准:没有标题行就是空,
// 不需要再按"节点配没配模板""是不是在线表单"做前置判断(那两个条件对标题行本身没有约束力)。
- flowTaskVo.setTitle(this.resolveTitleCached(flowWorkOrder, task.getTaskDefinitionKey(),
+ flowTaskVo.setTitle(this.resolveTitleCached(
taskInstanceExtMap.get(task.getProcessInstanceId() + ":" + task.getTaskDefinitionKey())));
flowTaskVoList.add(flowTaskVo);
}
@@ -2962,14 +2962,11 @@ public class FlowApiServiceImpl implements FlowApiService {
}
@Override
- public String resolveTitleCached(FlowWorkOrder workOrder, String taskKey, FlowTaskInstanceExt taskInstanceExt) {
+ public String resolveTitleCached(FlowTaskInstanceExt taskInstanceExt) {
// 标题只以 zz_flow_task_instance_ext 的落库值为准,不再回退到按模板实时解析。
// 这样"这个节点到底有没有落库"在列表上一眼可见,排查/联调时不会被实时兜底掩盖。
- if (workOrder == null || taskInstanceExt == null || StrUtil.isBlank(taskKey)
- || StrUtil.isBlank(taskInstanceExt.getTitle())) {
- return null;
- }
- return taskInstanceExt.getTitle();
+ String title = taskInstanceExt == null ? null : taskInstanceExt.getTitle();
+ return StrUtil.isBlank(title) ? null : title;
}
@Override
From e031e4dd51d467f086dabfb185131723aeee455c Mon Sep 17 00:00:00 2001
From: chenchuchuan <13554600537@163.com>
Date: Mon, 19 Oct 2026 10:34:13 +0800
Subject: [PATCH 2/2] =?UTF-8?q?chore(build):=20=E6=9B=B4=E6=96=B0=E6=9E=84?=
=?UTF-8?q?=E5=BB=BA=E9=85=8D=E7=BD=AE=E5=B9=B6=E4=BF=AE=E5=A4=8D=E6=B5=81?=
=?UTF-8?q?=E7=A8=8B=E6=9C=8D=E5=8A=A1=E7=A9=BA=E6=8C=87=E9=92=88=E9=97=AE?=
=?UTF-8?q?=E9=A2=98?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
- 将 Nexus 仓库地址从公网 IP 更新为内网地址 192.168.100.25
- 在 common 模块中新增 common-botp 子模块
- common-botp 依赖版本更新,common-core 改为变量引用方式
- FlowEntryServiceImpl 增加 tokenData 为空时的空指针防护逻辑
- FlowTaskTitleBackfillServiceImpl 移除 GlobalThreadLocal 调用,简化数据过滤逻辑
- FlowTaskTitleBackfillServiceImpl 重构 processDefinitionKey 判空逻辑为提前返回
---
common/common-botp/pom.xml | 6 +++---
.../common/flow/service/FlowEntryService.java | 10 ++++++++++
.../flow/service/impl/FlowEntryServiceImpl.java | 11 +++++++++++
.../impl/FlowTaskTitleBackfillServiceImpl.java | 21 +++++++--------------
common/pom.xml | 2 ++
pom.xml | 4 ++--
6 files changed, 35 insertions(+), 19 deletions(-)
diff --git a/common/common-botp/pom.xml b/common/common-botp/pom.xml
index 1fc7b12..f121380 100644
--- a/common/common-botp/pom.xml
+++ b/common/common-botp/pom.xml
@@ -17,17 +17,17 @@
apelet
common-core
- 1.0.0
+ ${common-core.version}
apelet
common-generator
- 1.0.3
+ 1.0.5
apelet
common-online
- 1.0.3
+ 1.0.6
compile
diff --git a/common/common-flow/src/main/java/apelet/common/flow/service/FlowEntryService.java b/common/common-flow/src/main/java/apelet/common/flow/service/FlowEntryService.java
index a21c89f..5d62b08 100644
--- a/common/common-flow/src/main/java/apelet/common/flow/service/FlowEntryService.java
+++ b/common/common-flow/src/main/java/apelet/common/flow/service/FlowEntryService.java
@@ -79,6 +79,16 @@ public interface FlowEntryService extends IBaseService {
*/
FlowEntry getFlowEntryFromCache(String processDefinitionKey);
+
+ /**
+ * 根据流程定义标识获取流程对象。从缓存中读取,如不存在则从数据库读取后,再同步到缓存。
+ *
+ * @param processDefinitionKey 流程定义标识。
+ * @param isToken 是否存在登录态
+ * @return 流程对象。
+ */
+ FlowEntry getFlowEntryFromCache(String processDefinitionKey ,Boolean isToken);
+
/**
* 根据流程Id获取流程发布列表数据。
*
diff --git a/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowEntryServiceImpl.java b/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowEntryServiceImpl.java
index 9642c75..602db84 100644
--- a/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowEntryServiceImpl.java
+++ b/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowEntryServiceImpl.java
@@ -240,10 +240,21 @@ public class FlowEntryServiceImpl extends BaseService implement
@Override
public FlowEntry getFlowEntryFromCache(String processDefinitionKey) {
+ return getFlowEntryFromCache(processDefinitionKey, true);
+ }
+
+ @Override
+ public FlowEntry getFlowEntryFromCache(String processDefinitionKey, Boolean isToken) {
String key = FlowRedisKeyUtil.makeFlowEntryKey(processDefinitionKey);
LambdaQueryWrapper qw = new LambdaQueryWrapper<>();
qw.eq(FlowEntry::getProcessDefinitionKey, processDefinitionKey);
+ if (Boolean.FALSE.equals(isToken)) {
+ return commonRedisUtil.getFromCacheWithQueryWrapper(key, qw, flowEntryMapper::selectOne, FlowEntry.class);
+ }
TokenData tokenData = TokenData.takeFromRequest();
+ if (tokenData == null) {
+ return null;
+ }
if (StrUtil.isNotBlank(tokenData.getAppCode())) {
qw.eq(FlowEntry::getAppCode, tokenData.getAppCode());
} else {
diff --git a/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowTaskTitleBackfillServiceImpl.java b/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowTaskTitleBackfillServiceImpl.java
index eab2a97..4e01c45 100644
--- a/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowTaskTitleBackfillServiceImpl.java
+++ b/common/common-flow/src/main/java/apelet/common/flow/service/impl/FlowTaskTitleBackfillServiceImpl.java
@@ -11,12 +11,7 @@ import apelet.common.flow.model.FlowTaskExt;
import apelet.common.flow.model.FlowTaskInstanceExt;
import apelet.common.flow.model.FlowWorkOrder;
import apelet.common.flow.model.constant.FlowBindFormType;
-import apelet.common.flow.service.FlowApiService;
-import apelet.common.flow.service.FlowEntryService;
-import apelet.common.flow.service.FlowTaskExtService;
-import apelet.common.flow.service.FlowTaskInstanceExtService;
-import apelet.common.flow.service.FlowTaskTitleBackfillService;
-import apelet.common.flow.service.FlowWorkOrderService;
+import apelet.common.flow.service.*;
import apelet.common.flow.vo.FlowTaskTitleBackfillVo;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.BooleanUtil;
@@ -30,11 +25,7 @@ import org.flowable.task.api.history.HistoricTaskInstance;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
+import java.util.*;
/**
* 节点标题回填服务实现。
@@ -84,7 +75,7 @@ public class FlowTaskTitleBackfillServiceImpl implements FlowTaskTitleBackfillSe
result.setDryRun(onlyCount);
// 回填是没有登录态的运维动作,且要跨租户跑;关掉数据权限过滤,
// 否则 getMasterData -> buildDataPermFilter -> processDataPerm 会因 TokenData 为空而 NPE。
- boolean dataFilterEnabled = GlobalThreadLocal.setDataFilter(false);
+ boolean dataFilterEnabled = false;
try {
List workOrderList = flowWorkOrderService.getListByWorkOrderIdAfter(cursorWorkOrderId, size);
for (FlowWorkOrder workOrder : workOrderList) {
@@ -113,8 +104,10 @@ public class FlowTaskTitleBackfillServiceImpl implements FlowTaskTitleBackfillSe
if (StrUtil.isBlank(processInstanceId)) {
return;
}
- FlowEntry flowEntry = StrUtil.isBlank(workOrder.getProcessDefinitionKey()) ? null
- : flowEntryService.getFlowEntryFromCache(workOrder.getProcessDefinitionKey());
+ if (StrUtil.isBlank(workOrder.getProcessDefinitionKey())) {
+ return;
+ }
+ FlowEntry flowEntry = flowEntryService.getFlowEntryFromCache(workOrder.getProcessDefinitionKey(), false);
// 路由表单流程本来就没有标题,跳过
if (flowEntry == null || !ObjectUtil.equal(flowEntry.getBindFormType(), FlowBindFormType.ONLINE_FORM)) {
return;
diff --git a/common/pom.xml b/common/pom.xml
index d79f21d..a2c592f 100644
--- a/common/pom.xml
+++ b/common/pom.xml
@@ -24,6 +24,8 @@
common-openapi
common-core
+
+ common-botp
diff --git a/pom.xml b/pom.xml
index 147aa5f..0a0aebf 100644
--- a/pom.xml
+++ b/pom.xml
@@ -138,13 +138,13 @@
nexus
nexus
- http://58.48.135.45:8081/repository/maven-releases/
+ http://192.168.100.25:8081/repository/maven-releases/
maven-snapshots
maven-snapshots
- http://58.48.135.45:8081/repository/maven-snapshots/
+ http://192.168.100.25:8081/repository/maven-snapshots/