1 year ago
#141614
J4N
How to use guards with NestJs gateway(web sockets)?
In my NestJS API, I'm JWT token, stored in a cookie to authenticate my users.
The user will have to call my login controller:
@UseGuards(LocalAuthenticationGuard)
@Post('login')
async logIn(@Req() request: RequestWithUser) {
const { user } = request;
const cookie = this.authenticationService.getCookieWithJwtToken(user._id);
request.res?.setHeader('Set-Cookie', cookie);
return user;
}
the LocalAuthenticatedGuard
authenticate the username-password and fill the request with the user, then the cookie is provided to the client and will be verified against any further request with my other guard:
@Injectable()
export default class JwtAuthenticationGuard extends AuthGuard('jwt') {}
and its associated strategy:
@Injectable()
export class JwtStrategy extends PassportStrategy(Strategy) {
constructor(
private readonly configService: ConfigService,
private readonly userService: UsersService,
) {
super({
jwtFromRequest: ExtractJwt.fromExtractors([
(request: Request) => {
return request?.cookies?.Authentication;
},
]),
secretOrKey: configService.get('JWT_SECRET'),
});
}
async validate(payload: TokenPayload) {
return this.userService.getById(payload.userId);
}
}
this work perfectly for my post/get methods.
But now I've some needs with web socket, so I tried the following:
@WebSocketGateway({
cors: {
origin: '*',
},
})
export class PokerGateway
implements OnGatewayInit, OnGatewayConnection, OnGatewayDisconnect
{
@WebSocketServer() server: Server;
private logger: Logger = new Logger('AppGateway');
@SubscribeMessage('msgToServer')
handleMessage(client: Socket, payload: string): void {
this.logger.log(`Client ${client.id} sent message: ${payload}`);
this.server.emit('msgToClient', payload);
}
afterInit(server: Server) {
this.logger.log('Init');
}
handleDisconnect(client: Socket) {
this.logger.log(`Client disconnected: ${client.id}`);
}
@UseGuards(JwtAuthenticationGuard)
handleConnection(
client: Socket,
@Req() req: RequestWithUser,
...args: any[]
) {
this.logger.log(`Client connected: ${client.id}`);
this.logger.log(client.handshake.query['poker-id']);
this.logger.log(req);
}
}
but:
- even when I'm not connected, the connection is established
- The user isn't set to my request
What would be:
- the way to use my auth guard and receive the matching user?
- For the further messages, should I just keep a dictionary of client.id <--> my users in the gateway? Or is there a way to also receive the user at each message?
authentication
websocket
nestjs
nestjs-jwt
nestjs-gateways
0 Answers
Your Answer