疑问:@Async 是怎样解析的,spring如何实现注解方法的异步调用?
...
0、@Async 的应用: Creating Asynchronous Methods
...
1、@Async 的作用
按照惯例,annotation 是bean-post-processor处理的。处理@Async 的processor 就是在解析task:annotation-driven 配置过程中注册的,参考Insight task:annotation-driven 解析。
看看注册的AsyncAnnotationBeanPostProcessor 做了什么:
a.processor 指定属性advisor默认为AsyncAnnotationAdvisor,至此可以知道spring 异步方法支持是通过AOP 实现的!
b.哪些类会创建proxy,判断bean class是否有@Async 或者method 有@Async(see AsyncAnnotationAdvisor.pointcut)。
...
2、异步方法实现:
AsyncAnnotationAdvisor.advice = new AnnotationAsyncExecutionInterceptor(executor)。
直接上AnnotationAsyncExecutionInterceptor源码:
/** * Intercept the given method invocation, * submit the actual calling of the method to the correct task executor and return immediately to the caller. */ public Object invoke(final MethodInvocation invocation) throws Throwable { Class targetClass = (invocation.getThis() != null ? AopUtils.getTargetClass(invocation.getThis()) : null); Method specificMethod = ClassUtils.getMostSpecificMethod(invocation.getMethod(), targetClass); specificMethod = BridgeMethodResolver.findBridgedMethod(specificMethod); AsyncTaskExecutor executor = determineAsyncExecutor(specificMethod); if (executor == null) { throw new IllegalStateException("No executor specified and no default executor set on AsyncExecutionInterceptor either"); } // 熟悉的Executor、Future Future result = executor.submit( new Callable() { public Object call() throws Exception { try { Object result = invocation.proceed(); if (result instanceof Future) { return ((Future ) result).get(); } } catch (Throwable ex) { ReflectionUtils.rethrowException(ex); } return null; } }); if (Future.class.isAssignableFrom(invocation.getMethod().getReturnType())) { return result; } else { return null; } } 看懂为什么要在call() 方法内进行result.get() 吗?@see AsyncResult 转手操作。
...
总结:
1、spring 创建异步方法是通过AOP实现的;
2、@Async 标识是否创建异步方法;
3、代理的方法需要声明为return Future。
