1. Spring AOP
-
代理模式
设计目的旨在为服务类与客户类之间插入其他功能,插入的功能对于调用者是透明的,起到伪装控制的作用。 如租房的例子:房客、中介、房东。 对应于代理模式中即:客户类、代理类 、委托类(被代理类)。 代理模式的两个设计原则: 1.代理类与委托类具有相似的行为(共同)。 2.代理类增强委托类的行为。 1.静态代理 三要素: 1.有共同的行为(结婚) - 接口 2.目标角色(新人) - 实现行为 3.代理角色(婚庆公司) - 实现行为 增强目标对象行为 特点: 1.目标角色固定。 2.在应用程序执行前就得到目标角色。 3.代理对象会增强目标对象的行为。 4.有可能存在多个代理 引起"类爆炸"(缺点)。 实现: 1.定义行为(共同) 定义接口。 2.目标对象(实现行为)。 3.代理对象(实现行为、增强目标对象的行为)。 4.通过代理对象实现目标对象的功能。 2.动态代理 动态代理类的字节码在程序运行时,由Java反射机制动态产生。 动态代理不仅简化了编程工作,而且提高了软件系统的可扩展性,因为反射机制可以生成任意类型的动态代理类。 特点: 1.目标对象不固定 。 2.在应用程序执行时动态创建目标对象 。 3.代理对象会增强目标对象的行为。 实现: 1.JDK动态代理(JDK动态代理的目标对象必须有接口实现) 1.newProxyInstance Proxy类: Proxy类是专门完成代理的 *** 作类,可以通过此类为一个或多个接口动态地生成实现类,此类提供了如下 *** 作方法: /*返回一个指定接口的代理类的实例方法调用分派到指定的调用处理程序。 (返回代理对象) loader:一个ClassLoader对象,定义了由哪个ClassLoader对象来对生成的代理对象进行加载 。 interfaces:一个Interface对象的数组,表示的是我将要给我需要代理的对象提供一组什么接口, 如果我提供了一组接口给它,那么这个代理对象就宣称实现了该接口(多态), 这样我就能调用这组接口中的方法了 。 h:一个InvocationHandler接口,表示代理实例的调用处理程序实现的接口。每个代理实例都具有一个关联的调用处理程序。 对代理实例调用方法时,将对方法调用进行编码并将其指派到它的调用处理程序的 invoke 方法(传入InvocationHandler接口的子类)。*/ public static Object newProxyInstance(ClassLoader loader, Class>[] interfaces, InvocationHandler h) 2.获取代理对象 public class JdkHandler implements InvocationHandler { //目标对象 private Object target; // 目标对象的类型不固定,创建时动态生成 //通过构造器将目标对象赋值 public JdkHandler(Object target) { this.target = target; } /*** 1、调用目标对象的方法(返回Object) * 2、增强目标对象的行为 * @param proxy 调用该方法的代理实例 * @param method 目标对象的方法 * @param args 目标对象的方法形参 * @return * @throws Throwable */ @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { //增强行为 System.out.println("==============方法前执行"); //调用目标对象的方法(返回Object) Object result = method.invoke(target,args); //增强行为 System.out.println("方法后执行=============="); return result; } /*** 得到代理对象 * @return */ public Object getProxy() { return Proxy.newProxyInstance(this.getClass().getClassLoader(),target.getClass().getInt erfaces(),this); } } 3.通过代理对象实现目标对象的功能 //目标对象 You you = new You(); //获取代理对象 JdkHandler jdkHandler = new JdkHandler(you); Marry marry = (Marry) jdkHandler.getProxy(); //通过代理对象调用目标对象中的方法 marry.toMarry(); Java动态代理类中的invoke是怎么调用的: 在生成的动态代理类$Proxy0.class中,构造方法调用了父类Proxy.class的构造方法,给成员变量 invocationHandler赋值, $Proxy0.class的static模块中创建了被代理类的方法,调用相应方法时方法体中调用了父类中的成员变量InvocationHandler的invoke()方法。 2.CGLIB动态代理 cglib是针对类来实现代理的,它的原理是对指定的目标类生成一个子类,并覆盖其中方法实现增强, 但因为采用的是继承,所以不能对final修饰的类进行代理。 1.添加依赖 pom.xml:
cglib cglib2.2.2 -
AOP
Aspect Oriented Programing面向切面编程,相比较oop面向对象编程来说,Aop关注的不再是程序代码中某个类,某些方法, 而aop考虑的更多的是一种面到面的切入,即层与层之间的一种切入,所以称之为切面。 作用: AOP主要应用于日志记录,性能统计,安全控制,事务处理等方面,实现公共功能性的重复使用。 特点: 1.降低模块与模块之间的耦合度,提高业务代码的聚合度。(高内聚低 耦合) 2.提高了代码的复用性。 3.提高系统的扩展性。(高版本兼容低版本) 4.可以在不影响原有的功能基础上添加新的功能。 底层实现: 动态代理(JDK + CGLIB) 基本概念: 1.Joinpoint(连接点) 被拦截到的每个点,spring中指被拦截到的每一个方法,spring aop一个连接点即代表一个方法的执行。 2.Pointcut(切入点) 对连接点进行拦截的定义(匹配规则定义 规定拦截哪些方法,对哪些方法进行处理),spring有专门的表达式语言定义。 3.Advice(通知) 拦截到每一个连接点即(每一个方法)后所要做的 *** 作。 1.前置通知 (前置增强)— before() 执行方法前通知 。 2.返回通知(返回增强)— afterReturn 方法正常结束返回后的通知 3.异常抛出通知(异常抛出增强)— afetrThrow() 4.最终通知 — after 无论方法是否发生异常,均会执行该通知。 5.环绕通知 — around 包围一个连接点(join point)的通知,如方法调用。 这是最强大的一种通知类型。 环绕通知可以在方法调用前后完成自定义的行为。它也会选择是否继续执行连接点或直接返回它们自己的 返回值或抛出异常来结束执行。 4.Aspect(切面) 切入点与通知的结合,决定了切面的定义, 切入点定义了要拦截哪些类的哪些方法, 通知则定义了拦截过方法后要做什么, 切面则是横切关注点的抽象,与类相似,类是对物体特征的抽象,切面则是横切关注点抽象。 5.Target(目标对象) 被代理的目标对象。 6.Weave(织入) 将切面应用到目标对象并生成代理对象的这个过程即为织入。 7.Introduction(引入) 在不修改原有应用程序代码的情况下,在程序运行期为类动态添加方法或者字段的过程称为引入。
-
Spring AOP的实现
环境搭建: 坐标依赖引入:
org.aspectj aspectjweaver1.8.9
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)