java

关注公众号 jb51net

关闭
首页 > 软件编程 > java > AspectJ实现AOP

基于AspectJ注解方式实现AOP

作者:96岁对抗java

这篇文章主要介绍了基于AspectJ注解方式实现AOP,使用AspectJ的注解可以更方便地编写和管理切面逻辑,而Spring AOP也是使用了AspectJ提供的注解来实现切面编程,需要的朋友可以参考下

基于AspectJ实现AOP(注解方式)

这里我们采用的是非完全注解方式

1. 创建类, 在类里面定义方法(连接点)

package com.ffyc.spring.aop;
//被增强的类(也就是被代理的类)
public class User {
    //被增强的方法(也就是被代理的方法)
    public void add(){
        System.out.println("add...");
    }
}

2. 创建增强类, 编写增强逻辑

package com.ffyc.spring.aop;
//增强类
public class UserProxy {
    //前置通知
    public void before(){
        System.out.println("before");
    }
    //这里还有后置通知, 异常通知, 环绕通知, 最终通知等, 现在逻辑先省略
}

3. 进行通知的配置

①: 在spring配置文件中, 开启注解扫描与开启注解自动生成代理对象

<!--    开启组件扫描, 开启了组件扫描之后我们的spring容器就会在对应的base-package位置进行一个扫描-->
    <!--    注意: 其实我们的组件扫描也是可以通过使用注解的方式进行配置-->
        <context:component-scan base-package="com.ffyc.spring"></context:component-scan>
<!--    开启Aspectj自动生成代理对象-->
        <aop:aspectj-autoproxy></aop:aspectj-autoproxy>

②: 使用注解创建User和UserProxy类的对象

package com.ffyc.spring.aop;
import org.springframework.stereotype.Component;
//被增强的类(也就是被代理的类)
@Component
public class User {
    //被增强的方法(也就是被代理的方法)
    public void add(){
        System.out.println("add...");
    }
}
package com.ffyc.spring.aop;
import org.springframework.stereotype.Component;
//增强类
@Component
public class UserProxy {
    //前置通知
    public void before(){
        System.out.println("before");
    }
}

③: 在增强类上面添加注解@Aspect

package com.ffyc.spring.aop;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;
//增强类
@Component
@Aspect
public class UserProxy {
    //前置通知
    public void before(){
        System.out.println("before");
    }
}

4. 配置不同类型的通知

package com.ffyc.spring.aop;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;
//增强类
@Component
@Aspect
public class UserProxy {
    @Pointcut(value = "execution(* com.ffyc.spring.aop.User.add(..))")
    private void method(){
    }
    //前置通知
    @Before(value = "execution (* com.ffyc.spring.aop.User.add(..))")
    public void before(){
        System.out.println("before...");
    }
    @AfterReturning(value = "method()")
    public void afterReturning(){
        System.out.println("afterReturning...");
    }
    @After(value = "execution(* com.ffyc.spring.aop.User.add(..))")
    public void after(){
        System.out.println("after...");
    }
    @AfterThrowing(value = "method()")
    public void afterThrowing(){
        System.out.println("afterThrowing...");
    }
    @Around(value = "method()")
    public void around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
        System.out.println("环绕前...");
        proceedingJoinPoint.proceed();
        System.out.println("环绕之后...");
    }
}

5. 测试:

package com.ffyc.spring.aop;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class TestAop {
    @Test
    public void testAop(){
        ApplicationContext applicationContext = new ClassPathXmlApplicationContext("spring.xml");
        User user = applicationContext.getBean("user", User.class);
        System.out.println(user);
        user.add();
    }
}

各个通知的执行顺序:

环绕前[@Around(前)] --> 前置通知[@Before] --> 被增强方法(切入点) --> 环绕后(@Around(后)) --> 最终通知(@After) --> 后置通知[@AfterReturning] (或者异常通知[@AfterThrowing])

补充:

@Aspect注解为什么要和@Component注解一起使用, 按理将使用一个@Aspect注解不是就已经是由SpringIOC荣IQ创建代理对象并交由SpringIOC容器管理了?

**官方文档解释如下: **

You may register aspect classes as regular beans in your Spring XML configuration, or autodetect them through classpath scanning - just like any other Spring-managed bean. However, note that the @Aspect annotation is not sufficient for autodetection in the classpath: For that purpose, you need to add a separate @Component annotation (or alternatively a custom stereotype annotation that qualifies, as per the rules of Spring’s component scanner).

翻译:

您可以在Spring XML配置中注册aspect类,或者通过类路径扫描自动检测它们,就像任何其他Spring管理bean一样。但是,请注意,@aspect注释对于在类路径中自动检测是不够的:为了达到这个目的,您需要添加一个单独的@component注解(或者根据Spring的组件扫描器的规则来定义一个定制的原型注解)

到此这篇关于基于AspectJ注解方式实现AOP的文章就介绍到这了,更多相关AspectJ实现AOP内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

您可能感兴趣的文章:
阅读全文