- 浏览: 6305822 次
- 性别:
- 来自: 一片神奇的土地
文章分类
- 全部博客 (745)
- JQuery (25)
- JS (33)
- 数据库 (59)
- Java基础 (56)
- JSON (8)
- XML (8)
- ireport (7)
- 设计模式 (10)
- 心情 (14)
- freemarker (1)
- 问题 (15)
- powerdesigner (2)
- CSS (15)
- DWR (4)
- tomcat (16)
- Hibernate (12)
- Oracle (7)
- Struts (7)
- Spring (34)
- JSP (23)
- 需学习 (64)
- 工具类库 (63)
- Maven (14)
- 笔试题 (34)
- 源码学习 (31)
- 多线程 (39)
- Android (32)
- 缓存 (20)
- SpringMVC (14)
- jQueryEasyUi (12)
- webservice-RPC (13)
- ant (1)
- ASP.NET (10)
- 正则表达式 (3)
- Linux (15)
- JBoss (1)
- EJB (3)
- UML (2)
- JMS (3)
- Flex (8)
- JSTL (2)
- 批处理 (5)
- JVM (16)
- 【工具】 (16)
- 数据结构 (29)
- HTTP/TCP/Socket (18)
- 微信 (1)
- tomcat源码学习 (15)
- Python (30)
- 主机 (2)
- 设计与架构 (19)
- thrift-RPC (2)
- nginx (6)
- 微信小程序 (0)
- 分布式+集群 (12)
- IO (1)
- 消息队列 (4)
- 存储过程 (8)
- redis (9)
- zookeeper (5)
- 海量数据 (5)
最新评论
-
360pluse:
技术更新,战术升级!Python爬虫案例实战从零开始一站通网盘 ...
Python爬虫实战:Scrapy豆瓣电影爬取 -
18335864773:
推荐用 pageoffice 组件生成 word 文件。
JAVA生成WORD工具类 -
jjhe369:
LISTD_ONE 写道起始地址为163.135.0.1 结束 ...
IP地址与CIDR -
baojunhu99:
private final int POOL_SIZE = 5 ...
使用CompletionService获取多线程返回值 -
LovingBaby:
胡说,javascript 运行时是单线程的,event lo ...
Ajax请求是否可以实现同步
引子:
AOP(面向方面编程:Aspect Oriented Programing)和IoC一样是Spring容器的内核,声明式事务的功能在此基础上开花结果。但是AOP和OOP差别较大,要很好地理解这个概念,做到心领神会还是不容易的,不过相信看完帖子,你就不再迷惑了。
编程语言最终极的目标就是能以更自然、更灵活的方式模拟世界,从原始机器语言到过程语言再到面向对象的语言,编程语言一步步地用更自然、更灵活的方式描述软件。AOP是软件开发思想发展到一定阶段的产物,但AOP的出现并不是要完全替代OOP,而仅是作为OOP的有益补充。虽然AOP作为一项编程技术已经有多年的历史,但一直长时间停留在学术领域,直到近几年,AOP才作为一项真正的实用技术在应用领域开疆扩土。需要指出的是AOP的应用场合是受限的,它一般只适合于那些具有横切逻辑的应用场合:如性能监测、访问控制、事务管理以及日志记录(虽然有很多文章用日志记录作为讲解AOP的实例,但很多人认为很难用AOP编写实用的程序日志,笔者对此观点非常认同)。不过,这丝毫不影响AOP作为一种新的软件开发思想在软件开发领域所占有的地位。
AOP到底是什么
AOP是Aspect Oriented Programing的简称,最初被译为“面向方面编程”,这个翻译向来为人所诟病,但是由于先入为主的效应,受众广泛,所以这个翻译依然被很多人使用,但我们更倾向于用“面向切面编程”的译法,因为它更加达意。
按照软件重构思想的理念,如果多个类中出现相同的代码,应该考虑定义一个共同的抽象类,将这些相同的代码提取到抽象类中。比如Horse、Pig、Camel这些对象都有run()、eat()的方法,通过引入一个包含这两个方法抽象的Animal父类,Horse、Pig、Camel就可以通过继承Animal复用到run()和eat()的方法。通过引入父类消除多个类中重复代码的方式在大多情况下是可行的,但世界并非永远这样简单,请看下面论坛管理业务类的代码:
代码清单6-1 ForumService
- package com.baobaotao.concept;
- public class ForumService {
- private TransactionManager transManager;
- private PerformanceMonitor pmonitor;
- private TopicDao topicDao;
- private ForumDao forumDao;
- public void removeTopic(int topicId) {
- pmonitor.start();//①-1性能监控开始
- transManager.beginTransaction();//②-1 事务处理开始
- topicDao.removeTopic(topicId); //③-1 业务逻辑
- transManager.commit();//②-1事务处理结束
- pmonitor.end();//①-2 性能监控结束
- }
- public void createForum(Forum forum) {
- pmonitor.start();//①-1性能监控开始
- transManager.beginTransaction();//②-1 事务处理开始
- forumDao.create(forum); //③-2 业务逻辑
- transManager.commit();//②-1事务处理结束
- pmonitor.end();//①-2 性能监控结束
- }
- …
- }
代码清单6-1中①的代码是方法性能监视代码,它在方法调用前启动,在方法调用返回前结束,并在内部记录性能监视的结果信息。
而②的代码是事务开始和事务提交的代码。我们发现③处的业务代码淹没在重复化非业务性的代码之中,性能监视和事务管理这些非业务性代码葛藤缠树般包围着业务性代码。
如图6-1所示,假设我们将ForumService业务类看成一段圆木,将removeTopic()和createForum()方法分别看成圆木的一截,我们会发现性能监视和事务管理的代码就好像一个年轮,而业务代码是圆木的树心,这也正是横切代码概念的由来。
我们无法通过抽象父类的方式消除以上所示的重复性横切代码,因为这些横切逻辑依附在业务类方法的流程中,它们不能转移到其他地方去。
AOP独辟蹊径通过横向抽取机制为这类无法通过纵向继承体系进行抽象的重复性代码提供了解决方案。对于习惯了纵向抽取的开发者来说,可能不容易理解横向抽取方法的工作机制,因为Java语言本身不直接提供这种横向抽象的能力,我们暂把具体实现放在一旁,先通过图解的方式归纳出AOP的解决思路,如图6-2所示。
从图6-2中,我们可以看出AOP希望将这些分散在各个业务逻辑代码中的相同代码,通过横向切割的方式抽取到一个独立的模块中,还业务逻辑类一个清新的世界。
当然,我们知道将这些重复性的横切逻辑独立出来是很容易的,但如何将这些独立的逻辑融合到业务逻辑中完成和原来一样的业务操作,这才是事情的关键,也正是AOP要解决的主要问题。
AOP术语
如学习电学就得先学习电阻、电压、电容等专业术语一样,AOP也有一些自己的行话,为了方便后面的学习,我们先来学习一下AOP相关重要术语。
连接点(Joinpoint)
程序执行的某个特定位置:如类开始初始化前、类初始化后、类某个方法调用前、调用后、方法抛出异常后。一个类或一段程序代码拥有一些具有边界性质的特定点,这些代码中的特定点就称为“连接点”。Spring仅支持方法的连接点,即仅能在方法调用前、方法调用后、方法抛出异常时以及方法调用前后这些程序执行点织入增强。我们知道黑客攻击系统需要找到突破口,没有突破口就无法进行攻击,从某种程度上来说,AOP是一个黑客(因为它要向目前类中嵌入额外的代码逻辑),连接点就是AOP向目标类打入楔子的候选点。
连接点由两个信息确定:第一是用方法表示的程序执行点;第二是用相对点表示的方位。如在Test.foo()方法执行前的连接点,执行点为Test.foo(),方位为该方法执行前的位置。Spring使用切点对执行点进行定位,而方位则在增强类型中定义。
切点(Pointcut)
每个程序类都拥有多个连接点,如一个拥有两个方法的类,这两个方法都是连接点,即连接点是程序类中客观存在的事物。但在这为数众多的连接点中,如何定位到某个感兴趣的连接点上呢?AOP通过“切点”定位特定接连点。通过数据库查询的概念来理解切点和连接点的关系再适合不过了:连接点相当于数据库中的记录,而切点相当于查询条件。切点和连接点不是一对一的关系,一个切点可以匹配多个连接点。
在Spring中,切点通过org.springframework.aop.Pointcut接口进行描述,它使用类和方法作为连接点的查询条件,Spring AOP的规则解析引擎负责解析切点所设定的查询条件,找到对应的连接点。其实确切地说,用切点定位应该是执行点而非连接点,因为连接点是方法执行前、执行后等包括方位信息的具体程序执行点,而切点只定位到某个方法上,所以如果希望定位到具体连接点上,还需要提供方位信息。
增强(Advice)
增强是织入到目标类连接点上的一段程序代码。是不是觉得AOP越来越像黑客了:),这不是往业务类中装入木马吗?读者大可按照这一思路去理解增强,因为这样更形象易懂。在Spring中,增强除用于描述一段程序代码外,还拥有另一个和连接点相关的信息,这便是执行点的方位。结合执行点方位信息和切点信息,我们就可以找到特定的连接点了!正因为增强既包含了用于添加到目标连接点上的一段执行逻辑,又包含了用于定位连接点的方位信息,所以Spring所提供的增强接口都是带方位名的:BeforeAdvice、AfterRetuningAdvice、ThrowsAdvice等。BeforeAdvice表示方法调用前的位置,而AfterReturingAdvice表示访问返回后的位置。所以只有结合切点和增强两者一起上阵才能确定特定的连接点并实施增强逻辑。
目标对象(Target)
增强逻辑的织入目标类。如果没有AOP,目标业务类需要自己实现所有逻辑,就如中ForumService所示。在AOP的帮助下,ForumService只实现那些非横切逻辑的程序逻辑,而性能监视和事务管理等这些横切逻辑则可以使用AOP动态织入到特定的连接点上。
引介(Introduction)
引介是一种特殊的增强,它为类添加一些属性和方法。这样,即使一个业务类原本没有实现某个接口,通过AOP的引介功能,我们可以动态地为该业务类添加接口的实现逻辑,让业务类成为这个接口的实现类。
织入(Weaving)
织入是将增强添加对目标类具体连接点上的过程,AOP像一台织布机,将目标类、增强或者引介通过AOP这台织布机天衣无缝地编织到一起。我们不能不说“织入”这个词太精辟了。根据不同的实现技术,AOP有三种织入的方式:
1)编译期织入,这要求使用特殊的Java编译器;
2)类装载期织入,这要求使用特殊的类装载器;
3)动态代理织入,在运行期为目标类添加增强生成子类的方式。
Spring采用动态代理织入,而AspectJ采用编译期织入和类装载期织入。
代理(Proxy)
一个类被AOP织入增强后,就产出了一个结果类,它是融合了原类和增强逻辑的代理类。根据不同的代理方式,代理类既可能是和原类具有相同接口的类,也可能就是原类的子类,所以我们可以采用调用原类相同的方式调用代理类。
切面(Aspect)
切面由切点和增强(引介)组成,它既包括了横切逻辑的定义,也包括了连接点的定义,Spring AOP就是负责实施切面的框架,它将切面所定义的横切逻辑织入到切面所指定的连接点中。
AOP的工作重心在于如何将增强应用于目标对象的连接点上,这里首先包括两个工作:第一,如何通过切点和增强定位到连接点上;第二,如何在增强中编写切面的代码。本章大部分的内容都围绕这两点展开。
AOP的实现者
AOP工具的设计目标是把横切的问题(如性能监视、事务管理)模块化。使用类似于OOP的方式进行切面的编程工作。位于AOP工具核心的是连接点模型,它提供了一种机制,可以识别出在哪里发生了横切。
AspectJ
AspectJ是语言级的AOP实现,2001年由Xerox PARC的AOP小组发布,目前版本已经更新到1.6。AspectJ扩展了Java语言,定义了AOP语法,能够在编译期提供横切代码的织入,所以它有一个专门的编译器用来生成遵守Java字节编码规范的Class文件。主页位于http://www.eclipse.org/aspectj。
AspectWerkz
基于Java的简单、动态、轻量级的AOP框架,该框架2002年就已经发布,由BEA Systems提供支持。它支持运行期或类装载期织入横切代码,所以它拥有一个特殊的类装载器。现在,AspectJ和AspectWerkz项目已经合并,以便整合两者的力量和技术创建统一的AOP平台。他们合作的第一个发布版本是AspectJ 5:扩展AspectJ语言,以基于注解的方式支持类似AspectJ的代码风格。
JBoss AOP
2004年作为JBoss应用程序服务器框架的扩展功能发布,读者可以从这个地址了解到JBoss AOP的更多信息:http://www.jboss.org/products/aop。
Spring AOP
Spring AOP使用纯Java实现,它不需要专门的编译过程,不需要特殊的类装载器,它在运行期通过代理方式向目标类织入增强代码。Spring并不尝试提供最完整的AOP实现,相反,它侧重于提供一种和Spring IoC容器整合的AOP实现,用以解决企业级开发中的常见问题。在Spring中,我们可以无缝地将Spring AOP、IoC和AspectJ整合在一起。
这些文章摘自于我的《Spring 3.x企业应用开发实战》的第6章。欢迎大家讨论。
延伸阅读:学习Spring必学的Java基础知识----动态代理http://www.iteye.com/topic/1123293
来源:http://stamen.iteye.com/blog/1512388
发表评论
-
Spring 配置多数据源实现数据库读写分离
2014-10-09 11:05 58152现在大型的电子商务 ... -
strust_spring_hibernate的优缺点
2014-10-08 09:41 2713struts框架具有组件的模块化,灵活性和重用性的优点,同时 ... -
声明式事务
2014-09-03 17:53 1740跟开涛学Spring 数据库事务 本 ... -
@Component注解
2014-08-20 15:43 37734Spring自带的@Component注 ... -
日志记录、性能监控的三种实现方式
2014-08-18 14:09 7561一、需解决的问题 部分API有签名参数(signatur ... -
BeanWrapper 设置和获取属性值
2014-08-18 11:10 95865.4. Bean处理和BeanWrapper - Spr ... -
SpringMVC的拦截器Interceptor
2014-08-15 10:23 5037跟开涛学SpringMVC 接口: Ha ... -
AOP
2014-08-14 17:00 10673跟开涛学Spring 问题: 使用BeanFac ... -
Bean作用域
2014-08-14 15:16 1740跟开涛学Spring 附:单例模式的DoubleChec ... -
DI
2014-08-14 10:26 1739跟开涛学Spring DI: ... -
IOC + 容器
2014-08-13 18:03 2869跟开涛学Spring 传统应用程序示意图 ... -
Spring中Bean初始化实例【重要】
2014-07-21 16:48 61150可参考文章: Spring Bean 生命周期 Spr ... -
bean的生命周期
2014-07-21 15:41 1465在spring中,从BeanFactory或Applica ... -
Spring中BeanPostProcessor
2014-07-21 15:19 50575Spring提供了很多扩展 ... -
context,listener,filter,servlet加载顺序
2014-04-22 14:08 7999web.xml加载过程(步骤):1.启动WEB项目的时候, ... -
Spring+hibernate的session问题
2013-09-27 10:20 3144在spring框架和hibernate框架集成的时候,根据 ... -
HttpServletRequestWrapper 用法
2013-09-25 16:50 8403HttpServletRequestWrapper ... -
IOC
2012-05-09 10:11 1552引述:IoC(控制反转:I ... -
事务隔离级别
2012-03-08 11:39 10335模拟数据库的四种隔离级别1 模拟数据库的四种隔离级 ... -
Spring事务的传播方式
2012-02-24 11:05 12422传播方式: 新建事务 req ...
相关推荐
spring-aop-1.1.1.jar spring-aop-1.2.6.jar spring-aop-1.2.9.jar spring-aop-2.0.2.jar spring-aop-2.0.6.jar spring-aop-2.0.7.jar spring-aop-2.0.8.jar spring-aop-2.0.jar spring-aop-2.5.1.jar spring-aop-...
开发工具 spring-aop-4.3.6.RELEASE开发工具 spring-aop-4.3.6.RELEASE开发工具 spring-aop-4.3.6.RELEASE开发工具 spring-aop-4.3.6.RELEASE开发工具 spring-aop-4.3.6.RELEASE开发工具 spring-aop-4.3.6.RELEASE...
赠送jar包:spring-aop-5.2.0.RELEASE.jar; 赠送原API文档:spring-aop-5.2.0.RELEASE-javadoc.jar; 赠送源代码:spring-aop-5.2.0.RELEASE-sources.jar; 赠送Maven依赖信息文件:spring-aop-5.2.0.RELEASE.pom;...
3、对spring aop认识模糊的,不清楚如何实现Java 自定义注解的 4、想看spring aop 注解实现记录系统日志并入库等 二、能学到什么 1、收获可用源码 2、能够清楚的知道如何用spring aop实现自定义注解以及注解的逻辑...
使用 Spring AOP 进行方法耗时监测的好处有以下几点: 1. 代码实现简单,易于维护:使用 Spring AOP 可以将耗时监测的逻辑与业务逻辑进行解耦,避免业务逻辑代码的冗余和代码维护难度的提高。 2. 安全性高:使用 ...
开发工具 aopalliance-1.0开发工具 aopalliance-1.0开发工具 aopalliance-1.0开发工具 aopalliance-1.0开发工具 aopalliance-1.0开发工具 aopalliance-1.0开发工具 aopalliance-1.0开发工具 aopalliance-1.0开发工具...
AOP的概念也很好理解,跟中间件差不多,说白了,就是我可以任意地在方法的前面或后面添加代码,这很适合用于缓存、日志等处理。 在net core2.2时,我当时就尝试过用autofac实现aop,但这次我不想用autofac,我用了一...
spring aop spring aop spring aop spring aop spring aop spring aop spring aop spring aop spring aop
内容概要:springboot+拦截器+aop+自定义注解+本地线程实现统一接口日志记录,记录下接口所在模块、接口描述、接口请求参数、接口返回参数、接口请求时间以及接口耗时用于接口优化,接口记录参数以及操作人防止使用...
在Spring1.2或之前的版本中,实现AOP的传统方式就是通过实现Spring的AOP API来定义Advice,并设置代理对象。Spring根据Adivce加入到业务流程的时机的不同,提供了四种不同的Advice:Before Advice、After Advice、...
java项目中 AOP事务所需要用的jar包....................................啊..........................................................
赠送jar包:spring-aop-5.0.10.RELEASE.jar; 赠送原API文档:spring-aop-5.0.10.RELEASE-javadoc.jar; 赠送源代码:spring-aop-5.0.10.RELEASE-sources.jar; 赠送Maven依赖信息文件:spring-aop-5.0.10.RELEASE....
基于注解实现SpringAop基于注解实现SpringAop基于注解实现SpringAop
aop所依赖的所有包+文档+源码,最新版全套aop aspectjweaver aopalliance aspects aspectjrt
AOP的意思就是面向切面编程。本文主要是通过梳理JDK中自带的反射机制,实现 AOP动态代理模式,这也是Spring AOP 的实现原理
spring aop jar 包
在使用spring的aop功能时,这两个jar是必须的,否则会报错,如下: Caused by: java.lang.ClassNotFoundException: org.aspectj.weaver.reflect.ReflectionWorld$ReflectionWorldException at java.net....
Spring是一个轻量级的控制反转(IoC)和面向切面(AOP)的容器框架。Spring AOP:通过配置管理特性,Spring AOP 模块直接将面向方面的编程功能集成到了 Spring 框架中。所以,可以很容易地使 Spring 框架管理的任何对象...
AOP in .NET: Practical Aspect-Oriented Programming 296 pages Publisher: Manning Publications; Pap/Psc edition (June 25, 2013) Language: English ISBN-10: 1617291145 ISBN-13: 978-1617291142 ...
SpringBoot下的Spring——DAY04——动态代理总结、AOP、自定义注解进行拦截、动态获取注解参数、通知方法 1.动态代理总结 1.1 JDK动态代理特点 1.2 CGlib动态代理 1.2.1 CGLib特点说明 1.3 动态代理的作用 2 Spring...