package com.ruoyi.cs.service.impl;

import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;

import cn.hutool.core.bean.BeanUtil;
import com.alibaba.fastjson.JSONObject;
import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.constant.Constants;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.email.EmailUtil;
import com.ruoyi.common.enums.ServiceResponseEnum;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.securityContext.CsOrderMemberUserSecurityContext;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.RSAUtils;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.uuid.IdUtils;
import com.ruoyi.cs.domain.TeamUserVO;
import com.ruoyi.cs.domain.dto.CsOrderMemberUserLoginDTO;
import com.ruoyi.cs.domain.dto.CsOrderMemberUserReSetPwdDTO;
import com.ruoyi.cs.domain.dto.CsOrderMemberUserRegisterDTO;
import com.ruoyi.cs.domain.vo.CsOrderMemberUserVO;
import org.apache.commons.lang3.ObjectUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;
import com.ruoyi.cs.mapper.CsOrderMemberUserMapper;
import com.ruoyi.cs.domain.CsOrderMemberUser;
import com.ruoyi.cs.service.ICsOrderMemberUserService;

import javax.annotation.Resource;

/**
 * 使用人员信息Service业务层处理
 *
 * @author cc
 * @date 2024-04-23
 */
@Service
public class CsOrderMemberUserServiceImpl implements ICsOrderMemberUserService
{
    @Resource
    private CsOrderMemberUserMapper csOrderMemberUserMapper;

    @Resource
    private RedisCache redisCache;

    //日志
    private static final Logger logger = LoggerFactory.getLogger(CsOrderMemberUserServiceImpl.class);

    @Resource
    private EmailUtil emailUtil;


    /**
     * 查询使用人员信息
     *
     * @param memberUserId 使用人员信息主键
     * @return 使用人员信息
     */
    @Override
    public CsOrderMemberUser selectCsUserInfoByMemberUserId(String memberUserId)
    {
        return csOrderMemberUserMapper.selectCsUserInfoByMemberUserId(memberUserId);
    }

    /**
     * 查询使用人员信息列表
     *
     * @param csOrderMemberUser 使用人员信息
     * @return 使用人员信息
     */
    @Override
    public List<CsOrderMemberUser> selectCsUserInfoList(CsOrderMemberUser csOrderMemberUser)
    {
        return csOrderMemberUserMapper.selectCsUserInfoList(csOrderMemberUser);
    }

    /**
     * 新增使用人员信息
     *
     * @param csOrderMemberUser 使用人员信息
     * @return 结果
     */
    @Override
    public int insertCsUserInfo(CsOrderMemberUser csOrderMemberUser)
    {
        return csOrderMemberUserMapper.insertCsUserInfo(csOrderMemberUser);
    }

    /**
     * 修改使用人员信息
     *
     * @param csOrderMemberUser 使用人员信息
     * @return 结果
     */
    @Override
    public int updateCsUserInfo(CsOrderMemberUser csOrderMemberUser)
    {
        return csOrderMemberUserMapper.updateCsUserInfo(csOrderMemberUser);
    }

    /**
     * 批量删除使用人员信息
     *
     * @param memberUserIds 需要删除的使用人员信息主键
     * @return 结果
     */
    @Override
    public int deleteCsUserInfoByMemberUserIds(String[] memberUserIds)
    {
        return csOrderMemberUserMapper.deleteCsUserInfoByMemberUserIds(memberUserIds);
    }

    /**
     * 删除使用人员信息信息
     *
     * @param memberUserId 使用人员信息主键
     * @return 结果
     */
    @Override
    public int deleteCsUserInfoByMemberUserId(String memberUserId)
    {
        return csOrderMemberUserMapper.deleteCsUserInfoByMemberUserId(memberUserId);
    }



