MKM
MKM

Reputation: 503

WebSocket Server in Python Not Receiving All Messages While Node.js Does

I am running a WebSocket server behind Nginx, and I have two different implementations: one in Node.js and one in Python. The Node.js WebSocket server receives all messages correctly, but the Python server misses one of the messages.

WebSocket Message Flow:

  1. Client opens WebSocket: /my-app/14515/
  2. Client sends message: { "type": "my-app:react_api:editor", "url_kwargs": {...} }
  3. Client sends message: { "type": "my-app:react_api:problem", "url_kwargs": {...} }
  4. Client opens another WebSocket: /editor/14515/

When using Node.js, both messages (my-app:react_api:editor and my-app:react_api:problem) are received. But when using Python, only the first message (my-app:react_api:editor) is logged, and the second one is missing.


Nginx Configuration:

location /ws/ {
    proxy_pass http://127.0.0.1:8387/;
    proxy_http_version 1.1;
    proxy_set_header Upgrade $http_upgrade;
    proxy_set_header Connection "upgrade";
    proxy_redirect off;
    proxy_buffering off;
    proxy_cache off;
    proxy_read_timeout 3600s;
    proxy_send_timeout 3600s;
    include proxy_params;
    proxy_set_header X-Forwarded-Host $server_name;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header X-Forwarded-Proto $scheme;
}

Node.js WebSocket Server (Works Fine)

const WebSocket = require('ws');

const wss = new WebSocket.Server({ port: 8387 });

wss.on('connection', (ws, req) => {
    const clientIP = req.socket.remoteAddress;
    const clientURL = req.url || '/'; 

    console.log(`✅ New connection from ${clientIP}, URL: ${clientURL}`);

    ws.send("👋 Welcome to the WebSocket server!");

    ws.on('message', (message) => {
        console.log(`📩 [${clientURL}] Message from ${clientIP}: ${message}`);
        ws.send(`📢 Echo: ${message}`);
    });

    ws.on('close', (code, reason) => {
        console.log(`🔴 [${clientURL}] Connection closed: Code ${code}, Reason: ${reason}`);
    });

    ws.on('error', (err) => {
        console.error(`❌ [${clientURL}] WebSocket error: ${err.message}`);
    });
});

console.log("🚀 WebSocket server running on ws://localhost:8387");

Python WebSocket Server (Missing Second Message)

import asyncio
import websockets

async def handle_connection(websocket, path):
    client_ip = websocket.remote_address[0]
    client_url = path if path else "/"
    
    print(f"✅ New connection from {client_ip}, URL: {client_url}")
    await websocket.send("👋 Welcome to the WebSocket server!")

    try:
        async for message in websocket:
            print(f"📩 [{client_url}] Message from {client_ip}: {message}")
            await websocket.send(f"📢 Echo: {message}")
    except websockets.exceptions.ConnectionClosed as e:
        print(f"🔴 [{client_url}] Connection closed: Code {e.code}, Reason: {e.reason}")
    except Exception as e:
        print(f"❌ [{client_url}] WebSocket error: {str(e)}")

async def main():
    async with websockets.serve(handle_connection, "localhost", 8387):
        await asyncio.Future()  # Run forever

print("🚀 WebSocket server running on ws://localhost:8387")
asyncio.run(main())

Observed Logs

Node.js Logs (Works as Expected)

🚀 WebSocket server running on ws://localhost:8387
✅ New connection from ::ffff:127.0.0.1, URL: /my-app/14515/
✅ New connection from ::ffff:127.0.0.1, URL: /editor/14515/
📩 [/my-app/14515/] Message from ::ffff:127.0.0.1: {"type":"my-app:react_api:editor",...}
📩 [/my-app/14515/] Message from ::ffff:127.0.0.1: {"type":"my-app:react_api:problem",...}

Python Logs (Missing my-app:react_api:problem)

🚀 WebSocket server running on ws://localhost:8387
✅ New connection from 127.0.0.1, URL: /my-app/14515/
📩 [/my-app/14515/] Message from 127.0.0.1: {"type":"my-app:react_api:editor",...}
✅ New connection from 127.0.0.1, URL: /editor/14515/

What I’ve Tried So Far

  1. Confirmed the client sends both messages by logging before sending.
  2. Logged path in the Python server to ensure it receives the correct WebSocket connection.
  3. Tried reading messages differently in Python, using:
    while True:
        message = await websocket.recv()
    
  4. Tried adding a small delay (await asyncio.sleep(0.01)) in Python after receiving a message.

Question

Why does the Python WebSocket server miss the second message, while the Node.js implementation works fine? How can I ensure Python properly receives and processes all WebSocket messages?

Upvotes: 0

Views: 23

Answers (0)

Related Questions