首先,要引入AspectJ
并且在applicationContext.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:aop="http://www.springframework.org/schema/aop"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="
http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd">
<!--自动注册-->
<context:component-scan base-package="com.ibuyi.free"/>
<!--aspectj aop代理-->
<aop:aspectj-autoproxy/>
</beans>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aop</artifactId>
<version>5.2.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.8.9</version>
</dependency>
然后我们就可以愉快的使用了!
先梳理一下AspectJ支持的几种通知
- 前置通知 @Before
- 后置通知 @AfterReturning
- 环绕通知 @Round
- 异常通知 @AfterThrowing
作用就不介绍了我们直接开始使用实战
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;
@Aspect
//Aspectj注解,可以认为是切面
@Component("aspectj")
//注解注册bean
public class MyAspectj {
//前置通知
//其中execution指定需要对那个类或者那个方法进行aop代理
@Before(value = "save()")
public void before(){
System.out.println("aspectj执行前置操作");
}
//后置通知
//其中returning指的是原代理方法的返回值
@AfterReturning(value = "save()",returning = "result")
public void after(Object result){
System.out.println("aspectj执行后置通知");
System.out.println(result);
}
//环绕通知
@Around(value = "execution(* com.ibuyi.free.spring.Product.delete (..))")
public Object around(ProceedingJoinPoint joinPoint) throws Throwable {
System.out.println("环绕前置通知");
//如果这里不执行joinPoint.proceed()方法,则会拦截原代理方法的执行
Object obj=joinPoint.proceed();
System.out.println("环绕后置通知");
return obj;
}
//异常通知
@AfterThrowing(value = "execution(* com.ibuyi.free.spring.Product.* (..))",throwing = "error")
public void error(Throwable error){
System.out.println("发生异常"+error.getMessage());
}
@Pointcut(value = "execution(* com.ibuyi.free.spring.Product.save(..))")
private void save(){
//指定save方法,这里必须是void和private类型,上面的通知可以直接调用这个切入点,就作用在save方法上了
}
}
package com.ibuyi.free.spring;
import org.springframework.stereotype.Component;
//目标类
@Component("product")
public class Product {
public void save(){
System.out.println("保存操作");
}
public void delete(){
System.out.println("删除操作");
}
public String update(){
System.out.println("更新操作");
return "helloworld";
}
public void find(){
System.out.println("查询操作");
}
}
package com.ibuyi.free.spring;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import javax.annotation.Resource;
//测试类
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:applicationContext.xml")
public class iTest {
@Resource(name = "product")
Product product;
@Test
public void demo1(){
product.save();
}
}
上面是通过注解方法使用AspectJ,下面介绍如何通过xml配置使用AspectJ
<?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:aop="http://www.springframework.org/schema/aop"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="
http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd">
<!--目标类-->
<bean id="person" class="com.ibuyi.free.spring.Person"/>
<!--切面类-->
<bean id="myaspectjxml" class="com.ibuyi.free.spring.MyAspectJXml"/>
<!--配置aop-config-->
<aop:config>
<aop:pointcut id="point1" expression="execution(* com.ibuyi.free.spring.Person.say(..))"></aop:pointcut>
<aop:aspect ref="myaspectjxml">
<aop:before method="save" pointcut-ref="point1"/>
</aop:aspect>
</aop:config>
</beans>
package com.ibuyi.free.spring;
public class Person {
public void say(){
System.out.println("说话....");
}
public void sleep(){
System.out.println("睡觉....");
}
public void eat(){
System.out.println("吃饭....");
}
public void smile(){
System.out.println("微笑....");
}
}
package com.ibuyi.free.spring;
public class MyAspectJXml {
public void save(){
System.out.println("前置通知");
}
}
结果可以自行测试!