async static Task Run(INetNode node)
        {
            node.Start();
            Console.WriteLine("Input server endpoint in form of ipaddress:port");
            string[] addressAndPort = Console.ReadLine().Split(':');
            var      endpoint       = new IPEndPoint(IPAddress.Parse(addressAndPort[0]), int.Parse(addressAndPort[1]));

            //before doing any network comms we should connect to some server node
            using (INetChannel channel = await node.Connect(endpoint))
            {
                await Task.Yield();

                Console.WriteLine("Enter your name");
                string name = Console.ReadLine();

                Console.WriteLine("Enter chat room name");
                string roomName = Console.ReadLine();

                //using connected channel we can send in request/reply pattern
                JoinRoomResponse response = await channel.SendRequestAsync <JoinRoomResponse>(
                    new JoinRoom
                {
                    ClientName = name,
                    RoomName   = roomName
                });

                if (response.RetCode == JoinRoomRetCode.NameIsTaken)
                {
                    Console.WriteLine("Name is taken");
                    return;
                }

                Console.WriteLine("You are connected, say something or enter exit");

                bool exit = false;
                while (!exit)
                {
                    await Task.Yield(); //client uses single threaded processing, so it's better noto block it with Console.Readline

                    string text = Console.ReadLine();
                    if (text == "exit")
                    {
                        exit = true;
                    }
                    else
                    {
                        //or we can send just one way messages
                        channel.Send(new Say {
                            Text = text
                        });
                    }
                }
            }
        }
        //beware: truly fire and forget async void flow, you'll never know if it failed
        async public void SendOneWay(Message msg)
        {
            try
            {
                await EnsureConnected();

                _mainConnection.Send(msg);
            }
            catch (Exception)
            {
                Logger.ConnectionHasTimedOut(this, _serverEndpoints[0]);
            }
        }
 public void Send(Message msg)
 {
     msg.AttachHeader(new CallbackHeader(_callbackRef.CallbackChannelId));
     _remoteNodeChannel.Send(msg);
 }