Пример #1
0
        public void DecodesFinalResponseAfterSwitchingProtocols()
        {
            const string SwitchingProtocolsResponse = "HTTP/1.1 101 Switching Protocols\r\n" +
                                                      "Connection: Upgrade\r\n" +
                                                      "Upgrade: TLS/1.2, HTTP/1.1\r\n\r\n";

            var codec = new HttpClientCodec(4096, 8192, 8192, true);
            var ch    = new EmbeddedChannel(codec, new HttpObjectAggregator(1024));

            IHttpRequest request = new DefaultFullHttpRequest(HttpVersion.Http11, HttpMethod.Get, "http://localhost/");

            request.Headers.Set(HttpHeaderNames.Connection, HttpHeaderValues.Upgrade);
            request.Headers.Set(HttpHeaderNames.Upgrade, "TLS/1.2");
            Assert.True(ch.WriteOutbound(request), "Channel outbound write failed.");

            Assert.True(
                ch.WriteInbound(Unpooled.CopiedBuffer(Encoding.UTF8.GetBytes(SwitchingProtocolsResponse))),
                "Channel inbound write failed.");
            var switchingProtocolsResponse = ch.ReadInbound <IFullHttpResponse>();

            Assert.NotNull(switchingProtocolsResponse);
            switchingProtocolsResponse.Release();

            Assert.True(
                ch.WriteInbound(Unpooled.CopiedBuffer(Encoding.UTF8.GetBytes(Response))),
                "Channel inbound write failed");
            var finalResponse = ch.ReadInbound <IFullHttpResponse>();

            Assert.NotNull(finalResponse);
            finalResponse.Release();
            Assert.True(ch.FinishAndReleaseAll(), "Channel finish failed");
        }
Пример #2
0
        public void FailsOnIncompleteChunkedResponse()
        {
            var codec = new HttpClientCodec(4096, 8192, 8192, true);
            var ch    = new EmbeddedChannel(codec);

            ch.WriteOutbound(new DefaultFullHttpRequest(HttpVersion.Http11, HttpMethod.Get, "http://localhost/"));
            var buffer = ch.ReadOutbound <IByteBuffer>();

            Assert.NotNull(buffer);
            buffer.Release();
            Assert.Null(ch.ReadInbound <IByteBuffer>());
            ch.WriteInbound(Unpooled.CopiedBuffer(Encoding.UTF8.GetBytes(IncompleteChunkedResponse)));
            var response = ch.ReadInbound <IHttpResponse>();

            Assert.NotNull(response);
            var content = ch.ReadInbound <IHttpContent>();

            Assert.NotNull(content); // Chunk 'first'
            content.Release();

            content = ch.ReadInbound <IHttpContent>();
            Assert.NotNull(content); // Chunk 'second'
            content.Release();

            content = ch.ReadInbound <IHttpContent>();
            Assert.Null(content);

            Assert.Throws <PrematureChannelClosureException>(() => ch.Finish());
        }
Пример #3
0
        public void FailsNotOnRequestResponseChunked()
        {
            var codec = new HttpClientCodec(4096, 8192, 8192, true);
            var ch    = new EmbeddedChannel(codec);

            SendRequestAndReadResponse(ch, HttpMethod.Get, ChunkedResponse);
            ch.Finish();
        }
Пример #4
0
        public void ConnectWithResponseContent()
        {
            var codec = new HttpClientCodec(4096, 8192, 8192, true);
            var ch    = new EmbeddedChannel(codec);

            SendRequestAndReadResponse(ch, HttpMethod.Connect, Response);
            ch.Finish();
        }
        /// <summary>
        /// Configure the pipeline for a cleartext upgrade from HTTP to HTTP/2.
        /// </summary>
        /// <param name="ch"></param>
        void ConfigureClearText(IChannel ch)
        {
            HttpClientCodec          sourceCodec    = new HttpClientCodec();
            Http2ClientUpgradeCodec  upgradeCodec   = new Http2ClientUpgradeCodec(_connectionHandler);
            HttpClientUpgradeHandler upgradeHandler = new HttpClientUpgradeHandler(sourceCodec, upgradeCodec, 65536);

            ch.Pipeline.AddLast(sourceCodec,
                                upgradeHandler,
                                new UpgradeRequestHandler(this),
                                new UserEventLogger());
        }
