spring--aop--02--注解实现

一、实现aop的三步:

  1. 创建目标类与切面类,加入到Spring容器中,并指明切面类
  2. 在切面类方法上标注通知注解
  3. 开启注解版aop模式

二、aop注解版实现代码

spring配置文件代码

<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.xsd
                            http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd">
    <!--开启注解扫描,用于扫描bean,IOC部分内容-->
    <context:component-scan base-package="com.fuping3.aopanno"/>


    <!--开启注解版aop-->
    <aop:aspectj-autoproxy></aop:aspectj-autoproxy>


</beans>

java代码:

package com.fuping3.aopanno;

import org.springframework.stereotype.Component;

@Component
public class User{
    public int  div(int i,int j){
        System.out.println("目标方法执行...");
        return i/j;
    }
}





package com.fuping3.aopanno;

import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;

import java.util.Arrays;
@Component
@Aspect//使用@Aspect注解,表示该类是切面类
public class UserProxy {
    /**
     * 将公共的切入点表达式抽取为公共的,使用@Pointcut注解
     */
    @Pointcut(value = "execution(* com.fuping3.aopanno.User.div(..))")
    public void pointDemo(){}

    @Before("pointDemo()")
    public void beforeDiv(){
        System.out.println("--------beforeDiv...");
    }

    /**
     * 后置通知(最终通知)--方法正常执行、异常执行都会执行,类似finally
     */
    @After("pointDemo()")
    public void afterDiv(){
        System.out.println("--------afterDiv...");
    }

    /**
     * 环绕通知--方法执行前后都执行,包括异常时
     * @param joinPoint
     * @return
     */
    @Around(value = "pointDemo()")
    public Object  aroundDiv(ProceedingJoinPoint joinPoint) throws Throwable {
        System.out.println("----------anno around div before...");
        System.out.println("方法名称:"+joinPoint.getSignature().getName());
        Object[] args = joinPoint.getArgs();
        System.out.println("参数列表"+ Arrays.toString(args));
        Object obj;
        //obj=joinPoint.proceed();
        try {
            obj=joinPoint.proceed();
        } catch (Throwable e) {
            obj=null;
            System.out.println("方法执行异常"+e);
        }

        System.out.println("anno around div after...");
        return obj;
    }

    /**
     * 返回通知--方法返回后进行的增强--方法正常执行会执行,异常执行不会执行
     * JoinPoint必须出现在第一个参数位置
     * returning给被增强方法返回值取个名字,给后面引用
     *
     * 备注:
     * 1、@AfterReturning如果和@Around一起使用,那么就需要给@Around的方法设置返回参数,因为@AfterReturning接收到的值其实是@Around返回的。
     * 2、@AfterReturning如果和@Around一起使用,若@Around中obj=joinPoint.proceed();使用try...catch捕获处理了异常,则有异常时:
     *      (a)该方法还是执行;
     *      并且
     *      (b)会导致@AfterThrowing增强不执行
     * @param
     * @param result
     */
    @AfterReturning(value ="pointDemo()",returning="result")
    public void afterReturningDiv(JoinPoint joinPoint,Object result){
        System.out.println("-----------anno afterReturning div...");
        System.out.println("方法名称:"+joinPoint.getSignature().getName());
        Object[] args = joinPoint.getArgs();
        System.out.println("参数列表"+ Arrays.toString(args));
        System.out.println("返回值:"+result);
    }

    /**
     * 异常增强--有异常时执行的增强
     * throwing用于指定异常的参数名
     * @param joinPoint
     * @param exception
     */
    @AfterThrowing(value ="pointDemo()",throwing="exception")
    public void afterDiv(JoinPoint joinPoint,Exception exception){
        System.out.println("------------anno afterThrowing div...");
        System.out.println("方法名称:"+joinPoint.getSignature().getName());
        Object[] args = joinPoint.getArgs();
        System.out.println("参数列表"+ Arrays.toString(args));
        System.out.println("异常值:"+exception);
    }
}

测试代码:

package com.fuping3.aopanno;

import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class Client {
    public static void main(String[] args) {
        ApplicationContext applicationContext=
                new ClassPathXmlApplicationContext("bean2.xml");
        User user = applicationContext.getBean("user", User.class);
        user.div(10, 2);
    }
}

输出结果

----------anno around div before...
方法名称:div
参数列表[10, 2]
--------beforeDiv...
目标方法执行...
anno around div after...
--------afterDiv...
-----------anno afterReturning div...
方法名称:div
参数列表[10, 2]
返回值:5

Process finished with exit code 0

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值