透过字节码分析Java动态代理机制。
Posted linlf03
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了透过字节码分析Java动态代理机制。相关的知识,希望对你有一定的参考价值。
一、创建动态代理代码
1、创建接口
public interface Subject void request();
2、创建接口实现类
public class RealSubject implements Subject @Override public void request() System.out.println("From real subject");
3、创建DynamicSubject类
public class DynamicSubject implements InvocationHandler private Object sub; public DynamicSubject(Object obj) this.sub = obj; @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable System.out.println("before calling:" + method); method.invoke(this.sub, args); System.out.println("after calling:" + method); return null;
4、创建测试类
public class Client public static void main(String[] args) System.getProperties().put("sun.misc.ProxyGenerator.saveGeneratedFiles","true"); RealSubject rs = new RealSubject(); InvocationHandler ds = new DynamicSubject(rs); Class<?> cls = rs.getClass(); Subject subject = (Subject) Proxy.newProxyInstance(cls.getClassLoader(), cls.getInterfaces(), ds); subject.request(); System.out.println(subject.getClass()); System.out.println(subject.getClass().getSuperclass());
输出结果:
before calling:public abstract void com.example.jvm.bytecode.Subject.request() From real subject after calling:public abstract void com.example.jvm.bytecode.Subject.request() class com.sun.proxy.$Proxy0 class java.lang.reflect.Proxy
查看源码,动态代理类在ProxyGenerator类的generateProxyClass生成。
public static byte[] generateProxyClass(final String var0, Class<?>[] var1, int var2) ProxyGenerator var3 = new ProxyGenerator(var0, var1, var2); final byte[] var4 = var3.generateClassFile(); if(saveGeneratedFiles) AccessController.doPrivileged(new PrivilegedAction<Void>() public Void run() try int var1 = var0.lastIndexOf(46); Path var2; if(var1 > 0) Path var3 = Paths.get(var0.substring(0, var1).replace(‘.‘, File.separatorChar), new String[0]); Files.createDirectories(var3, new FileAttribute[0]); var2 = var3.resolve(var0.substring(var1 + 1, var0.length()) + ".class"); else var2 = Paths.get(var0 + ".class", new String[0]); Files.write(var2, var4, new OpenOption[0]); return null; catch (IOException var4x) throw new InternalError("I/O exception saving generated file: " + var4x); ); return var4;
可以发现saveGeneratedFiles为true时,可以将代理类保存到磁盘上。
因此在测试类中sun.misc.ProxyGenerator.saveGeneratedFiles属性设置为true
System.getProperties().put("sun.misc.ProxyGenerator.saveGeneratedFiles","true");
最终生成的.class 文件位置如下图
以上是关于透过字节码分析Java动态代理机制。的主要内容,如果未能解决你的问题,请参考以下文章
jvm原理(36)透过字节码生成审视Java动态代理运作机制