在 NestJS 中有什么方法可以将数据从 Guards 传递到控制器吗?
In NestJS is there any way to pass data from Guards to the controller?
所以我目前在我的组织中广泛使用 NestJS。出于身份验证的目的,我们使用自己的守卫。所以我的问题是,除了 expressjs 的 response.locals
之外,如果有任何方法可以将数据从守卫传递到控制器,谁能指导我?这造成了对框架的硬依赖,我现在不想这样。
TIA。
将数据从 Guard 传递到 Controller 的唯一可能方法是将数据附加到请求的字段或使用某种元数据反射,这可能变得比它的价值更具挑战性。
在你的守卫中,你可以有一个 canActivate
函数,比如
canActivate(context: ExecutionContext): boolean | Promise<boolean> | Observable<boolean> {
const req = context.switchToHttp().getRequest();
if (/* some logic with req */) {
req.myData = 'some custom value';
}
return true;
}
然后在您的控制器中,您可以拉 req.myData
并取回 some custom value
字符串。
您可以创建自定义装饰器来获取数据,而不是使用 Guard:
export const Authorization = createParamDecorator((_, request: any) => {
const { authorization: accessToken } = request.headers;
try {
const decoded = jwt.verify(accessToken, process.env.JWT_HASH);
return pick(decoded, 'userId');
} catch (ex) {
throw new InvalidToken();
}
});
export interface AuthUser {
userId: string;
}
然后像这样传递给你的控制器:
@Post()
createFeedback(
@Body() body: FeedbackBody,
@Authorization() user: AuthUser,
): Promise<Feedback> {
body.userId = user.userId;
return this.feedbackService.feedback(body, user);
}
这可以充当守卫,因为当你的令牌无效时,它会抛出异常
正如其他人所说,您可以在守卫的请求对象上传递数据,但通过 @Req 装饰器接收它们并不花哨,特别是如果您对请求对象没有任何其他用途。您可以创建一个自定义装饰器,它将检索您想要的数据并将它们注入任何控制器
所以我目前在我的组织中广泛使用 NestJS。出于身份验证的目的,我们使用自己的守卫。所以我的问题是,除了 expressjs 的 response.locals
之外,如果有任何方法可以将数据从守卫传递到控制器,谁能指导我?这造成了对框架的硬依赖,我现在不想这样。
TIA。
将数据从 Guard 传递到 Controller 的唯一可能方法是将数据附加到请求的字段或使用某种元数据反射,这可能变得比它的价值更具挑战性。
在你的守卫中,你可以有一个 canActivate
函数,比如
canActivate(context: ExecutionContext): boolean | Promise<boolean> | Observable<boolean> {
const req = context.switchToHttp().getRequest();
if (/* some logic with req */) {
req.myData = 'some custom value';
}
return true;
}
然后在您的控制器中,您可以拉 req.myData
并取回 some custom value
字符串。
您可以创建自定义装饰器来获取数据,而不是使用 Guard:
export const Authorization = createParamDecorator((_, request: any) => {
const { authorization: accessToken } = request.headers;
try {
const decoded = jwt.verify(accessToken, process.env.JWT_HASH);
return pick(decoded, 'userId');
} catch (ex) {
throw new InvalidToken();
}
});
export interface AuthUser {
userId: string;
}
然后像这样传递给你的控制器:
@Post()
createFeedback(
@Body() body: FeedbackBody,
@Authorization() user: AuthUser,
): Promise<Feedback> {
body.userId = user.userId;
return this.feedbackService.feedback(body, user);
}
这可以充当守卫,因为当你的令牌无效时,它会抛出异常
正如其他人所说,您可以在守卫的请求对象上传递数据,但通过 @Req 装饰器接收它们并不花哨,特别是如果您对请求对象没有任何其他用途。您可以创建一个自定义装饰器,它将检索您想要的数据并将它们注入任何控制器