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

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.db.sql.Order;
import com.alibaba.druid.support.spring.stat.annotation.Stat;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.IdWorker;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.gree.mall.manager.bean.admin.AdminUserCom;
import com.gree.mall.manager.bean.listvo.workorder.OrderBaseVO;
import com.gree.mall.manager.bean.policy.WorkerManagerBean;
import com.gree.mall.manager.bean.policy.WorkerManagerDetail;
import com.gree.mall.manager.bean.policy.WorkerUserCount;
import com.gree.mall.manager.bean.workorder.WorkerNumberCheckVO;
import com.gree.mall.manager.commonmapper.CommonMapper;
import com.gree.mall.manager.enums.*;
import com.gree.mall.manager.enums.workorder.OrderBaseStatusEnum;
import com.gree.mall.manager.exception.RemoteServiceException;
import com.gree.mall.manager.logic.common.CommonLogic;
import com.gree.mall.manager.plus.entity.*;
import com.gree.mall.manager.plus.service.*;
import com.gree.mall.manager.utils.StringUtil;
import com.gree.mall.manager.zfire.bean.WorkerParamBean;
import com.gree.mall.manager.zfire.util.FieldUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.time.Instant;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.ZoneId;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

@Service
public class WorkerManagerLogic {

    @Autowired
    WebsitUserService websitUserService;

    @Autowired
    PgOrderBaseService pgOrderBaseService;

    @Autowired
    WorkerImgService workerImgService;

    @Autowired
    WorkerPolicyService workerPolicyService;

    @Autowired
    UserService userService;

    @Autowired
    AdminWebsitService adminWebsitService;

    @Autowired
    CommonLogic commonLogic;


    @Autowired
    PolicyOrderService policyOrderService;

    @Autowired
    SysDictCompanyService sysDictCompanyService;

    @Autowired
    CommonMapper commonMapper;

    @Autowired
    WorkerNumberCheckService workerNumberCheckService;

    @Autowired
    PolicyService policyService;



    public void stop(String id) {

        AdminUserCom adminUser = commonLogic.getAdminUser();
        WebsitUser websitUserBean = websitUserService.getById(id);
        if (!websitUserBean.getExamineStatus().equals(ExamineWorkerStatusEnum.OK.getKey()))
            throw new RemoteServiceException("师傅不处于审核通过");

        WebsitUser websitUser = new WebsitUser();
        websitUser.setId(id);
        websitUser.setExamineStatus(ExamineWorkerStatusEnum.STOP.getKey());
        websitUser.updateById();

        WebsitUserLog websitUserLog = new WebsitUserLog();

        websitUserLog.setTypeText("暂停接单");
        websitUserLog.setOpRemark("操作该账号暂停接单");
        websitUserLog.setWebsitUserId(websitUserBean.getId());
        websitUserLog.setWebsitName(websitUserBean.getWebsitName());
        websitUserLog.setWebsitId(websitUserBean.getWebsitId());
        websitUserLog.insert();

    }

    public void activation(String id) {

        WebsitUser websitUserBean = websitUserService.getById(id);
        if (!websitUserBean.getExamineStatus().equals(ExamineWorkerStatusEnum.STOP.getKey()))
            throw new RemoteServiceException("师傅不处于暂停状态");

        WebsitUser websitUser = new WebsitUser();
        websitUser.setId(id);
        websitUser.setExamineStatus(ExamineWorkerStatusEnum.POLICY_WAIT.getKey());
        websitUser.updateById();

        WebsitUserLog websitUserLog = new WebsitUserLog();

        websitUserLog.setTypeText("激活账号");
        websitUserLog.setOpRemark("操作激活账号");
        websitUserLog.setWebsitUserId(websitUserBean.getId());
        websitUserLog.setWebsitName(websitUserBean.getWebsitName());
        websitUserLog.setWebsitId(websitUserBean.getWebsitId());

        websitUserLog.insert();

        if (!StringUtil.isEmpty(websitUserBean.getWorkerNumber())
                && userService.lambdaQuery().eq(User::getWorkerNumber,websitUserBean.getWorkerNumber()).ne(User::getUserId,websitUserBean.getUserId())
                .count() > 0
        ){
            throw new RemoteServiceException("账号已被使用无法激活");
        }
    }

    @Transactional(rollbackFor = Exception.class)
    public void quit(String id) {

        WebsitUser websitUserBean = websitUserService.getById(id);
        if (!websitUserBean.getExamineStatus().equals(ExamineWorkerStatusEnum.OK.getKey()))
            throw new RemoteServiceException("师傅不处于审核通过");


        if (pgOrderBaseService.lambdaQuery()
                .and(item -> item.eq(!StringUtil.isEmpty(websitUserBean.getWorkerNumber()),PgOrderBase::getWorkerNumber,websitUserBean.getWorkerNumber())
                        .or(!StringUtil.isEmpty(websitUserBean.getWorkerNumber())).like(PgOrderBase::getWorkerIdList,websitUserBean.getUserId()))
                .eq(PgOrderBase::getWebsitId,websitUserBean.getWebsitId())
                .notIn(PgOrderBase::getOrderStatus, OrderBaseStatusEnum.YQX.getKey(),OrderBaseStatusEnum.YJS.getKey(),
                        OrderBaseStatusEnum.YWG.getKey(),OrderBaseStatusEnum.FWQX.getKey(),OrderBaseStatusEnum.YWGO.getKey(),
                        OrderBaseStatusEnum.YGBGD.getKey(),OrderBaseStatusEnum.FGFZF.getKey(),OrderBaseStatusEnum.YZFGD.getKey(),
                        OrderBaseStatusEnum.FZXBWG.getKey(),OrderBaseStatusEnum.FBBWG.getKey(),OrderBaseStatusEnum.LSXX.getKey(),
                        OrderBaseStatusEnum.PLGB.getKey(),OrderBaseStatusEnum.ZCGB.getKey()
                        ).count() > 0) {

            throw new RemoteServiceException("师傅存在未完工工单，请改派后再离职");
        }


        WebsitUser websitUser = new WebsitUser();
        websitUser.setId(id);
        websitUser.setExamineStatus(ExamineWorkerStatusEnum.QUIT.getKey());
        websitUser.updateById();

        AdminWebsit adminWebsit = adminWebsitService.getById(websitUserBean.getWebsitId());
        if (adminWebsit.getInsureType().equals("意外险,雇主险")){
            policyOrderService.lambdaUpdate()
                    .ge(PolicyOrder::getEndTime,new Date())
                    .eq(PolicyOrder::getWebsitUserId,websitUser.getId())
                    .eq(PolicyOrder::getType,PolicyTypeEnum.EM.getKey())
                    .set(PolicyOrder::getPolicyOrderStatus,PolicyOrderEmStutasEnum.KTH.getKey())
                    .update();

            workerPolicyService.lambdaUpdate()
                    .ge(WorkerPolicy::getEndTime,new Date())
                    .eq(WorkerPolicy::getWebsitUserId,websitUser.getId())
                    .eq(WorkerPolicy::getPolicyType,PolicyTypeEnum.EM.getKey())
                    .set(WorkerPolicy::getStatus,PolicyOrderEmStutasEnum.YSX.getKey())
                    .set(WorkerPolicy::getEndTime,new Date())
                    .update();

        }

        WebsitUserLog websitUserLog = new WebsitUserLog();

        websitUserLog.setTypeText("操作离职");
        websitUserLog.setOpRemark("操作离职");
        websitUserLog.setWebsitUserId(websitUserBean.getId());
        websitUserLog.setWebsitName(websitUserBean.getWebsitName());
        websitUserLog.setWebsitId(websitUserBean.getWebsitId());

        websitUserLog.insert();
    }

