'SetMetadata changes guard execution order nestjs

when i include @Permissions('read') my acessGuard stops receiving JWT info, @Permissions simply sets metadata (code below)

export const Permissions = (...permissions: string[]) => SetMetadata('permissions', permissions);

certificate.controller.ts:

@UseGuards(LocalAuthGuard, AccessGuard)
@Controller('certificate')
export class CertificateController {  
    constructor(private certificateService: CertificateService) {}
  
    @Get()
      @Permissions('read') // removing this req.user is filled with jwt data
      async getCertificates(@CurrentUser() user: User) {
        return this.certificateService.getCertificates(user.id);
    }

Bellow is the a guard which will control if the user has permission to execute the action

export class AccessGuard implements CanActivate {
   constructor(
     private readonly accessService: AccessService,
     @Inject('Reflector') private readonly reflector: Reflector,
   ) {}
    
     async canActivate(context: ExecutionContext): Promise<boolean> {
        const permissions = this.reflector.get<enAccessPoliciesModules[]>(
          'permissions',
          context.getHandler(),
        );
    
        console.log(context.switchToHttp().getRequest().user); // when i include @Permission('read') this line is undefined 
     }
}

i guess this has something to do with the execution order, at first it is LocalAuthGuard -> AccessGuard but after setting metadata it becomes AccessGuard -> LocalAuthGuard, that way request.user is undefined.

Any workarounds for that?



Solution 1:[1]

I found the problem

@Module({
  imports: [CoreModule, AuthModule, AccessPoliciesModule, CertificateModule],
  controllers: [AppController],
  providers: [
    AppService,
    { provide: APP_GUARD, useClass: AccessPoliciesGuard },
  ],
})
export class AppModule {}

as i was trying to fix an dependency error so i added that APP_GUARD inside appModule providers. I realized the guard was being executed 2 times, the first time it didn't had the token because it was a global guard, and i guess i has priority?

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 Kakiz