Log Все ответы и запросы spring webflux

Я хочу добавить ведение журнала в свой проект, я использую webFilter для добавления журнала. Я хочу регистрировать заголовки запросов (кроме заголовка аутентификации), методы запроса и код ответа. Я добавляю этот код в свой проект:

@Component
@Slf4j
public class LogFilter implements WebFilter {


    @Override
    public Mono<Void> filter(ServerWebExchange serverWebExchange,
                             WebFilterChain webFilterChain) {
        log.info("log :: requestId: {}, ip: {}, method: {},path :{}, headers: {}, response :{}",
                serverWebExchange.getRequest().getId(), serverWebExchange.getRequest().getRemoteAddress(),
                serverWebExchange.getRequest().getMethod(), serverWebExchange.getRequest().getPath(),
                serverWebExchange.getRequest().getHeaders().entrySet()
                        .stream().filter(stringListEntry -> !stringListEntry.getKey().equals("Authorization")).toList(),
                serverWebExchange.getResponse().getStatusCode);
        return webFilterChain.filter(serverWebExchange);
    } 

У меня есть все заголовки и необходимая информация для регистрации, но код ответа всегда 200 OK, но в результате ответ на некоторое время составляет 400.

1
0
132
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Ваше решение неверно, потому что вы использовали регистратор перед фильтром, и фильтр будет активирован, если кто-либо подпишется на него, поэтому цепочка потоков Mono/Fluw будет запускаться позже, а не другой код. Ваш контроллер еще не запущен, поэтому вы преждевременно читаете код ответа. Пожалуйста, в будущем используйте режим отладки и проверяйте, какой вызов будет выполняться первым.

В моем решении я жду окончания связи. Он может быть полным или ошибочным. Итак, я слежу за этими сигналами и зарегистрирую, если один из них.

Одно решение:

@Component
public class LogFilter implements WebFilter {
    Logger log = LoggerFactory.getLogger(LogFilter.class);

    @Override
    public Mono<Void> filter(ServerWebExchange exchange, WebFilterChain chain) {
        return chain.filter(exchange)
            .doOnEach(signal -> {
                if (signal.isOnComplete() || signal.isOnError()) {
                    log.info(
                        "log :: requestId: {}, ip: {}, method: {},path :{}, headers: {}, response :{}",
                        exchange.getRequest().getId(), exchange.getRequest().getRemoteAddress(),
                        exchange.getRequest().getMethod(), exchange.getRequest().getPath(),
                        exchange.getRequest().getHeaders().entrySet()
                                .stream().filter(stringListEntry -> !stringListEntry.getKey().equals("Authorization")).toList(),
                        exchange.getResponse().getStatusCode()
                    );
                }
            });
    }
}

Другие вопросы по теме