Should I use MEF for my general IoC needs?

Disclaimer: This is not an encouragement to use MEF to replace your IoC container, these are guidelines to help those who are considering it’s use.

This has been a question we hear again and again both internally and externally.  MEF in V1 is targetting third-party extensibility scenarios, or open-systems which discover their components rather than having them explicitly configured. This is why our attributed model was crafted in the fashion that it was.  Now that doesn’t answer the question, “Can I use MEF today for my general IoC needs?”. Like all things in software, it depends ;-), in this case on what your IoC needs are.

Update: The list has been updated based on feedback from my team.

On first glance, MEF may seem to be very similar to your favorite IoC container. However as they say, the devil is in the details. Here are a few details to consider which should help you in your decision and set proper expectations about using MEF:

  • If you  need/want centralized configuration of plain old CLR objects (POCOs) then MEF is not the right choice.
    • We do have TypeCatalogs which allow you pick and choose which Types you have in the container, but those types still have to attributed, thus the configuration mechanism is configuring which attributed MEF parts show up. This is because our attributed model is really optimized around discovery of a set of unknown components vs configuring a pre-defined set.
    • As we don’t have a central configuration mechanism, we also have no explict way to pipe configuration settings like “Port” or “Uri” into a specific part.
  • If you need AOP/Interception like injecting logging, or automatic transcation management then MEF doesn’t include any native support for this.
  • Open generics support (register IRepository<> which can handle all IRepository<T> dependencies) is not baked in.
  • If you need custom lifetime support such as per-thread, per-session MEF includes only two lifetime models, shared and non-shared. To get more complex lifetimes requires manually setting up container hierarchies. It is doable, but requires work.
  • If you need paramterized construction, that is creating a part where specific imports are passed in at the time of construction, then this is also not supported.

In enterprise applications with a large number of different types of components, the above list will probably be more significant. However, if none of the above are core concerns then MEF might be fine for your needs.    MEF does an excellent job of decoupling implementations and assembling component hierarchies, but it is tailored today for implicit composition and discovery.

In the next version of MEF that will ship post .NET 4.0,  we are planning to focus more on explicit composition, and will be addressing many of the items on the above list. Until then, it is likely that there will be some great community implementations such as MEF Contrib which will address many of these concerns, but these are not part of MEF itself.

