本文介绍了TcpListener:如何在等待 AcceptTcpClientAsync() 时停止监听?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我不知道如何在异步方法等待传入连接时正确关闭 TcpListener.我在 SO 上找到了这段代码,这里是代码:

I don't know how to properly close a TcpListener while an async method await for incoming connections.I found this code on SO, here the code :

public class Server
{
    private TcpListener _Server;
    private bool _Active;

    public Server()
    {
        _Server = new TcpListener(IPAddress.Any, 5555);
    }

    public async void StartListening()
    {
        _Active = true;
        _Server.Start();
        await AcceptConnections();
    }

    public void StopListening()
    {
        _Active = false;
        _Server.Stop();
    }

    private async Task AcceptConnections()
    {
        while (_Active)
        {
            var client = await _Server.AcceptTcpClientAsync();
            DoStuffWithClient(client);
        }
    }

    private void DoStuffWithClient(TcpClient client)
    {
        // ...
    }

}

还有主要的:

    static void Main(string[] args)
    {
        var server = new Server();
        server.StartListening();

        Thread.Sleep(5000);

        server.StopListening();
        Console.Read();
    }

这一行抛出异常

        await AcceptConnections();

当我调用 Server.StopListening() 时,对象被删除.

when I call Server.StopListening(), the object is deleted.

所以我的问题是,如何取消 AcceptTcpClientAsync() 以正确关闭 TcpListener.

So my question is, how can I cancel AcceptTcpClientAsync() for closing TcpListener properly.

推荐答案

由于这里没有合适的工作示例,这里是一个:

Since there's no proper working example here, here is one:

假设您同时拥有 cancellationTokentcpListener 的范围,那么您可以执行以下操作:

Assuming you have in scope both cancellationToken and tcpListener, then you can do the following:

using (cancellationToken.Register(() => tcpListener.Stop()))
{
    try
    {
        var tcpClient = await tcpListener.AcceptTcpClientAsync();
        // … carry on …
    }
    catch (InvalidOperationException)
    {
        // Either tcpListener.Start wasn't called (a bug!)
        // or the CancellationToken was cancelled before
        // we started accepting (giving an InvalidOperationException),
        // or the CancellationToken was cancelled after
        // we started accepting (giving an ObjectDisposedException).
        //
        // In the latter two cases we should surface the cancellation
        // exception, or otherwise rethrow the original exception.
        cancellationToken.ThrowIfCancellationRequested();
        throw;
    }
}

这篇关于TcpListener:如何在等待 AcceptTcpClientAsync() 时停止监听?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-19 00:08