Let's look my third API class - MEFWrapper.
MEFWrapper Class
The above two classes not only make the DI mappings easy, but they also try to expose MEF rich infrastructure as minimum as possible. How to load this DI information to MEF? This comes to the third class, MEFWrapper. The same applies to the MEFWrapper class. This class encapsulates the logic of how to create MEF's container and how add composable parts to the container.
Steps to Load DI Information
With this class, there are three steps to load DI information to MEF. The first step is get an instance of MEFWrapper through the static method CreateInstance(). This follows singleton pattern, to create a single MEF container instance per application.
The second step is to add DICatalog instances through Add() or AddRange() interfaces.
After all the DI information are added to MEFWrapper, the third step is to call the method of InitialzeDIMappings(), which encapsulates the logic of loading DI parts and catalogs to MEF container.
Get Mapped Instance
Now your MEF framework is ready for use. You can use MEF's Import attribute to let MEF to inject instances for your usage. MEFWrapper also provides static methods of GetInstance
Dispose MEFWrapper Instance
After your usage or your application is going to be terminated, you should call the method of dispose() (IDisposable implementation) of the MEFWrapper instance.
Here is an example of using this wrapper class in a DIRootCatalog class:
public class DIRootCatalog : DICatalogBase {
private static MEFWrapper _instance = null;
# region CTOR
private DIRootCatalog() :
base (Assembly.GetExecutingAssembly())
{ }
# endregion
public static void LoadDIMappings(){
// Create instance and load DIs only once
if (_instance == null) {
_instance = MEFWrapper.GetIntance(new DIRootCatalog());
// Exampels to add DIs to instance
// Assume DIs are based on DICatalogBase
_instance.Add(new DIDataReader());
_instance.Add(new DIProcessorController());
_instance.AddRange(
new DICatalogBase[]{
new DILog(), new DIDBService() }
);
_instance.Add(new DICatalogBase("DIExtensions"));
// Initialze MEF Container with DI parts through catalogs
_instance.InitializeDIMappings();
}
}
public static void UnLoadDIMappings() {
if (_instance != null) {
_instance.Dispose();
_instance = null;
}
}
}
...
internal class DIResolver : DIResolverBase {
// Define Import and Export properties
...
}
private static MEFWrapper _instance = null;
# region CTOR
private DIRootCatalog() :
base (Assembly.GetExecutingAssembly())
{ }
# endregion
public static void LoadDIMappings(){
// Create instance and load DIs only once
if (_instance == null) {
_instance = MEFWrapper.GetIntance(new DIRootCatalog());
// Exampels to add DIs to instance
// Assume DIs are based on DICatalogBase
_instance.Add(new DIDataReader());
_instance.Add(new DIProcessorController());
_instance.AddRange(
new DICatalogBase[]{
new DILog(), new DIDBService() }
);
_instance.Add(new DICatalogBase("DIExtensions"));
// Initialze MEF Container with DI parts through catalogs
_instance.InitializeDIMappings();
}
}
public static void UnLoadDIMappings() {
if (_instance != null) {
_instance.Dispose();
_instance = null;
}
}
}
...
internal class DIResolver : DIResolverBase {
// Define Import and Export properties
...
}
And there is an example of a console application where the above DIRootCataLog is used:
class Program {
static void Main(string[] args) {
// Load MEF framework with DI mappings
DIRootCatalog.LoadDIMappings();
// Get process controler instance from MEF
var mainProcess = MEFWrapper.GetInstance<IProcessController>();
// Start process
mainProcess.Start();
// Unload MEF framework
DIRootCatalog.UnLoadDIMappings();
}
}
static void Main(string[] args) {
// Load MEF framework with DI mappings
DIRootCatalog.LoadDIMappings();
// Get process controler instance from MEF
var mainProcess = MEFWrapper.GetInstance<IProcessController>();
// Start process
mainProcess.Start();
// Unload MEF framework
DIRootCatalog.UnLoadDIMappings();
}
}
Here is the library of DICommonLibrary project.
Note: the project depends on two library files: one is MEF library and another is a related open source library for MEF. Both are available from CodePlex:
System.ComponentModel.Composition.dll
Microsoft.Practices.ServiceLocation.dll
0 comments:
Post a Comment