123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152 |
- let isSocketClose = false; // 是否关闭socket
- let reconnectCount = 5; // 重连次数
- let heartbeatInterval = ""; // 心跳定时器
- let socketTask = null; // websocket对象
- let againTimer = null; //断线重连定时器
- let url = null;
- let onReFn = null;
- let onSucFn = null;
- let onErrFn = null;
- /**
- * sockeUrl:websocet的地址
- * onReceive:消息监听的回调
- * onErrorEvent:抛出错误的回调,且弹窗连接失败的提示框
- * onErrorSucceed:抛出成功回调,主要用于隐藏连接失败的提示框
- * */
- const sokcet = (sockeUrl, onReceive, onErrorEvent, onErrorSucceed) => {
- url = sockeUrl;
- onReFn = onReceive;
- onErrFn = onErrorEvent;
- onSucFn = onErrorSucceed;
- isSocketClose = false;
- //判断是否有websocet对象,有的话清空
- if (socketTask) {
- socketTask.close();
- socketTask = null;
- clearInterval(heartbeatInterval);
- }
- //WebSocket的地址
- // 【非常重要】必须确保你的服务器是成功的,如果是手机测试千万别使用ws://127.0.0.1:9099【特别容易犯的错误】
- let url = sockeUrl
- // 连接
- socketTask = uni.connectSocket({
- url: url,
- success(data) {
- console.log("websocket连接成功");
- clearInterval(againTimer) //断线重连定时器
- },
- fail: (err) => {
- console.log(url)
- console.log("报错", err);
- }
- });
- // 连接打开
- socketTask.onOpen((res) => {
- console.log('WebSocket打开');
- clearInterval(againTimer) //断线重连定时器
- onErrorSucceed({
- isShow: false
- }) // 用于提示框的隐藏
- heartbeatInterval && clearInterval(heartbeatInterval);
- // 10秒发送一次心跳
- heartbeatInterval = setInterval(() => {
- console.log('心跳')
- sendMsg('心跳ing')
- }, 1000 * 10)
- })
- // 监听连接失败
- socketTask.onError((err) => {
- console.log('WebSocket连接打开失败,请检查', err);
- //停止发送心跳
- clearInterval(heartbeatInterval)
- //如果不是人为关闭的话,进行重连
- if (!isSocketClose) {
- reconnect(url, onErrorEvent)
- }
- })
- // // 监听连接关闭 -
- socketTask.onClose((e) => {
- console.log('WebSocket连接关闭!'+JSON.stringify(e));
- clearInterval(heartbeatInterval)
- console.log('监听连接关闭'+isSocketClose)
- if (!isSocketClose) {
- reconnect(url, onErrorEvent)
- }
- })
- // 监听收到信息
- socketTask.onMessage((res) => {
- uni.hideLoading()
- let serverData = res.data
- //与后端规定好返回值分别代表什么,写业务逻辑
- serverData && onReceive(serverData);
- });
- }
- const reconnect = (url, onErrorEvent) => {
- console.log('进入断线重连', isSocketClose);
- clearInterval(againTimer) //断线重连定时器
- clearInterval(heartbeatInterval);
- socketTask && socketTask.close(); // 确保已经关闭后再重新打开
- socketTask = null;
- onErrorEvent({
- isShow: true,
- messge: '扫描头服务正在连接...'
- })
- // 连接 重新调用创建websocet方法
- againTimer = setInterval(() => {
- sokcet(url, onReFn, onErrFn, onSucFn)
- console.log('在重新连接中...');
- }, 1000 * 8)
- Vue.prototype.$againTimer =againTimer;
- }
- const sendMsg = (msg) => { //向后端发送命令
- msg = JSON.stringify(msg)
- try {
- //通过 WebSocket 连接发送数据
- socketTask.send({
- data: msg
- });
- } catch (e) {
- if (isSocketClose) {
- return
- } else {
- reconnect(url, onErrFn)
- }
- }
- }
- // 关闭websocket【必须在实例销毁之前关闭,否则会是underfined错误】beforeDestroy() {websocetObj.stop();}
- const stop = () => {
- isSocketClose = true;
- clearInterval(heartbeatInterval);
- clearInterval(againTimer) //断线重连定时器
- socketTask.close(); // 确保已经关闭后再重新打开
- socketTask = null;
- }
- const $debounce = function(fn, wait) {
- let timer = null;
- return function() {
- if (timer !== null) {
- clearTimeout(timer);
- }
- timer = setTimeout(fn, wait);
- }
- }
- export const MyWebSokcet = {
- sokcet,
- stop,
- sendMsg,
- socketTask
- };
|