首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >WebSocket异常闭锁不回ReceiveAsync

WebSocket异常闭锁不回ReceiveAsync
EN

Stack Overflow用户
提问于 2017-08-20 20:41:23
回答 1查看 2.1K关注 0票数 5

服务器上有一个线程,用于处理通过WebSocket连接从客户端接收的数据:

代码语言:javascript
复制
    public HttpResponseMessage Get()
    {
        if (HttpContext.Current.IsWebSocketRequest)
        {
            HttpContext.Current.AcceptWebSocketRequest(ProcessWebSocket);
        }

        return new HttpResponseMessage(HttpStatusCode.SwitchingProtocols);
    }

    private async Task ProcessWebSocket(AspNetWebSocketContext context)
    {
        WebSocket webSocket = context.WebSocket;    //Gets the current WebSocket object. 
        const int maxMessageSize = 1024;
        byte[] receivedDataBuffer = new byte[maxMessageSize];
        logger.Debug("WSC-New WebSocket connection");
        while (webSocket.State == WebSocketState.Open)
        {
            var timeOut = new CancellationTokenSource(70000).Token;
            WebSocketReceiveResult webSocketReceiveResult = await webSocket.ReceiveAsync(new ArraySegment<byte>(receivedDataBuffer), timeOut);
            //If input frame is cancelation frame, send close command. 
            if (webSocketReceiveResult.MessageType == WebSocketMessageType.Close)
            {
                await webSocket.CloseAsync(WebSocketCloseStatus.NormalClosure, String.Empty, CancellationToken.None);
                logger.Debug("WSC-Close WebSocket connection frame received");
            }
            else
            {
                //Process received data....
            }
        }
        logger.Debug("WSC-WebSocket closed, WebSocket state: {0}", webSocket.State.ToString());
    }

只要另一方正确地关闭WebSocket连接,我就会得到最后的记录器消息,说明websocket已经关闭,这意味着这个线程正确终止。如果客户端进入睡眠状态或程序突然停止,则不会发生正常的WebSocket闭包。在这种情况下,webSocket.ReceiveAsync永远不会返回。我担心,如果启动了足够多的这些线程,但始终没有终止,可能会有严重的内存泄漏。超时取消令牌应该在70秒后返回,但不会发生。在这种情况下,如果我试图从另一个线程访问webSocket对象,就会得到以下异常:无法访问已释放的对象。

如何从等待webSocket.ReceiveAsync(新ArraySegment(receivedDataBuffer),timeOut)返回;正确关闭这个线程?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2017-08-21 00:11:45

问题是:

几乎任何连接的突然关闭都会导致另一个套接字永远得不到数据,这将导致您的套接字被打开,就像您所说的。

解决办法:

尝试使用“保持活动”来决定连接何时超时,另一种解决方案是使用一个单独的线程,该线程可能会被删除,但是我不确定这种方法对您的效果有多好。

启动套接字前:

代码语言:javascript
复制
Thread X = new Thread(() => {
    Connect();
});
X.Start();

结束套接字输出:

代码语言:javascript
复制
X.Abort();
// You could also force a Garbage Collection using
GC.Collect();
票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/45786613

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档