Как заполнить плагин MEF данными, которые не жестко запрограммированы в сборке? - PullRequest
2 голосов
/ 30 мая 2010

Я работаю над программой, которая будет взаимодействовать с различными аппаратными средствами. Из-за различной природы элементов, которые он передает и контролирует, мне нужно иметь разные «драйверы» для каждого отдельного компонента оборудования. Это заставило меня подумать, что MEF станет отличным способом сделать эти драйверы плагинами, которые можно добавлять даже после выпуска продукта.

Я рассмотрел множество примеров использования MEF, но вопрос, на который я не смог найти ответ, заключается в том, как заполнить плагин MEF внешними данными (например, из базы данных). , Все примеры, которые я могу найти, имеют жестко запрограммированные «данные» в сборке, как в следующем примере:

[Export( typeof( IRule ) )]  
public class RuleInstance : IRule  
{
    public void DoIt() {}  

    public string Name  
    {  
        get { return "Rule Instance 3"; }  
    }

    public string Version  
    {  
        get { return "1.1.0.0"; }  
    }  

    public string Description  
    {  
        get { return "Some Rule Instance"; }  
    }  
}

Что если я хочу, чтобы имя, версия и описание поступали из базы данных? Как бы я сказал MEF, где взять эту информацию?

Я могу упустить что-то очень очевидное, но я не знаю, что это такое.

Ответы [ 2 ]

3 голосов
/ 31 мая 2010

Вы должны будете либо передать информацию плагину после его загрузки через свойства:

[Export( typeof( IRule ) )]  
public class RuleInstance : IRule  
{
    puliic void DoIt() 
    { }

    public string Name { get; set; }
}

public class Program
{
    [Import(typeof( IRule ))]
    public IRule instance { get; set; }

    public void Run()
    {
        // Load the assemblies here

        instance.Name = "Rule Instance 3";
    }             
}

Или плагин может запрашивать переменные через интерфейс хоста. Вы можете передать экземпляр IHost через свойство или через параметр конструктора, но параметры конструктора не просты с MEF. Вот через свойство:

 [Export( typeof( IRule ) )]  
public class RuleInstance : IRule  
{
    puliic void DoIt() 
    { }

    public void Initialise()
    {
        // Load our name from the host, this cannot be done in the constructor
        string name = Host.GetName(/* some parameters? */)
    }


    public IHost Host { get; set; }
    public string Name { get; set; }
}

public interface IHost
{
    string GetName(/* some parameters? */);
}

public class Program : IHost
{
    [Import(typeof( IRule ))]
    public IRule instance { get; set; }

    public void Run()
    {
        // Load the assemblies here       

        // Make sure the plugins know where the host is...
        instance.Host = this;
    }             
}

Вы также можете «Экспортировать» интерфейс базы данных и «Импортировать» его в любые плагины, которым необходим доступ к базе данных ...

1 голос
/ 03 июня 2010

Вы всегда можете экспортировать отдельные значения (через названия контрактов), вот пример:

public class Configuration
{
  [Export("SomeValue")]
  public string SomeValue
  {
    get { /* return value from database perhaps? */ }
  }
}

[Export(typeof(IRule))]
public class RuleInstance : IRule
{
  [Import("SomeValue")]
  public string SomeValue { get; private set; }
}
...