websocket入门一条龙,基础、封装与使用(代码开箱即用)

前言

Websocket是一种用于在服务器和客户端之间实现高效的双向通信的机制,通过WebSocket,其目的是在应用服务器进行频繁双向通信时,可以使服务器避免打开多个HTTP连接进行工作来节约资源,提高了工作效率和资源利用率。

WebSocket相关

1. 构造函数

WebSocket(url,protocols)构造函器会返回一个 WebSocket 对象。

url指WebSocket服务器将响应的URL。
protocols 可选字段,代表选择的子协议。

2. 常用属性

  • WebSocket.url是一个只读属性,对应构造函数创建WebSocket实例对象时的URL
  • WebSocket.readyState返回当前 WebSocket 的链接状态,只读。对应值为整型,如下:
    • 0 (WebSocket.CONNECTING) 正在链接中
    • 1 (WebSocket.OPEN) 已经链接并且可以通讯
    • 2 (WebSocket.CLOSING) 连接正在关闭
    • 3 (WebSocket.CLOSED) 连接已关闭或者没有链接成功
  • WebSocket.onopen属性定义建立连接并可以通讯时触发的回调函数,也就是readyState 变为1时调用;
  • WebSocket.onmessage该属性定义一个当收到来自服务器的消息时触发的回调函数。
  • WebSocket.onerror定义一个发生错误时执行的回调函数,此事件的事件名为"error"。
  • WebSocket.onclose属性返回一个事件监听器,这个事件监听器将在 WebSocket 连接的readyState 变为3时被调用。

websocket封装

websocket.js代码如下:

class Socket {
  /**
   * 构造函数
   * @param {object} params 构造函数参数
   */
  constructor(params) {
    window.WebSocket = window.WebSocket || window.MozWebSocket;
    if (!window.WebSocket) { // 检测浏览器支持
      console.error('错误: 浏览器不支持websocket');
      return;
    }
    this.websocket = null;
    this.params = params;
    this.socketInit(params);
  }

  /**
   * 初始化socket
   * @param {string}   url     WebSocket服务器将响应的URL
   * @param {function} onopen  open事件的回调函数
   * @param {function} onclose close事件的回调函数
   * @param {function} onerror error事件的回调函数
   * @param {function} onclose close事件的回调函数
   * @param {boolean}  reconnect 是否启用断线重连 默认为false
   * @param {number}   timer   心跳周期 若为空或0则不启用
   */
  socketInit({
    url, onopen, onmessage, onerror, onclose, reconnect = false, timer,
  }) {
    if (url !== undefined) {
      // 若不以wss?开头
      if (!/^wss?:\/\//.test(url)) {
        const { protocol } = window.location;
        // 则自动补上协议头
        url = protocol === 'http:' ? 'ws://' + url : 'wss://' + url;
      }
      try {
        this.websocket = new WebSocket(url);
        // 用于指定连接成功后的回调函数。
        this.websocket.onopen = (e) => {
          console.log('连接成功', e);
          if (timer > 0) {
            this.heartCheck(timer);
          }
          if (typeof onopen === 'function') {
            onopen(e);
          }
        };
        // 用于指定当从服务器接受到信息时的回调函数。
        this.websocket.onmessage = (e) => {
          console.log('接收数据', e);
          onmessage(e.data);
        };
        // 用于指定连接关闭后的回调函数。
        this.websocket.onclose = (e) => {
          console.log('连接关闭', e);
          reconnect && this.reconnect();
          if (typeof onclose === 'function') {
            onclose(e);
          }
        };
        // 用于指定连接失败后的回调函数。
        this.websocket.onerror = (e) => {
          console.log('连接异常', e);
          reconnect && this.reconnect();
          if (typeof onerror === 'function') {
            onerror(e);
          }
        };
      } catch (e) {
        reconnect && this.reconnect();
      }
    }
  }

  // 发送消息
  send(message) {
    // readyState 1 表示已经链接并且可以通讯
    if (!this.websocket || this.websocket.readyState !== 1) {
      console.log('请确认websocket是否已经链接并且可以通讯');
      return;
    }
    this.websocket.send(JSON.stringify(message));
  }

  // 手动关闭socket
  close() {
    this.heartInterval && clearInterval(this.heartInterval);
    this.reconnectTimeout && clearTimeout(this.reconnectTimeout);
    if (!this.websocket) {
      console.log('websocket 不可用');
      return;
    }
    this.websocket.close();
  }

  // 周期性发送ping 保活
  heartCheck(timer) {
    this.heartInterval = window.setInterval(() => {
      this.send({ type: 'ping' });
    }, timer);
  }

  // 断线重连
  reconnect() {
    if (this.lockReconnect) return;
    this.lockReconnect = true;
    this.reconnectTimeout && clearTimeout(this.reconnectTimeout);
    this.reconnectTimeout = window.setTimeout(() => {
      this.socketInit(this.params);
      this.lockReconnect = false;
    }, 5000);
  }
}
export default Socket;


使用方式

代码如下(示例):

import WebSocket from '@/utils/websocket';

const options = {
  url: 'ws://127.0.0.1:8080',
  onmessage: (res) => {
	// 接收数据后回调
  },
  // 保活周期 10s
  timer: 10000,
  // 断线重连
  reconnect: true,
};
const socket = new WebSocket(options);

业务处理完可以手动关闭连接

socket.close();

补充

可先用websocket在线测试工具测试服务器是否联通。封装代码易扩展,后续还可添加保活、重连功能。

2022.1.15号 更新

新增断线重连以及保活功能。

  • 8
    点赞
  • 35
    收藏
    觉得还不错? 一键收藏
  • 10
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值