package com.casic.missiles.service.Impl;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.lang.Assert;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.casic.missiles.core.model.auth.AuthUser;
import com.casic.missiles.core.shiro.ShiroKit;
import com.casic.missiles.dto.ReturnDTO;
import com.casic.missiles.dto.ReturnUtil;
import com.casic.missiles.dto.flowable.AllApproveDTO;
import com.casic.missiles.dto.flowable.ToBeApprovedDTO;
import com.casic.missiles.enums.BusinessExceptionEnum;
import com.casic.missiles.enums.system.ApprovalStatusEnum;
import com.casic.missiles.exception.BusinessException;
import com.casic.missiles.model.system.SystemFlowForm;
import com.casic.missiles.service.IBaseApprovalService;
import com.casic.missiles.service.system.ISystemFlowFormService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.flowable.common.engine.impl.identity.Authentication;
import org.flowable.engine.HistoryService;
import org.flowable.engine.RepositoryService;
import org.flowable.engine.RuntimeService;
import org.flowable.engine.TaskService;
import org.flowable.engine.history.HistoricProcessInstance;
import org.flowable.engine.repository.ProcessDefinition;
import org.flowable.engine.runtime.ProcessInstance;
import org.flowable.engine.runtime.ProcessInstanceBuilder;
import org.flowable.task.api.Task;
import org.flowable.task.api.history.HistoricTaskInstance;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @Description: 公共审批功能service
 * @Author: wangpeng
 * @Date: 2022/12/21 11:32
 */
@Slf4j
@Service
public class BaseApprovalServiceImpl implements IBaseApprovalService {
    @Resource
    private ISystemFlowFormService flowFormService;
    @Resource
    private RuntimeService runtimeService;
    @Resource
    private TaskService taskService;
    @Resource
    private HistoryService historyService;
    @Resource
    private RepositoryService repositoryService;

    @Transactional
    public ReturnDTO processSubmit(String formId, Long id) {
        SystemFlowForm flowForm = getSystemFlowForm(formId);
        if (Objects.isNull(flowForm) || StringUtils.isEmpty(flowForm.getDeployId()) || StringUtils.isEmpty(flowForm.getProcDefId())) {
            log.error("该表单不存在对应的流程定义，formId:{}", formId);
            return ReturnUtil.failed("流程提交处理失败，该表单不存在对应的流程定义，请重新提交");
        }
        //流程发起人
        AuthUser user = ShiroKit.getUser();
        Assert.isFalse(Objects.isNull(user), () -> {
            throw new BusinessException(BusinessExceptionEnum.LOGIN_USER_ACQUIRE_FAILED);
        });
        Authentication.setAuthenticatedUserId(String.valueOf(user.getId()));

        //根据流程key（SystemFlowForm中的procDefId）获取流程id
        ProcessDefinition processDefinition = repositoryService.createProcessDefinitionQuery().processDefinitionKey(flowForm.getProcDefId()).latestVersion().singleResult();
        if (Objects.isNull(processDefinition)) {
            throw new BusinessException(BusinessExceptionEnum.FLOW_NO_JOIN_FLOWABLE);
        }

        //流程变量后续根据使用设置
        Map<String, Object> processVariables = new HashMap<>();
//        processVariables.put(FORM_VAR,formData);
//        processVariables.put(PROCESS_STATUS,BUSINESS_STATUS_1);
//        processVariables.put(START_USER_INFO, JSONObject.toJSONString(startUserInfo));
        processVariables.put("root", String.valueOf(user.getId()));

        ProcessInstanceBuilder processInstanceBuilder = runtimeService.createProcessInstanceBuilder();
        ProcessInstance processInstance = processInstanceBuilder
                .processDefinitionId(processDefinition.getId()) //只能通过id启动，key启动不生效
                .variables(processVariables)//启动流程时设置的全局变量，整个流程实例生效
                .businessStatus(ApprovalStatusEnum.IN_APPROVED)//设置自定义的业务状态
                .businessKey(String.valueOf(id))//关联业务表主键
                .start();

        if (Objects.isNull(processInstance)) {
            log.error("流程实例启动失败，formId：{}，deployId：{}，procDefId:{}", formId, flowForm.getDeployId(), flowForm.getProcDefId());
            return ReturnUtil.failed("流程提交处理失败，流程实例启动失败");
        }
        return ReturnUtil.success(processInstance);
    }

