Node.js lightweight WebSocket distributed framework: an open source record!

In the process of developing a casual real-time game, I used socket.io at first , but its compatibility issues on native platforms were a headache. And the bloated framework, for me, using it is more about “adapting it” rather than “using it to solve problems”. Later, I switched to native WebSocket and used the ws module of Node.js on the server side. Although the communication is low-level enough and provides great flexibility, the functions of both the client and the server are extremely basic. Heartbeat mechanism, disconnection reconnection, message callback, room management…all of these need to be encapsulated by myself.

At the same time, Node.js’s single-threaded, memory-constrained, and GC characteristics may become bottlenecks at high concurrency, raising doubts about whether it can handle the “massive online player” scenario.

Therefore, I decided to build a simple and efficient WebSocket distributed framework myself, which can retain the flexibility of native WebSocket to the greatest extent and solve the pain points of “native flexibility but need to be expanded by oneself, unable to focus on the business layer” and “standalone is easy to use but distributed is hard to start with”. It encapsulates basic functions such as heartbeat mechanism, disconnection reconnection, event callback, room management, etc. It fully complies with the WebSocket protocol standard, does not rely on other upper-level frameworks, and keeps the operation logic transparent and controllable. At the same time, it breaks the limitations of Node.js on multi-process and distributed deployment. Whether it is releasing multi-core performance or deploying across physical machines, it can collaborate naturally and switch seamlessly. The message delivery of stand-alone and distributed machines maintains the same logic, and the stand-alone mode can be rolled back with one click when distribution is not needed. At the same time, it is also a lightweight cross-service event channel, suitable for a wider range of service-to-service communication scenarios.

The framework contains only two modules to ensure lightweight:
WebSocketCrossServerAdapter (server communication core)

A communication adapter designed for distributed architecture, supporting server-side event broadcasting, cross-server messaging, room management and other functions, suitable for game services, real-time systems, communication between microservices and other scenarios.
Main capabilities include:
• Cross-node event communication, support for callback/Promise
• Redis distributed support: dynamic addition of nodes, full channel subscription, compressed transmission
• Distributed room broadcasting, client tracking, global user statistics
• Events prioritize local response and automatically route target nodes
• Support the following multi-granularity message sending capabilities (independent of which node is connected):
○ Global broadcast (all nodes, all clients)
○ Single client sending (precise positioning across nodes)
○ SocketId batch sending
○ Distributed room broadcast

WebSocketConnector (client connection manager)

A lightweight and concise WebSocket client class, suitable for any platform based on the standard WebSocket protocol, such as browsers, Node.js, Electron, React Native, mini-programs, Cocos Creator, etc. It has built-in heartbeat mechanism, disconnection reconnection, event callback, delayed feedback and other functions.

My Vision:

I hope that when developers use this framework, they can focus on gameplay and business logic, rather than being bothered by infrastructure such as heartbeat, disconnection reconnection, and cross-server communication. Distributed should not be a lofty concept. Whether it is single-machine development or multi-server deployment, it should be able to switch with one click without changing any logic.
Even if it is a game developed by an individual, as long as you know JavaScript, you can easily build a WebSocket real-time system without relying on the backend team, and you can independently complete the front-end and back-end joint debugging, which really improves development efficiency.

In order to make it understandable and useful to others, I have to think from the perspective of others and polish it repeatedly, from code design to document writing. It is not enough to just “make it run”, but “others can understand it at a glance”. The process is indeed tiring, but this is the meaning of open source.

After many difficulties, I finally completed the open source release yesterday and posted an introduction article on a foreign technical forum. Soon I received a lot of positive feedback, but also received negative voices - some people even complained that the room mechanism is “only suitable for chat scenarios”. I just want to say that the room is just an abstract concept of logical grouping, broadcasting unit, and authority domain division, and it has nothing to do with chat.
Despite this, judging from the GitHub background data and npm downloads, there were dozens of downloads in one night, which also illustrates a fact: those who don’t need it are picking bones, and those who need it have already started to try it quietly. This is also a kind of motivation.

All documents provide bilingual support in Chinese and English. The source code structure is simple, and the core contains only two class files, which is easy to read and expand. I also explain the design ideas and logic in detail in the document.

Distributed scenarios are very diverse, welcome to test, any ideas or questions, feel free to communicate!
GitHub address: https://github.com/LiuYiSong/websocket-cross-server-adapter

1 Like

My experience with tsrpc open source is just like what you said, I use it to solve problems, not to adapt it. tsrpc is really easy to use. I am also going to clone it and take a closer look, and compare the experience with tsrpc.

I need two people to help me with my project Q941119950 If you have free time to take orders, please Q me