CreateInstanceAndUnwrap 和域

Posted

技术标签:

【中文标题】CreateInstanceAndUnwrap 和域【英文标题】:CreateInstanceAndUnwrap and Domain 【发布时间】:2011-08-12 18:54:15 【问题描述】:

我有一个属性,我希望其实例位于其他域中。

public ModuleLoader Loader
        
            get
            

                if(_loader == null)
                    _loader = (ModuleLoader)myDomain.CreateInstanceAndUnwrap(
                              this.GetType().Assembly.FullName,
                              "ModuleLoader",
                              false, 
                              System.Reflection.BindingFlags.CreateInstance,                                  
                              null, 
                              null, 
                              null, 
                              null);
                System.Diagnostics.Debug.WriteLine("Is proxy=0",
                             RemotingServices.IsTransparentProxy(_loader)); 
                                 //writes false
                 _loader.Session = this;
                 return _loader;
            
        

这很好用。但我假设 _loader 实例上的所有方法调用都将在其他域(myDomain)中调用。但是当我运行以下代码时,它仍然会写入主应用程序域。

public void LoadModule(string moduleAssembly)
        
            System.Diagnostics.Debug.WriteLine("Is proxy=0", 
                     RemotingServices.IsTransparentProxy(this));
            System.Diagnostics.Debug.WriteLine(
                          AppDomain.CurrentDomain.FriendlyName);
            System.Diagnostics.Debug.WriteLine("-----------");
        

是因为 Unwrap() 吗?我哪里做错了?

我了解 AppDomain 会创建单独的内存。我需要的是我的主应用程序运行,它在不同的 AppDomain 中加载模块。由于主应用程序还希望观察模块的某些活动并与在单独域中运行的对象进行交互,因此实现它的最佳方法是什么。

【问题讨论】:

【参考方案1】:

如果你想实际运行另一个程序集中的代码,你需要让你的ModuleLoader 类继承自MarshalByRefObject。如果你这样做,CreateInstanceAndUnwrap() 实际上会返回一个代理,并且调用将在另一个应用程序域中执行。

如果您不这样做,而是将类标记为Serializable(如异常消息所示),CreateInstanceAndUnwrap() 将在另一个应用程序域中创建对象,对其进行序列化,将序列化形式传输到原始appdomain,在那里反序列化它并在反序列化的实例上调用方法。

【讨论】:

以上是关于CreateInstanceAndUnwrap 和域的主要内容,如果未能解决你的问题,请参考以下文章

CreateInstanceAndUnwrap 在另一个域中?

ASP.NET:CreateDomain(...).CreateInstanceAndUnwrap(...) 或 Assembly.LoadFrom(...).GetExportedTypes() 抛

AppDomain.CreateInstanceAndUnwrap 在网站中不起作用

使用 AppDomain.CreateInstanceAndUnwrap 创建类型 T 的实例,然后提前绑定到类型 T 的方法

AppDomain CreateInstanceAndUnwrap:类型未标记为可序列化

如果库的名称已更改,AppDomain.CreateInstanceAndUnwrap 将失败