Dot Net Core dll 作为带有事件的 COM dll

Posted

技术标签:

【中文标题】Dot Net Core dll 作为带有事件的 COM dll【英文标题】:Dot Net Core dll as COM dll with events 【发布时间】:2021-03-19 09:27:41 【问题描述】:

鉴于可以在 Dot Net Core 中创建 COM dll,至少在 3.1 版以上...

是否有可能创建一个能够引发客户端应用程序(不是任何描述的 dot net)可以连接的 COM 事件的 COM dll?

我已经使用框架 3.5 中内置的 dll 成功地做到了这一点,但我在 CORE 中尝试了 3 次都没有成功。

有没有人成功地做到了这一点,并且有任何他们愿意分享的技巧或核心。

【问题讨论】:

好吧,我进行了庸医搜索,得到了这个结果docs.microsoft.com/en-us/dotnet/core/native-interop/… 谢谢,但我进行了同样的搜索,但对提高 com 事件没有帮助。 【参考方案1】:

是的,它可以正常工作。

这是一个 .NET Core 3.1 或 .NET 5 COM 类(或多或少遵循本教程并注册:Exposing .NET Core components to COM):

namespace ClassLibrary1

    [ComVisible(true)]
    [Guid("f39feec6-dd52-4da3-967a-c1e67de9346d")]
    [InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
    public interface IServer
    
        void ComputePi();
        double GetComputedPi();
    

    [ComVisible(true)]
    [Guid("5ff4acc2-2faa-4ea3-bae9-8c90fa67d75b")]
    [InterfaceType(ComInterfaceType.InterfaceIsIDispatch)] // this is marked obsolete in .NET Core 3.1 but not any more in .NET 5
    public interface IServerEvents
    
        [DispId(1234)]
        void OnPiComputed();
    

    [ComVisible(true)]
    [ClassInterface(ClassInterfaceType.None)]
    [ComSourceInterfaces(typeof(IServerEvents))] // this is marked obsolete in .NET Core 3.1 but not any more in .NET 5
    [Guid("32c58b14-b6fb-41f5-8368-52dc9289ae19")]
    public class Server : IServer
    
        private event OnPiComputedEvent OnPiComputed;

        public delegate void OnPiComputedEvent();

        public void ComputePi()
        
            Console.WriteLine("PI is being computed...");
            OnPiComputed?.Invoke();
        

        public double GetComputedPi() => Math.PI;
    

例如,.NET Framework COM 客户端(接口重新定义完全相同,但您可以创建通用类型库/.TLB 或共享 .cs):

class Program

    static void Main()
    
        var type = Type.GetTypeFromCLSID(new Guid("32c58b14-b6fb-41f5-8368-52dc9289ae19"));
        var obj = (IServer)Activator.CreateInstance(type);

        var container = (IConnectionPointContainer)obj;
        var iid = typeof(IServerEvents).GUID;
        container.FindConnectionPoint(ref iid, out var point);
        
        var sink = new ServerEvents();
        point.Advise(sink, out var cookie);
        
        obj.ComputePi();
        Console.ReadKey(true);

        point.Unadvise(cookie);
    


public class ServerEvents : IServerEvents

    public void OnPiComputed()
    
        Console.WriteLine("PI was computed!");
    


[ComVisible(true)]
[Guid("f39feec6-dd52-4da3-967a-c1e67de9346d")]
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
public interface IServer

    void ComputePi();
    double GetComputedPi();


[ComVisible(true)]
[Guid("5ff4acc2-2faa-4ea3-bae9-8c90fa67d75b")]
[InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]
public interface IServerEvents

    [DispId(1234)]
    void OnPiComputed();

运行时应显示:

PI is being computed...
PI was computed!

【讨论】:

是的,它将事件暴露为非 Dotnet COM 客户端可以捕获的东西是我的阻止程序。在 dot net core 中构建 dll 不会创建类型库,我不知道如何做到这一点,也不是我真正想做的事情。哦,好吧,也许 MS 会在一段时间内添加它 - 它在 Framework 中构建当然可以正常工作。 一种构建 .tlb 的方法:只需将 COM 定义复制粘贴到 .NET Framework 程序集中,然后使用 regasm /tlb 将其导出。然后,您可以按原样使用 .tlb 或使用 Windows SDK 中的 OleView 工具打开 .tlb,在新的 .idl 文件中提取您想要的部分并在其上运行 MIDL(来自 SDK 的编译器)以创建另一个 .tlb。

以上是关于Dot Net Core dll 作为带有事件的 COM dll的主要内容,如果未能解决你的问题,请参考以下文章

2. Note Dot Net Core CMD

Angular + core 如何将文件数组从 Angular 上传到 Dot Net Core

HTTP 错误 500.0 - Dot net core 3.1 中的 ASP.NET Core IIS 托管失败(进程中)

net反混淆脱壳工具de4dot的使用

调用put时出错,删除dot net core中的方法

如何使用WEB API Dot net core实现文件上传?