1

I feel like I should be able to register all my components into the application composition root container no matter what the current state of the environment is, even in the case environment lacks parts of configuration required to proper working of some of its components.

Currently, I sometimes run into code that for example uses Castle Windsor Dependency.OnValue functionality that allows custom code from the container to supply constructor values. When such custom code fails, application start fails in the composition phase, even before class initialization kicks in.

I feel like every failure in the composition phase that is not of IoC framework concern (like "circular dependency detected") is in fact a symptom of an improper separation concerns issue. So I am tempted to refactor such usages of Dependency.OnValue into a configuration component that still may fail, but later.

On the other hand, fail fast rule would suggest it's nice that system won't even start to function without some important environmental prerequisites being fulfilled.

What would you suggest?


Edit: code example:

public static IWindsorContainer Compose()
{
    var container = new WindsorContainer();
    container.Register(
        // lots of components there

        Component
            .For<IService>()
            .ImplementedBy<DefaultService>()
            .DependsOn(Dependency.OnValue<string>(Configuration.GetString("SomeKey")))
        //                                                      ^ this can fail

        // lots of components there
    );
    return container;
}

Now, unit test like this:

[TestMethod]
public void CompositionDoesntContainCycles()
{
    try
    {
        var container = CompositionRoot.Compose();
    }
    catch (SomeKindOfCycleExceptionThrownByWindsor)
    {
        Assert.Fail();
    }
}

will fail because I need to mock configuration as Compose() does two, not one, thing.

2
  • Some code sample maybe? Commented May 2, 2016 at 14:03
  • Good idea, added. Commented May 3, 2016 at 11:50

1 Answer 1

9

Should composition happen no matter what?

No.

If that's a good enough answer for you, you don't need to read the rest.


As with everything in programming, you shouldn't use a programming approach just because someone mentioned it somewhere and said an apple is better than a beef steak.

Yes, a beef steak might be better for your taste buds if you love meat, but you can be pretty sure a horse would prefer the apple instead.

Although the analogy is really weird, with programming it is the same. Not all design patterns are well suited for all problems and you really shouldn't use design patterns to make an application, design patterns shouldn't be your mantra. They should emerge naturally throughout the application development process.

You want to use composition (in cases not limited to but including) when you want to:

(All the following assume you're using composition in the form of dependency injection.)

  • decouple dependencies
  • make it pretty obvious what the class depends on for all the users of said class
  • you want to test a class without any knowledge of the rest of your application (mocking)

If none of these are your concern or aren't concern of a specific part of the application you're modeling, you don't really need dependency injection at all.


To address your specific concern, if I understood your question right, you're saying an application shouldn't fail during the wiring phase (during the construction of object graph) only because some required parts of configuration are missing.

I strongly disagree. That's why they're required, they need to be set and if they're required, I can only assume the application cannot work without them.

If the application does not need the dependencies, thus configuration from the environment, they're not really required and a default implementation should be provided when specialized is not.

I personally have not worked with Castle Windsor, but I don't think the framework matters, the rules apply everywhere.

3
  • The middle part of this answer is confusing because it addresses a different question, "should I always use dependency injection"
    – Alex
    Commented May 3, 2016 at 13:54
  • @AlexFoxGill I believe OP wants the answer in respect do dependency injection, if you look at the tags.
    – Andy
    Commented May 3, 2016 at 13:57
  • What I meant by the above is what you point out in the latter part of your answer: To address your specific concern, if I understood your question right, you're saying an application shouldn't fail during the wiring phase - you are correct that this was the actual question, so the part above is off-topic (it relates to the general use of dependency injection, nothing to do with this specific case). I think the second part of your answer is good but the first is misleading
    – Alex
    Commented May 3, 2016 at 15:41

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.