Nestjs日志响应数据对象

时间:2019-11-21 09:04:04

标签: javascript typescript express nestjs

我想在NestJs中记录传入请求和传出响应。我从这里Logging request/response in Nest.js和文档NestJs Aspect Interception中获取了信息。

通过不使用外部软件包来实现此目标真是太棒了,所以我非常希望使用本机的“嵌套”解决方案。

对于请求记录,我目前使用此代码

@Injectable()
export class RequestInterceptor implements NestInterceptor {
  private logger: Logger = new Logger(RequestInterceptor.name);

  intercept(context: ExecutionContext, next: CallHandler): Observable<any> {
    const {
      originalUrl,
      method,
      params,
      query,
      body,
    } = context.switchToHttp().getRequest();

    this.logger.log({
      originalUrl,
      method,
      params,
      query,
      body,
    });

    return next.handle();
  }
}

这将记录以下GET /users的结果

enter image description here

我还想记录传出的响应。目前,我使用此拦截器

@Injectable()
export class ResponseInterceptor implements NestInterceptor {
  private logger: Logger = new Logger(ResponseInterceptor.name);

  intercept(context: ExecutionContext, next: CallHandler): Observable<any> {
    const { statusCode } = context.switchToHttp().getResponse();

    return next.handle().pipe(
      tap(() =>
        this.logger.log({
          statusCode,
        }),
      ),
    );
  }
}

这将记录以下GET /users的结果

enter image description here

但是如何访问发送回客户端的数据?

1 个答案:

答案 0 :(得分:2)

首先,我建议将它们合并到一个记录器中,以便所有记录逻辑都放在一个地方。

第二,要获得将数据发送回客户端的功能,您需要在tap函数中向该函数添加一个参数,通常我们将其称为数据,这样您就可以知道要发送回什么数据。 Nest对此有点模糊,因为可观察对象的工作尚不清楚,但最终,类似这样的事情最终对您有用:

@Injectable()
export class AspectLogger implements NestInterceptor {
  intercept(context: ExecutionContext, next: CallHandler) {
    const req = context.switchToHttp().getRequest();
    const res = context.switchToHttp().getResponse();
    const {
      originalUrl,
      method,
      params,
      query,
      body,
    } = request;

    this.logger.log({
      originalUrl,
      method,
      params,
      query,
      body,
    });

    return next.handle().pipe(
      tap(data) => {
        this.logger.log({
          statusCode,
          data
        }),
    });
  }
}

如果您决定将其分成两个单独的拦截器,这也将起作用,但是只有一个拦截器也可以使确定通话时间变得更加容易。