<?xml version="1.0" encoding="UTF-8" ?>
<?xml-stylesheet type="text/xsl" href="http://codebetter.com/utility/FeedStylesheets/rss.xsl" media="screen"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/"><channel><title>Glenn Block</title><link>http://codebetter.com/blogs/glenn.block/default.aspx</link><description>Another ALT.NET guy at Microsoft
</description><dc:language>en</dc:language><generator>CommunityServer 2008.5 SP1 (Build: 31106.3070)</generator><item><title>Meffifying Windows Azure</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/07/03/meffifying-windows-azure.aspx</link><pubDate>Fri, 03 Jul 2009 17:09:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:249654</guid><dc:creator>Glenn Block</dc:creator><slash:comments>2</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=249654</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/07/03/meffifying-windows-azure.aspx#comments</comments><description>&lt;p&gt;&lt;a href="http://twitter.com/noopman"&gt;Magnus&lt;/a&gt; has been off doing some interesting work around integrating &lt;a href="http://mef.codeplex.com"&gt;MEF&lt;/a&gt; with &lt;a href="http://www.microsoft.com/azure"&gt;Windows Azure&lt;/a&gt;. The first question you might be asking is Why?&lt;/p&gt;
&lt;p&gt;In his words, he set out to build a template for Windows Azure templates that:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;enables testability &lt;/li&gt;
&lt;li&gt;abstracts away storage&lt;/li&gt;
&lt;li&gt;is extensible and easy to evolve during development &lt;/li&gt;
&lt;/ul&gt;
&lt;li&gt;
&lt;p&gt;In the post he shows how to take the RoleManger and expose it through MEF, thereby making it pluggable. He then creates a mock Role Manager for use in his unit tests, thus removing the dependency on all the Azure infrastructure.&lt;/p&gt;
&lt;p&gt;I am guessing this is the first of many posts to come on MEF and Azure. &lt;/p&gt;
&lt;p&gt;For more, check out Magnus post &lt;a href="http://blog.noop.se/archive/2009/07/03/windows-azure-plus-managed-extensibility-framework-mef-true.aspx"&gt;here&lt;/a&gt;. &lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;/li&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=249654" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/azure/default.aspx">azure</category></item><item><title>Upcoming talks at NDC in Oslo and Poland</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/06/10/upcoming-talks-at-ndc-in-olso-and-poland.aspx</link><pubDate>Wed, 10 Jun 2009 22:45:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:248378</guid><dc:creator>Glenn Block</dc:creator><slash:comments>3</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=248378</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/06/10/upcoming-talks-at-ndc-in-olso-and-poland.aspx#comments</comments><description>&lt;p&gt;&lt;img height="118" width="990" src="http://www.ndc2009.no/images/toppENG.png" border="0" alt="" /&gt;&lt;/p&gt;
&lt;p&gt;Next week, I am heading to Europe for two weeks to give several talks. My first stop is &lt;a href="http://www.ndc2009.no/en/"&gt;NDC 2009&lt;/a&gt;, where I&amp;rsquo;ll be delivering the following talks:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.ndc2009.no/en/agenda.aspx#TB_inline?height=600&amp;amp;width=830&amp;amp;inlineId=32940&amp;amp;modal=true"&gt;Framework Design Guidelines&lt;/a&gt; &lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.ndc2009.no/en/agenda.aspx#TB_inline?height=600&amp;amp;width=830&amp;amp;inlineId=32941&amp;amp;modal=true"&gt;Building Maintainable Enterprise Applications with Silverlight and WPF&lt;/a&gt; &lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.ndc2009.no/en/agenda.aspx#TB_inline?height=600&amp;amp;width=830&amp;amp;inlineId=32938&amp;amp;modal=true"&gt;Building openly extensible applications with .NET Framework 4.0&lt;/a&gt; &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;NDC looks like an &lt;strong&gt;&lt;em&gt;amazing&lt;/em&gt;&lt;/strong&gt; event with a great lineup of speakers. I am hoping to be able to attend a few talks so I can soak up all their goodness. All my talks are in one day, so it&amp;rsquo;s going to be real wild ride!&lt;/p&gt;
&lt;p&gt;&lt;a href="http://www.ms-groups.pl/glennblock/"&gt;&lt;img src="http://ms-groups.pl/olmug/Obrazy/GlennBlockTourBanner.jpg" alt="" /&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;Next is on to Poland for a 5 city &lt;a href="http://ms-groups.pl/glennblock/default.aspx"&gt;user group tour&lt;/a&gt; in: &lt;a href="http://ms-groups.pl/glennblock/Lists/Glenn%20Block%20Tour/DispForm.aspx?ID=1"&gt;Olsztyn&lt;/a&gt;, &lt;a href="http://ms-groups.pl/glennblock/Lists/Glenn%20Block%20Tour/DispForm.aspx?ID=2"&gt;Toruń&lt;/a&gt;, &lt;a href="http://ms-groups.pl/glennblock/Lists/Glenn%20Block%20Tour/DispForm.aspx?ID=3"&gt;Warszawa&lt;/a&gt;, &lt;a href="http://ms-groups.pl/glennblock/Lists/Glenn%20Block%20Tour/DispForm.aspx?ID=4"&gt;Krak&amp;oacute;w&lt;/a&gt;, &lt;a href="http://ms-groups.pl/glennblock/Lists/Glenn%20Block%20Tour/DispForm.aspx?ID=5"&gt;Katowice&lt;/a&gt; where I&amp;rsquo;ll be speaking about building extensible apps, or other topics if folks attending would like (comment to this post if you have other topics)&lt;/p&gt;
&lt;p&gt;If you are attending NDC or will be in any of the cities mentioned, I look forward to chatting with you about how we can build better software!&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=248378" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/prism/default.aspx">prism</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/WPF/default.aspx">WPF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/conference/default.aspx">conference</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/silverlight/default.aspx">silverlight</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category></item><item><title>Customizing container behavior part 2 of N - Defaults</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/05/14/customizing-container-behavior-part-2-of-n-defaults.aspx</link><pubDate>Thu, 14 May 2009 08:19:09 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:224783</guid><dc:creator>Glenn Block</dc:creator><slash:comments>2</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=224783</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/05/14/customizing-container-behavior-part-2-of-n-defaults.aspx#comments</comments><description>&lt;p&gt;Before I get into the post, let me start off with a word of advice for new bloggers. Never say in a post, this is the first of many to come. RESIST! You are just setting yourself up for never doing that second post. I know as the last post in this series was five months ago. ;-)&lt;/p&gt;  &lt;p&gt;In the last &lt;a href="http://codebetter.com/blogs/glenn.block/archive/2008/12/25/using-exportprovider-to-customize-container-behavior-part-i.aspx"&gt;post,&lt;/a&gt; I introduced the concept of ExportProviders as a way to customize how the CompositionContainer discovers exports. One of the primary use cases for doing this is to provide default exports, which is particularly important for cases where you are importing a single value for which there are multiple present. The common case I like to use is the overused Logger example. Let’s say you have multiple loggers in the system, which are used for different functions. One logger logs locally, while others can log remotely perhaps invoking a web service, or using MSMQ. These loggers are all pluggable, as different organizations that use the app may have different needs. Each of these loggers export an ILogger contract.&lt;/p&gt;  &lt;p&gt;Now most of the time when logging occurs the local logger is sufficient. It’s only exceptions to the rule that require the special loggers. And this is where you run into a problem. How do you specify that you need to import that default logger, where there are multiple present? In the default configuration of MEF, the only way to really handle this if you are using imports is to either create a specialized contract for the default logger say IDefaultLogger which is imported, or to import the entire collection lazily using Export&amp;lt;ILogger&amp;gt; and then looking at the metadata for each to find the right one. You could also create a custom service called LoggerService, which imports all the loggers finds the default one, and then returns it when LoggerService.DefaultLogger is called. None of these are optimal though. &lt;/p&gt;  &lt;p&gt;For example, you could do this….&lt;/p&gt;  &lt;pre class="code"&gt;[&lt;span style="color:#2b91af;"&gt;Export&lt;/span&gt;]
&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;LoggerManager &lt;/span&gt;: &lt;span style="color:#2b91af;"&gt;ILoggerManager
&lt;/span&gt;{
    [&lt;span style="color:#2b91af;"&gt;ImportingConstructor&lt;/span&gt;]
    &lt;span style="color:blue;"&gt;public &lt;/span&gt;LoggerManager(&lt;span style="color:#2b91af;"&gt;Export&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ILogger&lt;/span&gt;,&lt;span style="color:#2b91af;"&gt;ILoggerMetadata&lt;/span&gt;&amp;gt;[] loggers)
    {
        &lt;span style="color:blue;"&gt;var &lt;/span&gt;logger = loggers.Single(e =&amp;gt; e.MetadataView.IsDefault==&lt;span style="color:blue;"&gt;true&lt;/span&gt;);
        DefaultLogger = logger.GetExportedObject();
    }
    
    &lt;span style="color:blue;"&gt;public &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ILogger &lt;/span&gt;DefaultLogger { &lt;span style="color:blue;"&gt;get&lt;/span&gt;; &lt;span style="color:blue;"&gt;private set&lt;/span&gt;;}

}&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;The problem is this means the LoggerManager has to have hard knowledge of which logger is the default. It also means the logger itself needs to somehow declare that it is the default, which is problematic because one logger might be the default in one app, but not in another. Separation of concerns anyone? Even worse you might have two loggers that say they are the default!&lt;/p&gt;

&lt;p&gt;Now there are other mental hoops you can jump through to find a workable solution, but it’s a lot of pain when what you really want you want to do is tell MEF’s container somehow “This is my default logger for this application”. Not only that but you want to do it in a way that does not require the app to hardcode it, does not require explicit configuration, nor does it require the parts to somehow ‘tell’ MEF they are the default. Also you don’t want the parts that are importing ILogger to have to know or care about a LoggerManager or anything like that. Instead they should simply have an import of ILogger.&lt;/p&gt;

&lt;pre class="code"&gt;[&lt;span style="color:#2b91af;"&gt;Export&lt;/span&gt;]
&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;Executor
&lt;/span&gt;{
    [&lt;span style="color:#2b91af;"&gt;ImportingConstructor&lt;/span&gt;]
    &lt;span style="color:blue;"&gt;public &lt;/span&gt;Executor(&lt;span style="color:#2b91af;"&gt;ILogger &lt;/span&gt;logger)
    {
    }
}&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;The $25000 question is how? The answer is using our friendly ExportProvider. In my last post I described the role of ExportProviders, which is to simply return exports. Those exports can come from several different sources, including from catalogs.&lt;/p&gt;

&lt;h1 align="left"&gt;Constructing the container with ExportProviders&lt;/h1&gt;

&lt;p&gt;If you look on the constructor of the container, you’ll see several overloads which accept an ExportProvider.&lt;/p&gt;

&lt;div style="border-bottom:silver 1px solid;text-align:left;border-left:silver 1px solid;padding-bottom:4px;line-height:12pt;background-color:#f4f4f4;margin:20px 0px 10px;padding-left:4px;width:97.5%;padding-right:4px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;max-height:200px;font-size:8pt;overflow:auto;border-top:silver 1px solid;cursor:text;border-right:silver 1px solid;padding-top:4px;" id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; CompositionContainer(&lt;span style="color:#0000ff;"&gt;params&lt;/span&gt; ExportProvider[] providers);&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; CompositionContainer(ComposablePartCatalog catalog, &lt;span style="color:#0000ff;"&gt;params&lt;/span&gt; ExportProvider[] providers);  &lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Any export providers passed in to the container are incorporated into the container’s query strategy. This means whenever anyone pulls on the container for an export, these providers will also get queried. Now catalogs have a special provider associated with them called a CatalogExportProvider. As a matter of fact the overload on the container that accepts a catalog is really just syntactic sugar. Behind the scenes we immediately create a CatalogExportProvider passing in the catalog. This means you can pass in an additional default catalog. If you’ve worked with MEF before, you might be shaking your head at this point and thinking “How is this any different than just having an AggregateCatalog and adding two catalogs?” And that IS the key question ;-). &lt;/p&gt;

&lt;p&gt;The answer is that adding catalogs to an AggregateCatalog does not allow handling defaults, however using this technique with ExportProviders &lt;strong&gt;does&lt;/strong&gt;. I’ll explain how next.&lt;/p&gt;

&lt;h1 align="left"&gt;AggregateCatalogs vs AggregateExportProvider&lt;/h1&gt;

&lt;p&gt;AggregateCatalog is a catalog that contains a list of catalogs. It is a composite pattern, so querying the parent, queries all the children. This is especially useful when you have parts that are “built in” to the application which are added via an AssemblyCatalog, and other parts which are discovered through a DirectoryCatalog. You can add both catalogs to an AggregateCatalog and everything works nicely. It doesn’t help you though in a default scenario however. The reason is because if one of your catalogs contains your default ILogger and your other catalogs contain the pluggable ILogger implementations, then the aggregate catalog will return them all when it is queried. This means the Executor above will blow up as the constructor is expecting a single ILogger. &lt;/p&gt;

&lt;p&gt;For the AggregateExportProvider however, we designed specifically to allow this defaults scenario to be addressed. The provider behaves differently depending on whether it is being queried for a single export or multiple. If the query is for multiple exports, then it works similar to the AggregateCatalog and collects all the exports it finds in any of it’s providers. If on the other hand the query is for a single export, then it uses a prioritization scheme. It will start at the top of the list of ExportProviders and query the first one for the single export (Logger). If it does not find one, then it keeps querying on to the next ExportProvider and so on. Once it finds an ExportProvider that returns one, then it will be returned, if it does not find one, then it will throw an exception.&lt;/p&gt;

&lt;p&gt;This means you can have default ExportProviders in the chain (including CatalogExportProviders) that contain your defaults so that the Executor class always succeeds in creation. You can even configure the behavior so that the defaults are overridable or not. For example if you want the default ILogger to always be the logger that is returned for all single import queries no matter what, then put the defaults at the top of the chain. If however you want the default logger to be overridable by another single ILogger, then put it at the end.&lt;/p&gt;

&lt;p&gt;Here’s an illustration of what I mean.&lt;/p&gt;

&lt;div style="border-bottom:silver 1px solid;text-align:left;border-left:silver 1px solid;padding-bottom:4px;line-height:12pt;background-color:#f4f4f4;margin:20px 0px 10px;padding-left:4px;width:97.5%;padding-right:4px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;max-height:200px;font-size:8pt;overflow:auto;border-top:silver 1px solid;cursor:text;border-right:silver 1px solid;padding-top:4px;" id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; OverridableDefaults()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var catalog = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; DirectoryCatalog(&lt;span style="color:#006080;"&gt;@&amp;quot;.\Extensions&amp;quot;&lt;/span&gt;);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var defaultCatalogEP = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; CatalogExportProvider(&lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; DirectoryCatalog(&lt;span style="color:#006080;"&gt;@&amp;quot;.\Defaults&amp;quot;&lt;/span&gt;));&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var container = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; CompositionContainer(catalog, defaultCatalogEP);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    defaultCatalogEP.SourceProvider = container;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;In the configuration above, we are placing our defaults at the end of the chain of providers. Remember as&amp;#160; I mentioned above that the ‘catalog’ reference will get wrapped in a CatalogExportProvider as well. It will get added first, followed by the additional providers. We then have to set the SourceProvider to the container, I talked about why this is necessary today in my previous &lt;a href="http://codebetter.com/blogs/glenn.block/archive/2008/12/25/using-exportprovider-to-customize-container-behavior-part-i.aspx"&gt;post&lt;/a&gt;, though it may be possible for us to infer the setting in the future. Anyway, now when a query happens for a single logger, the container will first check the parts in the Extensions folder, and if none are found it will revert to the defaults. &lt;/p&gt;

&lt;div style="border-bottom:silver 1px solid;text-align:left;border-left:silver 1px solid;padding-bottom:4px;line-height:12pt;background-color:#f4f4f4;margin:20px 0px 10px;padding-left:4px;width:97.5%;padding-right:4px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;max-height:200px;font-size:8pt;overflow:auto;border-top:silver 1px solid;cursor:text;border-right:silver 1px solid;padding-top:4px;" id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; NonOverridableDefaults()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var defaultCatalog = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; DirectoryCatalog(&lt;span style="color:#006080;"&gt;@&amp;quot;.\Defaults&amp;quot;&lt;/span&gt;);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var catalogEP = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; CatalogExportProvider(&lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; DirectoryCatalog(&lt;span style="color:#006080;"&gt;@&amp;quot;.\Extensions&amp;quot;&lt;/span&gt;));&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var container = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; CompositionContainer(defaultCatalog, catalogEP);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    catalogEP.SourceProvider = container;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;In this example, we are passing in the default catalog first, and then passing the catalog (as an EP). This configuration now means that the defaults are NEVER overridable, as whenever the container is queried for a single logger, it will ALWAYS return the default.&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;h1 align="left"&gt;Using Type or Assembly Catalogs for defaults&lt;/h1&gt;

&lt;p&gt;Now in the approach above we are using DirectoryCatalogs for specifying defaults. But remember, this is an option, you don’t have to, and in many cases might not want to. For example you might want to just specify your list of defaults in code, or even in a config file. TypeCatalog provides a great way to do this. (It accepts a params of Types, so you can add as many as you want).&lt;/p&gt;

&lt;div style="border-bottom:silver 1px solid;text-align:left;border-left:silver 1px solid;padding-bottom:4px;line-height:12pt;background-color:#f4f4f4;margin:20px 0px 10px;padding-left:4px;width:97.5%;padding-right:4px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;max-height:200px;font-size:8pt;overflow:auto;border-top:silver 1px solid;cursor:text;border-right:silver 1px solid;padding-top:4px;" id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; OverridableDefaultsWithTypeCatalog()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var catalogEP = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; CatalogExportProvider(&lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; DirectoryCatalog(&lt;span style="color:#006080;"&gt;@&amp;quot;.\Extensions&amp;quot;&lt;/span&gt;));&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var defaultCatalogEP = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; CatalogExportProvider(&lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; TypeCatalog(&lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt; (ILogger)));&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var container = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; CompositionContainer(catalogEP, defaultCatalogEP);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;h1&gt;OK, so now that you sold me, what are the caveats?&lt;/h1&gt;

&lt;p&gt;As with all things, there are some. Really, I can only think of one primary one, and that is that there’s still a bit of indeterminism as to what will get returned on a single import depending on how you set up the provider chain. If you go with the approach of putting defaults first, then it is completely deterministic. You know that whenever a single import request is issued to the container, the exports in that catalog will be returned, period. If however you arrange the defaults at the end of the chain, then it really depends on what is in the middle. Let’s say you have 3 EPs, and the one in the middle has a part with the single export that you are looking for, while you also have a default. In that case the one in the middle will get returned. Another caveat might be that this does add a bit of complexity, however I would argue that’s a reasonable trasdeoff to having to import collections all over the place.&lt;/p&gt;

&lt;h1&gt;The code&lt;/h1&gt;

&lt;p&gt;You can download sample code that illustrates using ExportProviders in various fashions &lt;a href="http://cid-f8b2fd72406fb218.skydrive.live.com/self.aspx/blog/MEF%20Export%20Provider%20Tests%20.zip"&gt;here&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If you look inside, you’ll find much more than just what we covered here.&amp;#160; Including how to do do role based composition, or even wire MEF to a configuration store where config info is an import. All of this will get covered at some point.&lt;/p&gt;

&lt;p&gt;Additionally:&lt;/p&gt;

&lt;ol&gt;
  &lt;li&gt;You’ll find several test classes which are using a context/specification style of testing to illustrate how to use ExportProviders.&amp;#160; If you are not familiar with BDD/CS it may seem very foreign, but I think you’ll find it easy to follow once the initial shock wears off. Having gone through this experience made me a big fan of CS style, and that is for another post. &lt;/li&gt;

  &lt;li&gt;You’ll find several test helper classes I’ve written specifically for MEF. These are really useful for folks writing their own ExportProviders and who wish to mock / fake certain parts of our programming model. Specifically I am talking about FakeExportDefinition and FakeExportProvider. Additionally you’ll see some common classes I’ve used for my own CS experiments. &lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;For stuff relating to what was covered in this post, go check out the Import_Logger_Specs.cs unit-tests.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Special thanks to &lt;/strong&gt;&lt;a href="http://blog.scottbellware.com/"&gt;Scott Bellware&lt;/a&gt;&lt;strong&gt; as well as &lt;a href="http://www.scottcreynolds.com/"&gt;Scott C. Reynolds&lt;/a&gt; and &lt;a href="http://twitter.com/davidmfoley"&gt;David Foley&lt;/a&gt; who invested a lot of time and effort in getting me off the ground in using this style of testing. &lt;/strong&gt;Without their help, I would have been stranded in a pool of confusion. This post is really not doing CS justice, and I really need a separate series. I can’t guarantee that I’ll get to it, but I’ll try.&lt;/p&gt;

&lt;h2&gt;What’s next&lt;/h2&gt;

&lt;p&gt;In the next post we’ll talk about establishing parent-child containers hierarchies. You may be asking how does this relate to ExportProviders? I’ll leave you with this thought to ponder, our container &lt;strong&gt;IS&lt;/strong&gt; an ExportProvider.&lt;/p&gt;

&lt;p&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&amp;#160;&lt;/a&gt;&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=224783" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/Export+Provider/default.aspx">Export Provider</category></item><item><title>“View Model” - the movie, cast your vote.</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/05/04/view-model-the-movie-cast-your-vote.aspx</link><pubDate>Tue, 05 May 2009 02:01:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:214528</guid><dc:creator>Glenn Block</dc:creator><slash:comments>21</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=214528</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/05/04/view-model-the-movie-cast-your-vote.aspx#comments</comments><description>&lt;p&gt;&lt;img height="500" width="375" src="http://farm4.static.flickr.com/3159/3064808115_6f73ec874d.jpg?v=0" alt="Star Wars Script by Richard Moross." /&gt;&lt;/p&gt;
&lt;p&gt;&lt;a href="http://www.flickr.com/photos/richardmoross/3064808115/" title="http://www.flickr.com/photos/richardmoross/3064808115/"&gt;http://www.flickr.com/photos/richardmoross/3064808115/&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;No we&amp;rsquo;re not actually making a movie about View Model. If we were I am sure we&amp;rsquo;d get a low turn-out. :-) However it did get your attention.&lt;/p&gt;
&lt;p&gt;What we are doing is some serious exploration into how we can help from a platform perspective folks that are implementing ViewModel (AKA &lt;a href="http://blogs.msdn.com/johngossman/archive/2005/10/08/478683.aspx"&gt;Model-View-ViewModel&lt;/a&gt;&amp;nbsp; AKA &lt;a href="http://martinfowler.com/eaaDev/PresentationModel.html"&gt;Presentation Model&lt;/a&gt;)&amp;nbsp; in their Silverlight and WPF applications.&lt;/p&gt;
&lt;p&gt;In the sense of a movie production, we&amp;rsquo;re in the script-writing phase. Here&amp;rsquo;s the general background.&lt;/p&gt;
&lt;h2&gt;Why is ViewModel important?&lt;/h2&gt;
&lt;p&gt;There have been many a post on the importance of ViewModel as a pattern and the benefits it brings. In that there is little disagreement that it benefits &lt;em&gt;both&lt;/em&gt; &lt;em&gt;&lt;span style="text-decoration:underline;"&gt;developers&lt;/span&gt;&lt;/em&gt; and &lt;em&gt;&lt;span style="text-decoration:underline;"&gt;designers&lt;/span&gt;.&lt;/em&gt; &lt;/p&gt;
&lt;p&gt;For developers it allows them to have clean separation of presentation logic from the UI rendering, thus making the app easier to maintain. It removes code from the code-behind that often makes the UI logic difficult to test.&lt;/p&gt;
&lt;p&gt;For designers it provides a way for a designer to completely change the look of the UI in a tool such as Expression Blend, without breaking the application functionality. Furthermore it gives the designer freedoms beyond simple look and feel, to actually decide which data elements are exposed, as well as defining the interactions between the UI elements through commands and attached behaviors.&lt;/p&gt;
&lt;h2&gt;The debate over roles&lt;/h2&gt;
&lt;p&gt;Although the benefits of ViewModel are known, there&amp;rsquo;s quite a lot of debate both inside and outside Microsoft on the roles the developer and designer play in developing applications that use the pattern.&amp;nbsp; This runs the spectrum from the designer having complete control of every aspect of the UI,&amp;nbsp; to the development team having more of a tight handle on the UI components, and the designer being responsible for skinning. In either case there are tradeoffs.&lt;/p&gt;
&lt;h2&gt;What is important to you?&lt;/h2&gt;
&lt;p&gt;What is your experience with ViewModel today?&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Where does the platform help,? Where does it hinder?&lt;/li&gt;
&lt;li&gt;What can we do in the platform to make life easier?&lt;/li&gt;
&lt;li&gt;What role do developers / designers play in your application of ViewModel.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Like any movie, we need to touch on the right nerves in order to make it a box-office hit. We need your feedback so we can complete the script. &lt;/p&gt;
&lt;p&gt;Thanks for your help&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=214528" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/WPF/default.aspx">WPF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/silverlight/default.aspx">silverlight</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/ViewModel/default.aspx">ViewModel</category></item><item><title>Poco, Mef, and custom type systems. Are you ready to take the red pill?</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/04/27/poco-mef-and-custom-type-systems-are-you-ready-to-take-the-red-pill.aspx</link><pubDate>Mon, 27 Apr 2009 10:36:01 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:205223</guid><dc:creator>Glenn Block</dc:creator><slash:comments>24</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=205223</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/04/27/poco-mef-and-custom-type-systems-are-you-ready-to-take-the-red-pill.aspx#comments</comments><description>&lt;p&gt;&lt;img style="border-right-width:0px;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" border="0" alt="The Matrix" src="http://datacore.sciflicks.com/the_matrix/images/the_matrix_large_08.jpg" width="360" height="480" /&gt;&lt;/p&gt;  &lt;p&gt;&lt;a title="http://datacore.sciflicks.com/the_matrix/images/the_matrix_large_08.jpg" href="http://datacore.sciflicks.com/the_matrix/images/the_matrix_large_08.jpg"&gt;http://datacore.sciflicks.com/the_matrix/images/the_matrix_large_08.jpg&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;I am about to show you in this post an approach to how poco (Plain Old Clr Objects [without attributes]) can be achieved with our current MEF codebase through creation of a new type system.&lt;/p&gt;  &lt;h2&gt;Are you ready t0 take the red pill? &lt;/h2&gt;  &lt;p&gt;Before you do, let’s set a bit of context. You may find it surprising to know that in general I am not a huge fan of attributes, at least from the aspect of consumer code. There are several reasons for this, but at the top of my list is that they increase the signal-to-noise ratio of the code, reduce scan-ability, and also couple the code to a specific implementation. &lt;/p&gt;  &lt;p&gt;That being said, MEF uses attributes (at least our attributed programming model does) for discovery of parts. Attributes provide a means for part authors to express that a part is part, thus making it discoverable. They provide a means for a host to interrogate the available parts, and make decisions on what to load, as well as adapt dynamically based on that present set. Attributes provide another benefit which is static analyzability meaning that tooling can scan assemblies and automatically determine what is present. It works really well for extensible systems like Visual Studio, where there are 1 to n implementations of extensions provided by an unlimited set of ISVs. We like to refer to this as external extensibility, or implicit composition (composing based on what is present, rather than registration).&lt;/p&gt;  &lt;p&gt;But what happens when the set is not open-ended, which is common when you are composing within your application (otherwise known as internal extensibility)? In these cases adding attributes may seem unnecessary as you know the set of parts that you have available. Isn’t there some way to just tell MEF, “Use these!”? Up until now our answer to this question has been that our attributed model does not support this, but in the future custom programming models can be created that sit side-by-side with our attributed model which will support non-attributed configurations. &lt;/p&gt;  &lt;p&gt;As a matter of fact, someone has already proven this to be true. &lt;a href="http://www.thecodejunkie.com"&gt;Andreas Håkansson&lt;/a&gt; has gone and implemented a &lt;a href="http://mefcontrib.codeplex.com/"&gt;generic provider based model&lt;/a&gt; that allows providing alternative means for defining parts. He’s got some great sample providers that work with his model that allow doing fluent interface configuration, or app.config style. These models introduce a bunch of rich capabilities that our current model does not such as explicit defaults, custom activation, etc. As far as I know, Andreas model is the only current available &lt;em&gt;programming model&lt;/em&gt; for non-attributed parts.&lt;/p&gt;  &lt;h2&gt;Achieving Poco through a custom type system.&lt;/h2&gt;  &lt;p&gt;Recently we discovered however there is an additional alternative approach to new programming models which we are exploring. That is, build a custom type system :-) This may sound like you’ve stepped into the Matrix, but it’s not as crazy as it seems.&amp;#160; In this case I’d argue though that ignorance is&lt;em&gt; not&lt;/em&gt; bliss. ;-)&lt;/p&gt;  &lt;h2&gt;A few caveats and warnings on this approach&lt;/h2&gt;  &lt;p&gt;Creating custom derived System.Type implementations is not fool-proof, and there are a bunch of known issues. &lt;/p&gt;  &lt;p&gt;For one thing support for custom types is not throughout the framework, there are a few places in the framework which actually depend on RuntimeType, the default concrete implementation of type in the framework. In our case this doesn’t effect us because MEF ‘s attributed model does not have this dependency. If however you tried to pass custom Types throughout the framework you will find that some things might break. &lt;/p&gt;  &lt;p&gt;Creating custom type systems allows you to break&amp;#160; a lot of rules that tend to take for granted, similar to stepping into the matrix :-). You can easily have side-effects in your custom type system that could have ripple effects throughout your app. In the cases here, we are additive, and are not changing the existing underlying functionality.&lt;/p&gt;  &lt;h2&gt;The Red Pill - Type is Abstract&lt;/h2&gt;  &lt;p&gt;Before we go further, let me let out a small, but apparently not well known secret. &lt;strong&gt;System.Type is abstract. &lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;Don’t believe me? Check this screenshot below from Reflector. Actually not only is Type abstract, but ConstructorInfo, PropertyInfo and all the other infos are also abstract.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_0243EAAB.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="image" border="0" alt="image" src="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_thumb_5F00_2C43E8D3.png" width="393" height="166" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Your probably sitting in shock at this point, and rethinking everything you thought you knew about the type system. Hmm. OK, so once we’ve digested that, we can think whether not it has any implications for MEF? Well MEF has a TypeCatalog which accepts a collection of types. Our attributed model reads through the collection of types and their attributes to build up part definitions of imports, and exports.&lt;/p&gt;  &lt;p&gt;If &lt;strong&gt;THAT &lt;/strong&gt;is the case, then conceptually can’t we create a new type (basically an adapter) which will take an underlying non-attributed type, read it’s members and then create attributes for those types based on a set of conventions? It is possible.&lt;/p&gt;  &lt;p&gt; Here’s passing unit tests to prove it.&lt;/p&gt;  &lt;div style="border-bottom:silver 1px solid;text-align:left;border-left:silver 1px solid;padding-bottom:4px;line-height:12pt;background-color:#f4f4f4;margin:20px 0px 10px;padding-left:4px;width:103.26%;padding-right:4px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;height:272px;max-height:200px;font-size:8pt;overflow:auto;border-top:silver 1px solid;cursor:text;border-right:silver 1px solid;padding-top:4px;" id="codeSnippetWrapper"&gt;   &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;     &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Test]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; When_poco_type_is_reflected_then_export_attribute_is_returned()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var mefType = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; ComposablePartType&amp;lt;MyPoco, IPoco&amp;gt;();&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var exportAttribute = mefType.GetAttributes&amp;lt;ExportAttribute&amp;gt;().FirstOrDefault();&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    Assert.IsNotNull(exportAttribute != &lt;span style="color:#0000ff;"&gt;null&lt;/span&gt;);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Test]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; When_export_attribute_is_returned_then_contract_name_matches()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var mefType = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; ComposablePartType&amp;lt;MyPoco, IPoco&amp;gt;();&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var exportAttribute = mefType.GetAttributes&amp;lt;ExportAttribute&amp;gt;().FirstOrDefault();&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    Assert.AreEqual(&lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt;(IPoco), exportAttribute.ContractType);   &lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Test]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; When_poco_type_is_reflected_then_part_creation_policy_attribute_is_returned()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var mefType = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; ComposablePartType&amp;lt;MyPoco, IPoco&amp;gt;(CreationPolicy.Shared);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var partCreationPolicyAttribute = mefType.GetAttributes&amp;lt;PartCreationPolicyAttribute&amp;gt;().FirstOrDefault();&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    Assert.IsNotNull(partCreationPolicyAttribute != &lt;span style="color:#0000ff;"&gt;null&lt;/span&gt;);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Test]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; When_part_creation_policy_attribute_is_returned_then_is_shared()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var mefType = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; ComposablePartType&amp;lt;MyPoco, IPoco&amp;gt;(CreationPolicy.Shared);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var partCreationPolicyAttribute = mefType.GetAttributes&amp;lt;PartCreationPolicyAttribute&amp;gt;().FirstOrDefault();&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    Assert.AreEqual(CreationPolicy.Shared, partCreationPolicyAttribute.CreationPolicy);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Test]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; When_poco_type_is_reflected_then_importing_constructor_is_returned()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var mefType = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; ComposablePartType&amp;lt;MyPoco, IPoco&amp;gt;();&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var constructors =&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;        mefType.GetConstructors().Where(c =&amp;gt; c.GetAttributes&amp;lt;ImportingConstructorAttribute&amp;gt;().Count() == 1);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    Assert.IsTrue(constructors.Count() ==1 );&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Test]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; When_poco_type_is_added_to_type_catalog_then_part_is_created()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var catalog = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; TypeCatalog(&lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; ComposablePartType&amp;lt;MyPoco, IPoco&amp;gt;(CreationPolicy.Shared));&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    Assert.AreEqual(1, catalog.Parts.Count());&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Test]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;void&lt;/span&gt; When_poco_type_is_added_to_type_catalog_then_ipoco_export_can_be_retrieved()&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var catalog = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; TypeCatalog(&lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; ComposablePartType&amp;lt;MyPoco, IPoco&amp;gt;(CreationPolicy.Shared));&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var part = catalog.Parts.First();&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    var export = part.ExportDefinitions.Where(ed =&amp;gt; ed.ContractName == AttributedModelServices.GetContractName(&lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt;(IPoco)));&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    Assert.IsNotNull(export);&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;If you are thinking at this point, “Show me the code”, go get it from my skydrive &lt;/strong&gt;&lt;a href="http://cid-f8b2fd72406fb218.skydrive.live.com/self.aspx/blog/TypeExtensions.zip"&gt;&lt;strong&gt;here.&lt;/strong&gt;&lt;/a&gt;&lt;strong&gt; In the download you’ll find a new TypeExtensions library along with unit tests. Disclaimer: This is a prototype at this point and is not production code. &lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;Creating a new type&lt;/h2&gt;

&lt;p&gt;Take a look at the first test. I am creating a new type called ComposablePartType which is generic, and I am passing in MyPoco as the implementation type, and IPoco as the contract type. &lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartType&lt;/span&gt;&amp;lt;TImplementation, TContract&amp;gt; : &lt;span style="color:#2b91af;"&gt;TypeDelegator
&lt;/span&gt;{}&lt;/pre&gt;

&lt;p&gt;Notice it inherits from TypeDelegator, well what the heck is that?&lt;/p&gt;

&lt;p&gt;&lt;a href="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_64162CF6.png"&gt;&lt;img style="border-right-width:0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="image" border="0" alt="image" src="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_thumb_5F00_782F497F.png" width="346" height="177" /&gt;&lt;/a&gt; &lt;/p&gt;

&lt;p&gt;TypeDelegator is a lesser known member of the framework. It inherits from System.Type, accepts a type which it wraps, and then delegates all calls on itself to. TypeDelegator is really handy, because without it I would have to manually implement and delegate to all members myself&lt;/p&gt;

&lt;h2&gt;Export and PartCreationPolicy attributes&lt;/h2&gt;

&lt;p&gt;Below is the code for MyPoco and IPoco, “Look Ma, no attributes”&lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;MyPoco &lt;/span&gt;: &lt;span style="color:#2b91af;"&gt;IPoco
&lt;/span&gt;{
    &lt;span style="color:blue;"&gt;public &lt;/span&gt;MyPoco(&lt;span style="color:blue;"&gt;bool &lt;/span&gt;isPoco, &lt;span style="color:blue;"&gt;int &lt;/span&gt;theAnswer, &lt;span style="color:#2b91af;"&gt;ILogger &lt;/span&gt;logger)
    {
        &lt;span style="color:blue;"&gt;this&lt;/span&gt;.IsPoco = isPoco;
        &lt;span style="color:blue;"&gt;this&lt;/span&gt;.TheAnswer = theAnswer;
        &lt;span style="color:blue;"&gt;this&lt;/span&gt;.Logger = logger;
    }

    &lt;span style="color:blue;"&gt;public bool &lt;/span&gt;IsPoco { &lt;span style="color:blue;"&gt;get&lt;/span&gt;; &lt;span style="color:blue;"&gt;internal set&lt;/span&gt;; }
    &lt;span style="color:blue;"&gt;public int &lt;/span&gt;TheAnswer { &lt;span style="color:blue;"&gt;get&lt;/span&gt;; &lt;span style="color:blue;"&gt;internal set&lt;/span&gt;; }
    &lt;span style="color:blue;"&gt;public &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ILogger &lt;/span&gt;Logger { &lt;span style="color:blue;"&gt;get&lt;/span&gt;; &lt;span style="color:blue;"&gt;internal set&lt;/span&gt;; }
}

&lt;span style="color:blue;"&gt;public interface &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;IPoco
&lt;/span&gt;{
    &lt;span style="color:blue;"&gt;bool &lt;/span&gt;IsPoco { &lt;span style="color:blue;"&gt;get&lt;/span&gt;; }
    &lt;span style="color:blue;"&gt;int &lt;/span&gt;TheAnswer { &lt;span style="color:blue;"&gt;get&lt;/span&gt;; }
    &lt;span style="color:#2b91af;"&gt;ILogger &lt;/span&gt;Logger { &lt;span style="color:blue;"&gt;get&lt;/span&gt;; }
}&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;The unit test is then querying the attributes on this “type” to then see if it can find an ExportAttribute, which assuming the test succeeds it will. ComposablePartType is for all intents and purposes just like System.Type. With one major difference, it creates attributes on the fly based on underlying conventions on the Type it wraps. In this case it has created an Export attribute, exporting the IPoco contract, which is verified in the second test. &lt;/p&gt;

&lt;p&gt;Let’s look at the next two tests which relates to part creation policy. The first test is checking whether or not the type has a PartCreationPolicyAttribute it, and the second test is checking that the attribute is set to shared. OK, that’s just an extension pattern wise of the previous tests.&lt;/p&gt;

