java – ThreadLocal是否可以安全地与Tomcat NIO Connector一起使用

前端之家收集整理的这篇文章主要介绍了java – ThreadLocal是否可以安全地与Tomcat NIO Connector一起使用前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
负载测试期间测试Tomcat NIO连接器时,我们想到了这一点.我使用ThreadLocal另外我使用 Spring,我知道在几个地方它也使用它.

由于NIO连接器每个连接没有一个线程,我担心如果ThreadLocal对象在清理之前与另一个线程共享,则可能导致很难找到错误.但是,我认为这不是一个问题,因为它不是我能找到的文件警告,也没有发现任何其他帖子警告这一点.我假设NIO连接器对服务于实际请求的线程没有影响.

在我采用这个假设之前,我希望找到一些具体的证据.

@H_404_7@解决方法
只有熟悉Tomcat代码的人才能给你一个具体的答案,但我会尝试一个木制的:)

首先,您需要明确是否只是使用NIO连接器,或者您是否也在谈论Async servlet.
答案在每种情况下都会略有不同.

需要注意的主要事情是Java没有任何类型的延续,协同例程或线程重新安排.这意味着一旦你启动一个在线程上运行的代码,只有那段代码将在线程上运行直到它完成.

所以如果你有:myObject.doSomething();然后在doSomething运行的时候,它拥有对该线程的独占访问权限.该线程不会切换到其他一些代码 – 无论您使用的是什么类型的IO模型.

可能(将)会发生的是,不同的线程将被安排在不同的cpu上运行,但每个线程将运行一段代码来完成.

所以如果doSomething是:

public static final ThreadLocal<MyClass> VALUE = new ThreadLocal<MyClass>();
public void doSomething() {
  VALUE.set(this);
  try {
    doSomethingElse();
  } finally {
    VALUE.set(null);
  }
}

然后就没什么可担心的了 – doSomethingElse将运行一个线程,并且threadlocal将被设置为整个执行的正确值.

因此,简单的NIO连接器应该没有区别 – 容器将调用servlet上的服务方法,servlet将在单个线程中执行,然后最后完成所有操作.只是容器能够在处理连接时以更有效的方式处理IO.

如果您正在使用异步servlet,那么它会有所不同 – 在这种情况下,您的servlet可能会因单个请求被多次调用(因为异步模型的工作方式),并且这些调用可能位于不同的线程上,因此您可以在servlet的调用之间存储一些线程本地的东西.但是对于一次调用您的服务方法,它仍然没问题.

HTH.

猜你在找的Java相关文章