简体   繁体   中英

How to log request body in spring Webflux Java

I am receiving some XML payload in a POST request and want to see the payload as received for debugging purposes.

Below (my custom WebFilter) code logs the URI and request headers as expected but not the request body/payload, must be something wrong with my reactive code -

       final ServerHttpRequest request = exchange.getRequest();
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        LOGGER.info("Request: uri={}", request.getURI());
        LOGGER.info("Request: headers={}", request.getHeaders().entrySet());
        request.getBody().doOnNext(dataBuffer -> {
            try {
                Channels.newChannel(baos).write(dataBuffer.asByteBuffer().asReadOnlyBuffer());
                String body = new String(baos.toByteArray());
                LOGGER.info("Request: payload={}", body);
            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                try {
                    baos.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        });

I have looked at Brian's response for post below and followed it but since there is no code, I am probably making some silly mistake

How to log request and response bodies in Spring WebFlux

Updated Code

@Configuration
public class RequestFilter implements WebFilter {

    private static final Logger LOGGER = LoggerFactory.getLogger(RequestFilter.class);

    @Override
    @Order(Ordered.HIGHEST_PRECEDENCE)
    public Mono<Void> filter(ServerWebExchange serverWebExchange,
                             WebFilterChain webFilterChain) {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        serverWebExchange.getRequest().getBody().doOnNext(dataBuffer -> {
            try {
                Channels.newChannel(baos).write(dataBuffer.asByteBuffer().asReadOnlyBuffer());
                String body = new String(baos.toByteArray());
                LOGGER.info("Request: payload={}", body);
            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                try {
                    baos.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        });
        return webFilterChain.filter(serverWebExchange);
    }
}

You are doing it partially right except that you are extracting the body at the wrong place. You will have to do it in a ServerHttpRequestDecorator implementation and plug it in the WebFilter implementation.

public class RequestLoggingDecorator extends ServerHttpRequestDecorator {

  private static final Logger LOGGER = LoggerFactory.getLogger(RequestLoggingDecorator.class);

  public RequestLoggingDecorator(ServerHttpRequest delegate) {
    super(delegate);
  }

  @Override
  public Flux<DataBuffer> getBody() {
    ByteArrayOutputStream baos = new ByteArrayOutputStream();
    return super.getBody().doOnNext(dataBuffer -> {
      try {
        Channels.newChannel(baos).write(dataBuffer.asByteBuffer().asReadOnlyBuffer());
        String body = new String(baos.toByteArray(), StandardCharsets.UTF_8);
        LOGGER.info("Request: payload={}", body);
      } catch (IOException e) {
        e.printStackTrace();
      } finally {
        try {
          baos.close();
        } catch (IOException e) {
          e.printStackTrace();
        }
      }
    });
  }
}

Then you can configure this in a WebFilter implementation as follows:

@Configuration
public class RequestLoggingFilter implements WebFilter {
  @Override
  public Mono<Void> filter(ServerWebExchange serverWebExchange, WebFilterChain webFilterChain) {
    ServerWebExchangeDecorator decorator =
        new ServerWebExchangeDecorator(serverWebExchange) {
          @Override
          public ServerHttpRequest getRequest() {
            return new RequestLoggingDecorator(serverWebExchange.getRequest());
          }
        };

    return webFilterChain.filter(decorator);
  }
}

This should log your request body on every incoming Http request.

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.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM