As per this Wikipedia article: Implementing Dependency Inversion Principle can be done in two ways:
- Having an abstraction of a low level component in a separate package upon which both high level and low level components depend.
- Having the abstraction of the low level component reside in the same package of the high level component.
The following illustration depicts the dependencies before and after DIP using the two approaches:
Before DIP: The repository resides in a separate maven module and has no interface, and the service has a direct dependency on the Repository implementation.
Approach 1: An interface (abstraction) of the repository is introduced. The implementation of that interface is another module, and both the service and the repository implementation have direct dependency on the interface.
Approach 2: In this approach, the interface resides in the same package of the service. The diagram used by Fowler to describe Separated Interface pattern seems to be also an example of this approach.
I've been following Approach1 and because I used spring's JavaConfig, the services module had to have a ,maven dependency to both the infrastructure interfaces and implementation modules. Apart from my @Configuration
file, there's absolutely no reference to any infrastructure concrete implementation.
I'm currently considering switching to Approach2, but obviously it won't work with JavaConfig as I will end up having direct references in the code to the interface implementation module resulting in a cyclic dependency, something build tools like maven can't deal with.
The question is how can configure spring and maven to achieve Approach2? Is there a way I can ask spring to scan for components that are not added as a maven dependency? Will that require changes in the way I'm using maven?