&lt;p&gt;Here’s how it’s done under the hood.&lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public override object&lt;/span&gt;[] GetCustomAttributes(&lt;span style="color:blue;"&gt;bool &lt;/span&gt;inherit)
{
    &lt;span style="color:blue;"&gt;if &lt;/span&gt;(_attributes == &lt;span style="color:blue;"&gt;null&lt;/span&gt;)
    {
        _attributes =  &lt;span style="color:blue;"&gt;base&lt;/span&gt;.GetCustomAttributes(inherit);
        &lt;span style="color:#2b91af;"&gt;Array&lt;/span&gt;.Resize(&lt;span style="color:blue;"&gt;ref &lt;/span&gt;_attributes, _attributes.Length + 2);
        _attributes[_attributes.Length - 2] = 
            &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ExportAttribute&lt;/span&gt;(_contractName, &lt;span style="color:blue;"&gt;typeof&lt;/span&gt;(TContract));
        _attributes[_attributes.Length - 1] = 
            &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;PartCreationPolicyAttribute&lt;/span&gt;(_partCreationPolicy);
    }
    &lt;span style="color:blue;"&gt;return &lt;/span&gt;_attributes;
}&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;Above, I am taking the collection of attributes returned from the underlying type, increasing the size of the collection and adding the Export and PartCreationPolicy attributes. Once i do this, the type has become attributed ;-)&lt;/p&gt;

&lt;h2&gt;&lt;/h2&gt;

&lt;h2&gt;Greedy Constructors and parameter name conventions&lt;/h2&gt;

&lt;p&gt;Allright, let’s peel back the onion a little bit further and look at the next test, this one relates to constructors. In the test, I am querying for a constructor to see if I can find one that has an [ImportingConstructor] attribute. Notice that MyPoco has a single constructor and it is not parameterless. The new type system supports finding the greediest constructor. It finds that constructor and then adds an [ImportingConstructor] on it in order to make MEF’s attributed model happy.&lt;/p&gt;

&lt;p&gt;I have to say, I just adore Linq. Look at this code which handles finding the greediest constructor.&lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public override &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ConstructorInfo&lt;/span&gt;[] GetConstructors(&lt;span style="color:#2b91af;"&gt;BindingFlags &lt;/span&gt;bindingAttr)
{
    &lt;span style="color:blue;"&gt;if &lt;/span&gt;(_constructors == &lt;span style="color:blue;"&gt;null&lt;/span&gt;)
    {
        _constructors =
        &lt;span style="color:blue;"&gt;base&lt;/span&gt;.GetConstructors(bindingAttr).OrderByDescending(
        c =&amp;gt; c.GetParameters().Count()).ToArray();
        _constructors[0] = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartConstructorInfo&lt;/span&gt;(
            _constructors[0],_alwaysUseConstructorParamNameAsContract);
    }
    &lt;span style="color:blue;"&gt;return &lt;/span&gt;_constructors;
}&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;Once I have the greediest constructor, I replace it with a new custom ComposablePartConstructorInfo which wraps the existing constructor.&lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartConstructorInfo &lt;/span&gt;: &lt;span style="color:#2b91af;"&gt;ConstructorInfo &lt;font color="#000000"&gt;{}&lt;/font&gt;&lt;/span&gt;&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;_alwaysUseConstructorParamNameAsContract specifies whether or not the imports on the params for that constructor should be the parameter name or the contract. In MEF today, we default to use the type. Having this level of control at the type level allows me to augment that with additional conventions.&lt;/p&gt;

&lt;p&gt;ComposablePartConstructorInfo looks at the parameters of the constructor. If they are primitives, or types String/DateTime, or if the override params is set,&amp;#160; it will create a ComposablePartParameterInfo which in turn adds an [Import] attribute specifying the &lt;em&gt;parameter name&lt;/em&gt; as the contract. This is useful for cases where you have a sender parameter of type string where the contract is “Sender”.&lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public override &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ParameterInfo&lt;/span&gt;[] GetParameters()
{
    &lt;span style="color:blue;"&gt;if &lt;/span&gt;(_parameterInfos == &lt;span style="color:blue;"&gt;null&lt;/span&gt;)
    {
        &lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ParameterInfo&lt;/span&gt;&amp;gt; parameters = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ParameterInfo&lt;/span&gt;&amp;gt;();
        &lt;span style="color:blue;"&gt;foreach &lt;/span&gt;(&lt;span style="color:#2b91af;"&gt;ParameterInfo &lt;/span&gt;param &lt;span style="color:blue;"&gt;in &lt;/span&gt;_constructorInfo.GetParameters())
        {
            &lt;span style="color:blue;"&gt;if &lt;/span&gt;(_alwaysUseParamNameAsContract || 
                param.ParameterType.IsPrimitive ||
                param.ParameterType == &lt;span style="color:blue;"&gt;typeof &lt;/span&gt;(&lt;span style="color:blue;"&gt;string&lt;/span&gt;) || 
                param.ParameterType == &lt;span style="color:blue;"&gt;typeof &lt;/span&gt;(&lt;span style="color:#2b91af;"&gt;DateTime&lt;/span&gt;))
                parameters.Add(&lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartParameterInfo&lt;/span&gt;(param));
            &lt;span style="color:blue;"&gt;else
                &lt;/span&gt;parameters.Add(param);
        }
        _parameterInfos = parameters.ToArray();
    }
    &lt;span style="color:blue;"&gt;return &lt;/span&gt;_parameterInfos;
}&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;By now, I think you’re starting to get the picture of how this all fits together. I’ll leave you to explore ComposablePartParameterInfo yourself ;-)&lt;/p&gt;

&lt;p&gt;I’ll leave you with one other thought, you can take ComposablePartConstructorInfo&amp;#160; even further to do AOP-style interception and dynamic proxying. Can you see how? &lt;/p&gt;

&lt;h2&gt;Registering poco types with Part Registries&lt;/h2&gt;

&lt;p&gt;Now that we have our custom type system, we can start to feed these types to MEF. One approach to doing this is to simply use our TypeCatalog.&amp;#160; Combined with Linq you can do some pretty nifty things once you have an assembly in hand like registering all types that end in Service, or all types that live in the MyApp.Services namespace. That’s all well and good, but the one thing you lose in doing so is the reflect-ability and static-analysis that our attributed model currently provides, as these parts are registered on the fly at runtime. It would be nice if there was a way to combine the two approaches. There is, ComposablePartRegistry and PartRegistryCatalog.&lt;/p&gt;

&lt;p&gt;A registry is a class that contains a catalog. Catalogs in MEF contain parts. ComposablePartRegistry is below.&lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public abstract class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartRegistry
&lt;/span&gt;{
    &lt;span style="color:blue;"&gt;protected abstract &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartCatalog &lt;/span&gt;GetCatalog();
    &lt;span style="color:blue;"&gt;public &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartCatalog &lt;/span&gt;Catalog
    {
        &lt;span style="color:blue;"&gt;get &lt;/span&gt;{ &lt;span style="color:blue;"&gt;return &lt;/span&gt;GetCatalog(); }
    }
}&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;To register a set of pocos, you simply derive from ComposablePartRegistry and implement the GetCatalog method to return a TypeCatalog. &lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;TestRegistry &lt;/span&gt;: &lt;span style="color:#2b91af;"&gt;ComposablePartRegistry
&lt;/span&gt;{
    &lt;span style="color:blue;"&gt;protected override &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartCatalog &lt;/span&gt;GetCatalog()
    {
        &lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;Type&lt;/span&gt;&amp;gt; types = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;Type&lt;/span&gt;&amp;gt;();
        types.Add(&lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartType&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;MyPoco&lt;/span&gt;, &lt;span style="color:#2b91af;"&gt;IPoco&lt;/span&gt;&amp;gt;
            (&lt;span style="color:#2b91af;"&gt;CreationPolicy&lt;/span&gt;.Shared));
        types.Add(&lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartType&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;Logger&lt;/span&gt;, &lt;span style="color:#2b91af;"&gt;ILogger&lt;/span&gt;&amp;gt;
            (&lt;span style="color:#2b91af;"&gt;CreationPolicy&lt;/span&gt;.Shared));
        &lt;span style="color:blue;"&gt;return new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;TypeCatalog&lt;/span&gt;(types);
    }
}&lt;/pre&gt;

&lt;p&gt;Above TestRegistry is registering two parts, MyPoco and Logger both as shared. The last piece of the puzzle is to make registries discoverable. Once they are discoverable we can get back our full analyzability. This is where PartRegistryCatalog comes in.&amp;#160; This new catalog inherits from our AssemblyCatalog and adds in additional discovery of part registries. The important part is in the method below.&lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;private void &lt;/span&gt;LoadRegistries()
{
    &lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ComposablePartDefinition&lt;/span&gt;&amp;gt; parts = 
        &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ComposablePartDefinition&lt;/span&gt;&amp;gt;();
    &lt;span style="color:blue;"&gt;var &lt;/span&gt;registries = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ComposablePartRegistry&lt;/span&gt;&amp;gt;();

    &lt;span style="color:blue;"&gt;var &lt;/span&gt;registryTypes = Assembly.GetTypes().
        Where(t =&amp;gt; t.IsSubclassOf(&lt;span style="color:blue;"&gt;typeof&lt;/span&gt;(&lt;span style="color:#2b91af;"&gt;ComposablePartRegistry&lt;/span&gt;)));

    &lt;span style="color:blue;"&gt;foreach &lt;/span&gt;(&lt;span style="color:blue;"&gt;var &lt;/span&gt;registryType &lt;span style="color:blue;"&gt;in &lt;/span&gt;registryTypes)
    {
        &lt;span style="color:blue;"&gt;var &lt;/span&gt;registry = (&lt;span style="color:#2b91af;"&gt;ComposablePartRegistry&lt;/span&gt;)&lt;span style="color:#2b91af;"&gt;Activator&lt;/span&gt;.
            CreateInstance(registryType);
        registries.Add(registry);
        parts.AddRange(registry.Catalog.Parts);
    }
    _parts = parts.AsQueryable();
    &lt;span style="color:blue;"&gt;this&lt;/span&gt;.Registries = registries;
}&lt;/pre&gt;

&lt;p&gt;The method grabs all registries that it finds and then instantiates them. Once the registry is created, it’s parts are queried and stored within the registry catalog. When the catalog’s Part property is invoked, it will return a combination of parts discovered through registries and those discovered through the normal means.&lt;/p&gt;

&lt;h2&gt;Bringing it all together&lt;/h2&gt;

&lt;p&gt;Now with all the pieces in place, we can start composing pocos in the container. First we setup our container. Our current assembly has TestRegistry which will be discovered by the registry catalog. Next we can add our values to the container so that they can be injected.&lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;CompositionContainer &lt;/span&gt;SetupContainerUsingConstructorParamTypes...()
{
    &lt;span style="color:blue;"&gt;var &lt;/span&gt;catalog = &lt;span style="color:blue;"&gt;new 
        &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;PartRegistryCatalog&lt;/span&gt;(&lt;span style="color:blue;"&gt;typeof&lt;/span&gt;(&lt;span style="color:#2b91af;"&gt;ComposablePartTypeFixture&lt;/span&gt;).Assembly);
    &lt;span style="color:blue;"&gt;var &lt;/span&gt;container = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;CompositionContainer&lt;/span&gt;(catalog);

    &lt;span style="color:green;"&gt;//forcefully add some values to the container. 
    &lt;/span&gt;_isPoco = &lt;span style="color:blue;"&gt;true&lt;/span&gt;;
    _theAnswer = 42;
    container.ComposeExportedObject(&lt;span style="color:#a31515;"&gt;&amp;quot;IsPoco&amp;quot;&lt;/span&gt;,_isPoco);
    container.ComposeExportedObject(&lt;span style="color:#a31515;"&gt;&amp;quot;TheAnswer&amp;quot;&lt;/span&gt;,_theAnswer);
    &lt;span style="color:blue;"&gt;return &lt;/span&gt;container;
}&lt;/pre&gt;

&lt;p&gt;Finally we can run our tests which should be self-explanatory.&lt;/p&gt;

&lt;pre class="code"&gt;[&lt;span style="color:#2b91af;"&gt;Test&lt;/span&gt;]
&lt;span style="color:blue;"&gt;public void &lt;/span&gt;When_..._queried_from_the_container_then_Wow_is_injected...() 
{
    &lt;span style="color:blue;"&gt;var &lt;/span&gt;container = 
        SetupContainerUsingConstructorParamTypesAsTheContractName();
    &lt;span style="color:blue;"&gt;var &lt;/span&gt;poco = container.GetExportedObject&amp;lt;&lt;span style="color:#2b91af;"&gt;IPoco&lt;/span&gt;&amp;gt;();
    &lt;span style="color:#2b91af;"&gt;Assert&lt;/span&gt;.AreEqual(_isPoco, poco.IsPoco);
}

[&lt;span style="color:#2b91af;"&gt;Test&lt;/span&gt;]
&lt;span style="color:blue;"&gt;public void &lt;/span&gt;When_..._queried_from_the_container_then_42_is_injected...()
{
    &lt;span style="color:blue;"&gt;var &lt;/span&gt;container = 
        SetupContainerUsingConstructorParamTypesAsTheContractName();
    &lt;span style="color:blue;"&gt;var &lt;/span&gt;poco = container.GetExportedObject&amp;lt;&lt;span style="color:#2b91af;"&gt;IPoco&lt;/span&gt;&amp;gt;();
    &lt;span style="color:#2b91af;"&gt;Assert&lt;/span&gt;.AreEqual(_theAnswer, poco.TheAnswer);
}&lt;/pre&gt;

&lt;h2&gt;Summing up and what’s next?&lt;/h2&gt;

&lt;p&gt;At this point this is just a prototype illustrating a modified type system which dynamically creates attributes on non-attributed part through a set of conventions. This approach is very powerful in that it allows managing a closed set of parts, such as the internals of an application, and works harmoniously within our existing attributed programming model.&lt;/p&gt;

&lt;p&gt;A few differences / limitations of the current prototype.&lt;/p&gt;

&lt;p&gt;1. The Type is the export and there is only one contract exported. The model does not currently support exporting methods and properties. It could, it just doesn’t. This was deliberate in order to keep the model simplified. &lt;/p&gt;

&lt;p&gt;2. No metadata support. Currently ComposablePartType does not provide any means for providing metadata for the part. This was also to keep things simple, though it is possible to support it.&lt;/p&gt;

&lt;p&gt;3. Recomposition is not supported. Currently all imports that are created are not recomposable.&lt;/p&gt;

&lt;p&gt;We’d like your feedback on the approach in order to let us know whether we should take it further, or even consider putting it into Mef V1.&lt;/p&gt;

