我在Visual Studio 2017中使用MEF(System.ComponentModel.Composition)CompositionContainer和.net 4.5.1,从目录X加载dll中的某些类。
_catalogs = new AggregateCatalog();
var dir = new DirectoryCatalog("X", "*.dll");
compositionContainer = new CompositionContainer(_catalogs, true);
compositionContainer.ComposeParts();
我能够毫无问题地访问我需要的内容。 在某些时候,我将从合成中删除目录:
_catalogs.Catalogs.Remove(_catalogs.Catalogs.First());
这有效,之后,我在CompositionContainer或AggregateCatalog中没有我的dll实例。
我的问题是,现在,如果我的应用程序仍然打开,我无法删除目录" X",或移动它或重命名它。我得到了一条“拒绝访问路径”#39;消息,来自代码或来自资源管理器。
任何人都知道什么可能导致目录仍然附加到CompositionContainer,即使它被删除?还是我错了?
谢谢。
答案 0 :(得分:1)
Pfff ...仅删除目录甚至在其上调用Dispose()
是不够的。为什么?因为MEF默认情况下会将目录的程序集加载到当前AppDomain 中。这意味着您的程序集文件被AppDomain阻止,这就是您无法对它们执行任何IO操作的原因。
关于加载和卸载程序集的documentation:
如果不卸载包含它的所有应用程序域,就无法卸载单个程序集。使用AppDomain中的Unload方法卸载应用程序域。有关更多信息,请参见如何:卸载应用程序域。
现在,显然你无法卸载你的AppDomain,因为你只有一个=)。那么,让我们只有一个选择,是的,你是对的:使用另一个AppDomain
几个月前我有同样的要求,我跟着this CodeProject文章,这对我帮助很大。文章的名称是 MEF和AppDomain - 即时删除程序集,这几乎是你需要的东西=)
修改强> OP使用默认的appDomain设置ShadowCopyFiles解决了这个问题:
AppDomain.CurrentDomain.SetShadowCopyFiles();