package com.gree.mall.manager.logic.engin;


import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.gree.mall.manager.bean.admin.AdminUserCom;
import com.gree.mall.manager.bean.engin.*;
import com.gree.mall.manager.bean.websit.WorkerSettlementVO;
import com.gree.mall.manager.commonmapper.workorder.RpMaterialMaper;
import com.gree.mall.manager.enums.*;
import com.gree.mall.manager.enums.engin.FeePayMethodEnum;
import com.gree.mall.manager.enums.workorder.OrderOperatorLogTypeEnum;
import com.gree.mall.manager.exception.RemoteServiceException;
import com.gree.mall.manager.logic.common.CommonLogic;
import com.gree.mall.manager.logic.common.WxPubNoticeLogic;
import com.gree.mall.manager.logic.workorder.OrderLogLogic;
import com.gree.mall.manager.plus.entity.*;
import com.gree.mall.manager.plus.service.*;
import com.gree.mall.manager.zfire.bean.ZfireParamBean;
import com.gree.mall.manager.zfire.util.FieldUtils;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

@Service
@Slf4j
@RequiredArgsConstructor
public class RpMaterialLogic {

    @Autowired
    RpMaterialMaper rpMaterialMaper;

    @Autowired
    CommonLogic commonLogic;

    @Autowired
    RpMaterialOrderService rpMaterialOrderService;

    @Autowired
    RpMaterialOrderItemService rpMaterialOrderItemService;

    @Autowired
    RpProjectRepairService rpProjectRepairService;

    @Autowired
    RpProjectRepairByService rpProjectRepairByService;

    @Autowired
    PgOrderBaseService pgOrderBaseService;

    @Autowired
    PgOrderWorkerService pgOrderWorkerService;

    @Autowired
    PgOrderProductService pgOrderProductService;

    @Autowired
    WxPubNoticeLogic wxPubNoticeLogic;

    @Autowired
    WorkerSettlementService workerSettlementService;

    @Autowired
    UserService userService;

    @Autowired
    NoticeRecordService noticeRecordService;

    @Autowired
    AdminUserService adminUserService;

    @Autowired
    AdminUserWebsitRelaService adminUserWebsitRelaService;

    @Autowired
    OrderLogLogic orderLogLogic;

    public IPage<RpMaterialOrderVO> list(ZfireParamBean zfireParamBean) {

        FieldUtils.supplyParam(zfireParamBean, RpMaterialOrderVO.class, commonLogic.getAdminUser());
        zfireParamBean.setAdminWebsitIds(zfireParamBean.getAdminWebsitIds());
        IPage<RpMaterialOrderVO> page = rpMaterialMaper.list(new Page(zfireParamBean.getPageNum(), zfireParamBean.getPageSize()), zfireParamBean);

        return page;
    }

    @Transactional(rollbackFor = Exception.class)
    public void examine(String id, String examineRemark, String examineStatus) {

        AdminUserCom adminUser = commonLogic.getAdminUser();
        RpMaterialOrder rpMaterialOrder = rpMaterialOrderService.getById(id);

  /*      if (rpProjectRepairByService.lambdaQuery().eq(RpProjectRepairBy::getProjectRepairId,rpMaterialOrder.getRpProjectRepairId())
                .eq(RpProjectRepairBy::getMobile,adminUser.getLinkPhone()).count() < 1) {
            throw new RemoteServiceException("非项目负责人，不可审批");
        }*/


        if (!rpMaterialOrder.getExamineStatus().equals(MaterialExamineStatusEnum.WAIT.getKey()))
            throw new RemoteServiceException("订单不属于待审批");

        RpMaterialOrder rpMaterialOrderIn = new RpMaterialOrder();
        rpMaterialOrderIn.setOrderId(rpMaterialOrder.getOrderId());
        rpMaterialOrderIn.setExamineName(adminUser.getNickName());
        rpMaterialOrderIn.setExamineRemark(examineRemark);
        rpMaterialOrderIn.setExamineTime(new Date());
        rpMaterialOrderIn.setExamineStatus(examineStatus);
        if (examineStatus.equals(MaterialExamineStatusEnum.FAIL.getKey())){
            rpMaterialOrderIn.setPayStatus(PayStatusEnum.CANCEL.getKey());
        }else {
            rpMaterialOrderIn.setPayStatus(PayStatusEnum.PAID.getKey());
            rpMaterialOrderIn.setPayTime(new Date());
        }

        rpMaterialOrderIn.updateById();

        if (rpMaterialOrder.getIsAllFee().equals("NO") && rpMaterialOrder.getFeePayMethod().equals(FeePayMethodEnum.EXAMINE.getKey())){
            RpMaterialOrder rpMaterialOrderUp = rpMaterialOrderService.getById(id);
            this.sendMaterialExamine(rpMaterialOrderUp);
            this.addExLog(rpMaterialOrderUp);
        }
    }

