HeartPongWebsocket.js
/**
* `WebsocketHeartbeatJs` constructor.
*
* @param {Object} opts
* {
* url websocket链接地址
* pingTimeout 未收到消息多少秒之后发送ping请求,默认15000毫秒
pongTimeout 发送ping之后,未收到消息超时时间,默认10000毫秒
reconnectTimeout onreconnect之后2秒, 进行init
pingMsg
* }
* @api public
*/
function WebsocketHeartbeatJs({
url,
pingTimeout = 15000,
pongTimeout = 20000,
reconnectTimeout = 2000,
pingMsg = 'ping',
}){
this.opts = {
url: url,
pingTimeout: pingTimeout,
pongTimeout: pongTimeout,
reconnectTimeout: reconnectTimeout,
pingMsg: pingMsg,
};
this.ws = null; // websocket实例
// override hook function
this.onclose = () => {
};
this.onerror = () => {
};
this.onopen = () => {
};
this.onmessage = () => {
};
this.onreconnect = () => {
};
this.createWebSocket();
}
WebsocketHeartbeatJs.prototype.createWebSocket = function(){
try {
this.ws = new WebSocket(this.opts.url);
this.initEventHandle();
} catch (e) {
// this.reconnect(); // 暂时注释掉重连, 配合后端
throw e;
}
};
WebsocketHeartbeatJs.prototype.initEventHandle = function() {
this.ws.onclose = () => {
this.onclose();
// this.reconnect(); // 暂时注释掉重连, 配合后端
};
this.ws.onerror = () => {
this.onerror();
// this.reconnect(); // 暂时注释掉重连, 配合后端
};
this.ws.onopen = () => {
this.onopen();
//心跳检测重置
this.heartCheck();
};
this.ws.onmessage = (event) => {
this.onmessage(event);
//如果获取到消息,心跳检测重置
//拿到任何消息都说明当前连接是正常的
this.heartCheck();
};
};
WebsocketHeartbeatJs.prototype.reconnect = function(){
if(this.lockReconnect || this.forbidReconnect) return;
this.lockReconnect = true;
this.onreconnect();
//没连接上会一直重连,设置延迟避免请求过多
setTimeout(() => {
this.createWebSocket();
this.lockReconnect = false;
}, this.opts.reconnectTimeout);
};
WebsocketHeartbeatJs.prototype.send = function(msg){
this.ws.send(msg);
};
//心跳检测
WebsocketHeartbeatJs.prototype.heartCheck = function(){
this.heartReset();
this.heartStart();
};
WebsocketHeartbeatJs.prototype.heartStart = function(){
if(this.forbidReconnect) return;//不再重连就不再执行心跳
this.pingTimeoutId = setTimeout(() => {
//这里发送一个心跳,后端收到后,返回一个心跳消息,
//onmessage拿到返回的心跳就说明连接正常
this.ws.send(this.opts.pingMsg);
// // 后端未加重连,因此注释掉该段。
/* start 如果超过一定时间还没重置,说明后端主动断开了 */
// this.pongTimeoutId = setTimeout(() => {
// //如果onclose会执行reconnect,我们执行ws.close()就行了.如果直接执行reconnect 会触发onclose导致重连两次
// this.ws.close();
// }, this.opts.pongTimeout);
/* end 如果超过一定时间还没重置,说明后端主动断开了 */
}, this.opts.pingTimeout);
};
WebsocketHeartbeatJs.prototype.heartReset = function(){
clearTimeout(this.pingTimeoutId);
clearTimeout(this.pongTimeoutId);
};
WebsocketHeartbeatJs.prototype.close = function(){
//如果手动关闭连接,不再重连
this.forbidReconnect = true;
this.heartReset();
this.ws.close();
};
if(window) window.WebsocketHeartbeatJs = WebsocketHeartbeatJs;
export default WebsocketHeartbeatJs;
使用的文件:
import HeartPongWebSocketF from './knowledgeDialog/HeartPongWebSocketF'; // websocket 心跳包
const WEB_URL = 'xxxxxx';
this.ws = new HeartPongWebSocketF({
url: WEB_URL });