-
Notifications
You must be signed in to change notification settings - Fork 38.8k
Description
Josiah Haswell opened SPR-12603 and commented
It would be very nice for creating custom test annotations if we could get access to the GenericApplicationContext before it's loaded.
For instance:
I'm creating Cassandra and Datomic unit-testing support. I would like to generate schemata and import data before a test class is run, then clean up after a test is finished. Consider the following scenario:
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration
@CassandraTest(
configurationFile = "cassandra.yaml",
timeout = 3600,
port = 9143,
host = "localhost",
clusterName = "cluster"
)
public class CassandraPersistenceTestCase {
@Configuration
static class Config {
// Cassandra configuration ...
}
@Autowired
Cluster cluster;
// test methods ...
}In this scenario, I would like to use the annotation @CassandraTest on CassandraPersistenceTestCase to:
- Set up an embedded Cassandra instance
- Access the application context to register a Cluster configured from the annotation so that I may inject it into the test case.
If I use the TestExecutionListener APIs, then I have access to the PersistenceTestCase class, but only after the ApplicationContext has been refreshed.
If I use the ApplicationContextInitializer APIs, then I can access the ApplicationContext before it has been refreshed, but I cannot easily access the class annotated by CassandraTest.
I could implement all of this very easily if I could only get access to a subclass of the AbstractGenericContextLoader (specifically the customizeContext method), but everything in the call chain is package-local. I could even work around this if TestContextManager were an interface or an abstract superclass, but it isn't.
My proposal would be to introduce the following classes:
@Retention(RetentionPolicy.RUNTIME)
public @interface ContextDecorators {
Class<? extends ContextDecorator>[] value() default {};
}interface ContextDecorator {
void decorate(TestContext context);
}Then, in SpringJUnit4ClassRunner, check to see if that annotation exists on the test class. If it does, route it to an implementation of customizeContext() in AbstractGenericContextLoader that applies each ContextDecorator to that context.
This would be minimally invasive and not change the existing behavior at all if the annotation is omitted.
I will submit a pull request along these lines if no one has any objections, or if no superior alternatives are available.
Affects: 3.2 GA
Issue Links:
- Introduce ContextCustomizer API in the TestContext framework [SPR-13998] #18571 Introduce ContextCustomizer API in the TestContext framework
- Introduce ContextCustomizer API in the TestContext framework [SPR-13998] #18571 Introduce ContextCustomizer API in the TestContext framework ("is superseded by")