&lt;p&gt;Let us know!&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Download the code &lt;/strong&gt;&lt;a href="http://cid-f8b2fd72406fb218.skydrive.live.com/self.aspx/blog/TypeExtensions.zip"&gt;&lt;strong&gt;here&lt;/strong&gt;&lt;/a&gt;&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=205223" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/poco/default.aspx">poco</category></item><item><title>MEF Preview 5, changes and enhancements</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/04/11/mef-preview-5-changes-and-enhancements.aspx</link><pubDate>Sun, 12 Apr 2009 06:16:53 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:192910</guid><dc:creator>Glenn Block</dc:creator><slash:comments>6</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=192910</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/04/11/mef-preview-5-changes-and-enhancements.aspx#comments</comments><description>&lt;p&gt;We recently shipped &lt;a href="http://mef.codeplex.com/Release/ProjectReleases.aspx?ReleaseId=25797"&gt;MEF preview 5&lt;/a&gt; on &lt;a href="http://mef.codeplex.com/"&gt;Codeplex&lt;/a&gt;, an exciting release.&lt;/p&gt; &lt;p&gt;In the latest release, you’ll find we’ve made quite a few changes, and some really powerful enhancements to our previous codebase. In this post, I’ll talk about those changes in detail, and why we made them. I’ll also discuss some changes we will be making in the future, in order to give you a heads up, so that you can adjust your code bases now. &lt;/p&gt; &lt;p&gt;Throughout the development of preview 5, we’ve done our best to minimize the impact to you. There are some breaking changes, primarily in terms of namespace refactoring, most of which do &lt;b&gt;not&lt;/b&gt; effect part authors, but will effect MEF hosters, and authors of custom programming models or export providers. &lt;/p&gt; &lt;p&gt;Here’s a summary of these changes for those who want to just cut to the chase. For those who want the full skinny, that comes after the summary.&lt;/p&gt; &lt;table border="1" cellspacing="0" cellpadding="0" width="500"&gt; &lt;tbody&gt; &lt;tr&gt; &lt;td valign="top" width="103"&gt; &lt;p&gt;&lt;b&gt;Change&lt;/b&gt;&lt;/p&gt;&lt;/td&gt; &lt;td valign="top" width="395"&gt; &lt;p&gt;&lt;b&gt;Summary description&lt;/b&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt; &lt;tr&gt; &lt;td valign="top" width="102"&gt;New sample application, MEF Studio&lt;/td&gt; &lt;td valign="top" width="396"&gt; &lt;ul&gt; &lt;li&gt;We have included a new sample application which is a mock pluggable IDE using MEF.&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt;&lt;/tr&gt; &lt;tr&gt; &lt;td valign="top" width="102"&gt; &lt;p&gt;Namespace changes&lt;/p&gt;&lt;/td&gt; &lt;td valign="top" width="396"&gt; &lt;ul&gt; &lt;li&gt;System.ComponentModel.Composition – For part authors  &lt;li&gt;System.ComponentModel.Composition.Hosting – For hosters  &lt;li&gt;System.ComponentModel.Composition.Primitives – Infrastructure for defining programming models  &lt;li&gt;System.ComponentModel.Composition.ReflectionModel – Services for implementers of catalog caches, and for reflection based programming models. &lt;/li&gt;&lt;/ul&gt;&lt;/td&gt;&lt;/tr&gt; &lt;tr&gt; &lt;td valign="top" width="102"&gt; &lt;p&gt;Part Discovery Model and Lifetime Changes&lt;/p&gt;&lt;/td&gt; &lt;td valign="top" width="396"&gt; &lt;ul&gt; &lt;li&gt;CompositionOptions has been removed  &lt;li&gt;New PartCreationPolicyAttribute&amp;nbsp; for specifying part lifetime (Replaces CompositionOptionsAttribute.CreationPolicy )  &lt;li&gt;Exports are not discovered on base classes by default  &lt;li&gt;New PartNotDiscoverable attribute for specifying that a part should not be discovered by the catalog. (replaces [CompositionOptions(DiscoveryMode = DiscoveryMode.Never)])  &lt;li&gt;New PartExportsInherited attribute allows a base class / interface to declare itself as discoverable by inheritors. (replaces [CompositionOptions(DiscoveryMode = DiscoveryMode.Always)] ) &lt;/li&gt;&lt;/ul&gt;&lt;/td&gt;&lt;/tr&gt; &lt;tr&gt; &lt;td valign="top" width="102"&gt; &lt;p&gt;Collection Imports&lt;/p&gt;&lt;/td&gt; &lt;td valign="top" width="396"&gt; &lt;ul&gt; &lt;li&gt;New ImportManyAttribute replaces ImportAttribute on collections in the future.  &lt;li&gt;Array imports are now supported &lt;/li&gt;&lt;/ul&gt;&lt;/td&gt;&lt;/tr&gt; &lt;tr&gt; &lt;td valign="top" width="102"&gt; &lt;p&gt;Typed Import/Exports&lt;/p&gt;&lt;/td&gt; &lt;td valign="top" width="396"&gt; &lt;ul&gt; &lt;li&gt;Imports and Exports now match on type as well as contract.  &lt;li&gt;Exporters of string contracts such&amp;nbsp; as [Export(“Foo”)] must now specify the type they expect to be imported as well. e.g. [Export(“Foo”, typeof(string))] &lt;/li&gt;&lt;/ul&gt;&lt;/td&gt;&lt;/tr&gt; &lt;tr&gt; &lt;td valign="top" width="102"&gt; &lt;p&gt;Custom delegates&lt;/p&gt;&lt;/td&gt; &lt;td valign="top" width="396"&gt; &lt;ul&gt; &lt;li&gt;Method exports can now use custom delegates in addition to Action and Func &lt;/li&gt;&lt;/ul&gt;&lt;/td&gt;&lt;/tr&gt; &lt;tr&gt; &lt;td valign="top" width="102"&gt; &lt;p&gt;Directory Catalog changes&lt;/p&gt;&lt;/td&gt; &lt;td valign="top" width="396"&gt; &lt;ul&gt; &lt;li&gt;DirectoryCatalog no longer has watching functionality. We’ve added a Refresh() method for explicit refresh. &lt;/li&gt;&lt;/ul&gt;&lt;/td&gt;&lt;/tr&gt; &lt;tr&gt; &lt;td valign="top" width="102"&gt; &lt;p&gt;Removal of caching / new infrastructure&lt;/p&gt;&lt;/td&gt; &lt;td valign="top" width="396"&gt; &lt;ul&gt; &lt;li&gt;Old caching infrastructure has been ripped. We’ve added a new more general purpose API that is more flexible, and supports builders of custom programming models. We are not shipping a default caching implementation of that API in the box, but one is available in our samples. &lt;/li&gt;&lt;/ul&gt;&lt;/td&gt;&lt;/tr&gt; &lt;tr&gt; &lt;td valign="top" width="102"&gt;&amp;nbsp;&lt;/td&gt; &lt;td valign="top" width="396"&gt;&amp;nbsp;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt; &lt;h2&gt;&lt;span style="background:white;color:black;"&gt;MEF Studio&lt;/h2&gt; &lt;p&gt;MEF Studio is a designer hosting sample. It has an IDE that hosts various designers like Windows Forms, UserControl, etc. One can add controls on to these designers from the toolbox, set properties using the property grid, view generated code, etc. It provides design time experience for the designers and has extension points for extending the adding custom parts.&lt;/p&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/span&gt; &lt;h2&gt;&lt;a href="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_0180E8EB.png"&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;border-top:0px;border-right:0px;" title="image" border="0" alt="image" src="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_thumb_5F00_7FD01D16.png" width="507" height="378" /&gt;&lt;/a&gt; &lt;/h2&gt; &lt;h2&gt;Migrating from preview 4&lt;/h2&gt; &lt;p&gt;When you upgrade your existing apps, you will likely run into a few issues. &lt;a href="http://weblogs.asp.net/whaggard/"&gt;Wes&lt;/a&gt; put together the following useful list of common errors that you might run into when migrating.&lt;/p&gt; &lt;ul&gt; &lt;li&gt;System.ComponentModel.Composition.Container does not exist -&amp;gt; Add reference to System.ComponentModel.Composition.Hosting namespace  &lt;li&gt;CompositionContainer does not container method AddPart or Compose -&amp;gt; Need to start using CompositionBatch, or one of the helper extension methods ComposeParts or ComposeExportedObjects  &lt;li&gt;CompositionOptionsAttribute does not exist -&amp;gt; For CreationPolicy use PartCreationPolicyAttribute  &lt;li&gt;INotifyImportCompleted does not exist -&amp;gt; Use IPartImportsSatisfiedNotification interface and change method from ImportCompleted to OnImportsSatisfied &lt;/li&gt;&lt;/ul&gt; &lt;h2&gt;Part Lifetime changes&lt;/h2&gt; &lt;p&gt;Previously, the CreationPolicy property of the CompositionOptions attribute was used to declare a part’s lifetime. We found this was less discoverable for customers as they have to know about the existence of the attribute. We also found that CreationPolicy was ambiguous in name, as it does not make clear whether or not the policy applies to the part or the export.&lt;/p&gt; &lt;p&gt;With the new changes, you will use the new PartCreationPolicyAttribute. CompositionOptions has been removed. Having part in the name of the attribute makes it easier to discover, and also removes ambiguity as to it’s scope.&lt;/p&gt; &lt;p&gt;Below the Logger class is declared as shared:&lt;/p&gt;&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;PartCreationPolicy&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;CreationPolicy.Shared&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;)]
[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ILogger&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;))]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Logger &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ILogger
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
}&lt;/span&gt;&lt;/pre&gt;
&lt;h2&gt;Part Discovery / Inheritance&lt;/h2&gt;
&lt;p&gt;In MEF Preview 4, a part by default would be discovered if there was an export on the most derived class. Additionally a part author could decorate the part with the CompositionOptions attribute, and set the DiscoveryMode property to change the behavior. Regardless of which mode was chosen, we would always look at all exports in the inheritance chain and discover them once we determined a part was a part. 
&lt;p&gt;We heard quite a bit of feedback both internally and externally around both the naming of the different enum values for DiscoveryModel, and the resulting behavior. 
&lt;h3&gt;Default Behavior&lt;/h3&gt;
&lt;p&gt;By default we will only look only at the most derived type to discover exports. If exports are found, then we will do a deep dive to discover all imports wherever they live in the hierarchy, &lt;em&gt;including interface members. &lt;/em&gt;This is because imports are an implementation detail of a part, and the part many not function without them. 
&lt;p&gt;In the example, we will discover a single export of IOrderScreen, and the OrderList import.&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;))]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public abstract class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;OrderScreen &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
 [&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Import&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
 &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderListView &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;OrderList { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }
}

[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;))]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;NorthwindOrderScreen &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;OrderScreen
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
}&lt;/span&gt;&lt;/pre&gt;
&lt;p&gt;Below, we will not discover anything, as the export is on the base. &lt;/p&gt;&lt;span style="background:white;color:black;"&gt;&lt;font face="Courier New"&gt;&lt;/font&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/span&gt;&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;))]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public abstract class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;OrderScreen &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
}

&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;NorthwindOrderScreen &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;OrderScreen
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
 [&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Import&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
 &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderListView &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;OrderList { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }
}&lt;/span&gt;&lt;/pre&gt;
&lt;h3&gt;Inherited exports behavior – using the PartExportsInheritedAttributed&lt;/h3&gt;
&lt;p&gt;The PartExportsInherited attribute allows declaring on a base class or an &lt;strong&gt;interface&lt;/strong&gt; that it’s exports should be discovered by inheritors / implementers. This replaces the previous [CompositionOptions(DiscoveryMode = DiscoveryMode.Always)]. This basically allows you to define a template for a part, and is useful hiding MEF’s implementation details from a part author. Implementers can further extend on what has been provided, such as adding their own exports and imports. 
&lt;p&gt;There’s a few guidelines / caveats to using this feature. 
&lt;ul&gt;
&lt;li&gt;PartExportsInheritedAttribute only makes the exports of the type it decorates discoverable by inheritors. It does not make exports of derivers of that type discoverable. The deriver itself needs to be decorated in order to make its exports discoverable. 
&lt;li&gt;We will ignore loose ExportMetadata attributes (and custom metadata attributes) that do not have an associated export. 
&lt;li&gt;If an inheritor overrides a member from the base which has an export, and decorates the overridden member with an export, two exports will be discovered,&lt;em&gt; even if the contract names are the same. &lt;/em&gt;This means if you expect implementers to add their own metadata, this might not be the best option, or at least you will need to provide special handling. We are looking into changing this behavior to have the inheritor override rather than be additive.&lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;In the example below, NorthwindOrderScreen will automatically export IOrderScreen.&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;PartExportsInherited&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public interface &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
}

&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;NorthwindOrderScreen &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
}&lt;/pre&gt;&lt;p&gt;&lt;span style="background:white;color:black;"&gt;Below NorthwindOrderScreen exports 2 instances of IOrderScreen, one with metadata and one without. The explicit export of IOrderScreen by NorthwindOrderScreen is in addition to the existing export.&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;PartExportsInherited&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]&lt;br /&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]&lt;br /&gt;&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public interface &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen&lt;br /&gt;&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ExportMetadata&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&amp;quot;Customer&amp;quot;, &amp;quot;Northwind&amp;quot;]&lt;br /&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;))]&lt;br /&gt;&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;NorthwindOrderScreen &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;:&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen&lt;br /&gt;&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{&lt;br /&gt;}&lt;br /&gt;&lt;/p&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;h3&gt;Ignoring part discovery – Using the PartNotDiscoverableAttribute&lt;/h3&gt;&lt;p&gt;This attribute replaces replaces [CompositionOptions(DiscoveryMode.Never).&amp;nbsp; It is useful for when a part author has parts that they do not want to be automatically discovered by catalogs and .&amp;nbsp; The scenarios where this make sense are where you either have a part which you will manually compose outside of a catalog, or you have a part that you intend for inheritors to use in a catalog but which cannot be made abstract. &lt;p&gt;In the sample below,&amp;nbsp; class OrderScreen will be ignored by the catalog. However, when class NorthwindOrderScreen is scanned, we will discover IOrderScreen, and will satisfy the OrderList import.&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;PartNotDiscoverable&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;PartExportsInherited&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;))]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;OrderScreen &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderScreen
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
 [&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Import&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
 &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOrderListView &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;OrderList { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }
}

&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;NorthwindOrderScreen &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;OrderScreen
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
}&lt;/span&gt;&lt;/pre&gt;&lt;h2&gt;Changes to collection imports&lt;/h2&gt;&lt;h3&gt;ImportMany attribute&lt;/h3&gt;&lt;p&gt;We’ve added a new [ImportMany] attribute. This attribute is to be used for specifying that an importer is expected to import all parts that match the contract. This attribute is equivalent to using [Import] on collections today. By our next release however, [Import] will change to mean import an exported collection. &lt;p&gt;Once we make the switch, the [ImportMany] attribute will be required on both properties and importing constructor parameters in order to get the same behavior as today.&lt;p&gt;As an example let’s take an importer of a collection of IOperation contacts. &lt;p&gt;With the new build the following will have identical results.&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Import&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IEnumerable&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOperation&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;gt; Operations { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }

[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ImportMany&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IEnumerable&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOperation&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;gt; Operations { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }&lt;/span&gt;&lt;/pre&gt;&lt;p&gt;In the next drop,&amp;nbsp; the behavior of the first will change. Instead of importing all exports of IOperation, it will instead be looking for an exporter of IEnumerable&amp;lt;IOperation&amp;gt;. The main reason for this is to support custom collections. Today for example the following code won’t yield the expected results if IRepository&amp;lt;T&amp;gt; is an ICollection&amp;lt;T&amp;gt;.&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Import&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IRepository&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Customer&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;gt; Customers { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }&lt;/span&gt;&lt;/pre&gt;&lt;p&gt;What the part author is intending here is to import a repository of customers. The repository as a whole is the import. Instead what will happen today is the container will set Customers to a new instance of Repository&amp;lt;Customer&amp;gt;. It will then query for all the Customer exports and add them to the Repository.&lt;h3&gt;Array imports&lt;/h3&gt;&lt;p&gt;In this release we’ve added support for array imports.&amp;nbsp; This allows the following syntax to be supported.&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ImportMany&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOperation&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;[] Operations { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }&lt;/span&gt;&lt;/pre&gt;&lt;h3&gt;&lt;a name="_Toc226739122"&gt;Future Deprecation of ExportCollection&amp;lt;T&amp;gt; and ExportCollection&amp;lt;T,M&amp;gt;&lt;/a&gt;&lt;/h3&gt;&lt;p&gt;In the next preview (not this one) we will be removing ExportCollection from MEF. The reasoning is that ExportCollection does not introduce any additional functionality, and we don’t want to introduce a collection which is solely there for syntactic sugar. The alternative recommended syntax for doing ExportCollection will be to use the new array support. Using the new syntax is significantly more compact than using ExportCollection, and is also less cryptic as arrays are very clear as to how they function.&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ImportMany&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOperation&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;gt;[] Operations { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }

[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ImportMany&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOperation&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;, &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;IOperationMetadata&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;gt;[] Operations { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }&lt;/span&gt;&lt;/pre&gt;&lt;p&gt;Additionally we support custom derived collections, thus you can easily create your own collections that provide the sugar.&lt;h2&gt;Typed Import/Exports&lt;/h2&gt;&lt;p&gt;In Preview 4, MEF discovers exports based on contract name, and not based on the type of the exporter. This means that an export can actually have an incompatible type with the importer. At the time when the export is set on the import, if the cast fails, then an exception is thrown. &lt;p&gt;This new feature in Preview 5 enables MEF to match imports and exports on contract AND type. When a part imports a contract, it additionally specifies the specific type that it is looking for. Only those exporters that also match on the importer type are matched. This means instead of failing, if the exporter’s type is incompatible, then it will not be matched. &lt;p&gt;In most cases, the type specification is done implicitly, and does not require any work on the part of the part author. The overloads of Export and Import that used to take Type as param, will now in addition to converting to the string contract representation, also embed the type information.&lt;p&gt;For example the code below works as it would have before.&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Editor
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
 [&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Import&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
 &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ISpellChecker &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;SpellChecker { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }
}

[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ISpellChecker&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;))]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;SpellChecker &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ISpellChecker
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
}&lt;/span&gt;&lt;/pre&gt;&lt;p&gt;However code that uses pure string contracts, will yield a different result than it would have before. The SpellChecker below will not be imported into the Editor. &lt;/p&gt;&lt;span style="background:white;color:black;"&gt;&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Editor
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
 [&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Import&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#a31515;"&gt;&amp;quot;SpellChecker&amp;quot;&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;)]
 &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ISpellChecker &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;SpellChecker { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }
}

[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#a31515;"&gt;&amp;quot;SpellChecker&amp;quot;&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;)]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;SpellChecker &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ISpellChecker
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
}&lt;/span&gt;&lt;/pre&gt;&lt;p&gt;Although SpellChecker implements ISpellChecker the type that the export carries is SpellChecker. The importer on the other hand is of type ISpellChecker so they do not match. In order to make the above code work, the export needs to specify the type.&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#a31515;"&gt;&amp;quot;SpellChecker&amp;quot;&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;,&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ISpellChecker&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;))]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;SpellChecker &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;: &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ISpellChecker
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
}&lt;/span&gt;&lt;/pre&gt;&lt;p&gt;This works as long as the type of the importer is ISpellChecker. Another option is for the importer to lift the restriction altogether by specifying the type as object.&lt;/p&gt;&lt;font face="Courier New"&gt;&lt;/font&gt;&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Editor
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
 [&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Import&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#a31515;"&gt;&amp;quot;EditorContracts.SpellChecker&amp;quot;&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;,&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;object&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;))]
 &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;EditorContracts.&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ISpellChecker &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;SpellChecker { &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;get&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;set&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;; }
}&lt;/span&gt;&lt;/pre&gt;&lt;p&gt;Now SpellChecker can be imported by any importer with the same contract name as long as the importer is either a SpellChecker or a derived type.&lt;/p&gt;&lt;span style="background:white;color:black;"&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/span&gt;&lt;h2&gt;Custom delegates&lt;/h2&gt;&lt;p&gt;In Preview 4, we only support Func and Action delegates for exports. Back by popular demand, we now support custom delegates again as we did in our earlier previews. This means that when you export a method, you can use a custom delegate, as opposed to having to use one of the pre-baked ones. For example in the code below, the Validate method is exporting ValidatorDelegate&amp;lt;Customer&amp;gt; which CustomerView is importing. String contracts are also fully supported. &lt;pre class="code"&gt;&lt;span style="background:white;color:blue;"&gt;public delegate bool &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ValidatorDelegate&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;lt;T&amp;gt;(T value);

