diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow/FlowableRest.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow/FlowableRest.java index 963041ad..9566b14c 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow/FlowableRest.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow/FlowableRest.java @@ -28,7 +28,6 @@ package com.yxt.supervise.flowable.biz.flow; import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONObject; -import com.yxt.anrui.flowable.api.flow.*; import com.yxt.supervise.flowable.api.flow.*; import com.yxt.supervise.flowable.api.flowcomment.FlowComment; import com.yxt.supervise.flowable.api.flowtask.LatestTaskVo; diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow/FlowableService.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow/FlowableService.java index fdc7a008..645a4891 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow/FlowableService.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow/FlowableService.java @@ -2,7 +2,6 @@ package com.yxt.supervise.flowable.biz.flow; import cn.hutool.core.bean.BeanUtil; -import com.yxt.anrui.flowable.api.flow.*; import com.yxt.supervise.flowable.api.flow.*; import com.yxt.supervise.flowable.api.flowtask.FlowTask; import com.yxt.supervise.flowable.api.flowtask.FlowTaskVo; diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow2/FlowRest.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow2/FlowRest.java new file mode 100644 index 00000000..433904e3 --- /dev/null +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow2/FlowRest.java @@ -0,0 +1,93 @@ +package com.yxt.supervise.flowable.biz.flow2; + +import com.alibaba.fastjson.JSONObject; +import com.google.common.util.concurrent.ThreadFactoryBuilder; +import com.yxt.common.base.utils.StringUtils; +import com.yxt.common.core.result.ResultBean; +import com.yxt.supervise.flowable.api.flow.UpdateFlowFieldVo; +import com.yxt.supervise.flowable.sqloperationsymbol.BusinessVariables; +import io.swagger.annotations.ApiOperation; +import org.apache.tomcat.util.threads.ThreadPoolExecutor; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.PostMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +import java.util.HashMap; +import java.util.Map; +import java.util.concurrent.*; + +/** + * @description: + * @author: dimengzhe + * @date: 2023/11/28 + **/ +@RestController +@RequestMapping("v2/flow") +public class FlowRest { + + Logger log = LoggerFactory.getLogger(FlowRest.class); + + @Autowired + private FlowService flowService; + + @ApiOperation(value = "启动流程") + @PostMapping(value = "/startProcess") + public ResultBean startProcess(BusinessVariables bv) { + ResultBean rb = ResultBean.fireFail(); + //获取表单中的参数 + Map formVariables = bv.getFormVariables(); + formVariables = formVariables == null ? new HashMap<>() : formVariables; + //发起人的组织全路径 + String orgPath = bv.getOrgSidPath(); + formVariables.put("createrOrgPath", orgPath); + formVariables.put("businessSid", bv.getBusinessSid()); + //获取下一环节待办人 + if (StringUtils.isBlank(bv.getNextNodeUserSids())) { + ResultBean userResultBean = flowService.getNextNodeUser(bv); + if(userResultBean.getSuccess()){ + return rb.setMsg(userResultBean.getMsg()); + } + bv.setNextNodeUserSids(userResultBean.getData()); + } + //启动流程实例 + ResultBean startResultBean = flowService.businessStartProcessInstanceById(bv); + return startResultBean; + } + + public ResultBean handleProsess(BusinessVariables bv) { + ResultBean rb = ResultBean.fireFail(); + ResultBean updateFlowFieldVoResultBean = flowService.handleProsess(bv, true); + //添加抄送 + log.info("流程返回:{}", JSONObject.toJSONString(updateFlowFieldVoResultBean)); + //需要判断办结后再执行 TODO + if (updateFlowFieldVoResultBean.getSuccess()) { + log.info("流程返回:{}", JSONObject.toJSONString(updateFlowFieldVoResultBean)); + if ("Event_end".equals(updateFlowFieldVoResultBean.getData().getTaskDefKey())) { + try { + ThreadFactory namedThreadFactory = new ThreadFactoryBuilder() + .setNameFormat("demo-pool-%d").build(); + ExecutorService pool = new ThreadPoolExecutor(2, 100, + 0L, TimeUnit.MILLISECONDS, + new LinkedBlockingQueue(1024), namedThreadFactory, new ThreadPoolExecutor.AbortPolicy()); + + Future future1 = pool.submit(() -> { + HashMap map = new HashMap<>(); + map.put("bv", bv); + UpdateFlowFieldVo ufVo = updateFlowFieldVoResultBean.getData(); + ufVo.setTaskId(bv.getTaskId()); + map.put("uff", ufVo); +// flowService.cc(map, bv.getTaskDefKey()); + }); + } catch (Exception e) { + e.printStackTrace(); + return rb.setMsg("抄送失败"); + } + } + } + return updateFlowFieldVoResultBean; + } + +} diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow2/FlowService.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow2/FlowService.java new file mode 100644 index 00000000..f6f74230 --- /dev/null +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flow2/FlowService.java @@ -0,0 +1,506 @@ +package com.yxt.supervise.flowable.biz.flow2; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.JSONArray; +import com.alibaba.fastjson.JSONObject; +import com.yxt.common.base.utils.StringUtils; +import com.yxt.common.core.result.ResultBean; +import com.yxt.supervise.flowable.api.flow.UpdateFlowFieldVo; +import com.yxt.supervise.flowable.api.flowcomment.FlowComment; +import com.yxt.supervise.flowable.api.flowtask.LatestTaskVo; +import com.yxt.supervise.flowable.biz.flowtask.FlowTaskService; +import com.yxt.supervise.flowable.biz.process.ExpressionCmd; +import com.yxt.supervise.flowable.common.ProcessConstants; +import com.yxt.supervise.flowable.sqloperationsymbol.BusinessVariables; +import com.yxt.supervise.system.sysuser.SysUserFeign; +import com.yxt.supervise.system.sysuser.SysUserVo; +import com.yxt.supervise.system.sysuser.UserQuery; +import com.yxt.supervise.system.sysuser.UserssQuery; +import lombok.extern.slf4j.Slf4j; +import org.flowable.bpmn.model.*; +import org.flowable.common.engine.impl.identity.Authentication; +import org.flowable.engine.*; +import org.flowable.engine.impl.cfg.ProcessEngineConfigurationImpl; +import org.flowable.engine.repository.ProcessDefinition; +import org.flowable.engine.runtime.ProcessInstance; +import org.flowable.task.api.DelegationState; +import org.flowable.task.api.Task; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +import java.util.*; + +/** + * @description: + * @author: dimengzhe + * @date: 2023/11/28 + **/ +@Service +@Slf4j +public class FlowService { + + @Autowired + private SysUserFeign sysUserFeign; + @Autowired + RepositoryService repositoryService; + @Autowired + ManagementService managementService; + @Autowired + RuntimeService runtimeService; + @Autowired + ProcessEngineConfigurationImpl processEngineConfiguration; + @Autowired + protected IdentityService identityService; + @Autowired + protected TaskService taskService; + @Autowired + private FlowTaskService flowTaskService; + + public ResultBean getNextNodeUser(BusinessVariables bv) { + ResultBean rb = ResultBean.fireFail(); + //根据业务参数取流程流转的环节 信息 + List> list = (List>) getProcessCirculationNodesByMap(bv).getData(); + if (list == null || list.size() < 2) { + return rb.setMsg("流程设计问题"); + } + //取第二个环节的配置角色 + Object o = list.get(1).get("candidateGroups"); + if (o == null) { + return rb.setMsg("流程设计问题"); + } + JSONArray jsonArray = JSONArray.parseArray(JSON.toJSONString(o)); + String roleSid = jsonArray.get(0).toString(); + //根据组织架构、角色两个参数取相关符合条件的用户信息 + UserQuery userQuery = new UserQuery(); + userQuery.setRoleSid(roleSid); + userQuery.setProjectSid(bv.getProjectSid()); + String nextNodeUserSids_ = ""; + List sysUserVos = sysUserFeign.getUserByRoleAndProject(userQuery).getData(); + if (sysUserVos == null || sysUserVos.size() < 1) { + return rb.setMsg("下一环节无用户"); + } else { + StringBuilder nextNodeUserSids = new StringBuilder(); + for (SysUserVo su : sysUserVos) { + nextNodeUserSids.append(su.getSid()).append(","); + } + //符合条件的用户的sid,拼接的字符串 + nextNodeUserSids_ = nextNodeUserSids.toString(); + nextNodeUserSids_ = nextNodeUserSids_.substring(0, nextNodeUserSids_.length() - 1); + } + return rb.success().setData(nextNodeUserSids_); + } + + private ResultBean getProcessCirculationNodesByMap(BusinessVariables bv) { + ResultBean>> rb = new ResultBean>>(); + String modelId = bv.getModelId(); + List flowElements = calApprovePath(modelId, bv.getFormVariables()); + List> list = new ArrayList<>(); + for (FlowElement f : flowElements) { + Map map = new HashMap<>(); + map.put("name", f.getName()); + map.put("id", f.getId()); + String s = JSON.toJSONString(f); + JSONObject jsonObject = JSONObject.parseObject(s); + log.info("item:{}", jsonObject); + Object candidateGroups = jsonObject.get("candidateGroups"); + map.put("candidateGroups", candidateGroups); + list.add(map); + } + return rb.setData(list); + } + + /** + * 1. 首先拿到BpmnModel,所有流程定义信息都可以通过BpmnModel获取;若流程尚未发起,则用modelId查询最新部署的流程定义数据; + * 若流程已经发起,可以通过流程实例的processDefinitionId查询流程定义的历史数据。 + * + * @param variableMap 流程变量,用于计算条件分支 + */ + public List calApprovePath(String modelId, Map variableMap) { + BpmnModel bpmnModel = repositoryService.getBpmnModel(modelId); + Collection flowElements = new ArrayList<>(); + Collection flowElements2 = bpmnModel.getMainProcess().getFlowElements(); + flowElements.addAll(flowElements2); + List passElements = new ArrayList<>(); + dueStartElement(passElements, flowElements, variableMap); + return passElements; + } + + /** + * 2. 找到开始节点,通过它的目标节点,然后再不断往下找。 + */ + private void dueStartElement(List passElements, Collection flowElements, Map variableMap) { + Optional startElementOpt = flowElements.stream().filter(flowElement -> flowElement instanceof StartEvent).findFirst(); + startElementOpt.ifPresent(startElement -> { + flowElements.remove(startElement); + List outgoingFlows = ((StartEvent) startElement).getOutgoingFlows(); + String targetRef = outgoingFlows.get(0).getTargetRef(); + // 根据ID找到FlowElement + FlowElement targetElementOfStartElement = getFlowElement(flowElements, targetRef); + if (targetElementOfStartElement instanceof UserTask) { + this.getPassElementList(passElements, flowElements, targetElementOfStartElement, variableMap); + } + }); + } + + /** + * 3. 我只用到了UserTask、ExclusiveGateway、ParallelGateway,所以代码里只列举了这三种,如果用到了其他的,可以再自己补充 + */ + private void getPassElementList(List passElements, Collection flowElements, FlowElement curFlowElement, Map variableMap) { + // 任务节点 + if (curFlowElement instanceof UserTask) { + this.dueUserTaskElement(passElements, flowElements, curFlowElement, variableMap); + return; + } + // 排他网关 + if (curFlowElement instanceof ExclusiveGateway) { + this.dueExclusiveGateway(passElements, flowElements, curFlowElement, variableMap); + return; + } + // 并行网关 + if (curFlowElement instanceof ParallelGateway) { + this.dueParallelGateway(passElements, flowElements, curFlowElement, variableMap); + } + } + + private FlowElement getFlowElement(Collection flowElements, String targetRef) { + return flowElements.stream().filter(flowElement -> targetRef.equals(flowElement.getId())).findFirst().orElse(null); + } + + private void dueUserTaskElement(List passElements, Collection flowElements, + FlowElement curFlowElement, Map variableMap) { + passElements.add(curFlowElement); + List outgoingFlows = ((UserTask) curFlowElement).getOutgoingFlows(); + String targetRef = outgoingFlows.get(0).getTargetRef(); + if (outgoingFlows.size() > 1) { + // 找到表达式成立的sequenceFlow + SequenceFlow sequenceFlow = getSequenceFlow(variableMap, outgoingFlows); + targetRef = sequenceFlow.getTargetRef(); + } + // 根据ID找到FlowElement + FlowElement targetElement = getFlowElement(flowElements, targetRef); + this.getPassElementList(passElements, flowElements, targetElement, variableMap); + } + + + private void dueExclusiveGateway(List passElements, Collection flowElements, FlowElement curFlowElement, Map variableMap) { + // 获取符合条件的sequenceFlow的目标FlowElement + List exclusiveGatewayOutgoingFlows = ((ExclusiveGateway) curFlowElement).getOutgoingFlows(); + flowElements.remove(curFlowElement); + // 找到表达式成立的sequenceFlow + SequenceFlow sequenceFlow = getSequenceFlow(variableMap, exclusiveGatewayOutgoingFlows); + // 根据ID找到FlowElement + FlowElement targetElement = getFlowElement(flowElements, sequenceFlow.getTargetRef()); + this.getPassElementList(passElements, flowElements, targetElement, variableMap); + } + + private void dueParallelGateway(List passElements, Collection flowElements, FlowElement curFlowElement, Map variableMap) { + FlowElement targetElement; + List parallelGatewayOutgoingFlows = ((ParallelGateway) curFlowElement).getOutgoingFlows(); + for (SequenceFlow sequenceFlow : parallelGatewayOutgoingFlows) { + targetElement = getFlowElement(flowElements, sequenceFlow.getTargetRef()); + this.getPassElementList(passElements, flowElements, targetElement, variableMap); + } + } + + /** + * 4. 根据传入的变量,计算出表达式成立的那一条SequenceFlow + * + * @param variableMap + * @param outgoingFlows + * @return + */ + private SequenceFlow getSequenceFlow(Map variableMap, List outgoingFlows) { + Optional sequenceFlowOpt = outgoingFlows.stream().filter(item -> { + try { + return this.getElValue(item.getConditionExpression(), variableMap); + } catch (Exception e) { + log.error(e.getMessage(), e); + return false; + } + }).findFirst(); + return sequenceFlowOpt.orElse(outgoingFlows.get(0)); + } + + private boolean getElValue(String exp, Map variableMap) { + return managementService.executeCommand(new ExpressionCmd(runtimeService, processEngineConfiguration, null, exp, variableMap)); + } + + public ResultBean businessStartProcessInstanceById(BusinessVariables bv) { + ResultBean rb = ResultBean.fireFail(); + UpdateFlowFieldVo updateFlowFieldVo = new UpdateFlowFieldVo(); + String procDefId = bv.getModelId(); + String userSid = bv.getUserSid(); + String nextNodeUserSids = bv.getNextNodeUserSids(); + Map variables = bv.getFormVariables(); + Map variablesSeconds = bv.getFormVariables(); + //根据流程定义id查询 + ProcessDefinition processDefinition = repositoryService.createProcessDefinitionQuery().processDefinitionId(procDefId) + .latestVersion().singleResult(); + if (Objects.nonNull(processDefinition) && processDefinition.isSuspended()) { + return rb.setMsg("流程已被挂起,请先激活流程"); + } + // 设置流程发起人Id到流程中 + ResultBean sysUserVoResultBean = sysUserFeign.fetchBySid(userSid); + SysUserVo sysUser = sysUserVoResultBean.getData(); + identityService.setAuthenticatedUserId(sysUser.getSid()); + variables.put(ProcessConstants.PROCESS_INITIATOR, userSid); + variables.put(ProcessConstants.USER_TYPE_ASSIGNEE, userSid); + ProcessInstance processInstance = runtimeService.startProcessInstanceById(procDefId, variables); + // 给第一步申请人节点设置任务执行人和意见 todo:第一个节点不设置为申请人节点有点问题? + Task task = taskService.createTaskQuery().processInstanceId(processInstance.getProcessInstanceId()).singleResult(); + if (Objects.nonNull(task)) { + taskService.addComment(task.getId(), processInstance.getProcessInstanceId(), FlowComment.START.getType(), + sysUser.getName() + "发起流程申请"); + taskService.setAssignee(task.getId(), userSid); + taskService.complete(task.getId(), variables); + } + //根据流程实例的id查询最新的待办环节 + ResultBean> latestTasksNew = flowTaskService.getLatestTasksNew(processInstance.getId()); + List data = latestTasksNew.getData(); + LatestTaskVo latestTaskVo = data.get(0); + String id_ = latestTaskVo.getId_(); + String task_def_key_ = latestTaskVo.getTask_def_key_(); + //查询下一环节是否有转办并添加评论 +// nextNodeUserSids = change(nextNodeUserSids, processInstance.getProcessInstanceId()); + taskService.setAssignee(id_, nextNodeUserSids); + taskService.setVariablesLocal(id_, variables); + if (bv.getUserSid().equals(nextNodeUserSids)) { + //如果申请人与下一环节审批人相同,则自动审批 + bv.setModelId(procDefId); + bv.setInstanceId(task.getProcessInstanceId()); + bv.setTaskId(id_); + bv.setUserSid(nextNodeUserSids); + bv.setBusinessSid(bv.getBusinessSid()); + bv.setTaskDefKey(task_def_key_); + bv.setFormVariables(variables); + bv.setOrgSidPath(bv.getOrgSidPath()); + bv.setFormVariables(variablesSeconds); + bv.setComment("因与申请人相同,系统自动处理,需以下一级审批人审批意见为准!"); + bv.setNextNodeUserSids(""); + ResultBean updateFlowFieldVoResultBean = handleProsess(bv, false); + if (updateFlowFieldVoResultBean.getSuccess() && updateFlowFieldVoResultBean.getData() != null) { + UpdateFlowFieldVo vo = updateFlowFieldVoResultBean.getData(); + updateFlowFieldVo.setProcInsId(vo.getProcInsId()); + updateFlowFieldVo.setNodeState(vo.getNodeState()); + updateFlowFieldVo.setTaskId(vo.getTaskId()); + updateFlowFieldVo.setTaskDefKey(vo.getTaskDefKey()); + updateFlowFieldVo.setProcDefId(bv.getModelId()); + updateFlowFieldVo.setSid(bv.getBusinessSid()); + return rb.success().setData(updateFlowFieldVo).setMsg("流程启动成功"); + } + } + updateFlowFieldVo.setProcInsId(task.getProcessInstanceId()); + updateFlowFieldVo.setNodeState(latestTaskVo.getName_()); + updateFlowFieldVo.setTaskId(id_); + updateFlowFieldVo.setTaskDefKey(task_def_key_); + updateFlowFieldVo.setProcDefId(bv.getModelId()); + updateFlowFieldVo.setSid(bv.getBusinessSid()); + return rb.success().setData(updateFlowFieldVo).setMsg("流程启动成功"); + } + + /** + * 办理 + * + * @param bv + * @param b + * @return + */ + public ResultBean handleProsess(BusinessVariables bv, boolean b) { + ResultBean rb = ResultBean.fireFail(); + UpdateFlowFieldVo vo = new UpdateFlowFieldVo(); + //获取表单中的参数 + Map formVariables = bv.getFormVariables(); + formVariables = formVariables == null ? new HashMap<>() : formVariables; + formVariables.put("businessSid", bv.getBusinessSid()); + String nextUserSid = bv.getNextNodeUserSids(); + String taskId = bv.getTaskId(); + String userSid = bv.getUserSid(); + String instanceId = bv.getInstanceId(); + String comment = bv.getComment(); + String nodeState = ""; + String taskDefKey = ""; + String projectSid = bv.getProjectSid(); + //设置下一环节审批人是否自动审批通过,默认否 + boolean contains = false; + //设置是否是管理员自动审批,默认否 + boolean adminContains = false; + if (StringUtils.isBlank(nextUserSid)) { + ResultBean stringResultBean = getNextNodeUserSidsOfSubmit(bv); + if (!stringResultBean.getSuccess()) { + //下一环节用户为空的情况 + return rb.setMsg("下一环节无用户"); + } else { + nextUserSid = stringResultBean.getData(); + } + } + //查询任务id为taskId的任务是否存在 + Task task = taskService.createTaskQuery().taskId(taskId).singleResult(); + if (Objects.isNull(task)) { + return rb.setMsg("任务不存在"); + } + String assignee = task.getAssignee(); + if (b && (StringUtils.isNotBlank(assignee) && assignee.indexOf(userSid) < 0)) { + return rb.setMsg("当前用户不是环节的待办人,不能进行办理操作!"); + } + + if (DelegationState.PENDING.equals(task.getDelegationState())) { + //加签 + Authentication.setAuthenticatedUserId(userSid); + taskService.addComment(taskId, instanceId, + FlowComment.DELEGATE.getType(), comment); + taskService.resolveTask(taskId, formVariables); + nodeState = task.getName(); + taskDefKey = task.getTaskDefinitionKey(); + } else { + //当前环节办理通过,且将下一环节用户放入流程中 + taskService.addComment(taskId, instanceId, FlowComment.NORMAL.getType(), comment); + log.error("taskid:{},userSid:{}", taskId, userSid); + log.error("formVariables:{}", JSON.toJSONString(formVariables)); + taskService.setAssignee(taskId, userSid); + taskService.complete(taskId, formVariables);//当前用户办理通过 + //根据流程实例的id取最新的待办环节,给环节设置上用户sid + ResultBean> ll = flowTaskService.getLatestTasksNew(instanceId); + if (ll.getData().size() > 0) { + LatestTaskVo latestTaskVo = ll.getData().get(0); + String id_ = latestTaskVo.getId_(); + //查询下一环节用户是否有转办人 +// nextUserSid = change(nextUserSid, bv.getInstanceId()); + taskService.setAssignee(id_, nextUserSid);//将下一环节用户放入流程中 + vo.setTaskId(id_); + //在act_ru_variable表中增加环节上的业务参数的变量 + taskService.setVariablesLocal(id_, formVariables); + nodeState = latestTaskVo.getName_(); + taskDefKey = latestTaskVo.getTask_def_key_(); + } else { + nodeState = FlowComment.SETTLE.getRemark(); + taskDefKey = "Event_end"; + vo.setNodeState(FlowComment.SETTLE.getRemark()); + } + } + /* //设置管理员是否自动审批的字段是否是是。//若下一环节用户与系统管理员一致,则自动审批 + if (adminContains) { + bv.setUserSid(nextUserSid); + bv.setTaskId(vo.getTaskId()); + bv.setTaskDefKey(taskDefKey); + bv.setComment("系统自动跳过"); + bv.setNextNodeUserSids(""); + return handleProsess(bv, false); + }*/ + //获取该流程所有要走的环节节点 + List flowElements = calApprovePath(bv.getModelId(), + bv.getFormVariables()); + for (int i = 0; i < flowElements.size(); i++) { + FlowElement flowElement = flowElements.get(i); + String id = flowElement.getId(); + if (taskDefKey.equals(id) && i + 1 < flowElements.size()) { + //获取下下一环节 + FlowElement flowElement1 = flowElements.get(i + 1); + List sysUserVoLists2 = new ArrayList<>(); + if (i + 2 < flowElements.size()) { + //获取下下下一环节用户 + FlowElement flowElement2 = flowElements.get(i + 2); + if (flowElement2 instanceof UserTask) { + UserTask userTask = (UserTask) flowElement2; + List candidateGroups = userTask.getCandidateGroups(); + UserssQuery userssQuery = new UserssQuery(); + userssQuery.setCandidateGroups(candidateGroups); + userssQuery.setProjectSid(projectSid); + sysUserVoLists2 = sysUserFeign.getUserByRoleAndProject2(userssQuery).getData(); + if (sysUserVoLists2 == null) { + sysUserVoLists2 = new ArrayList<>(); + } + } + } + if (flowElement1 instanceof UserTask) { + UserTask userTask = (UserTask) flowElement1; + List candidateGroups = userTask.getCandidateGroups(); + List sysUserVoLists = new ArrayList<>(); + UserssQuery userssQuery = new UserssQuery(); + userssQuery.setCandidateGroups(candidateGroups); + userssQuery.setProjectSid(projectSid); + sysUserVoLists = sysUserFeign.getUserByRoleAndProject2(userssQuery).getData(); + if (sysUserVoLists == null) { + sysUserVoLists = new ArrayList<>(); + } + //当前环节运营部总经理 刘丽艳 点击同意 下一环节 事业部副总经理 (nextUserSid) 和事业部总经理(sysUserVoLists.get(0).getSid()) + //判断查询回来的用户的集合size是1 并且用户的sid和下一环节的用户的sid相同。 + if (sysUserVoLists.size() == 1 && sysUserVoLists.get(0).getSid().equals(nextUserSid)) { + contains = true; + break; + } + //如果下下一环节无用户,下下下一环节用户与下一环节用户相同且只有一个,则下一环节用户自动审批。 + if (sysUserVoLists.size() == 0 && sysUserVoLists2.size() == 1 && sysUserVoLists2.get(0).getSid().equals(nextUserSid)) { + contains = true; + break; + } + } + } + if (contains) { + break; + } + } + if (contains) { + bv.setUserSid(nextUserSid); + bv.setTaskId(vo.getTaskId()); + bv.setTaskDefKey(taskDefKey); + bv.setComment("因与下一级审批人相同,系统自动处理,需以下一级审批人审批意见为准!"); + return handleProsess(bv, false); + } + vo.setProcInsId(instanceId); + vo.setProcDefId(bv.getModelId()); + vo.setNodeState(nodeState); + vo.setTaskDefKey(taskDefKey); + vo.setSid(bv.getBusinessSid()); + return rb.success().setData(vo); + } + + /** + * 获取下一环节用户 + * + * @param bv + * @return + */ + public ResultBean getNextNodeUserSidsOfSubmit(BusinessVariables bv) { + ResultBean rb = ResultBean.fireFail(); + String projectSid = bv.getProjectSid(); + String taskDefKey = bv.getTaskDefKey(); + //根据业务参数取流程流转的环节 信息 + List> list = (List>) getProcessCirculationNodesByMap(bv).getData(); + Map task_map = new HashMap<>(); + boolean endTask = true; + for (int i = 0; i < list.size(); i++) { + String id = list.get(i).get("id").toString(); + if (id.equals(taskDefKey) && i + 1 < list.size()) { + task_map = list.get(i + 1); + endTask = false; + } + } + if (endTask) { + task_map.put("name", "结束"); + return rb.success(); + } else { + Object o = task_map.get("candidateGroups"); + JSONArray jsonArray = JSONArray.parseArray(JSON.toJSONString(o)); + String roleSid = jsonArray.get(0).toString(); + //根据组织架构、角色两个参数取相关符合条件的用户信息 + UserQuery userQuery = new UserQuery(); + userQuery.setRoleSid(roleSid); + userQuery.setProjectSid(projectSid); + String nextNodeUserSids_ = ""; + List sysUserVos = sysUserFeign.getUserByRoleAndProject(userQuery).getData(); + if (sysUserVos == null || sysUserVos.size() < 1) { + return rb; + } else { + StringBuilder nextNodeUserSids = new StringBuilder(); + for (SysUserVo su : sysUserVos) { + nextNodeUserSids.append(su.getSid()).append(","); + } + //符合条件的用户的sid,拼接的字符串 + nextNodeUserSids_ = nextNodeUserSids.toString(); + nextNodeUserSids_ = nextNodeUserSids_.substring(0, nextNodeUserSids_.length() - 1); + } + return rb.success().setData(nextNodeUserSids_); + } + } + +} diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flowtask/FlowTaskController.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flowtask/FlowTaskController.java index 94e4efa3..11f1dc65 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flowtask/FlowTaskController.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flowtask/FlowTaskController.java @@ -5,7 +5,6 @@ import com.alibaba.fastjson.JSONArray; import com.alibaba.fastjson.JSONObject; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.yxt.supervise.flowable.api.flow.UserAndOrgPath; -import com.yxt.anrui.flowable.api.flowtask.*; import com.yxt.supervise.flowable.api.utils.RecordQuery; import com.yxt.supervise.flowable.biz.process.ProcessService; import com.yxt.supervise.flowable.sqloperationsymbol.BusinessTaskParam; diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flowtask/FlowTaskService.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flowtask/FlowTaskService.java index 6466fab3..b528d4c1 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flowtask/FlowTaskService.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/flowtask/FlowTaskService.java @@ -9,7 +9,6 @@ import com.google.common.collect.Lists; import com.yxt.supervise.flowable.api.flow.UserAndOrgPath; import com.yxt.supervise.flowable.api.flowcomment.FlowComment; import com.yxt.supervise.flowable.api.flowcomment.FlowCommentDto; -import com.yxt.anrui.flowable.api.flowtask.*; import com.yxt.supervise.flowable.api.sysform.SysForm; import com.yxt.supervise.flowable.api.sysprourl.SysProUrlVo; import com.yxt.supervise.flowable.biz.flow.FlowableService; diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/processcomment/ProcessCommentRest.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/processcomment/ProcessCommentRest.java index 97bd4e28..4814c39f 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/processcomment/ProcessCommentRest.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/processcomment/ProcessCommentRest.java @@ -25,7 +25,6 @@ *********************************************************/ package com.yxt.supervise.flowable.biz.processcomment; -import com.yxt.anrui.flowable.api.processcomment.*; import com.yxt.common.core.query.PagerQuery; import com.yxt.common.core.result.ResultBean; import com.yxt.common.core.vo.PagerVo; diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/processcomment/ProcessCommentService.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/processcomment/ProcessCommentService.java index b31bbee4..5e9c0682 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/processcomment/ProcessCommentService.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/processcomment/ProcessCommentService.java @@ -29,7 +29,6 @@ import cn.hutool.core.bean.BeanUtil; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.baomidou.mybatisplus.core.metadata.IPage; import com.yxt.supervise.flowable.api.flowtask.AppUserVo; -import com.yxt.anrui.flowable.api.processcomment.*; import com.yxt.common.base.config.component.FileUploadComponent; import com.yxt.supervise.flowable.api.processcomment.*; import com.yxt.supervise.system.sysuser.SysUserFeign; diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/sysprourl/SysProUrlController.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/sysprourl/SysProUrlController.java index fce99932..e7be20f9 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/sysprourl/SysProUrlController.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/sysprourl/SysProUrlController.java @@ -3,7 +3,6 @@ package com.yxt.supervise.flowable.biz.sysprourl; import com.baomidou.mybatisplus.core.metadata.IPage; import com.yxt.supervise.flowable.api.sysdeployform.SysDeployForm; import com.yxt.supervise.flowable.api.sysform.SysForm; -import com.yxt.anrui.flowable.api.sysprourl.*; import com.yxt.supervise.flowable.biz.sysdeployform.SysDeployFormService; import com.yxt.common.base.utils.PagerUtil; import com.yxt.common.core.query.PagerQuery; diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/sysprourl/SysProUrlService.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/sysprourl/SysProUrlService.java index 88d60645..2b9ec048 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/sysprourl/SysProUrlService.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/flowable/biz/sysprourl/SysProUrlService.java @@ -4,7 +4,6 @@ import cn.hutool.core.bean.BeanUtil; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.baomidou.mybatisplus.core.metadata.IPage; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; -import com.yxt.anrui.flowable.api.sysprourl.*; import com.yxt.common.base.service.MybatisBaseService; import com.yxt.common.core.query.PagerQuery; import com.yxt.common.core.result.ResultBean; diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserFeign.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserFeign.java index 76b04fd1..ee5d2ded 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserFeign.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserFeign.java @@ -235,4 +235,8 @@ public interface SysUserFeign { @ApiModelProperty("根据项目和角色获取用户") @GetMapping("getUserByRoleAndProject") public ResultBean> getUserByRoleAndProject(@SpringQueryMap UserQuery userQuery); + + @ApiModelProperty("根据项目和角色获取用户") + @GetMapping("getUserByRoleAndProject2") + public ResultBean> getUserByRoleAndProject2(@SpringQueryMap UserssQuery userQuery); } \ No newline at end of file diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserFeignFallback.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserFeignFallback.java index a48f7a05..370e6eff 100644 --- a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserFeignFallback.java +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserFeignFallback.java @@ -224,4 +224,9 @@ public class SysUserFeignFallback implements SysUserFeign { public ResultBean> getUserByRoleAndProject(UserQuery userQuery) { return null; } + + @Override + public ResultBean> getUserByRoleAndProject2(UserssQuery userQuery) { + return null; + } } \ No newline at end of file diff --git a/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/UserssQuery.java b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/UserssQuery.java new file mode 100644 index 00000000..7656782b --- /dev/null +++ b/yxt_supervise/supervise-flowable/supervise-flowable-biz/src/main/java/com/yxt/supervise/system/sysuser/UserssQuery.java @@ -0,0 +1,19 @@ +package com.yxt.supervise.system.sysuser; + +import lombok.Data; + +import java.util.ArrayList; +import java.util.List; + +/** + * @description: + * @author: dimengzhe + * @date: 2023/11/28 + **/ +@Data +public class UserssQuery { + + private List candidateGroups = new ArrayList<>(); + + private String projectSid; +} diff --git a/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserRest.java b/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserRest.java index 92545fa7..6406fb23 100644 --- a/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserRest.java +++ b/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserRest.java @@ -733,6 +733,11 @@ public class SysUserRest implements SysUserFeign { return sysUserService.getUserByRoleAndProject(userQuery); } + @GetMapping("getUserByRoleAndProject2") + public ResultBean> getUserByRoleAndProject2(@SpringQueryMap UserssQuery userQuery) { + return sysUserService.getUserByRoleAndProject2(userQuery); + } + @GetMapping("getUserByType") public ResultBean getUserByType(@RequestParam("userType") String userType) { return sysUserService.getUserByType(userType); diff --git a/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserService.java b/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserService.java index 2253bc03..c414f6a0 100644 --- a/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserService.java +++ b/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/SysUserService.java @@ -1602,6 +1602,36 @@ public class SysUserService extends MybatisBaseService { return rb.success().setData(sysUserVoList); } + public ResultBean> getUserByRoleAndProject2(UserssQuery query) { + ResultBean> rb = ResultBean.fireFail(); + List sysUserVoList = new ArrayList<>(); + List candidateGroups = query.getCandidateGroups(); + candidateGroups.removeAll(Collections.singleton(null)); + if (!candidateGroups.isEmpty()) { + for (String roleSid : candidateGroups) { + //根据角色sid获取角色的层级 + sysUserVoList = baseMapper.getUserByRoleNoOrgPath(roleSid); + sysUserVoList.removeAll(Collections.singleton(null)); + } + } + List stringList = new ArrayList<>(); + //根据项目sid查询用户 + List sidsList = userProjectFeign.getWarehouse(query.getProjectSid()).getData(); + if(sidsList != null){ + sidsList.removeAll(Collections.singleton(null)); + if(!sidsList.isEmpty()){ + stringList = sidsList.stream().map(v->v.getUserSid()).collect(Collectors.toList()); + } + } + if(!stringList.isEmpty()){ + List finalStringList = stringList; + sysUserVoList = sysUserVoList.stream().filter(v-> finalStringList.contains(v.getSid())).collect(Collectors.toList()); + }else{ + return rb.setMsg("请设置项目相关人员"); + } + return rb.success().setData(sysUserVoList); + } + public ResultBean getUserByUserSid(String sid) { ResultBean rb = ResultBean.fireFail(); SysUserVo sysUserVo = baseMapper.getUserByUserSid(sid); diff --git a/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/UserssQuery.java b/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/UserssQuery.java new file mode 100644 index 00000000..7656782b --- /dev/null +++ b/yxt_supervise/supervise-system/supervise-system-biz/src/main/java/com/yxt/supervise/system/sysuser/UserssQuery.java @@ -0,0 +1,19 @@ +package com.yxt.supervise.system.sysuser; + +import lombok.Data; + +import java.util.ArrayList; +import java.util.List; + +/** + * @description: + * @author: dimengzhe + * @date: 2023/11/28 + **/ +@Data +public class UserssQuery { + + private List candidateGroups = new ArrayList<>(); + + private String projectSid; +}