    public void againQuit(String id) {

        WebsitUser websitUserBean = websitUserService.getById(id);
        if (!websitUserBean.getExamineStatus().equals(ExamineWorkerStatusEnum.QUIT.getKey()))
            throw new RemoteServiceException("师傅不处于离职状态");

        WebsitUser websitUser = new WebsitUser();
        websitUser.setId(id);
        websitUser.setExamineStatus(ExamineWorkerStatusEnum.POLICY_WAIT.getKey());
        websitUser.updateById();

        AdminWebsit adminWebsit = adminWebsitService.getById(websitUserBean.getWebsitId());
        if (adminWebsit.getInsureType().equals("意外险,雇主险")){
            List<PolicyOrder> policyOrders = policyOrderService.lambdaQuery()
                    .ge(PolicyOrder::getEndTime, new Date())
                    .eq(PolicyOrder::getWebsitUserId, websitUser.getId())
                    .eq(PolicyOrder::getType, PolicyTypeEnum.EM.getKey())
                    .eq(PolicyOrder::getPolicyOrderStatus, PolicyOrderEmStutasEnum.KTH.getKey())
                    .list();

            for (PolicyOrder policyOrder : policyOrders) {
                workerPolicyService.lambdaUpdate().eq(WorkerPolicy::getOrderId,policyOrder.getId())
                        .set(WorkerPolicy::getEndTime,policyOrder.getEndTime())
                        .set(WorkerPolicy::getStatus,PolicyOrderStatusEnum.BZZ.getKey()).update();

                policyOrder.setPolicyOrderStatus(PolicyOrderStatusEnum.BZZ.getKey());
                policyOrder.updateById();
            }

        }

        if (!StringUtil.isEmpty(websitUserBean.getWorkerNumber())
                && userService.lambdaQuery().eq(User::getWorkerNumber,websitUserBean.getWorkerNumber()).ne(User::getUserId,websitUserBean.getUserId())
                .count() > 0
        ){
            throw new RemoteServiceException("账号已被使用无法激活");
        }

        WebsitUserLog websitUserLog = new WebsitUserLog();

        websitUserLog.setTypeText("重新入职");
        websitUserLog.setOpRemark("操作重新入职");
        websitUserLog.setWebsitUserId(websitUserBean.getId());
        websitUserLog.setWebsitName(websitUserBean.getWebsitName());
        websitUserLog.setWebsitId(websitUserBean.getWebsitId());

        websitUserLog.insert();
    }

