• 首页

  • 归档
小 黑 捡 方 块
小 黑 捡 方 块

小黑捡方块

获取中...

07
10

Spring的AOP构造器为什么执行了两次,又没有执行两次?

发表于 2020-07-10 • Spring 面试题 • 被 262 人看爆

以下是通过搜索+看源码分析后的个人理解:

​ 看到这个问题,第一反应是很矛盾的,又不是量子态。所以是不是版本的问题?官网有Spring3AOP的说明:

https://docs.spring.io/spring-framework/docs/3.0.x/spring-framework-reference/html/aop.html#aop-proxying

​ 里面提到使用CGLIB的时候被代理对象构造器会被调用两次,两个对象被创建,一个是被代理对象,一个是实现了切面的子类实例,在使用JDK的动态代理的时候是不会有这种问题的。

​ 而在Spring4开始,Spring解决了这个问题,通过Objenesis库创建了CGLIB代理对象,不再使用构造器。相关类:ObjenesisCglibAopProxy.java,源码如下:

@Override
protected Object createProxyClassAndInstance(Enhancer enhancer, Callback[] callbacks) {
    Class<?> proxyClass = enhancer.createClass();
    Object proxyInstance = null;
	// 首先就是尝试使用objenesis库去创建代理实例
    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);
        }
    }
	// objenesis未能创建或未启用才会走和Spring3一样的逻辑
    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;
}
分享到:
捋顺Zookeeper启动,选举核心源码(v3.7.x)
ConcurrentHashMap核心部分源码注释
  • 文章目录
  • 站点概览
小黑捡方块

帅哥小黑捡方块

Github Email RSS
看爆 Top5
  • jenkins通过ssh连接失败:Failed to add SSH key. Message [invalid privatekey 1,458次看爆
  • docker运行的jenkins在构建项目并打包成docker镜像时问题总结 1,396次看爆
  • ConcurrentHashMap核心部分源码注释 1,255次看爆
  • docker启动后外网和主机死活访问不到springboot项目 811次看爆
  • Springboot+Nginx+certbot重定向400错误解决 718次看爆
蜀ICP备19040029号

Copyright © 2021 小黑捡方块 ·

Proudly published with Halo · Theme by fyang · 站点地图