package com.mosty.qwzx.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.mosty.base.model.entity.bkzx.TbBkRy;
import com.mosty.base.model.entity.qwzx.TbQwBmjlbb;
import com.mosty.base.model.entity.qwzx.TbQwBmjlbbJlmx;
import com.mosty.base.model.query.qwzx.TbQwQxjMyQuery;
import com.mosty.base.model.vo.base.DeptInfoVo;
import com.mosty.base.utils.DateUtils;
import com.mosty.base.utils.Kit;
import com.mosty.base.utils.UUIDGenerator;
import com.mosty.common.base.exception.BusinessException;
import com.mosty.common.token.UserInfo;
import com.mosty.common.token.UserInfoManager;
import com.mosty.common.util.PermissionsUtil;
import com.mosty.base.model.dto.qwzx.TbQwQxjEditDto;
import com.mosty.base.model.entity.qwzx.TbQwQxj;
import com.mosty.base.model.query.qwzx.TbQwQxjQuery;
import com.mosty.qwzx.mapper.TbQwBmjlbbJlmxMapper;
import com.mosty.qwzx.mapper.TbQwBmjlbbMapper;
import com.mosty.qwzx.mapper.TbQwQxjMapper;
import com.mosty.qwzx.remote.TbBaseAdaptRemoteService;
import com.mosty.qwzx.service.TbQwQxjService;
import lombok.AllArgsConstructor;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

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

/**
 * @author zengbo
 * @since 2022-06-27
 */
@AllArgsConstructor
@Service
public class TbQwQxjServiceImpl implements TbQwQxjService {

    private final TbQwQxjMapper tbQwQxjMapper;
    private final TbQwBmjlbbJlmxMapper tbQwBmjlbbJlmxMapper;
    private final TbQwBmjlbbMapper tbQwBmjlbbMapper;
    private final TbBaseAdaptRemoteService tbBaseAdaptRemoteService;

    @Override
    @Transactional
    public int addQxj(TbQwQxj qxj) {
        if (StringUtils.isBlank(qxj.getSqbmdm())) throw new BusinessException("请选择申请人部门！");
        DeptInfoVo dept = this.tbBaseAdaptRemoteService.getOrgByOrgcode(qxj.getSqbmdm());
//        if (dept != null) {
//            qxj.setSsbmid(dept.getDeptid());
//            qxj.setSqbmdm(dept.getDeptcode());
//            qxj.setSqbm(dept.getDeptname());
//        }
        // 查询该人员同时段是否有请修改数据
        List<TbQwQxj> list = this.tbQwQxjMapper.selectList(
                new LambdaQueryWrapper<TbQwQxj>()
                        .eq(TbQwQxj::getSqrId, qxj.getSqrId())
                        .eq(TbQwQxj::getXtScbz, "0")
                        .eq(TbQwQxj::getXtSjzt, "1")
                        .and(
                                t -> t.between(TbQwQxj::getKssj, qxj.getKssj(), qxj.getJssj()).or()
                                        .between(TbQwQxj::getJssj, qxj.getKssj(), qxj.getJssj())
                        )
        );
        if (list.size() > 0) {
            throw new BusinessException("该人员同时段有请休假数据，添加失败！");
        }
        qxj.setId(UUIDGenerator.getUUID());
        qxj.setXtSjly("1");
        int time = (int) ((qxj.getJssj().getTime() - qxj.getKssj().getTime()) / 24 / 60 / 60 / 1000) + 1;
        qxj.setQjsc(time);
        if (dept != null) {
            qxj.setSsbm(dept.getDeptname());
            qxj.setSsbmid(dept.getDeptid());
            qxj.setSsbmdm(dept.getDeptcode());
            qxj.setSsxgajdm(dept.getFxjcode());
            qxj.setSsxgajid(dept.getFxjid());
            qxj.setSsxgaj(dept.getFxjname());
            qxj.setSssgaj(dept.getDszname());
            qxj.setSssgajdm(dept.getDszcode());
            qxj.setSssgajid(dept.getDszid());
        }
        this.setBmjlbb(qxj);
        return tbQwQxjMapper.insert(qxj);
    }

