vue3+ts封装Websocket

Vue3中使用Websocket可以让我们轻松地实现实时数据传输。为了方便使用,我们可以封装一个好用的Websocket类。

安装依赖

首先我们需要安装 ws 库来处理Websocket连接,使用以下命令进行安装:

复制代码
npm install ws --save

使用ts+vue3封装组件

javascript 复制代码
import { onUnmounted } from 'vue';

//设置
interface SocketOptions {
  //心跳间隔
  heartbeatInterval?: number;
  //超时重传
  reconnectInterval?: number;
  //最大重传次数
  maxReconnectAttempts?: number;
}

class Socket {
  //路径
  url: string;
  ws: WebSocket | null = null;
  opts: SocketOptions;
  //重传次数
  reconnectAttempts: number = 0;
  listeners: { [key: string]: Function[] } = {};
  //心跳间隔
  heartbeatInterval: number | null = null;
  //构造函数
  constructor(url: string, opts: SocketOptions = {}) {
    this.url = url;
    this.opts = {
      //心跳间隔
      heartbeatInterval: 30000,
      //超时重传
      reconnectInterval: 5000,
      //最大重传次数
      maxReconnectAttempts: 5,
      ...opts
    };

    this.init();
  }
  //初始化
  init() {
    this.ws = new WebSocket(this.url);
    this.ws.onopen = this.onOpen.bind(this);
    this.ws.onmessage = this.onMessage.bind(this);
    this.ws.onerror = this.onError.bind(this);
    this.ws.onclose = this.onClose.bind(this);
  }
  //打开
  onOpen(event: Event) {
    console.log('WebSocket opened:', event);
    this.reconnectAttempts = 0;
    this.startHeartbeat();
    this.emit('open', event);
  }
  //收到的WebSocket消息
  onMessage(event: MessageEvent) {
    // console.log('WebSocket message received:', event.data);
    this.emit('message', event.data);
  }
  //错误
  onError(event: Event) {
    console.error('WebSocket error:', event);
    this.emit('error', event);
  }
  //重连逻辑中,在连接失败后自动重新连接
  onClose(event: CloseEvent) {
    console.log('WebSocket closed:', event);
    this.stopHeartbeat();
    this.emit('close', event);
    //重连逻辑中,在连接失败后自动重新连接,但会限制重连的次数和每次重连之间的间隔时间
    if (this.opts.maxReconnectAttempts !== 0 && this.reconnectAttempts < this.opts.maxReconnectAttempts!) {
      setTimeout(() => {
        // console.log("我有错误了1111111111111111111111111111111111111");
        this.reconnectAttempts++;
        this.init();
      }, this.opts.reconnectInterval);
    }
  }
  //开始心跳检测
  startHeartbeat() {
    if (!this.opts.heartbeatInterval) return;

    this.heartbeatInterval = window.setInterval(() => {
      if (this.ws?.readyState === WebSocket.OPEN) {
        this.ws.send('ping');
      }
    }, this.opts.heartbeatInterval);
  }
  //停止心跳检测
  stopHeartbeat() {
    if (this.heartbeatInterval) {
      clearInterval(this.heartbeatInterval);
      this.heartbeatInterval = null;
    }
  }
  //发送消息
  send(data: string) {
    if (this.ws?.readyState === WebSocket.OPEN) {
      this.ws.send(data);
    } else {
      console.error('WebSocket is not open. Cannot send:', data);
    }
  }
  //事件监听器注册功能的实现
  on(event: string, callback: Function) {
    if (!this.listeners[event]) {
      this.listeners[event] = [];
    }
    this.listeners[event].push(callback);
  }
  //从事件监听器中移除
  off(event: string) {
    if (this.listeners[event]) {
      delete this.listeners[event];
    }
  }
  //在事件监听器中触发一个指定的事件
  emit(event: string, data: any) {
    this.listeners[event]?.forEach(callback => callback(data));
  }
}

export function useSocket(url: string, opts?: SocketOptions) {
  const socket = new Socket(url, opts);

  onUnmounted(() => {
    socket.off('open');
    socket.off('message');
    socket.off('error');
    socket.off('close');
    socket.ws?.close(); // 关闭WebSocket连接  
  });

  return {
    socket,
    send: socket.send.bind(socket),
    on: socket.on.bind(socket),
    off: socket.off.bind(socket)
  };
}

使用

javascript 复制代码
import { useSocket } from "../../utils/websocket";

const { socket, send, on, off } = useSocket(
  `ws://192.168.22.32:8000/v1/user/chats`
);

 on("close", () => console.log("Socket closed!"));
  //webSocket连接上服务器时
  on("open", event => {
    console.log("webSocket连接上服务器时", event);
  });
socket.on("message", data => {
console.log("Received data:", data); })


   send(xxxx);
相关推荐
挨踢学霸3 小时前
技术全面重构|MsgHelper 新版深度拆解:交互、视觉与逻辑的底层优化(二)
经验分享·笔记·微信·架构·自动化
OxyTheCrack3 小时前
【C++】简述Observer观察者设计模式附样例(C++实现)
开发语言·c++·笔记·设计模式
Fuliy963 小时前
第三阶段:进化与群体智能 (Evolutionary & Swarm Intelligence)
人工智能·笔记·python·学习·算法
白云偷星子3 小时前
云原生笔记6
linux·运维·笔记·mysql·云原生
小陈phd3 小时前
多模态大模型学习笔记(十六)——Transformer 学习之 Decoder Only
人工智能·笔记·深度学习·学习·自然语言处理·transformer
白云偷星子3 小时前
云原生笔记5
linux·运维·笔记·云原生·tomcat
tingshuo29173 小时前
R001 记忆化搜索 ABCPATH - SPOJ 有方向的搜索
笔记
袁气满满~_~4 小时前
深度学习笔记七
笔记
智者知已应修善业4 小时前
【51单片机8位密码锁】2023-2-22
c语言·经验分享·笔记·单片机·嵌入式硬件·算法·51单片机
枷锁—sha4 小时前
【CTFshow-pwn系列】03_栈溢出【pwn 056-057】详解:32位 与64位Shellcode 与 Linux 系统调用底层原理剖析
linux·运维·网络·笔记·安全·网络安全·系统安全