Example #1
0
            public async Task RunShouldWriteBytesToWebSocket(
                int sequenceNumber,
                byte[] bytes,
                [Substitute] IClientWebSocket clientWebSocket,
                [Frozen, Substitute] IGatewayService gateway,
                [Frozen, Substitute] IChannel <GatewayMessage> channel,
                [Frozen, Substitute] ISerializer serializer,
                [Frozen, Substitute] IGatewayUtilsFactory factory,
                [Target] DefaultGatewayTxWorker worker
                )
            {
                var message = new GatewayMessage {
                    SequenceNumber = sequenceNumber
                };
                var cancellationToken = new CancellationToken(false);

                serializer.SerializeToBytes(Any <GatewayMessage>()).Returns(bytes);
                channel.Read(Any <CancellationToken>()).Returns(new ValueTask <GatewayMessage>(message));

                clientWebSocket.State.Returns(WebSocketState.Open);
                await worker.Start(gateway, clientWebSocket);

                await worker.Run(cancellationToken);

                await clientWebSocket.Received().Send(Is <ArraySegment <byte> >(bytes), Is(WebSocketMessageType.Text), Is(true), Is(cancellationToken));
            }
        public override async Task ConnectAsync()
        {
            await base.ConnectAsync();

            if (_webSocketTransport != null)
            {
                _webSocketTransport.OnTextReceived   -= OnTextReceived;
                _webSocketTransport.OnBinaryReceived -= OnBinaryReceived;
                _webSocketTransport.OnAborted        -= OnAborted;
                _webSocketTransport.Dispose();
            }
            Uri uri = UriConverter.GetServerUri(true, ServerUri, EIO, Options.Path, Options.Query);

            _clientWebSocket = ClientWebSocketProvider();
            if (Options.ExtraHeaders != null)
            {
                foreach (var item in Options.ExtraHeaders)
                {
                    _clientWebSocket.SetRequestHeader(item.Key, item.Value);
                }
            }
            _webSocketTransport = new WebSocketTransport(_clientWebSocket, EIO)
            {
                ConnectionTimeout = Options.ConnectionTimeout
            };
            _webSocketTransport.OnTextReceived   = OnTextReceived;
            _webSocketTransport.OnBinaryReceived = OnBinaryReceived;
            _webSocketTransport.OnAborted        = OnAborted;
            Debug.WriteLine($"[Websocket] Connecting");
            await _webSocketTransport.ConnectAsync(uri).ConfigureAwait(false);

            Debug.WriteLine($"[Websocket] Connected");
        }
Example #3
0
            public async Task RunShouldReadFromChannelIfWaitToReadReturnsTrue(
                int sequenceNumber,
                [Substitute] IClientWebSocket clientWebSocket,
                [Frozen, Substitute] IGatewayService gateway,
                [Frozen, Substitute] IChannel <GatewayMessage> channel,
                [Frozen, Substitute] IGatewayUtilsFactory factory,
                [Target] DefaultGatewayTxWorker worker
                )
            {
                var message = new GatewayMessage {
                    SequenceNumber = sequenceNumber
                };
                var cancellationToken = new CancellationToken(false);

                channel.Read(Any <CancellationToken>()).Returns(new ValueTask <GatewayMessage>(message));

                clientWebSocket.State.Returns(WebSocketState.Open);
                await worker.Start(gateway, clientWebSocket);

                await worker.Run(cancellationToken);

                await channel.Received().WaitToRead(Is(cancellationToken));

                await channel.Received().Read(Is(cancellationToken));
            }
