概念 †MEFでサービスのエクスポートやインポート時に識別子を付与する事が出来ます。この識別子を「コントラクト」と言います。コントラクトには以下の種類があります。
用語 †
サンプル †一般的な「Hello,World」サンプル: static void Main(string[] args) { Console.WriteLine("Hello,World."); } 上記のロジックを MEF でやり直します。ロジックを2つ部分を分けます、一つは文字列を提供する、一つは文字列を処理します。 public class StringProvider { [Export("Print")] public string Output { get { return "Hello,World"; } } } 文字列を処理するする部分では、下記のように、「message」変数に「Print」識別子で「Import」属性をつけます(複数のExportの場合は「ImportMany」を利用します。)、ここでは、「Print」識別子のエクスポートを探して、変数に渡します。 public class Client { [Import("Print")] private string message=null; public void print() { Console.WriteLine(this.message); } } インポート・エクスポートの識別子が存在しない場合、下記のような例外が発生します。 ハンドルされていない例外: System.ComponentModel.Composition.ChangeRejectedExcept ion: コンポジションは変更されませんでした。次のエラーのために、変更は拒否されま した: コンポジションで、コンポジション エラーが 1 件発生しました。根本原因は次の とおりです。 詳細については、CompositionException.Errors プロパティを確認してく ださい。 1) 制約 '((exportDefinition.ContractName == "System.String") AndAlso (exportDefi nition.Metadata.ContainsKey("ExportTypeIdentity") AndAlso "System.String".Equals (exportDefinition.Metadata.get_Item("ExportTypeIdentity"))))' に一致する有効なエ クスポートが見つかりませんでした。無効なエクスポートが拒否されている可能性があり ます。 結果: パーツ 'ConsoleApplication1.Client' のインポート 'ConsoleApplication1.Clie nt.message (ContractName="System.String")' を設定できません。 要素: ConsoleApplication1.Client.message (ContractName="System.String") --> Con soleApplication1.Client 以上で、エクスポートとインポートの口を完成しました。次は「コンテナー」によって動作させます。 using System; using System.ComponentModel.Composition; using System.ComponentModel.Composition.Hosting; namespace cc.ejb.blogs.example { class Program { static void Main(string[] args) { CompositionContainer container = new CompositionContainer(); CompositionBatch batch = new CompositionBatch(); Client client = new Client(); batch.AddPart(new StringProvider()); batch.AddPart(client); container.Compose(batch); client.print(); } } } ここでは合成コンテナー CompositionContainer のインスタンスを作成し、必要なパーツをコンテナーに追加します。MEFは AssemblyCatalog、DirectoryCatalog、また二つの組み合わせ方式で、パーツを抽出できます。 DirectoryCatalog は、指定されたディレクトリの中の DLL ファイルから属性付きパーツは抽出します。 AssemblyCatalogは、指定されたアセンブリの中から、属性付きパーツは抽出します。 AssemblyCatalog方法 CompositionContainer container = new CompositionContainer(new AssemblyCatalog(typeof(Client).Assembly)); Client client = new Client(); container.SatisfyImportsOnce(client); client.print(); DirectoryCatalog方法 CompositionContainer container = new CompositionContainer( new DirectoryCatalog( System.IO.Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) ,"*.exe" ) ); Client client = new Client(); container.SatisfyImportsOnce(client); client.print(); 両方: AggregateCatalog catalog = new AggregateCatalog(); catalog.Catalogs.Add(new AssemblyCatalog(typeof(Client).Assembly)); CompositionContainer _container = new CompositionContainer(catalog); 中古車買取実績No.1ガリバー コメント: |