@EnableAsync @Async

一. 基本介绍

@Async是spring为了方便开发人员进行异步调用的出现的,在方法上加入这个注解,spring会从线程池中获取一个新的线程来执行方法,实现异步调用

@EnableAsync表示开启对异步任务的支持,可以放在springboot的启动类上,也可以放在自定义线程池的配置类上,具体看下文

二.最简单的使用

在springboot项目中,直接在启动类上加上@EnableAsync,然后在service层的方法上对于需要异步调用的方法加上@Async,

那么当controller层调用这个方法的时候,就会在主线程外自动新建线程执行该方法,具体看下图demo

1.springboot启动类开启异步支持

 2.service层的方法加@Async,如果在类上加该注解表示整个类的方法都异步执行,建议加到具体的某个方法上

 3.controller层调用service层的异步方法,这里用主线程在异步方法前后执行了2次打印输出

 4.调用的结果

首先看看没有异步执行,正常的顺序执行的结果

可以看到,按顺序执行,全部是main线程http-nio-8181-exec-124执行,并且service方法的执行结果在中间,如下所示

 由于我们的方法使用了@Async注解,所以主线程http-nio-8181-exec-124不等异步方法完成,先结束了,异步线程task-1继续执行

 

tips:没有自定义线程池@Async默认的线程池是SimpleAsyncTaskExecutor

三.自定义线程池来使用@Async

1.新建一个线程池配置类,@EnableAsync在配置类上加,不用在启动类上加也行,可以配置不同的线程池,用bean的name做区分

 

 2.@Async的使用一样是在service层的方法上加,如果配置了多个线程池,可以用@Async("name"),那么表示线程池的@Bean的name,来指定用哪个线程池处理

假如只配置了一个线程池,直接用@Async就会用自定义的线程池执行

假如配置了多个线程池,用@Async没指定用哪个线程池,会用默认的SimpleAsyncTaskExecutor来处理

 假如配置了多个线程池,用@Async("name"),会用指定的线程池处理

比如service层方法上指定pool1线程池

 执行结果,异步线程名是pool配置的fzhThread

 

https://www.cnblogs.com/fzhblog/p/14012401.html

 四.注解没生效的原因

1.异步方法使用static修饰

2.异步方法类没有使用@Service注解(或其他注解)导致spring无法扫描到异步类

3.controller中需要使用@Autowired或@Resource等注解自动注入service类,不能自己手动new对象

我们在使用多线程的时候,往往需要创建Thread类,或者实现Runnable接口,来创建Executors,在使用spring中,已经给我们做了很好的支持,只要使用@Async可以定义一个线程任务。通过spring给我们提供的ThreadPoolTaskExecutor就可以使用线程池。

默认情况下,Spring将搜索相关的线程池定义:要么在上下文中搜索唯一的TaskExecutor bean,要么搜索名为“taskExecutor”的Executor bean。如果两者都无法解析,则将使用SimpleAsyncTaskExecutor来处理异步方法调用。

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值