/// <summary> /// Initializes a new instance of the <see cref="DeviceBase"/> class. /// </summary> /// <param name="frontendSocket"> /// A <see cref="NetMQSocket"/> that will pass incoming messages to <paramref name="backendSocket"/>. /// </param> /// <param name="backendSocket"> /// A <see cref="NetMQSocket"/> that will receive messages from (and optionally send replies to) <paramref name="frontendSocket"/>. /// </param> /// <param name="mode">The <see cref="DeviceMode"/> for the current device.</param> /// <param name="poller">The <see cref="Poller"/> to use.</param> protected DeviceBase(Poller poller, NetMQSocket frontendSocket, NetMQSocket backendSocket, DeviceMode mode) { if (frontendSocket == null) throw new ArgumentNullException("frontendSocket"); if (backendSocket == null) throw new ArgumentNullException("backendSocket"); FrontendSocket = frontendSocket; BackendSocket = backendSocket; FrontendSetup = new DeviceSocketSetup(FrontendSocket); BackendSetup = new DeviceSocketSetup(BackendSocket); m_poller = poller; FrontendSocket.ReceiveReady += FrontendHandler; BackendSocket.ReceiveReady += BackendHandler; m_poller.AddSocket(FrontendSocket); m_poller.AddSocket(BackendSocket); m_runner = mode == DeviceMode.Blocking ? new DeviceRunner(this) : new ThreadedDeviceRunner(this); }
public void TwoMessagesFromRouterToDealer() { using (var context = NetMQContext.Create()) using (var poller = new Poller()) using (var server = context.CreateRouterSocket()) using (var client = context.CreateDealerSocket()) { var port = server.BindRandomPort("tcp://*"); client.Connect("tcp://127.0.0.1:" + port); poller.AddSocket(client); var cnt = 0; client.ReceiveReady += (object sender, NetMQSocketEventArgs e) => { var strs = e.Socket.ReceiveMultipartStrings(); foreach (var str in strs) { Console.WriteLine(str); } cnt++; if (cnt == 2) { poller.Cancel(); } }; byte[] clientId = Encoding.Unicode.GetBytes("ClientId"); client.Options.Identity = clientId; const string request = "GET /\r\n"; const string response = "HTTP/1.0 200 OK\r\n" + "Content-Type: text/plain\r\n" + "\r\n" + "Hello, World!"; client.SendFrame(request); byte[] serverId = server.ReceiveFrameBytes(); Assert.AreEqual(request, server.ReceiveFrameString()); // two messages in a row, not frames server.SendMoreFrame(serverId).SendFrame(response); server.SendMoreFrame(serverId).SendFrame(response); poller.PollTimeout = 1000; poller.PollTillCancelled(); } }
public void Send_WrongServiceNameWithLogging_ShouldLogPermanentError() { const string hostAddress = "tcp://localhost:5555"; var loggingMessages = new List <string>(); // setup the counter socket for communication using (var context = NetMQContext.Create()) using (var broker = context.CreateRouterSocket()) using (var poller = new Poller()) using (var session = new MDPClient(hostAddress)) { broker.Bind(hostAddress); // we need to pick up any message in order to avoid errors broker.ReceiveReady += (s, e) => { // just swallow message -> wrong service name e.Socket.ReceiveMultipartMessage(); }; poller.AddSocket(broker); Task.Factory.StartNew(poller.PollTillCancelled); // set the event handler to receive the logging messages session.LogInfoReady += (s, e) => loggingMessages.Add(e.Info); // well formed message var requestMessage = new NetMQMessage(new[] { new NetMQFrame("REQUEST") }); // wrong service name session.Send("xyz", requestMessage); poller.CancelAndJoin(); poller.RemoveSocket(broker); Assert.That(loggingMessages.Count, Is.EqualTo(7)); Assert.That(loggingMessages[6], Is.EqualTo("[CLIENT ERROR] permanent error, abandoning!")); } }
public void Run(params string[] addresses) { using (m_context = NetMQContext.Create()) { var subscriber = Connect(addresses); if (subscriber == null) { throw new Exception("cannot connect to eny of the endpoints"); } // timeout timer, when heartbeat was not arrived for 5 seconds m_timeoutTimer = new NetMQTimer(TimeSpan.FromSeconds(5)); m_timeoutTimer.Elapsed += (sender, args) => { // timeout happend, first dispose existing subscriber subscriber.Dispose(); m_poller.RemoveSocket(subscriber); // connect again subscriber = Connect(addresses); if (subscriber == null) { throw new Exception("cannot connect to eny of the endpoints"); } m_poller.AddSocket(subscriber); }; m_poller = new Poller(subscriber); m_poller.AddTimer(m_timeoutTimer); m_poller.PollTillCancelled(); } }
public void WithPoller() { using (NetMQContext context = NetMQContext.Create()) using (NetMQQueue <int> queue = new NetMQQueue <int>(context)) { Poller poller = new Poller(); poller.AddSocket(queue); ManualResetEvent manualResetEvent = new ManualResetEvent(false); queue.ReceiveReady += (sender, args) => { manualResetEvent.Set(); }; poller.PollTillCancelledNonBlocking(); Assert.IsFalse(manualResetEvent.WaitOne(100)); queue.Enqueue(1); Assert.IsTrue(manualResetEvent.WaitOne(100)); poller.CancelAndJoin(); } }
public void WithPoller() { using (NetMQContext context = NetMQContext.Create()) using (NetMQQueue<int> queue = new NetMQQueue<int>(context)) { Poller poller = new Poller(); poller.AddSocket(queue); ManualResetEvent manualResetEvent = new ManualResetEvent(false); queue.ReceiveReady += (sender, args) => { manualResetEvent.Set(); }; poller.PollTillCancelledNonBlocking(); Assert.IsFalse(manualResetEvent.WaitOne(100)); queue.Enqueue(1); Assert.IsTrue(manualResetEvent.WaitOne(100)); poller.CancelAndJoin(); } }
public void AttachToPoller(Poller poller) { InternalStart(); m_attachedPoller = poller; poller.AddSocket(MonitoringSocket); }
public void AddTwoSocketAfterRemoving() { using (var context = NetMQContext.Create()) using (var router1 = context.CreateRouterSocket()) using (var router2 = context.CreateRouterSocket()) using (var router3 = context.CreateRouterSocket()) using (var router4 = context.CreateRouterSocket()) using (var dealer1 = context.CreateDealerSocket()) using (var dealer2 = context.CreateDealerSocket()) using (var dealer3 = context.CreateDealerSocket()) using (var dealer4 = context.CreateDealerSocket()) using (var poller = new Poller(router1, router2) { PollTimeout = TestPollTimeoutMillis }) { int port1 = router1.BindRandomPort("tcp://127.0.0.1"); int port2 = router2.BindRandomPort("tcp://127.0.0.1"); int port3 = router3.BindRandomPort("tcp://127.0.0.1"); int port4 = router4.BindRandomPort("tcp://127.0.0.1"); dealer1.Connect("tcp://127.0.0.1:" + port1); dealer2.Connect("tcp://127.0.0.1:" + port2); dealer3.Connect("tcp://127.0.0.1:" + port3); dealer4.Connect("tcp://127.0.0.1:" + port4); int router1Arrived = 0; int router2Arrived = 0; bool router3Arrived = false; bool router4Arrived = false; var signal1 = new ManualResetEvent(false); var signal2 = new ManualResetEvent(false); var signal3 = new ManualResetEvent(false); var signal4 = new ManualResetEvent(false); router1.ReceiveReady += (s, e) => { router1Arrived++; router1.SkipFrame(); // identity router1.SkipFrame(); // message poller.RemoveSocket(router1); signal1.Set(); }; router2.ReceiveReady += (s, e) => { router2Arrived++; router2.SkipFrame(); // identity router2.SkipFrame(); // message if (router2Arrived == 1) { poller.AddSocket(router3); poller.AddSocket(router4); signal2.Set(); } }; router3.ReceiveReady += (s, e) => { router3.SkipFrame(); // identity router3.SkipFrame(); // message router3Arrived = true; signal3.Set(); }; router4.ReceiveReady += (s, e) => { router4.SkipFrame(); // identity router4.SkipFrame(); // message router4Arrived = true; signal4.Set(); }; poller.PollTillCancelledNonBlocking(); dealer1.Send("1"); Assert.IsTrue(signal1.WaitOne(300)); dealer2.Send("2"); Assert.IsTrue(signal2.WaitOne(300)); dealer3.Send("3"); dealer4.Send("4"); dealer2.Send("2"); dealer1.Send("1"); Assert.IsTrue(signal3.WaitOne(300)); Assert.IsTrue(signal4.WaitOne(300)); poller.CancelAndJoin(); router1.SkipFrame(); bool more; Assert.AreEqual("1", router1.ReceiveFrameString(out more)); Assert.IsFalse(more); Assert.AreEqual(1, router1Arrived); Assert.AreEqual(2, router2Arrived); Assert.IsTrue(router3Arrived); Assert.IsTrue(router4Arrived); } }
public void Run() { Console.WriteLine("[CLIENT {0}] Starting", m_id); var rnd = new Random(m_id); // each request shall have an unique id in order to recognize an reply for a request var messageId = new byte[5]; // create clientId for messages var clientId = new[] { m_id }; // a flag to signal that an answer has arrived bool messageAnswered = false; // we use a poller because we have a socket and a timer to monitor var clientPoller = new Poller(); using (var ctx = NetMQContext.Create()) using (var client = ctx.CreateRequestSocket()) using (var monitor = ctx.CreatePushSocket()) { client.Connect(m_localFrontendAddress); monitor.Connect(m_monitorAddress); client.Options.Identity = new[] { m_id }; var timer = new NetMQTimer((int)TimeSpan.FromSeconds(10).TotalMilliseconds); // use as flag to indicate exit var exit = false; // every 10 s check if message has been received, if not then send error message and ext // and restart timer otherwise timer.Elapsed += (s, e) => { if (messageAnswered) { e.Timer.Enable = true; } else { var msg = string.Format("[CLIENT {0}] ERR - EXIT - lost message {1}", m_id, messageId); // send an error message monitor.Send(msg); // if poller is started than stop it if (clientPoller.IsStarted) { clientPoller.CancelAndJoin(); } // mark the required exit exit = true; } }; // process arriving answers client.ReceiveReady += (s, e) => { // mark the arrival of an answer messageAnswered = true; // worker is supposed to answer with our request id var reply = e.Socket.ReceiveMessage(); if (reply.FrameCount == 0) { // something went wrong monitor.Send(string.Format("[CLIENT {0}] Received an empty message!", m_id)); // mark the exit flag to ensure the exit exit = true; } else { var sb = new StringBuilder(); // create success message foreach (var frame in reply) { sb.Append("[" + frame.ConvertToString() + "]"); } // send the success message monitor.Send(string.Format("[CLIENT {0}] Received answer {1}", m_id, sb.ToString())); } }; // add socket & timer to poller clientPoller.AddSocket(client); clientPoller.AddTimer(timer); // start poller in extra task in order to allow the continued processing // clientPoller.Start() -> blocking call var pollTask = Task.Factory.StartNew(clientPoller.PollTillCancelled); // if true the message has been answered // the 0th message is always answered messageAnswered = true; while (exit == false) { // simulate sporadic activity by randomly delaying Thread.Sleep((int)TimeSpan.FromSeconds(rnd.Next(5)).TotalMilliseconds); // only send next message if the previous one has been replied to if (messageAnswered) { // generate random 5 byte as identity for for the message rnd.NextBytes(messageId); messageAnswered = false; // create message [client adr][empty][message id] and send it var msg = new NetMQMessage(); msg.Push(messageId); msg.Push(NetMQFrame.Empty); msg.Push(clientId); client.SendMessage(msg); } } } // stop poller if needed if (clientPoller.IsStarted) { clientPoller.CancelAndJoin(); } clientPoller.Dispose(); }
public void AddSocketAfterRemoving() { using (NetMQContext contex = NetMQContext.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (var router = contex.CreateRouterSocket()) using (var router2 = contex.CreateRouterSocket()) using (var router3 = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); router2.Bind("tcp://127.0.0.1:5003"); router3.Bind("tcp://127.0.0.1:5004"); using (var dealer = contex.CreateDealerSocket()) using (var dealer2 = contex.CreateDealerSocket()) using (var dealer3 = contex.CreateDealerSocket()) using (Poller poller = new Poller()) { dealer.Connect("tcp://127.0.0.1:5002"); dealer2.Connect("tcp://127.0.0.1:5003"); dealer3.Connect("tcp://127.0.0.1:5004"); bool router1arrived = false; bool router2arrived = false; bool router3arrived = false; bool more; router.ReceiveReady += (s, a) => { router1arrived = true; router.Receive(out more); router.Receive(out more); poller.RemoveSocket(router); }; poller.AddSocket(router); router3.ReceiveReady += (s, a) => { router3.Receive(out more); router3.Receive(out more); router3arrived = true; }; router2.ReceiveReady += (s, a) => { router2arrived = true; router2.Receive(out more); router2.Receive(out more); poller.AddSocket(router3); }; poller.AddSocket(router2); poller.PollTillCancelledNonBlocking(); dealer.Send("1"); Thread.Sleep(300); dealer2.Send("2"); Thread.Sleep(300); dealer3.Send("3"); Thread.Sleep(300); poller.Stop(true); Assert.IsTrue(router1arrived); Assert.IsTrue(router2arrived); Assert.IsTrue(router3arrived); } } } }
public void Receive_REPLYtoREQUEST_ShouldSendCorrectReply() { const string hostAddress = "tcp://localhost:5557"; var loggingMessages = new List <string> (); // setup the counter socket for communication using (var context = NetMQContext.Create()) using (var broker = context.CreateRouterSocket()) using (var poller = new Poller()) using (var session = new MDPWorker(hostAddress, "test", new[] { (byte)'W', (byte)'1' })) { broker.Bind(hostAddress); // we need to pick up any message in order to avoid errors broker.ReceiveReady += (s, e) => { var msg = e.Socket.ReceiveMultipartMessage(); if (msg[3].Buffer[0] == (byte)MDPCommand.Ready) { // this is a READY message and we // send REQUEST message var request = new NetMQMessage(); request.Push("echo test"); // [request] request.Push(NetMQFrame.Empty); // [e][request] request.Push("C1"); // [client adr][e][request] request.Push(new[] { (byte)MDPCommand.Request }); // [command][client adr][e][request] request.Push(msg[2]); // [header][command][client adr][e][request] request.Push(NetMQFrame.Empty); // [e][header][command][client adr][e][request] request.Push(msg[0]); // [worker adr][e][header][command][client adr][e][request] // send reply which is a request for the worker e.Socket.SendMessage(request); } if (msg[3].Buffer[0] == (byte)MDPCommand.Reply) { // we expect to receive // [WORKER ADR][e]["MDPW01"][REPLY][CLIENT ADR][e][request == "echo test"] // make sure the frames are as expected Assert.That(msg[0].ConvertToString(), Is.EqualTo("W1")); Assert.That(msg[1], Is.EqualTo(NetMQFrame.Empty)); Assert.That(msg[2].ConvertToString(), Is.EqualTo("MDPW01")); Assert.That(msg[3].BufferSize, Is.EqualTo(1)); Assert.That(msg[3].Buffer[0], Is.EqualTo((byte)MDPCommand.Reply)); Assert.That(msg[4].ConvertToString(), Is.EqualTo("C1")); Assert.That(msg[5], Is.EqualTo(NetMQFrame.Empty)); Assert.That(msg[6].ConvertToString(), Is.EqualTo("echo test")); // tell worker to stop gracefully var reply = new NetMQMessage(); reply.Push(new[] { (byte)MDPCommand.Kill }); // push MDP Version reply.Push(msg[2]); // push separator reply.Push(NetMQFrame.Empty); // push worker address reply.Push(msg[0]); // send reply which is a request for the worker e.Socket.SendMessage(reply); } }; poller.AddSocket(broker); Task.Factory.StartNew(poller.PollTillCancelled); // set the event handler to receive the logging messages session.LogInfoReady += (s, e) => loggingMessages.Add(e.Info); // initialise the worker - broker protocol // and get initial request var workerRequest = session.Receive(null); // just echo the request session.Receive(workerRequest); poller.CancelAndJoin(); poller.RemoveSocket(broker); Assert.That(loggingMessages.Count, Is.EqualTo(8)); Assert.That(loggingMessages[0], Is.EqualTo("[WORKER] connected to broker at tcp://localhost:5557")); Assert.That(loggingMessages[1].Contains("Ready")); Assert.That(loggingMessages[2].Contains("[WORKER] received")); Assert.That(loggingMessages[3].Contains("Request")); Assert.That(loggingMessages[4].Contains("Reply")); Assert.That(loggingMessages[6].Contains("Kill")); Assert.That(loggingMessages[7].Contains("abandoning")); } }
private void initClientR() { poller = new Poller(); { //clientR = context.CreateSubscriberSocket(); //clientS = context.CreatePushSocket(); { try { createRSocket(); createSSocket(); } catch (Exception ex) { DCLogger.LogError("Exception in connect work:{0}", ex.Message); } //r & s clientR.ReceiveReady += (sender, eventArgs) => { try { List <byte[]> dataLst = new List <byte[]>(); clientR.ReceiveMultipartBytes(ref dataLst, 2); //if (dataLst.Count != 2) // return; byte[] envelope = dataLst[0]; byte[] data = dataLst[1]; //if (envelope == null) // return; if (DCUtil.BytesStart(Global.DC_CTRL_HB, envelope)) { lastTicksOfHb = BitConverter.ToInt64(data, 0); DCLogger.LogInfo("Server's HeartBeat received: {0}", new DateTime(lastTicksOfHb)); } #region pubDataR 处理Sub接口订阅的数据 else if (DCUtil.BytesStart(Global.DC_HEAD_PS_PUB_BYTES, envelope)) { string envelopeStr = Global.Encoding.GetString(envelope); string envelopeStr0 = string.Concat(Global.DC_HEAD_PS_PUB, Global.ENVELOPE_SPLITTER, envelopeStr.Split(new string[] { Global.ENVELOPE_SPLITTER }, StringSplitOptions.None)[1]); //Console.WriteLine("keys:" + string.Concat(clientRHands.Keys) + "_key:" + envelopeStr); ConcurrentDictionary <Action <byte[]>, object> actions; bool envelopeStrBingo = false; if (subHands.TryGetValue(envelopeStr, out actions)) { envelopeStrBingo = true; foreach (Action <byte[]> handler in actions.Keys) { if (handler != null) { handler(data); } } } if (!envelopeStrBingo) { if (subHands.TryGetValue(envelopeStr0, out actions)) { foreach (Action <byte[]> handler in actions.Keys) { if (handler != null) { try { handler(data); } catch (Exception ex) { DCLogger.LogError("Exception occured when handling pub's data:{0}", ex.Message); } } } } } } #endregion #region actDataR 处理Srv接口接收的Act请求 else if (DCUtil.BytesStart(Global.DC_HEAD_AS_ACT_BYTES, envelope)) { string envelopeStr = Global.Encoding.GetString(envelope); string[] actDetail = envelopeStr.Split(new string[] { Global.ENVELOPE_SPLITTER }, StringSplitOptions.None); if (srvTypes.ContainsKey(actDetail[1 + 1])) { Thread inlineThread = new Thread(new ThreadStart(delegate() { byte[] actResultData = null; string replySn = "0"; string extInfo = string.Empty; string lastSlice = actDetail[actDetail.Length - 1]; try { replySn = actDetail[1 + 3]; int idx = lastSlice.IndexOf("?"); if (idx > 0) { extInfo = lastSlice.Substring(idx + 1); } actResultData = srvTypes[actDetail[1 + 1]](extInfo, data); } catch (Exception ex) { string srvSideException = string.Format("Srv side exception [{0}][{1}]: ", id, actDetail[1 + 1]) + ex.Message; actResultData = Global.Encoding.GetBytes(Global.Encoding.GetString(Global.DC_RPLY_EXCEPTION) + srvSideException); DCLogger.LogError(srvSideException); } if (actResultData == null) { actResultData = Global.DC_NULL_RPLY; } lock (clientSSync) { try { clientS.SendMultipartBytes(Global.Encoding.GetBytes(string.Concat(Global.DC_HEAD_AS_RPLY, Global.ENVELOPE_SPLITTER, actDetail[1 + 2], Global.ENVELOPE_SPLITTER, actDetail[1 + 1], Global.ENVELOPE_SPLITTER, id, Global.ENVELOPE_SPLITTER, replySn)), actResultData); } catch (Exception ex) { DCLogger.LogError("Exception occured when srv sending reply data back:{0}", ex.Message); } } } )); inlineThread.IsBackground = true; inlineThread.Start(); } } #endregion #region srvRplyDataR 处理Act请求的Srv Reply else if (DCUtil.BytesStart(Global.DC_HEAD_AS_RPLY_BYTES, envelope)) { string envelopeStr = Global.Encoding.GetString(envelope); if (DCUtil.BytesEqual(Global.DC_NULL_RPLY, data)) { data = null; } string[] replyDetail = envelopeStr.Split(new string[] { Global.ENVELOPE_SPLITTER }, StringSplitOptions.None); int snKey = int.Parse(replyDetail[1 + 3]); System.Diagnostics.Debug.WriteLine("ActResult received [{0}]", snKey); Action <ActResult> handler; if (actResultHands.TryGetValue(snKey, out handler)) { ActResult ar = new ActResult { ResultData = data, Type = replyDetail[1 + 1], Src = replyDetail[1 + 2], ActSn = int.Parse(replyDetail[1 + 3]) }; actResultHands.TryRemove(snKey, out handler); System.Diagnostics.Debug.WriteLine("Act Key removed [{0}]", snKey); if (DCUtil.BytesStart(Global.DC_RPLY_EXCEPTION, ar.ResultData)) { ar.Exception = new Exception(Global.Encoding.GetString(ar.ResultData, Global.DC_RPLY_EXCEPTION.Length, ar.ResultData.Length - Global.DC_RPLY_EXCEPTION.Length)); } try { //Task.Factory.StartNew(() =>handler(ar)); ThreadPool.QueueUserWorkItem(o => { ActResult ar_real = ar as ActResult; handler(ar_real); }, ar); } catch (Exception ex) { DCLogger.LogError("Exception occured when act handling srv's reply data:{0}", ex.Message); } StringAndTime tnt = new StringAndTime { UniqueString = ar.Src, LastRefresh = DateTime.Now.Ticks }; type2Srv.AddOrUpdate( ar.Type, new List <StringAndTime>(), (key, oldValue) => { if (oldValue.Contains(tnt)) { oldValue[oldValue.IndexOf(tnt)].LastRefresh = DateTime.Now.Ticks; } else { oldValue.Add(tnt); //Console.WriteLine("List<TypeAndTime>.Count: {0}", oldValue.Count); } //DCLogger.LogTrace("Refresh valid datetime of srv [{0}] type [{1}]", ar.Src, ar.Type); return(oldValue); } ); } } #endregion #region sndDataR 处理Rcv接口接受的数据 else if (DCUtil.BytesStart(Global.DC_HEAD_SR_SND_BYTES, envelope)) { string envelopeStr = Global.Encoding.GetString(envelope); ConcurrentDictionary <Action <byte[]>, object> actions; if (rcvHands.TryGetValue(envelopeStr, out actions)) { foreach (Action <byte[]> handler in actions.Keys) { if (handler != null) { try { handler(data); } catch (Exception ex) { DCLogger.LogError("Exception occured when rcv handling snd's data:{0}", ex.Message); } } } } } #endregion } catch (Exception ex) { DCLogger.LogError("Exception in receive data proc work:{0}", ex.Message); } }; poller.AddSocket(clientR); // send report every 8 seconds NetMQTimer heartbeatTimer = new NetMQTimer(5000); poller.AddTimer(heartbeatTimer); heartbeatTimer.Elapsed += (sender, eventArgs) => { try { if (lastTicksOfHb > 0 && (DateTime.Now.Ticks - lastTicksOfHb) > (38 * 10000000)) { DCLogger.LogError("Server's connection losed"); reconnect(); //new System.Threading.Tasks.Task(() => reconnect()).Start(); } IEnumerator <string> itor = this.srvTypes.Keys.GetEnumerator(); List <CltSrvInfo> srvInfos = new List <CltSrvInfo>(); while (itor.MoveNext()) { if (!itor.Current.Equals(Global.DC_CTRL_PING)) { srvInfos.Add(new CltSrvInfo { ClientId = this.id, ClientSrvType = itor.Current }); } } if (srvInfos.Count > 0) { byte[] data = DCSerializer.ObjToBytes(srvInfos); Task.Factory.StartNew(() => this.Act(Global.DC_DIR_CLTSRVINFO_RPT, Global.DC_DIR_SRVID, data, 5) ); DCLogger.LogInfo("Report client status ok."); } } catch (TimeoutException) { DCLogger.LogError("Report client status failed."); } catch (Exception ex) { DCLogger.LogError("Report detect a unhandled error:{0}", ex.Message); } }; poller.PollTillCancelled(); } } }
public void Evaluate(int SpreadMax) { if (FFrontendSocket.SliceCount == 0 || (FFrontendSocket.SliceCount == 1 && FFrontendSocket[0] == null) || FBackendSocket.SliceCount == 0 || (FBackendSocket.SliceCount == 1 && FBackendSocket[0] == null)) { return; } if (FEnable.IsChanged && !FEnable[0]) { foreach (var p in Proxies) { try { p.Stop(); } catch (InvalidOperationException e) { FLogger.Log(LogType.Warning, "\nvvvv.ZeroMQ: Proxy cannot be stopped. " + e.Message); } } } // spreading could cause weird behaviour, when multiple proxies feed on the same sockets SpreadMax = FFrontendSocket.CombineWith(FBackendSocket); for (int i = 0; i < SpreadMax; i++) { var backend = (NetMQSocket)FBackendSocket[i]; var frontend = (NetMQSocket)FFrontendSocket[i]; if (frontend == null || backend == null) { continue; } if (FEnable.IsChanged && FEnable[i]) { // FRONTEND try { Poll.AddSocket(frontend); } catch (ArgumentException) { FLogger.Log(LogType.Message, "\nvvvv.ZeroMQ: Socket already added to Poller in Proxy. Nothing to worry about."); } catch (ObjectDisposedException) { FLogger.Log(LogType.Error, "\nvvvv.ZeroMQ: Cannot add Socket to Proxy, already disposed."); } // BACKEND try { Poll.AddSocket(backend); } catch (ArgumentException) { FLogger.Log(LogType.Error, "\nvvvv.ZeroMQ: Socket already added to Poller in Proxy. Nothing to worry about."); } catch (ObjectDisposedException) { FLogger.Log(LogType.Error, "\nvvvv.ZeroMQ: Cannot add Socket to Proxy, already disposed."); } // PROXY try { var p = new Proxy(frontend, backend, null, Poll); p.Start(); // nonblocking from now on Proxies.Add(p); } catch (InvalidOperationException e) { FLogger.Log(LogType.Error, "\nvvvv.ZeroMQ: start Proxy failed.\n" + e); } } } }
public void AddSocketDuringWork() { using (var context = NetMQContext.Create()) using (var router1 = context.CreateRouterSocket()) using (var router2 = context.CreateRouterSocket()) using (var dealer1 = context.CreateDealerSocket()) using (var dealer2 = context.CreateDealerSocket()) using (var poller = new Poller(router1) { PollTimeout = TestPollTimeoutMillis }) { int port1 = router1.BindRandomPort("tcp://127.0.0.1"); int port2 = router2.BindRandomPort("tcp://127.0.0.1"); dealer1.Connect("tcp://127.0.0.1:" + port1); dealer2.Connect("tcp://127.0.0.1:" + port2); bool router1Arrived = false; bool router2Arrived = false; var signal1 = new ManualResetEvent(false); var signal2 = new ManualResetEvent(false); router1.ReceiveReady += (s, e) => { router1.SkipFrame(); router1.SkipFrame(); router1Arrived = true; poller.AddSocket(router2); signal1.Set(); }; router2.ReceiveReady += (s, e) => { router2.SkipFrame(); router2.SkipFrame(); router2Arrived = true; signal2.Set(); }; poller.PollTillCancelledNonBlocking(); dealer1.SendFrame("1"); Assert.IsTrue(signal1.WaitOne(300)); dealer2.SendFrame("2"); Assert.IsTrue(signal1.WaitOne(300)); poller.CancelAndJoin(); Assert.IsTrue(router1Arrived); Assert.IsTrue(router2Arrived); } }
public void AddTwoSocketAfterRemoving() { using (var context = NetMQContext.Create()) using (var router1 = context.CreateRouterSocket()) using (var router2 = context.CreateRouterSocket()) using (var router3 = context.CreateRouterSocket()) using (var router4 = context.CreateRouterSocket()) using (var dealer1 = context.CreateDealerSocket()) using (var dealer2 = context.CreateDealerSocket()) using (var dealer3 = context.CreateDealerSocket()) using (var dealer4 = context.CreateDealerSocket()) using (var poller = new Poller(router1, router2) { PollTimeout = TestPollTimeoutMillis }) { int port1 = router1.BindRandomPort("tcp://127.0.0.1"); int port2 = router2.BindRandomPort("tcp://127.0.0.1"); int port3 = router3.BindRandomPort("tcp://127.0.0.1"); int port4 = router4.BindRandomPort("tcp://127.0.0.1"); dealer1.Connect("tcp://127.0.0.1:" + port1); dealer2.Connect("tcp://127.0.0.1:" + port2); dealer3.Connect("tcp://127.0.0.1:" + port3); dealer4.Connect("tcp://127.0.0.1:" + port4); int router1Arrived = 0; int router2Arrived = 0; bool router3Arrived = false; bool router4Arrived = false; var signal1 = new ManualResetEvent(false); var signal2 = new ManualResetEvent(false); var signal3 = new ManualResetEvent(false); var signal4 = new ManualResetEvent(false); router1.ReceiveReady += (s, e) => { router1Arrived++; router1.SkipFrame(); // identity router1.SkipFrame(); // message poller.RemoveSocket(router1); signal1.Set(); }; router2.ReceiveReady += (s, e) => { router2Arrived++; router2.SkipFrame(); // identity router2.SkipFrame(); // message if (router2Arrived == 1) { poller.AddSocket(router3); poller.AddSocket(router4); signal2.Set(); } }; router3.ReceiveReady += (s, e) => { router3.SkipFrame(); // identity router3.SkipFrame(); // message router3Arrived = true; signal3.Set(); }; router4.ReceiveReady += (s, e) => { router4.SkipFrame(); // identity router4.SkipFrame(); // message router4Arrived = true; signal4.Set(); }; poller.PollTillCancelledNonBlocking(); dealer1.SendFrame("1"); Assert.IsTrue(signal1.WaitOne(300)); dealer2.SendFrame("2"); Assert.IsTrue(signal2.WaitOne(300)); dealer3.SendFrame("3"); dealer4.SendFrame("4"); dealer2.SendFrame("2"); dealer1.SendFrame("1"); Assert.IsTrue(signal3.WaitOne(300)); Assert.IsTrue(signal4.WaitOne(300)); poller.CancelAndJoin(); router1.SkipFrame(); bool more; Assert.AreEqual("1", router1.ReceiveFrameString(out more)); Assert.IsFalse(more); Assert.AreEqual(1, router1Arrived); Assert.AreEqual(2, router2Arrived); Assert.IsTrue(router3Arrived); Assert.IsTrue(router4Arrived); } }
public void AddSocketAfterRemoving() { using (var router1 = new RouterSocket()) using (var router2 = new RouterSocket()) using (var router3 = new RouterSocket()) using (var dealer1 = new DealerSocket()) using (var dealer2 = new DealerSocket()) using (var dealer3 = new DealerSocket()) using (var poller = new Poller(router1, router2) { PollTimeout = TestPollTimeoutMillis }) { int port1 = router1.BindRandomPort("tcp://127.0.0.1"); int port2 = router2.BindRandomPort("tcp://127.0.0.1"); int port3 = router3.BindRandomPort("tcp://127.0.0.1"); dealer1.Connect("tcp://127.0.0.1:" + port1); dealer2.Connect("tcp://127.0.0.1:" + port2); dealer3.Connect("tcp://127.0.0.1:" + port3); bool router1Arrived = false; bool router2Arrived = false; bool router3Arrived = false; var signal1 = new ManualResetEvent(false); var signal2 = new ManualResetEvent(false); var signal3 = new ManualResetEvent(false); router1.ReceiveReady += (s, e) => { router1Arrived = true; router1.SkipFrame(); router1.SkipFrame(); poller.RemoveSocket(router1); signal1.Set(); }; router2.ReceiveReady += (s, e) => { router2Arrived = true; router2.SkipFrame(); router2.SkipFrame(); poller.AddSocket(router3); signal2.Set(); }; router3.ReceiveReady += (s, e) => { router3Arrived = true; router3.SkipFrame(); router3.SkipFrame(); signal3.Set(); }; poller.PollTillCancelledNonBlocking(); dealer1.SendFrame("1"); Assert.IsTrue(signal1.WaitOne(300)); dealer2.SendFrame("2"); Assert.IsTrue(signal2.WaitOne(300)); dealer3.SendFrame("3"); Assert.IsTrue(signal3.WaitOne(300)); poller.CancelAndJoin(); Assert.IsTrue(router1Arrived); Assert.IsTrue(router2Arrived); Assert.IsTrue(router3Arrived); } }
public void Run() { //NOTES //1. Use many threads each writing to ConcurrentQueue //2. Extra thread to read from ConcurrentQueue, and this is the one that // will deal with writing to the server ConcurrentQueue <string> messages = new ConcurrentQueue <string>(); int delay = 3000; Poller poller = new Poller(); using (NetMQContext ctx = NetMQContext.Create()) { using (var server = ctx.CreateRouterSocket()) { server.Bind("tcp://127.0.0.1:5556"); //start some threads, where each thread, will use a client side //broker (simple thread that monitors a CooncurrentQueue), where //ONLY the client side broker talks to the server for (int i = 0; i < 3; i++) { Task.Factory.StartNew((state) => { while (true) { messages.Enqueue(state.ToString()); Thread.Sleep(delay); } }, string.Format("client {0}", i), TaskCreationOptions.LongRunning); } //single sender loop Task.Factory.StartNew((state) => { var client = ctx.CreateDealerSocket(); client.Connect("tcp://127.0.0.1:5556"); client.ReceiveReady += Client_ReceiveReady; poller.AddSocket(client); while (true) { string clientMessage = null; if (messages.TryDequeue(out clientMessage)) { var messageToServer = new NetMQMessage(); messageToServer.AppendEmptyFrame(); messageToServer.Append(clientMessage); client.SendMessage(messageToServer); } } }, TaskCreationOptions.LongRunning); //start the poller Task task = Task.Factory.StartNew(poller.Start); //server loop while (true) { var clientMessage = server.ReceiveMessage(); Console.WriteLine("========================"); Console.WriteLine(" INCOMING CLIENT MESSAGE "); Console.WriteLine("========================"); for (int i = 0; i < clientMessage.FrameCount; i++) { Console.WriteLine("Frame[{0}] = {1}", i, clientMessage[i].ConvertToString()); } if (clientMessage.FrameCount == 3) { var clientAddress = clientMessage[0]; var clientOriginalMessage = clientMessage[2].ConvertToString(); string response = string.Format("{0} back from server {1}", clientOriginalMessage, DateTime.Now.ToLongTimeString()); var messageToClient = new NetMQMessage(); messageToClient.Append(clientAddress); messageToClient.AppendEmptyFrame(); messageToClient.Append(response); server.SendMessage(messageToClient); } } } } }
static void Main(string[] args) { // this key should be shared between authorization server and publisher const string Key = "SecretKey"; string[] symbols = new[] { "EURUSD", "GBPUSD", "EURJPY", "USDJPY", "EURGBP", "GBPJPY" }; Random random = new Random(); using (var context = NetMQContext.Create()) { using (var publisher = context.CreateXPublisherSocket()) { publisher.Options.ManualPublisher = true; publisher.Bind("tcp://*:5558"); publisher.ReceiveReady += (sender, eventArgs) => { byte[] subscriptionBytes = publisher.Receive(); if (subscriptionBytes[0] == 1 || subscriptionBytes[0] == 0) { // the rest of the bytes is the token, convert them to string string serializedToken = Encoding.ASCII.GetString( subscriptionBytes, 1, subscriptionBytes.Length - 1); // deserialize the token Token token; if (Token.TryDeserialize(serializedToken, out token)) { // Check if the token is valid if (token.Validate(Key)) { // first byte indicate if it a subscription or unsubscription if (subscriptionBytes[0] == 1) { Console.WriteLine("Subscription request {0}", token.Subscription); publisher.Subscribe(token.Subscription); } else { publisher.Unsubscribe(token.Subscription); } } else { Console.WriteLine("Invalid token {0}", serializedToken); } } } }; // Some fake publishing NetMQTimer publishTimer = new NetMQTimer(100); publishTimer.Elapsed += (sender, eventArgs) => { publisher. SendMore(symbols[random.Next(symbols.Length)]). Send(random.Next().ToString()); }; Poller poller = new Poller(); poller.AddSocket(publisher); poller.AddTimer(publishTimer); poller.PollTillCancelled(); } } }
internal void AddSocket(NetMQSocket socket) { ExecuteOnPoller(() => _poller.AddSocket(socket)); }
public void AddTwoSocketAfterRemoving() { using (NetMQContext contex = NetMQContext.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (var router = contex.CreateRouterSocket()) using (var router2 = contex.CreateRouterSocket()) using (var router3 = contex.CreateRouterSocket()) using (var router4 = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); router2.Bind("tcp://127.0.0.1:5003"); router3.Bind("tcp://127.0.0.1:5004"); router4.Bind("tcp://127.0.0.1:5005"); using (var dealer = contex.CreateDealerSocket()) using (var dealer2 = contex.CreateDealerSocket()) using (var dealer3 = contex.CreateDealerSocket()) using (var dealer4 = contex.CreateDealerSocket()) using (Poller poller = new Poller()) { dealer.Connect("tcp://127.0.0.1:5002"); dealer2.Connect("tcp://127.0.0.1:5003"); dealer3.Connect("tcp://127.0.0.1:5004"); dealer4.Connect("tcp://127.0.0.1:5005"); int router1arrived = 0; int router2arrived = 0; bool router3arrived = false; bool router4arrived = false; bool more; router.ReceiveReady += (s, a) => { router1arrived++; router.Receive(out more); router.Receive(out more); poller.RemoveSocket(router); }; poller.AddSocket(router); router3.ReceiveReady += (s, a) => { router3.Receive(out more); router3.Receive(out more); router3arrived = true; }; router4.ReceiveReady += (s, a) => { router4.Receive(out more); router4.Receive(out more); router4arrived = true; }; router2.ReceiveReady += (s, a) => { router2arrived++; router2.Receive(out more); router2.Receive(out more); if (router2arrived == 1) { poller.AddSocket(router3); poller.AddSocket(router4); } }; poller.AddSocket(router2); Task task = Task.Factory.StartNew(poller.Start); dealer.Send("1"); Thread.Sleep(300); dealer2.Send("2"); Thread.Sleep(300); dealer3.Send("3"); dealer4.Send("4"); dealer2.Send("2"); dealer.Send("1"); Thread.Sleep(300); poller.Stop(true); task.Wait(); router.Receive(true, out more); Assert.IsTrue(more); router.Receive(true, out more); Assert.IsFalse(more); Assert.AreEqual(1, router1arrived); Assert.AreEqual(2, router2arrived); Assert.IsTrue(router3arrived); Assert.IsTrue(router4arrived); } } } }
void AddPoller() { poller.AddSocket(subSocket); ThreadPool.QueueUserWorkItem((o) => { poller.PollTillCancelled(); }); }
public void AddTwoSocketAfterRemoving() { using (Context contex = Context.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (RouterSocket router = contex.CreateRouterSocket()) using (RouterSocket router2 = contex.CreateRouterSocket()) using (RouterSocket router3 = contex.CreateRouterSocket()) using (RouterSocket router4 = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); router2.Bind("tcp://127.0.0.1:5003"); router3.Bind("tcp://127.0.0.1:5004"); router4.Bind("tcp://127.0.0.1:5005"); using (DealerSocket dealer = contex.CreateDealerSocket()) using (DealerSocket dealer2 = contex.CreateDealerSocket()) using (DealerSocket dealer3 = contex.CreateDealerSocket()) using (DealerSocket dealer4 = contex.CreateDealerSocket()) { dealer.Connect("tcp://127.0.0.1:5002"); dealer2.Connect("tcp://127.0.0.1:5003"); dealer3.Connect("tcp://127.0.0.1:5004"); dealer4.Connect("tcp://127.0.0.1:5005"); int router1arrived = 0; int router2arrived = 0; bool router3arrived = false; bool router4arrived = false; Poller poller = new Poller(contex); bool more; poller.AddSocket(router, (r) => { router1arrived++; router.Receive(out more); router.Receive(out more); poller.CancelSocket(router); }); poller.AddSocket(router2, (r) => { router2arrived++; router2.Receive(out more); router2.Receive(out more); if (router2arrived == 1) { poller.AddSocket(router3, (r2) => { router3.Receive(out more); router3.Receive(out more); router3arrived = true; }); poller.AddSocket(router4, (r3) => { router4.Receive(out more); router4.Receive(out more); router4arrived = true; }); } }); Task task = Task.Factory.StartNew(poller.Start); dealer.Send("1"); Thread.Sleep(100); dealer2.Send("2"); Thread.Sleep(100); dealer3.Send("3"); dealer4.Send("4"); dealer2.Send("2"); dealer.Send("1"); Thread.Sleep(100); poller.Stop(true); task.Wait(); router.Receive(true, out more); Assert.IsTrue(more); router.Receive(true, out more); Assert.IsFalse(more); Assert.AreEqual(1, router1arrived); Assert.AreEqual(2, router2arrived); Assert.IsTrue(router3arrived); Assert.IsTrue(router4arrived); } } } }
private void Connect() { List <SubscriberSocket> sockets = new List <SubscriberSocket>(); Poller poller = new Poller(); SubscriberSocket connectedSocket = null; // event handler to handle message from socket EventHandler <NetMQSocketEventArgs> handleMessage = (sender, args) => { connectedSocket = (SubscriberSocket)args.Socket; poller.Cancel(); }; NetMQTimer timeoutTimer = new NetMQTimer(TimeOut); // just cancel the poller without seting the connected socket timeoutTimer.Elapsed += (sender, args) => poller.Cancel(); poller.AddTimer(timeoutTimer); foreach (var address in m_addresses) { var socket = m_context.CreateSubscriberSocket(); sockets.Add(socket); socket.ReceiveReady += handleMessage; poller.AddSocket(socket); // Subscribe to welcome message socket.Subscribe(WelcomeMessage); socket.Connect(address); } poller.PollTillCancelled(); // if we a connected socket the connection attempt succeed if (connectedSocket != null) { // remove the connected socket form the list sockets.Remove(connectedSocket); // close all exsiting connections foreach (var socket in sockets) { // to close them immediatly we set the linger to zero socket.Options.Linger = TimeSpan.Zero; socket.Dispose(); } // set the socket m_subscriber = connectedSocket; // drop the welcome message m_subscriber.SkipMultipartMessage(); // subscribe to heartbeat m_subscriber.Subscribe(HeartbeatMessage); // subscribe to all subscriptions foreach (string subscription in m_subscriptions) { m_subscriber.Subscribe(subscription); } m_subscriber.ReceiveReady -= handleMessage; m_subscriber.ReceiveReady += OnSubscriberMessage; m_poller.AddSocket(m_subscriber); m_timeoutTimer.Enable = true; m_reconnectTimer.Enable = false; } else { // close all exsiting connections foreach (var socket in sockets) { // to close them immediatly we set the linger to zero socket.Options.Linger = TimeSpan.Zero; socket.Dispose(); } m_reconnectTimer.Enable = true; m_timeoutTimer.Enable = false; } }
public void CancelSocket() { using (Context contex = Context.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (RouterSocket router = contex.CreateRouterSocket()) using (RouterSocket router2 = contex.CreateRouterSocket()) using (RouterSocket router3 = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); router2.Bind("tcp://127.0.0.1:5003"); router3.Bind("tcp://127.0.0.1:5004"); using (DealerSocket dealer = contex.CreateDealerSocket()) using (DealerSocket dealer2 = contex.CreateDealerSocket()) using (DealerSocket dealer3 = contex.CreateDealerSocket()) { dealer.Connect("tcp://127.0.0.1:5002"); dealer2.Connect("tcp://127.0.0.1:5003"); dealer3.Connect("tcp://127.0.0.1:5004"); Poller poller = new Poller(contex); bool first = true; poller.AddSocket(router2, s => { bool more; // identity byte[] identity = s.Receive(out more); // message s.Receive(out more); s.SendMore(identity); s.Send("2"); }); poller.AddSocket(router, r => { if (!first) { Assert.Fail("This should happen because we cancelled the socket"); } first = false; bool more; // identity r.Receive(out more); string m = r.ReceiveString(out more); Assert.False(more); Assert.AreEqual("Hello", m); // cancellign the socket poller.CancelSocket(r); }); poller.AddSocket(router3, s => { bool more; // identity byte[] identity = s.Receive(out more); // message s.Receive(out more); s.SendMore(identity); s.Send("3"); }); Task pollerTask = Task.Factory.StartNew(poller.Start); dealer.Send("Hello"); // sending this should not arrive on the poller, therefore response for this will never arrive dealer.Send("Hello2"); Thread.Sleep(100); // sending this should not arrive on the poller, therefore response for this will never arrive dealer.Send("Hello3"); Thread.Sleep(500); bool more2; // making sure the socket defined before the one cancelled still works dealer2.Send("1"); string msg = dealer2.ReceiveString(out more2); Assert.AreEqual("2", msg); // making sure the socket defined after the one cancelled still works dealer3.Send("1"); msg = dealer3.ReceiveString(out more2); Assert.AreEqual("3", msg); // we have to give this some time if we want to make sure it's really not happening and it not only because of time Thread.Sleep(300); poller.Stop(); Thread.Sleep(100); Assert.IsTrue(pollerTask.IsCompleted); } } } }
public void Receive_RequestWithWrongMDPComand_ShouldLogCorrectMessage() { const string hostAddress = "tcp://localhost:5555"; var loggingMessages = new List <string> (); var first = true; // setup the counter socket for communication using (var context = NetMQContext.Create()) using (var broker = context.CreateRouterSocket()) using (var poller = new Poller()) using (var session = new MDPWorker(hostAddress, "test", Encoding.ASCII.GetBytes("Worker"), 2)) { broker.Bind(hostAddress); // we need to pick up any message in order to avoid errors broker.ReceiveReady += (s, e) => { var msg = e.Socket.ReceiveMultipartMessage(); // we expect to receive a 5 Frame message // [WORKER ADR][EMPTY]["MDPW01"]["READY"]["test"] if (msg.FrameCount != 5) { return; // it is a HEARTBEAT } // make sure the frames are as expected Assert.That(msg[1], Is.EqualTo(NetMQFrame.Empty)); Assert.That(msg[2].ConvertToString(), Is.EqualTo("MDPW01")); Assert.That(msg[3].BufferSize, Is.EqualTo(1)); Assert.That(msg[3].Buffer[0], Is.EqualTo((byte)MDPCommand.Ready)); Assert.That(msg[4].ConvertToString(), Is.EqualTo("test")); // tell worker to stop gracefully var reply = new NetMQMessage(); if (first) { reply.Push(new[] { (byte)0xff }); first = false; } else { reply.Push(new[] { (byte)MDPCommand.Kill }); } // push MDP Version reply.Push("MDPW01"); // push separator reply.Push(NetMQFrame.Empty); // push worker address reply.Push(msg[0]); // send reply which is a request for the worker e.Socket.SendMessage(reply); }; // set the event handler to receive the logging messages session.LogInfoReady += (s, e) => loggingMessages.Add(e.Info); poller.AddSocket(broker); Task.Factory.StartNew(poller.PollTillCancelled); session.HeartbeatDelay = TimeSpan.FromMilliseconds(250); session.ReconnectDelay = TimeSpan.FromMilliseconds(250); // initialise the worker - broker protocol session.Receive(null); Assert.That(loggingMessages.Count(m => m.Contains("[WORKER ERROR] invalid command received")), Is.EqualTo(1)); Assert.That(loggingMessages.Count(m => m.Contains("abandoning")), Is.EqualTo(1)); poller.CancelAndJoin(); poller.RemoveSocket(broker); } }
public void OverrideTimer() { using (Context contex = Context.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (RouterSocket router = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); using (DealerSocket dealer = contex.CreateDealerSocket()) { dealer.Connect("tcp://127.0.0.1:5002"); Poller poller = new Poller(contex); bool timerTriggered = false; bool timerTriggered2 = false; bool messageArrived = false; Console.WriteLine("register timer {0}", DateTime.Now.ToString("ss.fff")); // the timer will jump after 100ms poller.AddTimer(150, 1, id => { Console.WriteLine("timer triggered {0}", DateTime.Now.ToString("ss.fff")); // the timer should jump before the message timerTriggered = true; }); poller.AddSocket(router, s => { bool isMore; router.Receive(out isMore); router.Receive(out isMore); Console.WriteLine("message arrived {0}", DateTime.Now.ToString("ss.fff")); Assert.IsFalse(timerTriggered); messageArrived = true; // the timer will jump after 100ms poller.AddTimer(20, 1, id => { Console.WriteLine("timer 2 triggered {0}", DateTime.Now.ToString("ss.fff")); timerTriggered2 = true; }); }); Task.Factory.StartNew(poller.Start); dealer.Send("hello"); Console.WriteLine("message sent {0}", DateTime.Now.ToString("ss.fff")); Thread.Sleep(300); poller.Stop(); Assert.IsTrue(messageArrived); Assert.IsFalse(timerTriggered); Assert.IsTrue(timerTriggered2); } } } }
public void InprocRouterDealerTest() { // The main thread simply starts several clients and a server, and then // waits for the server to finish. List<Thread> workers = new List<Thread>(); byte[] s_ReadyMsg = Encoding.UTF8.GetBytes("RDY"); Queue<byte[]> s_FreeWorkers = new Queue<byte[]>(); using (var context = NetMQContext.Create()) { using (var backendsRouter = context.CreateRouterSocket()) { backendsRouter.Options.Identity = Guid.NewGuid().ToByteArray(); backendsRouter.Bind("inproc://backend"); backendsRouter.ReceiveReady += (o, e)=> { // Handle worker activity on backend while (e.Socket.HasIn) { var msg = e.Socket.ReceiveMultipartMessage(); var idRouter = msg.Pop(); // forget the empty frame if (msg.First.IsEmpty) msg.Pop(); var id = msg.Pop(); if (msg.First.IsEmpty) msg.Pop(); if (msg.FrameCount == 1) { // worker send RDY message queue his Identity to the free workers queue if (s_ReadyMsg[0] ==msg[0].Buffer[0] && s_ReadyMsg[1] ==msg[0].Buffer[1] && s_ReadyMsg[2] ==msg[0].Buffer[2]) { lock (s_FreeWorkers) { s_FreeWorkers.Enqueue(id.Buffer); } } } } }; Poller poller = new Poller(); poller.AddSocket(backendsRouter); for (int i = 0; i < 2; i++) { var workerThread = new Thread((state) => { byte[] routerId = (byte[])state; byte[] workerId = Guid.NewGuid().ToByteArray(); using (var workerSocket = context.CreateDealerSocket()) { workerSocket.Options.Identity = workerId; workerSocket.Connect("inproc://backend"); var workerReadyMsg = new NetMQMessage(); workerReadyMsg.Append(workerId); workerReadyMsg.AppendEmptyFrame(); workerReadyMsg.Append(s_ReadyMsg); workerSocket.SendMultipartMessage(workerReadyMsg); Thread.Sleep(1000); } }); workerThread.IsBackground = true; workerThread.Name = "worker" + i; workerThread.Start(backendsRouter.Options.Identity); workers.Add(workerThread); } poller.PollTillCancelledNonBlocking(); Thread.Sleep(1000); poller.CancelAndJoin(); Assert.AreEqual(2, s_FreeWorkers.Count); } } }
public void ReregisterTimer() { using (Context contex = Context.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (RouterSocket router = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); using (DealerSocket dealer = contex.CreateDealerSocket()) { dealer.Connect("tcp://127.0.0.1:5002"); Poller poller = new Poller(contex); bool messageArrived = false; poller.AddSocket(router, s => { bool isMore; router.Receive(out isMore); router.Receive(out isMore); messageArrived = true; }); int timerCounter = 0; // the timer will jump after 100ms poller.AddTimer(20, 1, id => { timerCounter++; poller.AddTimer(20, 1, id2 => { timerCounter++; }); }); Task.Factory.StartNew(poller.Start); Thread.Sleep(30); dealer.Send("hello"); Thread.Sleep(50); poller.Stop(); Assert.IsTrue(messageArrived); Assert.AreEqual(2, timerCounter); } } } }
private void initServerThr() { poller = new Poller(); using (NetMQContext context = NetMQContext.Create()) { using (var receiver = context.CreatePullSocket()) using (var publisher = context.CreatePublisherSocket()) { try { receiver.Bind(cfg.ServerR); publisher.Bind(cfg.ServerS); } catch (Exception ex) { DCLogger.LogError("Exception in ServerThr's bind work:{0}", ex.Message); } //r & s receiver.ReceiveReady += (sender, eventArgs) => { try { List <byte[]> dataLst = new List <byte[]>(); receiver.ReceiveMultipartBytes(ref dataLst, 2); //DCLogger.LogInfo("Received:{0}", Global.Encoding.GetString(dataLst[0])); if (dataLst.Count != 2) { return; } publisher.SendMultipartBytes(dataLst[0], dataLst[1]); //DCLogger.LogInfo("Sended:{0}", Global.Encoding.GetString(dataLst[0])); } catch (Exception ex) { DCLogger.LogError("Exception in ServerThr's exchange work:{0}", ex.Message); } }; poller.AddSocket(receiver); // send heartbeat every two seconds NetMQTimer heartbeatTimer = new NetMQTimer(30000); poller.AddTimer(heartbeatTimer); heartbeatTimer.Elapsed += (sender, eventArgs) => { try { publisher.SendMultipartBytes(Global.DC_CTRL_HB, BitConverter.GetBytes(DateTime.Now.Ticks)); DCLogger.LogInfo("Server's HeartBeat sended:{0}", DateTime.Now); } catch (Exception ex) { DCLogger.LogError("Exception in ServerThr's heartbeat work:{0}", ex.Message); } }; poller.PollTillCancelled(); } } }
public void ResponsePoll() { using (Context contex = Context.Create()) { using (ResponseSocket rep = contex.CreateResponseSocket()) { rep.Bind("tcp://127.0.0.1:5002"); using (RequestSocket req = contex.CreateRequestSocket()) { req.Connect("tcp://127.0.0.1:5002"); Poller poller = new Poller(contex); poller.AddSocket(rep, r => { bool more; string m = r.ReceiveString(out more); Assert.False(more); Assert.AreEqual("Hello", m); r.Send("World"); }); Task pollerTask = Task.Factory.StartNew(poller.Start); req.Send("Hello"); bool more2; string m1 = req.ReceiveString(out more2); Assert.IsFalse(more2); Assert.AreEqual("World", m1); poller.Stop(); Thread.Sleep(100); Assert.IsTrue(pollerTask.IsCompleted); } } } }
public void AddSocketAfterRemoving() { using (var context = NetMQContext.Create()) using (var router1 = context.CreateRouterSocket()) using (var router2 = context.CreateRouterSocket()) using (var router3 = context.CreateRouterSocket()) using (var dealer1 = context.CreateDealerSocket()) using (var dealer2 = context.CreateDealerSocket()) using (var dealer3 = context.CreateDealerSocket()) using (var poller = new Poller(router1, router2) { PollTimeout = TestPollTimeoutMillis }) { int port1 = router1.BindRandomPort("tcp://127.0.0.1"); int port2 = router2.BindRandomPort("tcp://127.0.0.1"); int port3 = router3.BindRandomPort("tcp://127.0.0.1"); dealer1.Connect("tcp://127.0.0.1:" + port1); dealer2.Connect("tcp://127.0.0.1:" + port2); dealer3.Connect("tcp://127.0.0.1:" + port3); bool router1Arrived = false; bool router2Arrived = false; bool router3Arrived = false; var signal1 = new ManualResetEvent(false); var signal2 = new ManualResetEvent(false); var signal3 = new ManualResetEvent(false); router1.ReceiveReady += (s, e) => { router1Arrived = true; router1.SkipFrame(); router1.SkipFrame(); poller.RemoveSocket(router1); signal1.Set(); }; router2.ReceiveReady += (s, e) => { router2Arrived = true; router2.SkipFrame(); router2.SkipFrame(); poller.AddSocket(router3); signal2.Set(); }; router3.ReceiveReady += (s, e) => { router3Arrived = true; router3.SkipFrame(); router3.SkipFrame(); signal3.Set(); }; poller.PollTillCancelledNonBlocking(); dealer1.Send("1"); Assert.IsTrue(signal1.WaitOne(300)); dealer2.Send("2"); Assert.IsTrue(signal2.WaitOne(300)); dealer3.Send("3"); Assert.IsTrue(signal3.WaitOne(300)); poller.CancelAndJoin(); Assert.IsTrue(router1Arrived); Assert.IsTrue(router2Arrived); Assert.IsTrue(router3Arrived); } }
public void TwoTimers() { using (Context contex = Context.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (RouterSocket router = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); using (DealerSocket dealer = contex.CreateDealerSocket()) { dealer.Connect("tcp://127.0.0.1:5002"); Poller poller = new Poller(contex); bool messageArrived = false; poller.AddSocket(router, s => { bool isMore; router.Receive(out isMore); router.Receive(out isMore); messageArrived = true; }); bool timerTriggered = false; // the timer will jump after 100ms poller.AddTimer(20, 1, id => { // the timer should jump before the message Assert.IsFalse(messageArrived); timerTriggered = true; }); bool timerTriggered2 = false; poller.AddTimer(80, 2, id => { // the timer should jump before the message Assert.IsTrue(messageArrived); timerTriggered2 = true; }); Task.Factory.StartNew(poller.Start); Thread.Sleep(50); dealer.Send("hello"); Thread.Sleep(50); poller.Stop(); Assert.IsTrue(messageArrived); Assert.IsTrue(timerTriggered); Assert.IsTrue(timerTriggered2); } } } }
public void AttachToPoller([NotNull] Poller poller) { InternalStart(); m_attachedPoller = poller; poller.AddSocket(m_monitoringSocket); }
public void SimpleTimer() { using (NetMQContext contex = NetMQContext.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (var router = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); using (var dealer = contex.CreateDealerSocket()) using (Poller poller = new Poller()) { dealer.Connect("tcp://127.0.0.1:5002"); bool messageArrived = false; router.ReceiveReady += (s, a) => { bool isMore; router.Receive(out isMore); router.Receive(out isMore); messageArrived = true; }; poller.AddSocket(router); bool timerTriggered = false; int count = 0; NetMQTimer timer = new NetMQTimer(TimeSpan.FromMilliseconds(100)); timer.Elapsed += (a, s) => { // the timer should jump before the message Assert.IsFalse(messageArrived); timerTriggered = true; timer.Enable = false; count++; }; poller.AddTimer(timer); Task.Factory.StartNew(poller.Start); Thread.Sleep(150); dealer.Send("hello"); Thread.Sleep(300); poller.Stop(); Assert.IsTrue(messageArrived); Assert.IsTrue(timerTriggered); Assert.AreEqual(1, count); } } } }
public void InprocRouterDealerTest() { // The main thread simply starts several clients and a server, and then // waits for the server to finish. List <Thread> workers = new List <Thread>(); byte[] s_ReadyMsg = Encoding.UTF8.GetBytes("RDY"); Queue <byte[]> s_FreeWorkers = new Queue <byte[]>(); using (var context = NetMQContext.Create()) { using (var backendsRouter = context.CreateRouterSocket()) { backendsRouter.Options.Identity = Guid.NewGuid().ToByteArray(); backendsRouter.Bind("inproc://backend"); backendsRouter.ReceiveReady += (o, e) => { // Handle worker activity on backend while (e.Socket.HasIn) { var msg = e.Socket.ReceiveMultipartMessage(); var idRouter = msg.Pop(); // forget the empty frame if (msg.First.IsEmpty) { msg.Pop(); } var id = msg.Pop(); if (msg.First.IsEmpty) { msg.Pop(); } if (msg.FrameCount == 1) { // worker send RDY message queue his Identity to the free workers queue if (s_ReadyMsg[0] == msg[0].Buffer[0] && s_ReadyMsg[1] == msg[0].Buffer[1] && s_ReadyMsg[2] == msg[0].Buffer[2]) { lock (s_FreeWorkers) { s_FreeWorkers.Enqueue(id.Buffer); } } } } }; Poller poller = new Poller(); poller.AddSocket(backendsRouter); for (int i = 0; i < 2; i++) { var workerThread = new Thread((state) => { byte[] routerId = (byte[])state; byte[] workerId = Guid.NewGuid().ToByteArray(); using (var workerSocket = context.CreateDealerSocket()) { workerSocket.Options.Identity = workerId; workerSocket.Connect("inproc://backend"); var workerReadyMsg = new NetMQMessage(); workerReadyMsg.Append(workerId); workerReadyMsg.AppendEmptyFrame(); workerReadyMsg.Append(s_ReadyMsg); workerSocket.SendMultipartMessage(workerReadyMsg); Thread.Sleep(1000); } }); workerThread.IsBackground = true; workerThread.Name = "worker" + i; workerThread.Start(backendsRouter.Options.Identity); workers.Add(workerThread); } poller.PollTillCancelledNonBlocking(); Thread.Sleep(1000); poller.CancelAndJoin(); Assert.AreEqual(2, s_FreeWorkers.Count); } } }
public void Run() { //NOTES //1. Use ThreadLocal<DealerSocket> where each thread has // its own client DealerSocket to talk to server //2. Each thread can send using it own socket //3. Each thread socket is added to poller ThreadLocal <DealerSocket> clientSocketPerThread = new ThreadLocal <DealerSocket>(); int delay = 3000; Poller poller = new Poller(); using (NetMQContext ctx = NetMQContext.Create()) { using (var server = ctx.CreateRouterSocket()) { server.Bind("tcp://127.0.0.1:5556"); //start some threads, each with its own DealerSocket //to talk to the server socket. Creates lots of sockets, //but no nasty race conditions no shared state, each //thread has its own socket, happy days for (int i = 0; i < 3; i++) { Task.Factory.StartNew((state) => { DealerSocket client = null; if (!clientSocketPerThread.IsValueCreated) { client = ctx.CreateDealerSocket(); client.Connect("tcp://127.0.0.1:5556"); client.ReceiveReady += Client_ReceiveReady; clientSocketPerThread.Value = client; poller.AddSocket(client); } else { client = clientSocketPerThread.Value; } while (true) { var messageToServer = new NetMQMessage(); messageToServer.AppendEmptyFrame(); messageToServer.Append(state.ToString()); client.SendMessage(messageToServer); Thread.Sleep(delay); } }, string.Format("client {0}", i), TaskCreationOptions.LongRunning); } //start the poller Task task = Task.Factory.StartNew(poller.Start); //server loop while (true) { var clientMessage = server.ReceiveMessage(); Console.WriteLine("========================"); Console.WriteLine(" INCOMING CLIENT MESSAGE "); Console.WriteLine("========================"); for (int i = 0; i < clientMessage.FrameCount; i++) { Console.WriteLine("Frame[{0}] = {1}", i, clientMessage[i].ConvertToString()); } if (clientMessage.FrameCount == 3) { var clientAddress = clientMessage[0]; var clientOriginalMessage = clientMessage[2].ConvertToString(); string response = string.Format("{0} back from server {1}", clientOriginalMessage, DateTime.Now.ToLongTimeString()); var messageToClient = new NetMQMessage(); messageToClient.Append(clientAddress); messageToClient.AppendEmptyFrame(); messageToClient.Append(response); server.SendMessage(messageToClient); } } } } }
public void CancelSocket() { using (NetMQContext contex = NetMQContext.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (var router = contex.CreateRouterSocket()) using (var router2 = contex.CreateRouterSocket()) using (var router3 = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); router2.Bind("tcp://127.0.0.1:5003"); router3.Bind("tcp://127.0.0.1:5004"); using (var dealer = contex.CreateDealerSocket()) using (var dealer2 = contex.CreateDealerSocket()) using (var dealer3 = contex.CreateDealerSocket()) using (Poller poller = new Poller()) { dealer.Connect("tcp://127.0.0.1:5002"); dealer2.Connect("tcp://127.0.0.1:5003"); dealer3.Connect("tcp://127.0.0.1:5004"); bool first = true; router2.ReceiveReady += (s, a) => { bool more; // identity byte[] identity = a.Socket.Receive(out more); // message a.Socket.Receive(out more); a.Socket.SendMore(identity); a.Socket.Send("2"); }; poller.AddSocket(router2); router.ReceiveReady += (s, a) => { if (!first) { Assert.Fail("This should happen because we cancelled the socket"); } first = false; bool more; // identity a.Socket.Receive(out more); string m = a.Socket.ReceiveString(out more); Assert.False(more); Assert.AreEqual("Hello", m); // cancellign the socket poller.RemoveSocket(a.Socket); }; poller.AddSocket(router); router3.ReceiveReady += (s, a) => { bool more; // identity byte[] identity = a.Socket.Receive(out more); // message a.Socket.Receive(out more); a.Socket.SendMore(identity).Send("3"); }; poller.AddSocket(router3); Task pollerTask = Task.Factory.StartNew(poller.Start); dealer.Send("Hello"); // sending this should not arrive on the poller, therefore response for this will never arrive dealer.Send("Hello2"); Thread.Sleep(100); // sending this should not arrive on the poller, therefore response for this will never arrive dealer.Send("Hello3"); Thread.Sleep(500); bool more2; // making sure the socket defined before the one cancelled still works dealer2.Send("1"); string msg = dealer2.ReceiveString(out more2); Assert.AreEqual("2", msg); // making sure the socket defined after the one cancelled still works dealer3.Send("1"); msg = dealer3.ReceiveString(out more2); Assert.AreEqual("3", msg); // we have to give this some time if we want to make sure it's really not happening and it not only because of time Thread.Sleep(300); poller.Stop(); Thread.Sleep(100); Assert.IsTrue(pollerTask.IsCompleted); } } } }
private SubscriberSocket Connect(string[] addresses) { List <SubscriberSocket> sockets = new List <SubscriberSocket>(); Poller poller = new Poller(); SubscriberSocket connectedSocket = null; // event handler to handle message from socket EventHandler <NetMQSocketEventArgs> handleMessage = (sender, args) => { if (connectedSocket == null) { connectedSocket = (SubscriberSocket)args.Socket; poller.Cancel(); } }; // If timeout elapsed just cancel the poller without seting the connected socket NetMQTimer timeoutTimer = new NetMQTimer(TimeSpan.FromSeconds(5)); timeoutTimer.Elapsed += (sender, args) => poller.Cancel(); poller.AddTimer(timeoutTimer); foreach (var address in addresses) { var socket = m_context.CreateSubscriberSocket(); sockets.Add(socket); socket.ReceiveReady += handleMessage; poller.AddSocket(socket); // Subscribe to welcome message socket.Subscribe("WM"); socket.Connect(address); } poller.PollTillCancelled(); // if we a connected socket the connection attempt succeed if (connectedSocket != null) { // remove the connected socket form the list sockets.Remove(connectedSocket); // close all existing sockets CloseSockets(sockets); // drop the welcome message connectedSocket.SkipMultipartMessage(); // subscribe to heartbeat connectedSocket.Subscribe("HB"); // subscribe to our only topic connectedSocket.Subscribe("A"); connectedSocket.ReceiveReady -= handleMessage; connectedSocket.ReceiveReady += OnSubscriberMessage; return(connectedSocket); } else { // close all existing sockets CloseSockets(sockets); return(null); } }
public void AddSocketDuringWork() { using (Context contex = Context.Create()) { // we are using three responses to make sure we actually move the correct socket and other sockets still work using (RouterSocket router = contex.CreateRouterSocket()) using (RouterSocket router2 = contex.CreateRouterSocket()) { router.Bind("tcp://127.0.0.1:5002"); router2.Bind("tcp://127.0.0.1:5003"); using (DealerSocket dealer = contex.CreateDealerSocket()) using (DealerSocket dealer2 = contex.CreateDealerSocket()) { dealer.Connect("tcp://127.0.0.1:5002"); dealer2.Connect("tcp://127.0.0.1:5003"); bool router1arrived = false; bool router2arrived = false; Poller poller = new Poller(contex); bool more; poller.AddSocket(router, (r) => { router1arrived = true; router.Receive(out more); router.Receive(out more); poller.AddSocket(router2, (r2) => { router2.Receive(out more); router2.Receive(out more); router2arrived = true; }); }); Task task = Task.Factory.StartNew(poller.Start); dealer.Send("1"); Thread.Sleep(100); dealer2.Send("2"); Thread.Sleep(100); poller.Stop(true); task.Wait(); Assert.IsTrue(router1arrived); Assert.IsTrue(router2arrived); } } } }
/// <summary> /// ParanoidPirate.Queue [-v] /// /// does load-balancing with heartbeating on worker tasks to detect /// crashed, blocked or slow running worker tasks /// </summary> static void Main(string[] args) { // serves as flag for exiting the program var exit = false; // catch CTRL+C as exit command Console.CancelKeyPress += (s, e) => { e.Cancel = true; exit = true; }; var verbose = args.Length > 0 && args[0] == "-v"; using (var ctx = NetMQContext.Create()) using (var frontend = ctx.CreateRouterSocket()) using (var backend = ctx.CreateRouterSocket()) using (var poller = new Poller()) { frontend.Bind(Commons.QUEUE_FRONTEND); backend.Bind(Commons.QUEUE_BACKEND); var workers = new Workers(); // client sends to this socket frontend.ReceiveReady += (s, e) => { // only process incoming client requests // if we have workers available handle client requests as long as we have workers // storage capability of the socket otherwise and pick up later if (workers.Available) { // get all message frames! var request = frontend.ReceiveMessage(); if (verbose) { Console.WriteLine("[QUEUE] received {0}", request); } // get next available worker var worker = workers.Next(); // wrap message with worker's address var msg = Wrap(worker, request); if (verbose) { Console.WriteLine("[QUEUE -> WORKER] sending {0}", msg); } backend.SendMessage(msg); } }; // worker sends to this socket backend.ReceiveReady += (s, e) => { var msg = e.Socket.ReceiveMessage(); if (verbose) { Console.WriteLine("[QUEUE <- WORKER] received {0}", msg); } // use workers identity for load-balancing var workerIdentity = Unwrap(msg); var worker = new Worker(workerIdentity); workers.Ready(worker); // just convenience var readableWorkerId = workerIdentity.ConvertToString(); if (msg.FrameCount == 1) { var data = msg[0].ConvertToString(); // the message is either READY or HEARTBEAT or corrupted switch (data) { case Commons.PPP_HEARTBEAT: Console.WriteLine("[QUEUE <- WORKER] Received a Heartbeat from {0}", readableWorkerId); break; case Commons.PPP_READY: Console.WriteLine("[QUEUE <- WORKER] Received a READY form {0}", readableWorkerId); break; default: Console.WriteLine("[QUEUE <- WORKER] ERROR received an invalid message!"); break; } } else { if (verbose) { Console.WriteLine("[QUEUE -> CLIENT] sending {0}", msg); } frontend.SendMessage(msg); } }; var timer = new NetMQTimer(Commons.HEARTBEAT_INTERVAL); // every specified ms QUEUE shall send a heartbeat to all connected workers timer.Elapsed += (s, e) => { // send heartbeat to every worker foreach (var worker in workers) { var heartbeat = new NetMQMessage(); heartbeat.Push(new NetMQFrame(Commons.PPP_HEARTBEAT)); heartbeat.Push(worker.Identity); Console.WriteLine("[QUEUE -> WORKER] sending heartbeat!"); backend.SendMessage(heartbeat); } // restart timer e.Timer.Enable = true; // remove all dead or expired workers workers.Purge(); }; if (verbose) { Console.WriteLine("[QUEUE] Start listening!"); } poller.AddSocket(frontend); poller.AddSocket(backend); poller.PollTillCancelledNonBlocking(); // hit CRTL+C to stop the while loop while (!exit) { } // Cleanup poller.RemoveTimer(timer); // stop the poler task poller.CancelAndJoin(); // remove the sockets - Dispose is called automatically poller.RemoveSocket(frontend); poller.RemoveSocket(backend); } }