Spring AOP使用整理:使用@AspectJ风格的切面声明

要启用基于@AspectJ风格的切面声明,需要进行以下的配置:

    <!-- 启用@AspectJ风格的切面声明 -->  
    <aop:aspectj-autoproxy proxy-target-class="true"/>  

    <!-- 通过注解定义bean。默认同时也通过注解自动注入 -->  
    <context:component-scan base-package="com.cjm"/>  

    /** 
     * 声明本类为一个切面 
     */  
    @Component  
    @Aspect  
    public class MyAspectJ {  
        /** 
         * 声明一个切入点(包括切入点表达式和切入点签名) 
         */  
        @Pointcut("execution(* com.cjm.model..*.*(..))")  
        public void pointcut1(){}  

        /** 
         * 声明一个前置通知 
         */  
        @Before("pointcut1()")  
        public void beforeAdvide(JoinPoint point){  
            System.out.println("触发了前置通知!");  
        }  

        /** 
         * 声明一个后置通知 
         */  
        @After("pointcut1()")  
        public void afterAdvie(JoinPoint point){  
            System.out.println("触发了后置通知,抛出异常也会被触发!");  
        }  

        /** 
         * 声明一个返回后通知 
         */  
        @AfterReturning(pointcut="pointcut1()", returning="ret")  
        public void afterReturningAdvice(JoinPoint point, Object ret){  
            System.out.println("触发了返回后通知,抛出异常时不被触发,返回值为:" + ret);  
        }  

        /** 
         * 声明一个异常通知 
         */  
        @AfterThrowing(pointcut="pointcut1()", throwing="throwing")  
        public void afterThrowsAdvice(JoinPoint point, RuntimeException throwing){  
            System.out.println("触发了异常通知,抛出了RuntimeException异常!");  
        }  

        /** 
         * 声明一个环绕通知 
         */  
        @Around("pointcut1()")  
        public Object aroundAdvice(ProceedingJoinPoint point)throws Throwable{  
            System.out.println("触发了环绕通知 开始");  
            Object o = point.proceed();  
            System.out.println("触发了环绕通知 结束");  
            return o;  
        }  
    }  

1、切入点表达式的格式:execution([可见性] 返回类型 [声明类型].方法名(参数) [异常])
2、切入点表达式通配符:
*:匹配所有字符
..:一般用于匹配多个包,多个参数
+:表示类及其子类
3、切入点表达式支持逻辑运算符:&&||!
4、切入点表达式关键词:
1)execution:用于匹配子表达式。

            //匹配com.cjm.model包及其子包中所有类中的所有方法,返回类型任意,方法参数任意
            @Pointcut("execution(* com.cjm.model..*.*(..))")
            public void before(){}

2)within:用于匹配连接点所在的Java类或者包。

            //匹配Person类中的所有方法
            @Pointcut("within(com.cjm.model.Person)")
            public void before(){}


            //匹配com.cjm包及其子包中所有类中的所有方法

            @Pointcut("within(com.cjm..*)")
            public void before(){}

3) this:用于向通知方法中传入代理对象的引用。

            @Before("before() && this(proxy)")
            public void beforeAdvide(JoinPoint point, Object proxy){
                  //处理逻辑
            }

4)target:用于向通知方法中传入目标对象的引用。

            @Before("before() && target(target)
            public void beforeAdvide(JoinPoint point, Object proxy){
                  //处理逻辑
            }

5)args:用于将参数传入到通知方法中。

            @Before("before() && args(age,username)")
            public void beforeAdvide(JoinPoint point, int age, String username){
                  //处理逻辑
            }

6)@within:用于匹配在类一级使用了参数确定的注解的类,其所有方法都将被匹配。

            @Pointcut("@within(com.cjm.annotation.AdviceAnnotation)") - 所有被@AdviceAnnotation标注的类都将匹配
            public void before(){}
    @Retention(RetentionPolicy.RUNTIME)  
    @Target({ElementType.TYPE, ElementType.METHOD})  
    @Documented  
    @Inherited  
    public @interface AdviceAnnotation {  

    }  

7)@target:和@within的功能类似,但必须要指定注解接口的保留策略为RUNTIME。

            @Pointcut("@target(com.cjm.annotation.AdviceAnnotation)")
            public void before(){}

8)@args:传入连接点的对象对应的Java类必须被@args指定的Annotation注解标注。

            @Before("@args(com.cjm.annotation.AdviceAnnotation)")
            public void beforeAdvide(JoinPoint point){
                  //处理逻辑
            }
    public class Person {  
        public void say(Address address){  
              //处理逻辑  
       }  
    }  

     @AdviceAnnotation  
     public class Address {  

     }  

如果需要在Person类的say方法被调用时触发beforeAdvide通知,那么say方法的参数对应的Java类型Address类必须要被@AdviceAnnotation标注。

9)@annotation:匹配连接点被它参数指定的Annotation注解的方法。也就是说,所有被指定注解标注的方法都将匹配。

            @Pointcut("@annotation(com.cjm.annotation.AdviceAnnotation)")
            public void before(){}



    public class Person {  
          @AdviceAnnotation  
          public void say(Address address){  
                  //处理逻辑  
        }  
    }  

Person类的say方法被@AdviceAnnotation标注,所以它匹配。

10)bean:通过受管Bean的名字来限定连接点所在的Bean。该关键词是Spring2.5新增的。

            @Pointcut("bean(person)")
            public void before(){}

idperson的受管Bean中的所有方法都将匹配。

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值