    @Transactional(rollbackFor = Exception.class)
    public void update(WorkerManagerBean workerManagerBean) {
        workerManagerBean.setCreateTime(null);

        User user = userService.getById(workerManagerBean.getUserId());

        WebsitUser websitUser = websitUserService.getById(workerManagerBean.getId());

        if (
                !(user.getIdCardEndTime().equals(workerManagerBean.getUser().getIdCardEndTime())) ||
                !(user.getIdCardStartTime().equals(workerManagerBean.getUser().getIdCardStartTime()))){
            WebsitUserLog websitUserLog = new WebsitUserLog();

            websitUserLog.setTypeText("身份证修改");
            websitUserLog.setOpRemark("原身份证日期"+ DateUtil.format(user.getIdCardStartTime(),"yyyy-MM-dd")+","+
                    DateUtil.format(user.getIdCardEndTime(),"yyyy-MM-dd")+"，变更为"+
                    DateUtil.format(workerManagerBean.getUser().getIdCardStartTime(),"yyyy-MM-dd")+","+
                            DateUtil.format(workerManagerBean.getUser().getIdCardEndTime(),"yyyy-MM-dd"));

            websitUserLog.setWebsitUserId(workerManagerBean.getId());

            websitUserLog.insert();
        }

        if (!user.getMobile().equals(workerManagerBean.getUser().getMobile())){

            if (userService.lambdaQuery().eq(User::getMobile,workerManagerBean.getUser().getMobile())
                    .ne(User::getUserId,websitUser.getUserId()).count() > 0) {

                throw new RemoteServiceException("手机号已经被绑定，无法更改");
            }

            WebsitUserLog websitUserLog = new WebsitUserLog();
            websitUserLog.setTypeText("手机号修改");
            websitUserLog.setOpRemark("原手机号为"+user.getMobile()+",变更为"+workerManagerBean.getUser().getMobile());

            websitUserLog.setWebsitUserId(workerManagerBean.getId());

            websitUserLog.insert();

        }

        if (!user.getNickName().equals(workerManagerBean.getUser().getNickName())){
            WebsitUserLog websitUserLog = new WebsitUserLog();
            websitUserLog.setTypeText("师傅名称修改");
            websitUserLog.setOpRemark("原师傅名称为"+user.getNickName()+",变更为"+workerManagerBean.getUser().getNickName());

            websitUserLog.setWebsitUserId(workerManagerBean.getId());

            websitUserLog.insert();
        }


        workerManagerBean.setExamineStatus(ExamineWorkerStatusEnum.POLICY_WAIT.getKey());



        if (!StringUtil.isEmpty(workerManagerBean.getUser().getWorkerNumber())) {

            workerManagerBean.setWorkerNumber(workerManagerBean.getUser().getWorkerNumber().trim());
            workerManagerBean.getUser().setWorkerNumber(workerManagerBean.getUser().getWorkerNumber().trim());

            if (userService.lambdaQuery().eq(User::getWorkerNumber, workerManagerBean.getUser().getWorkerNumber())
                    .ne(User::getUserId, workerManagerBean.getUserId()).count() > 0) {

                if (websitUserService.lambdaQuery().eq(WebsitUser::getWorkerNumber,  workerManagerBean.getUser().getWorkerNumber())
                        .ne(WebsitUser::getUserId, workerManagerBean.getUserId())
                        .notIn(WebsitUser::getExamineStatus, ExamineWorkerStatusEnum.QUIT.getKey(),ExamineWorkerStatusEnum.STOP.getKey()).count() > 0) {
                    throw new RemoteServiceException("已有该师傅编号");
                }

                //离职师傅去除手机号
                userService.lambdaUpdate().eq(User::getWorkerNumber, workerManagerBean.getWorkerNumber())
                        .ne(User::getUserId, workerManagerBean.getUserId())
                        .set(User::getWorkerNumber,"")
                        .set(User::getType,"GENERAL").update();

            }
        }


        workerManagerBean.setBankAccount(workerManagerBean.getUser().getBankAccount());
        workerManagerBean.setWorkerNumber(workerManagerBean.getUser().getWorkerNumber());

        workerManagerBean.updateById();


        workerManagerBean.getUser().updateById();




        workerManagerBean.getUser().setWorkerNumber(workerManagerBean.getWorkerNumber());

        workerManagerBean.getUser().updateById();

        workerImgService.lambdaUpdate().eq(WorkerImg::getWorkerId,workerManagerBean.getUserId())
                .remove();


        for (WorkerImg workerImg : workerManagerBean.getWorkerImgs()) {
            workerImg.setWorkerId(workerManagerBean.getUserId());
            workerImg.setUserId(workerManagerBean.getUserId());
        }


        workerImgService.saveOrUpdateBatch(workerManagerBean.getWorkerImgs());

        this.changeList(workerManagerBean.getWorkerPolicies(),workerManagerBean.getId());

        workerPolicyService.lambdaUpdate().eq(WorkerPolicy::getWebsitUserId,workerManagerBean.getId()).remove();


        for (WorkerPolicy workerPolicy : workerManagerBean.getWorkerPolicies()) {
            workerPolicy.setWorkerId(workerManagerBean.getUserId());
            workerPolicy.setWebsitUserId(workerManagerBean.getId());
            workerPolicy.setEndTime(this.getEndOfDay(workerPolicy.getEndTime()));
        }


        workerPolicyService.saveOrUpdateBatch(workerManagerBean.getWorkerPolicies());


        workerManagerBean.setExamineStatus(ExamineStatusEnum.OK.getKey());
        this.examine(workerManagerBean);

    }

    private void changeList(List<WorkerPolicy> workerPolicies, String id) {

        List<WorkerPolicy> workerPolicyList = workerPolicyService.lambdaQuery().eq(WorkerPolicy::getWebsitUserId, id).list();

        for (WorkerPolicy workerPolicy : workerPolicies) {

            String policy ="";

            if (workerPolicy.getPolicyType().equals(PolicyTypeEnum.AC.getKey()))
                policy = "意外险：";

            if (workerPolicy.getPolicyType().equals(PolicyTypeEnum.EM.getKey()))
                policy = "雇主险：";

            if (workerPolicy.getPolicyType().equals(PolicyTypeEnum.IN.getKey()))
                policy = "工伤险：";

            if (StringUtil.isEmpty(workerPolicy.getId())){
                WebsitUserLog websitUserLog = new WebsitUserLog();

                websitUserLog.setTypeText("添加保险");
                websitUserLog.setOpRemark(policy+"保险时间为"+ DateUtil.format(workerPolicy.getStartTime(),"yyyy-MM-dd")+","+
                        DateUtil.format(workerPolicy.getEndTime(),"yyyy-MM-dd"));

                websitUserLog.setWebsitUserId(workerPolicy.getWebsitUserId());
                websitUserLog.setWebsitName(workerPolicy.getWebsitName());
                websitUserLog.setWebsitId(workerPolicy.getWebsitId());

                websitUserLog.insert();
            }else {
                List<WorkerPolicy> workerPolicyLists = workerPolicyList.stream()
                        .filter(item -> item.getId().equals(workerPolicy.getId())).collect(Collectors.toList());
                if (CollectionUtils.isEmpty(workerPolicyLists))
                    continue;

                WorkerPolicy workerPolicyOne = workerPolicyLists.get(0);

                if (!(workerPolicyOne.getStartTime().equals(workerPolicy.getStartTime()) && workerPolicyOne.getEndTime().equals(workerPolicy.getEndTime()))) {
                    WebsitUserLog websitUserLog = new WebsitUserLog();

                    websitUserLog.setTypeText("更改保险日期");
                    websitUserLog.setOpRemark(policy+"原保险时间为"+ DateUtil.format(workerPolicyOne.getStartTime(),"yyyy-MM-dd")+","+
                            DateUtil.format(workerPolicyOne.getEndTime(),"yyyy-MM-dd")+"，变更为"+ DateUtil.format(workerPolicy.getStartTime(),"yyyy-MM-dd")+","+
                            DateUtil.format(workerPolicy.getEndTime(),"yyyy-MM-dd"));

                    websitUserLog.setWebsitUserId(workerPolicy.getWebsitUserId());
                    websitUserLog.setWebsitName(workerPolicy.getWebsitName());
                    websitUserLog.setWebsitId(workerPolicy.getWebsitId());

                    websitUserLog.insert();

                }


            }
        }
    }


