支付宝小程序实现 websocket 通信功能

在支付宝小程序中用 websocket 实现实时通信,通过设置心跳时间来监测连接是否存在,若心跳时间内并没接收到任何消息,将自动重连。

小程序 WebSocket 开发文档
在这里插入图片描述

此配置是用 多实例的方式 开发的,后续如果有其他socket通信,两者之间互不影响。

如果想用单实例,只要参考文档将对应的方法名修改就可,其他无需改动。

page.js

Page({
  data: {
    // websocket相关
    scoket: null, // websocket实例对象
    timeout: 30000, // 超时时间(心跳时间),超过30s无消息推送,重新发送连接
    timeoutObj: null, // 计时器对象——向后端发送心跳检测
    serverTimeoutObj: null, // 计时器对象——等待后端心跳检测的回复
    socketReconnectTimer: null, // 计时器对象——重连
    socketReconnectLock: false, // WebSocket重连的锁
    socketLeaveFlag: false, // 离开标记(解决 退出登录再登录 时出现的 多次相同推送 问题,出现的本质是多次建立了WebSocket连接)
    // websocket相关 (结束)
  },
  onLoad() {},
  // 页面销毁使用
  onUnload() {
    // 离开标记
    this.setData({
      socketLeaveFlag: true
    })
    // 关闭WebSocket
    this.data.scoket.close();
  },
  onShow() {
    this.createWebSocket();
  },
  createWebSocket() {
    // websocket启动
    const socketTask = my.connectSocket({
      url: 'ws://xxxx', // 此 url 仅为示例,开发者可替换自己的 URL
      multiple: true // multiple 为 true 则会返回 socketTask
    });
    // 连接成功建立的回调
    socketTask.onOpen(() => {
      this.onopenCallback();
    });

    // 连接发生错误的回调
    socketTask.onError(() => {
      this.onerrorCallback();
    });

    // 连接关闭的回调
    socketTask.onClose(() => {
      this.oncloseCallback();
    });

    // 接收到消息的回调
    socketTask.onMessage(res => {
      this.getMessageCallback(res.data);
    });

    this.setData({
      scoket: socketTask
    })
  },
  // websocket重连
  socketReconnect() {
    let {
      socketReconnectLock,
      socketReconnectTimer
    } = this.data;
    if (socketReconnectLock) {
      return;
    }
    socketReconnectLock = true;
    socketReconnectTimer && clearTimeout(socketReconnectTimer);
    socketReconnectTimer = setTimeout(() => {
      console.log("WebSocket:重连中...");
      socketReconnectLock = false;
      // websocket启动
      this.createWebSocket();
    }, 4000);
    this.setData({
      socketReconnectLock,
      socketReconnectTimer
    })
  },
  // 连接成功建立的回调
  onopenCallback() {
    console.log("WebSocket:已连接");
    // 心跳检测重置
    this.heartReset();
    // 心跳检测启动
    this.heartStart();
  },
  // 连接发生错误的回调
  onerrorCallback() {
    console.log("WebSocket:发生错误");
    // websocket重连
    this.socketReconnect();
  },
  // 连接关闭的回调
  oncloseCallback() {
    console.log("WebSocket:已关闭");
    // 心跳检测重置
    this.heartReset();
    if (!this.data.socketLeaveFlag) {
      // 没有离开——重连
      // websocket重连
      this.socketReconnect();
    }
  },
  // 接收到消息的回调
  getMessageCallback(rowInfo) {
    // 心跳回复——心跳检测重置
    if (rowInfo.data.indexOf("HeartBeat") > -1) {
      // 收到心跳检测回复就说明连接正常
      this.heartReset(); // 心跳检测重置
      this.heartStart(); // 心跳检测启动
    } else { // 普通推送——正常处理

    	// =======  在此进行逻辑处理 =========
    }
  },
  // 心跳检测重置
  heartReset() {
    let {
      timeoutObj,
      serverTimeoutObj
    } = this.data;
    timeoutObj && clearTimeout(timeoutObj);
    serverTimeoutObj && clearTimeout(serverTimeoutObj);
  },
  // 心跳检测启动
  heartStart() {
    let {
      timeoutObj,
      serverTimeoutObj,
      scoket,
      timeout
    } = this.data;
    timeoutObj && clearTimeout(timeoutObj);
    serverTimeoutObj && clearTimeout(serverTimeoutObj);
    timeoutObj = setTimeout(() => {
      // 这里向后端发送一个心跳检测,后端收到后,会返回一个心跳回复
      scoket.send("HeartBeat");
      console.log("发送心跳检测");
      serverTimeoutObj = setTimeout(() => {
        // 如果超过一定时间还没重置计时器,说明websocket与后端断开了
        console.log("未收到心跳检测回复");
        // 关闭WebSocket
        scoket.close();
      }, timeout);
    }, timeout);

    this.setData({
      timeoutObj,
      serverTimeoutObj
    })
  },
});
  • 服务连接
    在这里插入图片描述
  • 服务端推送的消息

在这里插入图片描述

  • 心跳监测,无通信则断开重连
    在这里插入图片描述
  • 7
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值