什么是AOP?
从百度百科上,大概的定义是这样的
在软件业,AOP为Aspect Oriented Programming的缩写,意为:面向切面编程,通过预编译方式和运行期动态代理实现程序功能的统一维护的一种技术。AOP是OOP的延续,是软件开发中的一个热点,也是Spring框架中的一个重要内容,是函数式编程的一种衍生范型。利用AOP可以对业务逻辑的各个部分进行隔离,从而使得业务逻辑各部分之间的耦合度降低,提高程序的可重用性,同时提高了开发的效率。
小总结:
- AOP是一种编程范式,不是编程语言
- AOP是OOP的补充,不是替代
- AOP是用来解决特定问题的,不是全部问题
除了AOP,我们所熟知的编程范式大概如下:
- 面向过程编程
- 面向对象编程
- 函数式编程
- 事件驱动编程
- 面向切面编程
AOP用来干什么?
从上面的定义我们可以了解到,AOP可以降低代码耦合度,提高程序可重用性,提高开发效率。其初衷就是为了解决代码重用性的问题,一般我们用来通用化功能代码的实现。
举个栗子:一个商城有权限模块、产品模块、订单模块、支付模块等,这些模块都用到日志的记录,比如记录IP地址、记录URI等等,倘若在每个模块都单独去写,不但代码很难维护,也增加了不少的工作量。
通用化功能代码的实现就能很好的解决这个问题,它就是一个切面,与业务功能模块分离。
常见的关注点分离有:
水平分离:展示层 ->服务层->持久层
垂直分离:模块划分(订单、库存等)
切面分离:分离功能性需求与非功能性需求
AOP的好处
- 集中处理某一个关注点/横切逻辑
- 方便添加删除关注点
- 侵入性少,增强代码可读性及可维护性
AOP的使用场景(偏非功能性需求)
- 权限控制
- 缓存控制
- 事务控制
- 审计日志
- 性能监控
- 分布式追踪
- 异常处理
AOP的三种织入方式
- 编译时织入:需要特殊的Java编译器,如AspectJ
- 类加载时织入:需要特殊的Java编译器,如AspectJ和AspectWerkz
- 运行时织入:Spring采用的方式,通过动态代理的方式,实现简单
AOP相关的关键词
- Aspect:切面,通用化功能代码的实现就是切面
- Target:被织入Aspect的目标对象
- JoinPoint:作为切入点的机会,所有方法都可以作为切入点
- PointCut:Aspect实际被应用的切入点,也就是JoinPoint,支持正则
- Advice:类里的方法以及这个方法如何织入到目标方法的方式
- Weaving:Aop的实现方式
其中Advice的种类有
- 前置通知(Before)
- 后置通知(AfterReturning)
- 异常通知(AfterThrowing)
- 最终通知(After)
- 环绕通知(Aroud)