package com.zd.smartlock.service.impl;

import com.zd.common.core.constant.SecurityConstants;
import com.zd.common.core.domain.R;
import com.zd.common.core.exception.ServiceException;
import com.zd.common.security.service.TokenService;
import com.zd.smartlock.domain.SlApplyApproval;
import com.zd.smartlock.domain.SlOpendoorApply;
import com.zd.smartlock.domain.api.SlUser;
import com.zd.smartlock.domain.vo.SlSubjectRelationVo;
import com.zd.smartlock.mapper.SlApplyApprovalMapper;
import com.zd.smartlock.mapper.SlOpendoorApplyMapper;
import com.zd.smartlock.mapper.SlSubjectRelationMapper;
import com.zd.smartlock.service.ISlApplyApprovalService;
import com.zd.smartlock.utils.SmartlockUtil;
import com.zd.system.api.RemoteUserService;
import com.zd.system.api.chemical.RemoteStockService;
import com.zd.system.api.domain.SysUser;
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.*;

/**
 * 人员关联Service业务层处理
 *
 * @author zd
 * @date 2022-09-02
 */
@Slf4j
@Service
public class SlApplyApprovalServiceImpl implements ISlApplyApprovalService
{

    @Autowired
    private TokenService tokenService;

    @Autowired
    private SlApplyApprovalMapper slApplyApprovalMapper;

    @Autowired
    private SlOpendoorApplyMapper slOpendoorApplyMapper;

    @Autowired
    private SlSubjectRelationMapper slSubjectRelationMapper;

    @Autowired
    private RemoteStockService remoteStockService;

    @Autowired
    private RemoteUserService remoteUserService;


    /**
     * 查询申请审核
     *
     * @param id 申请审核主键
     * @return 申请审核
     */
    @Override
    public SlApplyApproval selectSlApplyApprovalById(Long id)
    {
        return slApplyApprovalMapper.selectSlApplyApprovalById(id);
    }

    /**
     * 查询申请审核列表
     *
     * @param slApplyApproval 申请审核
     * @return 申请审核
     */
    @Override
    public List<SlApplyApproval> selectSlApplyApprovalList(SlApplyApproval slApplyApproval)
    {
        return slApplyApprovalMapper.selectSlApplyApprovalList(slApplyApproval);
    }

    @Override
    public List<SlApplyApproval> getListByIds(List<Long> ids){
        if (ids.isEmpty()){
            new ArrayList<>();
        }
        return slApplyApprovalMapper.getListByIds(ids);
    }