    private void addExLog(RpMaterialOrder rpMaterialOrderIn) {

        String status = "";
        if (rpMaterialOrderIn.getExamineStatus().equals(ExamineStatusEnum.FAIL.getKey()))
            status = "审批驳回";
        else if (rpMaterialOrderIn.getExamineStatus().equals(MaterialExamineStatusEnum.NO.getKey()))
            status = "取消";
        else
            status = "审批通过";
        PgOrderOperatorLog pgOrderOperatorLog = new PgOrderOperatorLog();
        pgOrderOperatorLog.setOrderBaseId(rpMaterialOrderIn.getWorkerOrderId());
        pgOrderOperatorLog.setType(OrderOperatorLogTypeEnum.FEIYONGEX.getRemark());
        pgOrderOperatorLog.setTypeText(OrderOperatorLogTypeEnum.FEIYONGEX.getRemark());
        pgOrderOperatorLog.setContent("费用申请"+status+"，审核人"+rpMaterialOrderIn.getExamineName());
        orderLogLogic.addLog(pgOrderOperatorLog);
    }

    private void sendMaterialExamine(RpMaterialOrder rpMaterialOrder) {
        List<RpMaterialOrderItem> rpMaterialOrderItems = rpMaterialOrderItemService.lambdaQuery().eq(RpMaterialOrderItem::getOrderId, rpMaterialOrder.getOrderId()).list();
        String text = "";
        for (RpMaterialOrderItem rpMaterialOrderItem : rpMaterialOrderItems) {
            text = text+rpMaterialOrderItem.getGoodsName()+"*"+rpMaterialOrderItem.getNum()+",";
        }
        String status = "";
        if (rpMaterialOrder.getExamineStatus().equals(ExamineStatusEnum.FAIL.getKey()))
            status = "审批驳回";
        else if (rpMaterialOrder.getExamineStatus().equals(MaterialExamineStatusEnum.NO.getKey()))
            status = "取消";
        else
            status = "审批通过";

        List<NoticeRecord> noticeRecords = new ArrayList<>();
        List<RpProjectRepairBy> list = rpProjectRepairByService.lambdaQuery().eq(RpProjectRepairBy::getProjectRepairId, rpMaterialOrder.getRpProjectRepairId()).list();
        for (RpProjectRepairBy rpProjectRepairBy : list) {
            wxPubNoticeLogic.addWbAmountApply(rpProjectRepairBy.getMobile(),rpMaterialOrder.getCompanyWechatId(),rpMaterialOrder.getWorkerName()+rpMaterialOrder.getWorkerMobile()
                    ,rpMaterialOrder.getCreateTime(),status+rpMaterialOrder.getRpProjectRepairName(),text+rpMaterialOrder.getTotalAmount(),rpMaterialOrder.getOrderId(),rpMaterialOrder.getOrderId());

            User user = userService.lambdaQuery().eq(User::getMobile, rpProjectRepairBy.getMobile()).last("limit 1").one();
            if (user != null) {
                NoticeRecord noticeRecord = new NoticeRecord();
                noticeRecord.setNoticeId(rpMaterialOrder.getOrderId());
                noticeRecord.setTitle("费用申请单"+status);
                noticeRecord.setContent(rpMaterialOrder.getOrderId());
                noticeRecord.setType(NoticeEnum.B.getKey());
                noticeRecord.setIsNotice(IsYesNoEnum.YES.getKey());
                noticeRecord.setReadFlag(IsYesNoEnum.NO.getKey());
                noticeRecord.setAdminUserId(user.getUserId());
                noticeRecord.setAdminNickName(user.getNickName());
                noticeRecord.setIsWorker(IsYesNoEnum.YES.getKey());
                noticeRecord.setIssueTime(new Date());
                noticeRecord.setAdminCompanyId(user.getUserId());
                noticeRecord.setAdminCompanyName(user.getCompanyName());
                noticeRecord.setNoticeType("WB");
                noticeRecord.setOrderId(rpMaterialOrder.getOrderId());
                noticeRecord.insert();
            }
        }

        List<AdminUserWebsitRela> adminUserWebsitRelas = adminUserWebsitRelaService.lambdaQuery()
                .eq(AdminUserWebsitRela::getAdminWebsitId, rpMaterialOrder.getWebsitId()).list();

        for (AdminUserWebsitRela adminUserWebsitRela : adminUserWebsitRelas) {
            AdminUser one = adminUserService.getById(adminUserWebsitRela.getAdminUserId());
            NoticeRecord noticeRecord = new NoticeRecord();
            noticeRecord.setNoticeId(rpMaterialOrder.getOrderId());
            noticeRecord.setTitle("费用申请单"+status);
            noticeRecord.setContent("费用申请单"+status);
            noticeRecord.setType(NoticeEnum.B.getKey());
            noticeRecord.setNoticeType(NoticeTypeEnum.SYSTEM.getKey());
            noticeRecord.setIsNotice(IsYesNoEnum.YES.getKey());
            noticeRecord.setReadFlag(IsYesNoEnum.NO.getKey());
            noticeRecord.setAdminUserId(adminUserWebsitRela.getAdminUserId());
            noticeRecord.setAdminNickName(one.getNickName());
            noticeRecord.setIssueTime(new Date());
            noticeRecord.setAdminCompanyId(rpMaterialOrder.getCompanyWechatId());
            noticeRecord.setAdminCompanyName(rpMaterialOrder.getCompanyWechatName());
            noticeRecord.setAdminNoticeType(AdminNoticTypeEnum.WBK.getKey());
            noticeRecord.setOrderId(rpMaterialOrder.getOrderId());
            noticeRecord.insert();
        }

        AdminUser one = adminUserService.lambdaQuery().eq(AdminUser::getCompanyWechatId, rpMaterialOrder.getCompanyWechatId())
                .eq(AdminUser::getType, 1).last("limit 1").one();

        NoticeRecord noticeRecordCom = new NoticeRecord();
        noticeRecordCom.setNoticeId(rpMaterialOrder.getOrderId());
        noticeRecordCom.setTitle("费用申请单"+status);
        noticeRecordCom.setContent("费用申请单"+status);
        noticeRecordCom.setType(NoticeEnum.B.getKey());
        noticeRecordCom.setNoticeType(NoticeTypeEnum.SYSTEM.getKey());
        noticeRecordCom.setIsNotice(IsYesNoEnum.YES.getKey());
        noticeRecordCom.setReadFlag(IsYesNoEnum.NO.getKey());
        noticeRecordCom.setAdminUserId(one.getAdminUserId());
        noticeRecordCom.setAdminNickName(one.getNickName());
        noticeRecordCom.setIssueTime(new Date());
        noticeRecordCom.setAdminCompanyId(rpMaterialOrder.getCompanyWechatId());
        noticeRecordCom.setAdminCompanyName(rpMaterialOrder.getCompanyWechatName());
        noticeRecordCom.setAdminNoticeType(AdminNoticTypeEnum.WBK.getKey());
        noticeRecordCom.setOrderId(rpMaterialOrder.getOrderId());
        noticeRecordCom.insert();
/*
        wxPubNoticeLogic.addWbAmountApply(rpMaterialOrder.getWorkerMobile(),rpMaterialOrder.getCompanyWechatId(),rpMaterialOrder.getWorkerName()+rpMaterialOrder.getWorkerMobile()
                ,rpMaterialOrder.getCreateTime(),status+rpMaterialOrder.getRpProjectRepairName(),text+rpMaterialOrder.getTotalAmount(),status+rpMaterialOrder.getOrderId(),rpMaterialOrder.getOrderId());

        NoticeRecord noticeRecord = new NoticeRecord();
        noticeRecord.setNoticeId(rpMaterialOrder.getOrderId());
        noticeRecord.setTitle("费用申请单"+status);
        noticeRecord.setContent(rpMaterialOrder.getOrderId());
        noticeRecord.setType(NoticeEnum.B.getKey());
        noticeRecord.setIsNotice(IsYesNoEnum.YES.getKey());
        noticeRecord.setReadFlag(IsYesNoEnum.NO.getKey());
        noticeRecord.setAdminUserId(rpMaterialOrder.getWorkerId());
        noticeRecord.setAdminNickName(rpMaterialOrder.getWorkerName());
        noticeRecord.setIsWorker("YES");
        noticeRecord.setIssueTime(new Date());
        noticeRecord.setAdminCompanyId(rpMaterialOrder.getWorkerId());
        noticeRecord.setAdminCompanyName(rpMaterialOrder.getCompanyWechatName());
        noticeRecord.setNoticeType("WB");
        noticeRecord.setOrderId(rpMaterialOrder.getOrderId());
        noticeRecords.add(noticeRecord);*/


        //noticeRecordService.saveBatch(noticeRecords);
    }

