1、静态代理,实现代码如下,实际上是对装饰器模式的一种应用
interface UserManager { public void addUser(); } class UserManagerImpl implements UserManager { public void addUser() { System.out.println("raw addUser"); } } class UserManagerImplProxy implements UserManager { private UserManager userManager; public UserManagerImplProxy(UserManager userManager) { this.userManager = userManager; } public void addUser() { System.out.println("in proxy"); userManager.addUser(); } } public class ProxyTest { public static void main(String args[]) { UserManager userManager = new UserManagerImplProxy(new UserManagerImpl()); userManager.addUser(); } }
2、动态AOP,借助 java.lang.reflect.InvocationHandler接口 和 java.lang.reflect.Proxy 类实现
java.lang.reflect.InvocationHandler接口的定义如下:
public interface InvocationHandler { public Object invoke(Object proxy, Method method, Object[] args) throws Throwable; }
Object proxy:被代理的对象
Method method:要调用的方法
Object[] args:方法调用时所需要参数
invoke 方法用于切面处理,调用相应的方法
java.lang.reflect.Proxy类的定义如下:
public static Object newProxyInstance(ClassLoader loader, Class<?>[] interfaces, InvocationHandler h) throws IllegalArgumentException
CLassLoader loader: 类的加载器
Class<?> interfaces: 得到全部的接口
InvocationHandler h: 实现 InvocationHandler 接口的子类的实例
import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; import java.lang.reflect.Proxy; interface UserManager { public void addUser(); } class UserManagerImpl implements UserManager { public void addUser() { System.out.println("raw addUser"); } } class UserManagerImplProxy implements InvocationHandler { private Object targetObject; public void log() { System.out.println("message info"); } public Object createProxyInstance(Object targetObject) { this.targetObject = targetObject; return Proxy.newProxyInstance(targetObject.getClass().getClassLoader(), targetObject.getClass().getInterfaces(), this); } @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { log(); Object ret = method.invoke(targetObject, args); return ret; } } public class ProxyTest { public static void main(String args[]) { UserManagerImplProxy proxy = new UserManagerImplProxy(); UserManager manager = (UserManager) proxy.createProxyInstance(new UserManagerImpl()); manager.addUser(); } }
3、动态代码字节生成
CGLib是动态代码字节生成的实现,它封装字节码生成工具Asm,原理是在运行期间目标字节码加载后,生成目标类的子类,将切面逻辑加入到子类中,所以使用Cglib实现AOP不需要基于接口。cglib 的核心是实现 MethodInterceptor 接口,使用 intercept() 方法进行面向切面的处理,调用相应的通知。其中 cglib 中有一个 Enhancer 类,可以使用他快速的创建一个代理类。
import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; import java.lang.reflect.Proxy; import net.sf.cglib.proxy.Enhancer; import net.sf.cglib.proxy.MethodInterceptor; import net.sf.cglib.proxy.MethodProxy; interface UserManager { public void addUser(); } class UserManagerImpl implements UserManager { public void addUser() { System.out.println("raw addUser"); } } class CGLIBProxyFactory implements MethodInterceptor{ // 要放回的代理对象 private Object obj; public Object createProxy(Object obj) { // 把传进来的代理对象赋值给obj this.obj = obj; Enhancer enhancer = new Enhancer(); // 需要为其实例指定一个父类,也就是我们 的目标对象,那么我们新创建出来的对象就是目标对象的子类,有目标对象的一样 enhancer.setSuperclass(this.obj.getClass()); // 除此之外,还要指定一个回调函数,这个函数就和Proxy的 invoke()类似 enhancer.setCallback(this); return enhancer.create(); } public void log() { System.out.println("message info"); } @Override public Object intercept(Object object, Method method, Object[] args, MethodProxy methodProxy) throws Throwable { Object proxyObject = null; UserManagerImpl um = (UserManagerImpl) obj; log(); proxyObject = methodProxy.invoke(um, args); return proxyObject; } } public class ProxyTest { public static void main(String args[]) { CGLIBProxyFactory gb = new CGLIBProxyFactory(); UserManager manager = (UserManager)gb.createProxy(new UserManagerImpl()); manager.addUser(); } }