    @Transactional(rollbackFor = Exception.class)
    public WorkerManagerDetail detail(String id) {

        WebsitUser websitUser = websitUserService.getById(id);

        AdminWebsit adminWebsit = adminWebsitService.getById(websitUser.getWebsitId());

        WorkerManagerDetail workerManagerDetail = BeanUtil.toBean(websitUser, WorkerManagerDetail.class);

        workerManagerDetail.setUser(userService.getById(workerManagerDetail.getUserId()));

        List<WorkerImg> list = workerImgService.lambdaQuery().eq(WorkerImg::getUserId, websitUser.getUserId()).list();

        List<WorkerPolicy> workerPolicies = workerPolicyService.lambdaQuery().eq(WorkerPolicy::getWebsitUserId, websitUser.getId()).list();

        workerManagerDetail.setWorkerImgs(list);
        workerManagerDetail.setWorkerPolicies(workerPolicies);

        workerManagerDetail.setWebsitName(adminWebsit.getName());

        return workerManagerDetail;

    }

    @Transactional(rollbackFor = Exception.class)
    public void examineWait(WorkerManagerBean workerManagerBean) {

        AdminUserCom adminUser = commonLogic.getAdminUser();

        WebsitUser websitUser = websitUserService.getById(workerManagerBean.getId());

        if (!websitUser.getExamineStatus().equals(ExamineWorkerStatusEnum.WAIT.getKey()))
            throw new RemoteServiceException("状态不为待审核状态");

        if (workerManagerBean.getUser().getEndTime() != null && workerManagerBean.getUser().getEndTime().before(new Date()))
            throw new RemoteServiceException("高空证不能填入失效时间");

        if (workerManagerBean.getUser().getIdCardEndTime() != null && workerManagerBean.getUser().getIdCardEndTime().before(new Date()))
            throw new RemoteServiceException("身份证不能填入过期时间");

        workerManagerBean.setCreateTime(null);


        workerManagerBean.setExamineBy(adminUser.getNickName());
        workerManagerBean.setExamineTime(new Date());

        workerManagerBean.setWorkerNumber(workerManagerBean.getUser().getWorkerNumber());
        User user = userService.getById(workerManagerBean.getUserId());

        if (!StringUtil.isEmpty(user.getWorkerNumber())){
            if (!workerManagerBean.getWorkerNumber().equals(user.getWorkerNumber())) {
                throw new RemoteServiceException("师傅编号已经录入不允许更改");
            }
        }
        if (!StringUtil.isEmpty(workerManagerBean.getUser().getWorkerNumber())) {


            if (userService.lambdaQuery().eq(User::getWorkerNumber, workerManagerBean.getUser().getWorkerNumber())
                    .ne(User::getUserId, workerManagerBean.getUserId()).count() > 0)
                throw new RemoteServiceException("已有该师傅编号");
        }


        workerManagerBean.setBankAccount(workerManagerBean.getUser().getBankAccount());
        workerManagerBean.setWorkerNumber(workerManagerBean.getUser().getWorkerNumber());


        workerManagerBean.updateById();

        workerManagerBean.getUser().updateById();

        workerImgService.lambdaUpdate().eq(WorkerImg::getWorkerId,workerManagerBean.getUserId())
                .remove();


        for (WorkerImg workerImg : workerManagerBean.getWorkerImgs()) {
            workerImg.setWorkerId(workerManagerBean.getUserId());
            workerImg.setUserId(workerManagerBean.getUserId());
        }

        this.changeList(workerManagerBean.getWorkerPolicies(),workerManagerBean.getId());


        workerImgService.saveOrUpdateBatch(workerManagerBean.getWorkerImgs());

        workerPolicyService.lambdaUpdate().eq(WorkerPolicy::getWebsitUserId,workerManagerBean.getId()).remove();


        for (WorkerPolicy workerPolicy : workerManagerBean.getWorkerPolicies()) {
            workerPolicy.setWorkerId(workerManagerBean.getUserId());
            workerPolicy.setWebsitUserId(workerManagerBean.getId());
            workerPolicy.setEndTime(this.getEndOfDay(workerPolicy.getEndTime()));
        }

        workerPolicyService.saveOrUpdateBatch(workerManagerBean.getWorkerPolicies());




        if (workerManagerBean.getExamineStatus().equals(ExamineWorkerStatusEnum.FAIL.getKey()))
            return;


        AdminWebsit adminWebsit = adminWebsitService.getById(workerManagerBean.getWebsitId());

        if (!CollectionUtils.isEmpty(workerManagerBean.getWorkerPolicies())) {

            for (WorkerPolicy workerPolicy : workerManagerBean.getWorkerPolicies()) {


                if (DateUtil.endOfDay(workerPolicy.getEndTime()).after(new Date()) && workerPolicy.getStartTime().before(new Date())) {
                    workerPolicy.setStatus("BZZ");
                } else {
                    workerPolicy.setStatus("DSX");
                }
                if (workerPolicy.getEndTime().before(new Date())) {
                    workerPolicy.setStatus("YSX");
                }
            }
        }

        //非自建需要判断齐全保险
        if (!adminWebsit.getAttr().equals(WebsitAttrEnum.SELF.getKey())) {

            List<WorkerPolicy> workerPolicies = workerManagerBean.getWorkerPolicies().stream().filter(item -> item.getPolicyType().equals("AC")).collect(Collectors.toList());

            if (CollectionUtils.isEmpty(workerPolicies))
                throw new RemoteServiceException("请填工程师意外险");


            if (workerPolicies.stream().filter(item -> item.getStatus().equals("BZZ")).count() < 1) {
                throw new RemoteServiceException("意外险必须有生效的保险");
            }

            Boolean wp = this.hasOverlap(workerPolicies);

            if (wp)
                throw new RemoteServiceException("意外险有相同覆盖范围内的保险");


            if (adminWebsit.getInsureType().equals("意外险,工伤险")) {

                if (workerManagerBean.getWorkerPolicies().stream()
                        .filter(item -> item.getPolicyType().equals("EM") && item.getStatus().equals("BZZ")).count() > 0) {
                    throw new RemoteServiceException("该网点未配置雇主保险");
                }


                List<WorkerPolicy> workerPoliciesIn = workerManagerBean.getWorkerPolicies().stream()
                        .filter(item -> item.getPolicyType().equals("IN")).collect(Collectors.toList());

                Boolean in = this.hasOverlap(workerPoliciesIn);

                if (in)
                    throw new RemoteServiceException("工伤险有相同覆盖范围内的保险");


                if (workerPoliciesIn.stream().filter(item -> item.getStatus().equals("BZZ")).count() > 0) {
                    throw new RemoteServiceException("工伤险必须有生效的保险");
                }

            } else {


                if (workerManagerBean.getWorkerPolicies().stream()
                        .filter(item -> item.getPolicyType().equals("IN") && item.getStatus().equals("BZZ")).count() > 0) {
                    throw new RemoteServiceException("该网点未配置工伤保险");
                }


                List<WorkerPolicy> workerPoliciesEm = workerManagerBean.getWorkerPolicies().stream()
                        .filter(item -> item.getPolicyType().equals("EM")).collect(Collectors.toList());

                Boolean em = this.hasOverlap(workerPoliciesEm);

                if (em)
                    throw new RemoteServiceException("雇主险有相同覆盖范围内的保险");


                if (workerPoliciesEm.stream().filter(item -> item.getStatus().equals("BZZ")).count() < 1) {
                    throw new RemoteServiceException("雇主险必须有生效的保险");
                }
            }
            workerManagerBean.setExamineStatus(ExamineWorkerStatusEnum.OK.getKey());
            workerManagerBean.getUser().setType("WORKER");

            websitUserService.lambdaUpdate()
                    .eq(WebsitUser::getUserId,workerManagerBean.getUserId())
                    .set(WebsitUser::getWorkerNumber,workerManagerBean.getWorkerNumber())
                    .update();

        }else {

            List<WorkerPolicy> workerPolicies = workerManagerBean.getWorkerPolicies().stream().filter(item -> item.getPolicyType().equals("AC")).collect(Collectors.toList());

            Boolean wp = this.hasOverlap(workerPolicies);

            if (wp)
                throw new RemoteServiceException("意外险有相同覆盖范围内的保险");

            if (workerPolicies.stream().filter(item -> item.getStatus().equals("BZZ")).count() < 1)
                workerManagerBean.setExamineStatus(ExamineWorkerStatusEnum.WAIT_WORKER.getKey());


            if (adminWebsit.getInsureType().equals("意外险,工伤险")) {
                List<WorkerPolicy> workerPoliciesIn = workerManagerBean.getWorkerPolicies().stream()
                        .filter(item -> item.getPolicyType().equals("IN")).collect(Collectors.toList());

                Boolean in = this.hasOverlap(workerPoliciesIn);

                if (in)
                    throw new RemoteServiceException("工伤险有相同覆盖范围内的保险");

                if (workerPoliciesIn.stream().filter(item -> item.getStatus().equals("BZZ") || item.getStatus().equals("DSX")).count() < 1) {
                    workerManagerBean.setExamineStatus(ExamineWorkerStatusEnum.WAIT_WORKER.getKey());
                    this.scGongShang(workerManagerBean);
                }

                if (workerManagerBean.getWorkerPolicies().stream().filter(item -> item.getStatus().equals("BZZ")).count() > 1) {
                    workerManagerBean.setExamineStatus(ExamineWorkerStatusEnum.OK.getKey());
                    workerManagerBean.getUser().setType("WORKER");

                    websitUserService.lambdaUpdate()
                            .eq(WebsitUser::getUserId,workerManagerBean.getUserId())
                            .set(WebsitUser::getWorkerNumber,workerManagerBean.getWorkerNumber())
                            .update();
                }



            } else {
                List<WorkerPolicy> workerPoliciesEm = workerManagerBean.getWorkerPolicies().stream()
                        .filter(item -> item.getPolicyType().equals("EM")).collect(Collectors.toList());

                Boolean em = this.hasOverlap(workerPoliciesEm);

                if (em)
                    throw new RemoteServiceException("雇主险有相同覆盖范围内的保险");

                if (workerPoliciesEm.stream().filter(item -> item.getStatus().equals("BZZ")).count() < 1) {
                    workerManagerBean.setExamineStatus(ExamineWorkerStatusEnum.WAIT_WORKER.getKey());
                    this.scGuZhu(workerManagerBean);
                }

                if (workerManagerBean.getWorkerPolicies().stream().filter(item -> item.getStatus().equals("BZZ")).count() > 1) {
                    workerManagerBean.setExamineStatus(ExamineWorkerStatusEnum.OK.getKey());
                    workerManagerBean.getUser().setType("WORKER");

                    websitUserService.lambdaUpdate()
                            .eq(WebsitUser::getUserId,workerManagerBean.getUserId())
                            .set(WebsitUser::getWorkerNumber,workerManagerBean.getWorkerNumber())
                            .update();
                }

            }


        }

        workerManagerBean.setExamineBy(adminUser.getNickName());
        workerManagerBean.setExamineTime(new Date());

        workerManagerBean.updateById();
        workerManagerBean.getUser().updateById();

        workerPolicyService.saveOrUpdateBatch(workerManagerBean.getWorkerPolicies());

    }

