一. 知识储备
1.1 前置通知
-
在方法前添加@Before注解,但是会报错,它说没有添加相关的属性值。其实是指定value=“xxx”。
-
value=“xxx”: 表示切入点的表达式,即你要在哪个方法前使用这个前置通知。前面讲到切入点类似于查找数据库记录里面的条件
-
所以要表示某个方法,必须要说明它的修饰符 返回值类型 所在类的全类名.方法名(参数列表的类型)如下图:
-
写好表达式后,我们就可以在方法里面写日志功能。这时要用到连接点JoinPoint。
-
连接点:即相当于数据库里面的记录,包含当前相关的信息。而在刚刚的切入点表达式
value="public int com.atguigu.spring.aop.aspectJ.ArithmeticCalculatorImpl.add(int, int)"
- 所以此时的连接点就是这个add方法。它包含这个add方法的所有信息(如方法名,形参),如下:
//方法名
String methodName = joinPoint.getSignature().getName();
//方法的参数列表
Object[] args = joinPoint.getArgs();
解释: 上面代码中的getSignature()是获取方法的签名,方法的签名包含方法名和参数列表
1.2 前置通知例子
ArithmeticCalculator.java
package com.atguigu.spring.aop.aspectJ;
/**
* 算数计算器
* @author user
*
*/
public interface ArithmeticCalculator {
/**
* 加法
* @param i
* @param j
* @return
*/
public int add(int i, int j);
/**
* 减法
* @param i
* @param j
* @return
*/
public int sub(int i, int j);
/**
* 乘法
* @param i
* @param j
* @return
*/
public int mul(int i, int j);
/**
* 除法
* @param i
* @param j
* @return
*/
public int div(int i, int j);
}
ArithmeticCalculatorImpl.java
package com.atguigu.spring.aop.aspectJ;
import org.springframework.stereotype.Component;
@Component
public class ArithmeticCalculatorImpl implements ArithmeticCalculator {
@Override
public int add(int i, int j) {
// TODO Auto-generated method stub
int result = i + j;
return result;
}
@Override
public int sub(int i, int j) {
// TODO Auto-generated method stub
int result = i - j;
return result;
}
@Override
public int mul(int i, int j) {
// TODO Auto-generated method stub
int result = i * j;
return result;
}
@Override
public int div(int i, int j) {
// TODO Auto-generated method stub
int result = i / j;
return result;
}
}
spring-annotation.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.0.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.0.xsd">
<!-- 组件扫描 -->
<context:component-scan base-package="com.atguigu.spring.aop.aspectJ" >
</context:component-scan>
<!-- 开启AOP注解支持,为切面所能作用到的目标类生成代理 -->
<aop:aspectj-autoproxy></aop:aspectj-autoproxy>
</beans>
LoggingAspect.java
package com.atguigu.spring.aop.aspectJ;
import java.util.Arrays;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.springframework.stereotype.Component;
/**
* 切面:日志切面
* @author user
*
*/
@Component //标识为一个组件
@Aspect //标识为一个切面
public class LoggingAspect {
/**
* 前置通知:在方法执行之前执行
* value: 切入点表达式
* 连接点对象: JoinPoint , 包含当前连接点相关信息(即当前作用的方法,即切入点表达式里面的方法)
*
*/
@Before(value = "execution(public int com.atguigu.spring.aop.aspectJ.ArithmeticCalculatorImpl.add(int, int))")
public void beforeMethod(JoinPoint joinPoint) {
//方法名
String methodName = joinPoint.getSignature().getName();
//方法的参数列表
Object[] args = joinPoint.getArgs();
System.out.println("LoggingAspect==> The method " + methodName + " begin with : " + Arrays.asList(args));
}
}
Main.java
package com.atguigu.spring.aop.aspectJ;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class Main {
public static void main(String[] args) {
ApplicationContext context =
new ClassPathXmlApplicationContext("spring-annotation.xml");
ArithmeticCalculator ac =
context.getBean("arithmeticCalculatorImpl", ArithmeticCalculator.class);
int result = ac.add(1, 1);
System.out.println("Main==>: " + result);
}
}
1.3 后置通知例子
在LoggingAspect.java中添加以下方法
/**
* 后置通知:在方法执行之后,不管目标方法有无抛出异常都会执行
* 切入点表达式:
* * : 任意修饰符任意返回值
* * : 包下的任意类
* * :类中任意方法
* ..: 任意参数列表
*/
@After(value="execution(* com.atguigu.spring.aop.aspectJ.*.*(..))")
public void afterMethod(JoinPoint joinPoint) {
String methodName = joinPoint.getSignature().getName();
System.out.println("LoggingAspect==> The method " + methodName + " ends.");
}
Android_la
发布了194 篇原创文章 · 获赞 16 · 访问量 1万+
私信
关注