Package org.springframework.core.annotation

# Interface MergedAnnotations

All Superinterfaces:
  `Iterable<MergedAnnotation<Annotation>>`

public interface MergedAnnotations extends Iterable<MergedAnnotation<Annotation>>
Provides access to a collection of merged annotations, usually obtained from a source such as a `Class` or `Method`.

Each merged annotation represents a view where the attribute values may be "merged" from different source values, typically:

- Explicit and Implicit `@AliasFor` declarations on one or more attributes within the annotation
- Explicit `@AliasFor` declarations for a meta-annotation
- Convention based attribute aliases for a meta-annotation
- From a meta-annotation declaration

For example, a `@PostMapping` annotation might be defined as follows:

     @Retention(RetentionPolicy.RUNTIME)
     @RequestMapping(method = RequestMethod.POST)
     public @interface PostMapping {

         @AliasFor(attribute = "path")
         String[] value() default {};

         @AliasFor(attribute = "value")
         String[] path() default {};
     }

If a method is annotated with `@PostMapping("/home")` it will contain merged annotations for both `@PostMapping` and the meta-annotation `@RequestMapping`. The merged view of the `@RequestMapping` annotation will contain the following attributes:

Name | Value | Source
--- | --- | ---
value | "/home" | Declared in `@PostMapping`
path | "/home" | Explicit `@AliasFor`
method | RequestMethod.POST | Declared in meta-annotation

`MergedAnnotations` can be obtained from any Java `AnnotatedElement`. They may also be used for sources that don't use reflection (such as those that directly parse bytecode).

Different search strategies can be used to locate related source elements that contain the annotations to be aggregated. For example, the following code uses `MergedAnnotations.SearchStrategy.TYPE_HIERARCHY` to search for annotations on `MyClass` as well as in superclasses and implemented interfaces.

     MergedAnnotations mergedAnnotations =
         MergedAnnotations.search(TYPE_HIERARCHY).from(MyClass.class);

From a `MergedAnnotations` instance you can either get a single annotation, or stream all annotations or just those that match a specific type. You can also quickly tell if an annotation is present.

Here are some typical examples:

     // is an annotation present or meta-present?
     mergedAnnotations.isPresent(ExampleAnnotation.class);

     // get the merged "value" attribute of ExampleAnnotation (either directly or
     // meta-present)
     mergedAnnotations.get(ExampleAnnotation.class).getString("value");

     // get all meta-annotations but no directly present annotations
     mergedAnnotations.stream().filter(MergedAnnotation::isMetaPresent);

     // get all ExampleAnnotation declarations (including any meta-annotations) and
     // print the merged "value" attributes
     mergedAnnotations.stream(ExampleAnnotation.class)
         .map(mergedAnnotation -> mergedAnnotation.getString("value"))
         .forEach(System.out::println);

NOTE: The `MergedAnnotations` API and its underlying model have been designed for composable annotations in Spring's common component model, with a focus on attribute aliasing and meta-annotation relationships. There is no support for retrieving plain Java annotations with this API; please use standard Java reflection or Spring's `AnnotationUtils` for simple annotation retrieval purposes.

WARNING: If an annotation cannot be loaded because one of its attributes references a `Class` or `Enum` that is not present in the classpath, that annotation will not be accessible via the `MergedAnnotations` API. To assist with diagnosing such scenarios, you can set the log level for `"org.springframework.core.annotation.MergedAnnotation"` to `DEBUG`, `INFO`, or `WARN`.

Since:
  5.2
Author:
  Phillip Webb, Sam Brannen
See Also:
  - `MergedAnnotation`
  - `MergedAnnotationCollectors`
  - `MergedAnnotationPredicates`
  - `MergedAnnotationSelectors`
  - `AliasFor`
  - `AnnotationUtils`
  - `AnnotatedElementUtils`

## Nested Class Summary

Nested Classes
Modifier and Type
Interface
Description
`static final class`
`MergedAnnotations.Search`
Fluent API for configuring the search algorithm used in the `MergedAnnotations` model and performing a search.
`static enum`
`MergedAnnotations.SearchStrategy`
Search strategies supported by `search(SearchStrategy)` as well as `from(AnnotatedElement, SearchStrategy)` and variants of that method.

## Method Summary

