J'ai deux composants simples qui sont supposés communiquer entre eux en utilisant le modèle REQ/REP ZeroMQ. Serveur (REP Socket) est implémenté en Python en utilisant pyzmq:ZeroMQ FiniteStateMachineException dans le modèle REQ/REP
import zmq
def launch_server():
print "Launching server"
with zmq.Context.instance() as ctx:
socket = ctx.socket(zmq.REP)
socket.bind('tcp://127.0.0.1:5555')
while True:
msg = socket.recv()
print "EOM\n\n"
Le client (prise REQ) écrit en C# en utilisant la bibliothèque NetMQ:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using NetMQ;
namespace PyNetMQTest
{
class Program
{
static void Main(string[] args)
{
string msg;
NetMQ.Sockets.RequestSocket socket = new NetMQ.Sockets.RequestSocket();
socket.Connect("tcp://127.0.0.1:5555");
for(int i=0; i<5; i++)
socket.SendFrame("test_"+i);
}
}
}
L'implémentation Python Server a été testé et fonctionne bien en parlant à un socket REQ implémenté en utilisant Python. Mais la prise C# REQ jette l'erreur suivante dans la première itération de la boucle et aucun message atteindre le serveur que ce soit:
Une exception non gérée du type « NetMQ.FiniteStateMachineException » a eu lieu dans NetMQ.dll Informations complémentaires: Req. XSend - ne peut pas envoyer une autre demande
Stacktrace:
at NetMQ.Core.Patterns.Req.XSend(Msg& msg)
at NetMQ.Core.SocketBase.TrySend(Msg& msg, TimeSpan timeout, Boolean more)
at NetMQ.NetMQSocket.TrySend(Msg& msg, TimeSpan timeout, Boolean more)
at NetMQ.OutgoingSocketExtensions.Send(IOutgoingSocket socket, Msg& msg, Boolean more)
at NetMQ.OutgoingSocketExtensions.SendFrame(IOutgoingSocket socket, String message, Boolean more)
at PyNetMQTest.Program.Main(String[] args) in d:\users\emes\documents\visual studio 2015\Projects\PyNetMQ Test\PyNetMQTest\Program.cs:line 20
at System.AppDomain._nExecuteAssembly(RuntimeAssembly assembly, String[] args)
at System.AppDomain.ExecuteAssembly(String assemblyFile, Evidence assemblySecurity, String[] args)
at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()
at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Threading.ThreadHelper.ThreadStart()
Ce sont les premiers mes premiers pas avec ZMQ et le code C# est tiré de la bibliothèque documentation. Qu'est-ce qui fait que le code lance cette erreur?
J'utilise:
- pyzmq 14,7
- NetMQ 3.3.3.4
- .NET 4,6
========== ============ SOLUTION =====================
Comme expliqué par @somdoron dans sa réponse, la raison principale était que les deux sockets doivent passer par le cycle complet d'envoi/réception avant d'être capables d'être réutilisés. En fait, la socket REP implémentée en python n'a jamais changé son état, donc l'erreur était dans les deux, le python ET le code C#. Voici le code fixe:
REP Socket
import zmq
def launch_server():
print "Launching server"
with zmq.Context.instance() as ctx:
socket = ctx.socket(zmq.REP)
socket.bind('tcp://127.0.0.1:5555')
while True:
msg = socket.recv()
socket.send("reply to "+msg)
print "EOM\n\n"
REQ Socket
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using NetMQ;
namespace PyNetMQTest
{
class Program
{
static void Main(string[] args)
{
NetMQ.Sockets.RequestSocket socket = new NetMQ.Sockets.RequestSocket();
socket.Connect("tcp://127.0.0.1:5555");
string msg, reply;
while (true)
{
Console.WriteLine("Type message: ");
msg = Console.ReadLine();
Console.WriteLine("Sending : " + msg);
socket.SendFrame(msg);
reply = socket.ReceiveFrameString();
Console.WriteLine("Received: " + reply + Environment.NewLine);
}
}
}
}
Merci @somdoron! C'était ça! Je n'étais pas au courant du concept de machine d'état fini. Va ajouter le code corrigé au corps de la question. – EmEs