I'm making a logging interceptor to log every http calls of an API,In happy path everything works fine but when I throw an exception I'm getting in Postman a 200 status from thrown exception (with status 400) from the controller and passed through the interceptor. I've read this and use it in interceptor class but I tried some way and I'm getting differents errors, How can I get an approach that I could use to throw the status that I need and also passing through the interceptor?. here is my interceptor and the exception class i'm trying to use from documentation:
@Injectable()
export class LogsInterceptor<T> implements NestInterceptor<T> {
constructor(
private logService: LogsService,
private jwtService: JwtService,
) {}
intercept(
context: ExecutionContext,
next: CallHandler<any>,
): Observable<any> {
const request = context.switchToHttp().getRequest();
let responseStatus = context.switchToHttp().getResponse();
let log: ILogModel;
let id: number;
let args: any = context.getArgs()[0];
console.log('before');
return next.handle().pipe(
map(async (data) => {
id = this.setId(args, id, data);
log = {
ip: args.hostname,
id,
tipo: args.method,
path: args.originalUrl,
query: args.query,
params: args.params,
body: args.body,
token: args.headers.authorization,
response: data,
statuscode: responseStatus.statusCode,
};
let idT: number = 0;
idT = await this.logRequest(log);
console.log(args.route.path);
let respuestaF = {};
if (
args.route.path == '/cards/:pan' ||
args.route.path == '/cards/:pan/paymentRequest'
) {
delete data[0].code;
delete data[0].solicitud;
respuestaF = {
requestId: idT,
message: data[0].message,
companyid: data[0].companyid,
expirationdate: data[0].expirationdate,
licenseplate: data[0].licenseplate,
};
} else {
respuestaF = {
requestId: idT,
data,
};
}
console.log('after');
return respuestaF;
}),
catchError(async (error: any) => {
console.log(request.statusCode);
console.log(responseStatus.statusCode);
id = this.setId(args, id, error);
log = {
ip: args.hostname,
id,
tipo: args.method,
path: args.originalUrl,
query: args.query,
params: args.params,
body: args.body,
token: args.headers.authorization,
response: error,
statuscode: error.status,
};
let idT: number = 0;
idT = await this.logRequest(log);
let respuestaF = {
requestId: idT,
error,
};
// if (error instanceof HttpException) {
// console.log('httpexcpcion');
// return throwError(
// () => new HttpException(respuestaF, HttpStatus.BAD_REQUEST),
// );
// }
console.log(log);
console.log(responseStatus.statusCode);
console.log('entrado por error');
return respuestaF;
}),
);
}
}
Here's how it looks the response, status 200 and in the body the messages of my thrown exception:
You can achieve an approach, you'll need to make a new exception package to customize the message of the exception but at least you are sending a 400 status code in the response, it's two lines but it will get you close to what you want, at the end of the catchError operator you ask if it's a HttpException instance and throw a Build-in exception from @nestjs/common, if you add a status to the thrown exception return a 200 status code, or if you change anything of the exception return 200 status code:
if(error instanceof HttpException){
throw new BadRequestException(respuestaF);
}
this way you are sending a generic 400 and inside all the info you can get of the exception, it's not a standar response but at least the client will know that something went wrong with his request