出错时接收HttpRequest的原始路径

Receive original path of HttpRequest if error occurs

我正在编写简单的拦截器,它将从我接收和发送的所有请求和响应中收集数据,并将其流式传输到外部队列,在那里我可以过滤并查看我有: 100 次 /test 调用,95 次以状态 200 结束,4 次以状态 400 结束,1 次以状态 500 结束

我写的 class 看起来像这样

@Component
public class HttpEventInterceptor extends HandlerInterceptorAdapter {
    private final HttpEventStream eventStream;
    private final ObjectMapper objectMapper;

    public HttpEventInterceptor(HttpEventStream eventStream) {
        this.eventStream = eventStream;
        this.objectMapper = new ObjectMapper();
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        final var eventJson = objectMapper.writeValueAsString(createHttpEvent(request, response));
        eventStream.outboundEvents().send(MessageBuilder
                .withPayload(eventJson)
                .setHeader(MessageHeaders.CONTENT_TYPE, MimeTypeUtils.APPLICATION_JSON)
                .build());
    }

    private HttpEvent createHttpEvent(HttpServletRequest request, HttpServletResponse response) {
        final var event = new HttpEvent();
        event.setTimestamp(System.currentTimeMillis());
        event.setMethod(request.getMethod());
        event.setUrl(request.getRequestURI()); // <-- This isn't working as expected
        event.setResponseCode(response.getStatus());
        return event;
    }
}

似乎一切正常,除了一件事。 比方说,我用错误的请求调用端点 /test 并且我按预期收到 HttpStatus 400 Bad Request。但是,此时在 createHttpEvent() 中调用的 request.getRequestURI() 没有返回 /test 而是 /error。此时如何到达原始调用端点?

我也尝试过 @Override preHandle(),但它是一样的,我还需要合并来自请求和响应的数据,所以我更愿意在 postHandle()

How do I reach original called endpoint at this point?

根据 Servlet API 规范 10.9.1,默认错误处理程序将其保存为请求属性,名称由 RequestDispatcher#ERROR_REQUEST_URI.

标识

所以,它必须可用如下:

String originalRequestURI = (String) request.getAttribute(RequestDispatcher.ERROR_REQUEST_URI);
// ...