Пример #6
0
        public void FailsOnMissingResponse()
        {
            var codec = new HttpClientCodec(4096, 8192, 8192, true);
            var ch    = new EmbeddedChannel(codec);

            Assert.True(ch.WriteOutbound(new DefaultFullHttpRequest(HttpVersion.Http11, HttpMethod.Get, "http://localhost/")));
            var buffer = ch.ReadOutbound <IByteBuffer>();

            Assert.NotNull(buffer);
            buffer.Release();

            Assert.Throws <PrematureChannelClosureException>(() => ch.Finish());
        }
Пример #7
0
        public void MultipleResponses()
        {
            string response = "HTTP/1.1 200 OK\r\n" +
                              "Content-Length: 0\r\n\r\n";

            HttpClientCodec codec = new HttpClientCodec(4096, 8192, 8192, true);
            EmbeddedChannel ch    = new EmbeddedChannel(codec, new HttpObjectAggregator(1024));

            IHttpRequest request = new DefaultFullHttpRequest(HttpVersion.Http11, HttpMethod.Get, "http://localhost/");

            Assert.True(ch.WriteOutbound(request));

            Assert.True(ch.WriteInbound(Unpooled.CopiedBuffer(response, Encoding.UTF8)));
            Assert.True(ch.WriteInbound(Unpooled.CopiedBuffer(response, Encoding.UTF8)));
            var resp = ch.ReadInbound <IFullHttpResponse>();

            Assert.True(resp.Result.IsSuccess);
            resp.Release();

            resp = ch.ReadInbound <IFullHttpResponse>();
            Assert.True(resp.Result.IsSuccess);
            resp.Release();
            Assert.True(ch.FinishAndReleaseAll());
        }
Пример #8
0
        private void InitDotNetty()
        {
            _responseHandler = new HttpResponseHandler();

            if (_proxyCredentials != null)
            {
                NetworkCredential credential = _proxyCredentials.GetCredential(_uri, "Basic");

                //TODO 除了Basic的其它实现
                string authString = !string.IsNullOrEmpty(credential.Domain) ?
                                    credential.Domain + "\\" + credential.UserName + ":" + credential.Password :
                                    credential.UserName + ":" + credential.Password;

                _authenticationString = new StringCharSequence($"Basic {Convert.ToBase64String(Encoding.UTF8.GetBytes(authString))}");

                _requestSetupFunc = request =>
                                    request.Headers.Remove(HttpHeaderNames.ProxyAuthorization).Add(HttpHeaderNames.ProxyAuthorization, _authenticationString);
            }

            _group     = new SingleThreadEventLoop();
            _bootstrap = new Bootstrap();
            _bootstrap
            .Group(_group)
            .Option(ChannelOption.TcpNodelay, true)
            .Option(ChannelOption.SoKeepalive, true)
            .Option(ChannelOption.Allocator, new UnpooledByteBufferAllocator())
            .Channel <TcpSocketChannel>()
            .Handler(new ActionChannelInitializer <IChannel>(channel =>
            {
                IChannelPipeline pipeline = channel.Pipeline;

                var aggregatorHandler = new HttpObjectAggregator(_maxLength);
                var codecHandler      = new HttpClientCodec(4096, 8192, 8192, false, false, _useProxy);

                if (IsHttps)
                {
                    if (_proxyUri is null)
                    {
                        pipeline.AddTlsHandler(Host, _certificateValidationCallback);
                        pipeline.AddLast(DotNettyHandlerNames.Codec, codecHandler);
                        pipeline.AddLast(DotNettyHandlerNames.Aggregator, aggregatorHandler);
                    }
                    else
                    {
                        pipeline.AddLast(DotNettyHandlerNames.Codec, codecHandler);
                        pipeline.AddLast(DotNettyHandlerNames.Aggregator, aggregatorHandler);
                        _connectionUpgradeHandler = new ConnectionUpgradeHandler(Host, _certificateValidationCallback);
                        pipeline.AddLast(DotNettyHandlerNames.ConnectionUpgrade, _connectionUpgradeHandler);
                    }
                }
                else
                {
                    pipeline.AddLast(DotNettyHandlerNames.Codec, codecHandler);
                    pipeline.AddLast(DotNettyHandlerNames.Aggregator, aggregatorHandler);
                }

                pipeline.AddLast(DotNettyHandlerNames.Response, _responseHandler);

                _dotNettyPipelineSetupCallback?.Invoke(pipeline);
            }));

            _dotNettyBootstrapSetupCallback?.Invoke(_bootstrap);
        }