js建立简单socket

js建立简单socket,第1张

import Stomp from "stompjs"

import SockJS from "sockjs-client"

let stompClient = null

class Socket {

  constructor(socketMsg) {

    this.socketMsg = socketMsg

  }

  /**

  * 向服务器发起websocket连接并发送CONNECT帧

  * @param {object} stompType 与服务器连接通道类型

  * @param {function} callback 回调方法

  */

  static startConnect( callback) {

    // 建立连接对象

    const socket = new SockJS(''连接地址)

    // 获取 STOMP 子协议的客户端对象

    stompClient = Stomp.over(socket)

    // 请求头验证,需要登陆

    const headers = {

      userId: JSON.parse(sessionStorage.getItem("id"))

    }

    // stompClient.debug = () =>{}

    stompClient.connect(

      headers,

      (result) =>{

        console.log("开始连接",result)

        // 订阅队列推送

        stompClient.subscribe('订阅1队列地址', res =>{

          // 收到推送内容

          callback(data)

        })

        // 订阅被邀请

        stompClient.subscribe('订阅2地址', res =>{

          callback(data)

        })

      },

      () =>{

        // console.log(err)

      }

    )

  }

  // 主动发送消息

  static send(data) {

    stompClient.send(data.url, headers, data.sendMsg)

  }

  // 断开连接

  static disconnect() {

    stompClient.disconnect(() =>{

      // console.log("连接关闭")

    })

  }

}

export default Socket

先说下我对socket.io的理解,websocket更像是开启了一个端口服务,来监视过往的通讯。所以我们可以依赖于当前站点80端口启socket服务,也可以放于其他端口上,比如:

1

require('socket.io').listen(3000)

这样就是监视3000端口了,由于我用的免费服务器,没有权限打开其他端口,所以,我还是使用80了,由于80已经被express使用了,所以我只好在express使用的时候传进来了。

var server = http.createServer(app)

var socket = require('./socket/msg')(server)

 然后 我在msg.js里是这样写的

var db = require('../db/mysql')

var sio = require('socket.io')

var IO = function(server) {

var io = sio.listen(server)

这样就和谐了,db是创建mysql连接的方法,不在本节内容里,略。

在socket.io里是这样的,首先创建一个io通道的连接,然后监视里面的socket的事件,nodejs是事件驱动嘛。代码如下:

io.on('connection', function(socket) {

console.log('a user connected.')

socket.on('disconnect', function() {

console.log('user disconnected.')

})

})

这时只要有用户连接上,就会进入connection中了,然后它的参数是个socket,如果是公聊,我们可以直接用

1

io.emit('chat message', {})

这种形式了。但我们这里是私聊,所以我们要临时的把这个socket对象保存在全局里,供与你私聊的对象使用找到你的socket,很绕口,其实这里的私聊,不算完全的点对点,它还是经过了服务器的,消息传给服务器,服务器再找到你要传达给的那个人的socket对象,发给他。这就是整个的过程了。这里我使用的是一个类数组对象来存储的.

var users = {},

usocket = {}

socket.on('user join', function(data) {

users[username] = username

usocket[username] = socket

})

由于我这里需要用户名登录,所以我就把用户名作为了唯一的标识,这里用类数组的形式的好处就是我不用循环也能够很快的找到它。再我给A发送私聊时,我会先在这个uscoket里面找到它,然后调用它的emit。

function sendUserMsg(data) {

if (data.to in usocket) {

console.log('================')

console.log('to' + data.to, data)

usocket[data.to].emit('to' + data.to, data)

usocket[data.user].emit('to' + data.user, data)

console.log('================')

}

}

这里我emit了两次的原因是,我发给对方消息的同时,我自己也要收到这个消息,然后把它显示出来,为什么这样?其一,接口统一了,聊天里的内容全是服务器过来的,其二,证明我发送成功了。

然后我在客户端监听时,也用我自己的用户名起了一个to+用户名的事件监听。

socket.on('to' + user, function(data) {

//console.log(data)

formatMsg(data)

})

这样,不管是我发的消息,还是我收到消息,都会进入这个事件了。最后,在用户离开的时候别忘记delete掉这个对象。

socket.on('disconnect', function() {

console.log('disconnect')

if (username) {

counter--

delete users[username]

delete usocket[username]

if (home.name == username) {

homeLeave(username)

}

sendmsg({

type: 0,

msg: "用户<b>" + username + "</b>离开聊天室",

counter: counter,

users: users

})

}

})


欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/sjk/6759445.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-03-27
下一篇 2023-03-27

发表评论

登录后才能评论

评论列表(0条)

保存