Önceki yazılarımdan bir tanesinde hatırlarsanız MEF’e giriş yapmıştık. Çok basit bir uygulama ile MEF’in nasıl işlediğini anlatmaya çalışmıştım.
Bu yazımda biraz daha derin konulara girip, “extension”larımıza(MEF’de ki adı “Part” oluyor) nasıl kendi “metadata” bilgilerimizi verebileceğimizi anlatmaya çalışacağız. Öncelikle neden böyle bir şeye ihtiyaç duyuyoruz, buna bir bakalım.
MEF ile geliştirdiğimiz bir uygulamayı doğası gereği esnek bir yapıda oluyor. Bu esnekliği MEF sağlıyor bize. Kendi yarattığımız arayüzlerden türeterek uygulamıza MEF Part’ları katabiliyoruz. Ama uygulamamızın sadece arayüzlerden türeyen “Part”lar ile esneklik kazanıyor olması bazen istenmeyen bir şey olabilir. Mesela IPlugin diye bir arayüzümüz var diyelim. Ana uygulamamız, bu arayüzden türeyen nesneleri kendi içinde çalıştırabiliyor olsun. IPlugin arayüzünü kullanarak kötü niyetli biri uygulamamızda kötü şeyler yapabilir. Bundan dolayı uygulamamızda “metadata” diye adlandırabileceğimiz ekstra içerik sağlayan özellikleri kullanmakta fayda var. Bu sayede IPlugin arayüzünden türeyen nesneleri kontrol edebiliriz. Ve uygulamamız için geçerli olmayan “metadata”ları uygulamamızın çalıştırmasını engelleyebiliriz.
Peki kendi geliştirdiğimiz “Part”lara kendi “metadata”larımızı nasıl ekleyeceğiz?
Çok basit…Öncelikle kendi “metadata”mızın ne gibi bilgiler içereceğini tanımlamamız lazım. Bunun için bir “interface” ya da “class” kullanabiliriz. Ama ben “interface”i seçeceğim bu örnekte. Aşağıdaki gibi bir kod işimizi görecektir.
9 //"Metadata"mızın içeriğni belirliyoruz.
10 //Ne gibi bilgiler tutabileceğimizi istediğimiz gibi tanımlayabiliriz.
11 public interface IPluginMetaData
12 {
13 string Name { get; }
14 string Version { get; }
15 string Author { get; }
16
17 }
Daha sonra bu arayüzü kullanan bir “Attribute” yaratmamız gerekmekte ki, geliştireceğimiz “Part”lara bu “metadata” özelliğini verebilelim. Bunun içinde aşağıdaki gibi bir kod işimizi görecektir.
21 //ExportAttribute tipinde, "Attribute" tanımlıyoruz ki
22 //Yaratacağımız Part’da bu "Attribute"u kullanabilelim
23 //Burda önemli olan constructor’da base’i çağırıp
24 //ExportAttribute’da hangi arayüz ile tanımlama yapacağımızı belirtmek.
25 [MetadataAttribute]
26 [AttributeUsage(AttributeTargets.Class, AllowMultiple = false)]
27 public class PluginMetadataAttribute : ExportAttribute
28 {
29 public PluginMetadataAttribute(string name, string version,string author)
30 : base(typeof(IPluginMetaData))
31 {
32 Name = name;
33 Version = version;
34 Author = author;
35
36
37 }
38
39 //IPluginMetaData arayüzünde ki özellikleri burada da tanımlıyoruz
40 //Hepsini tanımlama zorunda değiliz.Tanımlamadıklarımız varsayılan
41 //değerleri ile gelecektir.
42 public string Name { get; set; }
43 public string Version { get; set; }
44 public string Author { get; set; }
45
46 }
47
Artık yaratacağımız “Part”lar için kendi tanımlamamızı yapabileceğimiz “metadata” yapısına sahibiz. Şimdi tek yapmamız yaratacağımız “Part”da bu “metadata” özelliğini kullanmak.Bunun için de aşağıdaki gibi bir kod bloğu kullanmamız yeterli olacaktır.
48 [Export(typeof(IPlugin))]
49 [PluginMetadata("İlk Plugin", "1.0", "Arda")]
50 [PartCreationPolicy(CreationPolicy.NonShared)]
51 public class FirstPlugin : IPlugin
52 {
53
54 }
Dikkat ederseniz “PluginMetadata”, “Attribute”u bizim kendi yarattığımız “attribute” sınıfı.
İlerleyen yazılarda da bu “metadata” bilgilerini nasıl okuyup, MEF’de nasıl “Import” işlemi yapabiliyoruz bunu anlatıyor olacağım.Şimdilik bu kadar…