SubcribeMessage 装饰器不会触发事件 'message'

SubcribeMessage decorator doesn't trigger on event 'message'

我正在我的 NestJS 后端设置一个 WebSocket 服务器,当我尝试订阅默认的 'message' 事件类型时,方法 handleMessage() 没有被触发。

然而 listenForMessages() 方法有效(在服务器初始化后触发)。有谁知道为什么装饰器 @SubscribeMessage('message') 不起作用?

@WebSocketGateway()
export class AppWebsocketGateway implements OnGatewayInit, OnGatewayDisconnect {
  private clientIds = new Map<string, string>();
  // @ts-ignore
  @WebSocketServer() server: Server;
  private logger: Logger = new Logger('WebsocketGateway');

  constructor(private readonly evseService: EvseService) {
  }

  listenForMessages() {
    this.server.on('connection', (ws) => {
      ws.on('message', (e) => {
        console.log(e);
      });
    });
    this.logger.log('message received');
  }


  @SubscribeMessage('message')
  handleMessage(@ConnectedSocket() client: any, payload: any): void {
    this.logger.log('I received a message from the client!');
    this.server.emit('msgToClient', payload);
  }

  afterInit(server: Server) {
    this.logger.log('Init');
    this.listenForMessages();
  }

  handleDisconnect(@ConnectedSocket() client: any) {
    this.logger.log(`Client disconnected: ${client.id}`);
  }
}
//@SubscribeMessage('message') will look for the message that are in the format :
{
  event:'message',
  data: {someData} // Whatever in the data field will be the payload in 
                   //handleMessage()
}

// Another example 
// @SubscribeMessage('get_profile') will look for messages in the format : 

{
  event:'get_profile',
  data: {someData} // Whatever in the data field will be the payload in 
                   //handleMessage()
}

那么为什么@SubscribeMessage('message')需要这样的格式呢?好吧,为了利用 NestJS 的特性,如拦截器、管道等。如果你为传入消息(事件)实现这样的格式,将来,即使你将库更改为 [=27,你也不必更改处理程序逻辑=] 或 μWebsocket.js 或您自己的 websockets 实现。您只需要实现自己的自定义 websocket 适配器。

简而言之,即使底层技术发生变化,NestJS 也能确保您的代码保持一致。

listenForMessages() 直接在服务器上附加一个侦听器。这是一种特定于库的方法,如果您决定将库更改为:比如 socket.io.

,则需要更改所有侦听器逻辑

ws.on('message', callback);,将记录套接字发送的任何内容(根据您在 listenForMessages() 中的代码),忽略格式,即:您可以发送字符串、缓冲区、JSON、等.. 但对于 @SubscribeMessage(<event>) 它必须采用以下格式 :

{
event : <event>,
data : <any>, // Can be string, number, object, buffer, whatever you want
}

ws - 是连接到服务器的套接字。