package com.vctgo.common.websocket;

import cn.hutool.json.JSONObject;
import com.vctgo.common.domain.WebSocketMessage;
import lombok.extern.slf4j.Slf4j;

import javax.websocket.Session;
import java.io.IOException;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;

/**
 * websocket 客户端用户集
 *
 * @author ruoyi
 */
@Slf4j
public class WebSocketUsers {

    public static volatile boolean IS_PROCESSING = false;

    /**
     * 用户集
     */
    private static Map<String, Session> USERS = new ConcurrentHashMap<String, Session>();

    /**
     * 存储用户
     *
     * @param key     唯一键
     * @param session 用户信息
     */
    public static void put(String key, Session session) {
        USERS.put(key, session);
    }

    /**
     * 移除用户
     *
     * @param session 用户信息
     * @return 移除结果
     */
    public static boolean remove(Session session) {
        if (!USERS.containsValue(session)) {
            return true;
        }
        Set<Map.Entry<String, Session>> entries = USERS.entrySet();
        String key = null;
        for (Map.Entry<String, Session> entry : entries) {
            Session value = entry.getValue();
            if (value.equals(session)) {
                key = entry.getKey();
                break;
            }
        }
        return remove(key);
    }

    /**
     * 移出用户
     *
     * @param key 键
     */
    public static boolean remove(String key) {
        Session remove = USERS.remove(key);
        if (remove != null) {
            boolean containsValue = USERS.containsValue(remove);
            log.info("移出结果 - {}", containsValue ? "失败" : "成功");
            return containsValue;
        } else {
            return true;
        }
    }

    /**
     * 获取在线用户列表
     *
     * @return 返回用户集合
     */
    public static Map<String, Session> getUsers() {
        return USERS;
    }

    /**
     * 群发消息文本消息
     *
     * @param message 消息内容
     */
    public static void sendMessageToUsersByText(String message) {
        Collection<Session> values = USERS.values();
        for (Session value : values) {
            sendMessageToUserByText(value, message);
        }
    }

    /**
     * 给指定群用户发同一个消息文本
     *
     * @param message 给指定群用户发同一个消息文本
     */
    public static void sendMessageToUsersByText(List<String> userIdList, String message) {
        List<Session> sessionList = new ArrayList<>();
        userIdList.forEach(userId-> sessionList.add(USERS.get(userId)));
        sessionList.forEach(session -> sendMessageToUserByText(session, message));
    }

    /**
     * 给指定群用户发不同消息文本
     *
     * @param webSocketMessageList 给指定群用户发不同消息文本
     */
    public static void sendMessageToUsersByText(List<WebSocketMessage> webSocketMessageList) {
        webSocketMessageList.forEach(webSocketMessage -> {
            if (USERS.containsKey(webSocketMessage.getUserId())) {
                Session session = USERS.get(webSocketMessage.getUserId());
                if (Objects.nonNull(session) && session.isOpen()) {
                    sendMessageToUserByText(session, webSocketMessage.getMessage());
                }
            }
        });
    }

    /**
     * 发送文本消息
     *
     * @param session 用户连接信息
     * @param message 用户消息
     */
    public static void sendMessageToUserByText(Session session, String message) {
        if (Objects.nonNull(session)) {
            synchronized (session) {
                try {
                    session.getBasicRemote().sendText(message);
                } catch (IOException e) {
                    log.error("[发送消息异常]", e);
                }
            }
        }
    }
}
