Plugin Arquitetura com Interfaces; verificação de interface não funciona
-
13-09-2019 - |
Pergunta
Estou implementando um simples plug-in arquitetura em um aplicativo. Os requisitos plug-in são definidas utilizando uma interface (IPlugin) que está em um dll * que é referenciado pela aplicação e o plug-in. A aplicação tem um gerenciador de plug-in (também na mesma .dll *), que carrega os plugins por olhando para toda a .dll * está em uma pasta plugins, cargas deles, em seguida, verifica que os instrumentos de plugin a interface. Eu tenho feito isso verificando duas maneiras diferentes [anteriormente por um simples if (plugin é IPlugin)], mas nenhum deles vai reconhecer quando um plugin implementa a interface. Aqui está o código:
Assembly pluginAssembly = Assembly.LoadFrom(currFile.FullName);
if (pluginAssembly != null)
{
foreach (Type currType in pluginAssembly.GetTypes())
{
if (currType.GetInterfaces().Contains(typeof(IPlugin)))
{
// Code here is never executing
// even when the currType derives from IPlugin
}
}
}
I utilizado para testar um nome de classe particular ( "plug-in"), mas, em seguida, permiti-la a percorrer todas as classes no conjunto sem sucesso. (Isto segue um exemplo que I encontrada em outro lugar.) Para tornar isto um pouco mais complicado, existem duas interfaces de cada um dos que implementa a interface original (IPluginA, IPluginB). O plug-in realmente implementa uma das interfaces mais específicas (IPluginB). No entanto, eu tentei com o plugin simplesmente implementando a interface mais geral (IPlugin), e isso ainda não funciona.
[Edit: em resposta às duas respostas que recebeu pela primeira vez] Sim, eu tentei usar IsAssignableFrom. Consulte o seguinte:
Assembly pluginAssembly = Assembly.LoadFrom(currFile.FullName);
if (pluginAssembly != null)
{
foreach (Type currType in pluginAssembly.GetTypes())
{
if (typeof(IPlugin).IsAssignableFrom(currType))
{
string test = "test";
}
}
}
Solução
Você tentou:
typeof(IPlugin).IsAssignableFrom(currType)
Além disso, os tipos de implementar interfaces, mas eles não derive a partir deles. A BaseType
propriedade e IsSubclassOf
método show de derivação, onde mostra IsAssignableFrom
derivação ou implementação.
Editar: são suas montagens assinado? Eles poderiam ser carregamento side-by-side versões do seu assembly , e desde que os objetos Type
são comparados com ReferenceEquals
, o mesmo tipo em dois conjuntos de lado-a-lado seria completamente independente.
Editar 2: Tente isto:
public Type[] LoadPluginsInAssembly(Assembly otherAssembly)
{
List<Type> pluginTypes = new List<Type>();
foreach (Type type in otherAssembly.GetTypes())
{
// This is just a diagnostic. IsAssignableFrom is what you'll use once
// you find the problem.
Type otherInterfaceType =
type.GetInterfaces()
.Where(interfaceType => interfaceType.Name.Equals(typeof(IPlugin).Name, StringComparison.Ordinal)).FirstOrDefault();
if (otherInterfaceType != null)
{
if (otherInterfaceType == typeof(IPlugin))
{
pluginTypes.Add(type);
}
else
{
Console.WriteLine("Duplicate IPlugin types found:");
Console.WriteLine(" " + typeof(IPlugin).AssemblyQualifiedName);
Console.WriteLine(" " + otherInterfaceType.AssemblyQualifiedName);
}
}
}
if (pluginTypes.Count == 0)
return Type.EmptyTypes;
return pluginTypes.ToArray();
}
Outras dicas
O método IsAssignableFrom é o que você está procurando:
Type intType = typeof(IInterface);
foreach (Type t in pluginAssembly.GetTypes())
{
if (intType.IsAssignableFrom(t))
{
}
}