package org.wcs.business.redis;

import com.alibaba.fastjson2.JSONObject;
import lombok.RequiredArgsConstructor;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Component;
import org.wcs.constant.ConstantData;
import org.wcs.constant.enums.etag.LedBlinkingEnum;
import org.wcs.constant.enums.etag.LedColorEnum;
import org.wcs.model.po.app.AppEtagTagInfo;
import org.wcs.model.po.app.AppEtagTagLocation;
import org.wcs.model.po.app.AppEtagTask;
import org.wcs.utils.AppStringUtils;

import java.util.HashMap;
import java.util.Map;
import java.util.Set;

/**
 * 电子标签Redis操作类
 */
@Component
@RequiredArgsConstructor
public class EtagRedis {

    /**
     * Redis操作类
     */
    private final StringRedisTemplate stringRedisTemplate;


    // 电子标签小标签信息
    private static final String ETAG_TAG_KEY = ConstantData.SYSTEM_NAME + ":Etag:Tag";
    // 电子标签小标签ID信息，key 是用控制器编号拼接而成
    private static final String ETAG_TAG_ID_KEY = ConstantData.SYSTEM_NAME + ":Etag:TagId";
    // 电子标签位置信息
    private static final String ETAG_LOCATION_KEY = ConstantData.SYSTEM_NAME + ":Etag:Location";
    // 电子标签小标签绑定的任务信息
    private static final String ETAG_TAG_TASK_KEY = ConstantData.SYSTEM_NAME + ":Etag:TagTask";
    // 电子标签区域绑定的用户信息
    private static final String ETAG_AREA_USER_KEY = ConstantData.SYSTEM_NAME + ":Etag:AreaUser";
    // 电子标签小标签颜色信息 ---- 存储上次的颜色，防止重复发送颜色命令
    private static final String ETAG_TAG_COLOR_KEY = ConstantData.SYSTEM_NAME + ":Etag:TagColor";
    // 电子标签小标签闪烁信息 ---- 存储上次的闪烁信息，防止重复发送闪烁命令
    private static final String ETAG_TAG_BLINKING_KEY = ConstantData.SYSTEM_NAME + ":Etag:TagBlinking";
    // 电子标签绑定的当前载具编号
    private static final String ETAG_AREA_VEHICLE_KEY = ConstantData.SYSTEM_NAME + ":Etag:AreaVehicle";


    /* ******************** 电子标签小标签信息 *********************** */

    /**
     * 清空电子标签小标签信息
     */
    public void clearEtagTag() {
        Set<String> keys = stringRedisTemplate.keys(ETAG_TAG_KEY + ":*");
        stringRedisTemplate.delete(keys);
        Set<String> idKeys = stringRedisTemplate.keys(ETAG_TAG_ID_KEY + ":*");
        stringRedisTemplate.delete(keys);
    }

    /**
     * 设置电子标签小标签信息
     * @param tagName 标签名称
     * @param tagInfo 标签信息
     */
    public void setEtagTag(String tagName, AppEtagTagInfo tagInfo) {
        stringRedisTemplate.opsForValue().set(ETAG_TAG_KEY + ":" + tagName, AppStringUtils.objectToString(tagInfo));
        stringRedisTemplate.opsForValue().set(ETAG_TAG_ID_KEY + ":" + tagInfo.getControllerId() + "@" + tagInfo.getTagId(), tagName);
    }

    /**
     * 获取电子标签小标签信息
     * @param tagName 标签名称
     * @return 电子标签小标签信息
     */
    public AppEtagTagInfo getEtagTag(String tagName) {
        String tagInfo = stringRedisTemplate.opsForValue().get(ETAG_TAG_KEY + ":" + tagName);
        if(AppStringUtils.isEmpty(tagInfo)) {
            return null;
        }
        return JSONObject.parseObject(tagInfo, AppEtagTagInfo.class);
    }

    /**
     * 获取电子标签小标签信息
     * @param controllerId 控制器编号
     * @param tagId 标签编号
     * @return 电子标签小标签信息
     */
    public AppEtagTagInfo getEtagTag(String controllerId, Integer tagId) {
        String tagInfo = stringRedisTemplate.opsForValue().get(ETAG_TAG_ID_KEY + ":" + controllerId + "@" + tagId);
        if(AppStringUtils.isEmpty(tagInfo)) {
            return null;
        }
        return JSONObject.parseObject(tagInfo, AppEtagTagInfo.class);
    }


