Ad

Heroku Returns 400 Bad Request Response (Socket.IO Node.js)

- 1 answer

A 400 Bad Request is returned every time Socket.IO connects to my Heroku app. How do I fix this?

I have a Node.js web app that uses Socket.IO. There are no problems while in local development but when I deployed the app to Heroku, every socket.io connection returns a 400 Bad Request. I've tried manually setting the transport method to websocket, polling, and both but it still doesn't work. I've also turned on session affinity for my dyno.

In the server I have

const app = express();
const server = http.createServer(app);
const io = socketIO(server);

const namespace = io.of('/client-web-app');

the client connects through

const socket = io('/client-web-app')

as you ordinarily do.

Browser console logs the following:

polling-xhr.js:269 POST https://<app-name>.herokuapp.com/socket.io/?EIO=3&transport=polling&t=Mo5GHwF&sid=7Pn_tN47tE2NqFKMAAAc 400 (Bad Request)

there is also a GET and websocket versions of the request

Meanwhile, Heroku logs the following:

 at=info method=POST path="/socket.io/?EIO=3&transport=polling&t=Mo5GjRq&sid=wSTQhI8NQRpLbb3xAAAm" host=<app-name>.herokuapp.com request_id=da83df98-0522-4e0a-b0cc-fdbc3304b7f8 fwd="110.54.138.89" dyno=web.1 connect=0ms service=2ms status=400 bytes=296 protocol=https
2019-08-12T09:57:28.339289+00:00 app[web.1]: device disconnected
2019-08-12T09:57:28.628468+00:00 heroku[router]: at=info method=GET path="/socket.io/?EIO=3&transport=polling&t=Mo5GjRs&sid=wSTQhI8NQRpLbb3xAAAm" host=<app-name>.herokuapp.com request_id=99ba8299-6f8a-448f-a8ce-d0b34b4a062f fwd="110.54.138.89" dyno=web.1 connect=0ms service=2ms status=400 bytes=228 protocol=https

replaced my actual application name with <app-name> for reasons.

Ad

Answer

Found a solution to my own problem. Posting here in case anyone else is having the same problem as mine. Just explicitly state that you going to use websocket as your transport.

So in your socket.io server:

const app = express();
const server = http.createServer(app);
const io = socketIO(server, {transports: ['websocket']});

and in your socket.io client:

const socket = io('/client-web-app', {transports: ['websocket']});

It seems Heroku only supports websocket as a socket.io transport.

Ad
source: stackoverflow.com
Ad