终于看完了庞大的Spring core(spring ioc / spring aop),鉴于ioc更为庞大,先整理下aop的源码流程,也能简单回顾下springioc的流程
首先要理解spring bean的启动大致的流程与生命周期,建议看另一篇已经简要解释 spring生命周期
基础概念
AOP 与 Spring AOP 与 AspectJ的区别
AOP 是思想,Spring AOP 与 AspectJ是AOP的实现,Spring AOP实现的时候用了AspectJ的规范
基本使用与AOP概念
//TODO
源码解析
入口
1、AnnotationConfigApplicationContext annotationConfigApplicationContext = new AnnotationConfigApplicationContext(Application.class);
refresh()初始化bean和执行后置处理器
2、@EnableAspectJAutoProxy
添加AOP的后置处理器,等同于xml中的 aop:aspectj-autoproxy/
@EnableAspectJAutoProxy解析
1、@EnableAspectJAutoProxy注解中@Import了类AspectJAutoProxyRegistrar,AspectJAutoProxyRegistrar 实现了 ImportBeanDefinitionRegistrar,可以拿到BeanDefinitionRegistry(spring bean生命周期相关),可以在类初始化之前加入AOP的后置处理器 ----> AnnotationAwareAspectJAutoProxyCreator
2、AnnotationAwareAspectJAutoProxyCreator的父类实现了BeanPostProcessor,会在spring对象产生之后进行操作,spring最核心的扩展点
3、父类实现BeanPostProcessor,真正执行后置处理器的类在AbstractAutoProxyCreator#postProcessAfterInitialization
public Object AbstractAutoProxyCreator#postProcessAfterInitialization(@Nullable Object bean, String beanName) throws BeansException {
if (bean != null) {
Object cacheKey = getCacheKey(bean.getClass(), beanName);
if (!this.earlyProxyReferences.contains(cacheKey)) {
return wrapIfNecessary(bean, beanName, cacheKey);
}
}
return bean;
}
其中wrapIfNecessary()中执行了创建代理类的方法
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;
}
// Create proxy if we have advice.
Object[] specificInterceptors = getAdvicesAndAdvisorsForBean(bean.getClass(), beanName, null);
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;
}
4、动态代理的选择方式 (jdk、cjlib) DefaultAopProxyFactory#createAopProxy
// 这段代码有前人解释的很好了
public AopProxy DefaultAopProxyFactory#createAopProxy(AdvisedSupport config) throws AopConfigException {
//这段代码用来判断选择哪种创建代理对象的方式
//config.isOptimize() 是否对代理类的生成使用策略优化 其作用是和isProxyTargetClass是一样的 默认为false
//config.isProxyTargetClass() 是否使用Cglib的方式创建代理对象 默认为false
//hasNoUserSuppliedProxyInterfaces目标类是否有接口存在 且只有一个接口的时候接口类型不是
//SpringProxy类型
if (config.isOptimize() || config.isProxyTargetClass() || hasNoUserSuppliedProxyInterfaces(config)) {
//上面的三个方法有一个为true的话,则进入到这里
//从AdvisedSupport中获取目标类 类对象
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.");
}
//判断目标类是否是接口 如果目标类是接口的话,则还是使用JDK的方式生成代理对象
//如果目标类是Proxy类型 则还是使用JDK的方式生成代理对象
if (targetClass.isInterface() || Proxy.isProxyClass(targetClass)) {
return new JdkDynamicAopProxy(config);
}
//配置了使用Cglib进行动态代理 或者目标类没有接口 那么使用Cglib的方式创建代理对象
return new ObjenesisCglibAopProxy(config);
}
else {
//上面的三个方法没有一个为true 那使用JDK的提供的代理方式生成代理对象
return new JdkDynamicAopProxy(config);
}
}
用户可以自行配置@EnableAspectJAutoProxy注解有一个proxyTargetClass属性表示是否使用CGLIB进行代理,源码中可以看出,即便是自定义了CGLIB代理,如果是个接口口,依旧会选择jdk动态代理
jdk动态代理
public Object JdkDynamicAopProxy#getProxy(@Nullable ClassLoader classLoader) {
if (logger.isDebugEnabled()) {
logger.debug("Creating JDK dynamic proxy: target source is " + this.advised.getTargetSource());
}
Class<?>[] proxiedInterfaces = AopProxyUtils.completeProxiedInterfaces(this.advised, true);
findDefinedEqualsAndHashCodeMethods(proxiedInterfaces);
return Proxy.newProxyInstance(classLoader, proxiedInterfaces, this);
}
Cglib动态代理
protected Object ObjenesisCglibAopProxy#createProxyClassAndInstance(Enhancer enhancer, Callback[] callbacks) {
Class<?> proxyClass = enhancer.createClass();
Object proxyInstance = null;
if (objenesis.isWorthTrying()) {
try {
proxyInstance = objenesis.newInstance(proxyClass, enhancer.getUseCache());
}
catch (Throwable ex) {
logger.debug("Unable to instantiate proxy using Objenesis, " +
"falling back to regular proxy construction", ex);
}
}
if (proxyInstance == null) {
// Regular instantiation via default constructor...
try {
Constructor<?> ctor = (this.constructorArgs != null ?
proxyClass.getDeclaredConstructor(this.constructorArgTypes) :
proxyClass.getDeclaredConstructor());
ReflectionUtils.makeAccessible(ctor);
proxyInstance = (this.constructorArgs != null ?
ctor.newInstance(this.constructorArgs) : ctor.newInstance());
}
catch (Throwable ex) {
throw new AopConfigException("Unable to instantiate proxy using Objenesis, " +
"and regular proxy instantiation via default constructor fails as well", ex);
}
}
((Factory) proxyInstance).setCallbacks(callbacks);
return proxyInstance;
}
后置处理器在哪里执行的呢(spring bean相关,简略说一下) 以注解为例
入口: AnnotationConfigApplicationContext的构造方法中的 refresh()方法
一个问题: 代理类生成的时机是getbean的时候还是getbean之前呢?
答案: 在getbean之前,在AnnotationConfigApplicationContext构造方法中执行了refresh方法,执行了getbean实例化,并生成了代理类(源码解读)
refresh()方法中进行了较多的操作,实例化工厂、配置工厂、生成db、注册beanPostProcessor…,我们的重点在finishBeanFactoryInitialization(beanFactory);方法中
然后进入到默认工厂类DefaultListableBeanFactory#preInstantiateSingletons#getBean()
准备进入核心代码:(后面补上完整调用链)
AbstractAutowireCapableBeanFactory#doCreateBean(去除了干扰代码)
protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final @Nullable Object[] args)
throws BeanCreationException {
// Instantiate the bean.
BeanWrapper instanceWrapper = null;
if (mbd.isSingleton()) {
instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
}
if (instanceWrapper == null) {
instanceWrapper = createBeanInstance(beanName, mbd, args);
}
final Object bean = instanceWrapper.getWrappedInstance();
Class<?> beanType = instanceWrapper.getWrappedClass();
if (beanType != NullBean.class) {
mbd.resolvedTargetType = beanType;
}
boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
isSingletonCurrentlyInCreation(beanName));
if (earlySingletonExposure) {
addSingletonFactory(beanName, () -> getEarlyBeanReference(beanName, mbd, bean));
}
// Initialize the bean instance.
Object exposedObject = bean;
try {
//设置属性,非常重要
populateBean(beanName, mbd, instanceWrapper);
//执行后置处理器,aop就是在这里完成的处理
exposedObject = initializeBean(beanName, exposedObject, mbd);
}
catch (Throwable ex) {}
}
AbstractAutowireCapableBeanFactory#initializeBean
这里执行了后置处理器的after方法,这里就会执行第一步中注册的后置处理器,这里也能看出BeanPostProcessors执行的时机和spring bean创建的时机
protected Object initializeBean(final String beanName, final Object bean, @Nullable RootBeanDefinition mbd) {
if (System.getSecurityManager() != null) {
AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
invokeAwareMethods(beanName, bean);
return null;
}, getAccessControlContext());
}else {
invokeAwareMethods(beanName, bean);
}
Object wrappedBean = bean;
if (mbd == null || !mbd.isSynthetic()) {
//执行后置处理的befor
wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
}
try {
//执行bean的声明周期回调中的init方法
invokeInitMethods(beanName, wrappedBean, mbd);
}
catch (Throwable ex) {
}
if (mbd == null || !mbd.isSynthetic()) {
//执行后置处理器的after方法
wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
}
return wrappedBean;
}