package com.ruoyi.system.service.impl;

import com.ruoyi.common.config.AppCfg;
import com.ruoyi.common.core.domain.model.LoginUser;
import com.ruoyi.common.core.domain.model.WeChatUser;
import com.ruoyi.common.enums.MeetingType;
import com.ruoyi.common.enums.ReviewStatus;
import com.ruoyi.common.enums.SysYesNo;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StreamUtils;
import com.ruoyi.system.domain.CpsContentInfo;
import com.ruoyi.system.domain.CpsMeetingEnterpriseTripInfo;
import com.ruoyi.system.domain.CpsMeetingUsr;
import com.ruoyi.system.domain.CpsUsrApply;
import com.ruoyi.system.mapper.CpsContentInfoMapper;
import com.ruoyi.system.mapper.CpsMeetingEnterpriseTripInfoMapper;
import com.ruoyi.system.mapper.CpsMeetingUsrMapper;
import com.ruoyi.system.mapper.CpsUsrApplyMapper;
import com.ruoyi.system.service.ICpsMeetingUsrService;
import io.foldright.cffu.CompletableFutureUtils;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.ObjectUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ScheduledExecutorService;

/**
 * cps_usr_wechat微信用户Service业务层处理
 *
 * @author ruoyi
 * @date 2024-08-18
 */
@Service
public class CpsMeetingUsrServiceImpl implements ICpsMeetingUsrService {
    @Autowired
    private CpsMeetingUsrMapper cpsMeetingUsrMapper;

    @Autowired
    private CpsMeetingEnterpriseTripInfoMapper cpsMeetingTripService;

    @Autowired
    private CpsUsrApplyMapper cpsUsrApplyMapper;

    @Autowired
    private CpsContentInfoMapper contentInfoMapper;

    @Autowired
    private ScheduledExecutorService executor;

    @Autowired
    private AppCfg appCfg;

    /**
     * 查询cps_usr_wechat微信用户
     *
     * @param id cps_usr_wechat微信用户主键
     * @return cps_usr_wechat微信用户
     */
    @Override
    public CpsMeetingUsr selectCpsMeetingUsrById(Long id) {
        return cpsMeetingUsrMapper.selectCpsMeetingUsrById(id);
    }

    /**
     * 查询cps_usr_wechat微信用户列表
     *
     * @param cpsMeetingUsr cps_usr_wechat微信用户
     * @return cps_usr_wechat微信用户
     */
    @Override
    public List<CpsMeetingUsr> selectCpsMeetingUsrList(CpsMeetingUsr cpsMeetingUsr) {
        return cpsMeetingUsrMapper.selectCpsMeetingUsrList(cpsMeetingUsr);
    }

    /**
     * 新增cps_usr_wechat微信用户
     *
     * @param cpsMeetingUsr cps_usr_wechat微信用户
     * @return 结果
     */
    @Override
    public int insertCpsMeetingUsr(CpsMeetingUsr cpsMeetingUsr) {
        cpsMeetingUsr.setCreateTime(DateUtils.getNowDate());
        return cpsMeetingUsrMapper.insertCpsMeetingUsr(cpsMeetingUsr);
    }

    /**
     * 修改cps_usr_wechat微信用户
     *
     * @param cpsMeetingUsr cps_usr_wechat微信用户
     * @return 结果
     */
    @Override
    public int updateCpsMeetingUsr(CpsMeetingUsr cpsMeetingUsr) {
        cpsMeetingUsr.setUpdateTime(DateUtils.getNowDate());
        return cpsMeetingUsrMapper.updateCpsMeetingUsr(cpsMeetingUsr);
    }

    /**
     * 批量删除cps_usr_wechat微信用户
     *
     * @param ids 需要删除的cps_usr_wechat微信用户主键
     * @return 结果
     */
    @Override
    public int deleteCpsMeetingUsrByIds(Long[] ids) {
        return cpsMeetingUsrMapper.deleteCpsMeetingUsrByIds(ids);
    }

    /**
     * 删除cps_usr_wechat微信用户信息
     *
     * @param id cps_usr_wechat微信用户主键
     * @return 结果
     */
    @Override
    public int deleteCpsMeetingUsrById(Long id) {
        return cpsMeetingUsrMapper.deleteCpsMeetingUsrById(id);
    }

    @Override
    public Boolean existCpsMeetingUsr(String tel) {
        return cpsMeetingUsrMapper.exitUser(tel) > 0;
    }

    @Override
    public CpsMeetingUsr getWeChatUser(WeChatUser wxUser) {
        if (!existCpsMeetingUsr(wxUser.getTel())) {
            CpsMeetingUsr cpsMeetingUsr = new CpsMeetingUsr() {{
                setUsrName(wxUser.getNickName());
                setOpenId(wxUser.getOpenid());
                setTel(wxUser.getTel());
                setAvatarUrl(wxUser.getAvatarUrl());
            }};
            insertCpsMeetingUsr(cpsMeetingUsr);
            return cpsMeetingUsr;
        }
        return selectCpsMeetingUsrList(new CpsMeetingUsr() {{
            setTel(wxUser.getTel());
        }}).get(0);
    }

