/// <inheritdoc/> public async Task <GatewayConnectionResult> DisconnectAsync ( bool reconnectionIntended, CancellationToken ct = default ) { if (_clientWebSocket is null) { return(GatewayConnectionResult.FromError("The transport service is not connected.")); } switch (_clientWebSocket.State) { case WebSocketState.Open: case WebSocketState.CloseReceived: case WebSocketState.CloseSent: { try { // 1012 is used here instead of normal closure, because close codes 1000 and 1001 don't // allow for reconnection. 1012 is referenced in the websocket protocol as "Service restart", // which makes sense for our use case. var closeCode = reconnectionIntended ? (WebSocketCloseStatus)1012 : WebSocketCloseStatus.NormalClosure; await _clientWebSocket.CloseAsync ( closeCode, "Terminating connection by user request.", ct ); } catch (WebSocketException) { // Most likely due to some kind of premature or forced disconnection; we'll live with it } break; } } _clientWebSocket.Dispose(); _clientWebSocket = null; this.IsConnected = false; return(GatewayConnectionResult.FromSuccess()); }
/// <inheritdoc /> public async Task <GatewayConnectionResult> ConnectAsync(Uri endpoint, CancellationToken ct = default) { if (_clientWebSocket is not null) { return(GatewayConnectionResult.FromError("The transport service is already connected.")); } var socket = _services.GetRequiredService <ClientWebSocket>(); try { await socket.ConnectAsync(endpoint, ct); switch (socket.State) { case WebSocketState.Open: case WebSocketState.Connecting: { break; } default: { socket.Dispose(); return(GatewayConnectionResult.FromError("Failed to connect to the endpoint.")); } } } catch (Exception e) { socket.Dispose(); return(GatewayConnectionResult.FromError(e)); } _clientWebSocket = socket; this.IsConnected = true; return(GatewayConnectionResult.FromSuccess()); }