同步,异步永远是编程绕不开的话题。在面对特殊问题的时候,需要采取特定的方法。
熟悉的SSH框架是典型的同步模型,一个http请求进来Controller之后,由一个线程同步的执行业务逻辑。在Spring的较新版本里,Controller层和Service层已经支持异步了,现在我们来看一下@Async的异步方式。
使用@Async需要初始化一个线程池,用来执行@Async注解的任务。
@Bean(name = "service-executor")
public AsyncTaskExecutor taskExecutor() {
ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
executor.setThreadNamePrefix("service-executor");
executor.setMaxPoolSize(50);
executor.setCorePoolSize(10);
executor.setKeepAliveSeconds(5);
return executor;
}
然后service方法注解
@Async("service-executor")
public Future<String> http(String deviceName, String msg) {
//.....http请求
if (!resp.getSuccess()) {
//throw new BusinessException(ResultEnum.DEVICE_ACCESS_ERROR);
return AsyncResult.forExecutionException(new BusinessException("error!"));
}
return new AsyncResult<>(res);
}
@Async需要指定线程池,然后如果需要结果的话 return new AsyncResult<>(res); 如果出现异常那么,return AsyncResult.forExecutionException(new BusinessException("error!"));
值得注意的是 如果关心结果,那么返回值需要是 Future 因为Spring bena的代理会返回一个Future 的子类,如果是其他类型可能会发生 类型转换异常。
然后Future的使用方法就不多说了。
网友评论