package com.sunxung.factoring.service.purchcontractmanagement.impl;

import cn.hutool.extra.pinyin.PinyinUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.sunxung.factoring.component.exception.BusinessException;
import com.sunxung.factoring.component.exception.ValidatorException;
import com.sunxung.factoring.component.util.*;
import com.sunxung.factoring.dict.impl.FileModuleDict;
import com.sunxung.factoring.dict.impl.ProjectInitiationStatusDict;
import com.sunxung.factoring.dict.impl.PurchContractStatusDict;
import com.sunxung.factoring.entity.entprise.Enterprise;
import com.sunxung.factoring.entity.project.BusinessProcessingLog;
import com.sunxung.factoring.entity.project.vo.BusinessProcessingTaskVo;
import com.sunxung.factoring.entity.project.vo.SearchBusinessProcessingTask;
import com.sunxung.factoring.entity.purchcontractmanagement.*;
import com.sunxung.factoring.entity.purchcontractmanagement.vo.PurchContractCompletedVo;
import com.sunxung.factoring.entity.purchcontractmanagement.vo.PurchContractVo;
import com.sunxung.factoring.entity.salescontractmanagement.CSalesContract;
import com.sunxung.factoring.entity.salescontractmanagement.CSalesContractBasicInfo;
import com.sunxung.factoring.entity.salescontractmanagement.CSalesContractGoodsInfo;
import com.sunxung.factoring.entity.salescontractmanagement.SalesContractSupplementGoodsInfo;
import com.sunxung.factoring.entity.salescontractmanagement.vo.SalesContractBasicVo;
import com.sunxung.factoring.entity.supplier.SupplierInfo;
import com.sunxung.factoring.entity.sys.Dictionary;
import com.sunxung.factoring.entity.sys.FileStorage;
import com.sunxung.factoring.entity.sys.User;
import com.sunxung.factoring.entity.tradingPlatform.Platform;
import com.sunxung.factoring.mapper.purchcontractmanagement.PurchContractMapper;
import com.sunxung.factoring.service.entprise.IEnterpriseService;
import com.sunxung.factoring.service.project.BusinessProcessingLogService;
import com.sunxung.factoring.service.purchcontractmanagement.*;
import com.sunxung.factoring.service.salescontractmanagement.ICSalesContractBasicInfoService;
import com.sunxung.factoring.service.salescontractmanagement.ISalesContractSupplementGoodsInfoService;
import com.sunxung.factoring.service.salescontractmanagement.SalesContractGoodsInfoService;
import com.sunxung.factoring.service.salescontractmanagement.SalesContractService;
import com.sunxung.factoring.service.supplier.ISupplierInfoService;
import com.sunxung.factoring.service.sys.DictionaryService;
import com.sunxung.factoring.service.sys.FileStorageService;
import com.sunxung.factoring.service.sys.ISysAttachmentRefService;
import com.sunxung.factoring.service.sys.UserService;
import com.sunxung.factoring.service.sys.dto.AttachmentDto;
import com.sunxung.factoring.service.sys.flowable.FlowableService;
import com.sunxung.factoring.service.tradingPlatform.PlatformService;
import org.flowable.bpmn.model.BpmnModel;
import org.flowable.bpmn.model.EndEvent;
import org.flowable.bpmn.model.Process;
import org.flowable.engine.RepositoryService;
import org.flowable.engine.RuntimeService;
import org.flowable.engine.TaskService;
import org.flowable.engine.runtime.Execution;
import org.flowable.engine.runtime.ProcessInstance;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.servlet.http.HttpServletResponse;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @Description : 采购合同service实现类
 * @Author : JiaYf
 * @Date: 2021-09-14 14:33
 */
@Service("purchContractService")
public class PurchContractServiceImpl extends ServiceImpl<PurchContractMapper, PurchContractManagement> implements PurchContractService {

    @Autowired
    private PurchContractBasicInfoService purchContractBasicInfoService;

    @Autowired
    private PurchContractRetentionInfoService purchContractRetentionInfoService;

    @Autowired
    private PurchContractPriceRuleService purchContractPriceRuleService;

    @Autowired
    private PurchContractGoodsInfoService purchContractGoodsInfoService;

    @Autowired
    private SalesContractGoodsInfoService salesContractGoodsInfoService;

    @Autowired
    private ISalesContractSupplementGoodsInfoService salesContractSupplementGoodsInfoService;

    @Autowired
    private DictionaryService dictService;

    @Autowired
    private FlowableService flowableService;

    @Autowired
    private SalesContractService salesContractService;

    @Autowired
    private ICSalesContractBasicInfoService salesContractBasicInfoService;

    @Autowired
    private UserService userService;

    @Autowired
    private IPurchContractBuyerSellerService purchContractBuyerSellerService;

    @Autowired
    private PurchContractSettlePaymentService purchContractSettlePaymentService;

    @Autowired
    private IPurchContractBasicInfoHistoryService purchContractBasicInfoHistoryService;

