应用程序域隔离问题

本文关键字:问题 隔离 应用程序域 | 更新日期: 2023-09-27 18:34:56

我构建了一个后端,将业务逻辑放置在运行时加载的 dll 中。使用 ShadowCopyFiles = true 和文件系统监控,我能够在不重新启动主机进程的情况下修改业务逻辑。

目前为止,一切都好。。。

让我们将主机应用域 A 和其中一个子域称为 B。

遗憾的是,如果我在程序集 C 中进行更改,而程序集 C 由 B 引用,但未由 A 引用,则在重新加载 B 时不会反映这些更改。我认为这是因为 A 加载了 C 本身。我必须采取哪些步骤来防止 A 加载 C?

这是 A 用来加载 B 的代码:

        AppDomainSetup appDomainSetup = new AppDomainSetup();
        appDomainSetup.CachePath = ServiceDLLPath + @"'Shadow";
        appDomainSetup.ShadowCopyFiles = "true";
        ad = AppDomain.CreateDomain(assemblyName, null, appDomainSetup);
        ad.InitializeLifetimeService();
        try
        {
            service = (IService)ad.CreateInstanceFromAndUnwrap(assemblyName, 
                                  "AppName.Services." + typeName);
            service.Start();
        }
        catch (Exception e)
        {
            LogManager.Log("AppDomain load failed: " + e.Message);
            return false;
        }

应用程序域隔离问题

如果A引用C并且A是"主机",则无法在不停止并重新启动进程的情况下重新加载C

一种可能性是制作一个极薄的填充程序 AppDomain,用于引导A AppDomain(并且可以重新启动它(,但重新执行该过程可能与性能配置文件大致相同。

另一种(看似更理智的(方法是使A及其依赖项独立于C使用的依赖项,并且对于重叠的程序集,只需使它们足够稳定,以至于您不需要经常更改它们。

阅读答案和注释,听起来您最好将业务逻辑打包到 WCF 服务中。您可以使用净管道来最大程度地减少在同一台电脑上运行的开销。还应查看 MEF 以构建应用程序的可扩展性。不幸的是,MEF 也不允许您在不重新启动主机应用程序的情况下即时卸载和替换插件

好的,

我通过创建一个"接口"程序集解决了它。

因此,如果这个程序集称为 X,则链现在为:

A ->

X <- B -> C

(原名:A -> B -> C(

我现在可以在 B 或 C 中进行更改,这些更改会在 appDomain B 被 A 销毁并重新启动时反映出来。

编辑,应蒂姆的要求,更多细节。

应用程序域 A 中的代码没有更改,您可以看到它我的问题。唯一需要注意的是 IService 类型定义的位置:

 service = (IService)ad.CreateInstanceFromAndUnwrap(assemblyName, 
                              "AppName.Services." + typeName);

一旦IService被移动到一个专门构建的程序集,我就能够删除B和A中的引用,这些引用以某种方式最终将A连接到C.基本上Chris所说的一切都是正确的,只是并不总是清楚路径是什么。