jdk 代理 和 cglib 代理深度分析
2018-04-03 22:13
253 查看
参考 http://lrd.ele.me/2017/01/09/dynamic_proxy/
jdk 代理 rem target 实例化的对象 --> Proxy.newProxyInstance(target.getClass().getClassLoader(), target.getClass().getInterfaces(), this); --> Class<?> cl = getProxyClass0(loader, intfs); // intfs 对象接口 重点 : --> return proxyClassCache.get(loader, interfaces); // proxyClassCache 缓存 --> Object subKey = Objects.requireNonNull(subKeyFactory.apply(key, parameter)); // 获取subkey [KeyFactory类型] subKeyFactory --> Supplier<V> supplier = valuesMap.get(subKey); value 域 <ProxyClassFactory> 类型 supplier.apply() == ProxyClassFactory.apply() --> Map<Class<?>, Boolean> interfaceSet = new IdentityHashMap<>(interfaces.length); //Verify that the class loader resolves the name of this interface to the same Class object. //Verify that the Class object actually represents an interface. //Verify that this interface is not a duplicate. --> interfaceClass = Class.forName(intf.getName(), false, loader); // 逐个遍历 interfaces --> long num = nextUniqueNumber.getAndIncrement(); --> String proxyName = proxyPkg + proxyClassNamePrefix + num; //生成名称 --> byte[] proxyClassFile = ProxyGenerator.generateProxyClass( proxyName, interfaces, accessFlags); // 生成classbyte [核心] --> return defineClass0(loader, proxyName, proxyClassFile, 0, proxyClassFile.length); //定义类 --> factory = new Factory(key, parameter, subKey, valuesMap);// valueFactory 即 valuesMap 中 value 的封装 --> final Constructor<?> cons = cl.getConstructor(constructorParams); --> final InvocationHandler ih = h; --> return cons.newInstance(new Object[]{h}); -------------------------------------------- 生成$Proxy0 class 反编译 static { try { m1 = Class.forName("java.lang.Object").getMethod("equals", Class.forName("java.lang.Object")); m2 = Class.forName("java.lang.Object").getMethod("toString"); m3 = Class.forName("BookFacade").getMethod("addBook"); m0 = Class.forName("java.lang.Object").getMethod("hashCode"); } catch (NoSuchMethodException var2) { throw new NoSuchMethodError(var2.getMessage()); } catch (ClassNotFoundException var3) { throw new NoClassDefFoundError(var3.getMessage()); } } 生成的方法 public final void addBook() throws { try { super.h.invoke(this, m3, (Object[])null); } catch (RuntimeException | Error var2) { throw var2; } catch (Throwable var3) { throw new UndeclaredThrowableException(var3); } } jdk proxy的调用是一个反射调用的过程
cglib 动态代理的实现分析 代理类继承自org.springframework.cglib.proxy.MethodInterceptor 实现intercept方法 关键代码 :: Enhancer enhancer = new Enhancer(); enhancer.setSuperclass(this.target.getClass()); // 将接口直接设置成BookFacadeProxyCglib 实现类 // 回调方法 // enhancer.setCallbackType(this.getClass()); enhancer.setCallback(this); //设置回调 // 创建代理对象 return enhancer.create(); --> return this.createHelper(); --> this.setNamePrefix(this.superclass.getName());设置NamePrefix --> return super.create(KEY_FACTORY.newInstance(this.superclass != null ? this.superclass.getName() : null, ReflectUtils.getNames(this.interfaces), this.filter, this.callbackTypes, this.useFactory, this.interceptDuringConstruction, this.serialVersionUID)); // 代理产生的几个类 fastclass --> public class BookFacadeImpl$$EnhancerByCGLIB$$677aba98$$FastClassByCGLIB$$dcb5b9cc extends FastClass class --> public class BookFacadeImpl$$EnhancerByCGLIB$$677aba98 extends BookFacadeImpl implements Factory keyFactory --> public class Enhancer$EnhancerKey$$KeyFactoryByCGLIB$$4ce19e8f extends KeyFactory implements EnhancerKey methodwrapperkey --> public class MethodWrapper$MethodWrapperKey$$KeyFactoryByCGLIB$$552be97a extends KeyFactory implements MethodWrapperKey 调用路径 //使用的是这个对象 --> BookFacadeImpl$$EnhancerByCGLIB$$677aba98 | private boolean CGLIB$BOUND; | private static final ThreadLocal CGLIB$THREAD_CALLBACKS; //threadlocal 中存放callback | private static final Callback[] CGLIB$STATIC_CALLBACKS; // static callback | private MethodInterceptor CGLIB$CALLBACK_0; // 用户自己实现的MethodInterceptor | private static final Method CGLIB$addBook$0$Method; // 父类中的callback 方法 | private static final MethodProxy CGLIB$addBook$0$Proxy; // 方法代理 MethodProxy 类 | private static final Object[] CGLIB$emptyArgs; // 方法参数 | private static final Method CGLIB$finalize$1$Method; | private static final MethodProxy CGLIB$finalize$1$Proxy; | private static final Method CGLIB$equals$2$Method; | private static final MethodProxy CGLIB$equals$2$Proxy; | private static final Method CGLIB$toString$3$Method; | private static final MethodProxy CGLIB$toString$3$Proxy; | private static final Method CGLIB$hashCode$4$Method; | private static final MethodProxy CGLIB$hashCode$4$Proxy; | private static final Method CGLIB$clone$5$Method; | private static final MethodProxy CGLIB$clone$5$Proxy; | | static void CGLIB$STATICHOOK1() { | CGLIB$THREAD_CALLBACKS = new ThreadLocal(); | CGLIB$emptyArgs = new Object[0]; | Class var0 = Class.forName("BookFacadeImpl$$EnhancerByCGLIB$$677aba98"); //当前类的实例 | Class var1; | Method[] var10000 = ReflectUtils.findMethods(new String[]{"finalize", "()V", "equals", "(Ljava/lang/Object;)Z", "toString", "()Ljava/lang/String;", "hashCode", "()I", "clone", "()Ljava/lang/Object;"}, (var1 = Class.forName("java.lang.Object")).getDeclaredMethods()); | CGLIB$finalize$1$Method = var10000[0]; | CGLIB$finalize$1$Proxy = MethodProxy.create(var1, var0, "()V", "finalize", "CGLIB$finalize$1"); | CGLIB$equals$2$Method = var10000[1]; | CGLIB$equals$2$Proxy = MethodProxy.create(var1, var0, "(Ljava/lang/Object;)Z", "equals", "CGLIB$equals$2"); | CGLIB$toString$3$Method = var10000[2]; | CGLIB$toString$3$Proxy = MethodProxy.create(var1, var0, "()Ljava/lang/String;", "toString", "CGLIB$toString$3"); | CGLIB$hashCode$4$Method = var10000[3]; | CGLIB$hashCode$4$Proxy = MethodProxy.create(var1, var0, "()I", "hashCode", "CGLIB$hashCode$4"); | CGLIB$clone$5$Method = var10000[4]; | CGLIB$clone$5$Proxy = MethodProxy.create(var1, var0, "()Ljava/lang/Object;", "clone", "CGLIB$clone$5"); // var1 赋值 | CGLIB$addBook$0$Method = ReflectUtils.findMethods(new String[]{"addBook", "()V"}, (var1 = Class.forName("BookFacadeImpl")).getDeclaredMethods())[0]; | CGLIB$addBook$0$Proxy = MethodProxy.create(var1, var0, "()V", "addBook", "CGLIB$addBook$0"); | } --> addBook() --> -->| public final void addBook() { -->| MethodInterceptor var10000 = this.CGLIB$CALLBACK_0;//获取当前类中的methodintercepter -->| if (this.CGLIB$CALLBACK_0 == null) { -->| CGLIB$BIND_CALLBACKS(this); //如果为空 -->| var10000 = this.CGLIB$CALLBACK_0; -->| } -->| -->| if (var10000 != null) { // 执行MethodInterceptor 类中的方法 <实现了MethodInterceptor的类> --> -->| var10000.intercept(this, CGLIB$addBook$0$Method, CGLIB$emptyArgs, CGLIB$addBook$0$Proxy); -->| } else { -->| super.addBook(); -->| } -->| } -->| private static final void CGLIB$BIND_CALLBACKS(Object var0) { -->| BookFacadeImpl$$EnhancerByCGLIB$$677aba98 var1 = (BookFacadeImpl$$EnhancerByCGLIB$$677aba98)var0; -->| if (!var1.CGLIB$BOUND) { -->| var1.CGLIB$BOUND = true; -->| Object var10000 = CGLIB$THREAD_CALLBACKS.get(); -->| if (var10000 == null) { -->| var10000 = CGLIB$STATIC_CALLBACKS; -->| if (CGLIB$STATIC_CALLBACKS == null) { -->| return; -->| } -->| } -->| -->| var1.CGLIB$CALLBACK_0 = (MethodInterceptor)((Callback[])var10000)[0]; -->| } -->| -->| } 实现了 MethodInterceptor的类 -->|>|public class BookFacadeProxyCglib implements MethodInterceptor { -->|>| private Object target; -->|>| -->|>| public Object getInstance(Object target) { -->|>| this.target = target; -->|>| Enhancer enhancer = new Enhancer(); -->|>| enhancer.setSuperclass(this.target.getClass()); -->|>| // 回调方法 -->|>| // enhancer.set b9d8 CallbackType(this.getClass()); -->|>| enhancer.setCallback(this); -->|>| // 创建代理对象 -->|>| return enhancer.create(); -->|>| } -->|>| -->|>| @Override -->|>| public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable { -->|>| System.out.println("before run!"); // 执行MethodProxy的invokeSuper -->|>| proxy.invokeSuper(obj, args); -->|>| System.out.println("after run!"); -->|>| return null; -->|>| } -->|>|} MethodProxy的invokeSuper 方法 -->| public Object invokeSuper(Object obj, Object[] args) throws Throwable { -->| try { -->| this.init(); ------> | private void init() { ------> | if (this.fastClassInfo == null) { ------> | Object var1 = this.initLock; ------> | synchronized(this.initLock) { ------> | if (this.fastClassInfo == null) { ------> | MethodProxy.CreateInfo ci = this.createInfo; ----------------------- 对应 --> CGLIB$addBook$0$Proxy = MethodProxy.create(var1, var0, "()V", "addBook", "CGLIB$addBook$0"); MethodProxy 中的变量赋值 [ c1 = var1 = BookFacadeImpl ] [ c2 = var0 = BookFacadeImpl$$EnhancerByCGLIB$$677aba98 ] [ name1 = addBook = new Signature(name1, desc); ] [ name2 = CGLIB$addBook$0 = new Signature(name2, desc); ] --> | public static MethodProxy create(Class c1, Class c2, String desc, String name1, String name2) { --> | MethodProxy proxy = new MethodProxy(); --> | proxy.sig1 = new Signature(name1, desc); --> | proxy.sig2 = new Signature(name2, desc); --> | proxy.createInfo = new MethodProxy.CreateInfo(c1, c2); --> | return proxy; --> | } ----------------------- ------> | MethodProxy.FastClassInfo fci = new MethodProxy.FastClassInfo(); //实例化FastClassInfo ------> | fci.f1 = helper(ci, ci.c1); ---------------------------------------------------------------------------------------------------------------------- ---->| private static FastClass helper(MethodProxy.CreateInfo ci, Class type) { ---->| Generator g = new Generator(); ---->| g.setType(type); ---->| g.setClassLoader(ci.c2.getClassLoader()); ---->| g.setNamingPolicy(ci.namingPolicy); ---->| g.setStrategy(ci.strategy); ---->| g.setAttemptLoad(ci.attemptLoad); ---->| return g.create(); >| org.springframework.cglib.core.AbstractClassGenerator#create //最终调用AbstractClassGenerator的create方法 ---->| } ---------------------------------------------------------------------------------------------------------------------- ------> | fci.f2 = helper(ci, ci.c2); ------> | fci.i1 = fci.f1.getIndex(this.sig1); ------> | fci.i2 = fci.f2.getIndex(this.sig2); ------> | this.fastClassInfo = fci; ------> | this.createInfo = null; ------> | } ------> | } ------> | } ------> | } -->| MethodProxy.FastClassInfo fci = this.fastClassInfo; -->| return fci.f2.invoke(fci.i2, obj, args); -->| } catch (InvocationTargetException var4) { -->| throw var4.getTargetException(); -->| } -->| }
相关文章推荐
- tomcat源码分析3—>cglib动态代理深度解析
- Java JDK代理、CGLIB、AspectJ代理分析比较
- JDK和Cglib实现动态代理实例及优缺点分析
- JDK和Cglib实现动态代理实例及优缺点分析
- JDK和Cglib实现动态代理实例及优缺点分析
- Java JDK代理、CGLIB、AspectJ代理分析比较
- Java JDK代理、CGLIB、AspectJ代理分析比较
- Java动态代理机制详解(JDK 和CGLIB,Javassist,ASM)
- Java动态代理机制详解(JDK 和CGLIB,Javassist,ASM)
- 使用JDK和Cglib两种方式动态代理
- Java动态代理(JDK接口代理和Cglib类代理)
- 设计模式——代理模式(静态代理和JDK、CGLib动态代理)
- java 基于接口代理(JDK)和基于类的代理(CGLIB)
- Java代理(静态/动态 JDK,cglib)
- JDK动态代理实现分析
- Java动态代理机制详解(JDK 和CGLIB,Javassist,ASM)
- JDK动态代理与CGLIB动态代理
- jdk与cglib的动态代理
- JDK动态动态代理和cglib动态代理的实现
- Java动态代理机制详解(JDK 和CGLIB,Javassist,ASM)