    private void scGuZhu(WorkerManagerBean workerManagerBean) {

        AdminUserCom adminUser = commonLogic.getAdminUser();

        //找有无可替换，有替换，无生成
        List<PolicyOrder> policyOrders = policyOrderService.lambdaQuery().eq(PolicyOrder::getWebsitId, workerManagerBean.getWebsitId())
                .eq(PolicyOrder::getPolicyOrderStatus, PolicyOrderEmStutasEnum.KTH.getKey()).list();

        if (!CollectionUtils.isEmpty(policyOrders)) {

            User user = userService.getById(workerManagerBean.getUserId());

            policyOrderService.lambdaUpdate()
                    .eq(PolicyOrder::getId,policyOrders.get(0).getId())
                    .set(PolicyOrder::getPolicyOrderStatus,PolicyOrderEmStutasEnum.YSX.getKey())
                    .set(PolicyOrder::getEndTime,new Date()).update();

            workerPolicyService.lambdaUpdate()
                    .eq(WorkerPolicy::getOrderId,policyOrders.get(0).getId())
                    .eq(WorkerPolicy::getWebsitUserId,workerManagerBean.getId())
                    .set(WorkerPolicy::getStatus, "YSX")
                    .set(WorkerPolicy::getEndTime,new Date()).update();

            PolicyOrder policyOrder = policyOrders.get(0);
            policyOrder.setId(IdWorker.getIdStr());
            policyOrder.setReplaceName(policyOrder.getWorkerName());
            policyOrder.setReplacePhone(policyOrder.getWorkerMobile());
            policyOrder.setReplaceNumber(policyOrder.getWorkerNumber());
            policyOrder.setReplaceIdcard(policyOrder.getWorkerIdcard());

            policyOrder.setWorkerIdcard(user.getIdCard());
            policyOrder.setWorkerMobile(user.getMobile());
            policyOrder.setWorkerName(workerManagerBean.getUser().getNickName());
            policyOrder.setWorkerNumber(workerManagerBean.getUser().getWorkerNumber());
            policyOrder.setWebsitUserId(workerManagerBean.getId());

            policyOrder.setPolicyOrderStatus(PolicyOrderEmStutasEnum.DTH.getKey());

            policyOrder.setIsSend(IsYesNoEnum.NO.getKey());
            policyOrder.setIsReceipt(IsYesNoEnum.NO.getKey());
            policyOrder.insert();



        }else {

            AdminWebsit adminWebsit = adminWebsitService.getById(workerManagerBean.getWebsitId());
            PolicyOrder policyOrder = new PolicyOrder();
            policyOrder.setBelongCompany(adminWebsit.getBelongCompany());
            policyOrder.setBelongCompanyCode(adminWebsit.getBelongCompanyCode());
            policyOrder.setPolicyOrderStatus(PolicyOrderEmStutasEnum.XG.getKey());
            policyOrder.setPolicyName("雇主险");
            policyOrder.setCompanyWechatId(adminWebsit.getCompanyWechatId());
            policyOrder.setCompanyWechatName(adminWebsit.getCompanyWechatName());
            policyOrder.setPolicyId(IdWorker.getIdStr());
            policyOrder.setId(policyOrder.getPolicyId());
            policyOrder.setWebsitId(adminWebsit.getWebsitId());
            policyOrder.setWebsitName(adminWebsit.getName());
            policyOrder.setWorkerNumber(workerManagerBean.getWorkerNumber());
            policyOrder.setWorkerName(workerManagerBean.getUser().getNickName());
            policyOrder.setWorkerIdcard(workerManagerBean.getUser().getIdCard());
            policyOrder.setWorkerMobile(workerManagerBean.getUser().getMobile());
            policyOrder.setWebsitUserId(workerManagerBean.getId());
            policyOrder.setType("EM");
            policyOrder.insert();
        }
    }

