The usual result of Poor Man’s Dependency Injection

Alternate Title: An IoC Container is a Rich Man’s Factory Pattern Implementation

I ruffled some feathers with my last post on Poor Man’s Dependency Injection (PDMI), so please allow me to clarify further.

The natural progression of using PMDI is this:

  • You start out using PMDI, everything is fine. It goes really smooth and easy. “What’s the big deal?” you think.
  • Later, you need to add some functionality. DI makes it easy, but then you have all these “new()” calls lying around.  Well, that “new FooRepository()” call that’s being made in 17 places in your code now suddenly changes to “new FooRepository(new ConfiguredSessionSource())”, for example.  17 changes. Not terrible, but not good either.
  • Later, ConfiguredSessionSource needs to take in some configuration. This is getting out of hand. Making all these changes gets difficult.  I know! I’ll write a small factory that will manage the creation of all these objects.
  • Eventually even the factory gets too convoluted with all the different forms your dependency object graph can take. It’s out of hand now.
  • You now have to make a choice:  Improve your factory implementation and eventually implement a half-baked IoC container, or just use an IoC Container.

Every time I’ve used PDMI (which was a significant number of attempts a few years ago), I ended up at this point.  I wrote a few half-baked IoC containers that ended up being more complex than the application itself.  The rest of the time, I ended up going the IoC route, even for small apps with less than, say, 10 classes.

It’s my recommendation that you save yourself some headache and go right for the IoC container. Yes, I know it’s new and a little scary, but trust me, once you get the hang of it, you’ll never look back and laugh at all the fuss that’s being made over this.  It’s like wearing seat belts: Sure, it’s a hassle the first few times and the perceived benefit is little, but once you start doing it it’s not a big deal and the alternative is not pleasant to think about any more.

One more thing:  How small is too small for IoC?

If you have less than “a few” classes and have no expectation this project will grow further.  In my experience, every project usually grows and the ones that don’t are the very rare exception.

Once you have more than “a few” classes, the complexity of maintaining the coupling and dependency graph starts growing rapidly and you’ll wish you had an IoC container later.  You’ll then spend more time retrofitting in a container than if you had just started out that way. So save yourself some effort and just do it.

Also, since the effort, once familiar with a container, is so low that even if you don’t end up reaping the benefits, the sunk cost of using a container unnecessarily is negligible.

Related Articles:

Post Footer automatically generated by Add Post Footer Plugin for wordpress.

About Chad Myers

