我正在使用log4j ThreadContext在一个Sping Boot 应用程序中进行跟踪。我已经通过实现HandlerInterceptor创建了一个拦截器,该拦截器拦截一个请求,然后使用ThreadContext在ThreadContextMap中设置'x'值。put(“相关ID”,'x')。值'x'是从要求信头撷取的。在要求完成后,我会使用ThreadContext.clearMap清除ThreadContext()。要求是在日志中查看correlationId,每个日志语句都将得到满足。
public class RequestHandlerInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(
final HttpServletRequest request,
final HttpServletResponse response,
final Object handler)
throws Exception {
ThreadContext.put(CORRELATION_ID, request.getHeader(CORRELATION_ID_HEADER));
return true;
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable Exception ex) throws Exception {
ThreadContext.clearMap();
}}
现在我的问题是,如果多个用户同时发出多个请求,会发生什么情况?ThreadContextMap中correlationId的值会在旧请求完成之前被每个新请求替换吗?如果是,那么什么是正确的实现呢?因为如果correlationId的值在请求完成之前被替换,那么在日志中我将记录不正确的correlationId。任何帮助都将不胜感激。
1条答案
按热度按时间bakd9h0s1#
您使用的是blocking-还是Non-blocking-IO (NIO)?如果您使用的是blocking-IO(可能大多数应用程序在过去几十年中都使用过),那么服务器将为用户发出的每个请求创建一个线程。服务类中的业务逻辑以及对其他系统(如数据库或服务)的调用都由该请求处理(并且在等待来自这些系统的应答时被阻止)。
ThreadContext
是以每个线程为基础进行管理的,因此与其他线程和请求分开。如果您使用NIO,那么事情会变得更加复杂,因为用户发出的请求会由多个线程处理。