软件架构师之AOP

  如果要做为一名合格的软件架构师,AOP是必须知道的一门技术。那么AOP是什么呢,这就是今天所讨论的内容(也是本人最近一阵子的学习总结,希望大家多多指点)。

  AOP,全称ASPect Oriented Programming,中文名称叫面向方面编程,也叫面向切面编程

  在实际项目开发过程中,我们往往会注意到有一些模块/功能,如权限,缓存等,需要存在于软件的各个业务模块中,而这些模块/功能又与业务模块没有任何关系,甚至在设计业务模块时我们完全不用考虑这些模块/功能的存在,但是在开发过程中才发现这些模块/功能会给我们带来无尽的烦恼。因为传统的OOP方法考虑问题的出发点往往是要解决问题的本身和延伸,所以遇到此类情况时传统的OOP方法就很难解决。然而对业务模块和此类模块稍作分析,我们就会发现,其实它们本质是相同的,只是解决的问题不同,对一个软件的关注点不同,如下图所示:  

结合自己的经验,由图可知,日志,安全,事务等一类的模块在一个软件项目中的位置,AOP要解决的就是此类问题。 AOP的目标便是对这些“横切关注点”和业务模块解耦,从而提升软件的稳定性,扩展性。

  AOP通常包含以下主要概念:

    1. 方面(ASPect):一个关注点的模块化,这个关注点实现可能另外横切多个对象。事务管理是J2EE应用中横切关注点中一个很好的例子。
    2. 连接点(Joinpoint):程序执行过程中明确的点,如方法的调 用或特定的异常被抛出。
    3. 通知(Advice):在特定的连接点AOP框架执行的动作。各种类型的通知包括“around”、“before”和“throws”通知。通知类型将在下面讨论。许多AOP框架都是以拦截器做通知模型,维护一个“围绕”连接点的拦截器链。
    4. 切入点(Pointcut):指定一个通知将被引发的一系列连接点 的集合。AOP框架必须允许开发者指定切入点:例如,使用正则表达式。
    5. 引入(Introduction):添加方法或字段到通知化类。
    6. 接口(IsModified),来简化缓存。
    7. 目标对象(Target object):包含连接点的对象。也被用来 引用通知化或代理化对象。
    8. AOP代理: AOP框架创建的对象,包含通知。
    9. 织入(Weaving):组装方面创建通知化对象。这可以在编译时完成(例如使用ASPectJ编译器),也可以在运行时完成。Spring和其他一些纯Java AOP框架, 使用运行时织入。

        AOP通知类型包括:

        1. Around通知: 包围一个连接点的通知,如方法调用。这是最强大的通知。Aroud通知在方法调用前后完成自定义的行为。它们负责选择继续执行连接点或直接返回它们自己的返回值或抛出异常来短路执行。
        2. Before通知: 在一个连接点之前执行的通知,但这个通知 不能阻止流程继续执行到连接点(除非它抛出一个异常)。
        3. Throws通知: 在方法抛出异常时执行的通知。
        4. After returning通知: 在连接点正常完成后执行的通知, 例如,如果一个方法正常返回,没有抛出异常。
        5. Around通知是最通用的通知类型。大部分基于拦截器的AOP框架如Nanning和JBoss4只提供 Around通知。

            通常AOP的关注点有以下几方面:

            1. 权限(Authentication)
            2. 缓存(Cache)
            3. 内容传递(Context passing)
            4. 错误处理(Error handling)
            5. 懒加载(Lazy loading)
            6. 调试(Debug)
            7. 日志(Log)
            8. 跟踪,优化,校准(tracing, profiling and monitoring)
            9. 性能优化(Performance optimization)
            10. 持久化(Persistence)
            11. 资源池(Resource pooling)
            12. 同步(Synchronization)
            13. 事务(Transactions)

                了解了AOP的应用场景,下面以权限为例,比较一下传统方法与AOP方法各自的实现,说明AOP技术的应用

                传统方法:

                      BusinessA ClassicsPermission() {
              if (tag == "Pass") {
              return new BusinessA();
              }
              throw new Exception("你没有权限操作BusinessA.");
              }

              it知识库软件架构师之AOP,转载需保留来源!

              郑重声明:本文版权归原作者所有,转载文章仅为传播更多信息之目的,如作者信息标记有误,请第一时间联系我们修改或删除,多谢。