    /* ******************** 电子标签货位信息 *********************** */

    /**
     * 清空电子标签货位信息
     */
    public void clearEtagLocation() {
        Set<String> keys = stringRedisTemplate.keys(ETAG_LOCATION_KEY + ":*");
        stringRedisTemplate.delete(keys);
    }

    /**
     * 设置电子标签货位信息
     * @param locationId 货位ID
     * @param locationInfo 货位信息
     */
    public void setEtagLocation(String locationId, AppEtagTagLocation locationInfo) {
        stringRedisTemplate.opsForValue().set(ETAG_LOCATION_KEY + ":" + locationId, AppStringUtils.objectToString(locationInfo));
    }

    /**
     * 获取电子标签货位信息
     * @param locationId 货位ID
     * @return 货位信息
     */
    public AppEtagTagLocation getEtagLocation(String locationId) {
        String locationInfo = stringRedisTemplate.opsForValue().get(ETAG_LOCATION_KEY + ":" + locationId);
        if(AppStringUtils.isEmpty(locationInfo)) {
            return null;
        }
        return JSONObject.parseObject(locationInfo, AppEtagTagLocation.class);
    }

    /* ******************** 电子标签绑定的任务信息 *********************** */

    /**
     * 设置电子标签绑定的任务信息
     * @param tagName 标签名称
     * @param task 任务信息
     */
    public void setEtagTagTask(String tagName, AppEtagTask task) {
        stringRedisTemplate.opsForValue().set(ETAG_TAG_TASK_KEY + ":" + tagName, AppStringUtils.objectToString(task));
    }

    /**
     * 获取电子标签绑定的任务信息
     * @param tagName 标签名称
     * @return 任务信息
     */
    public AppEtagTask getEtagTagTask(String tagName) {
        String task = stringRedisTemplate.opsForValue().get(ETAG_TAG_TASK_KEY + ":" + tagName);
        if(AppStringUtils.isEmpty(task)) {
            return null;
        }
        return JSONObject.parseObject(task, AppEtagTask.class);
    }

    /**
     * 删除电子标签绑定的任务信息
     * @param tagName 标签名称
     */
    public void removeEtagTagTask(String tagName) {
        stringRedisTemplate.delete(ETAG_TAG_TASK_KEY + ":" + tagName);
    }

    /**
     * 清空电子标签绑定的任务信息
     */
    public void clearEtagTagTask() {
        Set<String> keys = stringRedisTemplate.keys(ETAG_TAG_TASK_KEY + ":*");
        stringRedisTemplate.delete(keys);
    }

    /**
     * 判断电子标签绑定的任务信息是否存在
     * @param tagName 标签名称
     * @return 是否存在
     */
    public boolean existsEtagTagTask(String tagName) {
        return stringRedisTemplate.hasKey(ETAG_TAG_TASK_KEY + ":" + tagName);
    }

    /**
     * 获取所有电子标签绑定的任务信息
     * @return 所有电子标签绑定的任务信息
     */
    public Map<String, String> getEtagTagTaskAll() {
        Map<String, String> tagInfoMap = new HashMap<>();
        Set<String> keys = stringRedisTemplate.keys(ETAG_TAG_TASK_KEY + ":*");
        for (String key : keys) {
            String tagInfo = stringRedisTemplate.opsForValue().get(key);
            String[] tagNameSplit = key.split(":");
            tagInfoMap.put(tagNameSplit[tagNameSplit.length - 1], tagInfo);
        }
        return tagInfoMap;
    }


    /* ******************** 电子标签区域绑定的用户信息 *********************** */

    /**
     * 清空电子标签区域绑定的用户信息
     */
    public void clearEtagAreaUser() {
        Set<String> keys = stringRedisTemplate.keys(ETAG_AREA_USER_KEY + ":*");
        stringRedisTemplate.delete(keys);
    }

    /**
     * 获取电子标签区域绑定的用户信息
     * @param areaId 区域ID
     * @return 区域用户信息
     */
    public String getEtagAreaUser(String areaId) {
        String areaUser = stringRedisTemplate.opsForValue().get(ETAG_AREA_USER_KEY + ":" + areaId);
        if(AppStringUtils.isEmpty(areaUser)) {
            return null;
        }
        return areaUser;
    }

