【问题标题】:Java custom annotation to invoke some other method before invoking the annotated method在调用带注释的方法之前调用其他方法的 Java 自定义注释
【发布时间】:2016-09-22 07:40:15
【问题描述】:

我正在尝试实现一个看起来像这样的自定义注释:

public class Foo{

@CustomAnnotation(classname="com.somepackage.ExternalClass", methodname="method1", invokation="before")
public void bar(){
  //method body..
  }
}

注解中指定的方法应该在实际方法被调用之前被调用。 请建议如何实现这一目标。

【问题讨论】:

  • IMO 你在这里做的事情没有多大意义。您正在尝试重新实现可以通过 AOP 更轻松地完成的事情。但是如果你使用 AOP,你为什么要用关于如何应用横切关注点的信息来污染你的主应用程序代码呢?一个干净的解决方案是将这些信息完全外部化到方面本身并摆脱反射魔法。如果您想看一个简单的 AspectJ 示例,请告诉我。

标签: java annotations aop aspectj interceptor


【解决方案1】:

你想在这里完成什么?为什么不直接从方法体内调用方法呢?

注解在编译期间被处理并且在运行时可用(如果它们的生命周期设置为运行时)。它们可用于在编译时生成代码或影响其他代码如何处理您的类,但是您不能在注释处理期间更改现有类。

您唯一能做的就是如果您只从一个位置调用该方法,您可以使用反射检查该注释并调用该方法(同样,使用反射调用该方法),类似于JUnit 是如何工作的(使用 @Test 和 @Before/@After 注释)。

【讨论】:

    【解决方案2】:

    您可以使用 AOP(AspectJ 或 Spring 或 Spring+AspectJ)来做到这一点。唯一可能成为问题的是invokation="before" 注释参数,因为beforeafteraround 等是在您的方面硬编码的建议。 AspectJ 代码示例如下:

    public aspect CustomAnnotationAspect {
    
        pointcut customAnnotationPointcut(Object t, CustomAnnotation annotationValue): execution(@CustomAnnotation * *.*(..)) &&  @this(annotationValue) && target(t);
    
        before(Object target, CustomAnnotation annotationValue): customAnnotationPointcut(target, annotationValue) {
            String className = annotationValue.className();
            String methodName = annotationValue.methodName();
            //do some reflection staff for className.methodName() invocation
        }
    
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-03-28
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-05-06
      • 1970-01-01
      • 2014-11-30
      • 2017-12-25
      相关资源
      最近更新 更多