我在Tomcat的运行,我正在使用线程池(Java 5中的ExecutorService)并行运行IO密集型操作,以提高性能的Web应用程序。 我想有一些每个线程池内使用是在请求范围豆,但在线程池的线程不必访问Spring上下文,并得到一个代理失败。 如何使Spring上下文提供给线程池的线程来解决代理失败的任何想法?
我猜必须有注册/注销ThreadPool中每个线程有春天以为每个任务的方式,但还没有任何运气找到如何做到这一点。
谢谢!
我在Tomcat的运行,我正在使用线程池(Java 5中的ExecutorService)并行运行IO密集型操作,以提高性能的Web应用程序。 我想有一些每个线程池内使用是在请求范围豆,但在线程池的线程不必访问Spring上下文,并得到一个代理失败。 如何使Spring上下文提供给线程池的线程来解决代理失败的任何想法?
我猜必须有注册/注销ThreadPool中每个线程有春天以为每个任务的方式,但还没有任何运气找到如何做到这一点。
谢谢!
我使用下面的超类为我的任务需要访问要求的范围。 基本上,你可以扩展它,并落实onRun()方法的逻辑。
import org.springframework.web.context.request.RequestAttributes;
import org.springframework.web.context.request.RequestContextHolder;
/**
* @author Eugene Kuleshov
*/
public abstract class RequestAwareRunnable implements Runnable {
private final RequestAttributes requestAttributes;
private Thread thread;
public RequestAwareRunnable() {
this.requestAttributes = RequestContextHolder.getRequestAttributes();
this.thread = Thread.currentThread();
}
public void run() {
try {
RequestContextHolder.setRequestAttributes(requestAttributes);
onRun();
} finally {
if (Thread.currentThread() != thread) {
RequestContextHolder.resetRequestAttributes();
}
thread = null;
}
}
protected abstract void onRun();
}
我也希望我有1000票给目前公认的答案。 我已经难倒如何做到这一点了一段时间。 在此基础上,这里是使用的情况下,要使用一些新的东西@Async在Spring 3.0可调用接口我的解决方案。
public abstract class RequestContextAwareCallable<V> implements Callable<V> {
private final RequestAttributes requestAttributes;
private Thread thread;
public RequestContextAwareCallable() {
this.requestAttributes = RequestContextHolder.getRequestAttributes();
this.thread = Thread.currentThread();
}
public V call() throws Exception {
try {
RequestContextHolder.setRequestAttributes(requestAttributes);
return onCall();
} finally {
if (Thread.currentThread() != thread) {
RequestContextHolder.resetRequestAttributes();
}
thread = null;
}
}
public abstract V onCall() throws Exception;
}
你可以尝试用另一种方式圆? 使用一个储存在请求范围内的数据容器,并给它的线程池(也许把它放进一个队列,从而使线程池一次可以拿一个数据容器,它的工作,将其标记为“完成”,并继续与下一个)。
Spring提供了ThreadPoolTaskExecutor类 ,你可以用它来从春季管理你的线程池类。 然而,它看起来像你必须做一些工作,使Spring上下文提供给每个线程。
我不知道,如果即使你不这样,虽然电线它涨它就会工作。 Spring使用令牌在线程局部来定位请求(或会话)范围的对象,所以,如果你想从不同的线程访问的请求范围豆,很可能是令牌不会在那里。