    /**
     * 注册/绑定
     * @param registerDTO 参数
     * @return 结果
     */
    @Override
    public JSONObject csMemberUserLoginOrRegister(CsOrderMemberUserRegisterDTO registerDTO) {
        JSONObject result = new JSONObject();
        String email = registerDTO.getEmail();
        String password = registerDTO.getPassword();
        String realName = registerDTO.getRealName();
        String phone = registerDTO.getPhone();
        String concatPhone = registerDTO.getConcatPhone();
        String registerCompanyName = registerDTO.getRegisterCompanyName();

        String uuid = registerDTO.getUuid();
        String code = registerDTO.getCode();


        // 校验验证码
        if (StringUtils.isNotBlank(uuid)){
            // redis缓存key
            String verifyKey = CacheConstants.CAPTCHA_CODE_KEY + StringUtils.nvl(uuid, "");
            // 验证码值
            String captcha = redisCache.getCacheObject(verifyKey);
            // 移除
            redisCache.deleteObject(verifyKey);
            if (captcha == null){
                throw new ServiceException(ServiceResponseEnum.CAPTCHA_EXPIRE);
            }

            if (!code.equalsIgnoreCase(captcha)){
                throw new ServiceException(ServiceResponseEnum.CAPTCHA_ERROR);
            }
        }



        CsOrderMemberUser userInfo = csOrderMemberUserMapper.getMemberUserInfo(null, email, null);
        if (ObjectUtils.isEmpty(userInfo)){
            // 注册
            CsOrderMemberUser newUser = new CsOrderMemberUser();
            String memberUserId = IdUtils.fastSimpleUUID();
            newUser.setMemberUserId(memberUserId);
            newUser.setEmail(email);
            newUser.setPassword(SecurityUtils.encryptPassword(password));
            newUser.setRealName(realName);
            newUser.setPhone(phone);
            newUser.setConcatPhone(concatPhone);
            newUser.setRegisterCompanyName(registerCompanyName);
            newUser.setStatus("2");
            newUser.setUserStatus("1");
            newUser.setCreateAt(DateUtils.getNowDate());
            newUser.setDelFlag("0");
            newUser.setGuideStatus("0");
            if(StringUtils.isNotBlank(registerDTO.getAcUserId())){
                newUser.setAcUid(registerDTO.getAcUserId());
            }

            newUser.setInviteCode(memberUserId);
            csOrderMemberUserMapper.insertCsUserInfo(newUser);

            // 发送激活账号邮件
            sendActivationEmail(result, newUser, 1);

        }else {
            /*if (userInfo.getStatus().equals('1')){
                throw new ServiceException(ServiceResponseEnum.USER_FREEZE);
            }
            // 登录成功
            //csUserLoginSuccess(result, userInfo, 1);*/

            throw new ServiceException(ServiceResponseEnum.USER_EMAIL_ALREADY_REGISTER);
        }
        return result;
    }

    /**
     * 发送激活邮件
     * @param result 返回参数
     * @param userInfo 超算用户
     * @param loginType 登录类型（0-小程序，1-PC）
     */
    @Override
    public void sendActivationEmail(JSONObject result, CsOrderMemberUser userInfo, Integer loginType){
        // 登录标识
        String activationCode = userInfo.getMemberUserId();
        String verifyKey = CacheConstants.ACTIVATION_CAPTCHA_CODE_KEY + activationCode;
        redisCache.setCacheObject(verifyKey, userInfo.getMemberUserId(), Constants.EMAIL_ACTIVATION_CAPTCHA_EXPIRATION, TimeUnit.MINUTES);

        activationCode = RSAUtils.publicEncrypt(activationCode);
        String url = "https://chaosuanuser.xnszz.com/login?activationCode="+activationCode;
        emailUtil.sendEmailMessage(userInfo.getEmail(),  url, "激活账号","activationMailtemplate.ftl");
        result.put("msg","注册成功，请在30分钟内前往邮箱激活账号");
    }