    private void setBmjlbb(TbQwQxj qxj) {
        // 更新部门警力报备数据
        Date now = DateUtils.strToDate(DateUtils.getQueryDateString(new Date(), "01"), "01");
        if (now.getTime() >= qxj.getKssj().getTime() && now.getTime() <= qxj.getJssj().getTime()) {
            TbQwBmjlbbJlmx jlmx = this.tbQwBmjlbbJlmxMapper.selectOne(
                    new LambdaQueryWrapper<TbQwBmjlbbJlmx>()
                            .eq(TbQwBmjlbbJlmx::getJlId, qxj.getSqrId())
                            .eq(TbQwBmjlbbJlmx::getBbrq, DateUtils.getQueryDateString(now, "01"))
                            .eq(TbQwBmjlbbJlmx::getJllx, qxj.getSqrlx())
            );
            if (jlmx != null) {
                jlmx.setJlzt("0");
                jlmx.setBblx("01".equals(qxj.getSqrlx()) ? "4" : "5");
                this.tbQwBmjlbbJlmxMapper.updateById(jlmx);
            }
            DeptInfoVo dept = this.tbBaseAdaptRemoteService.getOrgByOrgcode(qxj.getSsbmdm());
            List<TbQwBmjlbb> bbList = this.tbQwBmjlbbMapper.selectList(
                    new LambdaQueryWrapper<TbQwBmjlbb>()
                            .eq(TbQwBmjlbb::getBbrq, DateUtils.getQueryDateString(now, "01"))
                            .and(
                                    it -> it.eq(TbQwBmjlbb::getSsbmdm, dept.getDeptcode()).or()
                                            .eq(TbQwBmjlbb::getSsbmdm, dept.getFxjcode()).or()
                                            .eq(TbQwBmjlbb::getSsbmdm, dept.getDszcode())
                            )
            );
            bbList.forEach(item -> {
                if ("01".equals(qxj.getSqrlx())) {
                    // 删除在岗民警
                    item.setZgmjsl(item.getZgmjsl() - 1);
                    List<String> zgmjList = JSON.parseArray(item.getZgmj()).toJavaList(String.class);
                    zgmjList.remove(qxj.getSqrId());
                    item.setZgmj(JSON.toJSONString(zgmjList));
                    // 添加不在岗民警
                    List<String> bzgmjList = JSON.parseArray(item.getBzgmj()).toJavaList(String.class);
                    bzgmjList.add(qxj.getSqrId());
                    item.setBzgmj(JSON.toJSONString(bzgmjList));
                } else {
                    // 删除在岗辅警
                    item.setZgfjsl(item.getZgfjsl() - 1);
                    List<String> zgfjList = JSON.parseArray(item.getZgfj()).toJavaList(String.class);
                    zgfjList.remove(qxj.getSqrId());
                    item.setZgfj(JSON.toJSONString(zgfjList));
                    // 添加在岗辅警
                    List<String> bzgfjList = JSON.parseArray(item.getBzgfj()).toJavaList(String.class);
                    bzgfjList.add(qxj.getSqrId());
                    item.setBzgfj(JSON.toJSONString(bzgfjList));
                }
                this.tbQwBmjlbbMapper.updateById(item);
            });
        }
    }

    @Override
    public IPage<TbQwQxj> getQxj(TbQwQxjQuery qxj, IPage<TbQwQxj> page) {
        QueryWrapper<TbQwQxj> queryWrapper = new QueryWrapper<>();
//        UserInfo userInfo = UserInfoManager.get();
//        PermissionsUtil.queryWrapperUtil(queryWrapper, userInfo);
        qxj.setSsbmdm(this.tbBaseAdaptRemoteService.getSsbm(qxj.getSsbmdm(), null));
        if (qxj != null) {
            queryWrapper.lambda().eq(StringUtils.isNotBlank(qxj.getSqrlx()), TbQwQxj::getSqrlx, qxj.getSqrlx())
                    .eq(StringUtils.isNotBlank(qxj.getSqbmdm()), TbQwQxj::getSqbmdm, qxj.getSqbmdm())
                    .eq(StringUtils.isNotBlank(qxj.getSqbmid()), TbQwQxj::getSqbmid, qxj.getSqbmid())
                    .likeRight(StringUtils.isNotBlank(qxj.getSsbmdm()), TbQwQxj::getSsbmdm, qxj.getSsbmdm())
                    .eq(StringUtils.isNotBlank(qxj.getQjlx()), TbQwQxj::getQjlx, qxj.getQjlx())
                    .like(StringUtils.isNotBlank(qxj.getSqrXm()), TbQwQxj::getSqrXm, qxj.getSqrXm())
                    .like(StringUtils.isNotBlank(qxj.getLxdh()), TbQwQxj::getLxdh, qxj.getLxdh())
                    .orderByDesc(TbQwQxj::getXtCjsj);
            if (qxj.getKssj() != null) {
                queryWrapper.lambda().le(TbQwQxj::getKssj, qxj.getKssj());
            }
            if (qxj.getJssj() != null) {
                queryWrapper.lambda().ge(TbQwQxj::getJssj, qxj.getJssj());
            }
        }
        return tbQwQxjMapper.selectPage(page, queryWrapper);
    }

    @Override
    @Transactional
    public int editQxj(TbQwQxjEditDto qxj) {
        if (StringUtils.isBlank(qxj.getSqbmdm())) throw new BusinessException("请选择申请人部门！");
        // 暂时规定，时间开始不能删除和修改
        Date now = DateUtils.strToDate(DateUtils.getQueryDateString(new Date(), "01"), "01");
        if (now.getTime() >= qxj.getKssj().getTime() && now.getTime() <= qxj.getJssj().getTime()) {
            throw new BusinessException("请假设置时间已到，不能修改数据");
        }
        // 查询该人员同时段是否有请修改数据
        List<TbQwQxj> list = this.tbQwQxjMapper.selectList(
                new LambdaQueryWrapper<TbQwQxj>()
                        .eq(TbQwQxj::getSqrId, qxj.getSqrId())
                        .eq(TbQwQxj::getXtSjzt, "1")
                        .ne(TbQwQxj::getId, qxj.getId())
                        .and(
                                t -> t.between(TbQwQxj::getKssj, qxj.getKssj(), qxj.getJssj()).or()
                                        .between(TbQwQxj::getJssj, qxj.getKssj(), qxj.getJssj())
                        )
        );
        if (list.size() > 0) {
            throw new BusinessException("该人员同时段有请休假数据，添加失败！");
        }
        int time = (int) ((qxj.getJssj().getTime() - qxj.getKssj().getTime()) / 24 / 60 / 60 / 1000) + 1;
        qxj.setQjsc(time);
        TbQwQxj item = new TbQwQxj();
        BeanUtils.copyProperties(qxj, item);
        // 清除之前的人的数据
        this.deleteOldBmjlbb(qxj.getId());
        // 添加新的数据
        this.setBmjlbb(item);
        DeptInfoVo dept = this.tbBaseAdaptRemoteService.getOrgByOrgcode(item.getSqbmdm());
        if (dept != null) {
            qxj.setSsbm(dept.getDeptname());
            qxj.setSsbmid(dept.getDeptid());
            qxj.setSsbmdm(dept.getDeptcode());
            qxj.setSsxgajdm(dept.getFxjcode());
            qxj.setSsxgajid(dept.getFxjid());
            qxj.setSsxgaj(dept.getFxjname());
            qxj.setSssgaj(dept.getDszname());
            qxj.setSssgajdm(dept.getDszcode());
            qxj.setSssgajid(dept.getDszid());
        }
        return tbQwQxjMapper.updateById(item);
    }