    public List<String> getCanceledList(String formId) {
        //根据业务表单id获取流程定义
        SystemFlowForm flowForm = getSystemFlowForm(formId);
        if (Objects.isNull(flowForm) || StringUtils.isEmpty(flowForm.getDeployId()) || StringUtils.isEmpty(flowForm.getProcDefId())) {
            log.error("查询已取消的流程，该表单不存在对应的流程定义，formId:{}", formId);
            return new ArrayList<>();
        }
        List<HistoricProcessInstance> historicProcessInstances = new ArrayList<>();
        //管理员or其他用户
        if (ShiroKit.isAdmin()) {
            historicProcessInstances = getCanceledProcessInstances(flowForm);
        } else {
            AuthUser user = ShiroKit.getUser();
            Assert.isFalse(Objects.isNull(user), () -> {
                throw new BusinessException(BusinessExceptionEnum.LOGIN_USER_ACQUIRE_FAILED);
            });
            historicProcessInstances = getCanceledProcessInstancesForStarted(flowForm, user);
        }
        List<String> businessKeys = historicProcessInstances.stream().map(HistoricProcessInstance::getBusinessKey).collect(Collectors.toList());
        return businessKeys;
    }

    public List<String> getFailedList(String formId) {
        //根据业务表单id获取流程定义
        SystemFlowForm flowForm = getSystemFlowForm(formId);
        if (Objects.isNull(flowForm) || StringUtils.isEmpty(flowForm.getDeployId()) || StringUtils.isEmpty(flowForm.getProcDefId())) {
            log.error("查询未通过的流程，该表单不存在对应的流程定义，formId:{}", formId);
            return new ArrayList<>();
        }
        List<HistoricProcessInstance> historicProcessInstances = new ArrayList<>();
        //管理员or其他用户
        if (ShiroKit.isAdmin()) {
            //根据业务状态、流程定义查询该业务所有未通过的流程实例
            historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                    .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
//                    .deleted() //拒绝的审批流程要执行删除操作，也要设置业务状态，所以使用下行的状态可满足拒绝的查询
                    .processInstanceBusinessStatus(ApprovalStatusEnum.FAILED) //不加deleted查询的是所有的
                    .orderByProcessInstanceStartTime().desc()
                    .list();
        } else {
            AuthUser user = ShiroKit.getUser();
            Assert.isFalse(Objects.isNull(user), () -> {
                throw new BusinessException(BusinessExceptionEnum.LOGIN_USER_ACQUIRE_FAILED);
            });
            historicProcessInstances = getFailedProcessInstancesForStartedAndAssignee(flowForm, user, ApprovalStatusEnum.FAILED);
        }
        List<String> businessKeys = historicProcessInstances.stream().map(HistoricProcessInstance::getBusinessKey).collect(Collectors.toList());
        return businessKeys;
    }

    @Override
    public List<String> getFailedRejectList(String formId) {
        //根据业务表单id获取流程定义
        SystemFlowForm flowForm = getSystemFlowForm(formId);
        if (Objects.isNull(flowForm) || StringUtils.isEmpty(flowForm.getDeployId()) || StringUtils.isEmpty(flowForm.getProcDefId())) {
            log.error("查询未通过-驳回的流程，该表单不存在对应的流程定义，formId:{}", formId);
            return new ArrayList<>();
        }
        List<HistoricProcessInstance> historicProcessInstances = new ArrayList<>();
        //管理员or其他用户
        if (ShiroKit.isAdmin()) {
            historicProcessInstances = getFailedProcessInstances(flowForm, ApprovalStatusEnum.FAILED_REJECT);
        } else {
            AuthUser user = ShiroKit.getUser();
            Assert.isFalse(Objects.isNull(user), () -> {
                throw new BusinessException(BusinessExceptionEnum.LOGIN_USER_ACQUIRE_FAILED);
            });
            historicProcessInstances = getFailedProcessInstancesForStartedAndAssignee(flowForm, user, ApprovalStatusEnum.FAILED_REJECT);
        }
        List<String> businessKeys = historicProcessInstances.stream().map(HistoricProcessInstance::getBusinessKey).collect(Collectors.toList());
        return businessKeys;
    }

