2014-03-28 12 views
6

Ich versuche, eine einfache Nachricht zwischen zwei Anwendungen mithilfe von NetMQ zu implementieren (eine etwas ausführlichere Beschreibung dessen, was ich versuche, ist unten).
Nach ein wenig Versuch und Irrtum habe ich festgestellt, dass ich Nachrichten nicht sofort nach einem Connect/Bind-Aufruf senden oder empfangen kann, da sie nicht blockiert sind und tatsächlich zurückkommen, auch wenn die Verbindung noch nicht hergestellt wurde .
Für jetzt habe ich das mit Thread.Sleep() gelöst, aber das hat einen schlechten Geschmack und definitiv ein No-Go für ein Produktionssystem.Was ist der richtige Weg, auf Verbindungen zu warten?

Die Frage ist also, wie soll man das in NetMQ/ZeroMQ machen?

Client-Beispiel:

 using (NetMQContext ctx = NetMQContext.Create()) 
     { 
      using (var client = ctx.CreatePushSocket()) 
      { 
       client.Connect("tcp://127.0.0.1:5555"); 
       Thread.Sleep(100); // wait for connection 

       for (int i = 0; i < 5; i++) 
       { 
        client.Send("test " + i , true); 
       } 
      } 
     } 
    } 

Server Beispiel:

using (NetMQContext ctx = NetMQContext.Create()) 
    { 
     using (var server = ctx.CreatePullSocket()) 
     { 
      server.Bind("tcp://127.0.0.1:5555"); 
      Thread.Sleep(100); // wait for connection 
      while (true) 
      { 
       var str = server.ReceiveString(); 
       Console.Out.WriteLine(str); 
       Thread.Sleep(60*1000); // do msg processing 
      } 
     } 
    } 

Beschreibung von dem, was ich zu erreichen versuchen:

Client- - Sendet Nachrichten an einen einzelnen Server. Der Client sollte keine Nachrichten blockieren und nicht verwerfen, wenn der Server nicht verfügbar ist. Der Kunde kann jederzeit offline/online gehen.

Server - Empfängt Nachrichten von einem einzelnen Client. Der Server blockiert, bis eine Nachricht empfangen wird. Der Server muss die Nachricht lange verarbeiten und darf während der Verarbeitung keine anderen Nachrichten verlieren. Der Server kann jederzeit offline/online gehen.

+0

Das Beispiel auf der Netmq-Site führt "True" nicht in "Send". –

Antwort

5

Die beste Lösung für Ihren Schlaf auf der Server-Seite besteht darin, einen Socket-Poller zu erstellen und am Pull-Socket abzufragen, bis eine Nachricht empfangen wird. Dies vermeidet verschwenderisches Schlafen und sorgt für allgemein engeren Code.

Auf der Clientseite besteht die beste Lösung wahrscheinlich darin, zwei Sockets zu erstellen (einen für das Senden von Nachrichten, einen für den Empfang) und den Server seine Anwesenheit ankündigen zu lassen, damit der Client die Nachricht senden kann. Da ZeroMQ mehrere Verbindungen effizient verarbeitet, wird diese Lösung sehr gut funktionieren.

9

sowohl empfangen und senden können warten, bis ausgeführt werden kann, Sie übergeben, um dontWait Parameter in Ihrem Beispiel zu trauen, nur entfernen Sie es und es wird die Nachricht senden, wenn es möglich ist.

Für den Empfang müssen Sie nicht schlafen, weil es warten wird, bis die Nachricht verfügbar ist.

Wie vorgeschlagen mit Poller ist auch eine Lösung (Sie können abfragen, wenn der Socket senden kann und wenn Nachrichten bereit sind, verbraucht werden), werfen Sie einen Blick auf die Prüfung für Poller-Klasse: https://github.com/zeromq/netmq/blob/3.3.3-rc5/src/NetMQ.Tests/PollerTests.cs.

Verwandte Themen