    @Autowired
    private IPurchContractRetentionInfoHistoryService purchContractRetentionInfoHistoryService;

    @Autowired
    private IPurchContractPriceRuleHistoryService purchContractPriceRuleHistoryService;

    @Autowired
    private IPurchContractGoodsInfoHistoryService purchContractGoodsInfoHistoryService;

    @Autowired
    private IPurchContractSettlePaymentHistoryService purchContractSettlePaymentHistoryService;

    @Autowired
    private IPurchContractBuyerSellerHistoryService purchContractBuyerSellerHistoryService;

    @Autowired
    private PurchContractMapper purchContractMapper;

    @Autowired
    private PlatformService platformService;

    @Autowired
    private BusinessProcessingLogService processingLogService;

    @Autowired
    private RuntimeService runtimeService;

    @Autowired
    protected RepositoryService repositoryService;

    @Autowired
    private TaskService taskService;

    @Autowired
    private FileStorageService fileStorageService;

    @Autowired
    private ISysAttachmentRefService attachmentRefService;

    @Autowired
    private IPurchContractSupplementInfoService purchContractSupplementInfoService;

    @Autowired
    private BusinessProcessingLogService businessProcessingLogService;

    @Autowired
    private IEnterpriseService enterpriseService;

    @Autowired
    private ISupplierInfoService supplierInfoService;

