Spring中AOP实现

9 篇文章 0 订阅
  1. 标题之所以没叫Spring AOP实现,是因为SpringAOP的两种实现方式之一是被这样叫的…… -_-T

     

    Spring 中的AOP

    AOPSpring实现有两种:

     

  2. Spring AOP

    本质上就是动态代理+AspectJ的部分功能。被代理的对象必须由Spring容器管理。下文会详述。

    使用这种实现,可以用XMLannotation来做配置管理或aspect的声明等。

     

  3. 完整的AspectJ

    集成了eclipseAspectJ,以实现Weaving等。被代理的对象不需要由Spring容器管理。

     

    那么,在使用的时候如何选择用哪种实现呢?

  4. Spring AOP比用完整的AspectJ要简单,因为它不引进AspectJ的编译器、织入器。所以如果你只是想要去干预Spring Bean的执行过程,那么Spring AOP是最佳选择。

    注意:

    这里有个条件是“Spring Bean”,就是说如果你用了Spring AOP,那么必须用Spring容器来管理这些需要被代理的Bean类。

     

  5. 如果你想要去干预非Spring容器管理的Objects的执行过程,那么就用AspectJ

     

  6. 在之前AOP入门一文中,我提到过,joinpoints可以是任何一个类声明中的一行,比如field getset,那么如果你想要去advise这些并不是方法的joinpoints,必须要使用AspectJ

     

    使用时的style

  7. Spring AOP

    Spring AOP支持xml配置和annotation

    使用XML优点:

    1. 支持任何版本的JDK(可以忽略了,现在大多数都是JDK5+),当然,如果用了named pointcut,还是只能JDK 5+
    2. 如果你用了Spring容器来管理所有的beanservice,那么AOP的配置可以直接写在同一个配置文件中。显得集中而易于维护。

     

    缺点:

    1. 它没有完全的把相关的所有定义放在同一个地方。违反了DRY( Don't Repeat Yourself) 原则,该原则要求在一个系统中,任何一个单独的定义应该是独立、清楚、可靠的。在XML定义中,如何实现代理的这一个requirement被分散到后端的各个bean的定义以及XML的配置中。

    相比之下,@AspectJ这种风格就好的多,因为所有的定义都被封装在一起。

    1. XML风格的配置在组合pointcut时有一定的局限性。比如,在@AspectJ中,你可以这样写:

      @Pointcut(execution(* get*()))
      public void propertyAccess() {}

      @Pointcut(execution(org.xyz.Account+ *(..))
      public void operationReturningAnAccount() {}

      @Pointcut(propertyAccess() && operationReturningAnAccount())
      public void accountPropertyAccess() {}

    XML中,你只能声明前面两个pointcuts

      <aop:pointcut id="propertyAccess"
          expression="execution(* get*())"/>

      <aop:pointcut id="operationReturningAnAccount"
          expression="execution(org.xyz.Account+ *(..))"/>

    第三个联合的pointcutXML配置无法直接实现。

     

    @AspectJ的优点:

    1. 更好的支持aspect,更丰富的pointcut组合方式;
    2. 很好的封装了aspect,使其成为一个单独的modular,便于维护和修改;
    3. @AspectJ切面定义能同时被Spring AOPAspectJ所理解,所以,后期可以很容易的把Spring AOP实现换成AspectJ实现。

     

    个人比较倾向于annotation,因为XML定义最大的好处本来是可以灵活修改,方便维护,但在现在的企业开发中,一旦版本release后,后期修改XML的工作量和修改annotationJava代码量并没有很明显的减少。

     

    注意:

    Spring也支持混合两种使用。

     

  8. AspectJ

    使用完整的AspectJ,定义切面等,可以1)AspectJ语言的语法做.aj文件来写切面或者 2)@AspectJ annotationJAVA文件。具体选择:

    1. AspectJ在你的设计中占据很大的角色时,并且你又刚好是用Eclipse来做开发,那么用AspectJ Development Tools AJDTEclipse插件来使用AspectJ语法来定义是最佳选择:它更整洁和简单,因为AspectJ就是为了写切面而开发的语言。
    2. 如果你不是用Eclipse,或者只有少量的切面,在你的应用中并不占主要角色,你就可以选择用annotation,然后在build脚本中加入AspectWeaving部分。

     

    Spring AOP底层实现

     

    第一种 JDK 自带的动态代理技术

     

    JDK动态代理必须基于接口 进行代理

             作用:使用代理可以对目标对象进行性能监控(计算运行时间)、安全检查(是否具有权限)、记录日志等。

             注意:必须要有接口才能进行代理,代理后对象必须转换为接口类型

    例:



     

    第二种 CGLIB(CodeGenerationLibrary)是一个开源项目    

        

              Spring使用CGlib进行AOP代理, hibernate也是支持CGlib(默认使用 javassist)需要下载cglibjar包(Spring最新版本3.2内部已经集成了cglib无需下载cglib的jar )

             作用:可以为目标类,动态创建子类,对目标类方法进行代理(无需接口)

             原理:Spring AOP底层,会判断用户是根据接口代理还是目标类代理,如果针对接口代理就使用JDK代理,如果针对目标类代理就使用Cglib代理。

              注意:CGLIB要求目标类及其父类一定要有空参构造函数。JAVA默认对所有继承Object的类,都有默认空参构造函数。但是,如果你实现了一个非空参的构造函数,那么空参构造函数就必须显示申明,否则,默认为没有空参构造函数。

     


     

    参考文章:

    http://blog.csdn.net/javaliuzhiyue/article/details/9357849

    http://docs.spring.io/spring/docs/3.2.4.RELEASE/spring-framework-reference/html/aop.html#aop-ataspectj-or-xml

     

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值