@AspectJ切点函数之execution()
execution()是最常用的切点函数,语法如下:
execution(<修饰符模式>?<返回类型模式><方法名模式>(<参数模式>)<异常模式>?)
其中:返回类型模式、方法名模式、参数模式是必选项
通过execution()定义切点的不同方式
1.通过方法签名定义切点
execution(public * *(..))
匹配所有目标类的public方法。 第一个代表返回类型,第二个代表方法名,而..代表任意入参的方法
execution(* *To(..))
匹配目标类所有以To为后缀的方法。 第一个代表返回类型,而To代表任意以To为后缀的方法,而..代表任意入参的方法。
2.通过类定义切点
execution(* com.jiuyue.aop.spring.advisor.aspectJ.function.execution.classpoint.Cleaner.*(..))
3.通过类包定义切点
execution(* com.jiuyue.service.impl..*.*(..))
符号 | 含义 |
---|---|
execution() | 表达式的主体 |
第一个”*“符号 | 表示返回值的类型任意 |
com.jiuyue.service.impl | AOP所切的服务的包名,即,我们的业务部分 |
包名后面的”..“ | 表示当前包及子包 |
第二个”*“ | 表示类名,*即所有类 |
.*(..) | 表示任何方法名,括号表示参数,两个点表示任何参数类型 |
在类名模式串中,.* 表示包下的所有类,..*表示包、子孙包下的所有类
execution(* com.jiuyue.*(..))
匹配com.jiuyue包下所有类的所有方法
execution(* com.jiuyue..*(..))
匹配com.jiuyue包、子孙包下所有类的所有方法.比如 com.jiuyue.dao ,com.jiuyue.dao.impl,com.jiuyue.service,com.jiuyue.service.impl包下所有类的所有方法都匹配。 当 ..出现在类名中时,必须后面跟*表示子孙包下的所有类。
execution(* com..*Dao.find*(..))
匹配包名前缀为com的任何包下类名后缀为Dao的方法,方法名必须以find为前缀, 比如com.jiuyue.UserDao#findUserById()方法都是匹配切点。
4.通过方法入参定义切点
切点表达式中的方法入参部分比较复杂,可以使用*和..通配符。 其中 *表示任意参数类型的参数, 而..表示任意类型的参数且参数个数不限。
execution(* joke(String,int))
匹配joke(String,int)方法,且joke方法的第一个入参是String,第二个入参是int。 比如 匹配 SmartSeller#joke(String ,int)方法。 如果方法中的入参类型是java.lang包下的,这可以直接使用类名,否则必须使用全限定类名,比如 joke(java.util.List,int)
execution(* joke(String,*))
匹配目标类中的joke()方法,该方法第一个入参为String,第二个入参为任意类型。 比如 joke(String s1, String s2)和joke(String s1,double d)都匹配,但是 joke(String s1, String s2,double d3)不匹配。
execution(* joke(String,..))
匹配目标类中的joke方法,该方法的第一个入参为String,后面可以有任意个入参且入参类型不限。 比如 joke(String s1),joke(String s1,String s2)和joke(String s1,double d2,String s3)都匹配。
execution(* joke(Object+))
匹配目标类中的joke()方法,方法拥有一个入参,且入参是Object类型或该类的子类。 它匹配joke(String s1) 和joke(Client c) . 如果定义的切点是execution(* joke(Object)) ,则只匹配joke(Object object)而不匹配joke(String s1) 或者joke(Client c)。