关于前端:前端-H5新特性-websocket-封装

8次阅读

共计 3759 个字符,预计需要花费 10 分钟才能阅读完成。

WebSocket 对象

let Socket = new WebSocket(url, [protocol] );

以上代码中的第一个参数 url, 指定连贯的 URL。第二个参数 protocol 是可选的,指定了可承受的子协定。

1、websocket 事件;

let  socket = new WebSocket("// 申请地址"); // 定义 socket 

socket.onopen           连贯建设时触发
socket.onmessage        接收数据时触发
socket.onerror          通信谬误时触发
socket.onclose          连贯敞开时触发 

2、websocket 状态码(socket.readyState,示意连贯状态,能够是以下值)

 0:未连贯(正在建设连贯连贯,还没有实现)1:连贯已建设(连贯胜利建设,能够进行通信)2:连贯正在敞开(连贯正在进行敞开握手,行将敞开)3:连贯已敞开或打不开连贯(连贯曾经敞开或者基本没有建设)

3、websocket 办法;

 socket.send();向服务器发送数据
 socket.close();  敞开连贯 

封装

webSocket.js

/**
 * websocket 相干办法类
 * websocket 相干属性(仅供参考):* 在此新增、编辑、删除、获取 websocket
 * 应用时间接应用 send 办法即可,而后依据须要调用其余的办法
 * */
class WebsocketApi {constructor() {this.websocket = new Map(); // 初始化 websocket 容器
        this.baseUrl = baseUrl; // 默认 URL,在 config.js 中配置,在 main.js 中注入
        this.isOpen = false; // 开启标识,连贯标识 防止反复连贯
        this.heartbeatInterval = 60000; // 心跳发送频率, 每段时间发送一次心跳包 这里设置为 60s, 不同于重连频率
        this.heartbeatData = null; // 心跳发送的数据内容
        this.heartbeatTimer = null; // 心跳 timer
        this.heartbeat = null; // 延时发送音讯对象(启动心跳新建这个对象,收到音讯后重置对象)this.isReconnect = true; // 是否主动重连
        this.reconnectInterval = 3000; // 重连频率,不同于心跳包发送工夫距离
        this.reconnectCount = 3; // 重连次数
        this.reconnectCurrent = 0; // 已发动重连次数
        this.reconnectTimer = null; // 重连 timer
    }
    /**
     * 初始化 websocket
     * @param url
     * websocket 地址,默认为 this.baseUrl
     * @param callback
     * 初始化过程中的回调函数
     * 如果是一般字符串,则视为拼接到 websocketURL 前面的参数
     * @param callback:回调函数,用于获取 onmessage 事件返回的数据
     * @returns 无返回值
     */
    init(_url, callback) {
        const url = _url ? _url : this.baseUrl;
        if (!('WebSocket' in window)) {console.warn('浏览器不反对 WebSocket');
            return;
        }

        // 曾经创立过连贯不再反复创立
        if (this.websocket) {return this.websocket;}

        this.websocket = new WebSocket(url);

        // 连贯胜利
        this.websocket.onopen = () => {console.log('连贯胜利');
            this.isOpen = true;
            this.isReconnect = true;
            // 开启心跳
            this.heartbeat();};

        this.websocket.onmessage = res => {this.getMessage(res, callback);
        };

        // 连贯产生谬误
        this.websocket.onerror = function (e) {console.error('WebSocket 连贯产生谬误');
            if (!this.isOpen) {this.reconnect(url); // 重连
            }
        };

        // 敞开连贯
        this.websocket.onclose = e => {console.log(` 连贯已断开 (${e.code})`);
            clearInterval(this.heartbeatInterval);
            this.isOpen = false;

            // 须要从新连贯
            if (this.isReconnect) {this.reconnectTimer = setTimeout(() => {
                    // 超过重连次数
                    if (this.reconnectCurrent > this.reconnectCount) {clearTimeout(this.reconnectTimer);
                        return;
                    }

                    // 记录重连次数
                    this.reconnectCurrent += 1;
                    this.reconnect(url);
                }, this.reconnectInterval);
            }
        };
    }
    /**
     * 心跳办法,定时唤起连贯
     * @returns 没有返回值
     */
    heartbeat() {this.heartbeat = setInterval(() => {if (this.isOpen) {this.send(this.heartbeatData);
            } else {this.clear();
            }
        }, this.heartbeatInterval);

        if (this.heartbeatTimer) {clearInterval(this.heartbeatTimer);
        }
        this.heartbeatTimer = setInterval(() => {this.send(this.heartbeatData);
        }, this.heartbeatInterval);
    }
    /**
     * 发送音讯办法
     * @param data 要发送的数据内容
     * @param callback 发送之后的回调函数
     * @returns websocket 实例或者 undefined
     */
    send(data, callback) {
        // 开启状态间接发送
        if (this.websocket.readyState === this.websocket.OPEN) {this.websocket.send(JSON.stringify(data)); // 在这里依据本人的须要转换数据格式

            if (callback) {callback();
            }

            // 正在开启状态,则期待 1s 后从新调用
        } else if (this.websocket.readyState === this.websocket.CONNECTING) {setTimeout(() => {this.send(data, callback);
            }, 1000);

            // 未开启,则期待 1s 后从新调用
        } else {this.init();
            setTimeout(() => {this.send(data, callback);
            }, 1000);
        }
    }
    /**
     * 接管音讯办法
     * @param cb 接管到的音讯后的回调函数
     * @returns websocket 实例或者 undefined
     */
    getMessage(cb) {
        this.websocket.onmessage = message => {
            try {const params = JSON.parse(message.data);
                if (params !== null && cb) {return cb(params);
                } else {return params;}
            } catch (error) {console.error(error);
            }
        };
    }
    /**
     * 从新连贯的办法
     * @returns 没有返回值
     */
    reconnect(_url) {
        const url = _url ? _url : this.baseUrl;
        console.log('发动从新连贯', this.reconnectCurrent);
        if (this.websocket && this.isOpen) {this.clear();
        }
        this.websocket = null;
        this.init(url);
    }
    /**
     * 清理 websocket 容器中连贯曾经敞开或者关上链接失败的 websocket
     */
    clear() {this.websocket.close();
        this.heartbeat = null;
        this.heartbeatTimer = null;
    }
}
const websocketApi = new WebsocketApi();
export default websocketApi;

利用

例子 1
<script src="./webSocket.js"></script>
<script type="text/javascript">

websocketApi.init();
websocketApi.clear();
websocketApi.getMessage(res => {console.log(JSON.parse(res.data));
});
websocketApi.send('1234');

</script>

正文完
 0