node.jshttpsocketswebsocketnode-websockets

How to pass WS connection socket from parent process to child process


There is an example here: https://github.com/websockets/ws/issues/154

In the parent we have:

const cp = require('child_process');
const http = require('http');

const child = cp.fork('child.js');
const server = http.createServer();

server.on('upgrade', (request, socket) => {
  child.send({ headers: request.headers, method: request.method }, socket);
});

server.listen(8080);

and in the child process we have:

const WebSocket = require('ws');

const wss = new WebSocket.Server({ noServer: true });

process.on('message', (request, socket) => {
  wss.handleUpgrade(request, socket, undefined, (ws) => {
    ws.send('foo');
  });
});

my question: for my use-case, I would like the websocket server in the parent process, but allow the child process to write directly to the sockets of the WSS connections, is this possible?


Solution

  • While it is at least on UNIX systems possible to send a plain TCP socket using IPC to another process, this is not possible for TLS connections as needed for WSS. This is because the TLS state is inside the user space of the process which has done the TLS handshake. This state cannot be simply serialized and transferred to another process since it is intertwined with various structures in the SSL library using pointers into the memory of the parent process.

    If instead the TLS is not terminated in nodejs but (as common) in some reverse proxy in front of nodejs, then one has only to deal with plain TCP in which case propagating the socket to another process and doing the Websockets handshake inside this process is feasible.