org.springframework.core.annotation

Class AnnotationUtils

  • java.lang.Object
    • org.springframework.core.annotation.AnnotationUtils


  • public abstract class AnnotationUtils
    extends java.lang.Object
    General utility methods for working with annotations, handling meta-annotations, bridge methods (which the compiler generates for generic declarations) as well as super methods (for optional annotation inheritance).

    Note that most of the features of this class are not provided by the JDK's introspection facilities themselves.

    As a general rule for runtime-retained annotations (e.g. for transaction control, authorization, or service exposure), always use the lookup methods on this class (e.g., findAnnotation(Method, Class), getAnnotation(Method, Class), and getAnnotations(Method)) instead of the plain annotation lookup methods in the JDK. You can still explicitly choose between a get lookup on the given class level only (getAnnotation(Method, Class)) and a find lookup in the entire inheritance hierarchy of the given method (findAnnotation(Method, Class)).

    Terminology

    The terms directly present, indirectly present, and present have the same meanings as defined in the class-level javadoc for AnnotatedElement (in Java 8).

    An annotation is meta-present on an element if the annotation is declared as a meta-annotation on some other annotation which is present on the element. Annotation A is meta-present on another annotation if A is either directly present or meta-present on the other annotation.

    Meta-annotation Support

    Most find*() methods and some get*() methods in this class provide support for finding annotations used as meta-annotations. Consult the javadoc for each method in this class for details. For fine-grained support for meta-annotations with attribute overrides in composed annotations, consider using AnnotatedElementUtils's more specific methods instead.

    Attribute Aliases

    All public methods in this class that return annotations, arrays of annotations, or AnnotationAttributes transparently support attribute aliases configured via @AliasFor. Consult the various synthesizeAnnotation*(..) methods for details.

    Search Scope

    The search algorithms used by methods in this class stop searching for an annotation once the first annotation of the specified type has been found. As a consequence, additional annotations of the specified type will be silently ignored.

    Since:
    2.0
    Author:
    Rob Harrop, Juergen Hoeller, Sam Brannen, Mark Fisher, Chris Beams, Phillip Webb, Oleg Zhurakousky
    See Also:
    AliasFor, AnnotationAttributes, AnnotatedElementUtils, BridgeMethodResolver, AnnotatedElement.getAnnotations(), AnnotatedElement.getAnnotation(Class), AnnotatedElement.getDeclaredAnnotations()
    • Field Summary

      Fields 
      Modifier and Type Field and Description
      static java.lang.String VALUE
      The attribute name for annotations with a single element.
    • Constructor Summary

      Constructors 
      Constructor and Description
      AnnotationUtils() 
    • Method Summary

      All Methods Static Methods Concrete Methods 
      Modifier and Type Method and Description
      static void clearCache()
      Clear the internal annotation metadata cache.
      static <A extends java.lang.annotation.Annotation>
      A
      findAnnotation(java.lang.reflect.AnnotatedElement annotatedElement, java.lang.Class<A> annotationType)
      Find a single Annotation of annotationType on the supplied AnnotatedElement.
      static <A extends java.lang.annotation.Annotation>
      A
      findAnnotation(java.lang.Class<?> clazz, java.lang.Class<A> annotationType)
      Find a single Annotation of annotationType on the supplied Class, traversing its interfaces, annotations, and superclasses if the annotation is not directly present on the given class itself.
      static <A extends java.lang.annotation.Annotation>
      A
      findAnnotation(java.lang.reflect.Method method, java.lang.Class<A> annotationType)
      Find a single Annotation of annotationType on the supplied Method, traversing its super methods (i.e.
      static java.lang.Class<?> findAnnotationDeclaringClass(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType, java.lang.Class<?> clazz)
      Find the first Class in the inheritance hierarchy of the specified clazz (including the specified clazz itself) on which an annotation of the specified annotationType is directly present.
      static java.lang.Class<?> findAnnotationDeclaringClassForTypes(java.util.List<java.lang.Class<? extends java.lang.annotation.Annotation>> annotationTypes, java.lang.Class<?> clazz)
      Find the first Class in the inheritance hierarchy of the specified clazz (including the specified clazz itself) on which at least one of the specified annotationTypes is directly present.
      static <A extends java.lang.annotation.Annotation>
      A
      getAnnotation(java.lang.reflect.AnnotatedElement annotatedElement, java.lang.Class<A> annotationType)
      Get a single Annotation of annotationType from the supplied AnnotatedElement, where the annotation is either present or meta-present on the AnnotatedElement.
      static <A extends java.lang.annotation.Annotation>
      A
      getAnnotation(java.lang.annotation.Annotation annotation, java.lang.Class<A> annotationType)
      Get a single Annotation of annotationType from the supplied annotation: either the given annotation itself or a direct meta-annotation thereof.
      static <A extends java.lang.annotation.Annotation>
      A
      getAnnotation(java.lang.reflect.Method method, java.lang.Class<A> annotationType)
      Get a single Annotation of annotationType from the supplied Method, where the annotation is either present or meta-present on the method.
      static AnnotationAttributes getAnnotationAttributes(java.lang.reflect.AnnotatedElement annotatedElement, java.lang.annotation.Annotation annotation)
      Retrieve the given annotation's attributes as an AnnotationAttributes map.
      static AnnotationAttributes getAnnotationAttributes(java.lang.reflect.AnnotatedElement annotatedElement, java.lang.annotation.Annotation annotation, boolean classValuesAsString, boolean nestedAnnotationsAsMap)
      Retrieve the given annotation's attributes as an AnnotationAttributes map.
      static java.util.Map<java.lang.String,java.lang.Object> getAnnotationAttributes(java.lang.annotation.Annotation annotation)
      Retrieve the given annotation's attributes as a Map, preserving all attribute types.
      static java.util.Map<java.lang.String,java.lang.Object> getAnnotationAttributes(java.lang.annotation.Annotation annotation, boolean classValuesAsString)
      Retrieve the given annotation's attributes as a Map.
      static AnnotationAttributes getAnnotationAttributes(java.lang.annotation.Annotation annotation, boolean classValuesAsString, boolean nestedAnnotationsAsMap)
      Retrieve the given annotation's attributes as an AnnotationAttributes map.
      static java.lang.annotation.Annotation[] getAnnotations(java.lang.reflect.AnnotatedElement annotatedElement)
      Get all Annotations that are present on the supplied AnnotatedElement.
      static java.lang.annotation.Annotation[] getAnnotations(java.lang.reflect.Method method)
      Get all Annotations that are present on the supplied Method.
      static <A extends java.lang.annotation.Annotation>
      java.util.Set<A>
      getDeclaredRepeatableAnnotations(java.lang.reflect.AnnotatedElement annotatedElement, java.lang.Class<A> annotationType)
      Get the declared repeatable annotations of annotationType from the supplied AnnotatedElement, where such annotations are either directly present, indirectly present, or meta-present on the element.
      static <A extends java.lang.annotation.Annotation>
      java.util.Set<A>
      getDeclaredRepeatableAnnotations(java.lang.reflect.AnnotatedElement annotatedElement, java.lang.Class<A> annotationType, java.lang.Class<? extends java.lang.annotation.Annotation> containerAnnotationType)
      Get the declared repeatable annotations of annotationType from the supplied AnnotatedElement, where such annotations are either directly present, indirectly present, or meta-present on the element.
      static java.lang.Object getDefaultValue(java.lang.annotation.Annotation annotation)
      Retrieve the default value of the value attribute of a single-element Annotation, given an annotation instance.
      static java.lang.Object getDefaultValue(java.lang.annotation.Annotation annotation, java.lang.String attributeName)
      Retrieve the default value of a named attribute, given an annotation instance.
      static java.lang.Object getDefaultValue(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType)
      Retrieve the default value of the value attribute of a single-element Annotation, given the annotation type.
      static java.lang.Object getDefaultValue(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType, java.lang.String attributeName)
      Retrieve the default value of a named attribute, given the annotation type.
      static <A extends java.lang.annotation.Annotation>
      java.util.Set<A>
      getRepeatableAnnotations(java.lang.reflect.AnnotatedElement annotatedElement, java.lang.Class<A> annotationType)
      Get the repeatable annotations of annotationType from the supplied AnnotatedElement, where such annotations are either present, indirectly present, or meta-present on the element.
      static <A extends java.lang.annotation.Annotation>
      java.util.Set<A>
      getRepeatableAnnotations(java.lang.reflect.AnnotatedElement annotatedElement, java.lang.Class<A> annotationType, java.lang.Class<? extends java.lang.annotation.Annotation> containerAnnotationType)
      Get the repeatable annotations of annotationType from the supplied AnnotatedElement, where such annotations are either present, indirectly present, or meta-present on the element.
      static java.lang.Object getValue(java.lang.annotation.Annotation annotation)
      Retrieve the value of the value attribute of a single-element Annotation, given an annotation instance.
      static java.lang.Object getValue(java.lang.annotation.Annotation annotation, java.lang.String attributeName)
      Retrieve the value of a named attribute, given an annotation instance.
      static boolean isAnnotationDeclaredLocally(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType, java.lang.Class<?> clazz)
      Determine whether an annotation of the specified annotationType is declared locally (i.e.
      static boolean isAnnotationInherited(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType, java.lang.Class<?> clazz)
      Determine whether an annotation of the specified annotationType is present on the supplied clazz and is inherited (i.e.
      static boolean isAnnotationMetaPresent(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType, java.lang.Class<? extends java.lang.annotation.Annotation> metaAnnotationType)
      Determine if an annotation of type metaAnnotationType is meta-present on the supplied annotationType.
      static boolean isInJavaLangAnnotationPackage(java.lang.annotation.Annotation annotation)
      Determine if the supplied Annotation is defined in the core JDK java.lang.annotation package.
      static boolean isInJavaLangAnnotationPackage(java.lang.String annotationType)
      Determine if the Annotation with the supplied name is defined in the core JDK java.lang.annotation package.
      static void postProcessAnnotationAttributes(java.lang.Object annotatedElement, AnnotationAttributes attributes, boolean classValuesAsString)
      Post-process the supplied AnnotationAttributes, preserving nested annotations as Annotation instances.
      static void registerDefaultValues(AnnotationAttributes attributes)
      Register the annotation-declared default values for the given attributes, if available.
      static <A extends java.lang.annotation.Annotation>
      A
      synthesizeAnnotation(A annotation, java.lang.reflect.AnnotatedElement annotatedElement)
      Synthesize an annotation from the supplied annotation by wrapping it in a dynamic proxy that transparently enforces attribute alias semantics for annotation attributes that are annotated with @AliasFor.
      static <A extends java.lang.annotation.Annotation>
      A
      synthesizeAnnotation(java.lang.Class<A> annotationType)
      Synthesize an annotation from its default attributes values.
      static <A extends java.lang.annotation.Annotation>
      A
      synthesizeAnnotation(java.util.Map<java.lang.String,java.lang.Object> attributes, java.lang.Class<A> annotationType, java.lang.reflect.AnnotatedElement annotatedElement)
      Synthesize an annotation from the supplied map of annotation attributes by wrapping the map in a dynamic proxy that implements an annotation of the specified annotationType and transparently enforces attribute alias semantics for annotation attributes that are annotated with @AliasFor.
      static void validateAnnotation(java.lang.annotation.Annotation annotation)
      Check the declared attributes of the given annotation, in particular covering Google App Engine's late arrival of TypeNotPresentExceptionProxy for Class values (instead of early Class.getAnnotations() failure.
      • Methods inherited from class java.lang.Object

        clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
    • Field Detail

      • VALUE

        public static final java.lang.String VALUE
        The attribute name for annotations with a single element.
        See Also:
        Constant Field Values
    • Constructor Detail

      • AnnotationUtils

        public AnnotationUtils()
    • Method Detail

      • getAnnotation

        @Nullable
        public static <A extends java.lang.annotation.Annotation> A getAnnotation(java.lang.annotation.Annotation annotation,
                                                                                            java.lang.Class<A> annotationType)
        Get a single Annotation of annotationType from the supplied annotation: either the given annotation itself or a direct meta-annotation thereof.

        Note that this method supports only a single level of meta-annotations. For support for arbitrary levels of meta-annotations, use one of the find*() methods instead.

        Parameters:
        annotation - the Annotation to check
        annotationType - the annotation type to look for, both locally and as a meta-annotation
        Returns:
        the first matching annotation, or null if not found
        Since:
        4.0
      • getAnnotation

        @Nullable
        public static <A extends java.lang.annotation.Annotation> A getAnnotation(java.lang.reflect.AnnotatedElement annotatedElement,
                                                                                            java.lang.Class<A> annotationType)
        Get a single Annotation of annotationType from the supplied AnnotatedElement, where the annotation is either present or meta-present on the AnnotatedElement.

        Note that this method supports only a single level of meta-annotations. For support for arbitrary levels of meta-annotations, use findAnnotation(AnnotatedElement, Class) instead.

        Parameters:
        annotatedElement - the AnnotatedElement from which to get the annotation
        annotationType - the annotation type to look for, both locally and as a meta-annotation
        Returns:
        the first matching annotation, or null if not found
        Since:
        3.1
      • getAnnotation

        @Nullable
        public static <A extends java.lang.annotation.Annotation> A getAnnotation(java.lang.reflect.Method method,
                                                                                            java.lang.Class<A> annotationType)
        Get a single Annotation of annotationType from the supplied Method, where the annotation is either present or meta-present on the method.

        Correctly handles bridge Methods generated by the compiler.

        Note that this method supports only a single level of meta-annotations. For support for arbitrary levels of meta-annotations, use findAnnotation(Method, Class) instead.

        Parameters:
        method - the method to look for annotations on
        annotationType - the annotation type to look for
        Returns:
        the first matching annotation, or null if not found
        See Also:
        BridgeMethodResolver.findBridgedMethod(Method), getAnnotation(AnnotatedElement, Class)
      • getAnnotations

        @Nullable
        public static java.lang.annotation.Annotation[] getAnnotations(java.lang.reflect.AnnotatedElement annotatedElement)
        Get all Annotations that are present on the supplied AnnotatedElement.

        Meta-annotations will not be searched.

        Parameters:
        annotatedElement - the Method, Constructor or Field to retrieve annotations from
        Returns:
        the annotations found, an empty array, or null if not resolvable (e.g. because nested Class values in annotation attributes failed to resolve at runtime)
        Since:
        4.0.8
        See Also:
        AnnotatedElement.getAnnotations()
      • getAnnotations

        @Nullable
        public static java.lang.annotation.Annotation[] getAnnotations(java.lang.reflect.Method method)
        Get all Annotations that are present on the supplied Method.

        Correctly handles bridge Methods generated by the compiler.

        Meta-annotations will not be searched.

        Parameters:
        method - the Method to retrieve annotations from
        Returns:
        the annotations found, an empty array, or null if not resolvable (e.g. because nested Class values in annotation attributes failed to resolve at runtime)
        See Also:
        BridgeMethodResolver.findBridgedMethod(Method), AnnotatedElement.getAnnotations()
      • getRepeatableAnnotations

        public static <A extends java.lang.annotation.Annotation> java.util.Set<A> getRepeatableAnnotations(java.lang.reflect.AnnotatedElement annotatedElement,
                                                                                                            java.lang.Class<A> annotationType)
        Get the repeatable annotations of annotationType from the supplied AnnotatedElement, where such annotations are either present, indirectly present, or meta-present on the element.

        This method mimics the functionality of Java 8's AnnotatedElement.getAnnotationsByType(Class) with support for automatic detection of a container annotation declared via @Repeatable (when running on Java 8 or higher) and with additional support for meta-annotations.

        Handles both single annotations and annotations nested within a container annotation.

        Correctly handles bridge methods generated by the compiler if the supplied element is a Method.

        Meta-annotations will be searched if the annotation is not present on the supplied element.

        Parameters:
        annotatedElement - the element to look for annotations on
        annotationType - the annotation type to look for
        Returns:
        the annotations found or an empty set (never null)
        Since:
        4.2
        See Also:
        getRepeatableAnnotations(AnnotatedElement, Class, Class), getDeclaredRepeatableAnnotations(AnnotatedElement, Class, Class), AnnotatedElementUtils.getMergedRepeatableAnnotations(AnnotatedElement, Class), BridgeMethodResolver.findBridgedMethod(java.lang.reflect.Method), Repeatable, AnnotatedElement.getAnnotationsByType(java.lang.Class<T>)
      • getRepeatableAnnotations

        public static <A extends java.lang.annotation.Annotation> java.util.Set<A> getRepeatableAnnotations(java.lang.reflect.AnnotatedElement annotatedElement,
                                                                                                            java.lang.Class<A> annotationType,
                                                                                                            @Nullable
                                                                                                            java.lang.Class<? extends java.lang.annotation.Annotation> containerAnnotationType)
        Get the repeatable annotations of annotationType from the supplied AnnotatedElement, where such annotations are either present, indirectly present, or meta-present on the element.

        This method mimics the functionality of Java 8's AnnotatedElement.getAnnotationsByType(Class) with additional support for meta-annotations.

        Handles both single annotations and annotations nested within a container annotation.

        Correctly handles bridge methods generated by the compiler if the supplied element is a Method.

        Meta-annotations will be searched if the annotation is not present on the supplied element.

        Parameters:
        annotatedElement - the element to look for annotations on
        annotationType - the annotation type to look for
        containerAnnotationType - the type of the container that holds the annotations; may be null if a container is not supported or if it should be looked up via @Repeatable when running on Java 8 or higher
        Returns:
        the annotations found or an empty set (never null)
        Since:
        4.2
        See Also:
        getRepeatableAnnotations(AnnotatedElement, Class), getDeclaredRepeatableAnnotations(AnnotatedElement, Class), getDeclaredRepeatableAnnotations(AnnotatedElement, Class, Class), AnnotatedElementUtils.getMergedRepeatableAnnotations(AnnotatedElement, Class, Class), BridgeMethodResolver.findBridgedMethod(java.lang.reflect.Method), Repeatable, AnnotatedElement.getAnnotationsByType(java.lang.Class<T>)
      • getDeclaredRepeatableAnnotations

        public static <A extends java.lang.annotation.Annotation> java.util.Set<A> getDeclaredRepeatableAnnotations(java.lang.reflect.AnnotatedElement annotatedElement,
                                                                                                                    java.lang.Class<A> annotationType)
        Get the declared repeatable annotations of annotationType from the supplied AnnotatedElement, where such annotations are either directly present, indirectly present, or meta-present on the element.

        This method mimics the functionality of Java 8's AnnotatedElement.getDeclaredAnnotationsByType(Class) with support for automatic detection of a container annotation declared via @Repeatable (when running on Java 8 or higher) and with additional support for meta-annotations.

        Handles both single annotations and annotations nested within a container annotation.

        Correctly handles bridge methods generated by the compiler if the supplied element is a Method.

        Meta-annotations will be searched if the annotation is not present on the supplied element.

        Parameters:
        annotatedElement - the element to look for annotations on
        annotationType - the annotation type to look for
        Returns:
        the annotations found or an empty set (never null)
        Since:
        4.2
        See Also:
        getRepeatableAnnotations(AnnotatedElement, Class), getRepeatableAnnotations(AnnotatedElement, Class, Class), getDeclaredRepeatableAnnotations(AnnotatedElement, Class, Class), AnnotatedElementUtils.getMergedRepeatableAnnotations(AnnotatedElement, Class), BridgeMethodResolver.findBridgedMethod(java.lang.reflect.Method), Repeatable, AnnotatedElement.getDeclaredAnnotationsByType(java.lang.Class<T>)
      • getDeclaredRepeatableAnnotations

        public static <A extends java.lang.annotation.Annotation> java.util.Set<A> getDeclaredRepeatableAnnotations(java.lang.reflect.AnnotatedElement annotatedElement,
                                                                                                                    java.lang.Class<A> annotationType,
                                                                                                                    @Nullable
                                                                                                                    java.lang.Class<? extends java.lang.annotation.Annotation> containerAnnotationType)
        Get the declared repeatable annotations of annotationType from the supplied AnnotatedElement, where such annotations are either directly present, indirectly present, or meta-present on the element.

        This method mimics the functionality of Java 8's AnnotatedElement.getDeclaredAnnotationsByType(Class) with additional support for meta-annotations.

        Handles both single annotations and annotations nested within a container annotation.

        Correctly handles bridge methods generated by the compiler if the supplied element is a Method.

        Meta-annotations will be searched if the annotation is not present on the supplied element.

        Parameters:
        annotatedElement - the element to look for annotations on
        annotationType - the annotation type to look for
        containerAnnotationType - the type of the container that holds the annotations; may be null if a container is not supported or if it should be looked up via @Repeatable when running on Java 8 or higher
        Returns:
        the annotations found or an empty set (never null)
        Since:
        4.2
        See Also:
        getRepeatableAnnotations(AnnotatedElement, Class), getRepeatableAnnotations(AnnotatedElement, Class, Class), getDeclaredRepeatableAnnotations(AnnotatedElement, Class), AnnotatedElementUtils.getMergedRepeatableAnnotations(AnnotatedElement, Class, Class), BridgeMethodResolver.findBridgedMethod(java.lang.reflect.Method), Repeatable, AnnotatedElement.getDeclaredAnnotationsByType(java.lang.Class<T>)
      • findAnnotation

        @Nullable
        public static <A extends java.lang.annotation.Annotation> A findAnnotation(java.lang.reflect.AnnotatedElement annotatedElement,
                                                                                             java.lang.Class<A> annotationType)
        Find a single Annotation of annotationType on the supplied AnnotatedElement.

        Meta-annotations will be searched if the annotation is not directly present on the supplied element.

        Warning: this method operates generically on annotated elements. In other words, this method does not execute specialized search algorithms for classes or methods. If you require the more specific semantics of findAnnotation(Class, Class) or findAnnotation(Method, Class), invoke one of those methods instead.

        Parameters:
        annotatedElement - the AnnotatedElement on which to find the annotation
        annotationType - the annotation type to look for, both locally and as a meta-annotation
        Returns:
        the first matching annotation, or null if not found
        Since:
        4.2
      • findAnnotation

        @Nullable
        public static <A extends java.lang.annotation.Annotation> A findAnnotation(java.lang.reflect.Method method,
                                                                                             @Nullable
                                                                                             java.lang.Class<A> annotationType)
        Find a single Annotation of annotationType on the supplied Method, traversing its super methods (i.e. from superclasses and interfaces) if the annotation is not directly present on the given method itself.

        Correctly handles bridge Methods generated by the compiler.

        Meta-annotations will be searched if the annotation is not directly present on the method.

        Annotations on methods are not inherited by default, so we need to handle this explicitly.

        Parameters:
        method - the method to look for annotations on
        annotationType - the annotation type to look for
        Returns:
        the first matching annotation, or null if not found
        See Also:
        getAnnotation(Method, Class)
      • findAnnotation

        @Nullable
        public static <A extends java.lang.annotation.Annotation> A findAnnotation(java.lang.Class<?> clazz,
                                                                                             java.lang.Class<A> annotationType)
        Find a single Annotation of annotationType on the supplied Class, traversing its interfaces, annotations, and superclasses if the annotation is not directly present on the given class itself.

        This method explicitly handles class-level annotations which are not declared as inherited as well as meta-annotations and annotations on interfaces.

        The algorithm operates as follows:

        1. Search for the annotation on the given class and return it if found.
        2. Recursively search through all annotations that the given class declares.
        3. Recursively search through all interfaces that the given class declares.
        4. Recursively search through the superclass hierarchy of the given class.

        Note: in this context, the term recursively means that the search process continues by returning to step #1 with the current interface, annotation, or superclass as the class to look for annotations on.

        Parameters:
        clazz - the class to look for annotations on
        annotationType - the type of annotation to look for
        Returns:
        the first matching annotation, or null if not found
      • findAnnotationDeclaringClass

        @Nullable
        public static java.lang.Class<?> findAnnotationDeclaringClass(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType,
                                                                                @Nullable
                                                                                java.lang.Class<?> clazz)
        Find the first Class in the inheritance hierarchy of the specified clazz (including the specified clazz itself) on which an annotation of the specified annotationType is directly present.

        If the supplied clazz is an interface, only the interface itself will be checked; the inheritance hierarchy for interfaces will not be traversed.

        Meta-annotations will not be searched.

        The standard Class API does not provide a mechanism for determining which class in an inheritance hierarchy actually declares an Annotation, so we need to handle this explicitly.

        Parameters:
        annotationType - the annotation type to look for
        clazz - the class to check for the annotation on (may be null)
        Returns:
        the first Class in the inheritance hierarchy that declares an annotation of the specified annotationType, or null if not found
        See Also:
        Class.isAnnotationPresent(Class), Class.getDeclaredAnnotations(), findAnnotationDeclaringClassForTypes(List, Class), isAnnotationDeclaredLocally(Class, Class)
      • findAnnotationDeclaringClassForTypes

        @Nullable
        public static java.lang.Class<?> findAnnotationDeclaringClassForTypes(java.util.List<java.lang.Class<? extends java.lang.annotation.Annotation>> annotationTypes,
                                                                                        @Nullable
                                                                                        java.lang.Class<?> clazz)
        Find the first Class in the inheritance hierarchy of the specified clazz (including the specified clazz itself) on which at least one of the specified annotationTypes is directly present.

        If the supplied clazz is an interface, only the interface itself will be checked; the inheritance hierarchy for interfaces will not be traversed.

        Meta-annotations will not be searched.

        The standard Class API does not provide a mechanism for determining which class in an inheritance hierarchy actually declares one of several candidate annotations, so we need to handle this explicitly.

        Parameters:
        annotationTypes - the annotation types to look for
        clazz - the class to check for the annotations on, or null
        Returns:
        the first Class in the inheritance hierarchy that declares an annotation of at least one of the specified annotationTypes, or null if not found
        Since:
        3.2.2
        See Also:
        Class.isAnnotationPresent(Class), Class.getDeclaredAnnotations(), findAnnotationDeclaringClass(Class, Class), isAnnotationDeclaredLocally(Class, Class)
      • isAnnotationDeclaredLocally

        public static boolean isAnnotationDeclaredLocally(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType,
                                                          java.lang.Class<?> clazz)
        Determine whether an annotation of the specified annotationType is declared locally (i.e. directly present) on the supplied clazz.

        The supplied Class may represent any type.

        Meta-annotations will not be searched.

        Note: This method does not determine if the annotation is inherited. For greater clarity regarding inherited annotations, consider using isAnnotationInherited(Class, Class) instead.

        Parameters:
        annotationType - the annotation type to look for
        clazz - the class to check for the annotation on
        Returns:
        true if an annotation of the specified annotationType is directly present
        See Also:
        Class.getDeclaredAnnotations(), Class.getDeclaredAnnotation(Class), isAnnotationInherited(Class, Class)
      • isAnnotationInherited

        public static boolean isAnnotationInherited(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType,
                                                    java.lang.Class<?> clazz)
        Determine whether an annotation of the specified annotationType is present on the supplied clazz and is inherited (i.e. not directly present).

        Meta-annotations will not be searched.

        If the supplied clazz is an interface, only the interface itself will be checked. In accordance with standard meta-annotation semantics in Java, the inheritance hierarchy for interfaces will not be traversed. See the javadoc for the @Inherited meta-annotation for further details regarding annotation inheritance.

        Parameters:
        annotationType - the annotation type to look for
        clazz - the class to check for the annotation on
        Returns:
        true if an annotation of the specified annotationType is present and inherited
        See Also:
        Class.isAnnotationPresent(Class), isAnnotationDeclaredLocally(Class, Class)
      • isAnnotationMetaPresent

        public static boolean isAnnotationMetaPresent(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType,
                                                      @Nullable
                                                      java.lang.Class<? extends java.lang.annotation.Annotation> metaAnnotationType)
        Determine if an annotation of type metaAnnotationType is meta-present on the supplied annotationType.
        Parameters:
        annotationType - the annotation type to search on
        metaAnnotationType - the type of meta-annotation to search for
        Returns:
        true if such an annotation is meta-present
        Since:
        4.2.1
      • isInJavaLangAnnotationPackage

        public static boolean isInJavaLangAnnotationPackage(@Nullable
                                                            java.lang.annotation.Annotation annotation)
        Determine if the supplied Annotation is defined in the core JDK java.lang.annotation package.
        Parameters:
        annotation - the annotation to check
        Returns:
        true if the annotation is in the java.lang.annotation package
      • isInJavaLangAnnotationPackage

        public static boolean isInJavaLangAnnotationPackage(@Nullable
                                                            java.lang.String annotationType)
        Determine if the Annotation with the supplied name is defined in the core JDK java.lang.annotation package.
        Parameters:
        annotationType - the name of the annotation type to check
        Returns:
        true if the annotation is in the java.lang.annotation package
        Since:
        4.2
      • validateAnnotation

        public static void validateAnnotation(java.lang.annotation.Annotation annotation)
        Check the declared attributes of the given annotation, in particular covering Google App Engine's late arrival of TypeNotPresentExceptionProxy for Class values (instead of early Class.getAnnotations() failure.

        This method not failing indicates that getAnnotationAttributes(Annotation) won't failure either (when attempted later on).

        Parameters:
        annotation - the annotation to validate
        Throws:
        java.lang.IllegalStateException - if a declared Class attribute could not be read
        Since:
        4.3.15
        See Also:
        Class.getAnnotations(), getAnnotationAttributes(Annotation)
      • getAnnotationAttributes

        public static java.util.Map<java.lang.String,java.lang.Object> getAnnotationAttributes(java.lang.annotation.Annotation annotation,
                                                                                               boolean classValuesAsString)
        Retrieve the given annotation's attributes as a Map.

        Equivalent to calling getAnnotationAttributes(Annotation, boolean, boolean) with the nestedAnnotationsAsMap parameter set to false.

        Note: This method actually returns an AnnotationAttributes instance. However, the Map signature has been preserved for binary compatibility.

        Parameters:
        annotation - the annotation to retrieve the attributes for
        classValuesAsString - whether to convert Class references into Strings (for compatibility with AnnotationMetadata) or to preserve them as Class references
        Returns:
        the Map of annotation attributes, with attribute names as keys and corresponding attribute values as values (never null)
        See Also:
        getAnnotationAttributes(Annotation, boolean, boolean)
      • getAnnotationAttributes

        public static AnnotationAttributes getAnnotationAttributes(java.lang.annotation.Annotation annotation,
                                                                   boolean classValuesAsString,
                                                                   boolean nestedAnnotationsAsMap)
        Retrieve the given annotation's attributes as an AnnotationAttributes map.

        This method provides fully recursive annotation reading capabilities on par with the reflection-based StandardAnnotationMetadata.

        Parameters:
        annotation - the annotation to retrieve the attributes for
        classValuesAsString - whether to convert Class references into Strings (for compatibility with AnnotationMetadata) or to preserve them as Class references
        nestedAnnotationsAsMap - whether to convert nested annotations into AnnotationAttributes maps (for compatibility with AnnotationMetadata) or to preserve them as Annotation instances
        Returns:
        the annotation attributes (a specialized Map) with attribute names as keys and corresponding attribute values as values (never null)
        Since:
        3.1.1
      • getAnnotationAttributes

        public static AnnotationAttributes getAnnotationAttributes(@Nullable
                                                                   java.lang.reflect.AnnotatedElement annotatedElement,
                                                                   java.lang.annotation.Annotation annotation,
                                                                   boolean classValuesAsString,
                                                                   boolean nestedAnnotationsAsMap)
        Retrieve the given annotation's attributes as an AnnotationAttributes map.

        This method provides fully recursive annotation reading capabilities on par with the reflection-based StandardAnnotationMetadata.

        Parameters:
        annotatedElement - the element that is annotated with the supplied annotation; may be null if unknown
        annotation - the annotation to retrieve the attributes for
        classValuesAsString - whether to convert Class references into Strings (for compatibility with AnnotationMetadata) or to preserve them as Class references
        nestedAnnotationsAsMap - whether to convert nested annotations into AnnotationAttributes maps (for compatibility with AnnotationMetadata) or to preserve them as Annotation instances
        Returns:
        the annotation attributes (a specialized Map) with attribute names as keys and corresponding attribute values as values (never null)
        Since:
        4.2
      • registerDefaultValues

        public static void registerDefaultValues(AnnotationAttributes attributes)
        Register the annotation-declared default values for the given attributes, if available.
        Parameters:
        attributes - the annotation attributes to process
        Since:
        4.3.2
      • postProcessAnnotationAttributes

        public static void postProcessAnnotationAttributes(@Nullable
                                                           java.lang.Object annotatedElement,
                                                           AnnotationAttributes attributes,
                                                           boolean classValuesAsString)
        Post-process the supplied AnnotationAttributes, preserving nested annotations as Annotation instances.

        Specifically, this method enforces attribute alias semantics for annotation attributes that are annotated with @AliasFor and replaces default value placeholders with their original default values.

        Parameters:
        annotatedElement - the element that is annotated with an annotation or annotation hierarchy from which the supplied attributes were created; may be null if unknown
        attributes - the annotation attributes to post-process
        classValuesAsString - whether to convert Class references into Strings (for compatibility with AnnotationMetadata) or to preserve them as Class references
        Since:
        4.3.2
        See Also:
        postProcessAnnotationAttributes(Object, AnnotationAttributes, boolean, boolean), getDefaultValue(Class, String)
      • getValue

        @Nullable
        public static java.lang.Object getValue(java.lang.annotation.Annotation annotation)
        Retrieve the value of the value attribute of a single-element Annotation, given an annotation instance.
        Parameters:
        annotation - the annotation instance from which to retrieve the value
        Returns:
        the attribute value, or null if not found unless the attribute value cannot be retrieved due to an AnnotationConfigurationException, in which case such an exception will be rethrown
        See Also:
        getValue(Annotation, String)
      • getValue

        @Nullable
        public static java.lang.Object getValue(@Nullable
                                                          java.lang.annotation.Annotation annotation,
                                                          @Nullable
                                                          java.lang.String attributeName)
        Retrieve the value of a named attribute, given an annotation instance.
        Parameters:
        annotation - the annotation instance from which to retrieve the value
        attributeName - the name of the attribute value to retrieve
        Returns:
        the attribute value, or null if not found unless the attribute value cannot be retrieved due to an AnnotationConfigurationException, in which case such an exception will be rethrown
        See Also:
        getValue(Annotation), rethrowAnnotationConfigurationException(Throwable)
      • getDefaultValue

        @Nullable
        public static java.lang.Object getDefaultValue(java.lang.annotation.Annotation annotation)
        Retrieve the default value of the value attribute of a single-element Annotation, given an annotation instance.
        Parameters:
        annotation - the annotation instance from which to retrieve the default value
        Returns:
        the default value, or null if not found
        See Also:
        getDefaultValue(Annotation, String)
      • getDefaultValue

        @Nullable
        public static java.lang.Object getDefaultValue(@Nullable
                                                                 java.lang.annotation.Annotation annotation,
                                                                 @Nullable
                                                                 java.lang.String attributeName)
        Retrieve the default value of a named attribute, given an annotation instance.
        Parameters:
        annotation - the annotation instance from which to retrieve the default value
        attributeName - the name of the attribute value to retrieve
        Returns:
        the default value of the named attribute, or null if not found
        See Also:
        getDefaultValue(Class, String)
      • getDefaultValue

        @Nullable
        public static java.lang.Object getDefaultValue(java.lang.Class<? extends java.lang.annotation.Annotation> annotationType)
        Retrieve the default value of the value attribute of a single-element Annotation, given the annotation type.
        Parameters:
        annotationType - the annotation type for which the default value should be retrieved
        Returns:
        the default value, or null if not found
        See Also:
        getDefaultValue(Class, String)
      • getDefaultValue

        @Nullable
        public static java.lang.Object getDefaultValue(@Nullable
                                                                 java.lang.Class<? extends java.lang.annotation.Annotation> annotationType,
                                                                 @Nullable
                                                                 java.lang.String attributeName)
        Retrieve the default value of a named attribute, given the annotation type.
        Parameters:
        annotationType - the annotation type for which the default value should be retrieved
        attributeName - the name of the attribute value to retrieve.
        Returns:
        the default value of the named attribute, or null if not found
        See Also:
        getDefaultValue(Annotation, String)
      • synthesizeAnnotation

        public static <A extends java.lang.annotation.Annotation> A synthesizeAnnotation(A annotation,
                                                                                         @Nullable
                                                                                         java.lang.reflect.AnnotatedElement annotatedElement)
        Synthesize an annotation from the supplied annotation by wrapping it in a dynamic proxy that transparently enforces attribute alias semantics for annotation attributes that are annotated with @AliasFor.
        Parameters:
        annotation - the annotation to synthesize
        annotatedElement - the element that is annotated with the supplied annotation; may be null if unknown
        Returns:
        the synthesized annotation if the supplied annotation is synthesizable; null if the supplied annotation is null; otherwise the supplied annotation unmodified
        Throws:
        AnnotationConfigurationException - if invalid configuration of @AliasFor is detected
        Since:
        4.2
        See Also:
        synthesizeAnnotation(Map, Class, AnnotatedElement), synthesizeAnnotation(Class)
      • synthesizeAnnotation

        public static <A extends java.lang.annotation.Annotation> A synthesizeAnnotation(java.util.Map<java.lang.String,java.lang.Object> attributes,
                                                                                         java.lang.Class<A> annotationType,
                                                                                         @Nullable
                                                                                         java.lang.reflect.AnnotatedElement annotatedElement)
        Synthesize an annotation from the supplied map of annotation attributes by wrapping the map in a dynamic proxy that implements an annotation of the specified annotationType and transparently enforces attribute alias semantics for annotation attributes that are annotated with @AliasFor.

        The supplied map must contain a key-value pair for every attribute defined in the supplied annotationType that is not aliased or does not have a default value. Nested maps and nested arrays of maps will be recursively synthesized into nested annotations or nested arrays of annotations, respectively.

        Note that AnnotationAttributes is a specialized type of Map that is an ideal candidate for this method's attributes argument.

        Parameters:
        attributes - the map of annotation attributes to synthesize
        annotationType - the type of annotation to synthesize
        annotatedElement - the element that is annotated with the annotation corresponding to the supplied attributes; may be null if unknown
        Returns:
        the synthesized annotation
        Throws:
        java.lang.IllegalArgumentException - if a required attribute is missing or if an attribute is not of the correct type
        AnnotationConfigurationException - if invalid configuration of @AliasFor is detected
        Since:
        4.2
        See Also:
        synthesizeAnnotation(Annotation, AnnotatedElement), synthesizeAnnotation(Class), getAnnotationAttributes(AnnotatedElement, Annotation), getAnnotationAttributes(AnnotatedElement, Annotation, boolean, boolean)
      • clearCache

        public static void clearCache()
        Clear the internal annotation metadata cache.
        Since:
        4.3.15