    /**
     * 登录
     * @param loginDTO 参数
     * @return 结果
     */
    @Override
    public JSONObject csUserLogin(CsOrderMemberUserLoginDTO loginDTO) {
        JSONObject result = new JSONObject();
        String email = loginDTO.getEmail();
        String password = loginDTO.getPassword();

        String uuid = loginDTO.getUuid();
        String code = loginDTO.getCode();


        // 校验验证码
        if (StringUtils.isNotBlank(uuid)){
            // redis缓存key
            String verifyKey = CacheConstants.CAPTCHA_CODE_KEY + StringUtils.nvl(uuid, "");
            // 验证码值
            String captcha = redisCache.getCacheObject(verifyKey);
            // 移除
            redisCache.deleteObject(verifyKey);
            if (captcha == null){
                throw new ServiceException(ServiceResponseEnum.CAPTCHA_EXPIRE);
            }

            if (!code.equalsIgnoreCase(captcha)){
                throw new ServiceException(ServiceResponseEnum.CAPTCHA_ERROR);
            }
        }

        // 查询用户信息
        CsOrderMemberUser userInfo = csOrderMemberUserMapper.getMemberUserInfo(null, email, null);
        if (ObjectUtils.isEmpty(userInfo)){
            throw new ServiceException(ServiceResponseEnum.USER_EMAIL_NOT_REGISTER);
        }else {
            String userPassword = userInfo.getPassword();
            // 账号是否设置密码，密码校验
            if (StringUtils.isBlank(userPassword) || !SecurityUtils.matchesPassword(password, userPassword)){
                throw new ServiceException(ServiceResponseEnum.USER_LOGIN_FAIL);
            }else {
                if (userInfo.getStatus().equals("2")){
                    throw new ServiceException(ServiceResponseEnum.USER_NOT_ACTIVATED);
                }
                if (userInfo.getStatus().equals("1")){
                    throw new ServiceException(ServiceResponseEnum.USER_FREEZE);
                }
                // 登录成功
                csUserLoginSuccess(result, userInfo, 1);
            }
        }
        return result;
    }

    /**
     * 用户登录成功
     * @param result 返回参数
     * @param userInfo 超算用户
     * @param loginType 登录类型（0-小程序，1-PC）
     */
    public void csUserLoginSuccess(JSONObject result, CsOrderMemberUser userInfo, Integer loginType){
        // 登录标识
        String loginToken = IdUtils.getUserLoginToken();
        userInfo.setLastLoginTime(userInfo.getLoginTime());
        userInfo.setLoginToken(loginToken);
        userInfo.setLoginTime(DateUtils.getNowDate());
        csOrderMemberUserMapper.updateCsUserInfo(userInfo);

        String redisKey = CacheConstants.CS_MEMBER_LOGIN_TOKEN_KEY + loginToken;
        String redisValue = RSAUtils.publicEncrypt(userInfo.getMemberUserId());

        redisCache.setCacheObject(redisKey, redisValue, 3, TimeUnit.DAYS);

        result.put("csUserId", RSAUtils.publicEncrypt(loginToken));
    }

    /**
     * 查询用户信息
     * @param memberUserId 用户ID
     * @param email 邮箱
     * @param phone 用户电话
     * @return
     */
    @Override
    public CsOrderMemberUser getMemberUserInfo(String memberUserId, String email, String phone) {
        return csOrderMemberUserMapper.getMemberUserInfo(memberUserId, email, phone);
    }

    /**
     * 查询用户VO信息
     * @return 结果
     */
    @Override
    public CsOrderMemberUserVO getMemberUserInfo() {

        CsOrderMemberUser memberUserInfo = csOrderMemberUserMapper.getMemberUserInfo(CsOrderMemberUserSecurityContext.getMemberUserId(), null, null);
        CsOrderMemberUserVO infoVO = BeanUtil.toBean(memberUserInfo, CsOrderMemberUserVO.class);
        return infoVO;
    }


