Sam*_*e11 7 node.js passport.js nestjs
当涉及到身份验证/授权过程时,我很难弄清楚 NestJS 和 PassportJS 的组合,而且我是一种在开发时不喜欢魔法的开发人员。
基本上,我的目标是了解 AuthGuard 如何知道项目中正在实施的 Passport 策略,它可以是本地策略,也可以是任何其他策略,例如 JWT 策略。我有两个模块AuthModule和UserModule,这就是AuthService的样子:
@Injectable()
export class AuthService {
constructor(private usersService: UsersService){}
async validateUser(username: string, password: string): Promise<any> {
const user = await this.usersService.findOne(username);
if (user && user.password === password) {
const {password, ...result} = user
return result
}
return null
}
}
Run Code Online (Sandbox Code Playgroud)
用户服务:
import { Injectable } from '@nestjs/common';
export type User = any;
@Injectable()
export class UsersService {
private readonly users = [
{
userId: 1,
username: 'John Marston',
password: 'rdr1',
},
{
userId: 2,
username: 'Arthur Morgan',
password: 'rdr2',
},
]
async findOne(username: string): Promise<User | undefined> {
return this.users.find(user => user.username === username)
}
}
Run Code Online (Sandbox Code Playgroud)
安装 Passport 和 NestJS 的软件包后,我导入了PassportModule并实现了LocalStrategy,并将该策略作为提供程序导入到 AuthModule中
本地策略:
@Injectable()
export class LocalStrategy extends PassportStrategy(Strategy) {
constructor(private authService: AuthService) {
super()
}
async validate(username: string, password: string): Promise<any> {
const user = await this.authService.validateUser(username, password);
if (!user) {
throw new UnauthorizedException();
}
return user;
}
}
Run Code Online (Sandbox Code Playgroud)
@Module({
imports: [UsersModule, PassportModule],
providers: [AuthService, LocalStrategy]
})
export class AuthModule {}
Run Code Online (Sandbox Code Playgroud)
import { Controller, Post, Request, UseGuards } from '@nestjs/common';
import { AuthGuard } from '@nestjs/passport';
@Controller()
export class AppController {
@UseGuards(AuthGuard('local'))
@Post('login')
async login(@Request() req) {
return req.user;
}
}
Run Code Online (Sandbox Code Playgroud)
直到这一部分我都明白了。我也明白我们如何获取 req.user 对象等,但我不明白 AuthGuard 如何知道我们实施了 Passport 本地策略。它是否会查看文件(抱歉,如果这么说很愚蠢)并找到我们导入 PassportModule 的位置以及我们实现LocalStrategy 的位置,因为该类扩展了 PassportStrategy 类,但同样重要的是,是从 Passport-local 导入的。
我确实知道AuthGuard是一种特殊类型的 Guard,但我不确定我是否理解正确。
我有一篇关于此的相当好的文章,但也将其放在 StackOverflow 上:
Strategy包中的每个属性passport-*都有一个name属性,即策略的名称。因为passport-local那name是local。因为passport-jwt,那个名字是'jwt'。这并不总是一一对应,但每个包裹都应记录其护照名称。passport.use()这是传递给和的名称passport.authenticate()。passport.use通过类中的一些巧妙的代码调用PassportStrategy来@nestjs/passport将策略注册到 Passport 中,并在使用通过 Passport 模块的选项或通过 mixin 的参数设置的全局默认值的passport.authenticate内部进行调用,如代码示例中所示。AuthGuard()local