Modifier and Type
Method
Description
`static MergedAnnotations`
`from(Annotation... annotations)`
Create a new `MergedAnnotations` instance from the specified annotations.
`static MergedAnnotations`
`from(Object source, Annotation... annotations)`
Create a new `MergedAnnotations` instance from the specified annotations.
`static MergedAnnotations`
`from(Object source, Annotation[] annotations, RepeatableContainers repeatableContainers)`
Create a new `MergedAnnotations` instance from the specified annotations.
`static MergedAnnotations`
`from(Object source, Annotation[] annotations, RepeatableContainers repeatableContainers, AnnotationFilter annotationFilter)`
Create a new `MergedAnnotations` instance from the specified annotations.
`static MergedAnnotations`
`from(AnnotatedElement element)`
Create a new `MergedAnnotations` instance containing all annotations and meta-annotations from the specified element.
`static MergedAnnotations`
`from(AnnotatedElement element, MergedAnnotations.SearchStrategy searchStrategy)`
Create a new `MergedAnnotations` instance containing all annotations and meta-annotations from the specified element and, depending on the `MergedAnnotations.SearchStrategy`, related inherited elements.
`static MergedAnnotations`
`from(AnnotatedElement element, MergedAnnotations.SearchStrategy searchStrategy, RepeatableContainers repeatableContainers)`
Create a new `MergedAnnotations` instance containing all annotations and meta-annotations from the specified element and, depending on the `MergedAnnotations.SearchStrategy`, related inherited elements.
`static MergedAnnotations`
`from(AnnotatedElement element, MergedAnnotations.SearchStrategy searchStrategy, RepeatableContainers repeatableContainers, AnnotationFilter annotationFilter)`
Create a new `MergedAnnotations` instance containing all annotations and meta-annotations from the specified element and, depending on the `MergedAnnotations.SearchStrategy`, related inherited elements.
`<A extends Annotation>
MergedAnnotation<A>`
`get(Class<A> annotationType)`
Get the nearest matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.
`<A extends Annotation>
MergedAnnotation<A>`
`get(Class<A> annotationType, Predicate<? super MergedAnnotation<A>> predicate)`
Get the nearest matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.
`<A extends Annotation>
MergedAnnotation<A>`
`get(Class<A> annotationType, Predicate<? super MergedAnnotation<A>> predicate, MergedAnnotationSelector<A> selector)`
Get a matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.
`<A extends Annotation>
MergedAnnotation<A>`
`get(String annotationType)`
Get the nearest matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.
`<A extends Annotation>
MergedAnnotation<A>`
`get(String annotationType, Predicate<? super MergedAnnotation<A>> predicate)`
Get the nearest matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.
`<A extends Annotation>
MergedAnnotation<A>`
`get(String annotationType, Predicate<? super MergedAnnotation<A>> predicate, MergedAnnotationSelector<A> selector)`
Get a matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.
`<A extends Annotation>
boolean`
`isDirectlyPresent(Class<A> annotationType)`
Determine if the specified annotation type is directly present.
`boolean`
`isDirectlyPresent(String annotationType)`
Determine if the specified annotation type is directly present.
`<A extends Annotation>
boolean`
`isPresent(Class<A> annotationType)`
Determine if the specified annotation type is either directly present or meta-present.
`boolean`
`isPresent(String annotationType)`
Determine if the specified annotation type is either directly present or meta-present.
`static MergedAnnotations`
`of(Collection<MergedAnnotation<?>> annotations)`
Create a new `MergedAnnotations` instance from the specified collection of directly present annotations.
`static MergedAnnotations.Search`
`search(MergedAnnotations.SearchStrategy searchStrategy)`
Find merged annotations using the supplied `MergedAnnotations.SearchStrategy` and a fluent API for configuring and performing the search.
`Stream<MergedAnnotation<Annotation>>`
`stream()`
Stream all annotations and meta-annotations contained in this collection.
`<A extends Annotation>
Stream<MergedAnnotation<A>>`
`stream(Class<A> annotationType)`
Stream all annotations and meta-annotations that match the specified type.
`<A extends Annotation>
Stream<MergedAnnotation<A>>`
`stream(String annotationType)`
Stream all annotations and meta-annotations that match the specified type.

### Methods inherited from interface java.lang.Iterable

`forEach, iterator, spliterator`

## Method Details

### isPresent

<A extends Annotation> boolean isPresent(Class<A> annotationType)
Determine if the specified annotation type is either directly present or meta-present.

Equivalent to calling `get(annotationType).isPresent()`.

Parameters:
  `annotationType` - the annotation type to check
Returns:
  `true` if the annotation is present

### isPresent

boolean isPresent(String annotationType)
Determine if the specified annotation type is either directly present or meta-present.

Equivalent to calling `get(annotationType).isPresent()`.

Parameters:
  `annotationType` - the fully qualified class name of the annotation type to check
Returns:
  `true` if the annotation is present

### isDirectlyPresent

<A extends Annotation> boolean isDirectlyPresent(Class<A> annotationType)
Determine if the specified annotation type is directly present.

Equivalent to calling `get(annotationType).isDirectlyPresent()`.

Parameters:
  `annotationType` - the annotation type to check
Returns:
  `true` if the annotation is directly present

### isDirectlyPresent

boolean isDirectlyPresent(String annotationType)
Determine if the specified annotation type is directly present.

Equivalent to calling `get(annotationType).isDirectlyPresent()`.

Parameters:
  `annotationType` - the fully qualified class name of the annotation type to check
Returns:
  `true` if the annotation is directly present

### get

<A extends Annotation> MergedAnnotation<A> get(Class<A> annotationType)
Get the nearest matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.

Parameters:
  `annotationType` - the annotation type to get
Returns:
  a `MergedAnnotation` instance

### get

<A extends Annotation> MergedAnnotation<A> get(Class<A> annotationType, @Nullable Predicate<? super MergedAnnotation<A>> predicate)
Get the nearest matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.

Parameters:
  `annotationType` - the annotation type to get
  `predicate` - a predicate that must match, or `null` if only type matching is required
Returns:
  a `MergedAnnotation` instance
See Also:
  - `MergedAnnotationPredicates`

### get

<A extends Annotation> MergedAnnotation<A> get(Class<A> annotationType, @Nullable Predicate<? super MergedAnnotation<A>> predicate, @Nullable MergedAnnotationSelector<A> selector)
Get a matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.

Parameters:
  `annotationType` - the annotation type to get
  `predicate` - a predicate that must match, or `null` if only type matching is required
  `selector` - a selector used to choose the most appropriate annotation within an aggregate, or `null` to select the nearest
Returns:
  a `MergedAnnotation` instance
See Also:
  - `MergedAnnotationPredicates`
  - `MergedAnnotationSelectors`

### get

<A extends Annotation> MergedAnnotation<A> get(String annotationType)
Get the nearest matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.

Parameters:
  `annotationType` - the fully qualified class name of the annotation type to get
Returns:
  a `MergedAnnotation` instance

### get

<A extends Annotation> MergedAnnotation<A> get(String annotationType, @Nullable Predicate<? super MergedAnnotation<A>> predicate)
Get the nearest matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.

Parameters:
  `annotationType` - the fully qualified class name of the annotation type to get
  `predicate` - a predicate that must match, or `null` if only type matching is required
Returns:
  a `MergedAnnotation` instance
See Also:
  - `MergedAnnotationPredicates`

### get

<A extends Annotation> MergedAnnotation<A> get(String annotationType, @Nullable Predicate<? super MergedAnnotation<A>> predicate, @Nullable MergedAnnotationSelector<A> selector)
Get a matching annotation or meta-annotation of the specified type, or `MergedAnnotation.missing()` if none is present.

Parameters:
  `annotationType` - the fully qualified class name of the annotation type to get
  `predicate` - a predicate that must match, or `null` if only type matching is required
  `selector` - a selector used to choose the most appropriate annotation within an aggregate, or `null` to select the nearest
Returns:
  a `MergedAnnotation` instance
See Also:
  - `MergedAnnotationPredicates`
  - `MergedAnnotationSelectors`

### stream

<A extends Annotation> Stream<MergedAnnotation<A>> stream(Class<A> annotationType)
Stream all annotations and meta-annotations that match the specified type.

The resulting stream follows the same ordering rules as `stream()`.

Parameters:
  `annotationType` - the annotation type to match
Returns:
  a stream of matching annotations

### stream

<A extends Annotation> Stream<MergedAnnotation<A>> stream(String annotationType)
Stream all annotations and meta-annotations that match the specified type.

The resulting stream follows the same ordering rules as `stream()`.

Parameters:
  `annotationType` - the fully qualified class name of the annotation type to match
Returns:
  a stream of matching annotations

### stream

Stream<MergedAnnotation<Annotation>> stream()
Stream all annotations and meta-annotations contained in this collection.

The resulting stream is ordered first by the aggregate index and then by the annotation distance (with the closest annotations first). This ordering means that, for most use-cases, the most suitable annotations appear earliest in the stream.

Returns:
  a stream of annotations

### from

static MergedAnnotations from(AnnotatedElement element)
Create a new `MergedAnnotations` instance containing all annotations and meta-annotations from the specified element.

The resulting instance will not include any inherited annotations. If you want to include those as well you should use `from(AnnotatedElement, SearchStrategy)` with an appropriate `MergedAnnotations.SearchStrategy`.

Parameters:
  `element` - the source element
Returns:
  a `MergedAnnotations` instance containing the merged annotations for the supplied element
See Also:
  - `search(SearchStrategy)`

### from

static MergedAnnotations from(AnnotatedElement element, MergedAnnotations.SearchStrategy searchStrategy)
Create a new `MergedAnnotations` instance containing all annotations and meta-annotations from the specified element and, depending on the `MergedAnnotations.SearchStrategy`, related inherited elements.

Parameters:
  `element` - the source element
  `searchStrategy` - the search strategy to use
Returns:
  a `MergedAnnotations` instance containing the merged annotations for the supplied element
See Also:
  - `search(SearchStrategy)`

### from

static MergedAnnotations from(AnnotatedElement element, MergedAnnotations.SearchStrategy searchStrategy, RepeatableContainers repeatableContainers)
Create a new `MergedAnnotations` instance containing all annotations and meta-annotations from the specified element and, depending on the `MergedAnnotations.SearchStrategy`, related inherited elements.

Parameters:
  `element` - the source element
  `searchStrategy` - the search strategy to use
  `repeatableContainers` - the strategy to use for finding repeatable annotations and their container annotations
Returns:
  a `MergedAnnotations` instance containing the merged annotations for the supplied element
See Also:
  - `search(SearchStrategy)`

### from

static MergedAnnotations from(AnnotatedElement element, MergedAnnotations.SearchStrategy searchStrategy, RepeatableContainers repeatableContainers, AnnotationFilter annotationFilter)
Create a new `MergedAnnotations` instance containing all annotations and meta-annotations from the specified element and, depending on the `MergedAnnotations.SearchStrategy`, related inherited elements.

Parameters:
  `element` - the source element
  `searchStrategy` - the search strategy to use
  `repeatableContainers` - the strategy to use for finding repeatable annotations and their container annotations
  `annotationFilter` - an annotation filter used to restrict the annotations considered
Returns:
  a `MergedAnnotations` instance containing the merged annotations for the supplied element
See Also:
  - `search(SearchStrategy)`

### from

static MergedAnnotations from(Annotation... annotations)
Create a new `MergedAnnotations` instance from the specified annotations.

Parameters:
  `annotations` - the annotations to include
Returns:
  a `MergedAnnotations` instance containing the annotations
See Also:
  - `from(Object, Annotation...)`

### from

static MergedAnnotations from(Object source, Annotation... annotations)
Create a new `MergedAnnotations` instance from the specified annotations.

Parameters:
  `source` - the source for the annotations. This source is used only for information and logging. It does not need to actually contain the specified annotations, and it will not be searched.
  `annotations` - the annotations to include
Returns:
  a `MergedAnnotations` instance containing the annotations
See Also:
  - `from(Annotation...)`
  - `from(AnnotatedElement)`

### from

static MergedAnnotations from(Object source, Annotation[] annotations, RepeatableContainers repeatableContainers)
Create a new `MergedAnnotations` instance from the specified annotations.

Parameters:
  `source` - the source for the annotations. This source is used only for information and logging. It does not need to actually contain the specified annotations, and it will not be searched.
  `annotations` - the annotations to include
  `repeatableContainers` - the strategy to use for finding repeatable annotations and their container annotations
Returns:
  a `MergedAnnotations` instance containing the annotations

### from

static MergedAnnotations from(Object source, Annotation[] annotations, RepeatableContainers repeatableContainers, AnnotationFilter annotationFilter)
Create a new `MergedAnnotations` instance from the specified annotations.

Parameters:
  `source` - the source for the annotations. This source is used only for information and logging. It does not need to actually contain the specified annotations, and it will not be searched.
  `annotations` - the annotations to include
  `repeatableContainers` - the strategy to use for finding repeatable annotations and their container annotations
  `annotationFilter` - an annotation filter used to restrict the annotations considered
Returns:
  a `MergedAnnotations` instance containing the annotations

### of

static MergedAnnotations of(Collection<MergedAnnotation<?>> annotations)
Create a new `MergedAnnotations` instance from the specified collection of directly present annotations. This method allows a `MergedAnnotations` instance to be created from annotations that are not necessarily loaded using reflection. The provided annotations must all be `directly present` and must have an `aggregate index` of `0`.

The resulting `MergedAnnotations` instance will contain both the specified annotations and any meta-annotations that can be read using reflection.

Parameters:
  `annotations` - the annotations to include
Returns:
  a `MergedAnnotations` instance containing the annotations
See Also:
  - `MergedAnnotation.of(ClassLoader, Object, Class, java.util.Map)`

### search

static MergedAnnotations.Search search(MergedAnnotations.SearchStrategy searchStrategy)
Find merged annotations using the supplied `MergedAnnotations.SearchStrategy` and a fluent API for configuring and performing the search.

See `MergedAnnotations.Search` for details.

Parameters:
  `searchStrategy` - the search strategy to use
Returns:
  a `Search` instance to perform the search
Since:
  6.0