静态代理
public class TargetClass{
void method1()
}
public class ProxyClass{
private TargetClass target;
public void method1(){
target.method1()
}
}
- 代理类持有目标类的引用
动态代理
public interface TargetIntf{
void method1();
}
public DynamicProxy implements InvocationHandler{
@Override
public Object invoke(Object o, Method method, Object[] args){
//do proxy
}
}
InvocationHandler handler = new DynamicProxy();
Proxy theProxy = (TargetIntf)Proxy.newInstance(hander.getClass().getClassLoader(), new Class[]{TargetIntf.class}, handler);
theProxy.method1()
- 要有接口
- 要实现InocationHandler
- 通过Proxy.newInstance来生成代理类
- 通过强转取得目标类的实例
如何理解动态代理
当调用theProxy的method1时,会触发handler.invoke方法的调用,方法(Method)和参数都会传递给invoke方法,invoke方法里面想做什么都行。
为什么Proxy.newInstance可以强转成TargetIntf呢?
Proxy.newInstance返回的对象实现了TargetIntf接口的方法,所以可以强转。
为什么调用proxy的method1方法会调用到handler的invoke方法?
Proxy.newInstance返回的对象组合了handler,并在method1方法的实现逻辑中添加了handler.invoke的调用。
Proxy.newInstance如何动态的实现TargetIntf的方法并返回对象实例呢?
动态的生成class文件,java类的信息都是从class文件加载进来的,Proxy.newInstance方法中动态的生成了class文件并加载。
动态代理能干嘛?
- 提供了另外一种实现接口的方式,不用implements也能实现接口。
- 可以用来写框架
试想一下,如果没有动态代理,dubbo框架如何实现?
动态代理的dubbo实现:
- client和server端都依赖api的接口
- client端不实现api接口,通过动态代理,把api接口调用连接到Invocation.invoke方法上,在此方法中将对象、方法名、参数等通过网络发送给server端
- server端实现api的接口,把client端发送过来的rpc调用连接到api接口的具体实现上。
没有动态代理的实现:
- client和server端都依赖api接口
- client端实现api接口,接口的实现逻辑为把对象、方法名、参数等通过网络发送给server端
- server端实现api的接口,把client端发送过来的rpc调用连接到api接口的具体实现上。
有了动态代理,dubbo rpc中的网络交互部分可以完全写在dubbo框架中,对用户来说编程更加方便。
没有动态代理,client端的api实现代码也可以通过工具自动生成,不过这样让框架使用起来更加的复杂。
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。