意图:为其他对象提供一种代理以控制对这个对象的访问。
主要解决:在直接访问对象时带来的问题,比如说:要访问的对象在远程的机器上(RMI)。比如在这个方法执行时的前后进行前后处理(aop)。
何时使用:想在访问一个对象时做一些控制。
如何解决:增加中间层代理层proxy。
- JDKProxy,主要用来对接口及接口对象进行代理。
public class DirectJDKProxy {
private static Object getProxy(Object object) {
Class<?> klass = object.getClass();
//获取类加载器
ClassLoader classLoader = klass.getClassLoader();
//获取其所有的接口
Class<?>[] interfaces = klass.getInterfaces();
//获取代理对象
return Proxy.newProxyInstance(classLoader, interfaces, new InvocationHandler() {
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("前置处理");
Object result = method.invoke(object, args);
System.out.println("后置处理");
return result;
}
});
}
public static void main(String[] args) {
SomeClass someClass = new SomeClass();
ISomeClass someClassProxy = (ISomeClass) DirectJDKProxy.getProxy(someClass);
String str = someClassProxy.doDealString("这里是原始参数!");
System.out.println("执行结果:" + str);
System.out.println("-----------------------------------------");
str = someClass.doDealString("这是第二次用原对象执行时的原始参数");
System.out.println(str);
}
执行结果为:
可以看到结果中用代理给方法执行前和执行后加入了代码且执行了,而原对象没有。
也可以从代码中:
//获取类加载器
ClassLoader classLoader = klass.getClassLoader();
//获取其所有的接口
Class<?>[] interfaces = klass.getInterfaces();
//获取代理对象
return Proxy.newProxyInstance(classLoader, interfaces, new InvocationHandler() );
可以模糊的看出实际上是代理类继承了所有接口,像是一个复制品,但这个接口复制品可以给里面添加处理方法。
2.CglibProxy:主要是对普通类进行代理:
import java.lang.reflect.Method;
import com.smy.about_proxy.jdk.eg.Complex;
import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;
public class SimpleCglibProxy {
private Object object;
public SimpleCglibProxy() {
}
public Object getObject() {
return object;
}
p