GetType(string)在AppDomain.CurrentDomain.Load之后返回null

时间:2011-02-21 22:24:18

标签: c# reflection interface gettype

我正在构建一个小插件架构(遗憾的是MEF不是一个选项,因为它需要在.NET 2.0上运行)。 我希望能够将dll放在一个目录中,而无需重新编译主项目。 我的主要项目是一个winforms应用程序,它有一些对话框可以选择主程序所需的接口实现。

我有一个搜索某个目录的方法,并提供了我想要搜索实现该接口的类型的dll的位置列表。

public List<Type> GetPluginTypes()
{
  List<Type> types = new List<Type>();
  foreach (string dll in this.Plugins)
  {
    Assembly assembly;
    try
    {
      assembly = AppDomain.CurrentDomain.Load(AssemblyName.GetAssemblyName(dll));
    }
    catch
    {
      continue;
    }
    foreach (Type type in assembly.GetExportedTypes())
    {
      if (type.IsInterface || type.IsAbstract)
        continue;

      if (typeof(IMyInterface).IsAssignableFrom(type))
       types.Add(type);
    }
  }
  return types;
}

使用此方法,我向用户显示一个实现列表,选择一个,并将AssemblyQualifiedName保存到设置文件中。

当我启动主应用程序时,我从设置加载AQN并通过调用上述方法将所有插件加载到AppDomain中。

string typeName = GetSetting("MyPlugin");
GetPluginTypes(); // just to load the plugins into the app domain
Type.GetType(typeName); // allways returns null.

这是我的问题:Type.GetType(typeName),总是返回null。

我使用Type.GetType(typeName,true)来强制执行异常,我得到了: 无法加载文件或程序集“MyImpl,Version = 1.0.0.0,Culture = neutral,PublicKeyToken = null”或其依赖项之一。系统找不到指定的文件。“:”MyImpl,Version = 1.0.0.0,Culture = neutral,PublicKeyToken = null“}

我很无能为力。我已经将程序集加载到AppDomain中了,当我指定AQN时,仍然无法找到Type.GetType(string)。

2 个答案:

答案 0 :(得分:3)

这可以通过为AppDomain注册AppDomain.AssemblyResolve事件来解决,该事件将请求程序集并使处理程序返回已经加载的程序集。

这是处理程序在C#中的样子:

    private System.Reflection.Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args)
    {
        return
            AppDomain.CurrentDomain.GetAssemblies()
            .FirstOrDefault(Kandidaat => string.Equals(Kandidaat.GetName().FullName, args.Name));
    }

详细说明可以在这里找到: https://msdn.microsoft.com/en-us//library/ff527268(v=vs.110).aspx

答案 1 :(得分:1)

也许这是相关的。来自Type.GetType(String, Boolean)的文档:

  

如果typeName仅包含名称   Type,此方法在中搜索   调用对象的程序集,然后在   mscorlib.dll程序集。如果typeName是   完全符合部分或   完整的程序集名称,此方法   在指定的程序集中搜索。

您说您尝试使用type.AssemblyQualifiedName进行呼叫,但失败了。您是否检查了合格的名称以确定它是否合理?