    /**
     * 新增申请审核-需求变更废弃 2022-09-27
     *
     * @param slApplyApproval 申请审核
     * @return 结果
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public int insertSlApplyApproval(SlApplyApproval slApplyApproval)
    {
        int flg=0;
        try {
            SysUser sysUser = tokenService.getLoginUser().getSysUser();
            //部门id
            slApplyApproval.setDeptId(sysUser.getDept().getDeptId());
            //部门名称
            slApplyApproval.setDeptName(sysUser.getDept().getDeptName());
            //审核人id
            slApplyApproval.setApprovaId(sysUser.getUserId());
            //审核人姓名
            slApplyApproval.setApprovaName(sysUser.getNickName());
            //审核时间
            slApplyApproval.setCretaTime(new Date());

            //查询申请记录
            SlOpendoorApply opendoorApply = slOpendoorApplyMapper.selectSlOpendoorApplyById(slApplyApproval.getApplyId());

            if(opendoorApply.getApplyStatus()==3){
                throw new ServiceException("该记录已驳回，无需审核！");
            }
            if(opendoorApply.getApplyNumber()==2){
                throw new ServiceException("该记录已有两次审核，无需再次审核！");
            }
            //通过
            if(slApplyApproval.getApprovaStatus()==1){
                opendoorApply.setApplyNumber(opendoorApply.getApplyNumber()+1);
                //审核通过，下发密码(第二次，审核通过的情况下)
                if(opendoorApply.getApplyNumber()==2){
                    //判断是否同一个人连续审核
                    SlApplyApproval approval = new SlApplyApproval();
                    approval.setApplyId(slApplyApproval.getApplyId());
                    approval.setApprovaId(sysUser.getUserId());
                    List<SlApplyApproval> applyVoList = slApplyApprovalMapper.selectSlApplyApprovalList(approval);
                    if(applyVoList.size()>0){
                        throw new ServiceException("您已审核过该条申请，无需重复审核！");
                    }
                    //审核通过，刷新审核状态
                    opendoorApply.setApplyStatus(2L);
                    //审核通过后，添加人员并且授权、短信发送
                    String str =  authPower(opendoorApply.getId());
                    if(!"ok".equals(str)){
                        log.info("人员授权以及短信发送结果："+str);
                        throw new ServiceException(str);
                    }
                }
            }else if(slApplyApproval.getApprovaStatus()==2){
                //驳回
                opendoorApply.setApplyNumber(opendoorApply.getApplyNumber()+1);
                //修改申请表状态
                opendoorApply.setApplyStatus(3L);

                //申请人1短信发送通知
               R r1= remoteStockService.sendSydSms("【实验室安全系统】"+opendoorApply.getSubjectName()+"-门禁远程授权申请已拒绝，请联系实验室管理人员。",3,opendoorApply.getId(),opendoorApply.getPhonenumber());
               log.info("开门申请拒绝，人员1短信通知结果："+r1);
                //申请人2短信发送通知
               R r2= remoteStockService.sendSydSms("【实验室安全系统】"+opendoorApply.getSubjectName()+"-门禁远程授权申请已拒绝，请联系实验室管理人员。",3,opendoorApply.getId(),opendoorApply.getPhonenumber2());
                log.info("开门申请拒绝，人员2短信通知结果："+r2);
            }
            //申请表操作
            opendoorApply.setApprovalTime(new Date());
            opendoorApply.setApprovalUser(sysUser.getNickName());

            slOpendoorApplyMapper.updateSlOpendoorApply(opendoorApply);
            flg= slApplyApprovalMapper.insertSlApplyApproval(slApplyApproval);
        }catch (Exception e){
            log.info("申请审核异常"+e);
        }
        return flg;
    }

    /**
     * 修改申请审核
     *
     * @param slApplyApproval 申请审核
     * @return 结果
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public int updateSlApplyApproval(SlApplyApproval slApplyApproval)
    {
        return slApplyApprovalMapper.updateSlApplyApproval(slApplyApproval);
    }

    /**
     * 批量删除申请审核
     *
     * @param ids 需要删除的申请审核主键
     * @return 结果
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public int deleteSlApplyApprovalByIds(Long[] ids)
    {
        return slApplyApprovalMapper.deleteSlApplyApprovalByIds(ids);
    }

    /**
     * 删除申请审核信息
     *
     * @param id 申请审核主键
     * @return 结果
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public int deleteSlApplyApprovalById(Long id)
    {
        return slApplyApprovalMapper.deleteSlApplyApprovalById(id);
    }

    /***
     * 短信审核 需求变更，废弃2022-09-27
     * @param phone 回复人电话
     * @param content 回复内容
     * @param lockApplyId 申请id
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Map<String,Object> sysMsgApprova(String phone, String content, Long lockApplyId) {
        Map<String,Object> map = new HashMap<>();
        try {
            //审核状态 1通过 2驳回
            Long approvalStatus=1L ;
            SysUser sysUser =  remoteUserService.getUserByPhone(phone).getData();
            if(sysUser==null){
                map.put("msg","未查询到相关人信息");
                map.put("status","error");
                return map;
            }

            //查询申请记录
            SlOpendoorApply opendoorApply = slOpendoorApplyMapper.selectSlOpendoorApplyById(lockApplyId);

            if(opendoorApply.getApplyStatus()==3){
                map.put("msg","该记录已驳回，无需审核！");
                map.put("status","error");
                return map;
            }
            if(opendoorApply.getApplyNumber()==2){
                map.put("msg","该记录已有两次审核，无需再次审核！");
                map.put("status","error");
                return map;
            }
            //通过
            if( "1".equals(content)){
                opendoorApply.setApplyNumber(opendoorApply.getApplyNumber()+1);
                //审核通过，下发密码(第二次，审核通过的情况下)
                if(opendoorApply.getApplyNumber()==2){
                    //判断是否同一个人连续审核
                    SlApplyApproval approval = new SlApplyApproval();
                    approval.setApplyId(lockApplyId);
                    approval.setApprovaId(sysUser.getUserId());
                    List<SlApplyApproval> applyVoList = slApplyApprovalMapper.selectSlApplyApprovalList(approval);
                    if(applyVoList.size()>0){
                        map.put("msg","您已审核过该条申请，无需重复审核！");
                        map.put("status","error");
                        return map;
                    }
                    //审核通过，刷新审核状态
                    opendoorApply.setApplyStatus(2L);

                    //审核通过后，添加人员并且授权、短信发送
                    String str =  authPower(opendoorApply.getId());
                    if(!"ok".equals(str)){
                        map.put("msg",str);
                        map.put("status","error");
                        return map;
                    }
                }
            }else if( "0".equals(content)){
                approvalStatus=2L;
                //驳回
                opendoorApply.setApplyNumber(opendoorApply.getApplyNumber()+1);
                //修改申请表状态
                opendoorApply.setApplyStatus(3L);

                //申请人1短信发送通知
                R r1= remoteStockService.sendSydSms("【实验室安全系统】"+opendoorApply.getSubjectName()+"-门禁远程授权申请已拒绝，请联系实验室管理人员。",3,opendoorApply.getId(),opendoorApply.getPhonenumber());
                log.info("短信开门申请拒绝，人员1短信通知结果："+r1);
                //申请人2短信发送通知
                R r2= remoteStockService.sendSydSms("【实验室安全系统】"+opendoorApply.getSubjectName()+"-门禁远程授权申请已拒绝，请联系实验室管理人员。",3,opendoorApply.getId(),opendoorApply.getPhonenumber2());
                log.info("短信开门申请拒绝，人员2短信通知结果："+r2);
            }
            //申请表操作
            opendoorApply.setApprovalTime(new Date());
            opendoorApply.setApprovalUser(sysUser.getNickName());

            slOpendoorApplyMapper.updateSlOpendoorApply(opendoorApply);
            SlApplyApproval approval = new SlApplyApproval();
            approval.setApplyId(lockApplyId);
            approval.setApprovaId(sysUser.getUserId());
            approval.setDeptId(sysUser.getDept().getDeptId());
            approval.setDeptName(sysUser.getDept().getDeptName());
            approval.setApprovaId(sysUser.getUserId());
            approval.setApprovaName(sysUser.getNickName());
            approval.setApprovaStatus(approvalStatus);
            approval.setCretaTime(new Date());
            slApplyApprovalMapper.insertSlApplyApproval(approval);
        }catch (Exception e){
            log.info("短信审核处理异常："+e);
            map.put("msg",e);
            map.put("status","error");
            return map;
        }
        map.put("msg","成功");
        map.put("status","ok");
        return map;
    }

    /***
     * 审批通过后人员密码授权处理- 需求变更，废弃2022-09-27
     * @param applyId 申请id
     */
    public String authPower(Long applyId) throws Exception {
        log.info("========开始门锁授权===========");
        //人员1 授权结果
        Boolean auths1=false;
        //人员2授权结果
        Boolean auths2=false;
        //返回值
        String strMsg="ok";
        try {
            //查询申请记录
            SlOpendoorApply opendoorApply = slOpendoorApplyMapper.selectSlOpendoorApplyById(applyId);

            SlSubjectRelationVo subjectRelation = new SlSubjectRelationVo();
            subjectRelation.setSubjectId(opendoorApply.getSubjectId());
            List<SlSubjectRelationVo>  listsubRla = slSubjectRelationMapper.selectSlSubjectRelationList(subjectRelation);
            if(listsubRla.size()!=2){
                strMsg="该实验室暂未绑定双锁！";
            }

            Map<String,Object> detalisMap = new HashMap<>();
            SlUser user = new SlUser();
            //学号、工号
            user.setPersoncode(opendoorApply.getUserCode());
            //姓名
            user.setPersonname(opendoorApply.getUserName());
            //性别 （0=女，1=男）
            user.setPersonsex(opendoorApply.getUserSex()==null?1+"":0+"");
            //人员类别（1=学生，2=教职工，3=临时人员）
            user.setPersontype("1");
            //电话
            user.setPersonmobile(opendoorApply.getPhonenumber());
            log.info("=======人员1授权开始========");
            Map<String,Object> map1= SmartlockUtil.addUser(user,listsubRla.get(0).getLockRoomId());

            if(!SmartlockUtil.resultMsg.equals(map1.get("resultMsg").toString())){
                log.info("人员："+opendoorApply.getUserName()+"，授权失败，原因："+map1.get("resultMsg")+"，请联系管理员");
                strMsg="人员："+opendoorApply.getUserName()+"，授权失败，原因："+map1.get("resultMsg")+"，请联系管理员";
                return strMsg;
            }else {
                log.info("=======人员1授权成功========");
                auths1=true;
            }


            //人员1 备注详情
            detalisMap.put("人员1",opendoorApply.getUserName());
            detalisMap.put("锁编1号",listsubRla.get(0).getLockCode());
            detalisMap.put("人员1密码",map1.get("password"));

            //学号、工号
            user.setPersoncode(opendoorApply.getUserCode2());
            //姓名
            user.setPersonname(opendoorApply.getUserName2());
            //性别 （0=女，1=男）
            user.setPersonsex(opendoorApply.getUserSex2()==null?1+"":0+"");
            //人员类别（1=学生，2=教职工，3=临时人员）
            user.setPersontype("1");
            //电话
            user.setPersonmobile(opendoorApply.getPhonenumber2());

            log.info("=======人员2授权开始========");
            Map<String,Object> map2= SmartlockUtil.addUser(user,listsubRla.get(1).getLockRoomId());

            //人员2 备注详情
            detalisMap.put("人员2",opendoorApply.getUserName());
            detalisMap.put("锁编2号",listsubRla.get(1).getLockCode());
            detalisMap.put("人员2密码",map2.get("password"));
            if(!SmartlockUtil.resultMsg.equals(map2.get("resultMsg").toString())){
                log.info("人员2："+opendoorApply.getUserName()+"，授权失败，原因："+map2.get("resultMsg")+"，请联系管理员");
                strMsg="人员："+opendoorApply.getUserName()+"，授权失败，原因："+map2.get("resultMsg")+"，请联系管理员";
                return strMsg;
            }else {
                log.info("=======人员2授权成功========");
                auths2=true;
            }



            log.info("=======授权结束========人员1授权结果:"+auths1+" ,人员2授权结果:"+auths2);
            //人员入住办理成功,发送短信提示
            if(auths1 && auths2){
                log.info("=============双人授权成功，下发短信================");
                R p1 = remoteStockService.sendSydSms("【实验室安全系统】授权码："+map1.get("password")+"（"+SmartlockUtil.authsLength+"小时内有效），"+opendoorApply.getSubjectName()+"-门禁远程授权申请已通过，请勿泄露给他人。",3,applyId,new String[] {opendoorApply.getPhonenumber()});
                log.info("人员1短信发送结果："+p1);

                R p2 = remoteStockService.sendSydSms("【实验室安全系统】授权码："+map1.get("password")+"（"+SmartlockUtil.authsLength+"小时内有效），"+opendoorApply.getSubjectName()+"-门禁远程授权申请已通过，请勿泄露给他人。",3,applyId,new String[] {opendoorApply.getPhonenumber2()});
                log.info("人员2短信发送结果："+p2);

            /*String msg1="开门申请成功，门锁编号："+listsubRla.get(0).getLockCode()+"密码："+map1.get("password");
            String msg2="开门申请成功，门锁编号："+listsubRla.get(1).getLockCode()+"密码："+map1.get("password");*/
            }

            opendoorApply.setIllustrate(detalisMap.toString());
            slOpendoorApplyMapper.updateSlOpendoorApply(opendoorApply);

        }catch (Exception e){
            log.info("=======人员授权失败========"+e);
        }
        return strMsg;
    }
}
