Optional constructor injection arguments with .NET Core
In your example, you provide the serviceProvider
with a runtime value currentDependency
. Application components should not require runtime data during construction, as explained here. The solution is to refactor your design, as explained in that article.
About optional arguments:
The fact that some DI Containers support optional arguments, doesn't make it a good practice to use them. As a matter of fact, injection constructor arguments should never be optional.
As explained in this article:
An optional dependency implies that the reference to the dependency will be null when it’s not supplied. Null references complicate code because they require specific logic for the null-case. Instead of passing in a null reference, the caller could insert an implementation with no behavior, i.e. an implementation of the Null Object Pattern.
If not, what is a clean solution for this sort of problem?
As stated, the Null Object pattern is the solution for this, even when using a DI Container that actually supports optional constructor dependencies.
Normally, I create a factory by hand in this case.
public class TheFactory
{
public TheFactory( SomeType fromContainer )
{
_fromContainer = fromContainer;
}
public IProduct Create( SomeOtherType notFromContainer ) => new TheProduct( _fromContainer, notFromContainer );
private readonly SomeType _fromContainer;
private class TheProduct : IProduct
{
// ...
}
}
If you need per-product dependencies from the container, the factory's Create
has to resolve them. Or, in the case of e.g. unity, the factory gets a Func
from the container.