コード例 #1
0
        /// <summary>
        ///     Begin writing to a network stream
        /// </summary>
        private Task WriteAsync <T, U>(PipeTaskState <T> state, PipeRequest <U> request, CancellationToken cancellationToken)
        {
            try
            {
                if (cancellationToken.IsCancellationRequested)
                {
                    cancellationToken.ThrowIfCancellationRequested();
                }

                if (!_pipeClient.IsConnected)
                {
                    throw new IOException("Unable to send message, no connection established.");
                }

                if (_pipeClient.CanWrite)
                {
                    return(_pipeClient.WriteAsync(Encoding.UTF8.GetBytes(JsonConvert.SerializeObject(request)), cancellationToken).AsTask());
                }
            }
            catch (Exception ex)
            {
                _logger.Error($"{nameof(WriteAsync)}-{ex.Message}");
                state.Response = PipeResponse <T> .SetFail(ex.Message);
            }

            return(Task.CompletedTask);
        }
コード例 #2
0
        /// <summary>
        ///     Begin reading from a network stream
        /// </summary>
        private Task ReadAsync <T>(PipeTaskState <T> state, CancellationToken cancellationToken)
        {
            if (state.Response != null && state.Response.IsSuccess == false)
            {
                return(Task.CompletedTask);
            }

            try
            {
                if (cancellationToken.IsCancellationRequested)
                {
                    cancellationToken.ThrowIfCancellationRequested();
                }

                if (!_pipeClient.IsConnected)
                {
                    throw new IOException("Unable to recieve message, no connection established.");
                }

                if (_pipeClient.CanRead)
                {
                    return(_pipeClient.ReadAsync(_memoryOwner.Memory, cancellationToken).AsTask());
                }
            }
            catch (Exception ex)
            {
                _logger.Error($"{nameof(ReadAsync)}-{ex.Message}");
                state.Response = PipeResponse <T> .SetFail(ex.Message);
            }

            return(Task.CompletedTask);
        }
コード例 #3
0
        /// <summary>
        /// <see cref="PipeResponse"/> から <see cref="HttpResponseMessage"/> を作成します。
        /// </summary>
        /// <param name="pipeResponse"><see cref="HttpResponseMessage"/> を作成するための <see cref="PipeResponse"/></param>
        /// <param name="request"><see cref="HttpResponseMessage"/> を作成するための <see cref="HttpRequestMessage"/></param>
        /// <param name="checkAction">カスタムで処理を行う場合のアクション</param>
        /// <remarks>
        /// デフォルトで以下の判定を行います。
        /// <list type="list">
        ///     <item><see cref="PipeResponse.Data"/>が<see cref="null"/>の場合は、HTTPステータスコード Not Found の <see cref="HttpResponseMessage"/>を返します。</item>
        ///     <item>結果が<see cref="ValidationResult"/>で<see cref="ValidationResult.IsValid"/>が <see cref="false"/> の場合は、 HTTPステータスコード で BadRequest を返します。</item>
        ///     <item>上記以外の場合は<see cref="HttpResponseMessage" /> に <see cref="PipeResponse.StatusCode"/> と、<see cref="PipeResponse.Data"/>の値を設定してかえします。</item>
        /// </list>
        /// </remarks>
        /// <returns><see cref="HttpResponseMessage"/></returns>
        public static HttpResponseMessage CreateHttpResponse(this PipeResponse pipeResponse, HttpRequestMessage request, Func <PipeResponse, Func <HttpResponseMessage>, HttpResponseMessage> checkAction = null)
        {
            Contract.NotNull(pipeResponse, "pipeResponse");
            Contract.NotNull(request, "request");
            var defaultAction = new DefaultResponseAction(request, pipeResponse);

            if (checkAction != null)
            {
                return(checkAction(pipeResponse, defaultAction.CreateHttpResponse));
            }
            return(defaultAction.CreateHttpResponse());
        }
コード例 #4
0
 /// <summary>
 ///     Wait for a pipe to drain before another write/read
 /// </summary>
 private void WaitForPipeDrain <T>(PipeTaskState <T> state)
 {
     try
     {
         _pipeClient.WaitForPipeDrain();
     }
     catch (Exception ex)
     {
         _logger.Error(ex.Message);
         state.Response = PipeResponse <T> .SetFail(ex.Message);
     }
 }
