代理模式
为某一个对象(委托类)提供一个代理(代理类),用来控制对这个对象的访问
委托类和代理类有一个共同的父类或接口
代理模式的两个设计原则:
- 代理类和委托类具有共同的行为
- 代理类能够增强委托类的行为
常见的代理模式:
静态代理
动态代理
静态代理
代理三要素
1、有共同的行为 —定义接口
2、目标 —实现接口
3、代理--实现接口 增强行为
public interface Marry {
public void toMarry();
}
public class MarryCompanyProxy implements Marry {
private Marry target;
public MarryCompanyProxy(Marry target) {
this.target = target;
}
@Override
public void toMarry() {
System.out.println("marry before...");
target.toMarry();
System.out.println("marry after...");
}
}
public class You implements Marry {
@Override
public void toMarry() {
System.out.println(" i am marry ");
}
}
public class StaticProxy {
public static void main(String[] args) {
Marry marry = new You();
MarryCompanyProxy proxy = new MarryCompanyProxy(marry);
proxy.toMarry();
}
}
动态代理
!在这里插入图片描述
JDK动态代理
public interface Marry {
public void toMarry();
}
public class You implements Marry {
@Override
public void toMarry() {
System.out.println(" i am marry ");
}
}
//jdk动态代理类
public class JdkHanlder implements InvocationHandler {
//目标对象,为可变对象
private Object target;
//通过带参构造器传递目标对象
public JdkHanlder(Object target) {
this.target = target;
}
public Object getProxy(){
Object object = Proxy.newProxyInstance(this.getClass().getClassLoader(),
target.getClass().getInterfaces(),
this);
return object;
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
//用户的增强行为
System.out.println("方法执行前");
//调用目标对象中的方法
Object object = method.invoke(target,args);
System.out.println("方法执行后");
return object;
}
}
测试方法
public class StaticProxy {
public static void main(String[] args) {
You you = new You();
JdkHanlder jdkHanlder = new JdkHanlder(you);
Marry target = (Marry) jdkHanlder.getProxy();
target.toMarry();
}
}
运行结果
方法执行前
i am marry
方法执行后
Process finished with exit code 0
CGLIB动态代理
JDK动态代理机制只能代理实现了接口的类,cglib是针对类来实现代理的,他的原理是对指定的目标类生成一个子类,并覆盖其中的方法实现增强,但是因为采用的是继承,所以不能的对final修饰的类进行代理。
public class CglibInterceptor implements MethodInterceptor {
//目标对象
private Object target;
public CglibInterceptor(Object target) {
this.target = target;
}
//获取代理对象
public Object getProxy(){
Enhancer enhancer = new Enhancer();
enhancer.setSuperclass(target.getClass());
enhancer.setCallback(this);
return enhancer.create();
}
/**
* 拦截器 1、目标对象的方法调用 2、行为增强
* @param o
* @param method
* @param objects 参数列表
* @param methodProxy
* @return
* @throws Throwable
*/
@Override
public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
System.out.println("方法执行前");
Object object = methodProxy.invoke(target,objects);
System.out.println("方法执行后");
return object;
}
}
public class You1 {
public void toMarry() {
System.out.println(" i am marry ");
}
}
测试
public class StaticProxy {
public static void main(String[] args) {
You1 you = new You1();
CglibInterceptor cglibInterceptor = new CglibInterceptor(you);
You1 you1 = (You1) cglibInterceptor.getProxy();
you1.toMarry();
}
}
运行结果
方法执行前
Disconnected from the target VM, address: '127.0.0.1:57413', transport: 'socket'
i am marry
方法执行后
Process finished with exit code 0