我有一个C#项目,该项目创建一个用于POS终端的COM对象。在将其提供给客户之前,我想确保它可以作为COM dll工作。 RegAsm表示可行。
using System;
using System.Runtime.InteropServices;
namespace POS
{
[Guid( "0135bc5c-b248-444c-94b9-b0b4577f5a1a" )]
[InterfaceType( ComInterfaceType.InterfaceIsDual )]
[ComVisible( true )]
public interface ITwoWay
{
// The Initialize method is called to establish the communications connection...
[DispId( 1 )]
void Initialize( String IPAddress, long Port, long MaxPacketSize );
// A convenience method that allows the POS to test the Third Party’s back-end...
[DispId( 2 )]
void TestConnect();
// The Terminate method is called to indicate that the POS system is about to terminate...
[DispId( 3 )]
void Terminate();
// All interface calls made during a transaction send the same record format with specific reply fields ...
[DispId( 4 )]
void TransactionCall( String viPOSMsg, ref String InterceptArray );
}
}
实际的入口点是在TwoWay类中定义的
using System.Runtime.InteropServices;
using System.EnterpriseServices;
namespace POS
{
[Guid( "0135bc5c-b248-444c-94b9-b0b4577f5a1b" )]
[ComDefaultInterface(typeof(ITwoWay))]
[ClassInterface( ClassInterfaceType.None )]
[ComVisible( true )]
public class TwoWay : ITwoWay
...
[ComVisible( true )]
public void Initialize( string iPAddress, long port, long maxPacketSize )
...
我曾经以为我可以将.tlb导入另一个.net项目并以这种方式进行测试,但是当我将COM项目添加为COM引用时,VS拒绝了它,因为它是作为.NET dll创建的。
我试图创建一个vb脚本来运行CreateObject,但是权限错误。我试图设置I_USER帐户,等等,但是我做不到。
注册表显示具有正确名称的条目,并且将类ID设置为正确的GUID。但仍然,我想加载它并通过COM接口运行它。
如何验证COM .dll实际上是COM .dll?就像这样古老,必须有一种方法。
答案 0 :(得分:0)
一种快速的实现方法是使用.NET的dynamic功能,这对于COM编程非常有用
因此,如果您的类定义是这样的(我个人没有将COM接口与.NET一起使用,但是如果接口是双重的,则不会有任何改变),请注意,我添加了一个很好的COM做法: >
[Guid("0135bc5c-b248-444c-94b9-b0b4577f5a1a")]
[ProgId("MyComponent.TwoWay")]
[ComVisible(true)]
public class TwoWay
{
public void Initialize(string IPAddress, long Port, long MaxPacketSize)
{
Console.WriteLine(IPAddress);
}
// other methods...
}
然后我可以使用.NET这样进行测试(无需创建TLB,只需使用regasm注册它即可):
var type = Type.GetTypeFromProgID("MyComponent.TwoWay");
dynamic twoway = Activator.CreateInstance(type);
twoway.Initialize("hello", 0, 0);
不便之处在于您没有自动完成功能,您只需要注意传递合适的参数即可。 .NET足够聪明,可以将Int32
转换为Int64
(请注意,您使用的C#long
为64位宽)。