MEF allows you to import multiple parts via the use of the ImportMany
attribute. How does it determine the order in which it retrieves the relevant exports and adds them to the enumerable you are populating? For example, how would I import multiple IRules that had to fire in a particular order? The only way I can think of is to have an OrderValue property in IRule and sort manually:
public class Engine
{
[ImportMany]
public IEnumerable<IRule> Rules { get; set; }
public void Run()
{
// ...
// Initialise MEF
// ...
//
// Do I need to manually order Rules here?
//
foreach (IRule rule in Rules)
{
// Must execute开发者_运维问答 in a specific order
rule.Execute();
}
}
}
By default MEF does not guarantee any order of the exports that get imported. However in MEF you can do some ordering by using some metadata and a custom collection. For example you can do something like:
public interface IRule { }
[Export(typeof(IRule))]
[ExportMetadata("Order", 1)]
public class Rule1 : IRule { }
[Export(typeof(IRule))]
[ExportMetadata("Order", 2)]
public class Rule2 : IRule { }
public interface IOrderMetadata
{
[DefaultValue(Int32.MaxValue)]
int Order { get; }
}
public class Engine
{
public Engine()
{
Rules = new OrderingCollection<IRule, IOrderMetadata>(
lazyRule => lazyRule.Metadata.Order);
}
[ImportMany]
public OrderingCollection<IRule, IOrderMetadata> Rules { get; set; }
}
Then you will have a set of rules that are ordered by the metadata. You can find the OrderingCollection sample at http://codepaste.net/ktdgoh.
The best way to achieve this ordering in MEF is to utilize our metadata facilities. You can attach your own metadata to exports which you can use for ordering and filtering. Metadata also allows you to delay instantiation of parts until they are actually needed. Additionally you can create custom Export attributes which provide a nice clean way of providing the metadata.
Check this link for information on how to define metadata and custom exports: link text
You may also find this thread on our MEF forums useful. Within you'll find a discussion about an AdaptingCollection approach which lets you use a custom collection which applies a metadata filter / order.
HTH Glenn
You could have the rules import each other in order (using the Decorator pattern), but then each rule will need to know about the specific rule that precedes it, which probably isn't what you want.
MEF is there to help you discover the parts, what you do with them afterwards is up to you. If you want to sort the parts then go ahead, there's nothing wrong with that!
精彩评论