&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;CustomerValidator
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
  [&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;typeof&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ValidatorDelegate&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Customer&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;gt;))]
  &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public bool &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;Validate(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Customer &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;customer)
  {
    &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;return &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;customer.Name != &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;null &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;amp;&amp;amp; customer.Name != &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;String&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;.Empty;
  }
}&lt;/span&gt;&lt;/pre&gt;&lt;pre class="code"&gt;&lt;span style="background:white;color:black;"&gt;[&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Export&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
&lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;CustomerView
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;  [&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ImportingConstructor&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;]
  &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;CustomerView(&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;ValidatorDelegate&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Customer&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&amp;gt; validator)
  {
  }
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;}
&lt;/pre&gt;&lt;h2&gt;Directory Catalog changes&lt;/h2&gt;&lt;p&gt;Prior versions of the DirectoryCatalog internally used a FileSystemWatcher in order to notify the catalog that changes have occurred within the watched directory. Using the watcher was problematic for many reasons usually related to MEF trying to grab the file too early. Today it is very common for apps that enable the watcher to fail whenever a file is dropped in the folder. &lt;p&gt;As such we removed the watching functionality and replaced it with an explicit Refresh() method. The advantage of the refresh is it allows the host to determine when the refresh should occur. For example, a .NET Reflector type app could have a refresh button on the addins screen, the rescans the folders on demand. Once the folder is scanned, the catalog will do the delta to determine any changes, and it will fire change notifications as it does today, thus triggering re-composition in the container.&lt;/p&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/span&gt;&lt;pre class="code"&gt;&lt;span style="background:white;color:blue;"&gt;public class &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;Application
&lt;/span&gt;&lt;span style="background:white;color:black;"&gt;{
  &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;private &lt;/span&gt;&lt;span style="background:white;color:#2b91af;"&gt;DirectoryCatalog &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;catalog;

  &lt;/span&gt;&lt;span style="background:white;color:green;"&gt;//triggered by the user clicking the Refresh button on the addins page
  &lt;/span&gt;&lt;span style="background:white;color:blue;"&gt;public void &lt;/span&gt;&lt;span style="background:white;color:black;"&gt;Refresh()
  {
    catalog.Refresh();
  }
}&lt;/span&gt;&lt;/pre&gt;&lt;h2&gt;&lt;a name="_Toc226739126"&gt;Removal of caching / new infrastructure&lt;/a&gt;&lt;/h2&gt;&lt;p&gt;We found several issues with our previous caching design which was black box. We’ve completely removed the old caching apis. We’ve added in a new API that can be used for caching, however we are not including a default caching implementation within MEF itself. We will however be shipping a caching API sample which illustrates how to use the APIs. The new APIs provides the further benefit of making it much easier to build new programming models that utilize reflection for are reflection based. &lt;p&gt;We’ve now introduced a new set of classes in System.ComponentModel.Composition.ReflectionModel that can be used by cache implementers. ReflectionModelServices provides a set of static helper methods that can be used for manufacturing part definitions from a cache store.&lt;/p&gt;&lt;span style="background:white;color:black;"&gt;&lt;h2&gt;Summary&lt;/h2&gt;&lt;p&gt;A lot of new things to play with in preview 5. My personal favorite is the support we’ve now added for exports on interfaces, though I am sure if you ask different members of the team you’ll get a different answer.&amp;nbsp; &lt;/p&gt;&lt;p&gt;Thanks as always to the team for all their efforts, and thank you for your continual patience and feedback. We’re getting closer and closer to RTM!&lt;/p&gt;&lt;p&gt;So what are you waiting for? Go download MEF Preview 5 &lt;a href="http://mef.codeplex.com/Release/ProjectReleases.aspx?ReleaseId=25797"&gt;here&lt;/a&gt;.&lt;/p&gt;&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/span&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=192910" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category></item><item><title>Creating a functional programming model for MEF</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/04/03/creating-a-functional-programming-model-for-mef.aspx</link><pubDate>Fri, 03 Apr 2009 10:00:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:190238</guid><dc:creator>Glenn Block</dc:creator><slash:comments>0</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=190238</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/04/03/creating-a-functional-programming-model-for-mef.aspx#comments</comments><description>&lt;p&gt;&lt;strong&gt;Disclaimer:&lt;/strong&gt; This is a prototype, not production ready code. It is more illustrative of what you can do with MEF, and how things work under the covers.&lt;/p&gt;
&lt;p&gt;The other day I was working one of our internal partners who is looking to integrate MEF into their framework stack. One of the interesting ideas that came out of that discussion was around a need they had to add POCO instances directly to a catalog (in addition to using our standard attributed part). &lt;/p&gt;
&lt;p&gt;Now MEF supports the ability to add existing instances to the container through the AddExportedObject method, but that did not suit their need.&amp;nbsp; Instead they wanted these instances to actually be parts. Primarily because the types they were instantiating were not attributed MEF parts, and they did not want to incur the reflection cost.&lt;/p&gt;
&lt;p&gt;I started thinking down the path of creating a programming model where the part definitions are actually wrapping instances. What I mean by programming model, is teach MEF a new way to represent parts, exports and imports. In MEF parlance, a programming model is almost like a type system, though far less complex. For more on programming models themselves, i&amp;#39;d refer you to Daniel&amp;#39;s nice post on programming models themselves &lt;a href="http://blogs.msdn.com/dsplaisted/archive/2009/06/08/a-crash-course-on-the-mef-primitives.aspx"&gt;here&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Out of the box, MEF ships with an attributed programming model, however others can be created by implementing on top of a set of abstractions we call the primitives. What&amp;rsquo;s really nice about MEF is that all of the models can safely interact with one another in the container. &lt;/p&gt;
&lt;p&gt;Building an instance model however is problematic in that parts in MEF should be lazily instantiated. I realized (probably due much influence of my &lt;a href="http://code.google.com/p/autofac/"&gt;Autofac&lt;/a&gt; workmate &lt;a href="http://blogs.msdn.com/nblumhardt"&gt;Nick Blumhardt&lt;/a&gt;) that the right way to go was not build an instance model, but rather build a model for representing functions as parts. And so, the FuncCatalog was born. &lt;/p&gt;
&lt;h1&gt;FuncCatalog&lt;/h1&gt;
&lt;p&gt;The FuncCatalog allows you to add functions directly to itself, and to associate those functions with a type to be exported. Each function gets a single parameter which is an ExportProvider. This allows you to build up an instance within your function, that can have constructor parameters pulled from the EP, similar to the registration style in Autofac.&lt;/p&gt;
&lt;p&gt;Below is a sample acceptance test that illustrates how this works. In the example I am adding a function to funcCatalog which creates an OrderService. In the OrderService&amp;rsquo;s constructor, I am passing in an ILogger that I retrieved from the Export Provider.&lt;/p&gt;
&lt;p&gt;[&lt;span style="color:#2b91af;"&gt;TestMethod&lt;/span&gt;] &lt;br /&gt;&lt;span style="color:blue;"&gt;public void &lt;/span&gt;FuncPartCanImportFromTheContainer() &lt;br /&gt;{ &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color:blue;"&gt;var &lt;/span&gt;catalog = &lt;span style="color:blue;"&gt;new&lt;/span&gt;&lt;span style="color:#2b91af;"&gt;AggregateCatalog&lt;/span&gt;(); &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; catalog.Catalogs.Add(&lt;span style="color:blue;"&gt;new&lt;/span&gt;&lt;span style="color:#2b91af;"&gt;TypeCatalog&lt;/span&gt;(&lt;span style="color:blue;"&gt;typeof &lt;/span&gt;(&lt;span style="color:#2b91af;"&gt;AttributedLogger&lt;/span&gt;)));&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color:blue;"&gt;var &lt;/span&gt;funcCatalog = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncCatalog&lt;/span&gt;(); &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; funcCatalog.AddPart&amp;lt;&lt;span style="color:#2b91af;"&gt;OrderService&lt;/span&gt;&amp;gt;( &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ep =&amp;gt; &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;OrderService&lt;/span&gt;(ep.GetExportedObject&amp;lt;&lt;span style="color:#2b91af;"&gt;ILogger&lt;/span&gt;&amp;gt;())); &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; catalog.Catalogs.Add(funcCatalog); &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color:blue;"&gt;var &lt;/span&gt;container = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;CompositionContainer&lt;/span&gt;(catalog); &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color:blue;"&gt;var &lt;/span&gt;batch = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;CompositionBatch&lt;/span&gt;(); &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; batch.AddExportedObject&amp;lt;&lt;span style="color:#2b91af;"&gt;ExportProvider&lt;/span&gt;&amp;gt;(container); &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; container.Compose(batch); &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color:blue;"&gt;var &lt;/span&gt;service = container.GetExportedObject&amp;lt;&lt;span style="color:#2b91af;"&gt;OrderService&lt;/span&gt;&amp;gt;(); &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;span style="color:#2b91af;"&gt;Assert&lt;/span&gt;.IsNotNull(service.Logger); &lt;br /&gt;}&lt;/p&gt;
&lt;p&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;In terms of what the code is doing, I am first creating an aggregate catalog (a catalog of catalogs). Then I am adding to it a type catalog which contains an AttributedLogger (that is a logger with an ExportAttribute on it). Next I am creating a FuncCatalog which I am adding the new func part to. Notice how the lambda passes ep.&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ep =&amp;gt; &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;OrderService&lt;/span&gt;(ep.GetExportedObject&amp;lt;&lt;span style="color:#2b91af;"&gt;ILogger&lt;/span&gt;&amp;gt;())&lt;/p&gt;
&lt;p&gt;Next I am creating the container, and then adding itself to itself (via the batch) with ExportProvider as the contract. This is to allow the FuncPart to import the ExportProvider so it can use it to resolve other dependencies. &lt;/p&gt;
&lt;p&gt;Finally I am asking the container to grab me an OrderService, which I am then checking to see if there is a logger present. Remember the logger actually was an attributed part that was added through MEF&amp;rsquo;s normal catalogs. So right here we have an illustration of multiple models living side by side.&lt;/p&gt;
&lt;h1&gt;&lt;/h1&gt;
&lt;h1&gt;&lt;/h1&gt;
&lt;h1&gt;How is it done?&lt;/h1&gt;
&lt;p&gt;As I mentioned above, I created a custom programming model. Depending on the model, this can be a lot or a little work. &lt;a href="http://www.thecodejunkie.com/"&gt;Andreas Haakanson&lt;/a&gt; has a project on CodePlex that simplifies creating such programming models, but that is for another overdue post :-)&amp;nbsp; Below I&amp;rsquo;ll detail the approach I took in order to give you a view into how programming models work. &lt;/p&gt;
&lt;h1&gt;Programming model players&lt;/h1&gt;
&lt;p&gt;Below are the main abstractions you&amp;nbsp; need to implement for building your own programming model which live in the System.ComponentModel.Composition.Primitives namespace.&lt;/p&gt;
&lt;p&gt;&lt;a href="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_031266FE.png"&gt;&lt;img height="293" width="532" src="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_thumb_5F00_1D725A15.png" alt="image" border="0" title="image" style="border-bottom:0px;border-left:0px;display:inline;border-top:0px;border-right:0px;" /&gt;&lt;/a&gt; &lt;/p&gt;
&lt;p&gt;Here&amp;rsquo;s&amp;nbsp; a quick summary of the responsibilities for each of these classes.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;ComposablePartDefinition&lt;/strong&gt; &amp;ndash; Schema for a part, analogous to a type in many respects. As a matter of fact in our default Attributed Programming Model (APM), the Composable Part Definition wraps a type. Aside from being schema, the other main responsibility for CPD is to create a composable part. &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;ImportDefinition&lt;/strong&gt; &amp;ndash; An import definition is carries information about a contract that a part needs, it&amp;rsquo;s import. In the APM, import definitions are created for properties decorated with the ImportAttribute, or constructor parameters if the constructor has an ImportingConstructorAttribute.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;ExportDefinition&lt;/strong&gt; - An export definition carries information about a contract that a part offers up, it&amp;rsquo;s export. In the APM, an export definition is created for each member that is decorated with the ExportAttribute. This includes the class itself, or methods / properties.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;ComposablePartCatalog&lt;/strong&gt; &amp;ndash; The catalog aggregates part definitions, which the container will query during composition in order to find available exports. The catalog does not create any parts, it only returns requested definitions. In our APM, the catalogs read assemblies and types in order to create these definitions. &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;ComposablePart &amp;ndash;&lt;/strong&gt; The part itself. If the CPD is the schema, then the part is the instance. This does not mean it is the actual instance that is being returned from the container. No. The part contains an instance which will get created only at the time when the first exported object actually pulled from it. There&amp;rsquo;s a difference between an export and an exported object, but I&amp;rsquo;ll resist to go deeper and try to explain it for now.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;In my new model I implemented FuncCatalog, FuncExportDefinition, FuncPart, and FuncPartDefinition. I did not need a new ImportDefinition as the standard one was fine. Also my parts only support a single import, namely an ExportProvider.&lt;/p&gt;
&lt;p&gt;&lt;a href="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_27574B80.png"&gt;&lt;img height="310" width="538" src="http://codebetter.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/glenn.block/image_5F00_thumb_5F00_0663D8D9.png" alt="image" border="0" title="image" style="border-bottom:0px;border-left:0px;display:inline;border-top:0px;border-right:0px;" /&gt;&lt;/a&gt; &lt;/p&gt;
&lt;h1&gt;FuncExportDefinition&lt;/h1&gt;
&lt;p&gt;Ok, so first stop is to build a FuncExportDefinition. In my case I need a definition that carries a custom function. So here it is.&lt;/p&gt;
&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncExportDefinition &lt;/span&gt;: &lt;span style="color:#2b91af;"&gt;ExportDefinition
&lt;/span&gt;{
    &lt;span style="color:blue;"&gt;public &lt;/span&gt;FuncExportDefinition(&lt;span style="color:blue;"&gt;string &lt;/span&gt;contractName, 
        &lt;span style="color:#2b91af;"&gt;Func&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ExportProvider&lt;/span&gt;,&lt;span style="color:blue;"&gt;object&lt;/span&gt;&amp;gt; factory) :
        &lt;span style="color:blue;"&gt;base&lt;/span&gt;(contractName, &lt;span style="color:blue;"&gt;null&lt;/span&gt;)
    {
        Factory = factory;
    }

    &lt;span style="color:blue;"&gt;public &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;Func&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ExportProvider&lt;/span&gt;, &lt;span style="color:blue;"&gt;object&lt;/span&gt;&amp;gt; Factory { &lt;span style="color:blue;"&gt;get&lt;/span&gt;; &lt;span style="color:blue;"&gt;private set&lt;/span&gt;; }
}&lt;/pre&gt;
&lt;p&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;Pretty simple, I basically allow associating a contract and an additional func which accepts an ExportProvider as a parameter and returns object. Now notice the second parameter I pass to the base class is null. That represents metadata. I decided for simplicity to not allow support of metadata, though that could easily be added back.&lt;/p&gt;
&lt;h1&gt;FuncPartDefinition&lt;/h1&gt;
&lt;p&gt;Now that I can define Funcs as exports, I need a PartDefinition which can carry that information, and manufacture a part. This one was a bit tricky, below are the important pieces.&lt;/p&gt;
&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public abstract class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncPartDefinition &lt;/span&gt;: &lt;span style="color:#2b91af;"&gt;ComposablePartDefinition
&lt;/span&gt;{}

&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncPartDefinition&lt;/span&gt;&amp;lt;TContract&amp;gt; : &lt;span style="color:#2b91af;"&gt;FuncPartDefinition 
&lt;/span&gt;{
    &lt;span style="color:blue;"&gt;private static &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ContractBasedImportDefinition 
        &lt;/span&gt;_exportProviderImportDefinition;


    &lt;span style="color:blue;"&gt;static &lt;/span&gt;FuncPartDefinition()
    {
        &lt;span style="color:blue;"&gt;string &lt;/span&gt;importContractName = &lt;span style="color:#2b91af;"&gt;CompositionServices&lt;/span&gt;.GetContractName
            (&lt;span style="color:blue;"&gt;typeof&lt;/span&gt;(&lt;span style="color:#2b91af;"&gt;ExportProvider&lt;/span&gt;));
        _exportProviderImportDefinition = &lt;span style="color:blue;"&gt;new 
            &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ContractBasedImportDefinition&lt;/span&gt;(
            importContractName, &lt;span style="color:blue;"&gt;null&lt;/span&gt;,
            &lt;span style="color:#2b91af;"&gt;ImportCardinality&lt;/span&gt;.ZeroOrOne, &lt;span style="color:blue;"&gt;false&lt;/span&gt;, &lt;span style="color:blue;"&gt;false&lt;/span&gt;,
            &lt;span style="color:#2b91af;"&gt;CreationPolicy&lt;/span&gt;.Any);
    }

    &lt;span style="color:blue;"&gt;public &lt;/span&gt;FuncPartDefinition(&lt;span style="color:#2b91af;"&gt;Func&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ExportProvider&lt;/span&gt;, &lt;span style="color:blue;"&gt;object&lt;/span&gt;&amp;gt; factory)
    {
        _exportDefinitions.Add(&lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncExportDefinition
            &lt;/span&gt;(&lt;span style="color:#2b91af;"&gt;CompositionServices&lt;/span&gt;.GetContractName(&lt;span style="color:blue;"&gt;typeof&lt;/span&gt;(TContract)),
            factory));
        _importDefinitions.Add(_exportProviderImportDefinition);
    }

    &lt;span style="color:blue;"&gt;public &lt;/span&gt;FuncPartDefinition()
        : &lt;span style="color:blue;"&gt;this&lt;/span&gt;((ep)=&amp;gt;(TContract) &lt;span style="color:#2b91af;"&gt;Activator&lt;/span&gt;.
            CreateInstance(&lt;span style="color:blue;"&gt;typeof &lt;/span&gt;(TContract)))
    {
    }

    &lt;span style="color:blue;"&gt;public override &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePart &lt;/span&gt;CreatePart()
    {
        &lt;span style="color:blue;"&gt;return new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncPart&lt;/span&gt;&amp;lt;TContract&amp;gt;(&lt;span style="color:blue;"&gt;this&lt;/span&gt;);
    }
}&lt;/pre&gt;
&lt;h1&gt;&lt;/h1&gt;
&lt;p&gt;As I mentioned earlier, my func parts need to access an ExportProvider so they can retrieve things from the container. The question was how to do this. I could make the ExportProvider a parameter on the constructor of the part. Then however, I would have to pass it in to the catalog, which would pass it in to the part. This is further problematic as catalogs can actually be passed to several containers. So I decided the easiest way to do it, was to have the part actually import the ExportProvider through MEF&amp;rsquo;s composition, that is similar to the way I would import on an attributed part through a constructor param. &lt;/p&gt;
&lt;p&gt;In order to do this, all I need is to add a single ImportDefinition to every part instance. The static constructor of FuncPartDefinition does the work of creating this definition. The definition never changes, and it is cheaper to create it once, which is&amp;nbsp; why I made it static.&lt;/p&gt;
&lt;p&gt;The instance constructor accepts the&amp;nbsp; func. It then goes and creates a FuncExportDefinition which it adds to the collection of export definitions. Next it adds the export provider import. I added an additional overload just as a convenience which simply creates the type. Probably just being gratuitous ;-)&lt;/p&gt;
&lt;p&gt;Finally the CreatePart method goes and creates a FuncPart passing in the definition (the part&amp;rsquo;s schema) which leads us to our next suspect.&lt;/p&gt;
&lt;h1&gt;FuncPart&lt;/h1&gt;
&lt;p&gt;This guys job is to pass back export definitions of our func, to the container on request. Those definitions can later be activated to invoke the actual func.&lt;/p&gt;
&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncPart&lt;/span&gt;&amp;lt;TContract&amp;gt; : &lt;span style="color:#2b91af;"&gt;ComposablePart 
&lt;/span&gt;{
    &lt;span style="color:blue;"&gt;private &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncPartDefinition&lt;/span&gt;&amp;lt;TContract&amp;gt; _definition;
    &lt;span style="color:blue;"&gt;private &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ExportProvider &lt;/span&gt;_provider;

    &lt;span style="color:blue;"&gt;public &lt;/span&gt;FuncPart(&lt;span style="color:#2b91af;"&gt;FuncPartDefinition&lt;/span&gt;&amp;lt;TContract&amp;gt; definition)
    {
        _definition = definition;
    }

    &lt;span style="color:blue;"&gt;public override object &lt;/span&gt;GetExportedObject(&lt;span style="color:#2b91af;"&gt;ExportDefinition &lt;/span&gt;definition)
    {
        &lt;span style="color:blue;"&gt;var &lt;/span&gt;funcExportDefinition = definition &lt;span style="color:blue;"&gt;as &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncExportDefinition&lt;/span&gt;;
        &lt;span style="color:blue;"&gt;return &lt;/span&gt;funcExportDefinition.Factory(_provider);
    }

    &lt;span style="color:blue;"&gt;public override void &lt;/span&gt;SetImport(&lt;span style="color:#2b91af;"&gt;ImportDefinition &lt;/span&gt;definition, 
        &lt;span style="color:#2b91af;"&gt;IEnumerable&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;Export&lt;/span&gt;&amp;gt; exports)
    {
        _provider = exports.First().GetExportedObject() &lt;span style="color:blue;"&gt;as &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ExportProvider&lt;/span&gt;;
    }

    &lt;span style="color:blue;"&gt;public override &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;IEnumerable&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ExportDefinition&lt;/span&gt;&amp;gt; ExportDefinitions
    {
        &lt;span style="color:blue;"&gt;get &lt;/span&gt;{ &lt;span style="color:blue;"&gt;return &lt;/span&gt;_definition.ExportDefinitions; }
    }

    &lt;span style="color:blue;"&gt;public override &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;IEnumerable&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ImportDefinition&lt;/span&gt;&amp;gt; ImportDefinitions
    {
        &lt;span style="color:blue;"&gt;get &lt;/span&gt;{ &lt;span style="color:blue;"&gt;return &lt;/span&gt;_definition.ImportDefinitions; }
    }
}&lt;/pre&gt;
&lt;p&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;When the part gets constructed, it stores a copy of it&amp;rsquo;s definition. The ExportDefinitions and ImportDefinitions delegate directly to the part definitions members. In the SetImport method I have got a bit of a hack going on. This method will get called by the composition engine to set the imports. In the method, I am grabbing the first export passed in and then assuming it is the export provider. This is actually an OK assumption in my case, since there is only a single import that I allow in my programming model. However, I really should be verifying that it is passing me the right definition.&lt;/p&gt;
&lt;p&gt;And just when you thought I was done with hacks, another one :-) GetExportedObject takes the definition passed to it and assumes it is a FuncExportDefinition. Again, this is an ok assumption in the cases where I am using it, but it should be more bullet proof and not make those assumptions. Anyway, once it has the definition&amp;nbsp; unwrapped, it grabs the factory and invokes it passing in the provider.&lt;/p&gt;
&lt;h1&gt;FuncCatalog&lt;/h1&gt;
&lt;p&gt;Last stop on our journey is the func catalog.&amp;nbsp; He&amp;rsquo;s actually pretty straightforward. I added a few convenience methods on him so that you don&amp;rsquo;t have to create parts a head of time.&lt;/p&gt;
&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;public class &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncCatalog &lt;/span&gt;: &lt;span style="color:#2b91af;"&gt;ComposablePartCatalog&lt;/span&gt;,     
    &lt;span style="color:#2b91af;"&gt;INotifyComposablePartCatalogChanged
