【问题标题】:Socket emitting event multiple times套接字多次发出事件
【发布时间】:2019-05-22 10:11:13
【问题描述】:

我正在开发用于聊天的套接字。这是我在 nodejs 文件中运行良好的套接字代码。

外部套接字io.emit 运行良好,并将消息发送给连接到该conversationId 的所有用户。

但是我用来通知用户的socket.broadcast.emit(当用户使用应用程序时)会多次发出(socket.broadcast.emit)事件。为什么会这样?我是否完全错过了套接字方法。

socket.on('sendMessage', async(action2) => {
  try {
    action2.author = socket.decoded.id
    action2.readBy = [socket.decoded.id]
    action2.deliveredTo = [socket.decoded.id]
    const createMessage = await Message.create(action2)

    const sender = await User.findOne({ _id: socket.decoded.id }, { firstName: 1 })

    const memebers = //some api call to get members
    const promises = members.map(async(member) => {
      // socket for message
      const socketNotification = {
        // my object
      }
      console.log(socketNotification, 'socketNotifcication')
      socket.broadcast.emit(`messageSocket${member.memberId}`, socketNotification)
    })
    await Promise.all(promises)
    io.emit(action2.conversationId, messages) // "newMessage"
  } catch (err) {
    throw err
  }
})

【问题讨论】:

  • 不清楚的问题。只是无法从有限数量的代码中分辨出您要做什么或问题出在哪里。甚至不知道“应用程序多次发出事件”是什么意思。您没有显示任何客户端代码,因此我们可以看到它可能会执行多次连接或发送多条消息。此外,它看起来仍然像部分代码,因为在 .map() 循环中有些东西你从不使用。
  • @jfriend00 客户端代码在 (swift)"IOS" 平台上。我不知道他们到底在做什么,但我可以向你解释我在日志中得到的内容。 说明:- 当我在我的套接字函数中进行控制台时,我多次获取 sockeId 不知道为什么。我在this 上阅读了您的 cmets,并试图了解正在发生的事情。但问题是移动端只连接一次套接字,我得到控制台多次ids
  • @jfriend00 是的,但他们多次写socket.on 以捕捉不同的事件。有什么问题吗?
  • @jfriend00 好的,最后一个问题。我在移动端有独特的事件。独特的事件正在由独特的 mongodb _id 创建。那么为什么当我使用Socket.emit(_id, message) 发出时不发出事件呢?当我做io.emit || socket.broadcast.emit 它多次发射。 问题-> 套接字在eventlistners 上发出。请回复。

标签: javascript node.js socket.io chat messaging


【解决方案1】:

来自广播文档:

为事件数据的后续事件发射设置修饰符 只会广播到除发送者之外的所有套接字。

https://socket.io/docs/server-api/#Flag-%E2%80%98broadcast%E2%80%99

所以在你的循环中,你说除了原始套接字之外的每个人都发送这个,并且你多次调用它。你想用什么it.to

io.to(membersSocketID).emit('eventName', socketNotification)

从您的示例中不清楚 messageSocket${member.memberId} 是否应该是您指定的 socket.id 的事件名称。

这是https://socket.io/docs/emit-cheatsheet/ 的一个很好的备忘单

旁注,如果您获取成员 ID 的 api 调用很重要,您最好使用房间/命名空间并在连接时执行该查询以确定房间。

【讨论】:

    【解决方案2】:

    使用io.to(messageSocket${member.memberId}).emit() 代替socket.broadcast.emit()

    【讨论】:

    • 我应该把有效载荷放在哪里?
    • io.to(socket.id).emit('eventName', payload)
    猜你喜欢
    • 2016-08-12
    • 1970-01-01
    • 2021-12-31
    • 2019-10-30
    • 1970-01-01
    • 2019-12-14
    • 1970-01-01
    • 2021-02-23
    • 1970-01-01
    相关资源
    最近更新 更多