From 335890b699cbb5ad96d5cc8915673a0cc0965135 Mon Sep 17 00:00:00 2001 From: new_new_new <8454518+new-twice@user.noreply.gitee.com> Date: Thu, 4 Jun 2026 12:25:18 +0000 Subject: [PATCH] =?UTF-8?q?!32=20fix(flow):=20=E4=BF=AE=E5=A4=8D=E9=85=8D?= =?UTF-8?q?=E7=BD=AE=E5=89=8D=E7=BC=80=E9=94=99=E8=AF=AF=E5=AF=BC=E8=87=B4?= =?UTF-8?q?=20props=20=E4=B8=BA=20null=20=E5=8F=8A=E6=B5=81=E7=A8=8B?= =?UTF-8?q?=E5=8F=98=E9=87=8F=E8=8E=B7=E5=8F=96=E5=A4=B1=E8=B4=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * fix(flow): 修复配置前缀错误导致 props 为 null 及流程变量获取失败 * fix(flow): 修复 inspectImproveProps 字段初始化 NPE 问题 * feat(flow): 新增巡视整改流程党群领导审批表达式方法 * feat(dqinspecttask): 新增工作进展反馈子表独立Controller接口 --- .../jeecg/inspectimprove/InspectConstant.java | 8 + .../inspectimprove/InspectImproveConfig.java | 4 +- .../inspectimprove/InspectImproveFlow.java | 107 +++++++++++ .../src/main/resources/application-flow.yml | 2 + .../DqInspectProgressController.java | 166 ++++++++++++++++++ 5 files changed, 286 insertions(+), 1 deletion(-) create mode 100644 jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectConstant.java create mode 100644 jeecg-module-supervision/src/main/java/org/jeecg/modules/demo/dqinspecttask/controller/DqInspectProgressController.java diff --git a/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectConstant.java b/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectConstant.java new file mode 100644 index 0000000..cb314a5 --- /dev/null +++ b/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectConstant.java @@ -0,0 +1,8 @@ +package org.jeecg.inspectimprove; + +import org.jeecg.modules.demo.dqinspecttask.entity.DqInspectTask; + +public class InspectConstant { + public static final String NEED_APPROVE_STR = "1"; + public static final String NOT_NEED_APPROVE_STR = "0"; +} diff --git a/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectImproveConfig.java b/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectImproveConfig.java index 508e1fd..a17211c 100644 --- a/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectImproveConfig.java +++ b/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectImproveConfig.java @@ -6,7 +6,7 @@ import org.springframework.stereotype.Component; @Data @Component -@ConfigurationProperties(prefix = "inspect-improve") +@ConfigurationProperties(prefix = "flow-biz") public class InspectImproveConfig { private InspectImproveProperties inspectImprove; @@ -35,5 +35,7 @@ public class InspectImproveConfig { private String workProgressKey; /** 完成状态 key */ private String completionStatusKey; + private String dqDeptId; + private String ldRoleId; } } diff --git a/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectImproveFlow.java b/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectImproveFlow.java index ac62420..90282c3 100644 --- a/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectImproveFlow.java +++ b/jeecg-boot-module/jeecg-module-flow/src/main/java/org/jeecg/inspectimprove/InspectImproveFlow.java @@ -4,9 +4,14 @@ import com.alibaba.fastjson.JSONObject; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang.StringUtils; +import org.flowable.engine.delegate.DelegateExecution; +import org.jeecg.common.system.api.ISysBaseAPI; +import org.jeecg.modules.demo.dqinspecttask.entity.DqInspectTask; +import org.jeecg.modules.demo.dqinspecttask.service.IDqInspectTaskService; import org.jeecg.modules.dj.inspectimprove.entity.DjInspectImprove; import org.jeecg.modules.dj.inspectimprove.service.IDjInspectImproveService; import org.jeecg.modules.extbpm.process.common.expression.FlowNodeExpression; +import org.jeecg.xispeak.XiSpeakConfig; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; @@ -21,6 +26,108 @@ public class InspectImproveFlow { private final InspectImproveConfig inspectImproveConfig; private final IDjInspectImproveService djInspectImproveService; private final FlowNodeExpression flowNodeExpression; + private final XiSpeakConfig xiSpeakConfig; + private final ISysBaseAPI iSysBaseAPI; + private final IDqInspectTaskService dqInspectTaskService; + + //流程表达式内用法 ${inspectImproveFlow.getDqDeptLdUserIdList()} + public List getDqDeptLdUserIdList() { + InspectImproveConfig.InspectImproveProperties props = inspectImproveConfig.getInspectImprove(); + if (props == null || !org.apache.shiro.util.StringUtils.hasText(props.getDqDeptId())) { + log.error("流程配置缺失: [flow-biz.inspect-improve.dq-dept-id] 未在 YAML 中定义"); + return Collections.emptyList(); + } + + log.info("正在查询部门: {} 下的角色: {} 的用户列表", props.getDqDeptId(), props.getLdRoleId()); + List userList = iSysBaseAPI.getUsersListByDeptIdAndRoleIdLocalApi( + props.getDqDeptId(), + props.getLdRoleId() + ); + log.info("查询到的用户为: {}", userList); + return userList; + } + + //流程表达式内用法 ${inspectImproveFlow.getDqDeptLdUserIdListLength()} + public int getDqDeptLdUserIdListLength() { + List dqDeptLdUserIdList = this.getDqDeptLdUserIdList(); + if (dqDeptLdUserIdList != null && !dqDeptLdUserIdList.isEmpty()) { + return dqDeptLdUserIdList.size(); + } + log.warn("dq部门ld角色没有对应用户"); + return 0; + } + + // 流程表达式内用法 ${inspectImproveFlow.getNeedDqLeaderApprove(execution)} + public String getNeedDqLeaderApprove(DelegateExecution execution) { + DqInspectTask temDqInspectTask = this.getDqInspectTask(execution); + + // 如果上一步返回了 null(说明数据缺失),为了流程安全,这里直接抛出异常,阻止流程往错误的方向流转 + if (temDqInspectTask == null) { + throw new IllegalStateException("无法判定是否需要审批:未找到对应的业务表单数据,流程暂停。"); + } + + // 字符串比对的优雅写法:把常量放在前面,天然防范 NPE + if (InspectConstant.NOT_NEED_APPROVE_STR.equals(temDqInspectTask.getIsNeedAppro()) + || StringUtils.isBlank(temDqInspectTask.getIsNeedAppro())) { + return InspectConstant.NOT_NEED_APPROVE_STR; + } + + return InspectConstant.NEED_APPROVE_STR; + } + + // 流程表达式内用法:${inspectImproveFlow.getImplDeptLeaderList(execution)} + public List getImplDeptLeaderList(DelegateExecution execution) { + + DqInspectTask temDqInspectTask = this.getDqInspectTask(execution); + if (temDqInspectTask == null) { + throw new IllegalStateException("无法获取审批人:未找到对应的业务表单数据,流程暂停。"); + } + + String measureDeptId = temDqInspectTask.getMeasureResDept(); + if (StringUtils.isBlank(measureDeptId)) { + String errorMsg = String.format("流程流转失败: 业务表单[ID:%s]中的整改责任部门(measureResDept)为空,无法匹配审批人。", temDqInspectTask.getId()); + log.error(errorMsg); + throw new IllegalStateException(errorMsg); // 保持严谨,核心数据缺失直接抛异常阻断 + } + + + InspectImproveConfig.InspectImproveProperties props = inspectImproveConfig.getInspectImprove(); + log.info("正在查询整改责任部门: {} 下的角色: {} 的领导列表", measureDeptId, props.getLdRoleId()); + List leaderList = iSysBaseAPI.getUsersListByDeptIdAndRoleIdLocalApi( + measureDeptId, + props.getLdRoleId() + ); + + if (leaderList == null || leaderList.isEmpty()) { + log.warn("【节点预警】整改责任部门: {} 下未配置角色: {} 的用户,审批人列表为空!", measureDeptId, props.getLdRoleId()); + return Collections.emptyList(); + } + + log.info("查询到的整改责任部门领导为:{}", leaderList); + return leaderList; + } + + // 流程表达式内用法:${inspectImproveFlow.getImplDeptLeaderListLength(execution)} + public int getImplDeptLeaderListLength(DelegateExecution execution) { + return this.getImplDeptLeaderList(execution).size(); + } + + private DqInspectTask getDqInspectTask(DelegateExecution execution) { + Object inspectTaskId = execution.getVariable(inspectImproveConfig.getInspectImprove().getBusinessKey()); + + // 统一校验 null 和空字符串 + if (inspectTaskId == null || StringUtils.isBlank(inspectTaskId.toString())) { + log.error("【流程异常】流程实例id为 {} 的流程内未获取到有效的业务表单id", execution.getProcessInstanceId()); + return null; // 明确返回 null,不给上游返回空壳对象 + } + + // 如果 getById 没查到,MyBatis-Plus 也会返回 null + DqInspectTask task = dqInspectTaskService.getById(inspectTaskId.toString()); + if (task == null) { + log.error("【数据异常】通过业务表单id {} 未查询到数据库中的任务记录", inspectTaskId); + } + return task; + } // =================================================================== // 通用工具方法 diff --git a/jeecg-boot-module/jeecg-module-flow/src/main/resources/application-flow.yml b/jeecg-boot-module/jeecg-module-flow/src/main/resources/application-flow.yml index 912d688..d2f5639 100644 --- a/jeecg-boot-module/jeecg-module-flow/src/main/resources/application-flow.yml +++ b/jeecg-boot-module/jeecg-module-flow/src/main/resources/application-flow.yml @@ -19,6 +19,8 @@ flow-biz: sdw-leader-list-key: "sdwLeaderList" is-end-key: "isEnd" inspect-improve: + dq-dept-id: "2044677628281720834" + ld-role-id: "2044680793306591234" business-key: "business_id" json-data-key: "json_data" form-url: "dj/inspectimprove/components/DjInspectImproveBPMForm" diff --git a/jeecg-module-supervision/src/main/java/org/jeecg/modules/demo/dqinspecttask/controller/DqInspectProgressController.java b/jeecg-module-supervision/src/main/java/org/jeecg/modules/demo/dqinspecttask/controller/DqInspectProgressController.java new file mode 100644 index 0000000..5447d53 --- /dev/null +++ b/jeecg-module-supervision/src/main/java/org/jeecg/modules/demo/dqinspecttask/controller/DqInspectProgressController.java @@ -0,0 +1,166 @@ +package org.jeecg.modules.demo.dqinspecttask.controller; + +import java.util.Arrays; +import java.io.IOException; +import java.io.UnsupportedEncodingException; +import java.net.URLDecoder; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.jeecg.common.api.vo.Result; +import org.jeecg.common.system.query.QueryGenerator; +import org.jeecg.modules.demo.dqinspecttask.entity.DqInspectProgress; +import org.jeecg.modules.demo.dqinspecttask.service.IDqInspectProgressService; + +import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; +import com.baomidou.mybatisplus.core.metadata.IPage; +import com.baomidou.mybatisplus.extension.plugins.pagination.Page; +import lombok.extern.slf4j.Slf4j; + +import org.jeecgframework.poi.excel.ExcelImportUtil; +import org.jeecgframework.poi.excel.def.NormalExcelConstants; +import org.jeecgframework.poi.excel.entity.ExportParams; +import org.jeecgframework.poi.excel.entity.ImportParams; +import org.jeecgframework.poi.excel.view.JeecgEntityExcelView; +import org.jeecg.common.system.base.controller.JeecgController; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.*; +import org.springframework.web.multipart.MultipartFile; +import org.springframework.web.multipart.MultipartHttpServletRequest; +import org.springframework.web.servlet.ModelAndView; +import com.alibaba.fastjson.JSON; +import io.swagger.v3.oas.annotations.tags.Tag; +import io.swagger.v3.oas.annotations.Operation; +import org.jeecg.common.aspect.annotation.AutoLog; + +/** + * @Description: 工作进展反馈 + * @Author: jeecg-boot + * @Date: 2026-05-28 + * @Version: V1.0 + */ +@Tag(name="工作进展反馈") +@RestController +@RequestMapping("/dqinspecttask/dqInspectTask") +@Slf4j +public class DqInspectProgressController extends JeecgController { + @Autowired + private IDqInspectProgressService dqInspectProgressService; + + /** + * 分页列表查询 + * + * @param dqInspectProgress + * @param pageNo + * @param pageSize + * @param req + * @return + */ + @Operation(summary="工作进展反馈-分页列表查询") + @GetMapping(value = "/listDqInspectProgressByMainId") + public Result> queryPageList(DqInspectProgress dqInspectProgress, + @RequestParam(name="pageNo", defaultValue="1") Integer pageNo, + @RequestParam(name="pageSize", defaultValue="10") Integer pageSize, + HttpServletRequest req) { + QueryWrapper queryWrapper = QueryGenerator.initQueryWrapper(dqInspectProgress, req.getParameterMap()); + Page page = new Page(pageNo, pageSize); + IPage pageList = dqInspectProgressService.page(page, queryWrapper); + return Result.OK(pageList); + } + + /** + * 添加 + * + * @param dqInspectProgress + * @return + */ + @AutoLog(value = "工作进展反馈-添加") + @Operation(summary="工作进展反馈-添加") + @PostMapping(value = "/addDqInspectProgress") + public Result add(@RequestBody DqInspectProgress dqInspectProgress) { + dqInspectProgressService.save(dqInspectProgress); + return Result.OK("添加成功!"); + } + + /** + * 编辑 + * + * @param dqInspectProgress + * @return + */ + @AutoLog(value = "工作进展反馈-编辑") + @Operation(summary="工作进展反馈-编辑") + @PostMapping(value = "/editDqInspectProgress") + public Result edit(@RequestBody DqInspectProgress dqInspectProgress) { + dqInspectProgressService.updateById(dqInspectProgress); + return Result.OK("编辑成功!"); + } + + /** + * 通过id删除 + * + * @param id + * @return + */ + @AutoLog(value = "工作进展反馈-通过id删除") + @Operation(summary="工作进展反馈-通过id删除") + @DeleteMapping(value = "/deleteDqInspectProgress") + public Result delete(@RequestParam(name="id",required=true) String id) { + dqInspectProgressService.removeById(id); + return Result.OK("删除成功!"); + } + + /** + * 批量删除 + * + * @param ids + * @return + */ + @AutoLog(value = "工作进展反馈-批量删除") + @Operation(summary="工作进展反馈-批量删除") + @DeleteMapping(value = "/deleteBatchDqInspectProgress") + public Result deleteBatch(@RequestParam(name="ids",required=true) String ids) { + this.dqInspectProgressService.removeByIds(Arrays.asList(ids.split(","))); + return Result.OK("批量删除成功!"); + } + + /** + * 通过id查询 + * + * @param id + * @return + */ + @Operation(summary="工作进展反馈-通过id查询") + @GetMapping(value = "/queryDqInspectProgressById") + public Result queryById(@RequestParam(name="id",required=true) String id) { + DqInspectProgress dqInspectProgress = dqInspectProgressService.getById(id); + if(dqInspectProgress==null) { + return Result.error("未找到对应数据"); + } + return Result.OK(dqInspectProgress); + } + + /** + * 导出excel + * + * @param request + * @param dqInspectProgress + */ + @RequestMapping(value = "/exportDqInspectProgress") + public ModelAndView exportXls(HttpServletRequest request, DqInspectProgress dqInspectProgress) { + return super.exportXls(request, dqInspectProgress, DqInspectProgress.class, "工作进展反馈"); + } + + /** + * 通过excel导入数据 + * + * @param request + * @param response + * @return + */ + @RequestMapping(value = "/importDqInspectProgress", method = RequestMethod.POST) + public Result importExcel(HttpServletRequest request, HttpServletResponse response) { + return super.importExcel(request, response, DqInspectProgress.class); + } + +}