我可能一直在做某些错误的事情。所以,我有Spring的@Async
假设我有这段代码
@Async("poolbeanname")
Function () {
// some code
}
我还有一个,假设我有这段代码
@Async("poolbeanname")
Function () {
CompletableFuture.runAsync{ new Runnable ()...}
}
现在我可以看到第二个代码,产生了一些线程,但是第一种方法似乎产生的线程不止一个?
答案 0 :(得分:2)
要启用使用@Async
,您应该使用@EnableAsync
让我们开始通过Java配置启用异步处理–只需将@EnableAsync添加到配置类即可:
@Configuration @EnableAsync public class SpringAsyncConfig { ... }
并且您必须使用从其他类调用的public
方法:
@Async有两个限制:
它必须仅应用于公共方法
自调用–从同一类中调用async方法–不起作用
答案 1 :(得分:1)
@Async("poolbeanname")
Function () {
}
如果配置类中有@EnableAsync
,则以上代码段将使用线程池异步执行。
@Configuration
@EnableAsync
或
@SpringBootApplication
@EnableAsync
启用异步后,spring将搜索自定义taskExecutor或executor bean,如果找不到,则默认为其自己的taskExecutor。
检查您的日志中是否有Initializing ExecutorService....
行
开箱即用的是,它说它初始化了o.s.s.concurrent.ThreadPoolTaskExecutor
,默认情况下将为您提供1的核心池大小。
要覆盖执行程序,只需要将工厂方法添加到Executor
的配置类中。
@Bean
public Executor threadPoolTaskExecutor() {
ThreadPoolTaskExecutor threadPoolTaskExecutor = new ThreadPoolTaskExecutor();
threadPoolTaskExecutor.setCorePoolSize(10);
threadPoolTaskExecutor.setMaxPoolSize(50);
//etc...
return threadPoolTaskExecutor;
}
如果执行程序被覆盖,则可能是指定了一个线程池大小或使用了Executors.newSingleThreadExecutor();
。
CompletableFuture:
代码CompletableFuture.runAsync{ new Runnable ()}
将创建一个CompletableFuture
实例,并在每次调用时异步执行该代码(创建线程)。
CompletableFuture<Void> future
= CompletableFuture.runAsync(() -> "This is processed asynchronously");
答案 2 :(得分:0)
@ M.Deinum在他的评论中强调了这一点:
@Async("poolbeanname")
Function () {
CompletableFuture.runAsync{ new Runnable ()...}
}
除非您真正需要它,否则它是没有用的,因为:@Async
在poolbeanname
线程池中发送方法的执行,而CompletableFuture.runAsync{ new Runnable ()...}
将从{{1} }。
您可以简单地执行以下操作:
poolbeanname
请注意,由于spring的对象代理,如果这样做:
@Async("poolbeanname")
Function () {
CompletableFuture.completedFuture( futureResult);
}
但是您可以通过自动注入bean来使用此解决方法。
@Service
class YourService {
callAsyncFunction(){
function(); //@Async will not work here
}
@Async("poolbeanname")
function () {
CompletableFuture.completedFuture( futureResult);
}
}