Example #4
0
            public async Task RunShouldWaitUntilTheWebSocketIsOpen(
                int sequenceNumber,
                [Substitute] IClientWebSocket clientWebSocket,
                [Frozen, Substitute] IGatewayService gateway,
                [Frozen, Substitute] IChannel <GatewayMessage> channel,
                [Frozen, Substitute] IGatewayUtilsFactory factory,
                [Target] DefaultGatewayTxWorker worker
                )
            {
                var tries   = 0;
                var message = new GatewayMessage {
                    SequenceNumber = sequenceNumber
                };
                var cancellationToken = new CancellationToken(false);

                clientWebSocket.State.Returns(WebSocketState.Connecting);

                channel.Read(Any <CancellationToken>()).Returns(new ValueTask <GatewayMessage>(message));
                channel.WaitToRead(Any <CancellationToken>()).Returns(true);
                factory.CreateDelay(Any <uint>(), Any <CancellationToken>()).Returns(async x =>
                {
                    if (++tries == 2)
                    {
                        clientWebSocket.State.Returns(WebSocketState.Open);
                    }

                    await Task.CompletedTask;
                });

                await worker.Start(gateway, clientWebSocket);

                await worker.Run(cancellationToken);

                await factory.Received(2).CreateDelay(100, Is(cancellationToken));
            }
        async void HandleRequest(string requestName, IClientWebSocket clientWebSocket)
        {
            try
            {
                if (this.streamRequestHandlerProvider.TryGetHandler(requestName, out IStreamRequestHandler handler))
                {
                    Events.HandlerFound(requestName);
                    await handler.Handle(clientWebSocket, this.cts.Token);

                    await this.CloseWebSocketConnection(requestName, clientWebSocket, WebSocketCloseStatus.NormalClosure, string.Empty);
                }
                else
                {
                    Events.NoHandlerFound(requestName);
                    await this.CloseWebSocketConnection(requestName, clientWebSocket, WebSocketCloseStatus.InvalidPayloadData, $"Unknown request name - {requestName}");
                }

                Events.RequestCompleted(requestName);
            }
            catch (Exception e)
            {
                Events.ErrorHandlingRequest(requestName, e);
            }
            finally
            {
                this.streamLock.Release();
            }
        }
Example #6
0
 //public WebSocketTransport(IClientWebSocket ws, SocketIOOptions options, IJsonSerializer jsonSerializer, ILogger logger)
 //    : base(options, jsonSerializer, logger)
 public WebSocketTransport(IClientWebSocket ws, SocketIOOptions options, IJsonSerializer jsonSerializer)
     : base(options, jsonSerializer)
 {
     _ws       = ws;
     _sendLock = new SemaphoreSlim(1, 1);
     _ws.TextObservable.Subscribe(this);
     _ws.BytesObservable.Subscribe(this);
 }
Example #7
0
        /*/ Constructors /*/

        /// <summary>
        /// Initializes a new instance of the <see cref="SlackClient"/> class.
        /// </summary>
        /// <param name="clientWebSocket">Client web socket.</param>
        /// <param name="logManager">Log manager.</param>
        public SlackClient(IClientWebSocket clientWebSocket, ILogManager?logManager = null)
        {
            this.webSocket  = clientWebSocket ?? throw new ArgumentNullException(nameof(clientWebSocket));
            this.logManager = logManager;
            this.log        = this.logManager?.GetLogger(typeof(SlackClient));

            this.emptyStringContent = new StringContent(string.Empty);
        }
Example #8
0
 private void ResetState()
 {
     socket?.Abort();
     socket = null;
     receiveCancellationToken?.Cancel();
     receiveCancellationToken = null;
     sendCancellationToken?.Cancel();
     sendCancellationToken = null;
 }
Example #9
0
 public async Task UnSubscribe(IOrderbook market, IClientWebSocket client)
 {
     if (client.State == WebSocketState.Open)
     {
         await Client.SendAsync(
             new ArraySegment <byte>(Encoding.ASCII.GetBytes($"{{\"method\": \"unsubscribeOrderbook\",\"params\": {{ \"symbol\": \"{market.Symbol}\" }} }}")),
             WebSocketMessageType.Text, true, CancellationToken.None).ConfigureAwait(false);
     }
 }
Example #10
0
 public async Task UnSubscribe(IOrderbook market, IClientWebSocket client)
 {
     if (client.State == WebSocketState.Open)
     {
         await Client.SendAsync(new ArraySegment <byte>(
                                    Encoding.ASCII.GetBytes($"{{\"sub\": \"market.{market.Symbol.ToLower()}.mbp.150\",\n  \"id\": \"id{ID}\"\n }}")
                                    ), WebSocketMessageType.Text, true, CancellationToken.None).ConfigureAwait(false);
     }
 }
 public OrderbookListener(ILogger <OrderbookListener> logger, IClientWebSocket client, IExchange exch, int id)
 {
     _logger         = logger;
     Client          = client;
     Exchange        = exch;
     ID              = id;
     OrderbookType   = Exchange.OrderbookType;
     Client.Exchange = Exchange;
 }
            public async Task StartShouldStartTheTxWorker(
                [Frozen, Substitute] IClientWebSocket clientWebSocket,
                [Frozen, Substitute] IGatewayTxWorker txWorker,
                [Target] DefaultGatewayService gateway
                )
            {
                await gateway.StartAsync();

                await txWorker.Received().Start(Is(gateway), Is(clientWebSocket));
            }