    public RpmaterialOrderDetail detail(String id) {

        RpMaterialOrder rpMaterialOrder = rpMaterialOrderService.getById(id);
        RpmaterialOrderDetail rpmaterialOrderDetail = BeanUtil.toBean(rpMaterialOrder, RpmaterialOrderDetail.class);

        List<RpMaterialOrderItem> list = rpMaterialOrderItemService.lambdaQuery()
                .eq(RpMaterialOrderItem::getOrderId, rpMaterialOrder.getOrderId()).list();

        rpmaterialOrderDetail.setRpMaterialOrderItems(list);


        PgOrderBase pgOrderBase = pgOrderBaseService.getById(rpmaterialOrderDetail.getWorkerOrderId());

        List<PgOrderWorker> pgOrderWorkers = pgOrderWorkerService.lambdaQuery().eq(PgOrderWorker::getOrderBaseId, pgOrderBase.getId()).list();

        rpmaterialOrderDetail.setPgOrderBase(pgOrderBase);
        rpmaterialOrderDetail.setPgOrderWorkers(pgOrderWorkers);

        List<PgOrderProduct> pgOrderProducts = pgOrderProductService.lambdaQuery().eq(PgOrderProduct::getOrderBaseId, pgOrderBase.getId()).list();

        rpmaterialOrderDetail.setPgOrderProducts(pgOrderProducts);
        return rpmaterialOrderDetail;
    }