    private void scGongShang(WorkerManagerBean workerManagerBean) {


        AdminWebsit adminWebsit = adminWebsitService.getById(workerManagerBean.getWebsitId());
        SysDictCompany belongCompany = sysDictCompanyService.lambdaQuery()
                .eq(SysDictCompany::getCompanyWechatId, adminWebsit.getCompanyWechatId())
                .eq(SysDictCompany::getDictType, "INSURE_STEAD_UNIT")
                .eq(SysDictCompany::getDictCode, adminWebsit.getInsureSteadUnit())
                .one();


        PolicyOrder policyOrder = new PolicyOrder();
        policyOrder.setBelongCompany(adminWebsit.getBelongCompany());
        policyOrder.setBelongCompanyCode(adminWebsit.getBelongCompanyCode());
        policyOrder.setPolicyOrderStatus(PolicyOrderInStutasEnum.DGM.getKey());
        policyOrder.setPolicyName("工伤险");
        policyOrder.setCompanyWechatId(adminWebsit.getCompanyWechatId());
        policyOrder.setCompanyWechatName(adminWebsit.getCompanyWechatName());
        policyOrder.setPolicyId(IdWorker.getIdStr());
        policyOrder.setId(policyOrder.getPolicyId());
        policyOrder.setWebsitId(adminWebsit.getWebsitId());
        policyOrder.setWebsitName(adminWebsit.getName());
        policyOrder.setWorkerNumber(workerManagerBean.getWorkerNumber());
        policyOrder.setWorkerName(workerManagerBean.getUser().getNickName());
        policyOrder.setWorkerIdcard(workerManagerBean.getUser().getIdCard());
        policyOrder.setWorkerMobile(workerManagerBean.getUser().getMobile());
        policyOrder.setBuyUnitId(belongCompany.getDictCode());
        policyOrder.setBuyUnit(belongCompany.getDictValue());
        policyOrder.setCompany(belongCompany.getDictValue());

        policyOrder.setWebsitUserId(workerManagerBean.getId());
        policyOrder.setType("IN");
        policyOrder.insert();

    }

    public Boolean hasOverlap(List<WorkerPolicy> workerPolicies){

        for (int i= 0; i<workerPolicies.size();i++){
            WorkerPolicy workerPolicy = workerPolicies.get(i);
            for (int j = i+1; j <workerPolicies.size() ; j++) {
                WorkerPolicy workerPolicy2 = workerPolicies.get(j);
                if (workerPolicy.getEndTime().after(workerPolicy2.getStartTime()) && workerPolicy2.getEndTime().after(workerPolicy.getStartTime())){
                    return true;
                }
            }
        }

        return false;

    }