    /**
     * 发送验证码邮件
     * @param emailTo 超算用户
     */
    @Override
    public void sendEmailCode(String emailTo,String code){
        emailUtil.sendEmailMessage(emailTo, code, "找回密码","mailtemplate.ftl");
    }

    /**
     * 找回密码
     * @param resetPwdDTO 参数
     * @return 结果
     */
    @Override
    public int resetPassword(CsOrderMemberUserReSetPwdDTO resetPwdDTO) {
        String email = resetPwdDTO.getEmail();
        String password = resetPwdDTO.getPassword();
        String code = resetPwdDTO.getCode();
        String uuid = resetPwdDTO.getUuid();

        // 校验验证码
        if (StringUtils.isNotBlank(uuid)){
            // redis缓存key
            String verifyKey = CacheConstants.EMAIL_CAPTCHA_CODE_KEY + StringUtils.nvl(uuid, "");
            // 验证码值
            String captcha = redisCache.getCacheObject(verifyKey);

            if (captcha == null){
                throw new ServiceException(ServiceResponseEnum.CAPTCHA_EXPIRE);
            }

            if (!code.equalsIgnoreCase(captcha)){
                throw new ServiceException(ServiceResponseEnum.CAPTCHA_ERROR);
            }else{
                // 移除
                redisCache.deleteObject(verifyKey);
            }
        }

        CsOrderMemberUser memberUserInfo = csOrderMemberUserMapper.getMemberUserInfo(null, email, null);
        if (ObjectUtils.isEmpty(memberUserInfo)){
            throw new ServiceException(ServiceResponseEnum.USER_EMAIL_NOT_REGISTER);
        }else {
            memberUserInfo.setPassword(SecurityUtils.encryptPassword(password));
            memberUserInfo.setUpdateTime(DateUtils.getNowDate());
            return csOrderMemberUserMapper.updateCsUserInfo(memberUserInfo);
        }
    }

    /**
     * 激活账号
     * @param confirmCode 激活码
     * @return
     */
    @Override
    public AjaxResult  activationAccount(String confirmCode) {
        //验证激活码有效
            String codeuid = RSAUtils.privateDecrypt(confirmCode);
            // redis缓存key
            String verifyKey = CacheConstants.ACTIVATION_CAPTCHA_CODE_KEY + codeuid;

            long expire = redisCache.getExpire(verifyKey);
            // 验证码值
            String memberUserId = redisCache.getCacheObject(verifyKey);
            if (memberUserId == null){

                CsOrderMemberUser memberUserInfo = csOrderMemberUserMapper.getMemberUserInfo( codeuid,null, null);
                if(ObjectUtils.isNotEmpty(memberUserInfo)){
                    csOrderMemberUserMapper.deleteCsUserInfoByMemberUserId(codeuid);
                }
                return AjaxResult.error("已过期,请重新申请注册");

            }
            CsOrderMemberUser memberUserInfo = csOrderMemberUserMapper.getMemberUserInfo( memberUserId,null, null);
            if (ObjectUtils.isEmpty(memberUserInfo)){
                throw new ServiceException(ServiceResponseEnum.USER_EMAIL_NOT_REGISTER);
            }else {

                // 移除激活码
                redisCache.deleteObject(verifyKey);
                //修改用户状态为0-正常
                memberUserInfo.setStatus("0");
                memberUserInfo.setUserStatus("0");
                memberUserInfo.setUpdateAt(DateUtils.getNowDate());
                csOrderMemberUserMapper.updateCsUserInfo(memberUserInfo);
                return AjaxResult.success("账号激活成功");
            }
    }

    /**
     * 修改操作指引状态
     * @return
     */
    @Override
    public int editGuideStatus() {
        CsOrderMemberUser update = new CsOrderMemberUser();
        update.setMemberUserId(CsOrderMemberUserSecurityContext.getMemberUserId());
        update.setUpdateAt(DateUtils.getNowDate());
        update.setGuideStatus("1");
        return csOrderMemberUserMapper.updateCsUserInfo(update);
    }

