NestJS 的 Passport 本地策略“验证”方法从未被调用

问题描述 投票:0回答:4

我正在尝试实施 Passport 本地策略,但验证方法不起作用。当我执行

@UseGuards(AuthGuard("local"))
时,它会自动抛出未经授权的异常,而无需通过我编写的验证方法。我不知道我做错了什么,因为文档也是如此。

这是我的 LocalStrategy 课程:

@Injectable()
export class LocalStrategy extends PassportStrategy(Strategy) {
  constructor(
    @InjectRepository(UserRepository) private userRepository: UserRepository,
  ) {
    super();
  }

  async validate(credentials: string, password: string): Promise<User> {
    // this method is never called, I've already did some console.logs
    const user = await this.userRepository.findByCredentials(credentials);

    if (!user) throw new UnauthorizedException('Invalid credentials');

    if (!(await argon2.verify(user.hash, password)))
      throw new UnauthorizedException('Invalid credentials');

    return user;
  }
}

我的AuthModule导入:

@Module({
  imports: [TypeOrmModule.forFeature([UserRepository]), PassportModule],
  controllers: [AuthController],
  providers: [AuthService, LocalStrategy],
})
export class AuthModule {}

使用示例:

  @Post("/login")
  @UseGuards(LocalAuthGuard)
  async login(@Body() loginDto: LoginDto) {
    return this.authService.login(loginDto);
  }
authentication passport.js nestjs passport-local nestjs-passport
4个回答
32
投票

编辑

在花了更多时间研究代码并自己深入研究之后,validate方法必须具有参数

named
username
password
,这并不是事实,它们可以是
bob
alice 
对于所有这些都很重要,但是
 
重要的是你的 req.body 有两个属性
username
password
。如果您没有
req.body.username
req.body.password
,那么您将永远无法进入
validate
班的
LocalStrategy


validate

方法

must
具有参数username
password
参数must与传递给构造函数中usernameField
passwordField
super()
值相匹配。如果它们不匹配,则不会调用
validate
方法。我认为这是因为 Nest 调用了
validate(...args)
,但我不能 100% 确定。
    


0
投票

添加有效负载对象很重要

async validate(payload: {email: string, UserId: number, role: string}) { return { userId: payload.UserId, email:payload.email, role:payload.role };

}

我这样签署令牌:

async signToken(userId: number, email: string, role: string): Promise<{access_token:string}>{ const payload = { UserId: userId, email: email, role: role } console.log(payload) const secret = process.env.JWT_SECRET const token = await this.JwtService.signAsync(payload, { expiresIn: "1d", secret: secret })



0
投票

{ "email":"foo", "password":"crypto" }

enter image description here


-1
投票
LocalAuthGuard

课程。您需要使用此类创建一个文件,然后..

import { Injectable } from '@nestjs/common';
import { AuthGuard } from '@nestjs/passport';

@Injectable()
export class LocalAuthGuard extends AuthGuard('local') {}

然后将使用当地警卫。

© www.soinside.com 2019 - 2024. All rights reserved.