Best/proper way to share a single WebSocket connection across multiple tabs

2.9k views Asked by At

How does one share a single WebSocket connection across multiple browser tabs?

I'm aware of multiple questions/posts suggesting SharedWorker. However, it is not a viable solution due to the poor adoption of SharedWorker (only 35% globally according to Can I use at the time of writing), not to mention it has been dropped in Safari.

I have implemented a working version using SerivceWorker, which has some SharedWorker's capability, to share a single connection across tabs. Unfortunately during testing I realized that ServiceWorker can be killed/stopped by the browser, especially when the devtool is not opened. I'm also aware of some workaround to prevent this behaviour, such as pinging the ServiceWorker periodically. I would like to ask whether there is a proper way to handle this.

1

There are 1 answers

1
Newbie On BEST ANSWER

Unfortunately is not a straightforward task. But because many browsers are limiting the number of connections to the same origin it is an issue I faced a few times.

Sharing a WebSocket

Assuming you are forced to share the connection and other options are not feasible, these are the possibilities:

  1. SharedWorker (33.17% support). Allows you to share the connection as you already discovered.
  2. BroadcastChannel (91.23% support). Allows you to communicate between tabs.
  3. SessionStorage (97.25%). Allows you to communicate between tabs. This is a bit of a hack see but worked well for me.

The trick for 2 and 3 is that you will have only one tab holding the WS connection and sharing its usage with the other tabs through the communication channel. The trickiest part is when the "main" tab is closed; you will need to elect another tab to open the connection.

Please note that both 2 and 3 are subject to buffering delays and additional delays during the change of the "main" tab. SharedWorker also has its pitfalls. Thus none of the solutions are suitable for high-speed real-time applications (like a game). If you need a real-time solution or just one that is easier to implement go for the following option:

Unsollecitated option

If you just need to work around the connection limitation, this is a cheat that works flawlessly: create a domain like *.wss.example.com that points to the same server and then trick the browser by randomly generating the domain on each tab (something like 3af893.wss.example.com, a6a589.wss.example.com, ...). With this pattern, you can make unlimited connections. Just remember to setup solid CORS policies as this pattern exposes you to huge amounts of malicious traffic otherwise.

Despite implementing many of the above mentioned solutions, I ended using this one in production as it prooved to be more stable and reliable. This solution also works for Server Side Events (SSE).

Edit 1

Many of the mentioned options are discussed here Sharing websocket across browser tabs? as mentioned by Eskandar