0% found this document useful (0 votes)
10 views

docs-nestjs-com-websockets-adapter...

The document discusses the implementation of WebSocket adapters in a platform-agnostic manner, specifically focusing on the WebSocketAdapter interface and its methods. It details how to extend the socket.io functionality using a RedisIoAdapter for load-balanced instances and introduces the WsAdapter for faster WebSocket communication. Additionally, it provides guidance on setting up custom adapters and message parsing for different message formats.

Uploaded by

dharmendra
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
10 views

docs-nestjs-com-websockets-adapter...

The document discusses the implementation of WebSocket adapters in a platform-agnostic manner, specifically focusing on the WebSocketAdapter interface and its methods. It details how to extend the socket.io functionality using a RedisIoAdapter for load-balanced instances and introduces the WsAdapter for faster WebSocket communication. Additionally, it provides guidance on setting up custom adapters and message parsing for different message formats.

Uploaded by

dharmendra
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 7

Search dark_mode

Adapters
The WebSockets module is platform-agnostic, hence, you can bring your
own library (or even a native implementation) by making use of
WebSocketAdapter interface. This interface forces to implement few
Build your website for
methods described in the following table: just $3.88/mth. More
value and performance
with Namecheap.
ADS VIA CARBON

create

Creates a socket instance based on passed arguments

bindClientConnect

Binds the client connection event

bindClientDisconnect

Binds the client disconnection event (optional*)

bindMessageHandlers

Binds the incoming message to the corresponding message handler

close
Terminates a server instance

Extend socket.io
The socket.io package is wrapped in an IoAdapter class. What if you would like to enhance the basic
functionality of the adapter? For instance, your technical requirements require a capability to
broadcast events across multiple load-balanced instances of your web service. For this, you can
extend IoAdapter and override a single method which responsibility is to instantiate new socket.io
servers. But first of all, let's install the required package.

WARNING
To use socket.io with multiple load-balanced instances you either have to disable polling by
setting transports: ['websocket'] in your clients socket.io configuration or you have to
enable cookie based routing in your load balancer. Redis alone is not enough. See here for more
information.

$ npm i --save redis socket.io @socket.io/redis-adapter

Once the package is installed, we can create a RedisIoAdapter class.

import { IoAdapter } from '@nestjs/platform-socket.io'; content_copy


import { ServerOptions } from 'socket.io';
import { createAdapter } from '@socket.io/redis-adapter';
import { createClient } from 'redis';

export class RedisIoAdapter extends IoAdapter {


private adapterConstructor: ReturnType<typeof createAdapter>;

async connectToRedis(): Promise<void> {


const pubClient = createClient({ url: `redis://localhost:6379` });
const subClient = pubClient.duplicate();
await Promise.all([pubClient.connect(), subClient.connect()]);

this.adapterConstructor = createAdapter(pubClient, subClient);


}

createIOServer(port: number, options?: ServerOptions): any {


const server = super.createIOServer(port, options);
server.adapter(this.adapterConstructor);
return server;
}
}

Afterward, simply switch to your newly created Redis adapter.

const app = await NestFactory.create(AppModule); content_copy


const redisIoAdapter = new RedisIoAdapter(app);
await redisIoAdapter.connectToRedis();

app.useWebSocketAdapter(redisIoAdapter);

Ws library
Another available adapter is a WsAdapter which in turn acts like a proxy between the framework and
integrate blazing fast and thoroughly tested ws library. This adapter is fully compatible with native
browser WebSockets and is far faster than socket.io package. Unluckily, it has significantly fewer
functionalities available out-of-the-box. In some cases, you don't necessarily need them though.

HINT
ws library does not support namespaces (communication channels popularised by
socket.io ). However, to somehow mimic this feature, you can mount multiple ws servers on
different paths (example: @WebSocketGateway({ path: '/users' }) ).

In order to use ws , we firstly have to install the required package:


$ npm i --save @nestjs/platform-ws

Once the package is installed, we can switch an adapter:

const app = await NestFactory.create(AppModule); content_copy


app.useWebSocketAdapter(new WsAdapter(app));

HINT
The WsAdapter is imported from @nestjs/platform-ws .

The wsAdapter is designed to handle messages in the { event: string, data: any } format. If
you need to receive and process messages in a different format, you'll need to configure a message
parser to convert them into this required format.

const wsAdapter = new WsAdapter(app, { content_copy


// To handle messages in the [event, data] format
messageParser: (data) => {
const [event, payload] = JSON.parse(data.toString());
return { event, data: payload };
},
});

Alternatively, you can configure the message parser after the adapter is created by using the
setMessageParser method.

Advanced (custom adapter)


For demonstration purposes, we are going to integrate the ws library manually. As mentioned, the
adapter for this library is already created and is exposed from the @nestjs/platform-ws package as a
WsAdapter class. Here is how the simplified implementation could potentially look like:

ws-adapter.ts JS

import * as WebSocket from 'ws'; content_copy


import { WebSocketAdapter, INestApplicationContext } from '@nestjs/common';
import { MessageMappingProperties } from '@nestjs/websockets';
import { Observable, fromEvent, EMPTY } from 'rxjs';
import { mergeMap, filter } from 'rxjs/operators';

export class WsAdapter implements WebSocketAdapter {


constructor(private app: INestApplicationContext) {}

create(port: number, options: any = {}): any {


return new WebSocket.Server({ port, ...options });
}

bindClientConnect(server, callback: Function) {


server.on('connection', callback);
}

bindMessageHandlers(
client: WebSocket,
handlers: MessageMappingProperties[],
process: (data: any) => Observable<any>,
) {
fromEvent(client, 'message')
.pipe(
mergeMap(data => this.bindMessageHandler(data, handlers, process)),
filter(result => result),
)
.subscribe(response => client.send(JSON.stringify(response)));
}

bindMessageHandler(
buffer,
handlers: MessageMappingProperties[],
process: (data: any) => Observable<any>,
): Observable<any> {
const message = JSON.parse(buffer.data);
const messageHandler = handlers.find(
handler => handler.message === message.event,
);
if (!messageHandler) {
return EMPTY;
}
return process(messageHandler.callback(message.data));
}

close(server) {
server.close();
}
}

HINT
When you want to take advantage of ws library, use built-in WsAdapter instead of creating your
own one.

Then, we can set up a custom adapter using useWebSocketAdapter() method:

main.ts JS

const app = await NestFactory.create(AppModule); content_copy


app.useWebSocketAdapter(new WsAdapter(app));

Example
A working example that uses WsAdapter is available here.

Support us
Nest is an MIT-licensed open source project. It can grow thanks to the support by these awesome
people. If you'd like to join them, please read more here.

Principal Sponsors

Sponsors / Partners

Become a sponsor

Join our Newsletter


Subscribe to stay up to date with the latest Nest updates, features, and videos!

Email address..

Copyright © 2017-2025 MIT by Kamil Mysliwiec design by Jakub Staron


Official NestJS Consulting Trilon.io hosted by Netlify

You might also like