Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Dependency Injection and other constructor parameters - bad practice?

At the moment I am experimenting a little bit with dependency injection containers, this time with Unity.

Given the following interface:

public interface IPodcastCommService
{
    void Download();

    void Upload();
}

and the following implementation:

public class PodcastService
{
     private IPodcastCommService commservice;
     private String url;

     public PodcastService(String url, IPodcastCommService commservice)
     {
         this.commservice = commservice;
         this.url = url;
     }
}

Because of the constructor, I was looking for a solution to pass the parameter to it and found it:

var p = container.Resolve<IPodcastCommService>(new ParameterOverride("url", myUrl));

So far so good, but at the same time I read about how bad this is and how bad the design of the class is and yes, it looks a little bit ugly. But how can I pass a parameter to class in an elegant way?

My first thought was to do it as a property, but then I have to check every time I need the Url that it is already given.

Update: One example, where I read that this is bad design, is this:

But there may be cases where you have pass in custom constructor parameters for the resolve operation. Some may argue that this screams of bad architecture but there’s situations like bringing a DI-container to a legacy system which may require these kind of actions.

Source: http://mikaelkoskinen.net/unity-passing-constructor-parameters-to-resolve/

like image 286
Kai Avatar asked May 06 '13 08:05

Kai


People also ask

Is it difficult to inject dependency by constructor?

Frameworks that apply the Constrained Construction anti-pattern can make using Constructor Injection difficult. The main disadvantage to Constructor Injection is that if the class you're building is called by your current application framework, you might need to customize that framework to support it.

When to use constructor-based Dependency injection?

Constructor injection helps us to identify if our bean is dependent on too many other objects. If our constructor has a large number of arguments this may be a sign that our class has too many responsibilities. We may want to think about refactoring our code to better address proper separation of concerns.

Can you inject dependency through private constructor?

To answer your question, there is no way. by definition, private constructors are inaccessible by other classes.


1 Answers

I don't get it why you need PodcastService with composition of IPodcastCommService, instead of implemented IPodcastCommService and has the url injected by string. I don't understand why your design is bad. Injecting url is good IMHO.

If you think of a better way, I think it can be replaced by injecting a context / configuration instead of a native data type.

public class PodcastService
{
     private IPodcastCommService commservice;
     private IConnectionContext connection;

     public PodcastService(IConnectionContext connection, IPodcastCommService commservice)
     {
         this.commservice = commservice;
         this.connection= connection;
     }
}

public interface IConnectionContext{
    string PodcastServiceUrl{get;}
}

But again, I don't find any benefit from it (except you can handle session / constants / static fields) from the regular approach.

UPDATE:

I have found similiar question about the bad design here. In summary, it is not that native type parameter (string, etc) or custom constructor parameter is bad. It is just that you need to put the parameter to a class that really responsible for the parameter. And custom constructor parameter will be needed if you handle an if-else condition inside an abstract factory pattern.

like image 101
Fendy Avatar answered Sep 16 '22 19:09

Fendy