I have a few decorators that when called, I want to setMetadata to use it in my logging, In my controller, I have these:
@Post("somePath")
@Permission("somePermission")
@UseGuards(JwtAuthGuard)
@HttpCode(200)
@Grafana(
"endpoint",
"functionalmap"
)
async getSubscriptionFromPwebFormFilter(
@Body(ValidationPipe) someDto: someDtoType
): Promise<ISuccessResponse> {
// some logic
}
In my decorators I want to set some data into the metadata to use in my logging inteceptor,
Grafana decorator:
export const Grafana = (functionalMap: string, endpoint: string) =>
applyDecorators(
SetMetadata("endpoint", endpoint),
SetMetadata("functionalMap", functionalMap)
);
AuthGuard decorator:
@Injectable()
export class JwtAuthGuard extends AuthGuard("jwt") {
constructor(
private readonly reflector: Reflector,
private readonly someService: SomeService
) {
super();
}
public async canActivate(context: ExecutionContext): Promise<boolean> {
const role = this.reflector.get<string>("permission", context.getHandler());
const request = context.switchToHttp().getRequest();
const { valueToLog } = request.body;
const jwtToken = request.headers.authorization;
console.log("check value exist", valueToLog);
SetMetadata("valueToLog", valueToLog);
}
Now, in my logging interceptor, I am getting all the values of the metadata this way:
@Injectable()
export default class LoggingInterceptor {
constructor(private readonly reflector: Reflector) {}
intercept(context: ExecutionContext, next: CallHandler) {
const executionStart = Date.now();
return next.handle().pipe(
tap((responseData) => {
const response = context.switchToHttp().getResponse<ServerResponse>();
const { statusCode } = response;
const valueToLog = this.reflector.get(
"valueToLog",
context.getHandler()
); // this is undefined
const endpoint = this.reflector.get("endpoint", context.getHandler()); // this have value
const functionalMap = this.reflector.get(
"functionalMap",
context.getHandler()
); // this have value
...
// some logic
})
);
}
}
In my case, the value of endpoint and functionalMap can be retrieved from the reflector, however, valueToLog is appearing as undefined,
Is setting of metadata not working for auth guard decorator?
I will be using the term "Decorator" in this explanation so I will first define it.
Decorators are functions that accept information about the decorated declaration.
Ex:
function ClassDecorator(target: typeof DecoratedClass) {
// do stuff
}
// it can then be used like this
@ClassDecorator
class DecoratedClass {}
when calling @SetMetadata(key, value)
it returns a decorator. Functions like SetMetadata
are referred to as Decorator Factories .
Decorators use the form @expression, where expression must evaluate to a function that will be called at runtime with information about the decorated declaration.
In your example you called SetMetadata("valueToLog", valueToLog)
. This returns a decorator. Decorators must be called with information about the decorated declaration. To actually attach the metadata you can do something like this:
SetMetadata("valueToLog", valueToLog)(context.getHandler());
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.