为什么需要AOP?
OOP存在的局限性
- 静态化语言中的类结构限制
1.1 类结构固定:在静态化语言(如Java)中,类的结构在编译时就被固定下来,这意味着类的字段、方法等成员一旦定义,在运行时难以动态修改。
1.2 当然我们可以通过修改字节码的方式进行修改,修改以后使用ClassLoader进行重新加载,但是这样的操作过于麻烦对程序员的要求比较高,还可能引起很多问题。
灵活性受限:虽然可以通过字节码操作来修改类结构并重新加载,但这通常较为复杂且容易出错,不适合日常开发中的频繁使用。 - 侵入性拓展的挑战
比如我们定义的API已经发布了一个版本,这个时候我们需要进行拓展不能直接修改标准的API会影响到现有的使用。我们不得不通过继承或者组合发方式来拓展功能。
2.1 继承的局限性:
类层次复杂:过度使用继承可能导致类层次过于复杂,维护困难。
多继承限制:Java不支持多重继承,这限制了某些设计模式的应用。
2.2 组合的局限性:
接口耦合:当通过组合来扩展功能时,如果现有类的接口设计不合理,可能会导致组合类的设计变得复杂。
依赖过多:组合可能会引入过多的依赖关系,使得系统变得难以理解和维护。
AOP 的应用场景
- 日志场景:比如log4j或logback中的MDC,可以帮助我们打印一些辅助信息,比如打印方法的执行时间。
MDC(Mapped Diagnostic Context)是一种用于区分来自不同来源日志的工具。它的本质是一个由日志框架维护的Map存储结构,应用程序可以向其中写入键值对,并被日志框架访问。 - 统计场景:比如方法执行次数,执行异常次数,数据抽样,
- 安防场景:比如熔断(Hystrix),限流和降级(Sentinel),认证和授权(Spring Security),监控(JMX)
- 性能场景:比如缓存(Spring Cache),超时控制。