    public List<String> getPassedList(String formId) {
        SystemFlowForm flowForm = getSystemFlowForm(formId);
        if (Objects.isNull(flowForm) || StringUtils.isEmpty(flowForm.getDeployId()) || StringUtils.isEmpty(flowForm.getProcDefId())) {
            log.error("查询已通过的流程，该表单不存在对应的流程定义，formId:{}", formId);
            return new ArrayList<>();
        }
        List<HistoricProcessInstance> historicProcessInstances = new ArrayList<>();
        //未登录获取所有
        try {
            ShiroKit.isAdmin();
        } catch (Exception e) {
            historicProcessInstances = getPassedProcessInstances(flowForm);
            return historicProcessInstances.stream().map(HistoricProcessInstance::getBusinessKey).collect(Collectors.toList());
        }
        //管理员or其他用户
        if (ShiroKit.isAdmin()) {
            historicProcessInstances = getPassedProcessInstances(flowForm);
        } else {
            AuthUser user = ShiroKit.getUser();
            Assert.isFalse(Objects.isNull(user), () -> {
                throw new BusinessException(BusinessExceptionEnum.LOGIN_USER_ACQUIRE_FAILED);
            });
            historicProcessInstances = getPassedProcessInstancesForStartedAndAssignee(flowForm, user);
        }
        List<String> businessKeys = historicProcessInstances.stream().map(HistoricProcessInstance::getBusinessKey).collect(Collectors.toList());
        return businessKeys;
    }

    public List<String> getInApprovedList(String formId) {
        //根据业务表单id获取流程定义
        SystemFlowForm flowForm = getSystemFlowForm(formId);
        if (Objects.isNull(flowForm) || StringUtils.isEmpty(flowForm.getDeployId()) || StringUtils.isEmpty(flowForm.getProcDefId())) {
            log.error("查询审批中的任务，该表单不存在对应的流程定义，formId:{}", formId);
            return new ArrayList<>();
        }
        List<HistoricProcessInstance> historicProcessInstances = new ArrayList<>();
        //管理员or其他用户
        if (ShiroKit.isAdmin()) {
            historicProcessInstances = getInApprovedProcessInstances(flowForm);
        } else {
            AuthUser user = ShiroKit.getUser();
            Assert.isFalse(Objects.isNull(user), () -> {
                throw new BusinessException(BusinessExceptionEnum.LOGIN_USER_ACQUIRE_FAILED);
            });
            historicProcessInstances = getInApprovedProcessInstancesForStarted(flowForm, user);
        }
        List<String> businessKeys = historicProcessInstances.stream().map(HistoricProcessInstance::getBusinessKey).collect(Collectors.toList());
        return businessKeys;
    }