コード例 #5
0
        /// <summary>
        ///     Convert response from
        /// </summary>
        private void ConvertResponse <T>(PipeTaskState <T> state)
        {
            if (state.Response != null && state.Response.IsSuccess == false)
            {
                return;
            }

            try
            {
                var json = Encoding.UTF8.GetString(_memoryOwner.Memory.Span).TrimEnd('\0');

                if (string.IsNullOrWhiteSpace(json))
                {
                    throw new IOException("Response from server is empty.");
                }

                state.Response = JsonConvert.DeserializeObject <PipeResponse <T> >(json);
            }
            catch (Exception ex)
            {
                _logger.Error($"{nameof(ReadAsync)}-{ex.Message}");
                state.Response = PipeResponse <T> .SetFail(ex.Message);
            }
        }
コード例 #6
0
 public DefaultResponseAction(HttpRequestMessage request, PipeResponse pipeResponse)
 {
     this.request      = request;
     this.pipeResponse = pipeResponse;
 }
コード例 #7
0
ファイル: ServerFactory.cs プロジェクト: ArloL/gate
        public static IDisposable Create(AppDelegate app, int port, string path)
        {
            app = ErrorPage.Middleware(app);

            var effectivePath = path ?? "";
            if (!effectivePath.EndsWith("/"))
                effectivePath += "/";

            var listener = new System.Net.HttpListener();
            listener.Prefixes.Add(string.Format("http://+:{0}{1}", port, effectivePath));
            listener.Start();

            Action go = () => { };
            go = () => listener.BeginGetContext(
                ar =>
                {
                    HttpListenerContext context;
                    try
                    {
                        context = listener.EndGetContext(ar);
                    }
                    finally
                    {
                        // ReSharper disable AccessToModifiedClosure
                        go();
                        // ReSharper restore AccessToModifiedClosure
                    }

                    var requestPathBase = effectivePath;
                    if (requestPathBase == "/" || requestPathBase == null)
                        requestPathBase = "";

                    var requestPath = context.Request.Url.AbsolutePath;
                    if (string.IsNullOrEmpty(requestPath))
                        requestPath = "/";
                    if (requestPath.StartsWith(requestPathBase, StringComparison.OrdinalIgnoreCase))
                        requestPath = requestPath.Substring(requestPathBase.Length);

                    var requestQueryString = context.Request.Url.GetComponents(UriComponents.Query, UriFormat.UriEscaped);

                    var requestHeaders = context.Request.Headers.AllKeys
                        .ToDictionary(x => x, x => (IEnumerable<string>)context.Request.Headers.GetValues(x), StringComparer.OrdinalIgnoreCase);

                    var env = new Dictionary<string, object>
                    {
                        {OwinConstants.Version, "1.0"},
                        {OwinConstants.RequestMethod, context.Request.HttpMethod},
                        {OwinConstants.RequestScheme, context.Request.Url.Scheme},
                        {OwinConstants.RequestPathBase, requestPathBase},
                        {OwinConstants.RequestPath, requestPath},
                        {OwinConstants.RequestQueryString, requestQueryString},
                        {OwinConstants.RequestHeaders, requestHeaders},
                        {OwinConstants.RequestBody, RequestBody(context.Request.InputStream)},
                        {"System.Net.HttpListenerContext", context},
                        {"server.CLIENT_IP", context.Request.RemoteEndPoint.Address.ToString()},
                    };

                    app(env,
                        (status, headers, body) =>
                        {
                            context.Response.StatusCode = int.Parse(status.Substring(0, 3));
                            context.Response.StatusDescription = status.Substring(4);
                            foreach (var kv in headers)
                            {
                                // these may not be assigned via header collection
                                if (string.Equals(kv.Key, "Content-Length", StringComparison.OrdinalIgnoreCase))
                                {
                                    context.Response.ContentLength64 = long.Parse(kv.Value.Single());
                                }
                                else if (string.Equals(kv.Key, "Keep-Alive", StringComparison.OrdinalIgnoreCase))
                                {
                                    context.Response.KeepAlive = true;
                                }
                                //else if (string.Equals(kv.Key, "Transfer-Encoding", StringComparison.OrdinalIgnoreCase))
                                //{
                                //    // not sure what can be done about this
                                //}
                                //else if (string.Equals(kv.Key, "WWW-Authenticate", StringComparison.OrdinalIgnoreCase))
                                //{
                                //    // not sure what httplistener properties to assign
                                //}
                                else
                                {
                                    // all others are
                                    foreach (var v in kv.Value)
                                    {
                                        context.Response.Headers.Add(kv.Key, v);
                                    }
                                }
                            }
                            var pipeResponse = new PipeResponse(
                                context.Response.OutputStream,
                                ex => context.Response.Close(),
                                () => context.Response.Close());
                            pipeResponse.Go(body);
                        },
                        ex =>
                        {
                            // This should never be called
                            throw new NotImplementedException();
                        });
                },
                null);

            go();

            return new Disposable(() =>
            {
                go = () => { };
                listener.Stop();
            });
        }