具有 Chrome 原生消息传递功能的 C# 本机主机

本文关键字:本机 主机 功能 Chrome 原生 消息传递 具有 | 更新日期: 2023-09-27 17:56:32

我今天花了几个小时研究如何让Chrome原生消息与C#原生主机一起工作。从概念上讲,这很简单,但是我在以下其他问题的帮助下(部分)解决了一些障碍:

原生消息传递浏览器
从 chrome 扩展程序到用 C#
编写的本机主机的本机消息传递将"大量"数据从Chrome扩展程序传递到主机的速度非常慢(用C#编写)

我的解决方案发布在下面。

具有 Chrome 原生消息传递功能的 C# 本机主机

假设清单设置正确,下面是使用"port"方法与 C# 主机通信的完整示例:

using System;
using System.IO;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
namespace NativeMessagingHost
{
   class Program
   {
      public static void Main(string[] args)
      {
         JObject data;
         while ((data = Read()) != null)
         {
            var processed = ProcessMessage(data);
            Write(processed);
            if (processed == "exit")
            {
               return;
            }
         }
      }
      public static string ProcessMessage(JObject data)
      {
         var message = data["text"].Value<string>();
         switch (message)
         {
            case "test":
               return "testing!";
            case "exit":
               return "exit";
            default:
               return "echo: " + message;
         }
      }
      public static JObject Read()
      {
         var stdin = Console.OpenStandardInput();
         var length = 0;
         var lengthBytes = new byte[4];
         stdin.Read(lengthBytes, 0, 4);
         length = BitConverter.ToInt32(lengthBytes, 0);
         var buffer = new char[length];
         using (var reader = new StreamReader(stdin))
         {
            while (reader.Peek() >= 0)
            {
               reader.Read(buffer, 0, buffer.Length);
            }
         }
         return (JObject)JsonConvert.DeserializeObject<JObject>(new string(buffer));
      }
      public static void Write(JToken data)
      {
         var json = new JObject();
         json["data"] = data;
         var bytes = System.Text.Encoding.UTF8.GetBytes(json.ToString(Formatting.None));
         var stdout = Console.OpenStandardOutput();
         stdout.WriteByte((byte)((bytes.Length >> 0) & 0xFF));
         stdout.WriteByte((byte)((bytes.Length >> 8) & 0xFF));
         stdout.WriteByte((byte)((bytes.Length >> 16) & 0xFF));
         stdout.WriteByte((byte)((bytes.Length >> 24) & 0xFF));
         stdout.Write(bytes, 0, bytes.Length);
         stdout.Flush();
      }
   }
}

如果您不需要主动与主机通信,则使用 runtime.sendNativeMessage 就可以正常工作。为防止主机挂起,只需删除while循环并执行一次读/写。

为了测试这一点,我在这里使用了谷歌提供的示例项目:https://chromium.googlesource.com/chromium/src/+/master/chrome/common/extensions/docs/examples/api/nativeMessaging

注意:我正在使用 Json.NET 来简化 json 序列化/反序列化过程。

我希望这对某人有所帮助!

您也可以使用常规的 http 通信。并使用 fetch 或其他 js API 发送消息。主机应用程序将是在本地主机上运行的常规Web api项目。您还需要在 Web 应用中启用 cors 策略。也许在某些情况下矫枉过正,而且可能没有那么快。但它对大多数开发人员来说更加透明,并且在我的项目中效果很好。