Wednesday, 9 February 2022

asp.net WebSocket keep alive after Action is done

In an asp.net core (5.0) web application, is it possible to keep the socket alive without having a infinite while loop? (while (webSocket.State == WebSocketState.Open) If the loop is the only way to do that, isn't that very inefficient?

This is essentially what I would like to achieve

public class SocketController : Controller
{

  [HttpGet]
  [Route("Connect")]
  public async Task ConnectAsync()
  {
    if (HttpContext.WebSockets.IsWebSocketRequest)
    {
      var webSocket = await HttpContext.WebSockets.AcceptWebSocketAsync();
      SocketManager.registerSocket(User, webSocket);
      var outputBuffer = new ArraySegment<byte>(Encoding.UTF8.GetBytes("pong"));
      await webSocket.SendAsync(outputBuffer, WebSocketMessageType.Text, true, CancellationToken.None);
    }
    else
    {
      HttpContext.Response.StatusCode = (int)HttpStatusCode.BadRequest;
    }
  }

}

This seems to work but, it doesn't seem right

public class SocketController : Controller
{

  [HttpGet]
  [Route("Connect")]
  public async Task ConnectAsync()
  {
    if (HttpContext.WebSockets.IsWebSocketRequest)
    {
      var webSocket = await HttpContext.WebSockets.AcceptWebSocketAsync();
      // stuff
      while (webSocket.State == WebSocketState.Open) ;
    }
    else
    {
      HttpContext.Response.StatusCode = (int)HttpStatusCode.BadRequest;
    }
  }

}

Minimal example to check socket closing:

var socket = new WebSocket("wss://localhost:44331/Socket/Connect");
socket.onclose = function (err) {
    console.log("CLOSED");
    console.error(err);
};

If I remove the loop, the connection closes on the JS side, the moment the action finishes executing, output:

CLOSED
{
    isTrusted: true,
    bubbles: false,
    cancelBubble: false,
    cancelable: false,
    code: 1006,
    composed: false,
    currentTarget: [WebSocket Object],
    defaultPrevented: false,
    eventPhase: 0,
    path: [],
    reason: "",
    returnValue: true,
    srcElement: [WebSocket Object],
    target: [WebSocket Object],
    timeStamp: 958.5999999998603,
    type: "close",
    wasClean: false
}


from asp.net WebSocket keep alive after Action is done

No comments:

Post a Comment