&lt;/span&gt;{
    &lt;span style="color:blue;"&gt;private &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ComposablePartDefinition&lt;/span&gt;&amp;gt; _parts = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ComposablePartDefinition&lt;/span&gt;&amp;gt;();

    &lt;span style="color:blue;"&gt;public &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncPartDefinition &lt;/span&gt;AddPart&amp;lt;T&amp;gt;(
        &lt;span style="color:#2b91af;"&gt;Func&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ExportProvider&lt;/span&gt;, &lt;span style="color:blue;"&gt;object&lt;/span&gt;&amp;gt; factory)
    {
        &lt;span style="color:blue;"&gt;var &lt;/span&gt;addedParts = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;List&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;FuncPartDefinition&lt;/span&gt;&amp;gt;();
        &lt;span style="color:blue;"&gt;var &lt;/span&gt;definition = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncPartDefinition&lt;/span&gt;&amp;lt;T&amp;gt;(factory);
        _parts.Add(definition);
        
        addedParts.Add(definition);
        OnChanged(addedParts);
        &lt;span style="color:blue;"&gt;return &lt;/span&gt;definition;

    }

    &lt;span style="color:blue;"&gt;public void &lt;/span&gt;AddParts(&lt;span style="color:blue;"&gt;params &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncPartDefinition&lt;/span&gt;[] parts)
    {
        _parts.AddRange(parts);
        OnChanged(parts);
    }

    &lt;span style="color:blue;"&gt;public void &lt;/span&gt;RemoveParts(&lt;span style="color:blue;"&gt;params &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;FuncPartDefinition&lt;/span&gt;[] parts)
    {
        _parts.RemoveAll(c =&amp;gt; parts.Contains(c));
        OnChanged(parts);
    }
    
    &lt;span style="color:blue;"&gt;public override &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;IQueryable&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ComposablePartDefinition&lt;/span&gt;&amp;gt; Parts
    {
        &lt;span style="color:blue;"&gt;get
        &lt;/span&gt;{
            &lt;span style="color:blue;"&gt;return &lt;/span&gt;_parts.AsQueryable();
        }
    }

    &lt;span style="color:blue;"&gt;private void &lt;/span&gt;OnChanged(&lt;span style="color:#2b91af;"&gt;IEnumerable&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;FuncPartDefinition&lt;/span&gt;&amp;gt; parts)
    {
        &lt;span style="color:blue;"&gt;var &lt;/span&gt;args = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;ComposablePartCatalogChangedEventArgs&lt;/span&gt;(
            parts.Cast&amp;lt;&lt;span style="color:#2b91af;"&gt;ComposablePartDefinition&lt;/span&gt;&amp;gt;());
        Changed(&lt;span style="color:blue;"&gt;this&lt;/span&gt;, args);
    }

    &lt;span style="color:blue;"&gt;public event &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;EventHandler&lt;/span&gt;&amp;lt;&lt;span style="color:#2b91af;"&gt;ComposablePartCatalogChangedEventArgs&lt;/span&gt;&amp;gt; 
        Changed = &lt;span style="color:blue;"&gt;delegate &lt;/span&gt;{ };
}&lt;/pre&gt;
&lt;p&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;First thing is the catalog implements INotifyComposablePartCatalogChanged. This is to allow the catalog to notify the container when parts are added or removed from it. Implementing a catalog only requires to to override one property, namely the Parts property, which as you can see returns a queryable of Parts. The rest of the methods are concerned with the mutability of the container. Now catalogs do not have to be mutable, as you can handle loading up all the part defs in the constructor. However, for usability sake, I wanted mine to&amp;nbsp; be mutable. This means that I need to have methods for adding, removing, and I need to support notification.&amp;nbsp; The code should be pretty easy to follow.&lt;/p&gt;
&lt;h1&gt;&lt;/h1&gt;
&lt;h1&gt;So what have we learned?&lt;/h1&gt;
&lt;p&gt;Well first thing we learned that MEF supports alternative programming models other than the attributed model we ship in the box. Next, we learned about the key concepts involved in authoring your own programming model. In this case the model was very, very simple, which is why I was able to cover it in a single post. I am not recommending every one go out an author their own model. Lastly we saw learned that parts can be functions :-)&lt;/p&gt;
&lt;p&gt;If your interested in other applications of programming models in MEF, I recommend you check out Nick Blumhart&amp;rsquo;s posts on Ruby. Also don&amp;rsquo;t forget to check out &lt;a href="http://www.thecodejunkie.com"&gt;Andreas&amp;rsquo;s&lt;/a&gt; &lt;a href="http://mefcontrib.codeplex.com/Wiki/View.aspx?title=Documentation%20%26%20Features&amp;amp;referringTitle=Home"&gt;provider based programming model&lt;/a&gt; on MefContrib. &lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=190238" width="1" height="1"&gt;</description><enclosure url="http://cid-f8b2fd72406fb218.skydrive.live.com/self.aspx/blog/FuncCatalogExtensions.zip" length="37595" type="text/html; charset=utf-8" /><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category></item><item><title>Why doesn’t MEF support open-generics for exports? Because MEF is not type based.</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/03/21/why-doesn-t-mef-support-open-generics-for-exports-because-mef-is-not-type-based.aspx</link><pubDate>Sat, 21 Mar 2009 20:10:56 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:189561</guid><dc:creator>Glenn Block</dc:creator><slash:comments>7</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=189561</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/03/21/why-doesn-t-mef-support-open-generics-for-exports-because-mef-is-not-type-based.aspx#comments</comments><description>&lt;p&gt;I get this question all the time. Recently it popped it’s head on the forums in this &lt;a href="http://mef.codeplex.com/Thread/View.aspx?ThreadId=50504"&gt;thread&lt;/a&gt; (which I referred to in my last &lt;a href="http://codebetter.com/blogs/glenn.block/archive/2009/03/21/recomposition-and-constructors.aspx"&gt;post&lt;/a&gt;)&lt;/p&gt;  &lt;p&gt;In that thread, Andrew was asking why the following does not work?&lt;/p&gt;  &lt;div id="codeSnippetWrapper"&gt;   &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;     &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Export(&lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt;(IDomainController&amp;lt;&amp;gt;)), CompositionOptions(CreationPolicy = CreationPolicy.Shared)]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; DomainController&amp;lt;T&amp;gt; : IDomainController&amp;lt;T&amp;gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#008000;"&gt;/* some code here */&lt;/span&gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  [ImportingConstructor]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; DomainController(IRepository repository)&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    _Repository = repository&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  }&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;} &lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;That is he wants to export a generic IDomainController with the idea the closed generic versions like IDomainController&amp;lt;Customer&amp;gt; could be imported.&lt;/p&gt;

&lt;p&gt;He also rightly observed that many of the IoC containers that exist support this functionality including &lt;a href="http://msdn.microsoft.com/unity"&gt;Unity&lt;/a&gt;. (I chuckled when I heard that because I was in p&amp;amp;p when we first wrote Unity) However, it is a valid question, why don’t we support it? This is one of those questions that I, &lt;a href="http://hammett.castleproject.org/"&gt;Hammett&lt;/a&gt; and &lt;a href="http://blogs.msdn.com/nblumhardt"&gt;Nick&lt;/a&gt; all asked when we joined the team.&amp;#160; We do support closed generics without a problem, but not open. Why?&lt;/p&gt;

&lt;p&gt;As you dig into the details, it quickly becomes clear. The root of the answer is that MEF is not type based, it is contract based. Below are the details from my response…&lt;/p&gt;

&lt;p&gt;MEF parts relate on contracts which are strings, not types. To illustrate, see the code below.&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;namespace&lt;/span&gt; Orders {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;interface&lt;/span&gt; IOrderRepository {}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  [Export(&lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt;(IOrderRespository))]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; OrderRepository : IOrderRepository {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  }&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Although I have passed typeof(IOrderRepository) to the export, that is just a convenience that gets converted to a contract name of &amp;quot;Orders.IOrderRepository&amp;quot;. The same applies to the importer...&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Export]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; OrderService(&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  [Import]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; IOrderRepository Repository {gets;set;} &lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;)&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p align="left"&gt;The import on IOrderRepository also gets converted to a contract name of &amp;quot;Orders.IOrderRepository&amp;quot;. During composition, the container is able to satisfy the import as the 2 contracts match. In the same way we support closed generics, so this code....&amp;#160;&amp;#160;&amp;#160; &lt;/p&gt;

&lt;div&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;interface&lt;/span&gt; IRepository&amp;lt;T&amp;gt; {}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Export(&lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt;(IRepository&amp;lt;Order&amp;gt;))]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; OrderRepository : IRepository&amp;lt;Order&amp;gt; {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Export]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; OrderService(&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  [Import]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; IRepository&amp;lt;Order&amp;gt; Repository {gets;set;} &lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;)&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p align="left"&gt;will work because the OrderRepository is exporting the contract name &amp;quot;Orders.IRepository&amp;lt;Order&amp;gt;&amp;quot; and the OrderService is importing the same contract.&lt;/p&gt;

&lt;p align="left"&gt;However, this is what it looks like if we try the same with open generics.&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;interface&lt;/span&gt; IRepository&amp;lt;T&amp;gt; {}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;namespace&lt;/span&gt; Utils {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  [Export(&lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt;(IRepository&amp;lt;&amp;gt;))]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; Repository : IRepository&amp;lt;T&amp;gt; {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  }&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Export]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; OrderService(&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  [Import]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; IRepository&amp;lt;Order&amp;gt; Repository {gets;set;} &lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;)&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p align="left"&gt;Now the contract names will be different. The exporter will have a contract of&amp;#160; &amp;quot;Utils.IRepository&amp;lt;&amp;gt;&amp;quot; and the importer will have a contract of &amp;quot;Utils.IRepository&amp;lt;Order&amp;gt;&amp;quot;.
  &lt;br /&gt;&lt;/p&gt;

&lt;p align="left"&gt;It is a simple match up, that breaks down in the open-generics case. This is because fundamentally, MEF is not matching on type. &lt;/p&gt;

&lt;p&gt;There are theoretical ways to address it, but they are all very ugly, require a lot of string parsing and really go against the grain of MEF’s core design.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=189561" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/Generics/default.aspx">Generics</category></item><item><title>Recomposition and constructors</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/03/21/recomposition-and-constructors.aspx</link><pubDate>Sat, 21 Mar 2009 19:34:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:189559</guid><dc:creator>Glenn Block</dc:creator><slash:comments>4</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=189559</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/03/21/recomposition-and-constructors.aspx#comments</comments><description>&lt;p&gt;Yesterday on twitter I was expressing how far behind I am&amp;#160; on blogging, and how I don’t know where to start. &lt;a href="http://www.ayende.com/blog"&gt;Ayende&lt;/a&gt; (Oren) responded by saying “Just start bloggging!” So here goes.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://blog.benhall.me.uk/"&gt;Ben Hall&lt;/a&gt; pinged me over IM yesterday asking about recomposable imports on constructors, and whether or not they work? Natively MEF does not support this, but I did find a workaround. More about this later as the answer won’t make any sense without first understanding what in the heck recomposition is.&lt;/p&gt;  &lt;h1&gt;&lt;/h1&gt;  &lt;h2&gt;Recomposition&lt;/h2&gt;  &lt;p&gt;Recomposition is an opt-in feature of MEF that allows imports to be updated whenever there are changes in the container that relate to the availability of exports of that contract, you can think of this as live imports. &lt;/p&gt;  &lt;p&gt;Recomposition is one of those capabilities that is useful for systems that dynamically change after the app is running. The change does not only have to be due to new assemblies appearing, it could due to contextual changes in the application such as a user updating their profile, or the application moving into a different state.&lt;/p&gt;  &lt;p&gt;For example below I have a part that imports a collection of ILoggers.&lt;/p&gt;  &lt;div id="codeSnippetWrapper"&gt;   &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;     &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; LoggerManager {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  [Import(AllowRecomposition = &lt;span style="color:#0000ff;"&gt;true&lt;/span&gt;)]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; IEnumerable&amp;lt;ILogger&amp;gt; Loggers {get;set;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;&amp;#160;&lt;/p&gt;

&lt;p&gt;Notice the import is marked with AllowRecomposition = true. This means that after initial composition, the Loggers collection should be updated should new loggers either be manually added (or removed) to the container, or appear in a catalog. &lt;/p&gt;

&lt;p&gt;Recomposition is not only useful for collections, it can also be for single imports, which was Ben’s case. That is I could have a single logger import which is also recomposable. That means that if someone replaces the single logger in the system, then the part which imports will automatically be updated.&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; OrderProcessor {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  [Import(AllowRecomposition = &lt;span style="color:#0000ff;"&gt;true&lt;/span&gt;)]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;  &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; ILogger logger {get;set;}&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Now the OrderProcessor expects to see a single ILogger. That logger however is recomposable such that when the logger is replaced, it will get automatically updated.&lt;/p&gt;

&lt;h1&gt;&lt;/h1&gt;

&lt;h2&gt;Constructors&lt;/h2&gt;

&lt;p&gt;Now that we understand what Recomposition is, we can get to Ben’s question. Are constructors parameters supported? The answer is no (at least not without help). The reason is that recomposition on MEF is connected to the part,. Whenever a part has imports that are recomposable, we keep a pointer to the associated ComposablePart within the container. We then monitor changes on that particular contract that the&amp;#160; part is importing. Whenever changes occur, we then update the imports on the part which results in replacing the value of the corresponding property. This works because we can replace the reference. In the case of constructor parameters however, we cannot grab your parameter reference and change it.&lt;/p&gt;

&lt;h1&gt;&lt;/h1&gt;

&lt;h2&gt;OK, so we’re out of luck then?&lt;/h2&gt;

&lt;p&gt;Initially I thought yes, but then as I thought about it, I realized there is a workaround. That is create a generic Recomposable&amp;lt;T&amp;gt; which itself has an import of T that is recomposable. The class is so simple, it’s not even funny, and here it is.&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Export]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; Recomposable&amp;lt;T&amp;gt;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;{&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    [Import(AllowRecomposition=&lt;span style="color:#0000ff;"&gt;true&lt;/span&gt;)]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; T Value { get; &lt;span style="color:#0000ff;"&gt;private&lt;/span&gt; set; }&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;}&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Now you can do&amp;#160; an import such as the following:&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    [Export]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; UsesLogger&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;        [ImportingConstructor]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;        &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; UsesLogger(Recomposable&amp;lt;ILogger&amp;gt; logger)&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;        {&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;            _recompLogger = logger;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;        }&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;        &lt;span style="color:#0000ff;"&gt;private&lt;/span&gt; Recomposable&amp;lt;ILogger&amp;gt; _recompLogger;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&amp;#160;&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;        &lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; ILogger Logger { get { &lt;span style="color:#0000ff;"&gt;return&lt;/span&gt; _recompLogger.Value; } }&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;    }&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;The logger in UsesLogger is now recomposable. &lt;/p&gt;

&lt;p&gt;Now there is one caveat. Because MEF does not support open generics (see this &lt;a href="http://mef.codeplex.com/Thread/View.aspx?ThreadId=50504"&gt;thread&lt;/a&gt; for more on that), you need to either create closed versions of Recomposable&amp;lt;T&amp;gt; which export the correct contract and have them discovered in a catalog:&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;[Export(&lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt;(Recomposable&amp;lt;ILogger))]&lt;/pre&gt;


    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;&lt;span style="color:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="color:#0000ff;"&gt;class&lt;/span&gt; RecomposableLogger : Recomposable&amp;lt;ILogger&amp;gt; {}&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Or you need to use a TypeCatalog and manually add each type that you want to be able to import:&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:#f4f4f4;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style:none;text-align:left;padding-bottom:0px;line-height:12pt;border-right-style:none;background-color:white;margin:0em;padding-left:0px;width:100%;padding-right:0px;font-family:&amp;#39;Courier New&amp;#39;, courier, monospace;direction:ltr;border-top-style:none;color:black;font-size:8pt;border-left-style:none;overflow:visible;padding-top:0px;"&gt;var catalog = &lt;span style="color:#0000ff;"&gt;new&lt;/span&gt; TypeCatalog(&lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt; (UsesLogger), &lt;span style="color:#0000ff;"&gt;typeof&lt;/span&gt; (Recomposable&amp;lt;ILogger&amp;gt;));&lt;/pre&gt;
&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;The first approach is what extenders need to do if they were introducing new types that the main app does not now about.&lt;/p&gt;

&lt;h2&gt;With great power comes responsibility, proceed with caution!&lt;/h2&gt;

&lt;p&gt;Some of you might be rolling your eyes at this post and thinking, does he expect me to believe that this will just automagically work? And the answer is……NO!&lt;/p&gt;

&lt;p&gt;Recomposition does not come for free. I mean you can turn it on for free, but you have to design for it. When we recompose, we completely replace the property reference. There is no inherent thread-safety in this, it just happens (if you opt-in), and you need to prepare for it, and design with recomposition in mind. This means very carefully deciding where to use recomposition, and making sure where it is used, the proper safeguards are put in place. And that could probably be a whole other post.&lt;/p&gt;

&lt;h2&gt;See it in action&lt;/h2&gt;

