0

I have written some Configuration classes in Spring (4.1.7) to make writing some standard stuff (e.g. Testcases) easier. For this, I used @Condition to check, for example, if there already is a DataSource defined, if not, create a new in-memory one. This is, of course, bascially what Spring Boot already offers - but since we don't have Spring Boot in that application yet, this is not an option for us there.

The whole thing works very well, if you write, for example...

@RunWith(SpringJunit4Runner.class)
@ContextConfiguration( classes = {SomeTest.Config.class, DefaultConfig.class} )
public class SomeTest {

    static class Config {

       ...

In this case, first the static Config class is read, the beans there are created and then DefaultConfig is looked at and instantiates, for example, a DataSource, if Config did not.

The problem I have with this solution is, that it contains an implicit knowledge: You need to know that you have to write the more specific configuration class first in your @ContextConfiguration annotation. If you put DefaultConfig first, it will check that one first and since, for example, no DataSource was yet created, it will create one, which can lead to unfortunate side effects (since some stuff depending on a DataSource are also created there, for example).

I would really like to make this more stable by enforcing that DefaultConfig is ALWAYS loaded as the last configuration (without having to explicitly putting it last in the @ContextConfiguration annotation). So, if a developer messes the whole ordering up, nothing bad happens and everything still works as planned, since DefaultConfig is loaded last and only then checks if everyone else already defined a DataSource, for example.

Is there any way to achieve this? What I need is simply the Spring Boot behavior, where Auto-Configure classes are automatically processed last. Obviously @Order does not work there, since it is not intended for Configuration class ordering... Is there some class one can override to influence the behavior there?

Florian Schaetz
  • 10,454
  • 5
  • 32
  • 58
  • You could try `@Order` annotation on your configuration classes. Classes with lower value for `@Order` should be loaded first – Ivan Jul 20 '18 at 16:36
  • @Ivan Unfortunately, no. As I already mentioned, `@Order` does not work for Configuration classes (at least not in 4.1.7, see also the Javadoc there : "Annotation-based ordering is supported for specific kinds of components only,[..]") – Florian Schaetz Jul 20 '18 at 20:07
  • You could also try `@DependsOn` to mark (any) bean in your `DefaultConfig` `@DependsOn("dataSource")` https://stackoverflow.com/questions/22178735/why-did-spring-ignore-my-dependson-annotation. Maybe that will help – Ivan Jul 20 '18 at 20:12
  • @Ivan This will also not work, since the Configuration the `DefaultConfig` depends on is dynamic (one per test/module/whatever). And making `DefaultConfig` depend on `DateSource` is a bad idea, since `DefaultConfig` provides a `DataSource` when loaded first, thus fullfilling the DependsOn requirement. – Florian Schaetz Jul 20 '18 at 20:33

0 Answers0