Example #13
0
        public bool RegisterClient(string id, IClientWebSocket clientWebSocket)
        {
            if (!clientWebSockets.ContainsKey(id))
            {
                clientWebSockets.Add(id, clientWebSocket);
                return(true);
            }

            return(false);
        }
        /// <inheritdoc />
        public async Task Start(IGatewayService gateway, IClientWebSocket webSocket)
        {
            IsRunning      = true;
            this.webSocket = webSocket;

            timer = timerFactory.CreateTimer(Run, 0, WorkerThreadName);
            timer.StopOnException  = true;
            timer.OnUnexpectedStop = () => gateway.Restart();
            await timer.Start();
        }
Example #15
0
 public WebSocketTransport(IClientWebSocket ws, int eio)
 {
     _eio                = eio;
     _ws                 = ws;
     ReceiveChunkSize    = 1024 * 8;
     SendChunkSize       = 1024 * 8;
     ConnectionTimeout   = TimeSpan.FromSeconds(10);
     ReceiveWait         = TimeSpan.FromSeconds(1);
     _listenCancellation = new CancellationTokenSource();
     _sendLock           = new SemaphoreSlim(1, 1);
 }
Example #16
0
        /// <summary>
        /// Replaces the socket.
        /// </summary>
        /// <param name="socket">The socket.</param>
        private void ReplaceSocket(IClientWebSocket socket)
        {
            var previousSocket = _currentWebSocket;

            _currentWebSocket = socket;

            if (previousSocket != null)
            {
                previousSocket.Dispose();
            }
        }
        private async Task HandleOutgoingDataAsync(IClientWebSocket clientWebSocket, Stream localStream, CancellationToken cancellationToken)
        {
            var buffer = new byte[bufferSize];

            while (localStream.CanRead)
            {
                var receiveCount = await localStream.ReadAsync(buffer, 0, buffer.Length, cancellationToken).ConfigureAwait(false);

                await clientWebSocket.SendAsync(new ArraySegment <byte>(buffer, 0, receiveCount), WebSocketMessageType.Binary, true, cancellationToken).ConfigureAwait(false);
            }
        }
 async Task CloseWebSocketConnection(string requestName, IClientWebSocket clientWebSocket, WebSocketCloseStatus webSocketCloseStatus, string message)
 {
     try
     {
         await clientWebSocket.CloseAsync(webSocketCloseStatus, message, this.cts.Token);
     }
     catch (Exception ex)
     {
         Events.ErrorClosingWebSocket(requestName, ex);
     }
 }
Example #19
0
            public async Task StartShouldCreateTimer(
                [Substitute] IClientWebSocket clientWebSocket,
                [Frozen, Substitute] IGatewayService gateway,
                [Frozen, Substitute] ITimerFactory timerFactory,
                [Target] DefaultGatewayTxWorker txWorker
                )
            {
                await txWorker.Start(gateway, clientWebSocket);

                timerFactory.Received().CreateTimer(Is((AsyncTimerCallback)txWorker.Run), Is(0), Is("Gateway TX"));
            }
