先说结论:在spring-aop的默认逻辑中,aop默认优先使用JDK代理,前提是目标对象是基于接口的实现类。
源码如下:入口在AbstractAdvisingBeanPostProcessor.postProcessAfterInitialization(Object bean, String beanName)中
其中ProxyFactory继承自ProxyCreatorSupport:
而AopProxyFactory只有一个默认实现:DefaultAopProxyFactory,其中创建代理对象的核心方法为createAopProxy():
NativeDetector.inNativeImage() :是否使用GVM编译,一般为false;
config.isOptimize():代理是否应该执行积极优化,私有默认值为false;
config.isProxyTargetClass():是否是基于类的代理,如果想使用cglib代理,则设此值为true,默认为false;
hasNoUserSuppliedProxyInterfaces():如果存在一个接口,还是SpringProxy类型的,就返回true,否则就是false,自定义的肯定是false,如果没接口也是false。一般为false;
所以第一个循环条件在大多数情况下判断的依据是config.isProxyTargetClass(),proxyTargetClass是可以手动设置的(xml配置中指定proxy-target-class = "true" 或者使用注解@EnableAspectJAutoProxy(proxyTargetClass = true)),但一般情况下不会去设置它,而是由ProxyProcessorSupport.evaluateProxyInterfaces()去处理它的值。
如果目标对象没有基于接口的实现,便不会经此循环,hasReasonableProxyInterface会为false,proxyTargetClass会被设为true。
isConfigurationCallbackInterface(ifc):一般为false,是否包含以下接口的实现,InitializingBean.class,DisposableBean.class,Closeable.class ,AutoCloseable.class ,ObjectUtils.containsElement(ifc.getInterfaces(), Aware.class);
isInternalLanguageInterface(ifc):一般为false,是否是内部语言接口,ifc.getName().equals("groovy.lang.GroovyObject") || ifc.getName().endsWith(".cglib.proxy.Factory") || ifc.getName().endsWith(".bytebuddy.MockAccess");
所以(!isConfigurationCallbackInterface(ifc) && !isInternalLanguageInterface(ifc) && ifc.getMethods().length > 0 )一般为true;