diff --git a/spring-test/src/main/java/org/springframework/test/context/ContextLoaderUtils.java b/spring-test/src/main/java/org/springframework/test/context/ContextLoaderUtils.java
index 51a1b3dcc8..a3bd700d35 100644
--- a/spring-test/src/main/java/org/springframework/test/context/ContextLoaderUtils.java
+++ b/spring-test/src/main/java/org/springframework/test/context/ContextLoaderUtils.java
@@ -261,9 +261,9 @@ abstract class ContextLoaderUtils {
* never {@code null}
* @throws IllegalArgumentException if the supplied class is {@code null}; if
* neither {@code @ContextConfiguration} nor {@code @ContextHierarchy} is
- * present on the supplied class; or if a given class in the class hierarchy
- * declares both {@code @ContextConfiguration} and {@code @ContextHierarchy} as
- * top-level annotations.
+ * present on the supplied class; or if a test class or composed annotation
+ * in the class hierarchy declares both {@code @ContextConfiguration} and
+ * {@code @ContextHierarchy} as top-level annotations.
* @throws IllegalStateException if no class in the class hierarchy declares
* {@code @ContextHierarchy}.
*
@@ -296,7 +296,7 @@ abstract class ContextLoaderUtils {
if (contextConfigDeclaredLocally && contextHierarchyDeclaredLocally) {
String msg = String.format("Class [%s] has been configured with both @ContextConfiguration "
+ "and @ContextHierarchy. Only one of these annotations may be declared on a test class "
- + "or custom stereotype annotation.", declaringClass.getName());
+ + "or composed annotation.", declaringClass.getName());
logger.error(msg);
throw new IllegalStateException(msg);
}
@@ -305,12 +305,12 @@ abstract class ContextLoaderUtils {
if (contextConfigDeclaredLocally) {
convertAnnotationAttributesToConfigAttributesAndAddToList(descriptor.getAnnotationAttributes(),
- declaringClass, configAttributesList);
+ rootDeclaringClass, configAttributesList);
}
else if (contextHierarchyDeclaredLocally) {
ContextHierarchy contextHierarchy = getAnnotation(declaringClass, contextHierarchyType);
for (ContextConfiguration contextConfiguration : contextHierarchy.value()) {
- convertContextConfigToConfigAttributesAndAddToList(contextConfiguration, declaringClass,
+ convertContextConfigToConfigAttributesAndAddToList(contextConfiguration, rootDeclaringClass,
configAttributesList);
}
}
@@ -428,7 +428,7 @@ abstract class ContextLoaderUtils {
while (descriptor != null) {
convertAnnotationAttributesToConfigAttributesAndAddToList(descriptor.getAnnotationAttributes(),
- descriptor.getDeclaringClass(), attributesList);
+ descriptor.getRootDeclaringClass(), attributesList);
descriptor = findAnnotationDescriptor(descriptor.getRootDeclaringClass().getSuperclass(), annotationType);
}
diff --git a/spring-test/src/test/java/org/springframework/test/context/AbstractContextLoaderUtilsTests.java b/spring-test/src/test/java/org/springframework/test/context/AbstractContextLoaderUtilsTests.java
index bec2fa7e30..06515d4269 100644
--- a/spring-test/src/test/java/org/springframework/test/context/AbstractContextLoaderUtilsTests.java
+++ b/spring-test/src/test/java/org/springframework/test/context/AbstractContextLoaderUtilsTests.java
@@ -1,5 +1,5 @@
/*
- * Copyright 2002-2013 the original author or authors.
+ * Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -47,11 +47,11 @@ abstract class AbstractContextLoaderUtilsTests {
void assertAttributes(ContextConfigurationAttributes attributes, Class> expectedDeclaringClass,
String[] expectedLocations, Class>[] expectedClasses,
Class extends ContextLoader> expectedContextLoaderClass, boolean expectedInheritLocations) {
- assertEquals(expectedDeclaringClass, attributes.getDeclaringClass());
- assertArrayEquals(expectedLocations, attributes.getLocations());
- assertArrayEquals(expectedClasses, attributes.getClasses());
- assertEquals(expectedInheritLocations, attributes.isInheritLocations());
- assertEquals(expectedContextLoaderClass, attributes.getContextLoaderClass());
+ assertEquals("declaring class", expectedDeclaringClass, attributes.getDeclaringClass());
+ assertArrayEquals("locations", expectedLocations, attributes.getLocations());
+ assertArrayEquals("classes", expectedClasses, attributes.getClasses());
+ assertEquals("inherit locations", expectedInheritLocations, attributes.isInheritLocations());
+ assertEquals("context loader", expectedContextLoaderClass, attributes.getContextLoaderClass());
}
void assertMergedConfig(MergedContextConfiguration mergedConfig, Class> expectedTestClass,
diff --git a/spring-test/src/test/java/org/springframework/test/context/ContextLoaderUtilsConfigurationAttributesTests.java b/spring-test/src/test/java/org/springframework/test/context/ContextLoaderUtilsConfigurationAttributesTests.java
index d41708a120..f32d068e43 100644
--- a/spring-test/src/test/java/org/springframework/test/context/ContextLoaderUtilsConfigurationAttributesTests.java
+++ b/spring-test/src/test/java/org/springframework/test/context/ContextLoaderUtilsConfigurationAttributesTests.java
@@ -1,5 +1,5 @@
/*
- * Copyright 2002-2013 the original author or authors.
+ * Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -59,11 +59,12 @@ public class ContextLoaderUtilsConfigurationAttributesTests extends AbstractCont
@Test
public void resolveConfigAttributesWithBareAnnotations() {
- List attributesList = resolveContextConfigurationAttributes(BareAnnotations.class);
+ Class testClass = BareAnnotations.class;
+ List attributesList = resolveContextConfigurationAttributes(testClass);
assertNotNull(attributesList);
assertEquals(1, attributesList.size());
- assertAttributes(attributesList.get(0), BareAnnotations.class, EMPTY_STRING_ARRAY, EMPTY_CLASS_ARRAY,
- ContextLoader.class, true);
+ assertAttributes(attributesList.get(0), testClass, EMPTY_STRING_ARRAY, EMPTY_CLASS_ARRAY, ContextLoader.class,
+ true);
}
@Test
@@ -76,39 +77,43 @@ public class ContextLoaderUtilsConfigurationAttributesTests extends AbstractCont
@Test
public void resolveConfigAttributesWithMetaAnnotationAndLocations() {
- List attributesList = resolveContextConfigurationAttributes(MetaLocationsFoo.class);
+ Class testClass = MetaLocationsFoo.class;
+ List attributesList = resolveContextConfigurationAttributes(testClass);
assertNotNull(attributesList);
assertEquals(1, attributesList.size());
- assertAttributes(attributesList.get(0), MetaLocationsFooConfig.class, new String[] { "/foo.xml" },
- EMPTY_CLASS_ARRAY, ContextLoader.class, true);
+ assertAttributes(attributesList.get(0), testClass, new String[] { "/foo.xml" }, EMPTY_CLASS_ARRAY,
+ ContextLoader.class, true);
}
@Test
public void resolveConfigAttributesWithMetaAnnotationAndLocationsAndOverrides() {
- List attributesList = resolveContextConfigurationAttributes(MetaLocationsFooWithOverrides.class);
+ Class testClass = MetaLocationsFooWithOverrides.class;
+ List attributesList = resolveContextConfigurationAttributes(testClass);
assertNotNull(attributesList);
assertEquals(1, attributesList.size());
- assertAttributes(attributesList.get(0), MetaLocationsFooConfigWithOverrides.class, new String[] { "/foo.xml" },
- EMPTY_CLASS_ARRAY, ContextLoader.class, true);
+ assertAttributes(attributesList.get(0), testClass, new String[] { "/foo.xml" }, EMPTY_CLASS_ARRAY,
+ ContextLoader.class, true);
}
@Test
public void resolveConfigAttributesWithMetaAnnotationAndLocationsAndOverriddenAttributes() {
- List attributesList = resolveContextConfigurationAttributes(MetaLocationsFooWithOverriddenAttributes.class);
+ Class testClass = MetaLocationsFooWithOverriddenAttributes.class;
+ List attributesList = resolveContextConfigurationAttributes(testClass);
assertNotNull(attributesList);
assertEquals(1, attributesList.size());
- assertAttributes(attributesList.get(0), MetaLocationsFooConfigWithOverrides.class, new String[] { "foo1.xml",
- "foo2.xml" }, EMPTY_CLASS_ARRAY, ContextLoader.class, true);
+ assertAttributes(attributesList.get(0), testClass, new String[] { "foo1.xml", "foo2.xml" }, EMPTY_CLASS_ARRAY,
+ ContextLoader.class, true);
}
@Test
public void resolveConfigAttributesWithMetaAnnotationAndLocationsInClassHierarchy() {
- List attributesList = resolveContextConfigurationAttributes(MetaLocationsBar.class);
+ Class testClass = MetaLocationsBar.class;
+ List attributesList = resolveContextConfigurationAttributes(testClass);
assertNotNull(attributesList);
assertEquals(2, attributesList.size());
- assertAttributes(attributesList.get(0), MetaLocationsBarConfig.class, new String[] { "/bar.xml" },
- EMPTY_CLASS_ARRAY, ContextLoader.class, true);
- assertAttributes(attributesList.get(1), MetaLocationsFooConfig.class, new String[] { "/foo.xml" },
+ assertAttributes(attributesList.get(0), testClass, new String[] { "/bar.xml" }, EMPTY_CLASS_ARRAY,
+ ContextLoader.class, true);
+ assertAttributes(attributesList.get(1), MetaLocationsFoo.class, new String[] { "/foo.xml" },
EMPTY_CLASS_ARRAY, ContextLoader.class, true);
}
diff --git a/spring-test/src/test/java/org/springframework/test/context/ContextLoaderUtilsContextHierarchyTests.java b/spring-test/src/test/java/org/springframework/test/context/ContextLoaderUtilsContextHierarchyTests.java
index 2a0b24820c..11c82054d6 100644
--- a/spring-test/src/test/java/org/springframework/test/context/ContextLoaderUtilsContextHierarchyTests.java
+++ b/spring-test/src/test/java/org/springframework/test/context/ContextLoaderUtilsContextHierarchyTests.java
@@ -1,5 +1,5 @@
/*
- * Copyright 2002-2013 the original author or authors.
+ * Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -71,15 +71,16 @@ public class ContextLoaderUtilsContextHierarchyTests extends AbstractContextLoad
@Test
public void resolveContextHierarchyAttributesForSingleTestClassWithSingleLevelContextHierarchyFromMetaAnnotation() {
- List> hierarchyAttributes = resolveContextHierarchyAttributes(SingleTestClassWithSingleLevelContextHierarchyFromMetaAnnotation.class);
+ Class testClass = SingleTestClassWithSingleLevelContextHierarchyFromMetaAnnotation.class;
+ List> hierarchyAttributes = resolveContextHierarchyAttributes(testClass);
assertEquals(1, hierarchyAttributes.size());
List configAttributesList = hierarchyAttributes.get(0);
assertNotNull(configAttributesList);
assertEquals(1, configAttributesList.size());
debugConfigAttributes(configAttributesList);
- assertAttributes(configAttributesList.get(0), ContextHierarchyA.class, new String[] { "A.xml" },
- EMPTY_CLASS_ARRAY, ContextLoader.class, true);
+ assertAttributes(configAttributesList.get(0), testClass, new String[] { "A.xml" }, EMPTY_CLASS_ARRAY,
+ ContextLoader.class, true);
}
@Test
@@ -131,7 +132,8 @@ public class ContextLoaderUtilsContextHierarchyTests extends AbstractContextLoad
debugConfigAttributes(configAttributesListClassLevel1);
assertEquals(1, configAttributesListClassLevel1.size());
assertThat(configAttributesListClassLevel1.get(0).getLocations()[0], equalTo("A.xml"));
- assertAttributes(configAttributesListClassLevel1.get(0), ContextHierarchyA.class, new String[] { "A.xml" },
+ assertAttributes(configAttributesListClassLevel1.get(0),
+ TestClass1WithSingleLevelContextHierarchyFromMetaAnnotation.class, new String[] { "A.xml" },
EMPTY_CLASS_ARRAY, ContextLoader.class, true);
List configAttributesListClassLevel2 = hierarchyAttributes.get(1);
@@ -139,14 +141,17 @@ public class ContextLoaderUtilsContextHierarchyTests extends AbstractContextLoad
assertEquals(1, configAttributesListClassLevel2.size());
assertArrayEquals(new String[] { "B-one.xml", "B-two.xml" },
configAttributesListClassLevel2.get(0).getLocations());
- assertAttributes(configAttributesListClassLevel2.get(0), ContextHierarchyB.class, new String[] { "B-one.xml",
+ assertAttributes(configAttributesListClassLevel2.get(0),
+ TestClass2WithSingleLevelContextHierarchyFromMetaAnnotation.class,
+ new String[] { "B-one.xml",
"B-two.xml" }, EMPTY_CLASS_ARRAY, ContextLoader.class, true);
List configAttributesListClassLevel3 = hierarchyAttributes.get(2);
debugConfigAttributes(configAttributesListClassLevel3);
assertEquals(1, configAttributesListClassLevel3.size());
assertThat(configAttributesListClassLevel3.get(0).getLocations()[0], equalTo("C.xml"));
- assertAttributes(configAttributesListClassLevel3.get(0), ContextHierarchyC.class, new String[] { "C.xml" },
+ assertAttributes(configAttributesListClassLevel3.get(0),
+ TestClass3WithSingleLevelContextHierarchyFromMetaAnnotation.class, new String[] { "C.xml" },
EMPTY_CLASS_ARRAY, ContextLoader.class, true);
}
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfig.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfig.java
new file mode 100644
index 0000000000..d23a7b2c40
--- /dev/null
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfig.java
@@ -0,0 +1,89 @@
+/*
+ * Copyright 2002-2014 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.springframework.test.context.junit4.annotation.meta;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.Profile;
+import org.springframework.test.context.ActiveProfiles;
+import org.springframework.test.context.ActiveProfilesResolver;
+import org.springframework.test.context.ContextConfiguration;
+
+/**
+ * Custom configuration annotation with meta-annotation attribute overrides for
+ * {@link ContextConfiguration#classes} and {@link ActiveProfiles#resolver} and
+ * with default configuration local to the composed annotation.
+ *
+ * @author Sam Brannen
+ * @since 4.0.3
+ */
+@ContextConfiguration
+@ActiveProfiles
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.TYPE)
+public @interface ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfig {
+
+ @Configuration
+ @Profile("dev")
+ static class DevConfig {
+
+ @Bean
+ public String foo() {
+ return "Dev Foo";
+ }
+ }
+
+ @Configuration
+ @Profile("prod")
+ static class ProductionConfig {
+
+ @Bean
+ public String foo() {
+ return "Production Foo";
+ }
+ }
+
+ @Configuration
+ @Profile("resolver")
+ static class ResolverConfig {
+
+ @Bean
+ public String foo() {
+ return "Resolver Foo";
+ }
+ }
+
+ static class CustomResolver implements ActiveProfilesResolver {
+
+ @Override
+ public String[] resolve(Class> testClass) {
+ return testClass.getSimpleName().equals("ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfigTests") ? new String[] { "resolver" }
+ : new String[] {};
+ }
+ }
+
+
+ Class>[] classes() default { DevConfig.class, ProductionConfig.class, ResolverConfig.class };
+
+ Class extends ActiveProfilesResolver> resolver() default CustomResolver.class;
+
+}
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfigTests.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfigTests.java
new file mode 100644
index 0000000000..9b713a33bf
--- /dev/null
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfigTests.java
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2002-2014 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.springframework.test.context.junit4.annotation.meta;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
+
+import static org.junit.Assert.*;
+
+/**
+ * Integration tests for meta-annotation attribute override support, relying on
+ * default attribute values defined in {@link ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfig}.
+ *
+ * @author Sam Brannen
+ * @since 4.0.3
+ */
+@RunWith(SpringJUnit4ClassRunner.class)
+@ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfig
+public class ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfigTests {
+
+ @Autowired
+ private String foo;
+
+
+ @Test
+ public void foo() {
+ assertEquals("Resolver Foo", foo);
+ }
+}
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfigWithOverridesTests.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfigWithOverridesTests.java
new file mode 100644
index 0000000000..fb504dbcf8
--- /dev/null
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfigWithOverridesTests.java
@@ -0,0 +1,71 @@
+/*
+ * Copyright 2002-2014 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.springframework.test.context.junit4.annotation.meta;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.Profile;
+import org.springframework.test.context.ActiveProfilesResolver;
+import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
+
+import static org.junit.Assert.*;
+
+/**
+ * Integration tests for meta-annotation attribute override support, overriding
+ * default attribute values defined in {@link ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfig}.
+ *
+ * @author Sam Brannen
+ * @since 4.0.3
+ */
+@RunWith(SpringJUnit4ClassRunner.class)
+@ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfig(classes = LocalDevConfig.class, resolver = DevResolver.class)
+public class ConfigClassesAndProfileResolverWithCustomDefaultsMetaConfigWithOverridesTests {
+
+ @Autowired
+ private String foo;
+
+
+ @Test
+ public void foo() {
+ assertEquals("Local Dev Foo", foo);
+ }
+}
+
+@Configuration
+@Profile("dev")
+class LocalDevConfig {
+
+ @Bean
+ public String foo() {
+ return "Local Dev Foo";
+ }
+}
+
+class DevResolver implements ActiveProfilesResolver {
+
+ @Override
+ public String[] resolve(Class> testClass) {
+ // Checking that the "test class" name ends with "*Tests" ensures that an actual
+ // test class is passed to this method as opposed to a "*Config" class which would
+ // imply that we likely have been passed the 'declaringClass' instead of the
+ // 'rootDeclaringClass'.
+ return testClass.getName().endsWith("Tests") ? new String[] { "dev" } : new String[] {};
+ }
+}
\ No newline at end of file
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesMetaConfig.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesMetaConfig.java
new file mode 100644
index 0000000000..f5269f8d37
--- /dev/null
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesMetaConfig.java
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2002-2014 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.springframework.test.context.junit4.annotation.meta;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+import org.springframework.test.context.ActiveProfiles;
+import org.springframework.test.context.ContextConfiguration;
+
+/**
+ * Custom configuration annotation with meta-annotation attribute overrides for
+ * {@link ContextConfiguration#classes} and {@link ActiveProfiles#profiles} and
+ * no default configuration local to the composed annotation.
+ *
+ * @author Sam Brannen
+ * @since 4.0.3
+ */
+@ContextConfiguration
+@ActiveProfiles
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.TYPE)
+public @interface ConfigClassesAndProfilesMetaConfig {
+
+ Class>[] classes() default {};
+
+ String[] profiles() default {};
+
+}
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesMetaConfigTests.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesMetaConfigTests.java
new file mode 100644
index 0000000000..01386b97f1
--- /dev/null
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesMetaConfigTests.java
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2002-2014 the original author or authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.springframework.test.context.junit4.annotation.meta;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.Profile;
+import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
+
+import static org.junit.Assert.*;
+
+/**
+ * Integration tests for meta-annotation attribute override support, demonstrating
+ * that the test class is used as the declaring class when detecting default
+ * configuration classes for the declaration of {@code @ContextConfiguration}.
+ *
+ * @author Sam Brannen
+ * @since 4.0.3
+ */
+@RunWith(SpringJUnit4ClassRunner.class)
+@ConfigClassesAndProfilesMetaConfig(profiles = "dev")
+public class ConfigClassesAndProfilesMetaConfigTests {
+
+ @Configuration
+ @Profile("dev")
+ static class DevConfig {
+
+ @Bean
+ public String foo() {
+ return "Local Dev Foo";
+ }
+ }
+
+ @Configuration
+ @Profile("prod")
+ static class ProductionConfig {
+
+ @Bean
+ public String foo() {
+ return "Local Production Foo";
+ }
+ }
+
+
+ @Autowired
+ private String foo;
+
+
+ @Test
+ public void foo() {
+ assertEquals("Local Dev Foo", foo);
+ }
+}
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaConfig.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesWithCustomDefaultsMetaConfig.java
similarity index 89%
rename from spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaConfig.java
rename to spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesWithCustomDefaultsMetaConfig.java
index 51d2ec70a9..399ddc29f9 100644
--- a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaConfig.java
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesWithCustomDefaultsMetaConfig.java
@@ -1,5 +1,5 @@
/*
- * Copyright 2002-2013 the original author or authors.
+ * Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -29,7 +29,8 @@ import org.springframework.test.context.ContextConfiguration;
/**
* Custom configuration annotation with meta-annotation attribute overrides for
- * {@link ContextConfiguration#classes} and {@link ActiveProfiles#profiles}.
+ * {@link ContextConfiguration#classes} and {@link ActiveProfiles#profiles} and
+ * with default configuration local to the composed annotation.
*
* @author Sam Brannen
* @since 4.0
@@ -38,7 +39,7 @@ import org.springframework.test.context.ContextConfiguration;
@ActiveProfiles
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
-public @interface MetaConfig {
+public @interface ConfigClassesAndProfilesWithCustomDefaultsMetaConfig {
@Configuration
@Profile("dev")
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaConfigDefaultsTests.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesWithCustomDefaultsMetaConfigTests.java
similarity index 79%
rename from spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaConfigDefaultsTests.java
rename to spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesWithCustomDefaultsMetaConfigTests.java
index 0e42192f6e..55b30ae2da 100644
--- a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaConfigDefaultsTests.java
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesWithCustomDefaultsMetaConfigTests.java
@@ -1,5 +1,5 @@
/*
- * Copyright 2002-2013 the original author or authors.
+ * Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -25,14 +25,14 @@ import static org.junit.Assert.*;
/**
* Integration tests for meta-annotation attribute override support, relying on
- * default attribute values defined in {@link MetaConfig @MetaConfig}.
+ * default attribute values defined in {@link ConfigClassesAndProfilesWithCustomDefaultsMetaConfig}.
*
* @author Sam Brannen
* @since 4.0
*/
@RunWith(SpringJUnit4ClassRunner.class)
-@MetaConfig
-public class MetaConfigDefaultsTests {
+@ConfigClassesAndProfilesWithCustomDefaultsMetaConfig
+public class ConfigClassesAndProfilesWithCustomDefaultsMetaConfigTests {
@Autowired
private String foo;
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaConfigOverrideTests.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesWithCustomDefaultsMetaConfigWithOverridesTests.java
similarity index 79%
rename from spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaConfigOverrideTests.java
rename to spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesWithCustomDefaultsMetaConfigWithOverridesTests.java
index 3567d28bdd..c7e05b3023 100644
--- a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaConfigOverrideTests.java
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/ConfigClassesAndProfilesWithCustomDefaultsMetaConfigWithOverridesTests.java
@@ -1,5 +1,5 @@
/*
- * Copyright 2002-2013 the original author or authors.
+ * Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -28,14 +28,15 @@ import static org.junit.Assert.*;
/**
* Integration tests for meta-annotation attribute override support, overriding
- * default attribute values defined in {@link MetaConfig}.
+ * default attribute values defined in {@link ConfigClassesAndProfilesWithCustomDefaultsMetaConfig}.
*
* @author Sam Brannen
* @since 4.0
*/
@RunWith(SpringJUnit4ClassRunner.class)
-@MetaConfig(classes = { PojoAndStringConfig.class, MetaConfig.ProductionConfig.class }, profiles = "prod")
-public class MetaConfigOverrideTests {
+@ConfigClassesAndProfilesWithCustomDefaultsMetaConfig(classes = { PojoAndStringConfig.class,
+ ConfigClassesAndProfilesWithCustomDefaultsMetaConfig.ProductionConfig.class }, profiles = "prod")
+public class ConfigClassesAndProfilesWithCustomDefaultsMetaConfigWithOverridesTests {
@Autowired
private String foo;
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaMetaConfig.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaMetaConfig.java
index d468addee0..9cdd6dacf4 100644
--- a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaMetaConfig.java
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaMetaConfig.java
@@ -24,16 +24,17 @@ import java.lang.annotation.Target;
import org.springframework.test.context.ActiveProfiles;
/**
- * Custom configuration annotation that is itself meta-annotated with
- * {@link MetaConfig @MetaConfig} and {@link ActiveProfiles @ActiveProfiles}.
+ * Custom configuration annotation that is itself meta-annotated with {@link
+ * ConfigClassesAndProfilesWithCustomDefaultsMetaConfig} and {@link ActiveProfiles}.
*
* @author Sam Brannen
* @since 4.0.3
*/
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
-@MetaConfig
-// Override default "dev" profile from @MetaConfig:
+@ConfigClassesAndProfilesWithCustomDefaultsMetaConfig
+// Override default "dev" profile from
+// @ConfigClassesAndProfilesWithCustomDefaultsMetaConfig:
@ActiveProfiles("prod")
public @interface MetaMetaConfig {
diff --git a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaMetaConfigDefaultsTests.java b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaMetaConfigDefaultsTests.java
index 87277690e0..6ad89e9f31 100644
--- a/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaMetaConfigDefaultsTests.java
+++ b/spring-test/src/test/java/org/springframework/test/context/junit4/annotation/meta/MetaMetaConfigDefaultsTests.java
@@ -24,9 +24,9 @@ import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import static org.junit.Assert.*;
/**
- * Integration tests for meta-meta-annotation support, relying on
- * default attribute values defined in {@link MetaConfig @MetaConfig} and
- * overrides in {@link MetaMetaConfig @MetaMetaConfig}.
+ * Integration tests for meta-meta-annotation support, relying on default attribute
+ * values defined in {@link ConfigClassesAndProfilesWithCustomDefaultsMetaConfig} and
+ * overrides in {@link MetaMetaConfig}.
*
* @author Sam Brannen
* @since 4.0.3
diff --git a/spring-test/src/test/java/org/springframework/test/context/web/MetaAnnotationConfigWacTests.java b/spring-test/src/test/java/org/springframework/test/context/web/MetaAnnotationConfigWacTests.java
index 37d4f6d1c0..5ca2197929 100644
--- a/spring-test/src/test/java/org/springframework/test/context/web/MetaAnnotationConfigWacTests.java
+++ b/spring-test/src/test/java/org/springframework/test/context/web/MetaAnnotationConfigWacTests.java
@@ -1,5 +1,5 @@
/*
- * Copyright 2002-2012 the original author or authors.
+ * Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -22,6 +22,7 @@ import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.mock.web.MockServletContext;
+import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import org.springframework.web.context.WebApplicationContext;
@@ -29,14 +30,14 @@ import static org.junit.Assert.*;
/**
* Integration test that verifies meta-annotation support for {@link WebAppConfiguration}
- * and {@link org.springframework.test.context.ContextConfiguration ContextConfiguration}.
+ * and {@link ContextConfiguration}.
*
* @author Sam Brannen
* @since 4.0
- * @see WebTestStereotype
+ * @see WebTestConfiguration
*/
@RunWith(SpringJUnit4ClassRunner.class)
-@WebTestStereotype
+@WebTestConfiguration
public class MetaAnnotationConfigWacTests {
@Autowired
diff --git a/spring-test/src/test/java/org/springframework/test/context/web/WebTestStereotype.java b/spring-test/src/test/java/org/springframework/test/context/web/WebTestConfiguration.java
similarity index 81%
rename from spring-test/src/test/java/org/springframework/test/context/web/WebTestStereotype.java
rename to spring-test/src/test/java/org/springframework/test/context/web/WebTestConfiguration.java
index 1ee2c72727..be4f29d3a3 100644
--- a/spring-test/src/test/java/org/springframework/test/context/web/WebTestStereotype.java
+++ b/spring-test/src/test/java/org/springframework/test/context/web/WebTestConfiguration.java
@@ -24,23 +24,23 @@ import org.springframework.context.annotation.Configuration;
import org.springframework.test.context.ContextConfiguration;
/**
- * Custom stereotype combining {@link WebAppConfiguration} and
+ * Custom composed annotation combining {@link WebAppConfiguration} and
* {@link ContextConfiguration} as meta-annotations.
*
* @author Sam Brannen
* @since 4.0
*/
@WebAppConfiguration
-@ContextConfiguration
+@ContextConfiguration(classes = FooConfig.class)
@Retention(RetentionPolicy.RUNTIME)
-public @interface WebTestStereotype {
+public @interface WebTestConfiguration {
+}
- @Configuration
- static class Config {
+@Configuration
+class FooConfig {
- @Bean
- public String foo() {
- return "enigma";
- }
+ @Bean
+ public String foo() {
+ return "enigma";
}
}
\ No newline at end of file