来学习采用Spring框架如何进行面向切面(AOP)编程
使用Spring进行面向切面(AOP)编程
-------------------------------------------------------------
要进行AOP编程,首先我们要在spring的配置文件中引入aop命名空间:
如果要使用切面编程(AOP),还需要下列jar文件
lib/aspectj/aspectjweaver.jar和aspectjrt.jar
lib/cglib/cglib-nodep-2.1_3.jar
我们使用Spring框架进行AOP编程的时候呢,Spring提供了两种切面声明方式,实际工作中我们可以选用其中一种:
1.基于XML配置方式进行AOP开发。
2.基于注解方式进行AOP开发。
对这两种方式都进行下介绍,先学习基于注解方式进行AOP开发
先是beans.xml里,要引入AOP的命名空间,打开配置项
接下来的工作是,定义一个切面,在切面里面定义切入点,所谓切入点就是说我们要对业务bean里面的哪些方法进行拦截,我们还要定义通知,所谓通知,就是说我们拦截到方法后我们需要做的工作。
新建业务bean用作测试,PersonService.java
PersonServiceBean.java
Java代码
用作测试用的业务bean已经开发好了,接着就要进行AOP的开发,因为我们采用的是基于注解的方式来实现AOP功能,先了解一些概念
基于注解方式声明切面
------------------------------------------------------------------------------
在这里@Pointcut("execution(* cn.itcast.service..*.*(..))")
private void anyMethod() {}//声明一个切入点
切入点用来定义我们要拦截的方法,因为Spring只支持方法的拦截,所以这里说的是拦截方法
切入点的定义里面,使用了一个AOP的表达式语言@Pointcut("execution(* cn.itcast.service..*.*(..))"),这个语言是比较灵活的,功能也是比较强大的,在实际使用中呢几乎80%多我们使用的表达式都是类似这种写法,给大家介绍下切入点的表达式的含义。
execution代表执行,执行业务方法的时候我要进行拦截;
第一个*号代表的是返回值的类型,通配符*号表示的话就代表任何的返回值类型;
cn.itcast.service代表的是包名,也就是说你要对哪些包底下的类进行拦截;
然后是两个点..,这两个点代表对cn.itcast.service的子包底下的类也要进行拦截,如果不定义这两个点的话,那么它只会对service包底下的类进行拦截,如果定义了两个点,那么即会对service包底下的类进行拦截,也会对service子包底下的类进行拦截;
第二个*号代表的是类,你要对哪个类进行拦截,*号代表所有类,也就是说service子包底下的所有类进行拦截
第三个*号代表方法,代表所有的方法;
最后的括号里面有两个点(..),这两个点代表方法的参数可以任意,有可以,没有也可以。一个也可以,多个也可以,代表随意
MyInterceptor.java
这样切面就定义好了,在切面里面有我们关注的切入点,并且有我们关注的通知,我们的代码很简洁,当我们定义好切面之后就要注意了,要把MyInterceptor这个切面交给Spring容器管理,如果你不交给Spring管理的话,你定义完了它也不会起效果。
要交给Spring管理的话,有两种方式,一种方式是在配置文件里面通过<bean>元素把它交给Spring管理,还有种方式是通过扫描的方式,加一个注解@Component在public class MyInterceptor{上面的方式把这个bean交给Spring管理。现在并没有开启自动扫描的方式,所以这里就采用基于XML配置的方式把bean交给Spring管理
beans.xml
现在就来开发客户端,在客户端里面我们调用PersonServiceBean这个业务bean的save方法,看一下MyInterceptor这个切面能否帮我们拦截到这个方法,然后在拦截到之前先执行前置通知代码,然后再执行业务方法save()
新建一个单元测试
SpringAOPTest.java
运行单元测试代码,控制台输出
前置通知
我是save()方法
说明,先执行前置通知,在执行业务方法,前置通知起效果了。