MEF for Beginner – Part 5 (Import)
this post will focus on the Import aspect.
we will soon learn about the different signature that can be apply with the Import decoration,
but before starting with that, we should introduce the Lazy<T> class
which is a first citizen at the MEF world, and part of the CLR 4 types.
Lazy<T> is used in order of delaying the actual instantiation until it actually needed.
in fact using Lazy<T> the actual instantiation will occur the first time the Value property is accessed or ToString method is called.
you can use the Lazy<T> when ever you want to delay the actual instantiation of the
object that were discovered by the MEF composition.
The Import / ImportMany decorations
MEF is trying to discover parts that apply to Import definition constraint.
we can think at the Import definition as a where clause of the Linq query
(the from clause will be define by the Catalog / Export provider which will discuss latter on this series).
out of the box MEF offer an attribute model for the Import definition.
out of the box MEF is offering 2 type of Import decorations:
1. [Import] for single discoverable part.
2. [ImportMany] for discovering multiple parts.
Note: you should use [ImportMany] if there is a possibility that MEF will discover multiple Exported parts
even if you need only one of those parts (you can latter filter one using Linq query).
if you ask for single part and MEF discovering multiple it will throw an exception or return null
(depending on the MEF policy which will discuss in the next post on this series).
Import single instance
as I said in the previous paragraph, you should not use the [Import] attribute unless
you really expecting single discovery (like the case of discovering UI shell).
you apply the [Import] decoration to properties that having a getter and a setter (the setter can be private),
actually you can decorate a private property too (not in Silverlight).
Note: you can also decorate fields but it considered as bad practice.
and you can use the Lazy<T> if you want delay instantiation.
Import decoration may look like the following code:
in the sample above the Import contract is concluded from the type of the property,
while in the next sample it is explicitly define.
note that the Lazy<T> is not part of the contract.
using explicit contract is useful while we want MEF to search for contract of specific derived
type and not for the type of the property itself.
in case that the Imported property can have null value you should add the AllowDefault=true
to the Import decoration ( it will look like the following [Import (AllowDefault=true)] ).
Import multiple values
Importing multiple values is done by using the [ImportMany] attribute.
we can assign this attribute to properties that having IEnumerable<T>, Array () and
any type that derived from ICollection<T>.
the types within the above sets can be Lazy<T> for having delay instantiation.
the following code snippet will demonstrate the use of [ImportMany] decoration:
Construction time import
the last capability I’m going to discuss in this post,
is one that I advice against using whenever you can, because it can lead to
cross composition reference. just for knowing what to avoid from
I will now introduce you to the [ImportingConstructor].
the [ImportingConstructor] can be decorate constructor that should be use by
the MEF composition, so any parameter of this constructor is
treated as import which should be satisfied.
the constructor may look as follow:
in this post we learn which signature can be apply to the import definitions
and we present the Lazy<T> type and its role under the MEF world.
on the next post at this series we will survey different MEF policies that
can affects the behavior of the MEF composition process.
code snippet (console application) can be download from here.