• spring——AOP面向切面编程(转载)


    除了控制反转(IoC)和依赖注入(DI)外,Spring 框架还提供了对面向切面编程(AOP)的支持。本节,我们就对 AOP 面向切面编程进行讲解。

    AOP 的全称是“Aspect Oriented Programming”,译为“面向切面编程”,和 OOP(面向对象编程)类似,它也是一种编程思想。

    图1:应用模块的划分


    通常情况下,我们会根据业务使用 OOP(面向对象)思想,将应用划分为多个不同的业务模块,每个模块的核心功能都只为特定的业务领域提供服务,例如电商系统中的订单模块、商品模块、库存模块就分别是为维护电商系统的订单信息、商品信息以及库存信息而服务的。

    但除此之外,应用中往往还存在一些非业务的通用功能,例如日志管理、权限管理、事务管理、异常管理等。这些通用功能虽然与应用的业务无关,但几乎所有的业务模块都会使用到它们,因此这些通用功能代码就只能横向散布式地嵌入到多个不同的业务模块之中。这无疑会产生大量重复性代码,不利于各个模块的复用。

    您可能会想,可以将这些重复性代码封装成为公共函数,然后在业务模块中显式的调用,不也能减少重复性代码吗?是的,这样做的确能一定程度上减少重复性代码,但这样也增加了业务代码与公共函数的耦合性,任何对于公共函数的修改都会对所有与之相关的业务代码造成影响。

     

     

    面向切面编程(AOP)

    与 OOP 中纵向的父子继承关系不同,AOP 是通过横向的抽取机制实现的。它将应用中的一些非业务的通用功能抽取出来单独维护,并通过声明的方式(例如配置文件、注解等)定义这些功能要以何种方式作用在那个应用中,而不是在业务模块的代码中直接调用。

    这虽然设计公共函数有几分类似,但传统的公共函数除了在代码直接硬调用之外并没有其他手段。AOP 则为这一问题提供了一套灵活多样的实现方法(例如 Proxy 代理、拦截器、字节码翻译技术等),可以在无须修改任何业务代码的基础上完成对这些通用功能的调用和修改。

    AOP 编程和 OOP 编程的目标是一致的,都是为了减少程序中的重复性代码,让开发人员有更多的精力专注于业务逻辑的开发,只不过两者的实现方式大不相同。

    OOP 就像是一根“绣花针”,是一种婉约派的选择,它使用继承和组合方式,仔细地为所有涉及通用功能的模块编制成一套类和对象的体系,以达到减少重复性代码的目标。而 AOP 则更像是一把“砍柴刀”,是一种豪放派的选择,大刀阔斧的规定,凡是某包某类下的某方法都一并进行处理。

    AOP 不是用来替换 OOP 的,而是 OOP 的一种延伸,用来解决 OOP 编程中遇到的问题。

     

     

    AOP 联盟

    为了更好的应用 AOP 技术,技术专家们成立了 AOP 联盟(AOP Alliance)。

    AOP 联盟定义了一套用于规范 AOP 实现的底层 API,通过这些统一的底层 API,使得各个AOP 框架及工具产品之间可以相互移植。这些 API 主要以标准接口的形式提供,是 AOP 编程思想所要解决各种问题的最高抽象。所有的 AOP 框架都应该是对这些 AOP 接口规范的具体实现,因此通常我们也将 AOP 框架称作 AOP 实现。

    目前最流行的 AOP 实现(框架)主要有两个,分别为 Spring AOP 和 AspectJ
     

    AOP 框架说明
    Spring AOP 是一款基于 AOP 编程的框架,它能够有效的减少系统间的重复代码,达到松耦合的目的。

    Spring AOP 使用纯 Java 实现,不需要专门的编译过程和类加载器,在运行期间通过代理方式向目标类植入增强的代码。Spring AOP 支持 2 种代理方式,分别是基于接口的 JDK 动态代理和基于继承的 CGLIB 动态代理。
    AspectJ  是一个基于 Java 语言的 AOP 框架,从 Spring 2.0 开始,Spring AOP 引入了对 AspectJ 的支持。

    AspectJ 扩展了 Java 语言,提供了一个专门的编译器,在编译时提供横向代码的植入。

     

     

    AOP 术语

    与大多数的技术一样,AOP 已经形成一套属于自己的概念和术语。

    名称说明
    Joinpoint(连接点) AOP 的核心概念,指的是程序执行期间明确定义的一个点,例如方法的调用、类初始化、对象实例化等。

    在 Spring 中,连接点则指可以被动态代理拦截目标类的方法。
    Pointcut(切入点) 又称切点,指要对哪些 Joinpoint 进行拦截,即被拦截的连接点。
    Advice(通知) 指拦截到 Joinpoint 之后要执行的代码,即对切入点增强的内容。
    Target(目标) 指代理的目标对象,通常也被称为被通知(advised)对象。
    Weaving(织入) 指把增强代码应用到目标对象上,生成代理对象的过程。
    Proxy(代理) 指生成的代理对象。
    Aspect(切面) 切面是切入点(Pointcut)和通知(Advice)的结合。


    Advice 直译为通知,也有人将其翻译为“增强处理”,共有 5 种类型,如下表所示。

    通知说明
    before(前置通知) 通知方法在目标方法调用之前执行
    after(后置通知) 通知方法在目标方法返回或异常后调用
    after-returning(返回后通知) 通知方法会在目标方法返回后调用
    after-throwing(抛出异常通知) 通知方法会在目标方法抛出异常后调用
    around(环绕通知) 通知方法会将目标方法封装起来

     

    AOP 的类型

    AOP 可以被分为以下 2 个不同的类型。

     

    动态 AOP

    动态 AOP 的织入过程是在运行时动态执行的。其中最具代表性的动态 AOP 实现就是 Spring AOP,它会为所有被通知的对象创建代理对象,并通过代理对象对被原对象进行增强。

    相较于静态 AOP 而言,动态 AOP 的性能通常较差,但随着技术的不断发展,它的性能也在不断的稳步提升。

    动态 AOP 的优点是它可以轻松地对应用程序的所有切面进行修改,而无须对主程序代码进行重新编译。

     

    静态 AOP

    静态 AOP 是通过修改应用程序的实际 Java 字节码,根据需要修改和扩展程序代码来实现织入过程的。最具代表性的静态 AOP 实现是 AspectJ。

    相较于动态 AOP 来说,性能较好。但它也有一个明显的缺点,那就是对切面的任何修改都需要重新编译整个应用程序。

     

    AOP 的优势

    AOP 是 Spring 的核心之一,在 Spring 中经常会使用 AOP 来简化编程。

    在 Spring 框架中使用 AOP 主要有以下优势。

    • 提供声明式企业服务,特别是作为 EJB 声明式服务的替代品,最重要的是,这种服务是声明式事务管理。
    • 允许用户实现自定义切面。在某些不适合用 OOP 编程的场景中,采用 AOP 来补充。
    • 可以对业务逻辑的各个部分进行隔离,从而使业务逻辑各部分之间的耦合度降低,提高程序的可重用性,同时也提高了开发效率。
  • 相关阅读:
    python的三个函数map、filter、reduce详解
    python 对文件进行切分行
    sed 命令匹配行操作
    停止学习框架
    JS中双等号“==”使用情况
    JavaScript中数组迭代方法
    JavaScript中replace()方法的第二个参数解析
    Vue生命周期
    JS中浮点数精度误差解决
    大量DOM操作的解决方案
  • 原文地址:https://www.cnblogs.com/xiaobaibailongma/p/16163500.html
Copyright © 2020-2023  润新知