    @Transactional(rollbackFor = Exception.class)
    public void examine(WorkerManagerBean workerManagerBean) {
        AdminUserCom adminUser = commonLogic.getAdminUser();
        workerManagerBean.setPolicyExamineBy(adminUser.getNickName());
        workerManagerBean.setPolicyExamineTime(new Date());

        workerManagerBean.setPolicyExamineBy(adminUser.getNickName());
        workerManagerBean.setPolicyExamineTime(new Date());
        workerManagerBean.setBankAccount(workerManagerBean.getUser().getBankAccount());
        workerManagerBean.setWorkerNumber(workerManagerBean.getUser().getWorkerNumber());


        if (workerManagerBean.getUser().getEndTime() != null && workerManagerBean.getUser().getEndTime().before(new Date()))
            throw new RemoteServiceException("高空证不能填入失效时间");

        if (workerManagerBean.getUser().getIdCardEndTime() != null && workerManagerBean.getUser().getIdCardEndTime().before(new Date()))
            throw new RemoteServiceException("身份证不能填入过期时间");


        WebsitUser websitUser = websitUserService.getById(workerManagerBean.getId());

        if (!websitUser.getExamineStatus().equals(ExamineWorkerStatusEnum.POLICY_WAIT.getKey()))
            throw new RemoteServiceException("状态不为保险待审核状态");

        workerManagerBean.setCreateTime(null);
        workerManagerBean.updateById();


        workerManagerBean.getUser().setType("WORKER");
        workerManagerBean.getUser().updateById();

        workerImgService.lambdaUpdate().eq(WorkerImg::getWorkerId,workerManagerBean.getUserId())
                .remove();


        for (WorkerImg workerImg : workerManagerBean.getWorkerImgs()) {
            workerImg.setWorkerId(workerManagerBean.getUserId());
            workerImg.setUserId(workerManagerBean.getUserId());
        }


        workerImgService.saveOrUpdateBatch(workerManagerBean.getWorkerImgs());

        workerPolicyService.lambdaUpdate().eq(WorkerPolicy::getWebsitUserId,workerManagerBean.getId()).remove();


        for (WorkerPolicy workerPolicy : workerManagerBean.getWorkerPolicies()) {
            workerPolicy.setWorkerId(workerManagerBean.getUserId());
            workerPolicy.setWebsitUserId(workerManagerBean.getId());
            workerPolicy.setEndTime(this.getEndOfDay(workerPolicy.getEndTime()));
        }

        this.changeList(workerManagerBean.getWorkerPolicies(),workerManagerBean.getId());

        workerPolicyService.saveOrUpdateBatch(workerManagerBean.getWorkerPolicies());

        if (workerManagerBean.getExamineStatus().equals(ExamineWorkerStatusEnum.FAIL.getKey()))
            return;


        //检测保险情况 自建

        AdminWebsit adminWebsit = adminWebsitService.getById(workerManagerBean.getWebsitId());

        List<WorkerPolicy> workerPolicies = workerManagerBean.getWorkerPolicies().stream().filter(item -> item.getPolicyType()
                .equals("AC")).collect(Collectors.toList());

        if (CollectionUtils.isEmpty(workerPolicies))
            throw new RemoteServiceException("请填工程师意外险");

        for (WorkerPolicy workerPolicy : workerPolicies) {
            if (workerPolicy.getEndTime().after(new Date()) && workerPolicy.getStartTime().before(new Date())) {
                workerPolicy.setStatus("BZZ");
            }else {
                workerPolicy.setStatus("DSX");
            }
            if (workerPolicy.getEndTime().before(new Date())) {
                workerPolicy.setStatus("YSX");
            }
        }
        if (workerPolicies.stream().filter(item -> item.getStatus().equals("BZZ") ).count() < 1) {
            throw new RemoteServiceException("意外险必须有生效的保险");
        }

        PolicyOrder policyOrder = policyOrderService.lambdaQuery().eq(PolicyOrder::getWebsitUserId, websitUser.getId())
                .eq(PolicyOrder::getType, "AC")
                .isNull(PolicyOrder::getEndTime).last("limit 1").one();

        if (policyOrder !=null){
            Policy policy = policyService.getById(policyOrder.getPolicyId());
            for (int i= 0; i<workerPolicies.size();i++){

                WorkerPolicy workerPolicy2 = workerPolicies.get(i);
                if (policy.getEndTime().after(workerPolicy2.getStartTime()) && workerPolicy2.getEndTime().after(policy.getStartTime())){
                    throw new RemoteServiceException("意外险有已经购买相同覆盖范围内的保险");
                }

            }


        }


        Boolean wp = this.hasOverlap(workerPolicies);

        if (wp)
            throw new RemoteServiceException("意外险有相同覆盖范围内的保险");


        if (adminWebsit.getInsureType().equals("意外险,工伤险")) {

            if (workerManagerBean.getWorkerPolicies().stream()
                    .filter(item -> item.getPolicyType().equals("EM") && item.getStatus().equals("BZZ")).count() > 0) {
                throw new RemoteServiceException("该网点未配置雇主保险");
            }


            List<WorkerPolicy> workerPoliciesIn = workerManagerBean.getWorkerPolicies().stream()
                    .filter(item -> item.getPolicyType().equals("IN")).collect(Collectors.toList());

            Boolean in = this.hasOverlap(workerPoliciesIn);

            if (in)
                throw new RemoteServiceException("工伤险有相同覆盖范围内的保险");

            for (WorkerPolicy workerPolicy : workerPoliciesIn) {
                if (workerPolicy.getEndTime().after(new Date()) && workerPolicy.getStartTime().before(new Date())) {
                    workerPolicy.setStatus("BZZ");
                }else {
                    workerPolicy.setStatus("DSX");
                }
                if (workerPolicy.getEndTime().before(new Date())) {
                    workerPolicy.setStatus("YSX");
                }
            }

            if (workerPoliciesIn.stream().filter(item -> item.getStatus().equals("BZZ")).count() < 1) {
                throw new RemoteServiceException("工伤险必须有生效的保险");
            }

        } else {

            if (workerManagerBean.getWorkerPolicies().stream()
                    .filter(item -> item.getPolicyType().equals("IN") && item.getStatus().equals("BZZ")).count() > 0) {
                throw new RemoteServiceException("该网点未配置工伤保险");
            }
            List<WorkerPolicy> workerPoliciesEm = workerManagerBean.getWorkerPolicies().stream()
                    .filter(item -> item.getPolicyType().equals("EM")).collect(Collectors.toList());

            Boolean em = this.hasOverlap(workerPoliciesEm);

            if (em)
                throw new RemoteServiceException("雇主险有相同覆盖范围内的保险");


            for (WorkerPolicy workerPolicy : workerPoliciesEm) {
                if (workerPolicy.getEndTime().after(new Date()) && workerPolicy.getStartTime().before(new Date())) {
                    workerPolicy.setStatus("BZZ");
                }else {
                    workerPolicy.setStatus("DSX");
                }
                if (workerPolicy.getEndTime().before(new Date())) {
                    workerPolicy.setStatus("YSX");
                }
            }

            if (workerPoliciesEm.stream().filter(item -> item.getStatus().equals("BZZ")).count() < 1) {
                throw new RemoteServiceException("雇主险必须有生效的保险");
            }
        }


        workerPolicyService.saveOrUpdateBatch(workerManagerBean.getWorkerPolicies());

}

