我正在尝试使用以下代码将位于用户定义位置的强名称程序集加载到AppDomain中:
AppDomainSetup ads1 = new AppDomainSetup();
if (ads1.PrivateBinPath != null)
{
ads1.PrivateBinPath += ads1.PrivateBinPath.Length == 0 ? "" : Path.PathSeparator.ToString();
}
ads1.PrivateBinPath += @"c:\work\abc1";
sandbox1 = AppDomain.CreateDomain("sandbox1", null, ads1);
Object o1 = sandbox1.CreateInstanceFromAndUnwrap(@"abc, Version=1.0.0.0, Culture=neutral, PublicKeyToken=f10808f3df0adc34", "Abc.Def");当我运行时,我得到这个错误:
Unhandled Exception: System.IO.FileNotFoundException: Could not load file or assembly 'file:///C:\Users\gel\Documents\Visual Studio 2012\Projects\ConsoleApplicat
ion1\ConsoleApplication1\bin\Debug\abc, Version=1.0.0.0, Culture=neutral, PublicKeyToken=f10808f3df0adc34' or one of its dependencies. The system cannot find the fil
e specified.
at System.Reflection.RuntimeAssembly._nLoad(AssemblyName fileName, String codeBase, Evidence assemblySecurity, RuntimeAssembly locationHint, StackCrawlMark& stack
Mark, IntPtr pPrivHostBinder, Boolean throwOnFileNotFound, Boolean forIntrospection, Boolean suppressSecurityChecks)
at System.Reflection.RuntimeAssembly.InternalLoadAssemblyName(AssemblyName assemblyRef, Evidence assemblySecurity, RuntimeAssembly reqAssembly, StackCrawlMark& st
ackMark, IntPtr pPrivHostBinder, Boolean throwOnFileNotFound, Boolean forIntrospection, Boolean suppressSecurityChecks)
at System.Reflection.RuntimeAssembly.InternalLoadAssemblyName(AssemblyName assemblyRef, Evidence assemblySecurity, RuntimeAssembly reqAssembly, StackCrawlMark& st
ackMark, Boolean throwOnFileNotFound, Boolean forIntrospection, Boolean suppressSecurityChecks)
at System.Reflection.RuntimeAssembly.InternalLoadFrom(String assemblyFile, Evidence securityEvidence, Byte[] hashValue, AssemblyHashAlgorithm hashAlgorithm, Boole
an forIntrospection, Boolean suppressSecurityChecks, StackCrawlMark& stackMark)
at System.Reflection.Assembly.LoadFrom(String assemblyFile, Evidence securityEvidence)
at System.Activator.CreateInstanceFromInternal(String assemblyFile, String typeName, Boolean ignoreCase, BindingFlags bindingAttr, Binder binder, Object[] args, C
ultureInfo culture, Object[] activationAttributes, Evidence securityInfo)
at System.AppDomain.CreateInstanceFrom(String assemblyFile, String typeName)
at System.AppDomain.CreateInstanceFromAndUnwrap(String assemblyName, String typeName)
at System.AppDomain.CreateInstanceFromAndUnwrap(String assemblyName, String typeName)
at ConsoleApplication1.Program.Main(String[] args) in c:\Users\gel\Documents\Visual Studio 2012\Projects\ConsoleApplication1\ConsoleApplication1\Program.cs:li
ne 69这就好像AppDomain根本没有在PrivateBinPath中查找一样。我做错了什么?我已经在资源管理器窗口中进行了两次检查,并且可以在PrivateBinPath中指定的位置看到程序集。如果我只是执行Assembly.LoadFile并指定正确的路径,它可以很好地工作,但这与试图将其加载到另一个AppDomain中的目的背道而驰。
发布于 2012-11-24 16:37:55
我已经修改了你的代码,这很好用。查看您需要完成的更改。
AppDomainSetup ads1 = new AppDomainSetup();
if (ads1.PrivateBinPath != null)
{
ads1.PrivateBinPath += ads1.PrivateBinPath.Length == 0 ? "" : Path.PathSeparator.ToString();
}
ads1.PrivateBinPath += @"D:\ConsoleApplication1\ClassLibrary1\bin\debug";
AppDomain sandbox1 = AppDomain.CreateDomain("sandbox1", null, ads1);
Object o1 = sandbox1.CreateInstanceFromAndUnwrap(@"ClassLibrary1.dll", "ClassLibrary1.Class1");发布于 2012-11-24 14:33:39
我相信它无法将该程序集加载到您当前的AppDomain中,而不是加载到新的(它认为加载正常)。
这种行为有时被称为“将类型泄漏到其他域”,并由尝试直接使用创建的对象引起。要解决这个问题,需要在另一个AppDomain中完全创建类(即,通过运行一些处理创建的自定义代码),然后只公开两个域都知道的接口/类。有关详细信息,请查看Unloadable plugins。
摘自本文一小部分代码-使用CreateInstanceFromAndUnwrap在其他AppDomain中创建RemoteLoader类,并使用该对象在新AppDomain中加载/管理其他类型。
public class RemoteLoader : MarshalByRefObject
{
public void Load(string assemblyName, string typeName)
{
object instance = Activator.CreateInstance(assemblyName, typeName);
//Do something with instance, or return shared interface of it.
}
}附注:除非您是出于教育目的,否则请考虑使用现有的插件框架,如MEF。
https://stackoverflow.com/questions/13538792
复制相似问题