&lt;p&gt;For a sample of recomposition with an overriding logger, see this &lt;a href="http://pastebin.com/f923b3b"&gt;sample code&lt;/a&gt;.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=189559" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/recomposition/default.aspx">recomposition</category></item><item><title>Very colorful comments about Prism 2</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/03/15/very-colorful-comments-about-prism-2.aspx</link><pubDate>Mon, 16 Mar 2009 00:04:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:189317</guid><dc:creator>Glenn Block</dc:creator><slash:comments>16</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=189317</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/03/15/very-colorful-comments-about-prism-2.aspx#comments</comments><description>&lt;p&gt;This is a response to a&amp;nbsp;quite colorful rant I received in email from Steve regarding a&amp;nbsp; &lt;a href="http://codebetter.com/blogs/glenn.block/archive/2008/03/25/prism-drop-2.aspx#189298"&gt;Prism&lt;/a&gt; 2 post I did a while ago. I was so impressed by the literary quality of the piece that I thought it only fitting to publish.&lt;/p&gt;
&lt;p&gt;The cleaned up version goes like this:&lt;/p&gt;
&lt;p&gt;“ SO YOU ARE SAYING YOU TOOK AWAY THING THAT WERE IN THE OLD PRISM AND ADDED NEW THINGS IN THE NEW PRISM. SO WHATEVER I LEARN AND USED IN THE OLD PRISM I NOW HAVE TO FORGET AND GO BACK AND CHANGE FOR THE NEW STUFF. WELL HERE IS MY COMMENT TO YOU&lt;/p&gt;
&lt;p&gt;F@%$ YOU SOB M#&amp;amp;$*R FU#$#R&lt;/p&gt;
&lt;p&gt;JUST LIKE MISCROSOFT CREATE ONE THING SAY IT IS GREAT AND THEN CHANGE TO WHOLE DAMN THING&lt;/p&gt;
&lt;p&gt;OH YEA ONE MORE THING YOUR MAMA IS A CHIMP”&lt;/p&gt;
&lt;p&gt;Aside from the fact that the writing is a true masterpiece, I do have to point out that all the information is wrong.&lt;/p&gt;
&lt;p&gt;First: Prism 2 internals changed but the outward impact to authors of existing Prism apps was minimal. The reason for the change was to allow full parity between Silverlight and WPF, which is something customers asked for, thus allowing you to recompile your Views and such to work in either platform. I am guessing you never actually looked at Prism to know whether that was the case.&lt;/p&gt;
&lt;p&gt;I also am guessing you have no familiarity with actually how p&amp;amp;p works. For development of guidance like Prism 2, there is a customer advisory board heavily involved with the process and that would have screamed bloody murder had the decision been to completely break existing customers! &lt;/p&gt;
&lt;p&gt;Second: I know for a fact that my mom is not a chimp.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Steve&lt;/strong&gt;, please check your facts. Other than that keep up the good work. I think you have great writing potential!&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=189317" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/prism/default.aspx">prism</category></item><item><title>ALT.NET Seattle Day 1 reflection – Learn, Share, Grow</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/02/28/alt-net-seattle-day-1-reflection-learn-share-grow.aspx</link><pubDate>Sat, 28 Feb 2009 18:38:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:188755</guid><dc:creator>Glenn Block</dc:creator><slash:comments>1</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=188755</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/02/28/alt-net-seattle-day-1-reflection-learn-share-grow.aspx#comments</comments><description>&lt;p&gt;I am sitting here at the opening of ALT.NET Seattle. I look around and see the words &amp;quot;Learn, Share, Grow” on a poster, words I first wrote on the &lt;a href="http://altnetseattle.pbwiki.com/"&gt;ALT.NET wiki&lt;/a&gt; about two months ago. At the time when I wrote it, I sat back and thought to myself “What is ALT.NET about?”. I had a flurry of thoughts, some positive, and some negative. &lt;/p&gt;
&lt;p&gt;At the end of the day I boiled it all down to three fundamentals.&amp;nbsp; ALT.NET is about learning from others, sharing experiences and growing in the process. Now you may think this sounds all peachy clean and blue sky. Learning and sharing, &lt;strong&gt;doesn’t&lt;/strong&gt; mean we always agree and are on the same page. It &lt;strong&gt;doesn’t&lt;/strong&gt; mean we won’t get frustrated with each other about not getting across our viewpoints, or that our ideas are not being accepted, &lt;strong&gt;we will. &lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;What it means is that we recognize the value of the sum total of our experiences. We recognize that we all have something to give, and to take.&amp;nbsp; Benefitting, &lt;strong&gt;doesn’t &lt;/strong&gt;come for free, but the cost is a worthy investment.&lt;/p&gt;
&lt;p&gt;OK, I am ready to make mine. How about you?&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=188755" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/ALT.NET+Seattle/default.aspx">ALT.NET Seattle</category></item><item><title>Event Aggregation with MEF (with and without EventAggregator)</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/02/23/event-aggregation-with-mef-with-and-without-eventaggregator.aspx</link><pubDate>Mon, 23 Feb 2009 09:24:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:188605</guid><dc:creator>Glenn Block</dc:creator><slash:comments>8</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=188605</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/02/23/event-aggregation-with-mef-with-and-without-eventaggregator.aspx#comments</comments><description>&lt;p&gt;The title probably sounds like an oxymoron, but it is not. Recently there was a question on our CodePlex &lt;a href="http://www.codeplex.com/MEF/Thread/View.aspx?ThreadId=47468"&gt;forums&lt;/a&gt; from &lt;a href="http://denisvuyka.wordpress.com/"&gt;Denis Vuyka&lt;/a&gt; about whether or not MEF supports anything like EventBroker for pub/sub type communication. Asking such a question makes a lot of sense, as if you are building open-ended systems of extensions, you will run into cases where you need a loosely coupled way to communicate between the parts. For example you might have a dynamically populated navigation bar. like the one in Outlook, where you publish an event to indicate the item selection. The individual subsystems (contacts, mail, etc) all subscribe to that event to receive notifications.&lt;/p&gt;
&lt;p&gt;In as much as it make sense, we don’t currently have a specific facility for this, mostly due to the fact that we had bigger fish to fry. However using p&amp;amp;p’s EventAggregator for &lt;a href="http://www.microsoft.com/compositewpf"&gt;Prism&lt;/a&gt; is a great option. Of course I am biased, as I came from the Prism project before joining the MEF team. EventAggregator is a very simple service that allows writing up publishers and subscribers in a loosely coupled way. It also provides benefits over events in that it is delegate based and supports a weak delegate notion, thus allowing subscribers to not be held-alive by the publisher. Additionally EventAggregator supports providing lambda predicates for subscription, thus allowing subscribers to conditionally handle the notification based on custom filters against the payload. Finally it is thread safe, and can marshall between threads through using overloads on the event Subscribe() method. The EventAggregator also doesn’t have any real dependencies on Prism itself. Because it is so simple, it is very easy to integrate with MEF, thus allowing MEF parts to benefit from it’s capabilities. Sure enough, Denis went and wired up EA to MEF without a hitch, which he posted about &lt;a href="http://denisvuyka.wordpress.com/2009/02/21/using-eventaggregator-with-mef/"&gt;here&lt;/a&gt;.&amp;nbsp; Nice job Denis!&lt;/p&gt;
&lt;h1&gt;Event Aggregation without EventAggregator&lt;/h1&gt;
&lt;p&gt;Around the same time that Denis was looking at EventAggregator I started thinking about the problem as it relates to MEF. The question I kept toying with was did we really need EventAggregator at all, or could we simply remove it, and instead just expose the events directly? After a bit of chatting and pairing with &lt;a class="" href="http://blogs.southworks.net/jdominguez/"&gt;Julian Dominguez&lt;/a&gt; my former mate from patterns &amp;amp; practices, we realized we actually could. Instead of adding EventAggregator to the container at all, you can simply add Prism events as exports through a catalog which is passed to the container. Once you do, Publisher and Subscriber can easily import the event and access it in a similar fashion. Below are the steps you need to follow, and for which the code is in the attached zip (along with unit tests)&lt;/p&gt;
&lt;h2&gt;Creating the Event&lt;/h2&gt;
&lt;p&gt;First create your custom event class by deriving from CompositePresentationEvent and passing your custom args class. Add an Export to the event, and mark it as a shared CreationPolicy, this way all publishers / consumers share the same event instance. For example below I defined a CustomCompositionEvent.&lt;/p&gt;
&lt;div&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;[Export]
[CompositionOptions(CreationPolicy = CreationPolicy.Shared)]
&lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;class&lt;/span&gt; CustomCompositionEvent : CompositePresentationEvent&amp;lt;CustomArgs&amp;gt; {}

&lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;class&lt;/span&gt; CustomArgs{}&lt;/pre&gt;&lt;/div&gt;
&lt;h2&gt;&amp;nbsp;&lt;/h2&gt;
&lt;h2&gt;Registering&lt;/h2&gt;
&lt;p&gt;Next register the event in a catalog. You can use any catalog of your choice, in this case because I am in a unit-test (really an acceptance test as I am just using MEF), I registered manually with a TypeCatalog in a Setup() method. However in a real app, you would probably use a Directory / Assembly catalog.&lt;/p&gt;
&lt;div&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;&lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;void&lt;/span&gt; Setup()
{
    var catalog = &lt;span style="COLOR:#0000ff;"&gt;new&lt;/span&gt; TypeCatalog(&lt;span style="COLOR:#0000ff;"&gt;typeof&lt;/span&gt; (Subscriber), &lt;span style="COLOR:#0000ff;"&gt;typeof&lt;/span&gt; (Publisher), &lt;span style="COLOR:#0000ff;"&gt;typeof&lt;/span&gt;(CustomCompositionEvent));
    _container = &lt;span style="COLOR:#0000ff;"&gt;new&lt;/span&gt; CompositionContainer(catalog);
}&lt;/pre&gt;&lt;/div&gt;
&lt;h2&gt;Subscribing / Publishing&lt;/h2&gt;
&lt;p&gt;Once you have registered the event, you can easily import it into any of your parts. Below are my fake publisher and subscriber that I am using for my tests.&lt;/p&gt;
&lt;div&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;&amp;nbsp; [Export]
  &lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;class&lt;/span&gt; Publisher
  {
      [Import]
      &lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; CustomCompositionEvent CustomCompositionEvent { get; set; }
  }

  [Export]
  &lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;class&lt;/span&gt; Subscriber
  {
      [Import]
      &lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; CustomCompositionEvent CustomCompositionEvent { get; set; }
  }&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;To subscribe, call the Subscribe() method on the event, passing in a lambda for the subscriber method. To publish, call the Publish() method on the event and pass the args. See the p&amp;amp;p &lt;a href="http://msdn.microsoft.com/en-us/library/dd458915.aspx"&gt;documentation&lt;/a&gt; for more on the params available to both methods. &lt;/p&gt;
&lt;p&gt;Both can be seen below in my acceptance test.&lt;/p&gt;
&lt;div&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;[TestMethod]
&lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;void&lt;/span&gt; When_event_is_fired_subscriber_gets_notified()
{
    Setup();
    &lt;span style="COLOR:#0000ff;"&gt;bool&lt;/span&gt; eventRaised = &lt;span style="COLOR:#0000ff;"&gt;false&lt;/span&gt;;
    var subscriber = _container.GetExportedObject&amp;lt;Subscriber&amp;gt;();
    var customEvent = _container.GetExportedObject&amp;lt;CustomCompositionEvent&amp;gt;();
    subscriber.CustomCompositionEvent.Subscribe(a =&amp;gt; eventRaised = &lt;span style="COLOR:#0000ff;"&gt;true&lt;/span&gt;);
    customEvent.Publish(&lt;span style="COLOR:#0000ff;"&gt;null&lt;/span&gt;);
    Assert.IsTrue(eventRaised);
}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;In the code above, I am grabbing a Subscriber instance from the container, which imports the event. I am then grabbing the event directly. I could have actually used the instance of the event that was on the subscriber, but that might look confusing in code, so for clarity, I imported it again directly. This also drives home why it needs to be shared. Next the subscriber subscribes to the event. In this case in my unit test, I am simply setting a boolean when the event is raised, so I can verify it in the test. Finally i am calling publish. In live code, you would probably have the part wire itself up to subscribe in the property setter.&lt;/p&gt;
&lt;h2&gt;Conclusion&lt;/h2&gt;
&lt;p&gt;Prism’s EventAggregator infrastructure provides a great way to facilitate loosely coupled communication between parts in your MEF app. You can either use the EventAggregator itself in the container, or you can import CompositePresentationEvents directly. Either approach works well.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=188605" width="1" height="1"&gt;</description><enclosure url="http://codebetter.com" length="530046" type="application/x-zip-compressed" /><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/Composite+WPF/default.aspx">Composite WPF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/prism/default.aspx">prism</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/com/default.aspx">com</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/event+aggregator/default.aspx">event aggregator</category></item><item><title>CommonServiceLocator for MEF, a service is a service.</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/02/09/commonservicelocator-for-mef-a-service-is-a-service.aspx</link><pubDate>Mon, 09 Feb 2009 10:20:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:188213</guid><dc:creator>Glenn Block</dc:creator><slash:comments>7</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=188213</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/02/09/commonservicelocator-for-mef-a-service-is-a-service.aspx#comments</comments><description>&lt;p&gt;Today, I finally got around to uploading a CommonServiceLocator &lt;a href="http://tinyurl.com/mefcsl"&gt;adapter&lt;/a&gt; for MEF. &lt;/p&gt;
&lt;p&gt;The code is actually quite simple thanks to &lt;a href="http://www.tavaresstudios.com/Blog/"&gt;Chris Tavares&lt;/a&gt; providing ServiceLocatorImplBase &lt;strong&gt;(Updated thanks for feedback from a bunch of folks)&lt;/strong&gt;&lt;/p&gt;
&lt;div style="BORDER-RIGHT:gray 1px solid;PADDING-RIGHT:4px;BORDER-TOP:gray 1px solid;PADDING-LEFT:4px;FONT-SIZE:8pt;PADDING-BOTTOM:4px;MARGIN:20px 0px 10px;OVERFLOW:auto;BORDER-LEFT:gray 1px solid;WIDTH:87.79%;CURSOR:text;MAX-HEIGHT:200px;LINE-HEIGHT:12pt;PADDING-TOP:4px;BORDER-BOTTOM:gray 1px solid;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;HEIGHT:210px;BACKGROUND-COLOR:#f4f4f4;"&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;&lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;class&lt;/span&gt; MefServiceLocator : ServiceLocatorImplBase
{
    &lt;span style="COLOR:#0000ff;"&gt;private&lt;/span&gt; ExportProvider _provider;

    &lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; MefServiceLocator(ExportProvider provider)
    {
        _provider = provider;
    }

    &lt;span style="COLOR:#0000ff;"&gt;protected&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;override&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;object&lt;/span&gt; DoGetInstance(Type serviceType, &lt;span style="COLOR:#0000ff;"&gt;string&lt;/span&gt; key)
    {
        IEnumerable&amp;lt;Export&amp;lt;&lt;span style="COLOR:#0000ff;"&gt;object&lt;/span&gt;&amp;gt;&amp;gt; exports;
        &lt;span style="COLOR:#0000ff;"&gt;string&lt;/span&gt; contract = CompositionServices.GetContractName(serviceType);
        exports = key == &lt;span style="COLOR:#0000ff;"&gt;null&lt;/span&gt; ? _provider.GetExports&amp;lt;&lt;span style="COLOR:#0000ff;"&gt;object&lt;/span&gt;&amp;gt;(contract) : _provider.GetExports&amp;lt;&lt;span style="COLOR:#0000ff;"&gt;object&lt;/span&gt;&amp;gt;(key);

        &lt;span style="COLOR:#0000ff;"&gt;if&lt;/span&gt; (exports.Any())
            &lt;span style="COLOR:#0000ff;"&gt;return&lt;/span&gt; exports.First().GetExportedObject();
        
        &lt;span style="COLOR:#0000ff;"&gt;throw&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;new&lt;/span&gt; ActivationException(&lt;span style="COLOR:#0000ff;"&gt;string&lt;/span&gt;.Format(&lt;span style="COLOR:#006080;"&gt;&amp;quot;Could not locate any instances of contract {0}&amp;quot;&lt;/span&gt;, key));

    }

    &lt;span style="COLOR:#0000ff;"&gt;protected&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;override&lt;/span&gt; IEnumerable&amp;lt;&lt;span style="COLOR:#0000ff;"&gt;object&lt;/span&gt;&amp;gt; DoGetAllInstances(Type serviceType)
    {
        var exports = _provider.GetExportedObjects&amp;lt;&lt;span style="COLOR:#0000ff;"&gt;object&lt;/span&gt;&amp;gt;(CompositionServices.GetContractName(serviceType));
        &lt;span style="COLOR:#0000ff;"&gt;return&lt;/span&gt; exports;
    }
}&lt;/pre&gt;&lt;/div&gt;
&lt;p&gt;One thing you’ll notice is that in DoGetInstance, I am calling to GetExports and then manufacturing only the first export that I return. The reasoning for this is that MEF doesn’t have an internal notion of default. If I call GetExportedObject and more than one is returned, it will blow up with a composition exception. The reason is because we have no way of knowing which is the default as we simply grab parts from catalogs (In Preview 3 we actually provided a way to assign defaults through usage of Export Providers however that’s another story for another overdue post :-) ). So instead of calling for a single, I call for multiple which will succeed in all cases.&lt;/p&gt;
&lt;p&gt;To make the adapter satisfy the needs of the interface, I decided to apply &lt;a href="http://blogs.msdn.com/kcwalina"&gt;Krysztof’s&lt;/a&gt; rule of thumb which is to take the first one that is returned regardless, as he says, if I walk into a car dealership and say give me a Saab, I don’t care which. Calling for an export instead of an exported object allows me to only instantiate (and load if I am caching) the one that is being returned.&lt;/p&gt;
&lt;p&gt;Another thing you will notice is that i am passing object for the type as DoGetInstance only passes a type. The methods for retrieval on MEF’s Export Provider all allow you to pass object as the type, thus allowing me to do what I need to do.&lt;/p&gt;
&lt;p&gt;Finally you’ll notice that I have passed in an ExportProvider to the constructor rather than a container. MEF’s composition container is an ExportProvider. ExportProviders are simply for retrieving exports, which matches very well with ISL’s needs and makes it a good fit.&lt;/p&gt;
&lt;p&gt;You can download it &lt;a href="http://tinyurl.com/mefcsl"&gt;here&lt;/a&gt; along with unit tests. Thanks to &lt;a href="http://devlicio.us/blogs/rob_eisenberg/archive/2009/02/05/a-mef-misunderstanding.aspx"&gt;Rob Eisenberg&lt;/a&gt; for the initiative which encouraged me to actually get it done. &lt;/p&gt;
&lt;h2&gt;Onto CommonServiceLocator itself…and MEF usage&lt;/h2&gt;
&lt;p&gt;A while ago , I posted about the new &lt;a href="http://www.codeplex.com/commonservicelocator"&gt;CommonServiceLocator&lt;/a&gt; library (and IServiceLocator interface) a bunch of us co-designed and p&amp;amp;p developed. The purpose of this library was to allow applications to use a standard interface for accessing services without being bound to a specific service provider / container. &lt;/p&gt;
&lt;p&gt;Once the library launched on CodePlex it caused a healthy amt of debate. Plenty of folks were wondering “Why Service Locator?”. Was this an encouragement to throw away DI containers, and take a trip back in time to the good old days of the Service Locator pattern?&amp;nbsp; Was this the one abstraction to rule them all?&lt;/p&gt;
&lt;p&gt;The answer on both accounts was no. In terms of the first question, the primary place where we thought CSL would be used was for actually accessing a DI container.&amp;nbsp; That being said, nothing on the interface had anything particularly DI-ish about it. Instead it simply contained interfaces for querying for a service. Now, the thing that provides the service which sits behind the interface might very well be an IoC container which constructs components and&amp;nbsp; performs dependency injection. However, there is &lt;em&gt;nothing &lt;/em&gt;about the interface that enforces that so we felt we were staying true to the api itself.&amp;nbsp; Furthermore when you access an IoC container and call a Resolve / Get method you ARE performing Service Location. As I like to say, ServiceLocator is the Gateway to an IoC container.&lt;/p&gt;
&lt;p&gt;Additionally, wee did not intend IServiceLocator&amp;nbsp; calls to be scattered throughout the application thereby creating a ton of static dependencies. Instead, the intent was that ISL should be used minimally at the root of an application to compose a root graph, or low-level in framework libraries that were reused across applications.&lt;/p&gt;
&lt;p&gt;Now on to the second question. IServiceLocator does one thing, resolve services. We deliberately kept the interface focused around the common set of functionality that service locator’s provide. We kept out anything that was container specific, and also kept away from anything other than retrieval. The reasoning for this was so that this interface did not become some uber generic abstraction with a lot of leaky abstractions. Instead we kept short and sweet and focused on a single concern, resolving.&lt;/p&gt;
&lt;p&gt;So that leads to MEF. Why should one want to use ISL with MEF? Quite simply because in the same way that IoC containers can provide services, MEF also provides services. How it find them and how they are created is quite different, but in the end a service is a service.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=188213" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/Common+Service+Locator/default.aspx">Common Service Locator</category></item><item><title>Managed Extensibility Framework Preview 4, a grab bag of goodies.</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/01/28/managed-extensibility-framework-preview-4-a-grab-bag-of-goodies.aspx</link><pubDate>Thu, 29 Jan 2009 06:18:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:187854</guid><dc:creator>Glenn Block</dc:creator><slash:comments>4</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=187854</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/01/28/managed-extensibility-framework-preview-4-a-grab-bag-of-goodies.aspx#comments</comments><description>&lt;p&gt;If you haven’t seen &lt;a href="http://blogs.msdn.com/kcwalina/archive/2009/01/27/MEF4.aspx"&gt;Krys&lt;/a&gt; and &lt;a href="http://davesbox.com/archive/2009/01/27/new-managed-extensibility-framework-drop.aspx"&gt;David’s&lt;/a&gt; announcement,&amp;nbsp; we just released another drop of MEF (I need to hold myself from breaking out in hysterics when I say that ) on &lt;a href="http://www.codeplex.com/MEF"&gt;CodePlex&lt;/a&gt;. &lt;/p&gt;
&lt;p&gt;This release contains a whole grab bag of goodies, some of which may initially taste like sour candies (breaking changes), but are sweet in the middle. Most importantly, we’ve done a significant set of enhancements to the MEF codebase around Lifetime, Diagnostics, and Debugging.&lt;/p&gt;
&lt;h1&gt;Summary of the breaking changes:&lt;/h1&gt;
&lt;ul&gt;
&lt;li&gt;AllowNonPublicCompositionAttribute was removed. It is no longer needed MEF will always look at publics and non-publics. &lt;/li&gt;
&lt;li&gt;ComposablePartCatalog was moved from System.ComponentModel.Composition to System.ComponentModel.Compositioni.Primitives. &lt;/li&gt;
&lt;li&gt;AttributedTypesPartCatalog was renamed to TypeCatalog &lt;/li&gt;
&lt;li&gt;AttributedAssemblyPartCatalog was renamed to AssemblyCatalog &lt;/li&gt;
&lt;li&gt;DirectoryPartCatalog was renamed to DirectoryCatalog &lt;/li&gt;
&lt;li&gt;AggregatingComposablePartCatalog was renamed to AggregateCatalog &lt;/li&gt;
&lt;li&gt;Catalog Caching extensibility API’s have been made internal. &lt;/li&gt;
&lt;li&gt;Mutability APIs on the container have been changed to accept a batch. AddPart and RemovePart methods were removed from the container, and you know must pass a &lt;a href="http://www.codeplex.com/MEF/Wiki/View.aspx?title=Composition%20Batch&amp;amp;referringTitle=Guide"&gt;CompositionBatch&lt;/a&gt;. The advantage of the batch is that you can now replace a single part in the container with a new part in a single operation. You can also add or remove multiple parts in a single operation. This comes in very handy when you have parts that are recomposing. &lt;/li&gt;&lt;/ul&gt;
&lt;h1&gt;New features:&lt;/h1&gt;
&lt;p&gt;&lt;strong&gt;New wiki pages&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;We’ve (well really &lt;a href="http://hammett.castleproject.org/"&gt;Hammett&lt;/a&gt;) fleshed out all the TBD topics, plus added a ton of new ones both in our programming guide and the arch section. &lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Diagnostics and debugging&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Since joining the team once thing that I’ve heard over and over is just how bad our debugging experience was. Not only did i hear it…I experience it first hand, some times live on stage :-) Well fortunately &lt;a href="http://blogs.msdn.com/nblumhardt"&gt;Nick&lt;/a&gt; and his feature crew (David and Jad/Zhen) spent the last several months focused on&amp;nbsp;righting this wrong.&lt;/p&gt;
&lt;p&gt;&lt;b&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p&gt;We’ve made significant improvements in the debugging experience to address some problematic scenarios and deliver a foundation for diagnostics in all MEF features and extensions.&lt;/p&gt;
&lt;p&gt;The differences to note are:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Multiple composition errors are structured in numbered groups each relating to a single root cause &lt;/li&gt;
&lt;li&gt;The ‘causal chain’ (Resulting in: …) traces an issue all the way back to the root action that the application was trying to perform &lt;/li&gt;
&lt;li&gt;The ‘origin path’ (Element: …) describes how each object involved in the scenario came to be in the composition in the first place &lt;/li&gt;
&lt;li&gt;All of this information can be retrieved programmatically from the exception types if necessary &lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;Another difference will be the visualization of exceptions when they occur.&lt;/p&gt;
&lt;p&gt;Previously you would see something like the following, which was difficult to navigate.&lt;/p&gt;
&lt;p&gt;&lt;a href="http://codebetter.com/blogs/glenn.block/clip_image002_36826589.jpg"&gt;&lt;img title="clip_image002" style="BORDER-TOP-WIDTH:0px;DISPLAY:inline;BORDER-LEFT-WIDTH:0px;BORDER-BOTTOM-WIDTH:0px;BORDER-RIGHT-WIDTH:0px;" height="308" alt="clip_image002" src="http://codebetter.com/blogs/glenn.block/clip_image002_thumb_5B9FAFF5.jpg" width="668" border="0" /&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;With the changes, you will now see.&lt;/p&gt;
&lt;p&gt;&lt;a href="http://codebetter.com/blogs/glenn.block/clip_image004_7356E75B.jpg"&gt;&lt;img title="clip_image004" style="BORDER-TOP-WIDTH:0px;DISPLAY:inline;BORDER-LEFT-WIDTH:0px;BORDER-BOTTOM-WIDTH:0px;BORDER-RIGHT-WIDTH:0px;" height="203" alt="clip_image004" src="http://codebetter.com/blogs/glenn.block/clip_image004_thumb_79318AF4.jpg" width="692" border="0" /&gt;&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&lt;b&gt;Lifetime Management and Creation Policy&lt;/b&gt;&lt;/p&gt;
&lt;p&gt;Another concern we heard from customers was around how MEF handles lifetime management for parts. In previous releases we allowed the exporter to declare that a part has either a singleton or factory (transient) lifetime. &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;If a transient part implemented IDisposable, it’s resources would be released only when the container was disposed. Singletons would also be disposed in a similar manner. This forces transient parts which could container scarce resources to stay alive. For example if a part contains an unmanaged resource such as a database connection, it will stay open and not get recycled.&amp;nbsp; This is particularly problematic in server environments such as ASP.NET, where you have a limited number of resources shared by many active sessions. Not having the connections recycled could lead to starvation. &lt;/li&gt;
&lt;li&gt;Another challenge of the previous approach was that the Part had to determine its lifetime policy. As parts are reusable across different apps, it is very likely that a part in one app is a singleton, while in another it needs to be transient. In the same app there are even cases where the same part needs to be transient in one case and singleton in another. In our previous bits, there was no way to address this. &lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;Hammett and team (&lt;a href="http://weblogs.asp.net/whaggard/"&gt;Wes&lt;/a&gt;, Daniel) have been working tirelessly to come up with a solution to this one. Hammett personally was no stranger to this problem from all the work he’s done on the castle stack. Upon joining the team this is one area that he was relentless about finding a solution to. I am thankful for his passion to see this through as there were several times we hit road blocks that seemed insurmountable.&lt;/p&gt;
&lt;p&gt;In the new bits we have provided solutions to both of these problems.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;We’ve renamed Singleton and Factory creation policy to Shared / NonShared. &lt;/li&gt;
&lt;li&gt;Parts and Imports can now both declare creation policy. We’ve also added a new policy called Any, which allows a Part or an Import declare that it can work with either policy, i.e. a Part could have a policy of Any, where one&amp;nbsp; importer of the part’s exports has a policy of NonShared, while another importer has a policy of Shared. The grid below indicates the behavior in different scenarios. &lt;/li&gt;&lt;/ul&gt;
&lt;table class="" cellspacing="0" cellpadding="0"&gt;

