带有 groovy 的 Spring AOP:调用方法 [英] Spring AOP with groovy: get called method
问题描述
我正在使用带有 groovy 的 spring aop 并且有一个监控方面,应该记录每个方法的执行时间.问题是 groovy 调用与 java 调用不同,因此以下代码始终将getMetaClass()"打印为方法名称.
I'm using spring aop with groovy and have a monitoring aspect that should log each method's execution time. The problem is groovy calls are not the same as java calls so the following code always prints "getMetaClass()" as method name.
@Before("execution(* mypackage.MyService.*(..))")
void beforeMethod(JoinPoint joinPoint) {
logger.info(joinPoint.signature.name + " called")
}
我看到了两种解决问题的方法:
I see two ways to solve the problem:
- 从常规调用中查找实际方法
- 使用其他方式获取被调用的方法(而不是注入jointPoint参数)
有什么想法吗?
推荐答案
对于选项 1:尝试将 !getMetaClass()
Pointcut
添加到您的 @Aspect
类中,如下所示:
For Option 1:
Try adding a !getMetaClass()
Pointcut
to your @Aspect
class like this:
@Pointcut("!execution(* mypackage.MyService.*.getMetaClass(..))")
public void noMetaClassMethods() {}
以及将您的原始执行匹配器变成 Pointcut
:
As well as making your original execution matcher into a Pointcut
:
@Pointcut("execution(* mypackage.MyService.*(..))")
public void myServices() {}
然后将这两个组合在您的 @Before
中,如下所示:
Then combine those two in your @Before
like this:
@Before("myServices() && noMetaClassMethods()")
void beforeMethod(JoinPoint joinPoint) {
logger.info(joinPoint.signature.name + " called")
}
它应该给你你正在寻找的东西.
It should give you what you're looking for.
对于选项 2:您可以在目标方法的注释中添加名称属性:
For Option 2: You could add a name attribute to your annotation on the target method:
@Timed(name="methodIWantToTime")
def methodIWantTime(..)
然后只需将注释作为参数包含在您的 Aspect
类中:
Then just include the annotation as an argument your method in your Aspect
class:
@Around(value="@annotation(timed)")
def timeMethod(ProceedingJoinPoint proceedingJointPoint, Timed timed) {
println timed.name()
proceedingJointPoint.proceed()
}
然后把它剥下来.
这篇关于带有 groovy 的 Spring AOP:调用方法的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!