Example #20
0
            public async Task StartShouldStartTheWorkerThread(
                [Substitute] IClientWebSocket clientWebSocket,
                [Frozen, Substitute] IGatewayService gateway,
                [Frozen, Substitute] ITimer timer,
                [Target] DefaultGatewayTxWorker txWorker
                )
            {
                await txWorker.Start(gateway, clientWebSocket);

                await timer.Received().Start();
            }
            public async Task StopShouldAbortTheWebSocket(
                [Frozen, Substitute] IClientWebSocket clientWebSocket,
                [Target] DefaultGatewayService gateway
                )
            {
                await gateway.StartAsync();

                await gateway.StopAsync();

                clientWebSocket.Received().Abort();
            }
        private async Task HandleIncomingDataAsync(IClientWebSocket clientWebSocket, Stream localStream, CancellationToken cancellationToken)
        {
            var buffer = new byte[bufferSize];

            while (clientWebSocket.State == WebSocketState.Open)
            {
                var receiveResult = await clientWebSocket.ReceiveAsync(buffer, cancellationToken).ConfigureAwait(false);

                await localStream.WriteAsync(buffer, 0, receiveResult.Count, cancellationToken).ConfigureAwait(false);
            }
        }
        public async Task Handle(IClientWebSocket clientWebSocket, CancellationToken cancellationToken)
        {
            try
            {
                LogsStreamRequest streamRequest = await this.ReadLogsStreamingRequest(clientWebSocket, cancellationToken);

                Events.RequestData(streamRequest);

                if (ExpectedSchemaVersion.CompareMajorVersion(streamRequest.SchemaVersion, "logs stream request schema") != 0)
                {
                    Events.MismatchedMinorVersions(streamRequest.SchemaVersion, ExpectedSchemaVersion);
                }

                var socketCancellationTokenSource = new CancellationTokenSource();

                Task ProcessLogsFrame(ArraySegment <byte> bytes)
                {
                    if (clientWebSocket.State != WebSocketState.Open)
                    {
                        Events.WebSocketNotOpen(streamRequest, clientWebSocket.State);
                        socketCancellationTokenSource.Cancel();
                        return(Task.CompletedTask);
                    }
                    else
                    {
                        return(clientWebSocket.SendAsync(bytes, WebSocketMessageType.Binary, true, cancellationToken));
                    }
                }

                ILogsRequestToOptionsMapper requestToOptionsMapper = new LogsRequestToOptionsMapper(
                    this.runtimeInfoProvider,
                    streamRequest.Encoding,
                    streamRequest.ContentType,
                    LogOutputFraming.SimpleLength,
                    Option.None <LogsOutputGroupingConfig>(),
                    true);
                IList <(string id, ModuleLogOptions logOptions)> logOptionsList = await requestToOptionsMapper.MapToLogOptions(streamRequest.Items, cancellationToken);

                using (var linkedCts = CancellationTokenSource.CreateLinkedTokenSource(cancellationToken, socketCancellationTokenSource.Token))
                {
                    await this.logsProvider.GetLogsStream(logOptionsList, ProcessLogsFrame, linkedCts.Token);
                }

                Events.StreamingCompleted(streamRequest);
            }
            catch (Exception e)
            {
                Events.ErrorHandlingRequest(e);
            }
        }
        async Task <LogsStreamRequest> ReadLogsStreamingRequest(IClientWebSocket clientWebSocket, CancellationToken cancellationToken)
        {
            // Max size of the request can be 8k
            var buf    = new byte[MaxLogRequestSizeBytes];
            var arrSeg = new ArraySegment <byte>(buf);
            WebSocketReceiveResult result = await clientWebSocket.ReceiveAsync(arrSeg, cancellationToken);

            if (result.Count > 0)
            {
                string jsonString = Encoding.UTF8.GetString(buf, 0, result.Count);
                return(jsonString.FromJson <LogsStreamRequest>());
            }

            throw new InvalidOperationException("Did not receive logs request from server");
        }
Example #25
0
        /// <summary>
        ///
        /// </summary>
        /// <param name="clientWebSocket"></param>
        /// <param name="bufferSize"></param>
        /// <param name="cancellationToken"></param>
        public ClientWebSocketText(IClientWebSocket clientWebSocket, int bufferSize = 1024, CancellationToken cancellationToken = default(CancellationToken))
        {
            if (clientWebSocket == null)
            {
                throw new ArgumentNullException(nameof(clientWebSocket));
            }
            if (bufferSize <= 0)
            {
                throw new ArgumentOutOfRangeException(nameof(bufferSize), @"Receive buffer size should be greater than zero");
            }

            _clientWebSocket    = clientWebSocket;
            _bufferSize         = bufferSize;
            _cancellationToken  = cancellationToken;
            _lazyReceiveContext = new Lazy <BufferingContext>(() => new BufferingContextShared(bufferSize), LazyThreadSafetyMode.None);
        }
Example #26
0
        /*/ Constructors /*/

        /// <summary>
        /// Initializes a new instance of the <see cref="DiscordClient"/> class.
        /// </summary>
        /// <param name="clientWebSocket">Client web socket.</param>
        /// <param name="httpClient">Http client.</param>
        /// <param name="logManager">Log Manager.</param>
        public DiscordClient(
            IClientWebSocket clientWebSocket,
            IHttpClient httpClient,
            ILogManager?logManager = null)
        {
            this.httpClient = httpClient ?? throw new ArgumentNullException(nameof(httpClient));
            this.socket     = clientWebSocket ?? throw new ArgumentNullException(nameof(clientWebSocket));
            this.logManager = logManager;

            this.cancelToken    = new CancellationToken(false);
            this.heartbeatTimer = new Timer(
                this.OnHeartbeatInterval,
                null,
                HeartbeatIntervalDefault,
                HeartbeatIntervalDefault);
            this.log = this.logManager?.GetLogger(typeof(DiscordClient));
        }
