使用ThreadLocal进行数据的请求范围传递

时间:2019-05-19 17:10:26

标签: java spring multithreading thread-local spring-web

我使用Spring Boot 2创建了Java 8 rest API。可以使用自定义注释@DataAware对控制器端点进行注释。有一个HandlerInterceptor处于活动状态,它检查当前请求是否映射到具有此批注的方法。如果是这样,我希望拦截器解析请求的特定标头,并使结果对象在处理该请求的整个线程中可用。

例如:

  1. 请求包含标头“ specialData a:b:c”
  2. 端点用@DataAware注释
  3. DataInterceptor将解析标头,然后 创建一个对象列表parsedData =“ a”,“ b”和“ c”。
  4. DataInterceptor的作用类似于 ThreadForThisRequest.addProperty("data",myParsedData);
  5. 在我的应用程序的各个位置,类和对象都必须能够引用parsedData,并应使用该线程上当前处于活动状态的值。
  6. 当另一个请求进入系统时(可能同时),两个线程都将无法看到彼此的解析数据。如果重用同一线程,则应删除或覆盖以前存储的数据

我想为此目的使用MDC(映射的诊断上下文),但似乎是一种反模式,用于将数据存储在相对隐藏的“全局”上下文映射中。

我不喜欢请求属性,因为那样的话,我必须将请求对象传递到应用程序中的所有位置。对看起来像“ public static final XXX”的东西进行编程要容易得多,但实际上只限于该请求(线程)。

我偶然发现ThreadLocal,并希望确保它能够完成我认为的工作。如果我介绍以下字段:

public static ThreadLocal<List<String>> requestSpecificData

然后,每当我的应用程序使用此对象时,将仅给出THAT请求的数据,因为每个请求均由其自己的线程处理? Spring Web或Spring Boot的嵌入式Tomcat是否会对线程进行其他一些古怪的事情或将请求转发到(向其他线程?),以便我的控制器端点可能丢失数据或看到以前的请求数据而不是自己的请求数据?

0 个答案:

没有答案