    public Boolean isBy(String orderBaserId) {

        AdminUserCom adminUser = commonLogic.getAdminUser();

        PgOrderBase pgOrderBase = pgOrderBaseService.getById(orderBaserId);


        if (rpProjectRepairByService.lambdaQuery().eq(RpProjectRepairBy::getProjectRepairId,pgOrderBase.getRpProjectRepairId())
                .eq(RpProjectRepairBy::getMobile,adminUser.getLinkPhone())
                .eq(RpProjectRepairBy::getFeeExamine,"YES")
                .count() < 1) {
            return false;
        }

        return true;

    }

    public void cancel(String id) {

        AdminUserCom adminUser = commonLogic.getAdminUser();
        RpMaterialOrder rpMaterialOrder = rpMaterialOrderService.getById(id);

/*        if (rpProjectRepairByService.lambdaQuery().eq(RpProjectRepairBy::getProjectRepairId,rpMaterialOrder.getRpProjectRepairId())
                .eq(RpProjectRepairBy::getMobile,adminUser.getLinkPhone()).count() < 1) {
            throw new RemoteServiceException("非项目负责人，不可取消");
        }


        if (!rpMaterialOrder.getExamineStatus().equals(MaterialExamineStatusEnum.WAIT.getKey()))
            throw new RemoteServiceException("订单不属于待审批");*/

        RpMaterialOrder rpMaterialOrderIn = new RpMaterialOrder();
        rpMaterialOrderIn.setOrderId(rpMaterialOrder.getOrderId());
        rpMaterialOrderIn.setExamineStatus(MaterialExamineStatusEnum.NO.getKey());
        rpMaterialOrderIn.setCancelName(adminUser.getNickName());
        rpMaterialOrderIn.setCancelTime(new Date());
        rpMaterialOrderIn.updateById();

        if (rpMaterialOrder.getIsAllFee().equals("NO") && rpMaterialOrder.getFeePayMethod().equals(FeePayMethodEnum.EXAMINE.getKey())){
            RpMaterialOrder rpMaterialOrderUp = rpMaterialOrderService.getById(id);
            this.sendMaterialExamine(rpMaterialOrderUp);
        }
    }