    public WorkerUserCount countWorker( ) {


        AdminUserCom adminUser = commonLogic.getAdminUser();
        List<WebsitUser> websitUsers = websitUserService.lambdaQuery()
                .in(!CollectionUtils.isEmpty(adminUser.getAdminWebsitIds())
                , WebsitUser::getWebsitId, adminUser.getAdminWebsitIds())
                .list();

        WorkerUserCount workerUserCount = new WorkerUserCount();
        workerUserCount.setRzsp(websitUsers.stream().filter(item -> item.getExamineStatus().equals(ExamineWorkerStatusEnum.WAIT.getKey())).count());
        workerUserCount.setDsfgm(websitUsers.stream().filter(item -> item.getExamineStatus().equals(ExamineWorkerStatusEnum.WAIT_WORKER.getKey())).count());
        workerUserCount.setBxsp(websitUsers.stream().filter(item -> item.getExamineStatus().equals(ExamineWorkerStatusEnum.POLICY_WAIT.getKey())).count());
        workerUserCount.setZtzc(websitUsers.stream().filter(item -> item.getExamineStatus().equals(ExamineWorkerStatusEnum.OK.getKey())).count());
        workerUserCount.setYbh(websitUsers.stream().filter(item -> item.getExamineStatus().equals(ExamineWorkerStatusEnum.FAIL.getKey())).count());

        workerUserCount.setZjkgq(websitUsers.stream().filter(item -> item.getIsOverdue().equals(IsYesNoEnum.YES.getKey())).count());

        workerUserCount.setZjygq(websitUsers.stream().filter(item -> item.getExamineStatus().equals(ExamineWorkerStatusEnum.OVERDUE.getKey())).count());
        workerUserCount.setYzt(websitUsers.stream().filter(item -> item.getExamineStatus().equals(ExamineWorkerStatusEnum.STOP.getKey())).count());
        workerUserCount.setYlz(websitUsers.stream().filter(item -> item.getExamineStatus().equals(ExamineWorkerStatusEnum.QUIT.getKey())).count());
        return workerUserCount;


    }

    /**
     * 获取某天最小时间
     * @param date 时间
     * @return 获取某天最小时间
     */
    public  Date getEndOfDay(Date date) {
        LocalDateTime localDateTime = LocalDateTime.ofInstant(Instant.ofEpochMilli(date.getTime()), ZoneId.systemDefault());;
        LocalTime localTime = LocalTime.of(23, 59, 59);
        LocalDateTime endOfDay = localDateTime.with(localTime);
        return Date.from(endOfDay.atZone(ZoneId.systemDefault()).toInstant());
    }

    public IPage<WorkerNumberCheckVO> workerManagerCheck(WorkerParamBean zfireParamBean) {

        FieldUtils.supplyParam(zfireParamBean, WorkerNumberCheckVO.class, commonLogic.getAdminUser());
        zfireParamBean.setAdminWebsitIds(zfireParamBean.getAdminWebsitIds());

        IPage<WorkerNumberCheckVO> page = commonMapper.workerManagerCheck(new Page(zfireParamBean.getPageNum(), zfireParamBean.getPageSize(),false),
                zfireParamBean);
        Integer count = commonMapper.workerManagerCheckCount(zfireParamBean);
        page.setTotal(count);
        return page;

    }

    public void importData(List<Object> datas) {
        AdminUserCom adminUser = commonLogic.getAdminUser();
        int index = 0;
        List<WorkerNumberCheck> workerNumberChecks =new ArrayList<>();
        for (Object o : datas) {
            index++;
            String errPrefix = "第" + index + "行";
            List<Object> row = (List<Object>) o;


            WorkerNumberCheck workerNumberCheck = new WorkerNumberCheck();

            workerNumberCheck.setCompanyWechatId(adminUser.getCompanyWechatId());
            workerNumberCheck.setCompanyWechatName(adminUser.getCompanyName());
            workerNumberCheck.setWebsitId((String)row.get(0));
            workerNumberCheck.setWebsitName((String)row.get(1));
            workerNumberCheck.setWorkerNumberYun((String)row.get(2));
            workerNumberCheck.setWorkerName((String)row.get(3));
            workerNumberCheck.setWorkerPhoneYun((String)row.get(4));

            WorkerNumberCheck workerNumberCheckUp = workerNumberCheckService.lambdaQuery().eq(WorkerNumberCheck::getWorkerNumberYun, workerNumberCheck.getWorkerNumberYun())
                    .last("limit 1").one();

            if (workerNumberCheckUp != null){
                workerNumberCheck.setId(workerNumberCheckUp.getId());
            }

            workerNumberChecks.add(workerNumberCheck);


        }

        workerNumberCheckService.saveOrUpdateBatch(workerNumberChecks);
    }
}
