【发布时间】:2011-04-14 06:11:58
【问题描述】:
在我的程序中,我使用
动态创建 Com+ 对象(后期绑定)Type comObjectType = Type.GetTypeFromProgID(progId, true);
object comObject = Activator.CreateInstance(comObjectType);
然后使用反射调用其中一种方法
object result = comObjectType.InvokeMember(MethodToActivate, BindingFlags.InvokeMethod, null, comObjec, new object[] {....});
它在 .Net 1.1/2.0/3.5 中效果更好
现在我尝试在为 .Net 4.0 编译的同一台机器 (Windows XP) 上运行 相同的代码,但我有一个
Exception: Method 'System.__ComObject.{MethodName}' not found.
我对大多数 Com+ 对象(不是全部)都有例外。 有谁知道是什么问题? 为什么在 FW 4.0 环境中会出现异常? 我应该怎么做才能避免它?
非常感谢, 丹尼尔
经过进一步调查,我发现一些 Com+ 代理被创建为 System._ComObject(我想那些是本机代理),有些被创建为 System.Runtime.Remoting.Proxies._TransparentProxy(我认为那些是 .Net Com+对象)。方法调用适用于创建为System._ComObject 的方法,不适用于System.Runtime.Remoting.Proxies._TransparentProxy。
最有趣的事实是,在 .Net 2.0 中,所有对象都是以相同的方式创建的(_ComObject 和 _TransparentProxy),但方法调用确实可以正常工作。
另一个有趣的事实是,我可以使用反射在调试器中看到“缺失”的方法
((System.EnterpriseServices.RemoteServicedComponentProxy)((((System.Runtime.Remoting.Proxies.__TransparentProxy)(ObjectToActivate)))._rp)).ProxiedType.GetMethods()
我一度认为这可能是一个安全问题,但我在 WindowsService 以具有管理员权限的用户身份登录时运行代码
【问题讨论】:
-
您检查过任何 32/64 位问题吗?也许您的进程是 64 位的,因此访问了 64 位 COM 注册表(没有人居住的地方 :-)?
-
我觉得不是 32/34 位的问题,我的本地机器是 32 位的,远程服务器也是
-
适用于 32/64 位。现在,您的 COM 服务器似乎不在进程中或具有特定的线程模型(因此是代理)。你能提供更多细节吗?他们是在进程外托管的吗?在组件服务中?那么 Invoke 参数呢?你确定没有歧义吗? BindingFlags 呢?你不需要公共|实例吗?
-
大多数 com+ 服务器实际上位于远程机器(2003 服务器)上,但不是全部。它们作为服务器应用程序与其专用用户一起运行。我一直专注于一个本地的并将字符串作为参数并返回字符串(非常简单)。绑定 falg 是为 BindingFlags.InvokeMethod 设置的,我没有在其他 .Net 版本中使用 Public|Instance,这不是问题,但我会尝试,可能是 4.0 版本比以前的版本有更多的运行时限制
-
.NET 4.0 不应该自动处理这个吗?与其将 comObject 声明为对象,不如将其声明为动态的。试试看这个msmvps.com/blogs/paulomorgado/archive/2010/04/19/…