    /**
     * 查询工单用户信息列表
     *
     * @param csOrderMemberUser 工单用户信息
     * @return 工单用户信息
     */
    @Override
    public List<CsOrderMemberUser> selectCsOrderMemberUserList(CsOrderMemberUser csOrderMemberUser)
    {
        return csOrderMemberUserMapper.selectCsOrderMemberUserList(csOrderMemberUser);
    }

    /**
     * 查询管理端人员相关统计
     *
     * @param beginAt 开始时间
     * @param endAt 结束时间
     * @return 人员数量集合
     */
    @Override
    public Map<String, Object> selectUserStatistics(String beginAt, String endAt) {
        return csOrderMemberUserMapper.selectUserStatistics(beginAt, endAt);
    }

    /**
     * 查询工单用户、资源用户、特殊资源用户信息列表
     *
     * @param csOrderMemberUser 工单用户信息
     * @return 工单用户信息集合
     */
    @Override
    public List<CsOrderMemberUser> selectAllUserListByUserType(CsOrderMemberUser csOrderMemberUser) {
        return csOrderMemberUserMapper.selectAllUserListByUserType(csOrderMemberUser);
    }

    /**
     * 查询团队信息列表
     *
     * @param csOrderMemberUser 用户信息
     * @return 工单用户信息集合
     */
    @Override
    public List<TeamUserVO> selectTeamUserList(CsOrderMemberUser csOrderMemberUser) {
        return csOrderMemberUserMapper.selectTeamUserList(csOrderMemberUser);
    }

    /**
     * 查询团队信息
     *
     * @param memberUserId 用户ID
     * @return 团队信息
     */
    @Override
    public CsOrderMemberUser selectTeamUserInfoByMemberUserId(String memberUserId) {
        return csOrderMemberUserMapper.selectTeamUserInfoByMemberUserId(memberUserId);
    }

    /**
     * 用户重置密码
     *
     * @param csOrderMemberUser 人员信息
     * @return 结果
     */
    @Override
    public int resetPassword(CsOrderMemberUser csOrderMemberUser) {
        String password = csOrderMemberUser.getPassword();
        CsOrderMemberUser memberUserInfo = csOrderMemberUserMapper.getMemberUserInfo(csOrderMemberUser.getMemberUserId(), null, null);
        if (ObjectUtils.isEmpty(memberUserInfo)){
            throw new ServiceException(ServiceResponseEnum.NO_USER);
        }else {
            memberUserInfo.setPassword(SecurityUtils.encryptPassword(password));
            memberUserInfo.setUpdateTime(DateUtils.getNowDate());
            return csOrderMemberUserMapper.updateCsUserInfo(memberUserInfo);
        }
    }

    /**
     * 修改用户状态
     *
     * @param csOrderMemberUser 人员信息
     * @return 结果
     */
    @Override
    public int updateUserStatus(CsOrderMemberUser csOrderMemberUser) {
        CsOrderMemberUser memberUserInfo = csOrderMemberUserMapper.getMemberUserInfo(csOrderMemberUser.getMemberUserId(), null, null);
        if (ObjectUtils.isEmpty(memberUserInfo)){
            throw new ServiceException(ServiceResponseEnum.NO_USER);
        }else {
            memberUserInfo.setStatus(csOrderMemberUser.getUserStatus());
            memberUserInfo.setUserStatus(csOrderMemberUser.getUserStatus());
            return csOrderMemberUserMapper.updateCsUserInfo(memberUserInfo);
        }
    }

    /**
     * 查询团队成员列表
     *
     * @param csOrderMemberUser 用户信息
     * @return 工单用户信息集合
     */
    @Override
    public List<CsOrderMemberUser> selectTeamMemberList(CsOrderMemberUser csOrderMemberUser) {
        return csOrderMemberUserMapper.selectTeamMemberList(csOrderMemberUser);
    }
}