    /**
     * 设置电子标签区域绑定的用户信息
     * @param areaId 区域ID
     * @param userId 用户ID
     */
    public void setEtagAreaUser(String areaId, String userId) {
        stringRedisTemplate.opsForValue().set(ETAG_AREA_USER_KEY + ":" + areaId, userId);
    }

    /* ******************** 电子标签颜色信息 *********************** */

    /**
     * 设置电子标签颜色信息
     * @param tagName 标签名称
     * @param ledColor 颜色
     */
    public void setEtagTagColor(String tagName, LedColorEnum ledColor) {
        stringRedisTemplate.opsForValue().set(ETAG_TAG_COLOR_KEY + ":" + tagName, String.valueOf(ledColor.getCode()));
    }

    /**
     * 获取电子标签颜色信息
     * @param tagName 标签名称
     * @return 颜色
     */
    public LedColorEnum getEtagTagColor(String tagName) {
        String ledColor = stringRedisTemplate.opsForValue().get(ETAG_TAG_COLOR_KEY + ":" + tagName);
        if(AppStringUtils.isEmpty(ledColor)) {
            return null;
        }
        return LedColorEnum.getByCode(Integer.valueOf(ledColor));
    }

    /* ******************** 电子标签闪烁信息 *********************** */

    /**
     * 设置电子标签闪烁信息
     * @param tagName 标签名称
     * @param ledBlinkingEnum 闪烁模式
     */
    public void setEtagTagBlinking(String tagName, LedBlinkingEnum ledBlinkingEnum) {
        stringRedisTemplate.opsForValue().set(ETAG_TAG_BLINKING_KEY + ":" + tagName, String.valueOf(ledBlinkingEnum.getCode()));
    }

    /**
     * 获取电子标签闪烁信息
     * @param tagName 标签名称
     * @return 闪烁模式
     */
    public LedBlinkingEnum getEtagTagBlinking(String tagName) {
        String ledBlinking = stringRedisTemplate.opsForValue().get(ETAG_TAG_BLINKING_KEY + ":" + tagName);
        if(AppStringUtils.isEmpty(ledBlinking)) {
            return null;
        }
        return LedBlinkingEnum.getByCode(Integer.valueOf(ledBlinking));
    }

    /* ******************** 电子标签区域绑定的载具信息 *********************** */

    /**
     * 设置电子标签区域绑定的载具信息
     * @param areaId 区域ID
     * @param vehicleNo 载具编号
     */
    public void setEtagAreaVehicle(String areaId, String vehicleNo) {
        stringRedisTemplate.opsForValue().set(ETAG_AREA_VEHICLE_KEY + ":" + areaId, vehicleNo);
    }

    /**
     * 获取电子标签区域绑定的载具信息
     * @param areaId 区域ID
     * @return 载具编号
     */
    public String getEtagAreaVehicle(String areaId) {
        String vehicleNo = stringRedisTemplate.opsForValue().get(ETAG_AREA_VEHICLE_KEY + ":" + areaId);
        if(AppStringUtils.isEmpty(vehicleNo)) {
            return null;
        }
        return vehicleNo;
    }

    /**
     * 清空电子标签区域绑定的载具信息
     */
    public void clearEtagAreaVehicle() {
        Set<String> keys = stringRedisTemplate.keys(ETAG_AREA_VEHICLE_KEY + ":*");
        stringRedisTemplate.delete(keys);
    }

    /**
     * 清空电子标签区域绑定的载具信息
     * @param areaId 区域ID
     */
    public void clearEtagAreaVehicle(String areaId) {
        Set<String> keys = stringRedisTemplate.keys(ETAG_AREA_VEHICLE_KEY + ":" + areaId);
        stringRedisTemplate.delete(keys);
    }

    /**
     * 获取电子标签区域绑定的载具信息
     * @return < 区域号，载具编号 >
     */
    public Map<String, String> getEtagAreaVehicleAll() {
        Map<String, String> map = new HashMap<>();
        Set<String> keys = stringRedisTemplate.keys(ETAG_AREA_VEHICLE_KEY + ":*");
        for (String key : keys) {
            String vehicleNo = stringRedisTemplate.opsForValue().get(key);
            String[] KeySplitList = key.split(":");
            map.put(KeySplitList[KeySplitList.length - 1], vehicleNo);
        }
        return map;
    }




}
