我已按照此问题中描述的步骤进行操作:
所以,我有这个c#代码:
using System;
using System.IO;
namespace ComLib
{
public class LogWriter
{
public void WriteLine(string line)
{
using (var log = new StreamWriter(File.OpenWrite(@"c:\log.file")))
{
log.WriteLine(line);
}
}
}
}
在名为RubyToCSharp
我检查了VS中的Register for COM interop
并创建了以下ruby代码:
require "win32ole"
lib = WIN32OLE.new('RubyToCSharp.ComLib.LogWriter')
lib.WriteLine('calling .net from ruby via COM, hooray!')
现在我尝试从powerShell运行这个ruby并且我一直收到这个错误:
./exmpl.rb:4:in `initialize': unknown OLE server: `RubyToCSharp.ComLib.LogWriter' (WIN32OLERuntimeError)
HRESULT error code:0x800401f3
Invalid class string
from ./exmpl.rb:4:in `new'
from ./exmpl.rb:4:in `<main>'
对于我在这里错过了什么的想法?
根据this SO question检查我的dll是否已注册后, 看来确实我的dll已注册,但仍然会发生同样的错误。
在这里真的很困惑......
答案 0 :(得分:1)
在注册期间,只有标记为ComVisible的类才会导出到相应的键。它也是一个非常非常好的想法(我说是必须的)有一个Guid属性而不是默认值,它可以在每次编译时改变。您也可以拥有自己的ProgId属性,但通常默认的Namespace.ClassName就足够了(其中Namespace是您的类所在的命名空间,ClassName是您的类的名称)。
试试这个:
using System;
using System.IO;
using System.Runtime.InteropServices;
namespace ComLib
{
[ComVisible(true)] // needs to be marked ComVisible
[Guid("ad4c28c9-4612-4ac3-8ca4-04a343f4f2b9")] // generate your own
public class LogWriter
{
public void WriteLine(string line)
{
using (var log = new StreamWriter(File.OpenWrite(@"c:\log.file")))
{
log.WriteLine(line);
}
}
}
}
这是我从.NET方面看到的。我没有任何尝试使用Ruby的经验。
如果您的Ruby进程是32位,它也会有所帮助。 VIsual Studio通常只在64位操作系统上使用32位运行时系统注册该类。
对于IDE外部的独立注册,请使用以下内容:
regasm.exe /tlb /codebase YourDll.dll
确保将regasm.exe用于正确的.NET运行时并更正32/64位风格。
如果你的DLL在COM上正确注册,它应该可以通过VBScript调用。制作一个名为Test.vbs的简单VBScript:
Dim obj
set obj = CreateObject("ComLib.LogWriter")
MsgBox TypeName(obj)
如果双击文件名,在资源管理器中或只是从命令行shell键入test.vbs,它将尝试使用c:\ windows \ system32 \ wscript.exe中的wscript.exe运行VBS程序。
它可能会在64位操作系统上失败,因为默认情况下VS仅为32位子系统注册COM组件。要尝试在32位子系统上运行它,请尝试:
c:\windows\syswow64\wscript.exe test.vbs
如果其中任何一种方法失败,那么您的DLL未正确注册。
答案 1 :(得分:0)
解决了它,似乎是一个相当奇怪的解决方案。
改变了这个:
lib = WIN32OLE.new('RubyToCSharp.ComLib.LogWriter')
对此:
lib = WIN32OLE.new('ComLib.LogWriter')
一切正常。