Chad Myers is the Director of Development for Dovetail Software, in Austin, TX, where he leads a premiere software team building complex enterprise software products. Chad is a .NET software developer specializing in enterprise software designs and architectures. He has over 12 years of software development experience and a proven track record of Agile, test-driven project leadership using both Microsoft and open source tools. He is a community leader who speaks at the Austin .NET User's Group, the ADNUG Code Camp, and participates in various development communities and open source projects.
This entry was posted in Advice, IoC. Bookmark the permalink. Follow any comments here with the RSS feed for this post.
  • Kelly

    Thats an odd way to do PMDI, I see why you think PMDI is so crappy.

    Instead of doing new FooRepository(new ConfiguredSessionSource()).

    Make each class have a parameterless constructor. The class itself can decide what it needs to new up.

    FooRepository() : this(new ConfiguredSessionSource())

    If you do it like that, the only place you need to make changes is in the parameterless constructor.

    I recently attended the .Net bootcamp by JP Boodhoo. We started out with PMDI and moved towards and IoC, it was painless and easy. After your IoC is ready you simply delete all the parameterless cotors and your good to go.

  • http://www.lostechies.com/members/bogardj/default.aspx bogardj

    @Kelly

    So why bother with the pointless middle step, other than perhaps a teaching situation?

  • http://www.lostechies.com/members/chadmyers/default.aspx chadmyers

    @Kelly: I’m aware of this. The point I was trying to illustrate, however, was that eventually you’re going to get to a point where you can’t simply hard-code everything in a default c’tor.

    Eventually you’re going to have more than one concrete impl of an interface. Which one do you choose in your default c’tor then?

    You can’t. You must pass it in. At this point, PMDI breaks horribly and you start descending into the madness I describe in the post above.

  • http://home.infusionblogs.com/kszklenski/default.aspx Kyle Szklenski

    PDMI – Poor, Dependent-Man’s Injection == heroine?

    But seriously, I totally agree. I forget who said it, but if you’re doing something like PMDI, then you’re stealing from your customers, because free, well-supported (and customizable) IoCs exist. It’s also, in my opinion, not that steep of a learning curve to pick up some random IoC container and start using it, so instead of reimplementing the wheel, please, people: Use a real container.

  • Kelly

    @bogardj: Because its quick and easy. And yes thats what I said, its a great learning step.

    @chadmyers: So now your saying “eventually you’re going to get to a point…”

    Isn’t that exactly the point I was trying to make? like I said before, its a good starting point for beginners. PMDI buys you a lot (great for testability and sets the stage for IoC), and in the beginning, its very easy .

    “At this point, PMDI breaks horribly and you start descending into the madness I describe in the post above.”

    At that point you can choose to move over to an IoC. Iv done this, its not messy or difficult at all.

    All I’m trying to say is that PMDI is a great way for people to get into DI and discover what it can do for you.

  • http://www.lostechies.com/members/chadmyers/default.aspx chadmyers

    @Kelly:

    I just don’t buy the argument that PMDI is a lot easier. It’s just not that hard to get started with StructureMap, for example.

    And the pain that you’ll inevitably experience with PMDI makes it not even worth doing in the beginning.

  • http://graysmatter.codivation.com Justice~!

    OH MY GOODNESS, I TOTALLY AGREE WITH CHAD MYERS.

    Seriously I can’t tell you how much pain it saves me using DI/IOC like a real man rather than this wussy ass constructor based stuff. Often something I have to remind my team about.

  • Kelly

    ” It’s just not that hard to get started with StructureMap.”

    Its also just not that hard to move from PMDI to StructureMap.

    Iv moved from PMDI to IoC before, I didn’t experience all that pain your talking about.

  • http://nhforge.org/members/fabiomaulo/default.aspx Fabio Maulo

    Amen!!
    Too many people are scared by “IoC” and “DI” words, without study what really are.
    I can’t think in a modern application without, first, choose an IoC framework.

  • http://www.ericswann.org Eric Swann

    I’m with you on this one dude. Probably step 2 or 3 after creating a project for me now is to drop in a reference to one of the various IOC containers. I don’t even see the point of waiting. “Just do it”. There’s so many DI choices out there that make this so darn easy now.

  • cbp

    I have to respectfully disagree that it is easy to learn how to use StructureMap. I’m not certain what type of organisations you have experience with, but certainly the places that I have worked at would really struggle if a couple of developers were using StructureMap.

    You must remember that the use of IoC containers generally comes at the end of a long line of OO concepts, many of which take years to learn, have only recently been popularised and are not taught in many undergraduate CS courses.

    Whilst careful use of PMDI is not too scary, the use of IoC containers so drastically changes the way your code looks and feels, that it would be suicide for a senior developer to start using StructureMap when the rest of the developers on the team are still years behind.

    Think about the progression of a dedicated Joe Developer working for a smallish company, in a small state capital in Europe, Asia, Australia, Africa, without the structured environment sometimes found in big American companies: 3 years CS course after which he can program in some basic fashion. 2 years in which he gains initial competence in a particular programming environment. 2 year to realise he is doing everything wrong and to start improving his unit testing, OO pattern chops, etc.. 1 year to realise he is still doing it all wrong. So at the bare minimum, we are seeing at least 5 years of quite dedicated post-college experience before someone can begin to handle something like StructureMap.

    There are zillions of development teams around the world that have at most –one– developer on board who has been through this full progression. These teams are literally years away from being able to comfortably utilise a technology like StructureMap.

  • http://www.lostechies.com/members/chadmyers/default.aspx chadmyers

    @cbp:

    So you’re content to allow low-end developers wallow in their ignorance? You admit IoC/DI is better, yet you say it’s too hard for the common developer.

    Why not be part of the solution and help raise the bar? Of course it’ll be hard and trying, but that’s the price of advancement.

  • http://@cbp jasonvanbrackel

    IoC/DI are not that hard. In my previous job I was mentoring college interns in CS and BIS to do IoC with Windsor, and TDD with RhinoMocks. It’s not the difficulty of the technology, but the quality of your hires. There is a learning curve, but a properly motivated and incentivized junior workforce will climb that curve quickly.

  • Chris Hance

    As has been mentioned elsewhere, legacy code. In my case, VB6 legacy code. Constructors? In my (to)day, we had to walk uphill both ways, and then set everything in properties. Class_Initialize is a decent enough place for the “default” behavior. Yes, I want to use anything else. We’re working on it. But we’re still adding features to a VB6 app in the meantime, and I don’t particularly like Forms Over Data. My early… well, earlier attempts became Big Ball of Mud.