package com.hzs.system.config.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollectionUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.hzs.common.core.constant.CacheConstants;
import com.hzs.common.core.constant.Constants;
import com.hzs.common.core.enums.*;
import com.hzs.common.core.service.RedisService;
import com.hzs.common.domain.system.config.BdRange;
import com.hzs.common.domain.system.config.BdRangeDetails;
import com.hzs.common.domain.system.config.ext.BdRangeExt;
import com.hzs.common.security.utils.SecurityUtils;
import com.hzs.system.config.dto.RangeDTO;
import com.hzs.system.config.mapper.BdRangeMapper;
import com.hzs.system.config.service.IBdRangeDetailsService;
import com.hzs.system.config.service.IBdRangeService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.*;
import java.util.concurrent.TimeUnit;

/**
 * 极差配置 服务实现类
 */
@Slf4j
@Service
public class BdRangeServiceImpl extends ServiceImpl<BdRangeMapper, BdRange> implements IBdRangeService {

    @Autowired
    private IBdRangeDetailsService iBdRangeDetailsService;
    @Autowired
    private RedisService redisService;

    @Override
    public boolean saveRange(BdRangeExt rangeExt) {
        //字段翻译保存到数据库
        LambdaQueryWrapper<BdRange> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(BdRange::getPkCountry, rangeExt.getPkCountry());
        queryWrapper.eq(BdRange::getRangeValue, rangeExt.getRangeValue());
        List<BdRange> list = baseMapper.selectList(queryWrapper);
        if (CollectionUtil.isEmpty(list)) {
            baseMapper.insert(rangeExt);
            List<Integer> gradeList = rangeExt.getGradeList();
            List<Integer> awardsList = rangeExt.getAwardsList();
            //等级
            for (Integer gr : gradeList) {
                BdRangeDetails rangeDetails = new BdRangeDetails();
                rangeDetails.setPkRange(rangeExt.getPkId());
                rangeDetails.setPkLevel(gr);
                rangeDetails.setRangeType(ERangeType.GRADE.getValue());
                rangeDetails.setPkCountry(SecurityUtils.getPkCountry());
                rangeDetails.setPkCreator(SecurityUtils.getUserId());
                rangeDetails.setCreationTime(new Date());
                iBdRangeDetailsService.save(rangeDetails);
            }
            //奖衔
            for (Integer aw : awardsList) {
                BdRangeDetails rangeDetails = new BdRangeDetails();
                rangeDetails.setPkRange(rangeExt.getPkId());
                rangeDetails.setPkLevel(aw);
                rangeDetails.setRangeType(ERangeType.AWARDS.getValue());
                rangeDetails.setPkCountry(SecurityUtils.getPkCountry());
                rangeDetails.setPkCreator(SecurityUtils.getUserId());
                rangeDetails.setCreationTime(new Date());
                iBdRangeDetailsService.save(rangeDetails);
            }
        }
        redisService.deleteObject(CacheConstants.BD_RANGE + rangeExt.getPkCountry());
        return true;
    }

    @Override
    public boolean updateRange(BdRangeExt rangeExt) {
        baseMapper.updateById(rangeExt);
        LambdaUpdateWrapper<BdRangeDetails> updateWrapper = new LambdaUpdateWrapper<>();
        updateWrapper.set(BdRangeDetails::getDelFlag, EYesNo.NO.getIntValue());
        updateWrapper.eq(BdRangeDetails::getPkRange, rangeExt.getPkId());
        iBdRangeDetailsService.update(updateWrapper);
        List<Integer> gradeList = rangeExt.getGradeList();
        List<Integer> awardsList = rangeExt.getAwardsList();
        //等级
        for (Integer gr : gradeList) {
            BdRangeDetails rangeDetails = new BdRangeDetails();
            rangeDetails.setPkRange(rangeExt.getPkId());
            rangeDetails.setPkLevel(gr);
            rangeDetails.setRangeType(ERangeType.GRADE.getValue());
            rangeDetails.setPkCountry(SecurityUtils.getPkCountry());
            rangeDetails.setPkCreator(SecurityUtils.getUserId());
            rangeDetails.setCreationTime(new Date());
            iBdRangeDetailsService.save(rangeDetails);
        }
        //奖衔
        for (Integer aw : awardsList) {
            BdRangeDetails rangeDetails = new BdRangeDetails();
            rangeDetails.setPkRange(rangeExt.getPkId());
            rangeDetails.setPkLevel(aw);
            rangeDetails.setRangeType(ERangeType.AWARDS.getValue());
            rangeDetails.setPkCountry(SecurityUtils.getPkCountry());
            rangeDetails.setPkCreator(SecurityUtils.getUserId());
            rangeDetails.setCreationTime(new Date());
            iBdRangeDetailsService.save(rangeDetails);
        }
        redisService.deleteObject(CacheConstants.BD_RANGE + rangeExt.getPkCountry());
        return true;
    }

    @Override
    public List<BdRangeExt> queryRange(Integer pkCountry) {
        List<BdRangeExt> rangeList = redisService.getCacheList(CacheConstants.BD_RANGE + pkCountry);
        List<BdRangeExt> rangeListNew = new ArrayList<>();
        if (CollectionUtil.isEmpty(rangeList)) {
            LambdaQueryWrapper<BdRange> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(BdRange::getPkCountry, pkCountry);
            queryWrapper.orderByDesc(BdRange::getCreationTime);
            List<BdRange> list = baseMapper.selectList(queryWrapper);
            if (CollectionUtil.isNotEmpty(list)) {
                list.forEach(item -> rangeListNew.add(BeanUtil.copyProperties(item, BdRangeExt.class)));
                redisService.setCacheList(CacheConstants.BD_RANGE + pkCountry, rangeListNew);
            }
            return rangeListNew;
        } else {
            return rangeList;
        }
    }

    @Override
    public Map<String, RangeDTO> queryRangeDto() {
        Map<String, RangeDTO> rangeDtoMap = new HashMap<>(10);
        List<RangeDTO> rangeDtoS = baseMapper.queryRangeDto(null, null, null);
        rangeDtoS.forEach(rangeDto -> {
            String key = rangeDto.getPkCountry().toString() + rangeDto.getRangeType() + rangeDto.getPkLevel();
            rangeDtoMap.put(key, rangeDto);
        });
        return rangeDtoMap;
    }

    @Override
    public RangeDTO getRangeDTO(Integer pkCountry, Integer rangeType, Integer pkLevel) {
        String key = CacheConstants.BD_RANGE + pkCountry + rangeType + pkLevel;
        RangeDTO rangeDTO = redisService.getCacheObject(key);
        if (rangeDTO == null) {
            List<RangeDTO> rangeDTOList = baseMapper.queryRangeDto(pkCountry, rangeType, pkLevel);
            if (rangeDTOList != null && rangeDTOList.size() > 0) {
                rangeDTO = rangeDTOList.get(0);
                redisService.setCacheObject(key, rangeDTO, Constants.TIMEOUT_DAY, TimeUnit.DAYS);
            }
        }
        return rangeDTO;
    }
}