    @Override
    public PurchContractManagement get(Long id) {
        return baseMapper.getListInfo(id);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void add(PurchContractVo purchContractVo) {
        if (purchContractVo == null) {
            throw new ValidatorException(CodeUtil.FAIL, "采购合同信息不能为空");
        }
        PurchContractBasicInfo basicInfo = purchContractVo.getPurchContractBasicInfo();

        if (basicInfo == null) {
            throw new ValidatorException(CodeUtil.FAIL, "基础信息不能为空！");
        }

        if (purchContractVo.getCommit() == 1) {
            if (purchContractVo.getPurchContractRetentionInfo() == null) {
                throw new ValidatorException(CodeUtil.FAIL, "是否有质保金不能为空！");
            }

            if (purchContractVo.getPurchContractPriceRule() == null) {
                throw new ValidatorException(CodeUtil.FAIL, "价格规则不能为空！");
            }

            if (purchContractVo.getPurchContractSettlePayment() == null) {
                throw new ValidatorException(CodeUtil.FAIL, "结算与付款不能为空！");
            }

            if (CollectionUtil.isEmpty(purchContractVo.getPurchContractBuyerSellerList())) {
                throw new ValidatorException(CodeUtil.FAIL, "供应商发货人不能为空！");
            }

            if (CollectionUtil.isEmpty(purchContractVo.getPurchContractGoodsInfoList())) {
                throw new ValidatorException(CodeUtil.FAIL, "货物信息不能为空！");
            }
        }

        ThreadLocalUtil.setUser(userService.getByLoginName("admin"));

        SalesContractBasicVo basicInfoVo = purchContractVo.getBasicInfo();

        PurchContractRetentionInfo purchContractRetentionInfo = purchContractVo.getPurchContractRetentionInfo();
        PurchContractPriceRule purchContractPriceRule = purchContractVo.getPurchContractPriceRule();
        PurchContractSettlePayment purchContractSettlePayment = purchContractVo.getPurchContractSettlePayment();
        List<PurchContractBuyerSeller> purchContractBuyerSellerList = purchContractVo.getPurchContractBuyerSellerList();
        List<PurchContractGoodsInfo> purchContractGoodsInfo = purchContractVo.getPurchContractGoodsInfoList();

        PurchContractManagement management = getById(purchContractVo.getBusinessKey());
        basicInfo.setBuyerName(basicInfoVo.getEnterprise());
        basicInfo.setTradingPlatformId(basicInfoVo.getPlatformId());
        basicInfo.setProjectName(basicInfoVo.getProjectName());
        basicInfo.setSupplierName(basicInfoVo.getMainEnterprise());


        //合同编号，系统自动生成，生成规则为：
        //CHB+供应商名称前四个字首字母大写+年份+00X，如陕西旺通供应链管理有限公司，则为CHBSXWT2023001,以此类推。
        if (StringUtil.isEmpty(purchContractVo.getPurchContractBasicInfo().getContractNumber())) {
            String supplierName = purchContractVo.getPurchContractBasicInfo().getSupplierName();
            //去除名字里面的括号
            supplierName = StringUtil.deleteString(supplierName, '（');
            supplierName = StringUtil.deleteString(supplierName, '）');
            String contractNumberPer = "CHB" + PinyinUtil.getFirstLetter(supplierName, "").toUpperCase().substring(0, 4)
                    + DateUtil.getTheYear(new Date());
            List<PurchContractBasicInfo> list = purchContractBasicInfoService.lambdaQuery()
                    .like(PurchContractBasicInfo::getContractNumber, contractNumberPer)
                    .orderByDesc(PurchContractBasicInfo::getGmtCreate)
                    .list();
            String newNumberStr = "001";
            if (CollectionUtil.isNotEmpty(list)) {
                int number = list.size() + 1;
                newNumberStr = String.format("%03d", number);
            }
            String contractNumber = contractNumberPer + newNumberStr;
            basicInfo.setContractNumber(contractNumber);
        }

        if (purchContractVo.getBusinessKey() != null) {
            management.setIsChange(0);
            management.setSupplierId(basicInfoVo.getSupplierId());
            management.setTradingPlatformId(basicInfoVo.getPlatformId());
            //退回
            updateById(management);
            purchContractBasicInfoService.updateById(basicInfo);

            if (purchContractRetentionInfo != null) {
                purchContractRetentionInfoService.remove(new QueryWrapper<PurchContractRetentionInfo>().eq("c_purch_contract_basic_info_id", basicInfo.getId()));
                purchContractRetentionInfo.setPurchContractBasicInfoId(basicInfo.getId());
                purchContractRetentionInfoService.save(purchContractRetentionInfo);
            }

            if (purchContractPriceRule != null) {
                purchContractPriceRuleService.remove(new QueryWrapper<PurchContractPriceRule>()
                        .eq("c_purch_contract_basic_info_id", basicInfo.getId()));
                purchContractPriceRule.setPurchContractBasicInfoId(basicInfo.getId());
                purchContractPriceRuleService.save(purchContractPriceRule);
            }

            if (purchContractSettlePayment != null) {
                purchContractSettlePaymentService.remove(new QueryWrapper<PurchContractSettlePayment>()
                        .eq("c_purch_contract_basic_info_id", basicInfo.getId()));
                purchContractSettlePayment.setPurchContractBasicInfoId(basicInfo.getId());
                purchContractSettlePaymentService.save(purchContractSettlePayment);
            }

            if (CollectionUtil.isNotEmpty(purchContractBuyerSellerList)) {
                purchContractBuyerSellerService.remove(new QueryWrapper<PurchContractBuyerSeller>().eq("c_purch_contract_basic_info_id", basicInfo.getId()));
                purchContractBuyerSellerList.forEach(c -> c.setPurchContractBasicInfoId(basicInfo.getId()));
                purchContractBuyerSellerService.saveBatch(purchContractBuyerSellerList);
            }


            if (CollectionUtil.isNotEmpty(purchContractGoodsInfo)) {
                purchContractGoodsInfoService.remove(new QueryWrapper<PurchContractGoodsInfo>().eq("c_purch_contract_basic_info_id", basicInfo.getId()));
                purchContractGoodsInfo.forEach(c -> {
                    c.setPurchContractBasicInfoId(basicInfo.getId());
                    c.setSalesContractGoodsInfoId(c.getId());
                    c.setId(null);
                });
                purchContractGoodsInfoService.saveBatch(purchContractGoodsInfo);
            }

        } else {

            management = new PurchContractManagement();
            management.setSupplierId(basicInfoVo.getSupplierId());
            management.setTradingPlatformId(basicInfoVo.getPlatformId());
            management.setBusinessNumber(basicInfoVo.getBusinessNumber());
            management.setContractStatus(ProjectInitiationStatusDict.ChildEnum.PROCESSING.getCode());
            //保存
            save(management);
            purchContractVo.setBusinessKey(management.getId());

            //保存合同信息
            basicInfo.setPurchContractManagementId(management.getId());
            purchContractBasicInfoService.save(basicInfo);
            //质保金
            if (purchContractRetentionInfo != null) {
                purchContractRetentionInfo.setPurchContractBasicInfoId(basicInfo.getId());
                purchContractRetentionInfoService.save(purchContractRetentionInfo);
            }

            //价格规则
            if (purchContractPriceRule != null) {
                purchContractPriceRule.setPurchContractBasicInfoId(basicInfo.getId());
                purchContractPriceRuleService.save(purchContractPriceRule);
            }

            //结算与付款
            if (purchContractSettlePayment != null) {
                purchContractSettlePayment.setPurchContractBasicInfoId(basicInfo.getId());
                purchContractSettlePaymentService.save(purchContractSettlePayment);
            }

            //供货商发货人
            if (CollectionUtil.isNotEmpty(purchContractBuyerSellerList)) {
                purchContractBuyerSellerList.forEach(purchContractBuyerSeller -> {
                    purchContractBuyerSeller.setPurchContractBasicInfoId(basicInfo.getId());
                    purchContractBuyerSellerService.save(purchContractBuyerSeller);
                });
            }


            //货物信息
            if (CollectionUtil.isNotEmpty(purchContractGoodsInfo)) {
                purchContractGoodsInfo.forEach(goods -> {
                    goods.setPurchContractBasicInfoId(basicInfo.getId());
                    goods.setSalesContractGoodsInfoId(goods.getId());
                });
                purchContractGoodsInfoService.saveBatch(purchContractGoodsInfo);
            }

        }

        BusinessProcessingLog lastLog = businessProcessingLogService.getByBusinessTypeBusinessKey(ConstantUtil.PURCH_CONTRACT, management.getId());
        if (lastLog == null) {
            //开启流程
            startProjectProcess(purchContractVo);
        }

        if (purchContractVo.getCommit() == 1) {

            completeProces(management.getId());

            //占用销售合同
            salesContractService.lambdaUpdate().eq(CSalesContract::getBusinessNumber, management.getBusinessNumber())
                    .set(CSalesContract::getPurch, 1)
                    .update();

            //占用销售合同的货物
            purchContractGoodsInfo.forEach(goods -> {
                if (goods.getSupplement()) {
                    SalesContractSupplementGoodsInfo salesContractSupplementGoodsInfo =
                            salesContractSupplementGoodsInfoService.getById(goods.getSalesContractGoodsInfoId());
                    if (salesContractSupplementGoodsInfo != null) {
                        salesContractSupplementGoodsInfo.setOccupy(1);
                        salesContractSupplementGoodsInfoService.updateById(salesContractSupplementGoodsInfo);
                    }

                } else {
                    CSalesContractGoodsInfo salesContractGoodsInfo = salesContractGoodsInfoService.getById(goods.getSalesContractGoodsInfoId());
                    if (salesContractGoodsInfo != null) {
                        salesContractGoodsInfo.setOccupy(1);
                        salesContractGoodsInfoService.updateById(salesContractGoodsInfo);
                    }
                }
            });
        }


    }

    private Long addHistory(PurchContractBasicInfo purch) {
        Long oldId = purch.getId();
        //添加合同信息
        PurchContractBasicInfoHistory purchContractBasicInfoHistory = new PurchContractBasicInfoHistory();
        BeanUtils.copyProperties(purch, purchContractBasicInfoHistory);
        purchContractBasicInfoHistory.setPartnerEntityId(oldId);
        purchContractBasicInfoHistory.setId(null);
        purchContractBasicInfoHistoryService.save(purchContractBasicInfoHistory);
        //添加付款条件
//        List<PurchContractPaymentCondition> purchContractPaymentConditionList = purchContractPaymentConditionService.list(
//                new QueryWrapper<PurchContractPaymentCondition>().eq("purch_contract_basic_info_id", oldId)
//        );
//        if (purchContractPaymentConditionList != null && purchContractPaymentConditionList.size() > 0) {
//            for (PurchContractPaymentCondition purchContractPaymentCondition : purchContractPaymentConditionList) {
//                PurchContractPaymentConditionHistory purchContractPaymentConditionHistory = new PurchContractPaymentConditionHistory();
//                BeanUtils.copyProperties(purchContractPaymentCondition, purchContractPaymentConditionHistory);
//                purchContractPaymentConditionHistory.setPurchContractBasicInfoId(purchContractBasicInfoHistory.getId());
//                purchContractPaymentConditionHistoryService.save(purchContractPaymentConditionHistory);
//            }
//        }

        //添加质保金
        PurchContractRetentionInfo purchContractRetentionInfo = purchContractRetentionInfoService.getOne(
                new QueryWrapper<PurchContractRetentionInfo>().eq("c_purch_contract_basic_info_id", oldId)
        );
        if (purchContractRetentionInfo != null) {
            PurchContractRetentionInfoHistory purchContractRetentionInfoHistory = new PurchContractRetentionInfoHistory();
            BeanUtils.copyProperties(purchContractRetentionInfo, purchContractRetentionInfoHistory);
            purchContractRetentionInfoHistory.setPurchContractBasicInfoHisId(purchContractBasicInfoHistory.getId());
            purchContractRetentionInfoHistoryService.save(purchContractRetentionInfoHistory);
        }
        //添加价格规则
        PurchContractPriceRule purchContractPriceRule = purchContractPriceRuleService.getOne(
                new QueryWrapper<PurchContractPriceRule>().eq("c_purch_contract_basic_info_id", oldId)
        );
        if (purchContractPriceRule != null) {
            PurchContractPriceRuleHistory purchContractPriceRuleHistory = new PurchContractPriceRuleHistory();
            BeanUtils.copyProperties(purchContractPriceRule, purchContractPriceRuleHistory);
            purchContractPriceRuleHistory.setPurchContractBasicInfoHisId(purchContractBasicInfoHistory.getId());
            purchContractPriceRuleHistoryService.save(purchContractPriceRuleHistory);
        }

        //添加货物信息
        List<PurchContractGoodsInfo> purchContractGoodsInfoList = purchContractGoodsInfoService.list(
                new QueryWrapper<PurchContractGoodsInfo>().eq("c_purch_contract_basic_info_id", oldId)
        );
        if (purchContractGoodsInfoList != null && purchContractGoodsInfoList.size() > 0) {
            for (PurchContractGoodsInfo goodsInfo : purchContractGoodsInfoList) {
                PurchContractGoodsInfoHistory purchContractGoodsInfoHistory = new PurchContractGoodsInfoHistory();
                BeanUtils.copyProperties(goodsInfo, purchContractGoodsInfoHistory);
                purchContractGoodsInfoHistory.setPurchContractBasicInfoHisId(purchContractBasicInfoHistory.getId());
                purchContractGoodsInfoHistoryService.save(purchContractGoodsInfoHistory);
            }
        }


        //结算与付款
        PurchContractSettlePayment purchContractSettlePayment = purchContractSettlePaymentService.getOne(
                new QueryWrapper<PurchContractSettlePayment>().eq("c_purch_contract_basic_info_id", oldId)
        );
        if (purchContractSettlePayment != null) {
            //结算与付款
            PurchContractSettlePaymentHistory purchContractSettlePaymentHistory = new PurchContractSettlePaymentHistory();
            BeanUtils.copyProperties(purchContractSettlePayment, purchContractSettlePaymentHistory);
            purchContractSettlePaymentHistory.setPurchContractBasicInfoHisId(purchContractBasicInfoHistory.getId());
            purchContractSettlePaymentHistoryService.save(purchContractSettlePaymentHistory);
        }

        //收货人 发货人
        List<PurchContractBuyerSeller> purchContractBuyerSellerList = purchContractBuyerSellerService.list(
                new QueryWrapper<PurchContractBuyerSeller>().eq("c_purch_contract_basic_info_id", oldId)
        );
        if (purchContractBuyerSellerList != null && purchContractBuyerSellerList.size() > 0) {
            for (PurchContractBuyerSeller purchContractBuyerSeller : purchContractBuyerSellerList) {
                PurchContractBuyerSellerHistory purchContractBuyerSellerHistory = new PurchContractBuyerSellerHistory();
                BeanUtils.copyProperties(purchContractBuyerSeller, purchContractBuyerSellerHistory);
                purchContractBuyerSellerHistory.setPurchContractBasicInfoHisId(purchContractBasicInfoHistory.getId());
                purchContractBuyerSellerHistoryService.save(purchContractBuyerSellerHistory);
            }
        }
        return purchContractBasicInfoHistory.getId();
    }

    @Override
    public List<BusinessProcessingTaskVo> findMyCompletedList(SearchBusinessProcessingTask search) {
        return baseMapper.findMyCompletedList(search);
    }

    @Override
    public List<BusinessProcessingTaskVo> findAllList(SearchBusinessProcessingTask search) {
        List<BusinessProcessingTaskVo> list = baseMapper.findAllList(search);

        if (list != null && list.size() > 0) {
            list.stream().forEach(processingTaskVo -> {
                autoButtonFlag(processingTaskVo);
                BusinessProcessingLog log = businessProcessingLogService
                        .getByBusinessTypeBusinessKey(search.getSimpleClassName(), processingTaskVo.getId());
                if (log != null && log.getEndTime() == null) {
                    String taskName = log.getTaskName();
                    if (taskName.contains("采购合同录入") || taskName.contains("采购合同创建") || taskName.contains("签署")) {
                        processingTaskVo.setExecutor("供应商");
                    } else if (taskName.contains("审核") || taskName.contains("终审")) {
                        processingTaskVo.setExecutor("法务专员");
                    }
                }
            });
        }
        return list;
    }


    //判断变更按钮是否显示
    private void autoButtonFlag(BusinessProcessingTaskVo processingTaskVo) {
        Dictionary signApprovalDict = dictService.getByCode(PurchContractStatusDict.ChildEnum.CONFIRM.getCode());
        Dictionary signApprovalChangeDict = dictService.getByCode(PurchContractStatusDict.ChildEnum.CONFIRM_CHANGE.getCode());

        if (signApprovalDict == null && signApprovalDict.getId() == null) {
            processingTaskVo.setButtonFlag(false);
        } else if (signApprovalChangeDict == null && signApprovalChangeDict.getId() == null) {
            processingTaskVo.setButtonFlag(false);
        } else if (processingTaskVo.getAssignee() == null || processingTaskVo.getAssignee().getId() == null) {
            processingTaskVo.setButtonFlag(false);
        } else if (processingTaskVo.getStatus() == null || processingTaskVo.getStatus().getId() == null) {
            processingTaskVo.setButtonFlag(false);
        } else {

            //获得当前用户Id
            Long userId = ThreadLocalUtil.getUserId();
            if (userId.equals(processingTaskVo.getAssignee().getId()) && (signApprovalDict.getId()
                    .equals(processingTaskVo.getStatus().getId()) || signApprovalChangeDict.getId().equals(processingTaskVo.getStatus().getId()))) {
                processingTaskVo.setButtonFlag(true);
            } else {
                processingTaskVo.setButtonFlag(false);
            }
        }

        //是否展示下载按钮
        processingTaskVo.setDownloadFileFlag(false);
        if (processingTaskVo.getStatus().getId().equals(signApprovalDict.getId()) ||
                signApprovalChangeDict.getId().equals(processingTaskVo.getStatus().getId())) {
            processingTaskVo.setDownloadFileFlag(true);
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void startChangeProcess(Long id) {
        PurchContractManagement purchContractManagement = baseMapper.selectById(id);
        if (purchContractManagement == null) {
            throw new ValidatorException(CodeUtil.FAIL, "对应采购管理信息不存在");
        }
        CSalesContract salesContractManagement = salesContractService.getOne(new QueryWrapper<CSalesContract>()
                .eq("business_number", purchContractManagement.getBusinessNumber()));
        if (salesContractManagement == null) {
            throw new ValidatorException(CodeUtil.FAIL, "销售合同信息不能为空！");
        }

        SalesContractBasicVo salesContractBasicVo = salesContractService.getBasicInfoById(salesContractManagement.getId());

        purchContractManagement.setContractStatus(ProjectInitiationStatusDict.ChildEnum.PROCESSING.getCode());
        baseMapper.updateById(purchContractManagement);

        //2.开启销售合同变更流程
        //开启流程实例
        Map<String, Object> procVariables = new HashMap<>(1);
        User admin = userService.getByLoginName("admin");
        procVariables.put(ConstantUtil.PURCH_CONTRACT_CHANGE + ConstantUtil.ASSIGNEE, admin.getId());
        Map<String, Object> msgVariables = new HashMap<>(2);
        msgVariables.put(ConstantUtil.FLOWABLE_MSG_TITLE, salesContractBasicVo.getProjectName());
        msgVariables.put(ConstantUtil.FLOWABLE_MSG_CONTENT,
                "业务编号为“" + purchContractManagement.getBusinessNumber() + "”的项目已进入“"
                        + ConstantConversionUtil.flowBusinessKeyNames.get(ConstantUtil.PURCH_CONTRACT_CHANGE_PROCESS) + "—formBusiness”阶段，"
                        + ConstantUtil.FLOWABLE_MSG_ASSIGNEE);
        //查询条件：业务编号/供应商名称/业务名称
        SupplierInfo supplierInfo = supplierInfoService.get(purchContractManagement.getSupplierId());
        Enterprise supplier = enterpriseService.getById(supplierInfo.getcEnterpriseId());
        if (supplier == null || supplier.getCorporateName() == null) {
            throw new BusinessException(CodeUtil.FAIL, "查询不到对应供应商信息");
        }
        String queryBusiness = purchContractManagement.getBusinessNumber() + FlowableUtil.splitChar + supplier.getCorporateName() +
                FlowableUtil.splitChar + salesContractBasicVo.getProjectName() + FlowableUtil.splitChar + salesContractBasicVo.getEnterprise()
                + FlowableUtil.splitChar + salesContractBasicVo.getMainEnterprise();
        ProcessInstance processInst = flowableService.startProcessInstance(purchContractManagement, procVariables,
                FlowableUtil.generateBusinessKey(purchContractManagement, ConstantUtil.PURCH_CONTRACT_CHANGE_PROCESS, queryBusiness), msgVariables, ConstantUtil.PURCH_CONTRACT_CHANGE_PROCESS);
        if (processInst == null) {
            throw new BusinessException(CodeUtil.FAIL, "流程启动失败");
        }

    }

    @Override
    public List<PurchContractSupplementInfo> findByManagerId(Long id) {
        return purchContractMapper.findByManagerId(id);
    }

//    @Override
//    public List<PurchContractBuyerSeller> findByBusinessInfo(BusinessSupplierInfo supplierInfo) {
//        supplierInfo = businessSupplierInfoService.getOne(new QueryWrapper<BusinessSupplierInfo>()
//                .eq("business_basic_info_id", supplierInfo.getBusinessBasicInfoId())
//                .eq("supplier_id", supplierInfo.getSupplierId()));
//        BusinessBasicInfo businessBasicInfo = businessBasicInfoService.get(supplierInfo.getBusinessBasicInfoId());
//        PurchContractManagement purchContractManagement = getOne(new QueryWrapper<PurchContractManagement>()
//                .eq("supplier_id", supplierInfo.getSupplierId()).eq("business_number", businessBasicInfo.getBusinessNumber()));
//        PurchContractBasicInfo purchContractBasicInfo = purchContractBasicInfoService
//                .getOne(new QueryWrapper<PurchContractBasicInfo>()
//                        .eq("purch_contract_management_id", purchContractManagement.getId())
//                        .orderByDesc("gmt_modified").last("limit 1"));
//        List<PurchContractBuyerSeller> purchContractSellers = purchContractBuyerSellerService.list(new QueryWrapper<PurchContractBuyerSeller>()
//                .eq("purch_contract_basic_info_id", purchContractBasicInfo.getId())
//                .eq("buyer_or_seller", 2));
//        return purchContractSellers;
//    }


    @Override
    public void deleteContract(Long id) {
        PurchContractManagement purchContractManagement = getById(id);
        if (ProjectInitiationStatusDict.ChildEnum.PROCESSING.getCode().equals(purchContractManagement.getContractStatus())) {
            //终止在途销售合同流程
            stopProcess(purchContractManagement.getId(), ConstantUtil.PURCH_CONTRACT);
            //删除销售合同
            removeById(id);
        } else {
            throw new ValidatorException(CodeUtil.FAIL, "该笔合同不可删除!");
        }
    }

    @Override
    public void downloadAllPurchFile(Long id, HttpServletResponse response) {

        List<FileStorage> allPurchFiles = new ArrayList<>();
        PurchContractBasicInfo basicInfo = purchContractBasicInfoService.lambdaQuery()
                .eq(PurchContractBasicInfo::getPurchContractManagementId, id).one();


        //采购合同已签署文件
        allPurchFiles.addAll(attachmentRefService.getFiles(AttachmentDto.builder()
                .setEntityId(basicInfo.getId()).setChildEnum(FileModuleDict.ChildEnum.PURCHASE_CONTRACT_SIGN_FILE).build()));

        List<PurchContractSupplementInfo> contractSupplementInfos = purchContractSupplementInfoService
                .list(new QueryWrapper<PurchContractSupplementInfo>().eq("c_purch_contract_management_id", id));

        if (CollectionUtil.isNotEmpty(contractSupplementInfos)) {
            contractSupplementInfos.stream().forEach(contractSupplementInfo -> {

                //采购合同变更已签署文件
                AttachmentDto attachmentDto = AttachmentDto.builder().setEntityId(contractSupplementInfo.getId())
                        .setChildEnum(FileModuleDict.ChildEnum.PURCHASE_CONTRACT_SUPPLEMENT_SIGN_FILE).build();
                allPurchFiles.addAll(attachmentRefService.getFiles(attachmentDto));
            });
        }

        //文件名去重
        fileStorageService.renameFileStorageList(allPurchFiles);
        fileStorageService.downloadZipFile(allPurchFiles, FileModuleDict.ChildEnum.PURCHASE_CONTRACT_ZIP_FILE.getCname(),
                FileModuleDict.ChildEnum.PURCHASE_CONTRACT_ZIP_FILE, response);


    }

    @Override
    public PurchContractCompletedVo getCompletedPurchContractByBusinessNumber(String businessNumber) {
        PurchContractCompletedVo purchContractCompletedVo = baseMapper.getCompletedPurchContractByBusinessNumber(businessNumber);
        if (purchContractCompletedVo != null) {
            if (purchContractCompletedVo.getCoreEnterpriseId() != null) {
                Enterprise coreEnterprise = enterpriseService.getById(purchContractCompletedVo.getCoreEnterpriseId());
                if (coreEnterprise != null) {
                    purchContractCompletedVo.setCoreEnterpriseName(coreEnterprise.getCorporateName());
                }
            }
            if (purchContractCompletedVo.getMainEnterpriseId() != null) {
                Enterprise mainEnterprise = enterpriseService.getById(purchContractCompletedVo.getMainEnterpriseId());
                if (mainEnterprise != null) {
                    purchContractCompletedVo.setMainEnterpriseName(mainEnterprise.getCorporateName());
                }
            }
            if (purchContractCompletedVo.getPlatformId() != null) {
                Platform platform = platformService.getById(purchContractCompletedVo.getPlatformId());
                if (platform != null) {
                    purchContractCompletedVo.setPlatformName(platform.getPlatformName());
                }
            }
            //经办人（供应商）
            PurchContractBuyerSeller cPurchContractBuyerSeller = purchContractBuyerSellerService.getOne(new QueryWrapper<PurchContractBuyerSeller>().eq("c_purch_contract_basic_info_id", purchContractCompletedVo.getcPurchContractBasicInfoId()).orderByDesc("gmt_modified")
                    .last("limit 1"));
            purchContractCompletedVo.setOperatorSupplier(cPurchContractBuyerSeller.getName());
        }
        return purchContractCompletedVo;
    }

    public void startProjectProcess(PurchContractVo purchContractVo) {


        User admin = userService.getByLoginName("admin");
        ThreadLocalUtil.setUser(admin);

        SalesContractBasicVo basicInfo = purchContractVo.getBasicInfo();
        CSalesContractBasicInfo contractBasicInfo = salesContractBasicInfoService.lambdaQuery()
                .eq(CSalesContractBasicInfo::getcSalesContractManagementId, purchContractVo.getBusinessKey()).one();
        PurchContractManagement purchContractManagement = get(purchContractVo.getBusinessKey());
        PurchContractBasicInfo purchContractBasicInfo = purchContractBasicInfoService
                .lambdaQuery().eq(PurchContractBasicInfo::getPurchContractManagementId, purchContractManagement.getId()).one();


        //开启流程
        Map<String, Object> procVariables = new HashMap<>();
        procVariables.put(ConstantUtil.PURCH_CONTRACT_CREATE_ASSIGNEE, admin.getId());
        //查询条件：业务编号 项目名称 主企业名称 核心企业名称
        String queryBusiness = basicInfo.getBusinessNumber() + FlowableUtil.splitChar + basicInfo.getProjectName()
                + FlowableUtil.splitChar + purchContractBasicInfo.getContractNumber() + FlowableUtil.splitChar +
                basicInfo.getMainEnterprise() + FlowableUtil.splitChar + basicInfo.getEnterprise();
        ProcessInstance processInst = flowableService.startProcessInstance(purchContractManagement, procVariables,
                FlowableUtil.generateBusinessKey(purchContractManagement, ConstantUtil.PURCH_CONTRACT, queryBusiness),
                null, ConstantUtil.PURCH_CONTRACT);
        if (processInst == null) {
            throw new BusinessException(CodeUtil.FAIL, "流程启动失败");
        }


    }

    private void completeProces(Long id) {

        PurchContractManagement purchContractManagement = baseMapper.selectById(id);
        PurchContractBasicInfo purch = purchContractBasicInfoService.getOne(new QueryWrapper<PurchContractBasicInfo>()
                .eq("c_purch_contract_management_id", id));
        //完成第一步流程
        //保存历史
        Long hisId = addHistory(purch);
        BusinessProcessingLog processingLog = businessProcessingLogService
                .getByBusinessTypeBusinessKey(ConstantUtil.PURCH_CONTRACT, purchContractManagement.getId());

        List<Long> legalSpecialists = userService.findUserIdByRole(ConstantUtil.LEGAL_SPECIALIST);
        String ids = legalSpecialists.stream().map(c -> c.toString()).collect(Collectors.joining(","));
        Map<String, Object> procVariables = new HashMap<>();
        procVariables.put(ConstantUtil.PURCH_CONTRACT_APPROVAL_CANDIDATEUSERS, ids);
        String taskId = processingLog.getHistoricTaskId();

        Map<String, Object> msgVariables = new HashMap<>();
        msgVariables.put(ConstantUtil.FLOWABLE_MSG_TITLE, "项目名称：" + purch.getProjectName());
        msgVariables.put(ConstantUtil.FLOWABLE_MSG_CONTENT,
                "项目名称“" + purch.getProjectName() + "”的项目已进入“"
                        + ConstantConversionUtil.flowBusinessKeyNames.get(ConstantUtil.PURCH_CONTRACT) + "—采购合同审核，"
                        + ConstantUtil.FLOWABLE_MSG_ASSIGNEE);
        flowableService.completeMyTask(taskId, purchContractManagement, procVariables, null, hisId, msgVariables,
                ConstantUtil.PURCH_CONTRACT, legalSpecialists);

    }

    private void stopProcess(Long businessKey, String businessType) {
        //查询日志信息
        List<BusinessProcessingLog> businessProcessingLogs = processingLogService.listForNullValueOfEndTime(businessKey, businessType);
        if (businessProcessingLogs != null && businessProcessingLogs.size() > 0) {
            Set<String> historyTaskId = businessProcessingLogs.stream().map(r -> r.getHistoricTaskId()).collect(Collectors.toSet());
            historyTaskId.forEach(taskId -> {
                String existTaskId = null;
                for (BusinessProcessingLog businessProcessingLog : businessProcessingLogs) {
                    if (taskId.equals(businessProcessingLog.getHistoricTaskId()) && (existTaskId == null || !existTaskId.equals(businessProcessingLog.getHistoricTaskId()))) {
                        existTaskId = businessProcessingLog.getHistoricTaskId();
                        //是否存在task
                        Boolean flag = flowableService.existTask(businessProcessingLog.getHistoricTaskId());
                        if (flag) {
                            String procInstId = taskService.createTaskQuery().taskId(businessProcessingLog.getHistoricTaskId()).singleResult().getProcessInstanceId();
                            ProcessInstance processInstance = runtimeService.createProcessInstanceQuery().processInstanceId(procInstId).singleResult();
                            if (processInstance != null) {
                                List<EndEvent> endNodes;
                                BpmnModel bpmnModel = repositoryService.getBpmnModel(processInstance.getProcessDefinitionId());
                                if (bpmnModel != null) {
                                    Process mainProcess = bpmnModel.getMainProcess();
                                    endNodes = mainProcess.findFlowElementsOfType(EndEvent.class);
                                } else {
                                    throw new BusinessException(CodeUtil.FAIL, "终止失败");
                                }
                                String endId = endNodes.get(0).getId();
                                String processInstanceId = processInstance.getProcessInstanceId();
                                //执行终止
                                List<Execution> executions = runtimeService.createExecutionQuery().parentId(processInstanceId).list();
                                List<String> executionIds = new ArrayList<>();
                                executions.forEach(execution -> executionIds.add(execution.getId()));
                                runtimeService.createChangeActivityStateBuilder().moveExecutionsToSingleActivityId(executionIds, endId).changeState();
                            }
                        }
                    }
                }
            });
        }
    }

}
