javascript socket.io:发送消息到特定房间(客户端)

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/30435673/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-28 12:10:11  来源:igfitidea点击:

socket.io: send message to specific room (client side)

javascriptnode.jssocket.io

提问by alapeno

In socket.io, you usually use a specific syntax on the server sideif you want to send a message to a specific room: io.to(room).emit('event', 'message');.

在socket.io,您通常使用一个特定的语法在服务器端,如果你想将消息发送到特定的房间:io.to(room).emit('event', 'message');

But how would a client(what I mean is the socket.io-related code running in a browser) indicate that a message should go to a specific room?

但是客户端(我的意思是在浏览器中运行的与 socket.io 相关的代码)如何指示消息应该发送到特定房间?

Is it common to just create something like this (of course the server has to evaluate it):

创建这样的东西是否很常见(当然服务器必须评估它):

socket.emit('chat message', {room: 'abc', msg: 'hello there'});

Or does the socket.io client-side library offer a specific syntax for this purpose as well?

或者 socket.io 客户端库是否也为此目的提供了特定的语法?

edit: to clarify, my suggestion from above seems to work, I'm just not sure if there's a better solution.

编辑:澄清一下,我上面的建议似乎有效,我只是不确定是否有更好的解决方案。

采纳答案by Gabriel L.

You've pretty much figured it out. Only the server can emit to specific rooms, because it is only the server that is actually connected to multiple clients. In other words, clients aren't connected to each other —?the client-side library only manages communications between that one client and the server. So, if you want your client app to instruct the server to emit a message to all clients connected to a given room… that's basic API design. You could emit a socket event, or just do a regular http call to a route on your server. Either way you'll be sending metadata about which room(s) the server should broadcast to. The former (emitting) is probably preferred however, because that way on the server side you can use socket.broadcast.toto emit to all clients in the room EXCEPT the socket that initiated the call (a pretty common use case).

你已经很清楚了。只有服务器可以发射到特定房间,因为实际上只有服务器连接到多个客户端。换句话说,客户端没有相互连接——客户端库只管理那个客户端和服务器之间的通信。因此,如果您希望您的客户端应用程序指示服务器向连接到给定房间的所有客户端发送一条消息……这就是基本的 API 设计。您可以发出套接字事件,或者只是对服务器上的路由进行常规 http 调用。无论哪种方式,您都将发送有关服务器应向哪个房间广播的元数据。然而,前者(发射)可能更受欢迎,socket.broadcast.to

回答by Sam

Alapeno's solution was for the client to send a specific room as part of the message data to the server, so that the server would know which room to broadcast the message to.

Alapeno 的解决方案是让客户端将特定房间作为消息数据的一部分发送到服务器,以便服务器知道将消息广播到哪个房间。

However, if you just want the client to send a message to its own room, you can have the server detect the client's room on its own via the socket.roomsobject. Thus, you wouldn't need the client to send the name of its room as part of the message as you indicated.

但是,如果您只是希望客户端向其自己的房间发送消息,则可以让服务器通过socket.rooms对象自行检测客户端的房间。因此,您不需要客户端按照您的指示将其房间的名称作为消息的一部分发送。

Client.js:

客户端.js:

socket.emit('chat message', 'hello');

Server.js:

服务器.js:

socket.on('chat message', function(msg){
    var keys = Object.keys(socket.rooms);
    for (var i = 0; i < keys.length; i++) {
        io.to(socket.rooms[keys[i]]).emit('chat message', msg);
    }
});


Update: The socket.roomsobject includes a sort of hash such as the example below, thus you'd better send to all the rooms in the socket.roomsto be sure the room members receive it. You can't be guaranteed the ordering of the keys.

更新:该socket.rooms对象包含一种如下面的示例的哈希,因此您最好将其发送到 中的所有房间socket.rooms以确保房间成员收到它。不能保证密钥的顺序。

Example:

例子:

socket.rooms[keys[0]]) = WMWlX-ekAxa8hP8FAAAE

socket.rooms[keys[0]]) = WMWlX-ekAxa8hP8FAAAE

socket.rooms[keys[1]]) = app-chat-room

socket.rooms[keys[1]]) = app-chat-room