import { ElMessage, EVENT_CODE } from 'element-plus'

// 定义消息类型，用于类型检查
type MessageType = {
    [key: string]: any
}

export default class SocketService {
    // 单例模式实例
    private static instance: SocketService | null = null
    // 和服务端连接的socket对象
    private ws: WebSocket | null = null
    // 存储回调函数
    private callBackMapping: { [key: string]: ((message: MessageType) => void) | null } = {}
    // 标识是否连接成功
    private connected: boolean = false
    // 记录重试的次数
    private sendRetryCount: number = 0
    // 重新连接尝试的次数
    private connectRetryCount: number = 0
    // Web Worker 实例
    private work: Worker | null = null
    // 临时的 Blob URL
    private workerBlobUrl: string | null = null
    // 上次活动时间戳
    private lastActivityTime: number = 0
    // 最后一次收到心跳回复时间
    private lastResponseHeartTime: number = Date.now()
    // 重新连接延迟，单位毫秒
    private reconnectDelay: number = 5000

    // 单例模式获取实例
    public static get Instance(): SocketService {
        if (!this.instance) {
            this.instance = new SocketService()
        }
        return this.instance
    }

    // 定义连接服务器的方法
    public async connect(url: string) {
        if (!window.WebSocket) {
            console.log('您的浏览器不支持WebSocket')
            return
        }
        
        console.log("🚀 ~ SocketService ~ connect ~ url:", url)
       if (url === null || (typeof url === 'string' && url.includes('null'))) return;

        setTimeout(() => {
            this.ws = new WebSocket(url)

            this.ws.onopen = () => this.handleOpen()
            this.ws.onclose = () => this.handleClose()
            this.ws.onerror = () => this.handleError()
            this.ws.onmessage = event => this.handleMessage(event)
        }, 0)
    }
    // 处理连接成功事件
    private handleOpen(): void {
        // ElMessage.success('webSocket连接服务端成功了')
        console.log('连接服务端成功了')
        this.connected = true
        this.connectRetryCount = 0
        this.updateLastActivityTime()
        this.startHeartbeat()
    }

    // 处理连接关闭事件
    private handleClose(): void {
        console.log('连接webSocket服务端关闭')
        this.connected = false
        this.connectRetryCount++
        this.clearHeartbeat()
        // 可根据需要添加重连逻辑
        // setTimeout(() => this.connect(), 500 * this.connectRetryCount);
    }

    // 处理连接错误事件
    private handleError(): void {
        ElMessage.error('webSocket连接异常！')
    }

    // 处理服务端发送过来的数据
    private handleMessage(event: MessageEvent): void {
        // console.log('🚀 ~ SocketService ~ handleMessage ~ event.data:', event.data)

        if (event.data == '连接成功') {
            this.sendHeartbeat()
        } else if (event.data == 'over') {
        } else if (event.data.length > 10) {
            let message: MessageType
            try {
                // console.log('Received message:', event.data)
                message = JSON.parse(event.data)
            } catch (e) {
                console.error('消息解析失败', event.data, e)
                return
            }
            // console.log("🚀 ~ SocketService ~ handleMessage ~ message:", message)

            // 通过接受服务端发送的type字段来回调函数

            if ((message.key || message.code || message.time) && this.callBackMapping['message']) {
                this.callBackMapping['message']!(message)
            } else {
                console.log('抛弃====>')
                // console.log(event.data)
                // 丢弃或继续写你的逻辑
            }
        } else {
            this.callBackMapping['message']!({ Flag: false })
            if(event.data == 'connect')return
            ElMessage.error(event.data)
        }
    }

    // 启动心跳检测
    private startHeartbeat(): void {
        this.lastResponseHeartTime = Date.now()
        const url = window.URL.createObjectURL(
            new Blob(['(function(e){setInterval(function(){this.postMessage(null)},30000)})()'])
        )
        this.workerBlobUrl = url
        this.work = new Worker(url)
        this.work.onmessage = e => this.handleWorkerMessage(e)
    }

    // 处理 Web Worker 消息
    private handleWorkerMessage(e: MessageEvent): void {
        // if (this.lastActivityTime - this.lastResponseHeartTime > 30000) {
        //     // 说明已经三轮心跳没收到回复了，关闭检测，提示用户。
        //     // ElMessage.error('业务主体模块发生未知异常，请尝试重新启动！')
        //     this.clearHeartbeat()
        //     return
        // }
        // console.log(123);

        this.sendHeartbeat()
    }

    // 发送心跳消息
    private sendHeartbeat(): void {
        // console.log(new Date() + '进入心跳消息发送。。。。。。。。。。。。。')
        if (this.ws) {
            this.ws.send('alive')
            this.updateLastActivityTime()
        }
    }

    // 更新活动时间
    private updateLastActivityTime(): void {
        this.lastActivityTime = Date.now()
    }

    // 清除心跳检测
    private clearHeartbeat(): void {
        if (this.work) {
            this.work.terminate()
            this.work = null
        }
        if (this.workerBlobUrl) {
            window.URL.revokeObjectURL(this.workerBlobUrl)
            this.workerBlobUrl = null
        }
    }

    // 回调函数的注册
    public registerCallBack(socketType: string, callBack: (message: MessageType) => void): void {
        this.callBackMapping[socketType] = callBack
    }

    // 取消某一个回调函数
    public unRegisterCallBack(socketType: string): void {
        this.callBackMapping[socketType] = null
    }

    // 发送数据的方法
    public send(data: any): void {
        if (this.connected) {
            this.sendRetryCount = 0
            try {
                if (this.ws) {
                    this.ws.send(JSON.stringify(data))
                }
            } catch (e) {
                if (this.ws) {
                    this.ws.send(data)
                }
            }
        } else {
            this.sendRetryCount++
            setTimeout(() => this.send(data), this.sendRetryCount * 500)
        }
    }

    // 断开方法
    public closeWs(): void {
        if (this.connected && this.ws) {
            this.ws.close()
        }
        console.log('执行WS关闭命令..')
    }
}
