Spring 组合注解

在JAVA1.5新特性描述里有这样一句话

Annotation type declarations cannot be generic. (Annotation types implicitly extend annotation.Annotation.) 这表明了注解类(这里说的是 @interface类,不是被注解标注的那种普通类)之间不能有继承关系,在编译阶段注解类之间的继承是不被允许的(如下图);

如果我想共用一些注解的属性怎么办呢,毕竟继承带来的复用和代码量减少都是很可观的;在Spring中则利用元注解“巧妙地”实现了这一特性。

元注解

能够标记在注解上的注解被称为元注解,比如JAVA提供的最基础的元注解 

Spring则巧妙的运用了元注解代替了“父类”的角色,实现了注解的“派生”(《Spring boot编程思想 核心篇》里小马哥是这样定义的),这样的注解可以称之为“组合注解”;

Spring中有一个最最重要的元注解,也是大家最熟悉的  @Component ,这个注解在Spring框架中派生出很多组合注解如:

@Controller @Service @Repository 等

Spring中封装了一系列的组合注解相关的api,主要有 AnnotationUtils、AnnotatedElementUtils,这些api在org.springframework.core.annotation这个路径下面,有兴趣的可以一起研究研究

这里也看到了上一篇文章所AliasFor标签了

简单例子

上一篇文章一样,我们定义两个注解,并将一个注解当作元注解标注在另一个注解上

元注解:

package com.uu.annotation;

import java.lang.annotation.*;

@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
public @interface MyAnnotation {
    String name() default "";
}

目标注解:

package com.uu.annotation;

import org.springframework.core.annotation.AliasFor;

import java.lang.annotation.*;

@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@MyAnnotation(name = "zzz")
public @interface DemoAnnotation {
    String name1() default "";
}

测试代码:

package com.uu;

import com.uu.annotation.DemoAnnotation;
import com.uu.annotation.MyAnnotation;
import org.junit.Test;
import org.springframework.core.annotation.AnnotatedElementUtils;

@DemoAnnotation(name1 = "9991")
public class DemoTest {
    @Test
    public  void test(){
        MyAnnotation bb = AnnotatedElementUtils.getMergedAnnotation(DemoTest.class, MyAnnotation.class);
        System.out.println(bb);
    }
}

测试打印结果:

虽然我们没有在测试类上标注  @MyAnnotation,但是我们还是通过@DemoAnnotation获得了其相关信息;Spring中这种使用常用太常见。

Guess you like

Origin blog.csdn.net/Aqu415/article/details/107588647