    public List<ToBeApprovedDTO> getToBeApprovedList(String formId) {
        //根据业务表单id获取流程定义
        SystemFlowForm flowForm = getSystemFlowForm(formId);
        if (Objects.isNull(flowForm) || StringUtils.isEmpty(flowForm.getDeployId()) || StringUtils.isEmpty(flowForm.getProcDefId())) {
            log.error("查询待审批的任务，该表单不存在对应的流程定义，formId:{}", formId);
            return new ArrayList<>();
        }
        JSONObject jsonObject = JSONObject.parseObject(flowForm.getFlowDef());
        JSONObject workFlowDef = jsonObject.getJSONObject("workFlowDef");
        Integer decisionItem = workFlowDef.getInteger("decisionItem");

        AuthUser user = ShiroKit.getUser();
        Assert.isFalse(Objects.isNull(user), () -> {
            throw new BusinessException(BusinessExceptionEnum.LOGIN_USER_ACQUIRE_FAILED);
        });
        //根据流程定义、登录用户id获取该业务待办任务
        List<Task> tasks = taskService.createTaskQuery()
                .processDefinitionKey(flowForm.getProcDefId())
//                .deploymentId(flowForm.getDeployId())
                .taskAssignee(String.valueOf(user.getId()))
//                .includeProcessVariables()
                .orderByTaskCreateTime().desc()
                .list();
        List<ToBeApprovedDTO> toBeApprovedDTOs = new ArrayList<>();
        for (Task task : tasks) {
            HistoricProcessInstance historicProcessInstance = historyService.createHistoricProcessInstanceQuery()
                    .processInstanceId(task.getProcessInstanceId()).singleResult();
            if (ApprovalStatusEnum.CANCELED.equals(historicProcessInstance.getBusinessStatus())) {
                continue;
            }
            //任务id，用户进行任务审批使用
            ToBeApprovedDTO toBeApprovedDTO = new ToBeApprovedDTO();
            toBeApprovedDTO.setTaskId(task.getId());
            toBeApprovedDTO.setBusinessKey(historicProcessInstance.getBusinessKey());
            toBeApprovedDTO.setDecisionItem(decisionItem); //设置可选决策项
            toBeApprovedDTO.setCreateTime(DateUtil.format(task.getCreateTime(), "yyyy-MM-dd HH:mm:ss"));
            toBeApprovedDTO.setProcessId(task.getProcessInstanceId());
            toBeApprovedDTOs.add(toBeApprovedDTO);
        }

        //返回任务id和关联业务主键id
        return toBeApprovedDTOs;
    }

