C#Socket继续接收空消息

时间:2017-06-12 17:50:05

标签: c# tcp server

我正在努力训练自己,而且我正在构建一个小型Tcp服务器/客户端。

我目前有3个连接,监听客户端和收听消息的小班。以下是3个类:

public class ServersLauncher
{

    #region Main
    public static void Main(string[] args)
    {
        ServersLauncher sl = new ServersLauncher();
        Console.ReadLine();
        sl._udpServer?.Dispose();
        sl._tcpServer?.Dispose();
    }
    #endregion Main

    private UdpServer _udpServer;
    private TcpServer _tcpServer;

    private ServersLauncher()
    {
        _tcpServer = new TcpServer();
        Socket sc = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        IPEndPoint localEndPoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 25004);
        sc.Bind(localEndPoint);
        IPEndPoint distantEndPoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 25000);
        sc.Connect(distantEndPoint);
        while (!sc.Connected)
            Thread.Sleep(1000);
        byte[] buffer = Utility.ConvertMessage("Hell world !");
        sc.Send(buffer, buffer.Length, SocketFlags.None);
        sc.Close();
    }

}

在顶部是服务器启动器,它启动服务器,创建客户端并发送消息。

public class TcpServer : IDisposable
{

    private readonly int _portTcp = 25000;
    private Socket _socket;
    private Thread _connectionsThread;
    private List<TcpClient> _clients;

    public TcpServer()
    {
        _clients = new List<TcpClient>();

        _socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        IPEndPoint endPoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), _portTcp);
        _socket.Bind(endPoint);
        _connectionsThread = new Thread(new ThreadStart(ListenConnections));
        _connectionsThread.Start();
    }

    public void Dispose()
    {
        _connectionsThread.Abort();
        for(int i = 0; i < _clients.Count; i++)
        {
            _clients[i].Dispose();
        }
        _socket.Close();
    }

    private void ListenConnections()
    {
        _socket.Listen(100);
        while (true)
        {
            Socket clientSocket = _socket.Accept();
            _clients.Add(new TcpClient(clientSocket));
        }
    }

}

最重要的是TcpServer,它在一个客户端连接时监听连接并创建客户端接口。

public class TcpClient : IDisposable
{

    private Socket _client;
    private Thread _receiverThread;

    public TcpClient(Socket client)
    {
        _client = client;
        _receiverThread = new Thread(ReceiveMessage);
        _receiverThread.Start();
    }

    public void Dispose()
    {
        _receiverThread.Abort();
    }

    private void ReceiveMessage()
    {
        while (true)
        {
            byte[] buffer = new byte[1024];
            _client.Receive(buffer);
            Utility.DisplayThread("A message has been received : " + Encoding.ASCII.GetString(buffer).Trim());
        }
    }

}

这是存储套接字客户端并侦听消息的TcpClient。 没有什么复杂,但我有一个阅读消息的问题。现在,如果我启动程序,客户端连接,但然后...非停止消息!我收到了一个地狱世界&#34;然后空消息。我阅读了Socket的Receive方法的文档,看起来它应该阻塞并等待消息继续进行。 我在某处做错了吗?在断开连接之前,我是否需要从客户端刷新流? 谢谢你的帮助!

2 个答案:

答案 0 :(得分:1)

接收空消息的原因是您的客户端套接字保持连接

您可以等待与您的客户端接收更多消息,如果这是您想要的尝试:

 private void ReceiveMessage()
        {
            while (true) {
                if(_client.Available > 0) {
                    byte[] buffer = new byte[1024];
                    _client.Receive(buffer);
                    Console.WriteLine("A message has been received : " + Encoding.ASCII.GetString(buffer));
                }
            }
        }
  

if(_client.Available&gt; 0)检查是否有任意数量的字节   从网络接收并可以读取的数据。

告诉我如何发展;

祝你好运;

答案 1 :(得分:0)

嗯,我不确定你期望看到什么行为。

您创建了一个新的ServerLauncher,然后执行此操作时,您将执行以下操作:

sc.Connect(distantEndPoint);
while (!sc.Connected)
   Thread.Sleep(1000);
byte[] buffer = Utility.ConvertMessage("Hell world !");
sc.Send(buffer, buffer.Length, SocketFlags.None);
sc.Close();

连接,等待连接,发送消息然后关闭。

然后您的主要方法会调用Console.ReadLine(); ...

如果您的服务器已关闭,则不会再收到任何消息。删除sc.Close();行(或仅在调用某个标志时调用它,如X

也许你应该创建一个循环并从循环中发送消息,或者更好的是,从命令行传递消息。