写在前面
本笔记所记录的方式来源于 socket.io
官方文档,但是实际测量下来经过这样后还会有问题,最后迫不得已,将 websocket
功能抽出成单独的服务。
注意
截止到目前(2021年11月17日),中文文档和官方文档中都使用了socket.io-redis这个包,但是这个包已经在 6
个月前就声明 deprecated
了,迁移至新的@socket.io/redis-adapter地址了。
实现原理与方式
写不过来了,有空补。
使用redis包
注意
目前 redis
包升级到了 4.x
,官方文档上的写法已经不可以了,官方文档还没有给出新的写法,如果使用这个方案,暂时先使用 redis 3.x
吧(记录于2022年1月11日)。
安装必要包
$ pnpm add @nestjs/websockets @nestjs/platform-socket.io socket.io @socket.io/redis-adapter redis $ pnpm add -D @types/redis点击复制复制失败已复制
编写适配器
建立适配器文件 redis-io.adapter.ts
,写入如下内容:
import { ConfigType } from '@nestjs/config'; import { NestExpressApplication } from '@nestjs/platform-express'; import { IoAdapter } from '@nestjs/platform-socket.io'; import { createAdapter } from '@socket.io/redis-adapter'; import { createClient, RedisClient } from 'redis'; import { ServerOptions } from 'socket.io'; import { RedisConfigRegister } from '../../config/registers/redis.register'; /** socket.io redis 适配器 */ export class RedisIoAdapter extends IoAdapter { constructor(app: NestExpressApplication, redisConfig: ConfigType<typeof RedisConfigRegister>) { super(app); this.pubClient = createClient({ host: redisConfig.common.host, port: redisConfig.common.port }); this.subClient = this.pubClient.duplicate(); } private pubClient: RedisClient; private subClient: RedisClient; createIOServer(port: number, options?: ServerOptions): any { const server = super.createIOServer(port, options); server.adapter(createAdapter(this.pubClient, this.subClient)); return server; } }点击复制复制失败已复制
提示
主要参考 socket.io
的官方文档中redis适配器部分。
使用
在 main.ts
文件中配置,具体参考如下:
…… const app = await NestFactory.create<NestExpressApplication>(AppModule); const redisConfig = app.select(AppModule).get<ConfigType<typeof RedisConfigRegister>>(RedisConfigRegister. KEY); // 使用Redis socket.io适配器 app.useWebSocketAdapter(new RedisIoAdapter(app, redisConfig)); ……点击复制复制失败已复制
使用ioredis包
安装必要包
$ pnpm add @nestjs/websockets @nestjs/platform-socket.io socket.io @socket.io/redis-adapter ioredis点击复制复制失败已复制
编写适配器
建立适配器文件 redis-io.adapter.ts
,写入如下内容:
import { ConfigType } from '@nestjs/config'; import { NestExpressApplication } from '@nestjs/platform-express'; import { IoAdapter } from '@nestjs/platform-socket.io'; import { createAdapter } from '@socket.io/redis-adapter'; import { Cluster } from 'ioredis'; import { ServerOptions } from 'socket.io'; import { RedisConfigRegister } from '../../config/registers/redis.register'; /** socket.io redis 适配器 */ export class RedisIoAdapter extends IoAdapter { constructor(app: NestExpressApplication, redisConfig: ConfigType<typeof RedisConfigRegister>) { super(app); this.pubClient = new Cluster([{ host: redisConfig.common.host, port: redisConfig.common.port }]); this.subClient = this.pubClient.duplicate(); } private pubClient: Cluster; private subClient: Cluster; createIOServer(port: number, options?: ServerOptions): any { const server = super.createIOServer(port, options); server.adapter(createAdapter(this.pubClient, this.subClient)); return server; } } 点击复制复制失败已复制
提示
主要参考 socket.io
的官方文档中redis适配器部分。
使用
在 main.ts
文件中配置,具体参考如下:
…… const app = await NestFactory.create<NestExpressApplication>(AppModule); const redisConfig = app.select(AppModule).get<ConfigType<typeof RedisConfigRegister>>(RedisConfigRegister. KEY); // 使用Redis socket.io适配器 app.useWebSocketAdapter(new RedisIoAdapter(app, redisConfig)); ……