    @Override
    public List<AllApproveDTO> getAllList(String formId) {
        SystemFlowForm flowForm = getSystemFlowForm(formId);
        if (Objects.isNull(flowForm) || StringUtils.isEmpty(flowForm.getDeployId()) || StringUtils.isEmpty(flowForm.getProcDefId())) {
            log.error("查询全部的流程，该表单不存在对应的流程定义，formId:{}", formId);
            return new ArrayList<>();
        }
        List<AllApproveDTO> list = new ArrayList<>();
        //管理员or其他用户
        if (ShiroKit.isAdmin()) {
            //审批中实例
            getInApprovedProcessInstances(flowForm).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.IN_APPROVED);
            });
            //已通过实例
            getPassedProcessInstances(flowForm).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.PASSED);
            });
            ;
            //未通过-拒绝实例
            getFailedProcessInstances(flowForm, ApprovalStatusEnum.FAILED_REJECT).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.FAILED_REJECT);
            });
            //未通过实例
            getFailedProcessInstances(flowForm, ApprovalStatusEnum.FAILED).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.FAILED);
            });
            //已取消实例
            getCanceledProcessInstances(flowForm).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.CANCELED);
            });
        } else {
            AuthUser user = ShiroKit.getUser();
            Assert.isFalse(Objects.isNull(user), () -> {
                throw new BusinessException(BusinessExceptionEnum.LOGIN_USER_ACQUIRE_FAILED);
            });
            //审批中实例
            getInApprovedProcessInstancesForStarted(flowForm, user).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.IN_APPROVED);
            });
            //已通过实例
            getPassedProcessInstancesForStartedAndAssignee(flowForm, user).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.PASSED);
            });
            //未通过-拒绝实例
            getFailedProcessInstancesForStartedAndAssignee(flowForm, user, ApprovalStatusEnum.FAILED_REJECT).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.FAILED_REJECT);
            });
            //未通过实例
            getFailedProcessInstancesForStartedAndAssignee(flowForm, user, ApprovalStatusEnum.FAILED).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.FAILED);
            });
            //已取消实例
            getCanceledProcessInstancesForStarted(flowForm, user).forEach(instance -> {
                enrichList(list, instance, ApprovalStatusEnum.CANCELED);
            });
        }
        return list;
    }

    @Override
    @Transactional
    public void failUpdate(String processId) {
        //发起人审批通过
        Task task = taskService.createTaskQuery()
                .processInstanceId(processId)
                .active()
                .singleResult();
        taskService.complete(task.getId());
        //更新状态为审批中
        runtimeService.updateBusinessStatus(task.getProcessInstanceId(), ApprovalStatusEnum.IN_APPROVED);
    }

    private void enrichList(List<AllApproveDTO> list, HistoricProcessInstance instance, String status) {
        AllApproveDTO allApproveDTO = new AllApproveDTO();
        allApproveDTO.setBusinessKey(instance.getBusinessKey());
        allApproveDTO.setStatus(status);
        list.add(allApproveDTO);
    }

    private SystemFlowForm getSystemFlowForm(String formId) {
        //根据业务表单id获取流程定义
        QueryWrapper<SystemFlowForm> wrapper = new QueryWrapper<>();
        wrapper.eq("form_id", formId);
        return flowFormService.getOne(wrapper);
    }

    private List<HistoricProcessInstance> getPassedProcessInstancesForStartedAndAssignee(SystemFlowForm flowForm, AuthUser user) {
        List<HistoricProcessInstance> historicProcessInstances;
        //根据流程定义、登录用户id查询该业务已完成的流程实例（作为发起者）
        historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
                .finished()
                .notDeleted()
                .startedBy(String.valueOf(user.getId()))
                .orderByProcessInstanceStartTime().desc()
                .list();
        //根据流程定义、登录用户id获取该业务流程的实例结束的已办任务（作为审批者）
        List<HistoricTaskInstance> tasks = historyService.createHistoricTaskInstanceQuery()
                .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
                .taskAssignee(String.valueOf(user.getId()))
                .processFinished() //todo:此参数若表示实例已完成，则这里使用正确，需验证
                .orderByTaskCreateTime().desc()
                .list();
        //根据作为审批者的任务查询流程实例
        for (HistoricTaskInstance task : tasks) {
            HistoricProcessInstance historicProcessInstance = historyService.createHistoricProcessInstanceQuery()
                    .notDeleted()
                    .processInstanceId(task.getProcessInstanceId()).singleResult();
            if(Objects.nonNull(historicProcessInstance)){
                historicProcessInstances.add(historicProcessInstance);
            }
        }
        return historicProcessInstances;
    }

    private List<HistoricProcessInstance> getInApprovedProcessInstances(SystemFlowForm flowForm) {
        List<HistoricProcessInstance> historicProcessInstances;
        //根据流程定义查询该业务所有未完成的流程实例
        historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                .processDefinitionKey(flowForm.getProcDefId()) //这里使用流程定义，因为更新流程定义不会更新定义id，会更新部署id
//                    .deploymentId(flowForm.getDeployId())
//                .or()
//                .unfinished()
                .processInstanceBusinessStatus(ApprovalStatusEnum.IN_APPROVED) //查询审批中状态
//                .endOr()
                .orderByProcessInstanceStartTime().desc()
                .list();
        return historicProcessInstances;
    }

    private List<HistoricProcessInstance> getInApprovedProcessInstancesForStarted(SystemFlowForm flowForm, AuthUser user) {
        List<HistoricProcessInstance> historicProcessInstances;
        //根据流程定义、登录用户id查询该业务未完成的流程实例
        historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
//                .or()
//                .unfinished()
                .processInstanceBusinessStatus(ApprovalStatusEnum.IN_APPROVED) //查询审批中状态
//                .endOr()
                .startedBy(String.valueOf(user.getId()))
                .orderByProcessInstanceStartTime().desc()
                .list();
        return historicProcessInstances;
    }

    private List<HistoricProcessInstance> getPassedProcessInstances(SystemFlowForm flowForm) {
        //根据流程定义查询该业务所有已完成的流程实例
        List<HistoricProcessInstance> historicProcessInstances;
        historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
                .finished()
                .notDeleted()
                .orderByProcessInstanceStartTime().desc()
                .list();
        return historicProcessInstances;
    }

    private List<HistoricProcessInstance> getFailedProcessInstances(SystemFlowForm flowForm, String failStatus) {
        //根据业务状态、流程定义查询该业务所有未通过的流程实例
        List<HistoricProcessInstance> historicProcessInstances;
        historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
                .notDeleted()//驳回的是没有被删除的
                .processInstanceBusinessStatus(failStatus)
                .orderByProcessInstanceStartTime().desc()
                .list();
        return historicProcessInstances;
    }

    private List<HistoricProcessInstance> getFailedProcessInstancesForStartedAndAssignee(SystemFlowForm flowForm, AuthUser user, String failStatus) {
        //根据业务状态、流程定义、登录用户id查询该业务未通过的流程实例（作为发起者）
        List<HistoricProcessInstance> historicProcessInstances = new ArrayList<>();
        if (ApprovalStatusEnum.FAILED.equals(failStatus)) {
            historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                    .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
                    .startedBy(String.valueOf(user.getId()))
                    .processInstanceBusinessStatus(failStatus)
                    .orderByProcessInstanceStartTime().desc()
                    .list();
        } else if (ApprovalStatusEnum.FAILED_REJECT.equals(failStatus)) {
            historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                    .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
                    .notDeleted()//驳回的是没有被删除的
                    .startedBy(String.valueOf(user.getId()))
                    .processInstanceBusinessStatus(failStatus)
                    .orderByProcessInstanceStartTime().desc()
                    .list();
        }
        //根据业务状态、流程定义、登录用户id获取该业务的未通过的流程实例的审批者已完成任务（作为审批者）
        List<HistoricTaskInstance> tasks = historyService.createHistoricTaskInstanceQuery()
                .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
                .taskAssignee(String.valueOf(user.getId()))
                .finished() //审批者已完成审批
                .processUnfinished() //todo:此参数若表示实例未完成，则这里使用正确，需验证
                .orderByTaskCreateTime().desc()
                .list();
        //根据作为审批者的任务查询未通过的流程实例
        for (HistoricTaskInstance task : tasks) {
            HistoricProcessInstance historicProcessInstance = historyService.createHistoricProcessInstanceQuery()
                    .processInstanceId(task.getProcessInstanceId())
                    .processInstanceBusinessStatus(failStatus)
                    .singleResult();
            if(Objects.nonNull(historicProcessInstance)){
                historicProcessInstances.add(historicProcessInstance);
            }
        }
        return historicProcessInstances;
    }

    private List<HistoricProcessInstance> getCanceledProcessInstancesForStarted(SystemFlowForm flowForm, AuthUser user) {
        List<HistoricProcessInstance> historicProcessInstances;//根据业务状态、流程定义、登录用户id查询该业务已取消的流程实例
        historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
                .startedBy(String.valueOf(user.getId()))
                .processInstanceBusinessStatus(ApprovalStatusEnum.CANCELED)
                .orderByProcessInstanceStartTime().desc()
                .list();
        return historicProcessInstances;
    }

    private List<HistoricProcessInstance> getCanceledProcessInstances(SystemFlowForm flowForm) {
        List<HistoricProcessInstance> historicProcessInstances;
        //根据业务状态、流程定义查询该业务所有已取消的流程实例-拒绝
        historicProcessInstances = historyService.createHistoricProcessInstanceQuery()
                .processDefinitionKey(flowForm.getProcDefId())
//                    .deploymentId(flowForm.getDeployId())
//                .deleted() //取消的要执行删除操作，也要设置业务状态，此处可同时设置为条件进行查询
                .processInstanceBusinessStatus(ApprovalStatusEnum.CANCELED) //对应取消按钮中设置的业务状态
                .orderByProcessInstanceStartTime().desc()
                .list();
        return historicProcessInstances;
    }
}