    private void deleteOldBmjlbb(String id) {
        TbQwQxj qxj = this.tbQwQxjMapper.selectById(id);
        Date now = DateUtils.strToDate(DateUtils.getQueryDateString(new Date(), "01"), "01");
        if (now.getTime() >= qxj.getKssj().getTime() && now.getTime() <= qxj.getJssj().getTime()) {
            TbQwBmjlbbJlmx jlmx = this.tbQwBmjlbbJlmxMapper.selectOne(
                    new LambdaQueryWrapper<TbQwBmjlbbJlmx>()
                            .eq(TbQwBmjlbbJlmx::getJlId, qxj.getSqrId())
                            .eq(TbQwBmjlbbJlmx::getBbrq, DateUtils.getQueryDateString(now, "01"))
                            .eq(TbQwBmjlbbJlmx::getJllx, qxj.getSqrlx())
            );
            if (jlmx != null) {
                jlmx.setJlzt("1");
                jlmx.setBblx("01".equals(qxj.getSqrlx()) ? "1" : "2");
                this.tbQwBmjlbbJlmxMapper.updateById(jlmx);
            }
            DeptInfoVo dept = this.tbBaseAdaptRemoteService.getOrgByOrgcode(qxj.getSqbmdm());
            List<TbQwBmjlbb> bbList = this.tbQwBmjlbbMapper.selectList(
                    new LambdaQueryWrapper<TbQwBmjlbb>()
                            .eq(TbQwBmjlbb::getBbrq, DateUtils.getQueryDateString(now, "01"))
                            .and(it -> it.eq(TbQwBmjlbb::getSsbmdm, dept.getDeptcode()).or()
                                    .eq(TbQwBmjlbb::getSsbmdm, dept.getFxjcode()).or()
                                    .eq(TbQwBmjlbb::getSsbmdm, dept.getDszcode())
                            )
            );
            bbList.forEach(item -> {
                if ("01".equals(qxj.getSqrlx())) {
                    // 添加在岗民警
                    item.setZgmjsl(item.getZgmjsl() + 1);
                    List<String> zgmjList = JSON.parseArray(item.getZgmj()).toJavaList(String.class);
                    zgmjList.add(qxj.getSqrId());
                    item.setZgmj(JSON.toJSONString(zgmjList));
                    // 删除不在岗民警
                    List<String> bzgmjList = JSON.parseArray(item.getBzgmj()).toJavaList(String.class);
                    bzgmjList.remove(qxj.getSqrId());
                    item.setBzgmj(JSON.toJSONString(bzgmjList));
                } else {
                    // 删除在岗辅警
                    item.setZgfjsl(item.getZgfjsl() + 1);
                    List<String> zgfjList = JSON.parseArray(item.getZgfj()).toJavaList(String.class);
                    zgfjList.add(qxj.getSqrId());
                    item.setZgfj(JSON.toJSONString(zgfjList));
                    // 添加在岗辅警
                    List<String> bzgfjList = JSON.parseArray(item.getBzgfj()).toJavaList(String.class);
                    bzgfjList.remove(qxj.getSqrId());
                    item.setBzgfj(JSON.toJSONString(bzgfjList));
                }
                this.tbQwBmjlbbMapper.updateById(item);
            });
        }
    }

    @Override
    @Transactional
    public boolean deleteBatch(List<String> ids) {
        List<TbQwQxj> list = this.tbQwQxjMapper.selectList(
                new LambdaQueryWrapper<TbQwQxj>()
                        .in(TbQwQxj::getId, ids)
        );
        list.forEach(item -> {
            Date now = DateUtils.strToDate(DateUtils.getQueryDateString(new Date(), "01"), "01");
            if (now.getTime() >= item.getKssj().getTime() && now.getTime() <= item.getJssj().getTime()) {
                throw new BusinessException("请假设置时间已到，不能删除数据");
            }
            // 清除之前的人的数据
            this.deleteOldBmjlbb(item.getId());
        });
        if (ids.size() > 0) {
            int rs = tbQwQxjMapper.deleteQxj(ids);
            return rs > 0;
        }
        return true;
    }

    @Override
    public boolean deleteById(String id) {
        TbQwQxj qxj = this.tbQwQxjMapper.selectById(id);
        Date now = DateUtils.strToDate(DateUtils.getQueryDateString(new Date(), "01"), "01");
        if (now.getTime() >= qxj.getKssj().getTime() && now.getTime() <= qxj.getJssj().getTime()) {
            throw new BusinessException("请假设置时间已到，不能删除数据");
        }
        this.deleteOldBmjlbb(id);
        List<String> ids = new ArrayList<>();
        ids.add(id);
        return tbQwQxjMapper.deleteQxj(ids) > 0;
    }

    @Override
    public TbQwQxj selectById(String id) {
        return tbQwQxjMapper.selectById(id);
    }

    @Override
    public IPage<TbQwQxj> getMyQxjList(TbQwQxjMyQuery dto) {
        UserInfo user = UserInfoManager.get();
        return this.tbQwQxjMapper.selectPage(
                new Page<>(dto.getPageCurrent(), dto.getPageSize()),
                new LambdaQueryWrapper<TbQwQxj>()
                        .eq(TbQwQxj::getSqrId, String.valueOf(user.getUserId()))
                        .eq(StringUtils.isNotBlank(dto.getQjlx()), TbQwQxj::getQjlx, dto.getQjlx())
                        .and(dto.getKssj() != null && dto.getJssj() != null,
                                t -> t.between(TbQwQxj::getKssj, dto.getKssj(), dto.getJssj()).or()
                                        .between(TbQwQxj::getJssj, dto.getKssj(), dto.getJssj())
                        )
                        .orderByDesc(TbQwQxj::getXtCjsj)
        );
    }
}
