【发布时间】:2013-01-02 14:49:22
【问题描述】:
我正在从新 AppDomain 中的特定“扩展”目录中加载所有 DLL,以从中获取一些与反射相关的信息。
这就是我正在尝试的:
我在我的解决方案中创建了一个新库 AssemblyProxy,它只有这个类:
public class AssemblyProxy : MarshalByRefObject
{
public Assembly LoadFile( string assemblyPath )
{
try
{
return Assembly.LoadFile( assemblyPath );
}
catch
{
return null;
}
}
}
我确保此 DLL 存在于我的“扩展”目录中。然后我使用以下代码将所有程序集从“扩展”目录加载到新的AppDomain。
foreach( string extensionFile in Directory.GetFiles( ExtensionsDirectory, "*.dll" ) )
{
Type type = typeof( AssemblyProxy.AssemblyProxy );
var value = (AssemblyProxy.AssemblyProxy) Domain.CreateInstanceAndUnwrap(
type.Assembly.FullName,
type.FullName );
var extensionAssembly = value.LoadFile( extensionFile );
types.AddRange( extensionAssembly.GetTypes() );
}
某些 DLL 确实可以成功加载,但在某些 DLL 上会抛出如下异常:
Could not load file or assembly 'Drivers, Version=2.3.0.77, Culture=neutral, PublicKeyToken=null' or one of its dependencies. The system cannot find the file specified.
编辑:新的 AppDomain 中不会引发异常。 DLL 在新的 AppDomain 中成功加载。一旦程序集引用返回到主/调用 AppDomain,就会引发异常。主/调用 AppDomain 是否尝试在收到引用时自行加载程序集?
谢谢。
【问题讨论】:
-
ReflectionLoadOnly不足以满足您的(不为人知的)目的吗? -
CreateInstanceAndUnwrap 有什么问题?
-
@ConradFrix
ReflectionOnlyLoad确实在当前AppDomain中加载程序集,而不是它的依赖项。据我所知,您无法从当前的AppDomain卸载它们。 -
@ConradFrix:还有其他原因。就像只是扫描程序集或构建插件系统(在插件之后扫描程序集,如果没有则卸载它+卸载不再使用的插件)
-
@user1004959:因为你要返回
Assembly。您将需要创建一个安全的可序列化/远程对象来传输该信息。一旦类型越界,你就完蛋了;p