55

According to socket.io examples:

To broadcast, simply add a broadcast flag to emit and send method calls. Broadcasting means sending a message to everyone else except for the socket that starts it.

var io = require('socket.io').listen(80);

io.sockets.on('connection', function (socket) {
  socket.broadcast.emit('user connected');
});

I tried to combine this with the new socket.io namsepace feature, so I got this:

var chat = ioserver.of('/chat');

chat.on('connection', function (socket) {
      console.log('chat connection');   
      socket.on('message', function (msg) {
        console.log(msg);  
        chat.send(msg);
      });
  });

This works fine, everyone on the chat channel (and no other channels) gets the message. But the sender also gets it. So I tried to do the following:

chat.on('connection', function (socket) {
      console.log('chat connection');   
      socket.on('message', function (msg) {
        console.log(msg);  
        chat.broadcast.send(msg);
      });
  });

and got an Exception: 'Cannot call method 'send' of undefined.' Ok, so I thought, that broadcast is the feature of a single socket (it feels a bit weird though - how a single socket can brodacast to all other...). So I tried:

chat.on('connection', function (socket) {
      console.log('chat connection');   
      socket.on('message', function (msg) {
        console.log(msg);  
        socket.broadcast.send(msg);
      });
  });

but now it was even worse - no one received the message, not even the sender. Anyway, it was what I logically expected - one socket cannot broadcast something through itself. And no exceptions this time, so broadcast is defined for the socket.

If I do:

chat.on('connection', function (socket) {
      console.log('chat connection');   
      socket.on('message', function (msg) {
        console.log(msg);  
        socket.send(msg);
      });
  });

then only the original sender gets the message, and that is again pretty logical - I used the 'send' of the client-related socket.

So the question is: what is the correct way to use the broadcast feature?

Maybe the developer of socket.io made a mistake and added the broadcast feature to the wrong object (as I understand, it should be the feature of the namespace but now it is defined only for the socket)?

2
  • Have you tried chat.socket.broadcast ?
    – Raynos
    Commented Jun 25, 2011 at 12:57
  • @Raynos: thanks for idea, but still chat.socket.broadcast.send and chat.socket.broadcast throw undefined exception. Commented Jun 25, 2011 at 14:50

4 Answers 4

75
+25

Seems I was able to solve this for myself after opening a bounty. Sorry about that.

Anyway, see if this helps:

chat.on('connection', function (socket) {
  socket.on('message', function (msg) {
    socket.emit(msg); // Send message to sender
    socket.broadcast.emit(msg); // Send message to everyone BUT sender
  });
});

However, you could save some bandwidth and create a more snappy experience for users if you don't resend it to the sender. Just add their messages directly to the chat log, and optionally use use only self-emit to confirm it was received without issue.

4
  • 11
    and if you use io.sockets.emit('signal', obj) sends the signal to everyone
    – orloxx
    Commented Dec 3, 2012 at 19:32
  • This example should be near the top of the Socket.IO docs. Most applications need to reply to each connection independently, rather than always broadcast to all listeners unconditionally!
    – Cuadue
    Commented Sep 16, 2014 at 16:38
  • Using this code you emit the message to all the sockets in the namespace and not only to the sockets of a particular room. Am I right? Commented Apr 14, 2015 at 22:25
  • 3
    I don't understand. You said in the question that this exact code, minus socket.emit(msg);, caused no one to receive the message. Why does adding socket.emit(msg); suddenly cause socket.broadcast.emit(msg); to send the message to everyone but the sender? Commented Aug 5, 2015 at 13:46
38

You solution works if you are working in an evented environment where messages from the client trigger a response to all others, but not if you want the server to sent messages to all clients.

You can do this using io.sockets.emit:

var io = require('socket.io').listen(80);
io.sockets.emit('message', { message: "Hello everyone!" });

However the documentation isn't clear for how to do this to a specific namespace. io.sockets is just a shortcut to io.of(''), as such you can broadcast to everyone on a namespace by calling io.of('/namespace').emit:

var io = require('socket.io').listen(80);
io.of('/admins').emit('message', { message: "Hello admins!" });
4
  • 2
    To me this sounded a bit like mixed up the terms of namespace and room for sockets. Which are treated separately. For those who look for broadcasting to a specific room (from server) the syntax would be io.sockets.in('room name').emit Commented Apr 13, 2015 at 11:06
  • I don't understand how this answers the question... The question is how to broadcast a message, your answer sends message to everyone which already works in OPs code
    – T J
    Commented Dec 30, 2015 at 14:02
  • Just as an update - a server emitting to all the clients till isn't specific in the Docs. You'll figure it out when you play with it but it's not readily intuitive how to use < insert(io,namespace,socket) here>.emit. Their docs really need to add more examples so it clicks. Commented Jan 25, 2016 at 6:13
  • saved me big time here! 'sockets' vs io.of()
    – DanR
    Commented Oct 27, 2016 at 20:54
33
var customNS = ioserver.of('/chat'); 

customNS.on('connection', function (socket) {
   socket.on('message', function (msg) {

       // Send message to sender 
       socket.emit(msg);

       // Send message to everyone on customNS INCLUDING sender
       customNS.emit(msg);

       // Send message to everyone on customNS BUT sender
       socket.broadcast.emit(msg);

       // Send message to everyone on ROOM chanel of customNS INCLUDING sender
       customNS.in('ROOM').emit(msg); 

       // Send message to everyone on ROOM chanel of customNS BUT sender
       socket.broadcast.in('ROOM').emit(msg); 


   });
});

also check this answer Send response to all clients except sender (Socket.io)

1
  • Change chat to customNS Commented Jul 28, 2014 at 4:48
14

Maybe this will help someone

socket.broadcast.to('room1').emit('updatechat', 'SERVER', username + ' has connected to this room'); 

see

Nodejs and Socketio Multiroom Chat Tutorial

0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.