&lt;tr&gt;
&lt;td class=""&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;&lt;b&gt;Part.Any&lt;/b&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;&lt;b&gt;Part.Shared&lt;/b&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;&lt;b&gt;Part.NonShared&lt;/b&gt;&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;
&lt;td class=""&gt;
&lt;p&gt;&lt;b&gt;Import.Any&lt;/b&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;Shared&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;Shared&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;Non Shared&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;
&lt;td class=""&gt;
&lt;p&gt;&lt;b&gt;Import.Shared&lt;/b&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;Shared&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;Shared&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;No match&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;
&lt;td class=""&gt;
&lt;p&gt;&lt;b&gt;Import.NonShared&lt;/b&gt;&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;Non Shared&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;No match&lt;/p&gt;&lt;/td&gt;
&lt;td class=""&gt;
&lt;p&gt;Non Shared&lt;/p&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;
&lt;p&gt;An importer specifies the required policy through the use of the new RequiredCreationPolicy as can be seen below.&lt;/p&gt;
&lt;div style="BORDER-RIGHT:gray 1px solid;PADDING-RIGHT:4px;BORDER-TOP:gray 1px solid;PADDING-LEFT:4px;FONT-SIZE:8pt;PADDING-BOTTOM:4px;MARGIN:20px 0px 10px;OVERFLOW:auto;BORDER-LEFT:gray 1px solid;WIDTH:97.5%;CURSOR:text;MAX-HEIGHT:200px;LINE-HEIGHT:12pt;PADDING-TOP:4px;BORDER-BOTTOM:gray 1px solid;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BACKGROUND-COLOR:#f4f4f4;"&gt;
&lt;div style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:white;BORDER-BOTTOM-STYLE:none;"&gt;[Export]&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;&lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; &lt;span style="COLOR:#0000ff;"&gt;class&lt;/span&gt; Window : System.Windows.Forms.Form&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:white;BORDER-BOTTOM-STYLE:none;"&gt;{&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;    [Import(RequiredCreationPolicy = CreationPolicy.NonShared)]&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:white;BORDER-BOTTOM-STYLE:none;"&gt;    &lt;span style="COLOR:#0000ff;"&gt;public&lt;/span&gt; ExportCollection&amp;lt;IShape&amp;gt; Shapes { get; set; }&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;    ...&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:white;BORDER-BOTTOM-STYLE:none;"&gt;}&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;&amp;nbsp;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;Parts can now be explicitly released from the container by using the &lt;b&gt;Container.ReleaseExport&lt;/b&gt; method. This method takes the export and traverses all its references that are non-shared and disposes of them if they implement IDisposable. This prevents what we call viral disposability where every part in the chain must implement IDisposable in order for the deepest child to be disposed. This is an extremely difficult problem for you to manage, and without this feature the likelihood of memory leaks is high. &lt;/li&gt;&lt;/ul&gt;
&lt;blockquote&gt;
&lt;p&gt;For example, below you can see where the jobExport is explicitly released from the container.&lt;/p&gt;&lt;/blockquote&gt;
&lt;div style="BORDER-RIGHT:gray 1px solid;PADDING-RIGHT:4px;BORDER-TOP:gray 1px solid;PADDING-LEFT:4px;FONT-SIZE:8pt;PADDING-BOTTOM:4px;MARGIN:20px 0px 10px;OVERFLOW:auto;BORDER-LEFT:gray 1px solid;WIDTH:97.5%;CURSOR:text;MAX-HEIGHT:200px;LINE-HEIGHT:12pt;PADDING-TOP:4px;BORDER-BOTTOM:gray 1px solid;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BACKGROUND-COLOR:#f4f4f4;"&gt;
&lt;div style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:white;BORDER-BOTTOM-STYLE:none;"&gt;var container = &lt;span style="COLOR:#0000ff;"&gt;new&lt;/span&gt; CompositionContainer(...);&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;var jobExports = container.GetExports&amp;lt;IJob&amp;gt;();&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:white;BORDER-BOTTOM-STYLE:none;"&gt;&lt;span style="COLOR:#0000ff;"&gt;foreach&lt;/span&gt;(var jobExport &lt;span style="COLOR:#0000ff;"&gt;in&lt;/span&gt; jobExports)&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;{&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:white;BORDER-BOTTOM-STYLE:none;"&gt;     var jobProcessor = jobExport.GetExportedObject();&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;     jobProcess.Process();&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:white;BORDER-BOTTOM-STYLE:none;"&gt;     container.ReleaseExport(jobExport);&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:#f4f4f4;BORDER-BOTTOM-STYLE:none;"&gt;}&lt;/pre&gt;&lt;pre style="PADDING-RIGHT:0px;PADDING-LEFT:0px;FONT-SIZE:8pt;PADDING-BOTTOM:0px;MARGIN:0em;OVERFLOW:visible;WIDTH:100%;COLOR:black;BORDER-TOP-STYLE:none;LINE-HEIGHT:12pt;PADDING-TOP:0px;FONT-FAMILY:consolas, &amp;#39;Courier New&amp;#39;, courier, monospace;BORDER-RIGHT-STYLE:none;BORDER-LEFT-STYLE:none;BACKGROUND-COLOR:white;BORDER-BOTTOM-STYLE:none;"&gt;&amp;nbsp;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;A Non-shared part that has a recomposable import will be held conditionally based on the lifetime of its exports. If&amp;nbsp; the exports are gc’d the part will be released as well. &lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;Be sure to check out the new wiki page on &lt;/strong&gt;&lt;a href="http://www.codeplex.com/MEF/Wiki/View.aspx?title=Parts%20Lifetime&amp;amp;referringTitle=Guide"&gt;Lifetime&lt;/a&gt;&lt;strong&gt; for a much more detailed explanation.&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;This should be the last release where we introduce major API changes. We’re getting into the home stretch now, with Beta 1 around the corner. There’s still time for us to make fixes though so please get your feedback in.&lt;/p&gt;
&lt;p&gt;Special thanks to &lt;a href="http://hammett.castleproject.org/"&gt;Hammett&lt;/a&gt; for making sure this release got out the door and for the wiki page work. Also thanks to &lt;a href="http://davesbox.com/Default.aspx"&gt;David&lt;/a&gt; and &lt;a href="http://blogs.msdn.com/dsplaisted/"&gt;Daniel&lt;/a&gt; for their supporting efforts on the site. And thanks to the whole team for the awesome work they are doing! Lastly thank to you for your feedback!&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=187854" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/MEF/default.aspx">MEF</category></item><item><title>ALT.NET Seattle 2009 is happening.</title><link>http://codebetter.com/blogs/glenn.block/archive/2009/01/02/alt-net-seattle-2009-is-happening.aspx</link><pubDate>Fri, 02 Jan 2009 09:49:00 GMT</pubDate><guid isPermaLink="false">d21fbbc9-c112-4f32-ad14-95939a2c53d4:186867</guid><dc:creator>Glenn Block</dc:creator><slash:comments>18</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://codebetter.com/blogs/glenn.block/rsscomments.aspx?PostID=186867</wfw:commentRss><comments>http://codebetter.com/blogs/glenn.block/archive/2009/01/02/alt-net-seattle-2009-is-happening.aspx#comments</comments><description>&lt;p&gt;If you attended ALT.NET Seattle least year, you might be wondering whether or not it&amp;#39;s happening this year.&lt;/p&gt;
&lt;p&gt;While at &lt;a href="http://www.kaizenconf.com/"&gt;Kaizenconf&lt;/a&gt;, a bunch of us wondered the same thing. &lt;a href="http://codebetter.com/blogs/david_laribee/"&gt;David Laribee&lt;/a&gt;, &lt;a href="http://twitter.com/cbilson"&gt;Chris Bilson&lt;/a&gt;, &lt;a href="http://twitter.com/kellyleahy"&gt;Kelly Leahy&lt;/a&gt; and I chatted about hosting another ALT.NET Seattle conference. David basically told us it was time to pass the reigns, if we wanted it to happen, &lt;strong&gt;we&lt;/strong&gt; had to make it happen. Well after returning from the conference, we started brainstorming on the idea at our local ALT.NET monthly open-space and thanks to a bunch of efforts from our local guys....&lt;/p&gt;
&lt;p&gt;I am excited to announce that we are actually going to host an ALT.NET Seattle conference this year. &lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;What: &lt;/strong&gt;&lt;a href="http://altnetseattle.pbwiki.com/"&gt;ALT.NET Seattle 2009.&lt;/a&gt; (The site is still being worked on. Thanks to &lt;a href="http://www.aboutjustin.com/"&gt;Justin Bozonier&lt;/a&gt; and &lt;a href="http://twitter.com/shoshanahb"&gt;Shoshanah Bain&lt;/a&gt; for getting the site up). &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Where: &lt;/strong&gt;&lt;a href="https://www.digipen.edu/"&gt;Digipen&lt;/a&gt; (thanks to &lt;a href="http://www.twitter.com/jefftucker"&gt;Jeff Tucker&lt;/a&gt; for lining up the space) &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;When:&lt;/strong&gt; Evening February 27th through March 1st. &lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Registration: &lt;/strong&gt;Opens this tuesday evening at 6PM PST. We&amp;#39;re holding on registration to allow the word to spread. There will be a max of 150 attendees. Check the &lt;a href="http://altnetseattle.pbwiki.com/"&gt;wiki&lt;/a&gt; on Tuesday for details. &lt;/li&gt;&lt;/ul&gt;
&lt;p&gt;If you&amp;#39;ve never been to an &lt;a href="http://en.wikipedia.org/wiki/Open-space_meeting"&gt;Open Space&lt;/a&gt; event all I can tell you is it will defy your expectations. This is not simply sitting in a room listening to speaker after speaker. This is an organic conversation that emerges based on an agenda that attendees put together on site. At open-space everyone is a speaker, and everyone is a listener. You just have to experience it.&lt;/p&gt;
&lt;p&gt;If you haven&amp;#39;t heard about &lt;a href="http://altdotnet.org/"&gt;ALT.NET&lt;/a&gt; or what you have heard is not appealing, let me tell you from first hand experience what it&amp;#39;s about. It&amp;#39;s about you. It&amp;#39;s about being&amp;nbsp; a better software developer. It&amp;#39;s about learning and sharing. It&amp;#39;s about&amp;nbsp; using all the tools (patterns, practices, frameworks, etc) at your disposal to get the job done. It&amp;#39;s about growing.&amp;nbsp; &lt;/p&gt;
&lt;p&gt;The event will be immediately before the MVP summit, rather than after.&amp;nbsp; We decided to do it earlier for several reasons. First several folks gave us feedback that having it after the MVP summit was tough due to being worn out from the week. Second as a lot of folks are traveling from a-far, having it after meant that we have to cut Sunday pretty short to allow for travel.&lt;/p&gt;
&lt;p&gt;Things will be a little different last year than this year.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;David and Scott are off the hook for organizing it :-) &lt;/li&gt;
&lt;li&gt;Two full days of sessions (preceeded by an evening kick-off on Friday) &lt;/li&gt;
&lt;li&gt;We&amp;#39;re opening the doors&amp;nbsp; on attendance, and severely limiting the reserved slots. We want the attendance to be as diverse as possible.&amp;nbsp; You don&amp;#39;t need a secret decoder ring to get in :-) &lt;/li&gt;
&lt;li&gt;Unfortunately &lt;a href="http://www.twitter.com/athought"&gt;Stephen List&lt;/a&gt; (Doc) won&amp;#39;t be facilitating as he has a conflict. We&amp;#39;re looking for a top-notch facilitator to fill his place. &lt;/li&gt;
&lt;li&gt;We&amp;#39;re looking into having some kind of evening coding challenge. The point here is to do something that&amp;#39;s fun and learn at the same time. &lt;/li&gt;
&lt;li&gt;We&amp;#39;re looking into telecasting some of the sessions over livemeeting for folks that can&amp;#39;t attend. &lt;/li&gt;&lt;/ol&gt;
&lt;p&gt;If you&amp;#39;ve been to previous ALT.NET events and have any suggestions, please let us know. &lt;/p&gt;
&lt;p&gt;We look forward to seeing you in Seattle (well technically Redmond) &amp;nbsp;the end of February!&lt;/p&gt;
&lt;p&gt;PS: We&amp;#39;re also looking for sponsors for the event who are willing to contribute financially. If your company is interested, contact &lt;a href="http://www.iamnotmyself.com/"&gt;Bobby Johnson&lt;/a&gt; who I am sure will be posting on this shortly.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://codebetter.com/aggbug.aspx?PostID=186867" width="1" height="1"&gt;</description><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/ALT.NET/default.aspx">ALT.NET</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/conference/default.aspx">conference</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/ALT.NET+Seattle/default.aspx">ALT.NET Seattle</category><category domain="http://codebetter.com/blogs/glenn.block/archive/tags/altnetseattle2009/default.aspx">altnetseattle2009</category></item></channel></rss>