动态代理(动态生成代理类)
:可以控制某个对象(类)的方法,可以在调用这个方法前和方法后做些处理。
核心角色:
- 抽象角色:定义代理角色和真是角色的对外方法。
- 真是角色:实现抽象角色,定义真实的角色所要实现的业务逻辑,供代理角色调用;关注真正的业务逻辑。
- 代理角色:实现抽象的角色,是真实角色的代理,通过真实角色的业务逻辑方法来实现抽象方法,并附加自己的操作;将统一的流程控制放到代理角色中处理。
1. 第一种实现方式:
Rent:抽象角色,定义动作(租房这个动作)
Host:真实角色,真实的业务(真正出租的是房东)
JdkClient:jdk动态代理客户端的调用
JdkProxyHandler:jdk代理角色,流程控制和附加操作
package com.test.dynamicProxy;
/**
* 抽象角色 只定义动作
* @author zhb
*
*/
public interface Rent {
public void seeHouse();
public void signContract();
public void money();
}
package com.test.dynamicProxy;
/**
* 真实角色,真正的业务逻辑
* @author zhb
*
*/
public class Host implements Rent{
@Override
public void seeHouse() {
System.out.println("看房");
}
@Override
public void signContract() {
System.out.println("签合同");
}
@Override
public void money() {
System.out.println("付款");
}
}
package com.test.dynamicProxy.jdk;
import com.test.dynamicProxy.Host;
import com.test.dynamicProxy.Rent;
/**
* 调用jdk动态代理类的客户端
* @author zhb
*
*/
public class JdkClient {
public static void main(String[] args) {
Rent rent = new Host();
JdkProxyHandler handler = new JdkProxyHandler(rent);
Rent proxy = (Rent) handler.getProxy();
proxy.signContract();
}
}
package com.test.dynamicProxy.jdk;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
public class JdkProxyHandler implements InvocationHandler{
private Object target;
public JdkProxyHandler(Object target){
this.target = target;
}
/**
* 获取动态代理对象
* @return
*/
public Object getProxy(){
return Proxy.newProxyInstance(ClassLoader.getSystemClassLoader(), target.getClass().getInterfaces(), this);
}
/**
* 动态执行要方法
*/
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.err.println("调用方法"+method.getName()+"前处理");
method.invoke(target, args);
System.err.println("调用方法"+method.getName()+"后处理");
return null;
}
}
2. 第二种实现方式:
CglibClient:cglib动态代理客户端的调用
CglibProxy:cglib代理角色,流程控制和附加操作
用到的jar包:
package com.test.dynamicProxy.cglib;
import com.test.dynamicProxy.Host;
import com.test.dynamicProxy.Rent;
/**
* 调用cglib动态代理类的客户端
* @author zhb
*
*/
public class CglibClient {
public static void main(String[] args) {
CglibProxy cglibProxy = new CglibProxy();
Rent proxy = (Rent)cglibProxy.getProxy(Host.class);
proxy.signContract();
}
}
package com.test.dynamicProxy.cglib;
import java.lang.reflect.Method;
import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;
/**
*
* @author zhb
*
*/
public class CglibProxy implements MethodInterceptor{
/**
* 获取动态代理对象
* @param target
* @return
*/
public Object getProxy(Object target){
Enhancer enhancer = new Enhancer();
enhancer.setSuperclass((Class) target);
enhancer.setCallback(this);
return enhancer.create();
}
/**
* 动态执行要方法
*/
@Override
public Object intercept(Object o, Method method, Object[] args, MethodProxy methodProxy) throws Throwable {
System.out.println(method.getName());
System.err.println("调用方法"+method.getName()+"前处理");
methodProxy.invokeSuper(o, args);
System.err.println("调用方法"+method.getName()+"后处理");
return null;
}
}
网友评论