This entry was posted in MEF. Bookmark the permalink. Follow any comments here with the RSS feed for this post.
  • http://blogs.msdn.com/gblock Glenn Block

    Unity is not trying to solve the same problem. MEF’s usage of attributes is to address discoverability of 3rd party components that you don’t own which are added to your app.  It addresses an open ecosystem where components are reused across many applications.

    For the cases where you are building more closed systems, MEF v2 allows you to use conventions through a fluent interface thus removing any need for attributes.

    MEF also introduced in V1 the InheritedExport attribute for allowing you to annotate an interface which implementers automatically export.

    Dependency Injection/IoC mechanisms are  back box. Unity has UnityExtensions which perform all sorts of interception, etc as do plenty of IoCs.

    MEF has a very clear discovery model, you create catalogs and we look through those catalogs. Fair statement on the diagnostics, definite work is needed there. That story is being greatly improved in V2.

  • Chris Bordeman

    With Unity, my container is set up in one or a few places, so if I need to see what goes with what, it’s easy just to go there.  What I really dislike about MEF is how it separates the exports from the imports using attributes scattered throughout your code, making it increasingly difficult to understand as the code grows.  I also don’t have to deal with stepping on toes when manually creating objects in MEF, something that seems simple only at first.

    But the biggest reason not to use MEF is the difficulty of knowing what the heck it is doing under the covers.  It’s discovery process is a total black box and debugging failures in a larger app will drive you bonkers.

  • http://twitter.com/Marlinspike2010 Saucy Jack

    Glenn – thanks again for another great article. Very helpful.

  • TT

    Not sure why there is such a need to separate the two?
    Both have the goal to choose an implementation of your interfaces. The thing separating them is how you configure what implementation to pick. I use MEF as a IoC container on several websites and I have never had any problems with it.

  • http://codebetter.com/members/gblock/default.aspx Glenn Block

    Hi Daniel

    By XAML, do you mean declaring MEF parts in XAML? Or having elements within XAML get composed with MEF imports, as I mentioned here: http://codebetter.com/blogs/glenn.block/archive/2009/07/18/mef-and-xaml-integration-self-composition.aspx?

  • http://codebetter.com/members/gblock/default.aspx Glenn Block

    Ronald, glad it helped. I made a few updates to the list btw.

  • http://codebetter.com/members/gblock/default.aspx Glenn Block

    Hi Joe

    I was planning a follow up post on “Should I use MEF with another IoC container” which will cover this. Yes, this is a very valid concern if you are using both. There are several approaches on getting the two to work together such that you can mix and match components from each.

    IoC containers can be enabled to talk to MEF catalogs where there is only one container present. Basically this means the container also understands how to read MEF’s attributes model, though it uses parts of MEF to do it. Nick Blumhardt has a post on how this is possible here: http://blogs.msdn.com/nblumhardt/archive/2009/03/16/hosting-mef-extensions-in-an-ioc-container.aspx

    The other pattern is to have two containers that are wired to talk to each other. Piotr has put together a Unity integration layer that takes advantage of extension points in both Unity and MEF to create a bridge between the two. In this model, MEF’s container is hidden behind the scenes but handles providing MEF components. You can read about that here: http://pwlodek.blogspot.com/2009/05/unity-mef-integration-layer.html

    Look for more on this in the future.

    Regards
    Glenn

  • Ronald S Woan

    Thanks! Just what I was looking for, that clears things up for us.

  • http://smellegantcode.wordpress.com/ Daniel Earwicker

    “Explicit composition” – any likelihood of that linking up with XAML? It seems like if you want to explicitly state exactly how a hierarchy of components should be assembled, XAML already provides an answer to that, and is there to be used as a “configuration format”.

  • http://www.joefuture.com Joe

    The thing that’s bugging me about MEF so far (and maybe I’m just not using it properly) is that if my plugins have dependencies on any internal app interfaces, then I have to MEF’ify those too. For example, I’m trying to use MEF to locate plugins for a web application. If those plugins take an IFooRepository, then IFooRepository needs to have MEF attributes too so when the ImportingConstructor is called, MEF can auto-create the dependencies.

  • http://codebetter.com/members/gblock/default.aspx Glenn Block

    Steve

    Glad we didn’t have a head-popping scene :-)

    The distinguishing characterestic about MEF vs IoC is MEF’s suitability and optimization toward third-party extensibility and discovery.

    The point of this post is not to tell you to use MEF over Castle, Autofac, etc. Even if I wanted to say that (which I wouldn’t), Nick and Hamilton on my team would never let me get away with it ;-)

    Instead the point is to set expectations on MEF’s usage for more general needs other than extensibility. In some applications it may be fine, in other’s it won’t be. I’ve given the list of some of the key driving factors to consider. For example if poco is at the top of your list, then you’ve already made your decision.

    This is for those who are considering MEF’s usage for these cases. In general we have been very clear at not recommending to replace your favorite IoC with MEF. If you are happy with using your favorite (mine these days is Autofac) then rock-on.

  • Steve Py

    er… Ok, my head almost popped but I think the pressure stabilized….

    Wasn’t the whole point of discerning MEF from “just” an IoC was that it was targetted at very large enterprise applications where the availability or configuration of components could be managed, and that it wasn’t really designed to be another IoC.

    I didn’t see any features in MEF that seemed remotely useful for small projects that I couldn’t do with Windsor or Autofac.

    pressure building again… clock, clock, which one is a clock again? … *pop*

  • http://blog.noop.se Magnus Martensson

    You’re right – it depends. In a large proj we used an IoC + MEF but for small projs I use MEF alone as an IoC + for extensibility.