Spring+Aspectj+Maven使用xml方式实现aop入门示例

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/u014248473/article/details/88839415

一、本文摘要

  1. 实现AOP的方式采用Spring+Aspectj+Maven+XML配置;
  2. 介绍五种通知方式:前置通知、后置通知、环绕通知、异常通知、异常后置通知;

二、在POM中引入依赖

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.yale</groupId>
    <artifactId>spring-aop</artifactId>
    <version>1.0-SNAPSHOT</version>

    <properties>
        <spring.version>4.2.8.RELEASE</spring.version>
    </properties>

    <dependencies>
        <!-- spring core -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-core</artifactId>
            <version>${spring.version}</version>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-beans</artifactId>
            <version>${spring.version}</version>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>${spring.version}</version>
        </dependency>

        <!-- spring test -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-test</artifactId>
            <version>${spring.version}</version>
        </dependency>

        <dependency>
            <groupId>org.aspectj</groupId>
            <artifactId>aspectjweaver</artifactId>
            <version>1.9.2</version>
        </dependency>

        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.12</version>
            <scope>test</scope>
        </dependency>
    </dependencies>

</project>

三、创建一个接口和实现类

package com.yale.service;

public interface StudentService {
    void insert(String name);
    void delete(int id);
    void update(int id, String name);
    void select(String name);
}

package com.yale.service;

public class StudentServiceImpl implements StudentService {

    public void insert(String name) {
        System.out.println("插入数据:" + name);
    }

    public void delete(int id) {
        System.out.println("删除数据:" + id);
    }

    public void update(int id, String name) {
        System.out.println("更新数据:" + name);
    }

    public void select(String name) {
        System.out.println("查询数据:" + name);
    }
}

四、创建一个通知类

package com.yale.advice;

import org.aspectj.lang.ProceedingJoinPoint;

public class MyAdvice {

    //前置通知
    public void before(){
        System.out.println("前置通知");
    }

    //后置通知,无论是否出现异常都会调用
    public void after(){
        System.out.println("后置通知,无论是否出现异常都会调用");
    }

    //后置通知,出现异常不调用
    public void afterReturning(){
        System.out.println("后置通知,出现异常不调用");
    }

    //异常通知
    public void afterException(){
        System.out.println("异常通知");
    }

    //环绕通知
    public Object around(ProceedingJoinPoint point) throws Throwable{
        System.out.println("环绕通知前置");
        Object object = point.proceed();
        System.out.println("环绕通知后置");
        return object;
    }

}

五、创建一个spring配置文件:spring-aop.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"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
              http://www.springframework.org/schema/beans/spring-beans.xsd
              http://www.springframework.org/schema/aop
              http://www.springframework.org/schema/aop/spring-aop.xsd">

       <!-- 目标对象 -->
       <bean id="studentService" class="com.yale.service.StudentServiceImpl" />

       <!-- 通知对象 -->
       <bean id="myAdvice" class="com.yale.advice.MyAdvice" />

       <!-- 将通知对象织入目标对象 -->
       <aop:config>
              <aop:pointcut id="pointcut" expression="execution(* com.yale.service..*.*(..))" />
              <aop:aspect ref="myAdvice">
                     <aop:before method="before" pointcut-ref="pointcut" />
              </aop:aspect>
       </aop:config>

</beans>

六、创建一个测试类

package com.yale.advice;

import com.yale.service.StudentService;
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:spring-aop.xml")
public class MyAdviceTest {

    @Resource
    private StudentService studentService;

    @Test
    public void test(){
        studentService.insert("tom");
    }

}

1.测试前置通知 myAdvice.before()

直接运行上面的test()方法,返回结果如下:

前置通知
插入数据:tom

ok, 在studentService.insert()方法前成功调用了myAdvice.before()方法。

2.测试后置通知 myAdvice.after()

修改 StudentServiceImpl 中 delete(int id) 方法

public void delete(int id) {
    System.out.println("删除数据:" + id);
    throw new ArithmeticException("arithmeticException");
}

修改 spring-aop.xml 中的 aop:aspect

<aop:aspect ref="myAdvice">
     <!--<aop:before method="before" pointcut-ref="pointcut" />-->
     <aop:after method="after" pointcut-ref="pointcut" />
</aop:aspect>

在 MyAdviceTest 中添加 test2()

@Test
public void test2(){
    try {
        studentService.delete(1);
    }catch (ArithmeticException e){
        System.out.println(e.getMessage());
    }
}

运行 test2() 方法后,返回结果如下:

删除数据:1
后置通知,无论是否出现异常都会调用
arithmeticException

ok, 尽管有异常,还是调用了myAdvice.after()方法。

3.测试异常后置通知 myAdvice.afterReturning()

修改 spring-aop.xml 中的 aop:aspect

<aop:aspect ref="myAdvice">
     <!--<aop:before method="before" pointcut-ref="pointcut" />-->
     <!--<aop:after method="after" pointcut-ref="pointcut" />-->
     <aop:after-returning method="afterReturning" pointcut-ref="pointcut" />
</aop:aspect>

运行 test2() 方法后,返回结果如下:

删除数据:1
arithmeticException

ok,myAdvice.afterReturning()中的打印语句并没有输出,证明遇到异常后并没有调用afterReturning()方法。

4.测试异常后置通知 myAdvice.afterException()

修改 spring-aop.xml 中的 aop:aspect

<aop:aspect ref="myAdvice">
     <!--<aop:before method="before" pointcut-ref="pointcut" />-->
     <!--<aop:after method="after" pointcut-ref="pointcut" />-->
     <!--<aop:after-returning method="afterReturning" pointcut-ref="pointcut" />-->
    <aop:after-throwing method="afterException" pointcut-ref="pointcut" />
</aop:aspect>

运行 test2() 方法后,返回结果如下:

删除数据:1
异常通知
arithmeticException

ok, 遇见异常,调用了myAdvice.afterException()方法。

5.测试异常后置通知 myAdvice.around()

修改 spring-aop.xml 中的 aop:aspect

<aop:aspect ref="myAdvice">
     <!--<aop:before method="before" pointcut-ref="pointcut" />-->
     <!--<aop:after method="after" pointcut-ref="pointcut" />-->
     <!--<aop:after-returning method="afterReturning" pointcut-ref="pointcut" />-->
    <!--<aop:after-throwing method="afterException" pointcut-ref="pointcut" />-->
    <aop:around method="around" pointcut-ref="pointcut" />
</aop:aspect>

运行 test() 方法,返回结果如下:

环绕通知前置
插入数据:tom
环绕通知后置

ok, 成功调用了myAdvice.around()方法。

猜你喜欢

转载自blog.csdn.net/u014248473/article/details/88839415