Example #27
0
        private void ConnectWebsocket()
        {
            Console.WriteLine("About to connect to main socket at " + webSocketLocation);

            this.websocket = new WebSocket4NetSocketClient();
            this.websocket.MessageReceived += this.WebsocketMessageReceived;
            this.websocket.Connect(webSocketLocation);

            Task.Factory.StartNew(this.WaitForSocketToConnect);

            var socketConnected = this.socketConnectedEvent.WaitOne(TimeSpan.FromSeconds(3));

            if (!socketConnected)
            {
                throw new WebSocketCouldNotConnectException();
            }
        }
        internal async Task RejectAsync(Uri rendezvousUri)
        {
            IClientWebSocket clientWebSocket = null;

            try
            {
                if (this.Response.StatusCode == HttpStatusCode.Continue)
                {
                    this.Response.StatusCode        = HttpStatusCode.BadRequest;
                    this.Response.StatusDescription = "Rejected by user code";
                }

                // Add the status code/description to the URI query string
                int requiredCapacity = rendezvousUri.OriginalString.Length + 50 + this.Response.StatusDescription.Length;
                var stringBuilder    = new StringBuilder(rendezvousUri.OriginalString, requiredCapacity);
                stringBuilder.AppendFormat("&{0}={1}", HybridConnectionConstants.StatusCode, (int)this.Response.StatusCode);
                stringBuilder.AppendFormat("&{0}={1}", HybridConnectionConstants.StatusDescription, WebUtility.UrlEncode(this.Response.StatusDescription));
                Uri rejectUri = new Uri(stringBuilder.ToString());

                clientWebSocket = this.CreateWebSocket();
                using (var cancelSource = new CancellationTokenSource(AcceptTimeout))
                {
                    await clientWebSocket.ConnectAsync(rejectUri, cancelSource.Token).ConfigureAwait(false);
                }
            }
            catch (Exception e) when(!Fx.IsFatal(e))
            {
                WebException    webException;
                HttpWebResponse httpWebResponse;

                if (e is WebSocketException &&
                    (webException = e.InnerException as WebException) != null &&
                    (httpWebResponse = webException.Response as HttpWebResponse) != null &&
                    httpWebResponse.StatusCode == HttpStatusCode.Gone)
                {
                    // status code of "Gone" is expected when rejecting a client request
                    return;
                }

                RelayEventSource.Log.HandledExceptionAsWarning(this, e);
            }
            finally
            {
                clientWebSocket?.WebSocket?.Abort();
            }
        }
            public async Task RunShouldReceiveChunksFromTheWebSocket(
                [Frozen, Options] IOptions <GatewayOptions> options,
                [Frozen, Substitute] IClientWebSocket webSocket,
                [Frozen, Substitute] IGatewayRxWorker rxWorker,
                [Target] DefaultGatewayService gateway
                )
            {
                var cancellationToken = new CancellationToken(false);

                webSocket.Receive(Any <Memory <byte> >(), Any <CancellationToken>()).Returns(x => new ValueWebSocketReceiveResult(0, WebSocketMessageType.Text, true));

                await gateway.StartAsync();

                await gateway.Run(cancellationToken);

                await webSocket.Received().Receive(Any <Memory <byte> >(), Is(cancellationToken));
            }
            public async Task RunShouldNotConnectToTheWebSocketServerIfAlreadyConnected(
                [Frozen, Options] IOptions <GatewayOptions> options,
                [Frozen, Substitute] IClientWebSocket webSocket,
                [Frozen, Substitute] IGatewayRxWorker rxWorker,
                [Target] DefaultGatewayService gateway
                )
            {
                var cancellationToken = new CancellationToken(false);

                webSocket.State.Returns(WebSocketState.Open);
                webSocket.Receive(Any <Memory <byte> >(), Any <CancellationToken>()).Returns(x => new ValueWebSocketReceiveResult(0, WebSocketMessageType.Text, true));

                await gateway.StartAsync();

                await gateway.Run(cancellationToken);

                await webSocket.DidNotReceive().Connect(Is(options.Value.Uri), Is(cancellationToken));
            }