【问题标题】:Akka.NET Remote between Linux and WindowsLinux 和 Windows 之间的 Akka.NET Remote
【发布时间】:2016-08-12 12:22:48
【问题描述】:

我有一个分布式演员系统,一些在 Windows 上,一些在 Linux 机器上。有时一个参与者可能需要连接其他参与者并进行一些通信。当然,也有一种情况是在 Windows 上,另一种在 Linux 系统上。

Actor 通过 ActorSelection 相互连接。问题是,当 Windows 参与者尝试与 Linux 进行通信时,一切正常。但是当 Linux Actor 发起通信时,ActorSelection.ResolveOne 失败。

我在这里做了一个小样本:

static void Main(string[] args)
{
    ActorSystem system = ActorSystem.Create("TestSystem");
        system.ActorOf(Props.Create(() => new ConnectActor()), "test");

        while (true)
        {
            var address = Console.ReadLine();
            if (string.IsNullOrEmpty(address))
            {
                system.Terminate();
                return;
            }

            var remoteAddress = $"akka.tcp://{system.Name}@{address}/user/test";
            try
            {
                var actor = system.ActorSelection(remoteAddress).ResolveOne(TimeSpan.FromMilliseconds(5000)).Result;
                Console.WriteLine("Resolved: " + actor.Path);
            }
            catch (Exception ex)
            {
                Console.WriteLine("Failed: " + ex.Message);
            }
        }
}

app.config 中的配置如下:

akka {
          loggers = ["Akka.Logger.NLog.NLogLogger, Akka.Logger.NLog"]
          suppress-json-serializer-warning = on
          loglevel = "DEBUG"
          log-config-on-start = on

          actor {
            provider = "Akka.Remote.RemoteActorRefProvider, Akka.Remote"

            debug {
              receive = on
              autoreceive = on
              lifecycle = on
              event-stream = on
              unhandled = on
            }
          }

          remote {    
            log-remote-lifecycle-events = DEBUG
            log-received-messages = on

            helios.tcp {
                transport-class = "Akka.Remote.Transport.Helios.HeliosTcpTransport, Akka.Remote"
                transport-protocol = tcp
                applied-adapters = []
                port = 9000
                hostname = "0.0.0.0"
                public-hostname = "192.168.0.251" // This is different for different hosts, of course
            }
         }
      }

public-hostname 是公开的 ip 地址。

所以,以下是案例:

  • 在运行 Windows/Windows 时,两个实例可以互相看到(我给它们远程地址 - 它们输出“已解决”)
  • 在运行 Windows/Linux 时,将 linux actor 的地址提供给 windows actor,它会输出“Resolved”。所以windows连接linux没有问题。之后将 Windows Actor 的地址提供给 linux Actor 也会给出“已解决” - 我想,连接已经建立并且没有真正的握手传递
  • 但是当运行 Windiws/Linux 并将 windows actor 的地址提供给 linux actor 时,它给出“失败”。没有关于任何错误或丢弃包的消息。在日志的末尾有以下内容:

Akka.Remote.Transport.AkkaProtocolManager|现在监督 akka://TestSystem/system/transports/akkaprotocolmanager.tcp.0/akkaProtocol-tcp%3A%2F%2FTestSystem%40%5B%3A%3Affff%3A192.168.0 .252%5D%3A36983-1|||| 13:20:08.3766|DEBUGAkka.Remote.Transport.ProtocolStateActor|开始 (Akka.Remote.Transport.ProtocolStateActor)|||| 13:20:08.3922|调试|Akka.Remote.Transport.ProtocolStateActor|已停止||||

此处描述了类似日志的问题:Akka.net starting and stopping with no activity 原因是系统协议不兼容。这是同一个问题吗?正如我从 Akka.NET 文档和发行说明中获得的那样,它具有完整的 linux 支持......

那么,我是否在配置中遗漏了什么?任何人都可以让这个示例与 Linux -> Windows 连接一起使用吗?

【问题讨论】:

    标签: c# linux akka.net


    【解决方案1】:

    这里的问题似乎是 Mono 出于某种原因在其绑定地址中使用映射到 IPV4 的 IPV6 地址。

    akka://TestSystem/system/transports/akkaprotocolmanager.tcp.0/akkaProtocol-tcp%3A%2F%2FTestSystem%40%5B%3A%3Affff%3A192.168.0.252%5D%3A36983-1

    如果你解码这个被翻译成的 URL

    akkaProtocol-tcp://TestSystem@[::ffff:192.168.0.252]:36983-

    所以我认为这里发生的事情是 Helios 应该从中解析的出站地址在 Linux 端被搞砸了,因此它试图连接到一个与该地址不同的格式错误的地址Windows 监听。我怀疑演员选择 URI 解析代码中特定于平台的内容不正确。

    我在这里提交了一个错误:https://github.com/akkadotnet/akka.net/issues/2254

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-07-20
      • 2010-10-29
      • 2023-03-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多