5

The socketio client successfully connects to the server and sends messages with emit to the server but the other direction server to the client fails. I cannot find the source of error. It is

Here is the server python in app.py based on the example in python-socketio website:

from aiohttp import web
import socketio

sio = socketio.AsyncServer()
app = web.Application()
sio.attach(app)

async def index(request):
    """Serve the client-side application."""
    with open('index.html') as f:
        return web.Response(text=f.read(), content_type='text/html')

@sio.on('connect', namespace='/chat')
def connect(sid, environ):
    print("connect", sid)

@sio.on('chat message', namespace='/chat')
async def message(sid, data):
    print("server received message!", data)
    await sio.emit('reply', data)
    await sio.send(data)

@sio.on('disconnect', namespace='/chat')
def disconnect(sid):
    print('disconnect', sid)

app.router.add_static('/static', 'static')
app.router.add_get('/', index)

if __name__ == '__main__':
    web.run_app(app)

I tried commenting one of await sio.emit('reply', data) or await sio.send(data) but result was the same. Here is the javascript client in index.html:

<html>
  <head>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/socket.io/1.3.5/socket.io.min.js"></script>
  </head>
  <body>
    <form id="the_form">
      <input type="input" name="msg" id="msg"></input>
      <input type="submit" value="➤"></input>
    </form>
    <script>
      var socket = io('http://localhost:8080/chat');

      socket.on('connect', function(){console.log('connect!')});
      socket.on('message', function(msg){console.log('message!', msg)});
      socket.on('disconnect', function(){console.log('disconnect!')});
      socket.on('reply', function(msg){console.log('reply!', msg)});

      document.getElementById('the_form').onsubmit = function(e) {
        let msg = document.getElementById('msg').value;
        document.getElementById('msg').value = '';

        // send it to the server
        socket.emit('chat message', msg);

        return false
      };
    </script>
  </body>
</html>

On the terminal window, I run the server. Then, I open two browser windows (Chrome Version 69.0.3497.100 (Official Build) (64-bit)) and send 'test' from one of them. Here is what I see on each window:

Terminal

$ python3 app.py 
======== Running on http://0.0.0.0:8080 ========
(Press CTRL+C to quit)
connect 9b18034f7b8b4d4c857dec394ef01429
connect 3adea48a3e00459f807855da0337599c
server received message! test

Window 1 (console log)

connect!

Window 2 (console log)

connect!
Mehdi
  • 4,202
  • 5
  • 20
  • 36
  • try doing `await sio.emit('reply', room=sid)` and just delete `await sio.send(data)` – evgeni fotia Oct 13 '18 at 10:03
  • OK, I did that. didn't work. I also tried `sio.enter_room(sid, 'test_room')` in connect function and `await sio.emit('reply', room='test_room')` as a way to send the message to the other client instead of echoing it. but none of them worked so far. – Mehdi Oct 13 '18 at 10:07
  • what about this one `await sio.emit('reply', data, room=sid)` – evgeni fotia Oct 13 '18 at 10:13
  • yes, sorry I meant that. – Mehdi Oct 13 '18 at 10:16
  • 2
    Check these exemples from the official github page https://github.com/miguelgrinberg/python-socketio/tree/master/examples I don't know witch one apply to your case. – evgeni fotia Oct 13 '18 at 10:20
  • Thanks for the link. these examples worked. I think I found the problem. – Mehdi Oct 13 '18 at 10:28

1 Answers1

2

Based on the examples here suggested in comments by evgeni-fotia, the namespace argument is necessary here. It seems the default namespace, at least on this version, is not the namespace of the async function. So, the correct way to broadcast with echo back a message is the following:

@sio.on('chat message', namespace='/chat')
async def message(sid, data):
    print("server received message!", data)
    await sio.emit('reply', data, namespace='/chat')
Mehdi
  • 4,202
  • 5
  • 20
  • 36
  • as of Y2023 it seems better to update `socket.io.min.js` and get rid of line `app.router.add_static('/static', 'static')` as it is not immediately clear what is it for. – garej Mar 22 '23 at 06:28
  • for testing I had to correct this line as well: `sio = socketio.AsyncServer(cors_allowed_origins='*')` – garej Mar 22 '23 at 06:32