    public IPage<WorkerMaterialSettlementVO> workerSettlementPageV2(ZfireParamBean zfireParamBean) {
        AdminUserCom adminUser = commonLogic.getAdminUser();
        List<String> companyWechatIds = adminUser.getCompanyWechatIds();

        //1.组装查询条件
        ZfireParamBean zfireParam = FieldUtils.supplyParam(zfireParamBean, WorkerSettlementVO.class,adminUser);
        IPage<WorkerMaterialSettlementVO> workerMaterialSettlementVOIPage = rpMaterialMaper.workerSettlementPageV2(new Page(zfireParamBean.getPageNum(),
                        zfireParamBean.getPageSize()),
                zfireParam);

        return workerMaterialSettlementVOIPage;
    }

    public List<RpMaterialOrderAllVO> detailWorker(String workerOrderId) {
        List<RpMaterialOrder> rpMaterialOrders = rpMaterialOrderService.lambdaQuery().eq(RpMaterialOrder::getWorkerOrderId, workerOrderId).list();

        List<RpMaterialOrderAllVO> rpMaterialOrderVOS = BeanUtil.copyToList(rpMaterialOrders, RpMaterialOrderAllVO.class);

        for (RpMaterialOrderAllVO rpMaterialOrderVO : rpMaterialOrderVOS) {
            List<RpMaterialOrderItem> rpMaterialOrderItemList = rpMaterialOrderItemService.lambdaQuery().eq(RpMaterialOrderItem::getOrderId, rpMaterialOrderVO.getOrderId()).list();
            rpMaterialOrderVO.setRpMaterialOrderItems(rpMaterialOrderItemList);

            PgOrderBase pgOrderBase = pgOrderBaseService.getById(rpMaterialOrderVO.getWorkerOrderId());

            List<PgOrderWorker> list = pgOrderWorkerService.lambdaQuery().eq(PgOrderWorker::getOrderBaseId, pgOrderBase.getId()).list();

            rpMaterialOrderVO.setPgOrderBase(pgOrderBase);
            rpMaterialOrderVO.setPgOrderWorkers(list);

            List<PgOrderProduct> pgOrderProducts = pgOrderProductService.lambdaQuery().eq(PgOrderProduct::getOrderBaseId, pgOrderBase.getId()).list();

            rpMaterialOrderVO.setPgOrderProducts(pgOrderProducts);
        }

        return rpMaterialOrderVOS;

    }

    public IPage<RpMaterialOrderLineVO> listLine(ZfireParamBean zfireParamBean) {
        FieldUtils.supplyParam(zfireParamBean, RpMaterialOrderVO.class, commonLogic.getAdminUser());
        zfireParamBean.setAdminWebsitIds(zfireParamBean.getAdminWebsitIds());
        IPage<RpMaterialOrderLineVO> page = rpMaterialMaper.listLine(new Page(zfireParamBean.getPageNum(), zfireParamBean.getPageSize()), zfireParamBean);

        return page;
    }

