Variations of this question have been asked here and, to a lesser extent, here although I don't believe this to be a duplicate question. I have a scenario similar to the question asked in the first link: I have a core library that I am working on that uses DI. For many of the classes my expectation is that the calling application is going to provide implementations of the interfaces that these classes expect, so it is reasonable to assume that the calling application would setup their container correctly (if at all).
What I am having trouble with are a couple of facades that I have setup. The interfaces that these facades rely on are implemented in my library and they are not something that should ever be provided by a calling application. In the first link Mark Seemann suggests using a highly discoverable facade to encapsulate the dependency combinations if the API is to complex for novice users. While I don't think there is anything overly complex about the API, my goal is for a calling application to be able to do something like this (understanding that Widget has internal dependencies):
var foo = new Widget();
If I run with Mark's idea about a facade to return the implementations Widget
expects, my implementation of Widget
would probably look something like this:
public class Widget()
{
public Widget() : this(DependencyFacade.SystemOneDep()) { }
internal Widget(ISystemOne sysOne)
{
//Do work
}
}
Where the SystemOneDep()
call just returns an implementation of ISystemOne
. Certainly this would work but (and I may be over thinking this) this smells a little bit to me because I am now coupled to the DependencyFacade class (internally maybe the DependencyFacade is making calls into factories that actually return the instances instead of simply newing objects up in the facade). Understandably, at some point, something needs to know about the concrete implementation of the interfaces and provide it back to consumers so maybe this is the correct approach.
The real question here is: does a better approach exist for achieving the desired outcome or is the use of a facade the "best" approach to achieve the outcome?