@AliasFor 不适用于自定义注释中的属性

@AliasFor doesn't work on attribute in custom annotation

我正在使用 SpringBoot 2.4.2。我正在努力使用带有自定义注释的@AliasFor。

我在下面实现了自定义注释。

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface CustomAnnotation {

  @AliasFor("aliasAttribute")
  String value() default "";

  @AliasFor("value")
  String aliasAttribute() "";
}

并像这样使用它。

@CustomAnnoatation("test")
@Component
public class TestClass() {
 // codes here
}

并且此测试代码失败。

@SpringBootTest(classes = TestClass.class)
public class CustomAnnotationTest {

  @Autowired
  TestClass testClass;

  @Test
  public void valueTest1() {
    Annotation annotation = testClass.getClass().getAnnotation(CustomAnnotation.class);

    assertThat(((CustomAnnotation) annotation).value()).isEqualTo(((CustomAnnotation) annotation).aliasAttribute());
  }
}

有消息

org.opentest4j.AssertionFailedError: 
Expecting:
 <"">
to be equal to:
 <"test">

不知道为什么,有人知道吗?

注释是 class、字段等的静态元数据,因此 Spring 无法更改它的任何内容。为了使特征尽可能 @AliasFor Spring 使用,他们称之为合成注释。对于那些要成为 used/detected 的人,您需要利用 Spring 内部机制来获取合成注释并使 @AliasFor 起作用。为此使用 AnnotationUtils.findAnnotation(Spring 也在内部使用)。

@AliasFor 是一项 Spring 功能,因此如果不使用 Spring 组件,这将不起作用。

你的测试方法和

基本一样
@Test
  public void valueTest1() {
    Annotation annotation = TestClass.class.getAnnotation(CustomAnnotation.class);

    assertThat(((CustomAnnotation) annotation).value()).isEqualTo(((CustomAnnotation) annotation).aliasAttribute());
  }

此测试和您的测试都将失败,因为它们根本不使用 Spring 基础设施来检测注释并应用 Spring.

的功能

当使用 AnnotationUtils.findAnnotation 时,测试将通过。

class CustomAnnotationTest {

    @Test
    void testStandardJava() {
        CustomAnnotation annotation = TestClass.class.getAnnotation(CustomAnnotation.class);
        assertThat(annotation.value()).isEqualTo(annotation.aliasAttribute());
    }

    @Test
    void testWithSpring() {
        CustomAnnotation annotation = AnnotationUtils.findAnnotation(TestClass.class, CustomAnnotation.class);
        assertThat(annotation.value()).isEqualTo(annotation.aliasAttribute());
    }
}

testStandardJava 会失败,testWithSpring 会通过,因为它使用了正确的机制。