[原创]spring及springmvc精简版--AOP
接上一篇:[原创]spring及springmvc精简版--IOC
理解AOP。java是一种面向对象的语言。而AOP是面向切面,在我看来是面向逻辑或者业务编程,它是对一组逻辑的抽象和分配。
经典例子,很多系统都有日志。以登录为例子。常规编程流程大致如下:点击登录--->写入日志--->后台处理--->写入日志。因为我们的系统中会有很多功能逻辑代码都是如此去处理日志。假设有一天,需求改变不需要日志了。那么我们如何去处理这些已经存在于整体逻辑单元中的日志代码?无非是找到每一个使用日志的地方,逐一删除。大家可想这样的效率?代码的耦合度?
而AOP变成。就是为了高度的解耦儿产生。它将登录的整个流程进行按照特定的,共同的业务逻辑进行切割,从而抽象出来了一组公共的逻辑单元。然后在根据不同业务模块的需求,在某些业务指定的地方将公共的业务逻辑植入其中,从而形成了一个整体的业务逻辑单元,实现某一模块功能。(这些是自己思考,总结的,刚开始接触的时候,没有理解到这点,也吃了很多闭门羹)有了这样的认识和理解,我们理解spring AOP中的一些常用的概念就很简单:
横切关注点:哪些业务需要拦截,拦截后干什么?
切面:若干个横切关注点的抽象结合。即:抽象出来的公共的业务逻辑单元
连接点:需要拦截的业务。原本剩下的业务逻辑
切入点:连接点的表达式。和通知相似。
通知:将共同的逻辑代码植入的提示。前置,后置,异常,返回,环绕。
1.applicationContext.xml
1 <?xml version="1.0" encoding="UTF-8"?>
2 <beans xmlns="http://www.springframework.org/schema/beans"
3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4 xmlns:aop="http://www.springframework.org/schema/aop"
5 xmlns:context="http://www.springframework.org/schema/context"
6 xmlns:tx="http://www.springframework.org/schema/tx"
7 xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
8 http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.0.xsd
9 http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.0.xsd
10 http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.0.xsd">
11 <!--
12 <bean id="person" class="com.bean2.Person">
13 <constructor-arg value="12" type="int"></constructor-arg>
14 </bean>
15 -->
16
17 <bean id="myMath" class="com.bean2.MyMath"></bean>
18
19 <bean id="mylog" class="com.bean2.Log"></bean>
20 <!-- aop配置 -->
21 <aop:config>
22 <!--配置切入点
23 * com.bean.person.*(..):person类中的所有方法
24 * com.bean.*.*(..) bean包里的所有类的所有犯法
25 * com.bean.person.add*(int,int) :person 类中以add开头的方法,并且参数是两个int值
26 -->
27 <aop:pointcut expression="execution(* com.bean2.MyMath.*(..))" id="pc"/>
28 <!-- 切面 -->
29 <aop:aspect ref="mylog">
30 <!-- 通知
31 <aop:before method="beforelog" pointcut-ref="pc"/>
32 <aop:after method="afterlog" pointcut-ref="pc" />
33 <aop:after-returning method="returnLog" pointcut-ref="pc" returning="o"/>
34 <aop:after-throwing method="throwLog" pointcut-ref="pc" throwing="e"/>
35 -->
36
37 <aop:around method="aroundLog" pointcut-ref="pc"/>
38 </aop:aspect>
39 </aop:config>
40 </beans>
2.Log
1 package com.bean2;
2
3 import java.util.Arrays;
4
5 import org.aspectj.lang.JoinPoint;
6 import org.aspectj.lang.ProceedingJoinPoint;
7
8 public class Log {
9
10 public void beforelog(JoinPoint jp){
11 String methodName = jp.getSignature().getName();
12 Object[] os = jp.getArgs();
13 System.out.println("正在运行"+methodName+"方法,参数是:"+Arrays.asList(os));
14 }
15 public void afterlog(JoinPoint jp){
16 String methodName = jp.getSignature().getName();
17 System.out.println(methodName+"方法运行完");
18 }
19 public void returnLog(JoinPoint jp,Object o){
20 String methodName = jp.getSignature().getName();
21 System.out.println(methodName+"方法的返回结果是:"+o);
22 }
23 public void throwLog(JoinPoint jp,Throwable e){
24 String methodName = jp.getSignature().getName();
25 System.out.println(methodName+"方法发生了异常,异常信息是:"+e.getMessage());
26 }
27
28 public void aroundLog(ProceedingJoinPoint jp){
29 String methodName = jp.getSignature().getName();
30 Object[] os = jp.getArgs();
31 //前置
32 System.out.println("正在运行"+methodName+"方法,参数是:"+Arrays.asList(os));
33 //执行目标对象
34 try {
35 Object result = jp.proceed();
36 //返回
37 System.out.println(methodName+"方法的返回结果是:"+result);
38 } catch (Throwable e) {
39 // TODO Auto-generated catch block
40 e.printStackTrace();
41 //异常
42 System.out.println(methodName+"方法发生了异常,异常信息是:"+e.getMessage());
43 }finally{
44 //后置通知
45 System.out.println(methodName+"方法运行完");
46 }
47 }
48 }
3.MyMath
1 package com.bean2;
2
3 public class MyMath {
4
5 public int add(int num1,int num2){
6
7 int result = num1+num2;
8 return result;
9 }
10 public int sub(int num1,int num2){
11 //System.out.println("正在运行sub方法,参数是:"+num1+","+num2);
12 int result = num1-num2;
13
14 //System.out.println("sub方法运行完,结果是:"+result);
15 return result;
16 }
17 public int div(int num1,int num2){
18 int result = num1/num2;
19 return result;
20 }
21 public int mul(int num1,int num2){
22 int result = num1*num2;
23 return result;
24 }
25 }
4.Person
1 package com.bean2;
2
3 public class Person {
4
5 private double num1;
6 private int num2;
7
8
9 public Person(double num){
10 System.out.println("double");
11 this.num1 = num;
12 }
13 public Person(int num){
14 System.out.println("int");
15 this.num2 = num;
16 }
17 public void show(){
18 System.out.println(num1+","+num2);
19
20 }
21
22 }