    @Override
    public void usrThemeConferenceRegister(CpsUsrApply user, String type) {
        List<CpsUsrApply> cpsUsrApplies = cpsUsrApplyMapper.selectCpsUsrApplyList(new CpsUsrApply() {{
            setTel(user.getTel());
            setApplyType(type);
            setReviewState(ReviewStatus.PASS.getCode());
        }});
        if (CollectionUtils.isNotEmpty(cpsUsrApplies)) {
            throw new ServiceException("该手机号已经报名，请勿反复报名");
        }
        user.setReviewState(ReviewStatus.WAIT.getCode());
        user.setApplyType(type);
        user.setReviewMsg("");
        WeChatUser loginUser = (WeChatUser)SecurityUtils.getLoginUser();
        user.setUpdateBy(loginUser.getOpenid());
        CpsContentInfo cpsContentInfo = contentInfoMapper.selectCpsContentInfoById(user.getContentId());
        user.setDeptId(cpsContentInfo.getDeptId());
        cpsUsrApplyMapper.insertCpsUsrApplyOrUpdate(user);
    }

    @Override
    public void usrMeetingRegister(CpsUsrApply user) throws ExecutionException, InterruptedException {
        CompletableFuture<List<List<CpsUsrApply>>> registersFetures = CompletableFutureUtils.allResultsOf(CompletableFuture.supplyAsync(() -> cpsUsrApplyMapper.selectCpsUsrApplyList(new CpsUsrApply() {{
            setTel(user.getTel());
            setApplyType(MeetingType.MEETING.getCode());
            setReviewState(ReviewStatus.PASS.getCode());
        }}), executor), CompletableFuture.supplyAsync(() -> cpsUsrApplyMapper.selectCpsUsrApplyList(new CpsUsrApply() {{
            setTel(user.getTel());
            setApplyType(MeetingType.CONFERENCE.getCode());
            setReviewState(ReviewStatus.PASS.getCode());
        }}), executor));

        List<List<CpsUsrApply>> registers = registersFetures.get();
        List<CpsUsrApply> allRegisters = new ArrayList<>();
        for (List<CpsUsrApply> register : registers) {
            if (CollectionUtils.isNotEmpty(register)) {
                allRegisters.addAll(register);
            }
        }
        Map<String, List<CpsUsrApply>> stringListMap = StreamUtils.groupByKey(allRegisters, CpsUsrApply::getApplyType);
        if (CollectionUtils.isNotEmpty(stringListMap.get(MeetingType.MEETING.getCode()))) {
            throw new ServiceException("该手机号已经报名，请勿反复报名");
        }
        if (MeetingType.CONFERENCE.getCode().equals(user.getApplyType()) && CollectionUtils.isNotEmpty(stringListMap.get(MeetingType.CONFERENCE.getCode()))) {
            throw new ServiceException("该手机号已经参与会场调研，请勿反复报名");
        }
        LoginUser loginUser = SecurityUtils.getLoginUser();
        user.setUpdateBy(loginUser.getUsername());
        user.setReviewState(ReviewStatus.WAIT.getCode());
        user.setUsrWechatId(loginUser.getUserId());
        if (SysYesNo.YES.getCode().equals(user.getConferenceFlag())) {
            CpsContentInfo cpsContentInfo = contentInfoMapper.selectCpsContentInfoById(user.getContentId());
            user.setContentTitle(cpsContentInfo.getTitle());
            user.setApplyType(MeetingType.CONFERENCE.getCode());
            user.setConferenceFlag(SysYesNo.NO.getCode());
            user.setDeptId(cpsContentInfo.getDeptId());
            cpsUsrApplyMapper.insertCpsUsrApplyOrUpdate(user);
            user.setConferenceFlag(SysYesNo.YES.getCode());
            user.setApplyType(MeetingType.MEETING.getCode());
            user.setConferenceRel(user.getId());
            user.setDeptId(appCfg.getRoleTopDeptId());
            cpsUsrApplyMapper.insertCpsUsrApplyOrUpdate(user);
            return;
        }
        user.setApplyType(MeetingType.MEETING.getCode());
        user.setConferenceRel(null);
        user.setReviewMsg("");
        user.setDeptId(appCfg.getRoleTopDeptId());
        cpsUsrApplyMapper.insertCpsUsrApplyOrUpdate(user);
    }

    @Override
    public List<CpsContentInfo> qryUsrCollectContent(String openId, String keyword) {
        return cpsMeetingUsrMapper.qryUsrCollectContent(openId, keyword);
    }

    @Override
    public CpsMeetingEnterpriseTripInfo qryUsrTripContent(String openId) {
        CpsMeetingUsr cpsMeetingUsr = cpsMeetingUsrMapper.selectCpsMeetingUsrByOpenId(openId);
        if (ObjectUtils.isEmpty(cpsMeetingUsr)) {
            return null;
        }
        return cpsMeetingTripService.selectCpsMeetingEnterpriseTripInfoById(cpsMeetingUsr.getTripId());
    }
}