    public void lineSettlement(List<String> id) {
        AdminUserCom adminUser = commonLogic.getAdminUser();

        if (rpMaterialOrderService.lambdaQuery()
                .in(RpMaterialOrder::getOrderId, id)
                .eq(RpMaterialOrder::getPayType, SettlementPayTypeEnum.LINE.getKey())
                .notIn(RpMaterialOrder::getStatus, SettlementStatusEnum.WAIT.getKey())
                .count() > 0) {
            throw new RemoteServiceException("存在非待结算得结算");
        }
        List<RpMaterialOrder> list = rpMaterialOrderService.lambdaQuery()
                .in(RpMaterialOrder::getOrderId, id)
                .eq(RpMaterialOrder::getStatus, SettlementStatusEnum.WAIT.getKey())
                .eq(RpMaterialOrder::getPayType, SettlementPayTypeEnum.LINE.getKey())
                .list();

        for (RpMaterialOrder settlementOrder : list) {
            WorkerSettlement one = workerSettlementService.lambdaQuery()
                    .eq(WorkerSettlement::getWorkerId, settlementOrder.getWorkerId())
                    .eq(WorkerSettlement::getPayType, SettlementPayTypeEnum.LINE.getKey())
                    .eq(WorkerSettlement::getType, "PROJECT")
                    .last("limit 1").one();
            one.setGiveAmount(one.getGiveAmount().add(settlementOrder.getTotalAmount()));

            one.updateById();
        }

        rpMaterialOrderService.lambdaUpdate()
                .in(RpMaterialOrder::getOrderId, id)
                .eq(RpMaterialOrder::getStatus, SettlementStatusEnum.WAIT.getKey())
                .set(RpMaterialOrder::getStatus, SettlementStatusEnum.OVER.getKey())
                .set(RpMaterialOrder::getSettleName,adminUser.getNickName() )
                .set(RpMaterialOrder::getSettleTime, new Date())
                .update();
    }

    public IPage<RpMaterialOrderWechatVO> listWechat(ZfireParamBean zfireParamBean) {
        FieldUtils.supplyParam(zfireParamBean, RpMaterialOrderVO.class, commonLogic.getAdminUser());
        zfireParamBean.setAdminWebsitIds(zfireParamBean.getAdminWebsitIds());
        IPage<RpMaterialOrderWechatVO> page = rpMaterialMaper.listWechat(new Page(zfireParamBean.getPageNum(), zfireParamBean.getPageSize()), zfireParamBean);

        return page;
    }

    public void lineSettlementHui(String workerId, String websitId) {
        AdminUserCom adminUser = commonLogic.getAdminUser();

        List<RpMaterialOrder> list = rpMaterialOrderService.lambdaQuery()
                .in(RpMaterialOrder::getWorkerId, workerId)
                .in(RpMaterialOrder::getWebsitId, websitId)
                .eq(RpMaterialOrder::getStatus, SettlementStatusEnum.WAIT.getKey())
                .eq(RpMaterialOrder::getPayType, SettlementPayTypeEnum.LINE.getKey())
                .list();

        for (RpMaterialOrder settlementOrder : list) {
            WorkerSettlement one = workerSettlementService.lambdaQuery()
                    .eq(WorkerSettlement::getWorkerId, settlementOrder.getWorkerId())
                    .eq(WorkerSettlement::getWebsitId, settlementOrder.getWebsitId())
                    .eq(WorkerSettlement::getPayType, SettlementPayTypeEnum.LINE.getKey())
                    .eq(WorkerSettlement::getType, "PROJECT")
                    .last("limit 1").one();
            one.setGiveAmount(one.getGiveAmount().add(settlementOrder.getTotalAmount()));

            one.updateById();
        }

        rpMaterialOrderService.lambdaUpdate()
                .in(RpMaterialOrder::getWorkerId, workerId)
                .in(RpMaterialOrder::getWebsitId, websitId)
                .eq(RpMaterialOrder::getStatus, SettlementStatusEnum.WAIT.getKey())
                .set(RpMaterialOrder::getStatus, SettlementStatusEnum.OVER.getKey())
                .set(RpMaterialOrder::getSettleName,adminUser.getNickName() )
                .set(RpMaterialOrder::getSettleTime, new Date())
                .update();
    }

    public IPage<RpMaterialOrderAllListVO> listAll(ZfireParamBean zfireParamBean) {
        FieldUtils.supplyParam(zfireParamBean, RpMaterialOrderVO.class, commonLogic.getAdminUser());
        zfireParamBean.setAdminWebsitIds(zfireParamBean.getAdminWebsitIds());
        IPage<RpMaterialOrderAllListVO> page = rpMaterialMaper.listAll(new Page(zfireParamBean.getPageNum(), zfireParamBean.getPageSize()), zfireParamBean);

        return page;
    }
}
