NestJS ws(非Socket.io)WebSocket格式限制能否绕过?求官方文档
绕过NestJS ws适配器的默认消息格式限制
完全可以绕过{event: "eventname", data: {data}}的默认格式限制,NestJS基于ws的WebSocket适配器支持自定义消息解析逻辑,以下是具体实现方式及官方相关说明:
1. 自定义WebSocket适配器
NestJS的WsAdapter是可扩展的,通过继承并重写核心方法,能完全掌控消息的解析流程:
import { WsAdapter } from '@nestjs/platform-ws'; import { WebSocket } from 'ws'; export class CustomWsAdapter extends WsAdapter { bindMessageHandlers( client: WebSocket, handlers: Map<string, (...args: unknown[]) => void>, transform: (data: unknown) => unknown, ) { client.on('message', async (message: Buffer) => { // 按你的固定格式解析原始消息,示例为直接解析JSON对象 const parsedMessage = JSON.parse(message.toString()); // 替换成你实际用来标识事件的字段,比如"type" const eventName = parsedMessage.type; const handler = handlers.get(eventName); if (!handler) return; // 直接传递解析后的完整数据给处理器 await handler(parsedMessage); }); } }
在模块中注册自定义适配器:
import { Module } from '@nestjs/common'; import { CustomWsAdapter } from './custom-ws.adapter'; import { AppGateway } from './app.gateway'; @Module({ providers: [AppGateway], }) export class AppModule { configure(consumer) { consumer.applyWebSocketAdapter(new CustomWsAdapter()); } }
2. 自定义参数装饰器获取原始消息
如果仅需在个别处理器中使用自定义格式,可创建装饰器直接获取原始消息:
import { createParamDecorator, ExecutionContext } from '@nestjs/common'; export const RawMessage = createParamDecorator( (data: unknown, ctx: ExecutionContext) => { const message = ctx.switchToWs().getData(); // 按你的固定格式解析后返回,或直接返回原始内容 return JSON.parse(message.toString()); }, );
在网关中使用:
import { WebSocketGateway, SubscribeMessage } from '@nestjs/websockets'; import { RawMessage } from './raw-message.decorator'; @WebSocketGateway() export class AppGateway { @SubscribeMessage('your-event') handleEvent(@RawMessage() message: any) { // 直接使用固定格式的消息内容 console.log(message); return { status: 'processed' }; } }
官方文档说明
NestJS官方文档明确指出,WebSocket适配器是可定制组件,默认的event/data格式是WsAdapter的内置约定,而非强制要求。开发者可通过扩展适配器或实现WebSocketAdapter接口,自定义消息的序列化、反序列化及分发逻辑,以适配特定格式需求。
文档的「WebSocket - 自定义适配器」章节,详细说明了如何通过继承适配器类,修改消息接收与解析的核心逻辑。
内容的提问来源于stack exchange,提问作者JS_illiterate
相关产品推荐
相关产品推荐

