Spring AOP 中pointcut expression表達式解析及配置


Pointcut是指那些方法需要被執行”AOP”,是由”Pointcut Expression”來描述的. 

Pointcut可以有下列方式來定義或者通過&& || 和!的方式進行組合.

expression常用方法

    方法參數匹配
args()
@args()

    方法描述匹配
execution()

    當前AOP代理對象類型匹配
this()

    目標類匹配
target()
@target()
within()
@within()

    標有此注解的方法匹配
@annotation()

    其中execution 是用的最多的,其格式為:
execution(modifiers-pattern? ret-type-pattern declaring-type-pattern? name-pattern(param-pattern)throws-pattern?) 
returning type pattern,name pattern, and parameters pattern是必須的. 
ret-type-pattern:可以為*表示任何返回值,全路徑的類名等. 
name-pattern:指定方法名, *代表所有 
set*代表以set開頭的所有方法. 
parameters pattern:指定方法參數(聲明的類型),(..)代表所有參數,(*)代表一個參數 
(*,String)代表第一個參數為任何值,第二個為String類型.

舉例說明:

任意公共方法的執行:
execution(public * *(..))
任何一個以“set”開始的方法的執行:
execution(* set*(..))
AccountService 接口的任意方法的執行:
execution(* com.xyz.service.AccountService.*(..))
定義在service包里的任意方法的執行:
execution(* com.xyz.service.*.*(..))
定義在service包和所有子包里的任意類的任意方法的執行:
execution(* com.xyz.service..*.*(..))
定義在pointcutexp包和所有子包里的JoinPointObjP2類的任意方法的執行:
execution(* com.test.spring.aop.pointcutexp..JoinPointObjP2.*(..))")
***> 最靠近(..)的為方法名,靠近.*(..))的為類名或者接口名,如上例的JoinPointObjP2.*(..))

pointcutexp包里的任意類.
within(com.test.spring.aop.pointcutexp.*)
pointcutexp包和所有子包里的任意類.
within(com.test.spring.aop.pointcutexp..*)
實現了MyInterface接口的所有類,如果MyInterface不是接口,限定MyInterface單個類.
this(com.test.spring.aop.pointcutexp.MyInterface)
***> 當一個實現了接口的類被AOP的時候,用getBean方法必須cast為接口類型,不能為該類的類型.

帶有@MyTypeAnnotation標注的所有類的任意方法.
@within(com.elong.annotation.MyTypeAnnotation)
@target(com.elong.annotation.MyTypeAnnotation)
帶有@MyTypeAnnotation標注的任意方法.
@annotation(com.elong.annotation.MyTypeAnnotation)
***> @within和@target針對類的注解,@annotation是針對方法的注解

參數帶有@MyMethodAnnotation標注的方法.
@args(com.elong.annotation.MyMethodAnnotation)
參數為String類型(運行是決定)的方法.
args(String)

 

配置Pointcut

  • 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: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-3.0.xsd
    http://www.springframework.org/schema/context
    http://www.springframework.org/schema/context/spring-context-3.0.xsd
    http://www.springframework.org/schema/aop 
    http://www.springframework.org/schema/aop/spring-aop-3.0.xsd "
    default-autowire="byName">
    <bean id="ecoServiceInterceptor"  class="com.elong.eco.EcoServiceInterceptor"/>
    <aop:config>
       <aop:pointcut id="ecoPoint" expression="(execution(public * *..*.*(..))) && (@within(com.elong.eco.annotation.EcoExtension))"/>
       <aop:advisor pointcut-ref="ecoPoint" advice-ref="ecoServiceInterceptor"/>
    </aop:config>
</beans>

 

  • java注解
<?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: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-3.0.xsd
    http://www.springframework.org/schema/context
    http://www.springframework.org/schema/context/spring-context-3.0.xsd
    http://www.springframework.org/schema/aop 
    http://www.springframework.org/schema/aop/spring-aop-3.0.xsd "
    default-autowire="byName">
    <!-- 自動掃描bean -->
    <context:component-scan base-package="com.elong.eco"/>
    <!-- 開啟aop注解支持 -->
    <aop:aspectj-autoproxy/>
</beans>
package com.elong.eco;


import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
@Compoment
@Aspect
public class EcoServiceAspect {


    @Pointcut("(execution(public * *..*.*(..))) && (@within(com.elong.eco.annotation.EcoExtension))")
    public void ecoAnotationPoint() {
    }

    @Around("ecoAnotationPoint()")
    public Object around(ProceedingJoinPoint point) throws Throwable {
        // TODO something
        return point.proceed(); // 不調用point.proceed()不會執行目標方法
    }
}

轉載:https://blog.csdn.net/qq525099302/article/details/53996344

更詳細請查看:https://www.cnblogs.com/rainy-shurun/p/5195439.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM