001/*
002 * Copyright 2002-2015 the original author or authors.
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *      https://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016
017package org.springframework.core.annotation;
018
019import java.lang.annotation.Annotation;
020import java.lang.annotation.Documented;
021import java.lang.annotation.ElementType;
022import java.lang.annotation.Retention;
023import java.lang.annotation.RetentionPolicy;
024import java.lang.annotation.Target;
025
026/**
027 * {@code @AliasFor} is an annotation that is used to declare aliases for
028 * annotation attributes.
029 *
030 * <h3>Usage Scenarios</h3>
031 * <ul>
032 * <li><strong>Explicit aliases within an annotation</strong>: within a single
033 * annotation, {@code @AliasFor} can be declared on a pair of attributes to
034 * signal that they are interchangeable aliases for each other.</li>
035 * <li><strong>Explicit alias for attribute in meta-annotation</strong>: if the
036 * {@link #annotation} attribute of {@code @AliasFor} is set to a different
037 * annotation than the one that declares it, the {@link #attribute} is
038 * interpreted as an alias for an attribute in a meta-annotation (i.e., an
039 * explicit meta-annotation attribute override). This enables fine-grained
040 * control over exactly which attributes are overridden within an annotation
041 * hierarchy. In fact, with {@code @AliasFor} it is even possible to declare
042 * an alias for the {@code value} attribute of a meta-annotation.</li>
043 * <li><strong>Implicit aliases within an annotation</strong>: if one or
044 * more attributes within an annotation are declared as attribute overrides
045 * for the same meta-annotation attribute (either directly or transitively),
046 * those attributes will be treated as a set of <em>implicit</em> aliases
047 * for each other, resulting in behavior analogous to that for explicit
048 * aliases within an annotation.</li>
049 * </ul>
050 *
051 * <h3>Usage Requirements</h3>
052 * <p>Like with any annotation in Java, the mere presence of {@code @AliasFor}
053 * on its own will not enforce alias semantics. For alias semantics to be
054 * enforced, annotations must be <em>loaded</em> via the utility methods in
055 * {@link AnnotationUtils}. Behind the scenes, Spring will <em>synthesize</em>
056 * an annotation by wrapping it in a dynamic proxy that transparently enforces
057 * <em>attribute alias</em> semantics for annotation attributes that are
058 * annotated with {@code @AliasFor}. Similarly, {@link AnnotatedElementUtils}
059 * supports explicit meta-annotation attribute overrides when {@code @AliasFor}
060 * is used within an annotation hierarchy. Typically you will not need to
061 * manually synthesize annotations on your own since Spring will do that for
062 * you transparently when looking up annotations on Spring-managed components.
063 *
064 * <h3>Implementation Requirements</h3>
065 * <ul>
066 * <li><strong>Explicit aliases within an annotation</strong>:
067 * <ol>
068 * <li>Each attribute that makes up an aliased pair must be annotated with
069 * {@code @AliasFor}, and either {@link #attribute} or {@link #value} must
070 * reference the <em>other</em> attribute in the pair.</li>
071 * <li>Aliased attributes must declare the same return type.</li>
072 * <li>Aliased attributes must declare a default value.</li>
073 * <li>Aliased attributes must declare the same default value.</li>
074 * <li>{@link #annotation} should not be declared.</li>
075 * </ol>
076 * </li>
077 * <li><strong>Explicit alias for attribute in meta-annotation</strong>:
078 * <ol>
079 * <li>The attribute that is an alias for an attribute in a meta-annotation
080 * must be annotated with {@code @AliasFor}, and {@link #attribute} must
081 * reference the attribute in the meta-annotation.</li>
082 * <li>Aliased attributes must declare the same return type.</li>
083 * <li>{@link #annotation} must reference the meta-annotation.</li>
084 * <li>The referenced meta-annotation must be <em>meta-present</em> on the
085 * annotation class that declares {@code @AliasFor}.</li>
086 * </ol>
087 * </li>
088 * <li><strong>Implicit aliases within an annotation</strong>:
089 * <ol>
090 * <li>Each attribute that belongs to a set of implicit aliases must be
091 * annotated with {@code @AliasFor}, and {@link #attribute} must reference
092 * the same attribute in the same meta-annotation (either directly or
093 * transitively via other explicit meta-annotation attribute overrides
094 * within the annotation hierarchy).</li>
095 * <li>Aliased attributes must declare the same return type.</li>
096 * <li>Aliased attributes must declare a default value.</li>
097 * <li>Aliased attributes must declare the same default value.</li>
098 * <li>{@link #annotation} must reference an appropriate meta-annotation.</li>
099 * <li>The referenced meta-annotation must be <em>meta-present</em> on the
100 * annotation class that declares {@code @AliasFor}.</li>
101 * </ol>
102 * </li>
103 * </ul>
104 *
105 * <h3>Example: Explicit Aliases within an Annotation</h3>
106 * <p>In {@code @ContextConfiguration}, {@code value} and {@code locations}
107 * are explicit aliases for each other.
108 *
109 * <pre class="code"> public &#064;interface ContextConfiguration {
110 *
111 *    &#064;AliasFor("locations")
112 *    String[] value() default {};
113 *
114 *    &#064;AliasFor("value")
115 *    String[] locations() default {};
116 *
117 *    // ...
118 * }</pre>
119 *
120 * <h3>Example: Explicit Alias for Attribute in Meta-annotation</h3>
121 * <p>In {@code @XmlTestConfig}, {@code xmlFiles} is an explicit alias for
122 * {@code locations} in {@code @ContextConfiguration}. In other words,
123 * {@code xmlFiles} overrides the {@code locations} attribute in
124 * {@code @ContextConfiguration}.
125 *
126 * <pre class="code"> &#064;ContextConfiguration
127 * public &#064;interface XmlTestConfig {
128 *
129 *    &#064;AliasFor(annotation = ContextConfiguration.class, attribute = "locations")
130 *    String[] xmlFiles();
131 * }</pre>
132 *
133 * <h3>Example: Implicit Aliases within an Annotation</h3>
134 * <p>In {@code @MyTestConfig}, {@code value}, {@code groovyScripts}, and
135 * {@code xmlFiles} are all explicit meta-annotation attribute overrides for
136 * the {@code locations} attribute in {@code @ContextConfiguration}. These
137 * three attributes are therefore also implicit aliases for each other.
138 *
139 * <pre class="code"> &#064;ContextConfiguration
140 * public &#064;interface MyTestConfig {
141 *
142 *    &#064;AliasFor(annotation = ContextConfiguration.class, attribute = "locations")
143 *    String[] value() default {};
144 *
145 *    &#064;AliasFor(annotation = ContextConfiguration.class, attribute = "locations")
146 *    String[] groovyScripts() default {};
147 *
148 *    &#064;AliasFor(annotation = ContextConfiguration.class, attribute = "locations")
149 *    String[] xmlFiles() default {};
150 * }</pre>
151 *
152 * <h3>Example: Transitive Implicit Aliases within an Annotation</h3>
153 * <p>In {@code @GroovyOrXmlTestConfig}, {@code groovy} is an explicit
154 * override for the {@code groovyScripts} attribute in {@code @MyTestConfig};
155 * whereas, {@code xml} is an explicit override for the {@code locations}
156 * attribute in {@code @ContextConfiguration}. Furthermore, {@code groovy}
157 * and {@code xml} are transitive implicit aliases for each other, since they
158 * both effectively override the {@code locations} attribute in
159 * {@code @ContextConfiguration}.
160 *
161 * <pre class="code"> &#064;MyTestConfig
162 * public &#064;interface GroovyOrXmlTestConfig {
163 *
164 *    &#064;AliasFor(annotation = MyTestConfig.class, attribute = "groovyScripts")
165 *    String[] groovy() default {};
166 *
167 *    &#064;AliasFor(annotation = ContextConfiguration.class, attribute = "locations")
168 *    String[] xml() default {};
169 * }</pre>
170 *
171 * <h3>Spring Annotations Supporting Attribute Aliases</h3>
172 * <p>As of Spring Framework 4.2, several annotations within core Spring
173 * have been updated to use {@code @AliasFor} to configure their internal
174 * attribute aliases. Consult the Javadoc for individual annotations as well
175 * as the reference manual for details.
176 *
177 * @author Sam Brannen
178 * @since 4.2
179 * @see AnnotatedElementUtils
180 * @see AnnotationUtils
181 * @see AnnotationUtils#synthesizeAnnotation(Annotation, java.lang.reflect.AnnotatedElement)
182 * @see SynthesizedAnnotation
183 */
184@Retention(RetentionPolicy.RUNTIME)
185@Target(ElementType.METHOD)
186@Documented
187public @interface AliasFor {
188
189        /**
190         * Alias for {@link #attribute}.
191         * <p>Intended to be used instead of {@link #attribute} when {@link #annotation}
192         * is not declared &mdash; for example: {@code @AliasFor("value")} instead of
193         * {@code @AliasFor(attribute = "value")}.
194         */
195        @AliasFor("attribute")
196        String value() default "";
197
198        /**
199         * The name of the attribute that <em>this</em> attribute is an alias for.
200         * @see #value
201         */
202        @AliasFor("value")
203        String attribute() default "";
204
205        /**
206         * The type of annotation in which the aliased {@link #attribute} is declared.
207         * <p>Defaults to {@link Annotation}, implying that the aliased attribute is
208         * declared in the same annotation as <em>this</em> attribute.
209         */
210        Class<? extends Annotation> annotation() default Annotation.class;
211
212}