一、AOP功能注解使用步骤
@EnableAspectJAutoProxy
注解开启Spring
的AOP
功能;@Aspect
注解定义切面类, 使用@Before, @After, @AfterReturning, @AfterThrowing
定义通知方法以及切点(可通过@Pointcut
抽取公用的切入点表达式), 通知方法上第一个参数(且只能是第一个参数)可以写上JoinPoint joinPoint
, Spring
会自动注入连接点, 可通过连接点获取被增强方法的信息;IOC
容器中@Configuration
@EnableAspectJAutoProxy // 开启AOP
public class SpringAopConfig {
@Bean // 注册切面
public RoleAspect roleAspect() {
return new RoleAspect();
}
@Bean // 注册被增强类
public RoleServiceImpl roleServiceImpl() {
return new RoleServiceImpl();
}
}
@Aspect // 定义切面类 这里需要导入AspectJ的相关jar包才可以使用
public class RoleAspect {
// 抽取公共的切入点表达式
@Pointcut("execution(public int study.bryan.spring.service.impl.RoleServiceImpl.addRole(..))")
public void pointcut() {
}
// 前置通知 被增强方法调用前, 前置通知被调用
@Before("pointcut()")
public void before(JoinPoint joinPoint) {
Object[] args = joinPoint.getArgs();
System.err.println("@Before....."+Arrays.toString(args));
}
// 后置通知 无论被增强方法是否正常原型, 后置通知被调用
@After(value = "pointcut()")
public void after() {
System.err.println("@After.....");
}
// 返回通知 被增强方法正常运行返回后, 返回通知被调用 returning 指定通知方法里是哪个参数接收被增强方法的返回值
@AfterReturning(value = "pointcut()", returning = "result")
public void afterReturning(Object result) {
System.err.println("@AfterReturning....."+result);
}
// 异常通知 被增强方法出现异常, 异常通知被调用 throwing 指定通知方法哪个参数接收被增强方法抛出的异常
@AfterThrowing(value = "pointcut()", throwing = "exception")
public void afterThrowing(Exception exception) {
System.err.println("@AfterThrowing....."+exception.getMessage());
}
// 还有一个环绕通知
}
// 被增强类
public class RoleServiceImpl {
public int addRole(int i, int k) {
int j = i/k;
return j;
}
}
二、@EnableAspectJAutoProxy: Spring何时注册AnnotationAwareAspectJAutoProxyCreator的Bean信息
Spring
通过@EnableAspectJAutoProxy
注解开启AOP功能@EnableAspectJAutoProxy
注解中被@Import
注解标注, @Import
中存在AspectJAutoProxyRegistrar
类, 这个类实现了ImportBeanDefinitionRegistrar
接口, 重写registerBeanDefinitions()
方法;registerBeanDefinitions()
方法中向Spring
容器中注册了ID
为org.springframework.aop.config.internalAutoProxyCreator
,对象为AnnotationAwareAspectJAutoProxyCreator
类的bean
信息beanDefinition
(只是注册bean信息, 还没有实例化);refresh()
方法中的invokeBeanFactoryPostProcessors(beanFactory);
方法里就是处理了关于@Import
注解中所导入的类, 将这些类的信息注册至容器中(放进一个Map beanDefinitionMap
中)@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
// IOC学习部分讲解中 @Import用来向SpringIOC容器中注册Bean, AspectJAutoProxyRegistrar实现了ImportBeanDefinitionRegistrar接口, 那么在重写的registerBeanDefinitions()就可以看出AspectJAutoProxyRegistrar向容器中注册了`ID`为`org.springframework.aop.config.internalAutoProxyCreator`,对象为`AnnotationAwareAspectJAutoProxyCreator`的类
@Import(AspectJAutoProxyRegistrar.class)
public @interface EnableAspectJAutoProxy {
....
}
class AspectJAutoProxyRegistrar implements ImportBeanDefinitionRegistrar {
/**
* 注册,扩展,和配置一个AspectJ的自动代理创建器
* Register, escalate, and configure the AspectJ auto proxy creator based on the value
* of the @{@link EnableAspectJAutoProxy#proxyTargetClass()} attribute on the importing
* {@code @Configuration} class.
*/
@Override
public void registerBeanDefinitions(
AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) {
// 1. 传入注册器 调用 AopConfigUtils的方法注册bean
AopConfigUtils.registerAspectJAnnotationAutoProxyCreatorIfNecessary(registry);
....其他源码
}
}
public abstract class AopConfigUtils {
// 这里定义了 自动代理创建器在容器中的ID值 常量 在注册的时候使用了
public static final String AUTO_PROXY_CREATOR_BEAN_NAME =
"org.springframework.aop.config.internalAutoProxyCreator";
.... 其他源码
// 2.
@Nullable
public static BeanDefinition registerAspectJAnnotationAutoProxyCreatorIfNecessary(BeanDefinitionRegistry registry) {
return registerAspectJAnnotationAutoProxyCreatorIfNecessary(registry, null);
}
// 3. 可以看到这里就直接放入了一个AnnotationAwareAspectJAutoProxyCreator 类
@Nullable
public static BeanDefinition registerAspectJAnnotationAutoProxyCreatorIfNecessary(
BeanDefinitionRegistry registry, @Nullable Object source) {
return registerOrEscalateApcAsRequired(AnnotationAwareAspectJAutoProxyCreator.class, registry, source);
}
.... 其他源码
// 4. Class> cls就是上面传入的AnnotationAwareAspectJAutoProxyCreator 类
@Nullable
private static BeanDefinition registerOrEscalateApcAsRequired(
Class<?> cls, BeanDefinitionRegistry registry, @Nullable Object source) {
Assert.notNull(registry, "BeanDefinitionRegistry must not be null");
if (registry.containsBeanDefinition(AUTO_PROXY_CREATOR_BEAN_NAME)) {
BeanDefinition apcDefinition = registry.getBeanDefinition(AUTO_PROXY_CREATOR_BEAN_NAME);
if (!cls.getName().equals(apcDefinition.getBeanClassName())) {
int currentPriority = findPriorityForClass(apcDefinition.getBeanClassName());
int requiredPriority = findPriorityForClass(cls);
if (currentPriority < requiredPriority) {
apcDefinition.setBeanClassName(cls.getName());
}
}
return null;
}
// 5. 传入cls创建一个BeanDefinition 用于存储Bean的信息 这里的cls就是AnnotationAwareAspectJAutoProxyCreator
RootBeanDefinition beanDefinition = new RootBeanDefinition(cls);
beanDefinition.setSource(source);
beanDefinition.getPropertyValues().add("order", Ordered.HIGHEST_PRECEDENCE);
beanDefinition.setRole(BeanDefinition.ROLE_INFRASTRUCTURE);
// 6. 最终看到调用注册方法 将AnnotationAwareAspectJAutoProxyCreator 注册至容器中, 且ID是AUTO_PROXY_CREATOR_BEAN_NAME ,也就是上面的常量
registry.registerBeanDefinition(AUTO_PROXY_CREATOR_BEAN_NAME, beanDefinition);
return beanDefinition;
}
.... 其他源码
}
三、AnnotationAwareAspectJAutoProxyCreator的继承树
从继承树看出AnnotationAwareAspectJAutoProxyCreator
是一个beanPostProcessor
后置处理器, 也是一个Aware
, 只要分析出AnnotationAwareAspectJAutoProxyCreator
作为Bean
后置处理器时被Spring
在何时使用, 作为Aware
时被Spring
何时使用, 就能大致分析出AnnotationAwareAspectJAutoProxyCreator
怎么被实例化, 怎么为其他Bean
创建代理对象;
四、Spring怎么将AnnotationAwareAspectJAutoProxyCreator实例化:
在容器的refresh()
方法中的registerBeanPostProcessors()
方法里处理所有需要实例化的Bean后置处理器, 而AnnotationAwareAspectJAutoProxyCreator
就是一个BeanPostProcessor
, 所以AnnotationAwareAspectJAutoProxyCreator
就是再此时被Spring
实例化
BeanPostProcessor
;BeanPostProcessor
;BeanPostProcessor
, 调用getBean()
实例化BeanPostProcessor
, 然后分离BeanPostProcessor
为三类, 其中在实例化的时候, 就会调用AnnotationAwareAspectJAutoProxyCreator
作为Aware
接口时的setBeanFactory()
方法, 调用到initBeanFactory()
方法用来初始化BeanFactoryAspectJAdvisorsBuilder(Aspect通知处理构造器)
;BeanPostProcessor
注册至BeanFactory中,a.先注册实现了PriorityOrdered
接口的BeanPostProcessor
; b. 再注册实现了Ordered
接口的BeanPostProcessor
; c. 最后注册没有实现优先级接口的BeanPostProcessor
; 其中AnnotationAwareAspectJAutoProxyCreator
是实现了Ordered
接口的;public static void registerBeanPostProcessors(
ConfigurableListableBeanFactory beanFactory, AbstractApplicationContext applicationContext) {
// 获取所有的需要实例化的Bean后置处理器
String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanPostProcessor.class, true, false);
// Register BeanPostProcessorChecker that logs an info message when
// a bean is created during BeanPostProcessor instantiation, i.e. when
// a bean is not eligible for getting processed by all BeanPostProcessors.
int beanProcessorTargetCount = beanFactory.getBeanPostProcessorCount() + 1 + postProcessorNames.length;
// 添加一些其他的Bean后置处理器
beanFactory.addBeanPostProcessor(new BeanPostProcessorChecker(beanFactory, beanProcessorTargetCount));
// 将Bean后置处理器分离为三种
// Separate between BeanPostProcessors that implement PriorityOrdered,
// Ordered, and the rest.
List<BeanPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
List<BeanPostProcessor> internalPostProcessors = new ArrayList<>();
List<String> orderedPostProcessorNames = new ArrayList<>();
List<String> nonOrderedPostProcessorNames = new ArrayList<>();
for (String ppName : postProcessorNames) {
if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
// 调用getBean()实例化并初始化Bean后置处理器
BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
priorityOrderedPostProcessors.add(pp);
if (pp instanceof MergedBeanDefinitionPostProcessor) {
internalPostProcessors.add(pp);
}
}
else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
orderedPostProcessorNames.add(ppName);
}
else {
nonOrderedPostProcessorNames.add(ppName);
}
}
// 分别处理三类Bean后置处理器, 将BeanPostProcessor放进BeanFactory的List beanPostProcessors中
// First, register the BeanPostProcessors that implement PriorityOrdered.
sortPostProcessors(priorityOrderedPostProcessors, beanFactory);
registerBeanPostProcessors(beanFactory, priorityOrderedPostProcessors);
// Next, register the BeanPostProcessors that implement Ordered.
List<BeanPostProcessor> orderedPostProcessors = new ArrayList<>(orderedPostProcessorNames.size());
for (String ppName : orderedPostProcessorNames) {
BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
orderedPostProcessors.add(pp);
if (pp instanceof MergedBeanDefinitionPostProcessor) {
internalPostProcessors.add(pp);
}
}
sortPostProcessors(orderedPostProcessors, beanFactory);
registerBeanPostProcessors(beanFactory, orderedPostProcessors);
// Now, register all regular BeanPostProcessors.
List<BeanPostProcessor> nonOrderedPostProcessors = new ArrayList<>(nonOrderedPostProcessorNames.size());
for (String ppName : nonOrderedPostProcessorNames) {
BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
nonOrderedPostProcessors.add(pp);
if (pp instanceof MergedBeanDefinitionPostProcessor) {
internalPostProcessors.add(pp);
}
}
registerBeanPostProcessors(beanFactory, nonOrderedPostProcessors);
// Finally, re-register all internal BeanPostProcessors.
sortPostProcessors(internalPostProcessors, beanFactory);
registerBeanPostProcessors(beanFactory, internalPostProcessors);
// Re-register post-processor for detecting inner beans as ApplicationListeners,
// moving it to the end of the processor chain (for picking up proxies etc).
beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(applicationContext));
}
五、AnnotationAwareAspectJAutoProxyCreator在什么时候为bean创建代理:
在容器的refresh()
方法中的finishBeanFactoryInitialization(beanFactory)
方法里完成对beanFanctory
的初始化, 会实例化剩余的单例Bean
, 观察Bean
实例化的整个周期可以发现原理;
beanFactory.preInstantiateSingletons()
方法中, 获取所有需要实例化的beanDefinitionNames
, 循环这些Bean
信息, 调用getBean()->doGetBean()->getSingleton()->createBean()
来实例化bean
; @Override
public void preInstantiateSingletons() throws BeansException {
if (logger.isTraceEnabled()) {
logger.trace("Pre-instantiating singletons in " + this);
}
// 获取所有的beanDefinitionNames 已注册的BeanDefinition信息名称
// Iterate over a copy to allow for init methods which in turn register new bean definitions.
// While this may not be part of the regular factory bootstrap, it does otherwise work fine.
List<String> beanNames = new ArrayList<>(this.beanDefinitionNames);
// Trigger initialization of all non-lazy singleton beans...
// 循环
for (String beanName : beanNames) {
RootBeanDefinition bd = getMergedLocalBeanDefinition(beanName);
if (!bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit()) {
if (isFactoryBean(beanName)) {
// 调用getBean()实例化Bean
Object bean = getBean(FACTORY_BEAN_PREFIX + beanName);
if (bean instanceof FactoryBean) {
FactoryBean<?> factory = (FactoryBean<?>) bean;
boolean isEagerInit;
if (System.getSecurityManager() != null && factory instanceof SmartFactoryBean) {
isEagerInit = AccessController.doPrivileged(
(PrivilegedAction<Boolean>) ((SmartFactoryBean<?>) factory)::isEagerInit,
getAccessControlContext());
}
else {
isEagerInit = (factory instanceof SmartFactoryBean &&
((SmartFactoryBean<?>) factory).isEagerInit());
}
if (isEagerInit) {
// 调用getBean()实例化Bean
getBean(beanName);
}
}
}
else {
// 调用getBean()实例化Bean
getBean(beanName);
}
}
}
// Trigger post-initialization callback for all applicable beans...
for (String beanName : beanNames) {
Object singletonInstance = getSingleton(beanName);
if (singletonInstance instanceof SmartInitializingSingleton) {
StartupStep smartInitialize = this.getApplicationStartup().start("spring.beans.smart-initialize")
.tag("beanName", beanName);
SmartInitializingSingleton smartSingleton = (SmartInitializingSingleton) singletonInstance;
if (System.getSecurityManager() != null) {
AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
smartSingleton.afterSingletonsInstantiated();
return null;
}, getAccessControlContext());
}
else {
smartSingleton.afterSingletonsInstantiated();
}
smartInitialize.end();
}
}
}
protected <T> T doGetBean(
String name, @Nullable Class<T> requiredType, @Nullable Object[] args, boolean typeCheckOnly)
throws BeansException {
.... 其他源码
// Create bean instance.
if (mbd.isSingleton()) {
sharedInstance = getSingleton(beanName, () -> {
try {
// 在这里实例化Bean
return createBean(beanName, mbd, args);
}
catch (BeansException ex) {
// Explicitly remove instance from singleton cache: It might have been put there
// eagerly by the creation process, to allow for circular reference resolution.
// Also remove any beans that received a temporary reference to the bean.
destroySingleton(beanName);
throw ex;
}
});
bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
}
.... 其他源码
}
createBean()
方法中,resolveBeforeInstantiation()
方法尝试使用Bean
后置处理器拦截先创建一个代理Bean
实例返回;
resolveBeforeInstantiation()
方法中调用bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName)
;方法尝试返回bean
;applyBeanPostProcessorsBeforeInstantiation()
方法中循环IOC容器中已注册的所有实现了InstantiationAwareBeanPostProcessor
接口的Bean
后置处理器, 调用这些Bean
后置处理器的postProcessBeforeInstantiation()
方法; 而AnnotationAwareAspectJAutoProxyCreator
恰好就是实现了InstantiationAwareBeanPostProcessor
接口的类, 在其父类AbstractAutoProxyCreator
中重写了postProcessBeforeInstantiation()
方法;AbstractAutoProxyCreator.postProcessBeforeInstantiation()
方法中, 需要满足一定条件后就会为需要实例化的Bean
创建代理Bean
;Bean
成功之后就直接调用AbstractAutoProxyCreator.postProcessAfterInitialization()
方法,继续处理代理Bean
, 然后直接返回Bean
, 不在对Bean
进行实例化,赋值属性,初始化等生命周期里的常规处理;@Override
protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
throws BeanCreationException {
.....其他源码
try {
// 在实例化Bean之前提前拦截 尝试使用BeanPostProcessors 去创建代理Bean, 成功则直接返回代理Bean
// Give BeanPostProcessors a chance to return a proxy instead of the target bean instance.
Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
if (bean != null) {
return bean;
}
}
catch (Throwable ex) {
throw new BeanCreationException(mbdToUse.getResourceDescription(), beanName,
"BeanPostProcessor before instantiation of bean failed", ex);
}
try {
// 如果没有创建代理Bean, 则调用doCreateBean()去实例化Bean
Object beanInstance = doCreateBean(beanName, mbdToUse, args);
if (logger.isTraceEnabled()) {
logger.trace("Finished creating instance of bean '" + beanName + "'");
}
return beanInstance;
}
catch (BeanCreationException | ImplicitlyAppearedSingletonException ex) {
// A previously detected exception with proper bean creation context already,
// or illegal singleton state to be communicated up to DefaultSingletonBeanRegistry.
throw ex;
}
.....其他源码
}
@Nullable
protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
Object bean = null;
if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
// Make sure bean class is actually resolved at this point.
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
Class<?> targetType = determineTargetType(beanName, mbd);
if (targetType != null) {
// 调用applyBeanPostProcessorsBeforeInstantiation(), 这里面就调用了postProcessBeforeInstantiation()方法
bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
// 如果Bean被实例化成功 则直接调用Bean后置处理器的BeanPostProcessorsAfterInitialization()方法
if (bean != null) {
bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
}
}
}
mbd.beforeInstantiationResolved = (bean != null);
}
return bean;
}
@Nullable
protected Object applyBeanPostProcessorsBeforeInstantiation(Class<?> beanClass, String beanName) {
for (InstantiationAwareBeanPostProcessor bp : getBeanPostProcessorCache().instantiationAware) {
// 循环所有的InstantiationAwareBeanPostProcessor, 调用InstantiationAwareBeanPostProcessor.postProcessBeforeInstantiation();
// 如果当前InstantiationAwareBeanPostProcessor刚好是AnnotationAwareAspectJAutoProxyCreator, 那么就会调用其父类 `AbstractAutoProxyCreator.postProcessBeforeInstantiation()`的方法去尝试创建代理Bean
Object result = bp.postProcessBeforeInstantiation(beanClass, beanName);
if (result != null) {
return result;
}
}
return null;
}
resolveBeforeInstantiation()
没有成功创建代理Bean
, 则调用doCreateBean()
真正实例化(调用Bean
的构造器实例化)bean[createBeanInstance()]
,给bean
属性赋值[populateBean()]
, 初始化bean[initializeBean()]
;
initializeBean()
方法中, 调用applyBeanPostProcessorsBeforeInitialization()
, 在此方法中循环所有的Bean
后置处理器, 调用Bean
后置处理器的postProcessBeforeInitialization()
方法;invokeInitMethods()
方法, 此方法中如果bean
实现了InitializingBean
接口,则调用bean
重写的afterPropertiesSet()
方法, 如果init-method
属性指定了bean
的初始化方法那么接着回调bean
的初始化方法;applyBeanPostProcessorsAfterInitialization()
方法,此方法中循环所有Bean
后置处理器, 调用Bean
后置处理器的postProcessAfterInitialization()
方法;而AnnotationAwareAspectJAutoProxyCreator
的父类AbstractAutoProxyCreator
实现了BeanPostProcessor
的postProcessAfterInitialization()
;Spring
在AbstractAutoProxyCreator.postProcessAfterInitialization()
方法中为需要实例化的Bean
创建代理Bean
; // 实例化Bean的方法
protected Object doCreateBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
throws BeanCreationException {
// Instantiate the bean.
BeanWrapper instanceWrapper = null;
if (mbd.isSingleton()) {
instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
}
if (instanceWrapper == null) {
// 在这里首次调用Bean构造器实例化Bean
instanceWrapper = createBeanInstance(beanName, mbd, args);
}
Object bean = instanceWrapper.getWrappedInstance();
.....其他源码....
// Initialize the bean instance.
Object exposedObject = bean;
try {
// 为Bean的属性赋值
populateBean(beanName, mbd, instanceWrapper);
// 初始化Bean
exposedObject = initializeBean(beanName, exposedObject, mbd);
}
catch (Throwable ex) {
if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {
throw (BeanCreationException) ex;
}
else {
throw new BeanCreationException(
mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);
}
}
.....其他源码....
return exposedObject;
}
// 初始化Bean的方法
protected Object initializeBean(String beanName, Object bean, @Nullable RootBeanDefinition mbd) {
if (System.getSecurityManager() != null) {
AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
invokeAwareMethods(beanName, bean);
return null;
}, getAccessControlContext());
}
else {
// 如果Bean实现了Aware接口, 这里就会回调重写Aware接口的某些方法, 为Bean赋值一些Spring底层的组件
invokeAwareMethods(beanName, bean);
}
Object wrappedBean = bean;
if (mbd == null || !mbd.isSynthetic()) {
// 调用Bean后置处理器的BeanPostProcessorsBeforeInitialization()方法 处理Bean
wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
}
try {
// 回调Bean的初始化方法 如果Bean实现了`InitializingBean`接口,则调用`bean`重写的`afterPropertiesSet()`方法, 如果`init-method`属性指定了`bean`的初始化方法那么接着回调`bean`的初始化方法
invokeInitMethods(beanName, wrappedBean, mbd);
}
catch (Throwable ex) {
throw new BeanCreationException(
(mbd != null ? mbd.getResourceDescription() : null),
beanName, "Invocation of init method failed", ex);
}
if (mbd == null || !mbd.isSynthetic()) {
// 调用Bean后置处理器的BeanPostProcessorsAfterInitialization()方法 处理Bean
// 在这里AnnotationAwareAspectJAutoProxyCreator的父类AbstractAutoProxyCreator重写了BeanPostProcessor的BeanPostProcessorsAfterInitialization(), 在重写的方法里为Bean创建了代理Bean
wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
}
return wrappedBean;
}
综上所述: AnnotationAwareAspectJAutoProxyCreator
在Spring
调用doCreateBean()
方法将Bean
实例化之前就拦截一次, 调用AbstractAutoProxyCreator.postProcessBeforeInstantiation()
尝试创建代理Bean
; 如果没有创建成功, 则在Bean
实例化,属性复制, 初始化之后,调用AbstractAutoProxyCreator.postProcessAfterInitialization()
方法创建代理Bean
;
六、AnnotationAwareAspectJAutoProxyCreator如何为bean创建代理:
已知Spring
会在Bean
实例化之前调用AbstractAutoProxyCreator.postProcessBeforeInstantiation()
尝试创建代理Bean
, 已经在初始化后调用AbstractAutoProxyCreator.postProcessAfterInitialization()
方法创建代理Bean
, 那么分析这两个方法中是如何处理的, 就能知道Spring
是如何为Bean
创建代理Bean
;
AbstractAutoProxyCreator.postProcessBeforeInstantiation()
方法分析:
Bean
是否已经在 advisedBeans(存放了所有被增强的代理Bean)中, 如果存在就返回null;Bean
是否实现了Advice,Pointcut,Advisor,AopInfrastructureBean
接口或者是否被@Aspect
注解标注, 如果是则表示当前Bean
是一个切面类, 那就返回Null
;Advisor
, 如果这些通知存在一个是AspectJPointcutAdvisor
, 那么需要跳过, 方法返回Null
;TargetSource
, 如果TargetSource
存在, 则通过TargetSource
创建代理Bean
;@Override
public Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) {
Object cacheKey = getCacheKey(beanClass, beanName);
if (!StringUtils.hasLength(beanName) || !this.targetSourcedBeans.contains(beanName)) {
if (this.advisedBeans.containsKey(cacheKey)) {
return null;
}
if (isInfrastructureClass(beanClass) || shouldSkip(beanClass, beanName)) {
this.advisedBeans.put(cacheKey, Boolean.FALSE);
return null;
}
}
// Create proxy here if we have a custom TargetSource.
// Suppresses unnecessary default instantiation of the target bean:
// The TargetSource will handle target instances in a custom fashion.
TargetSource targetSource = getCustomTargetSource(beanClass, beanName);
if (targetSource != null) {
if (StringUtils.hasLength(beanName)) {
this.targetSourcedBeans.add(beanName);
}
Object[] specificInterceptors = getAdvicesAndAdvisorsForBean(beanClass, beanName, targetSource);
Object proxy = createProxy(beanClass, beanName, specificInterceptors, targetSource);
this.proxyTypes.put(cacheKey, proxy.getClass());
return proxy;
}
return null;
}
AbstractAutoProxyCreator.postProcessAfterInitialization()
方法分析:
wrapIfNecessary()
方法, 包装Bean
;wrapIfNecessary()
中, 先按postProcessBeforeInstantiation()
方法前三点一样判断, 满足条件后往下走Bean
的所有增强器(通知方法)AdvisorsForBean
: 也就是通过切入点表达式去匹配, 获取能够符合当前Bean
的通知方法;Bean
的增强器, 那么将当前Bean存入advisedBeans
中, 标志已增强;然后调用createProxy()
方法创建代理Bean;createProxy()
方法中利用ProxyFactory
代理工厂创建代理Bean
, 先将符合Bean
的增强器Advisors
注入至ProxyFactory
, 然后调用proxyFactory.getProxy(getProxyClassLoader())
方法;proxyFactory.getProxy()
方法中先调用createAopProxy()
方法根据规则返回一个AopProxy
接口的代理工厂对象, 可能是CglibAopProxy
,也可能是JdkDynamicAopProxy
, 然后调用AopProxy
接口的getProxy()
方法为当前Bean
创建代理对象, 最终给容器返回被增强后的代理对象;Bean
时, 容器返回的就是被增强后的代理Bean
; @Override
public Object postProcessAfterInitialization(@Nullable Object bean, String beanName) {
if (bean != null) {
Object cacheKey = getCacheKey(bean.getClass(), beanName);
if (this.earlyProxyReferences.remove(cacheKey) != bean) {
return wrapIfNecessary(bean, beanName, cacheKey);
}
}
return bean;
}
protected Object wrapIfNecessary(Object bean, String beanName, Object cacheKey) {
if (StringUtils.hasLength(beanName) && this.targetSourcedBeans.contains(beanName)) {
return bean;
}
if (Boolean.FALSE.equals(this.advisedBeans.get(cacheKey))) {
return bean;
}
if (isInfrastructureClass(bean.getClass()) || shouldSkip(bean.getClass(), beanName)) {
this.advisedBeans.put(cacheKey, Boolean.FALSE);
return bean;
}
// 获取符合当前Bean的增强器, 根据切入点表达式去匹配
// Create proxy if we have advice.
Object[] specificInterceptors = getAdvicesAndAdvisorsForBean(bean.getClass(), beanName, null);
// 如果存在增强器, 则创建代理对象, 如果不存在增强器, 则不创建直接放回Bean
if (specificInterceptors != DO_NOT_PROXY) {
this.advisedBeans.put(cacheKey, Boolean.TRUE);
Object proxy = createProxy(
bean.getClass(), beanName, specificInterceptors, new SingletonTargetSource(bean));
this.proxyTypes.put(cacheKey, proxy.getClass());
return proxy;
}
this.advisedBeans.put(cacheKey, Boolean.FALSE);
return bean;
}
// 创建代理对象
protected Object createProxy(Class<?> beanClass, @Nullable String beanName,
@Nullable Object[] specificInterceptors, TargetSource targetSource) {
if (this.beanFactory instanceof ConfigurableListableBeanFactory) {
AutoProxyUtils.exposeTargetClass((ConfigurableListableBeanFactory) this.beanFactory, beanName, beanClass);
}
ProxyFactory proxyFactory = new ProxyFactory();
proxyFactory.copyFrom(this);
if (!proxyFactory.isProxyTargetClass()) {
if (shouldProxyTargetClass(beanClass, beanName)) {
proxyFactory.setProxyTargetClass(true);
}
else {
evaluateProxyInterfaces(beanClass, proxyFactory);
}
}
// 获取符合当前Bean的增强器
Advisor[] advisors = buildAdvisors(beanName, specificInterceptors);
// 将增强器注入代理工厂
proxyFactory.addAdvisors(advisors);
proxyFactory.setTargetSource(targetSource);
customizeProxyFactory(proxyFactory);
proxyFactory.setFrozen(this.freezeProxy);
if (advisorsPreFiltered()) {
proxyFactory.setPreFiltered(true);
}
// 创建代理工厂对象, 调用getProxy()创建代理Bean
return proxyFactory.getProxy(getProxyClassLoader());
}
// 这段代码决定Spring是使用Cglib还是JDK来为Bean创建动态代理
@Override
public AopProxy createAopProxy(AdvisedSupport config) throws AopConfigException {
if (!IN_NATIVE_IMAGE &&
(config.isOptimize() || config.isProxyTargetClass() || hasNoUserSuppliedProxyInterfaces(config))) {
Class<?> targetClass = config.getTargetClass();
if (targetClass == null) {
throw new AopConfigException("TargetSource cannot determine target class: " +
"Either an interface or a target is required for proxy creation.");
}
// 当前Bean是一个接口或者当前Bean继承了JDK的Proxy的动态代理,那么Spring就会选择适用JDK动态代理
if (targetClass.isInterface() || Proxy.isProxyClass(targetClass)) {
return new JdkDynamicAopProxy(config);
}
return new ObjenesisCglibAopProxy(config);
}
else {
return new JdkDynamicAopProxy(config);
}
}
七、增强器(通知方法)如何拦截代理对象的目标方法的执行:
已知Spring
开启AOP
功能之后,会为需要需要增强的Bean实例化一个代理对象, 之后每次从容器中获取Bean
时,拿到的都是代理对象, 使用代理对象执行目标方法时, Spring
会根据按照一定顺序执行通知方法;那么Spring
是如何实现的拦截目标方法执行前后来执行通知方法的呢?
当执行目标方法时, 会被CglibAopProxy&DynamicAdvisedInterceptor.intercept()
方法拦截;
首先拦截方法中会根据目标对象和目标方法获取 拦截器链 List
; 实际上这部分操作是将目标方法的所有增强器(通知方法)封装成MethodInterceptor
集合
如果没有拦截器链, 则直接执行目标方法
如果有拦截器链, 则需要创建一个CglibMethodInvocation
对象, 并调用CglibMethodInvocation.proceed()
方法
proceed()
方法触发所有通知方法和目标方法的调用proceed()
方法中 有一个常量this.currentInterceptorIndex
用来代表当前拦截器链索引, 默认为-1,每次进入proceed()
方法时this.currentInterceptorIndex
都自增一次, 通过索引在之前封装的chain
中获取拦截器(其实就是增强器), 获取到拦截器后, 调用拦截器的invoke()
方法, 在每个拦截器的invoke()
方法中回调proceed()
,且处理回调相关的通知方法;this.currentInterceptorIndex
的值等于chain
的长度-1时, 表示已经循环到最后的连接器链, 此时回调目标方法, 将目标方法的返回值返回;然后依次返回前一次调用的方法;综上所述: SpringAOP通过CglibAopProxy来拦截目标方法的, 获取目标方法的所有增强器(通知方法), 将通知方法按一定顺序封装成MethodInterceptor(方法拦截器)集合, 形成一个拦截器链; 根据目标对象目标方法以及获取的拦截器链创建CglibMethodInvocation对象, 调用CglibMethodInvocation.proceed()方法, 类似递归一样,循环获取拦截器链来处理回调通知方法; 达到在目标方法前后能够执行各种通知方法的目的