/// <summary>
        /// Подождать завершение задачи
        /// </summary>
        public void Wait()
        {
            if (_isCompleted)
            {
                if (_isCancelled)
                {
                    throw new OperationInterruptedException();
                }
                if (_exception != null)
                {
                    _exception.Throw();
                }
                return;
            }

            lock (_syncObject)
            {
                while (!_isCompleted)
                {
                    Monitor.Wait(_syncObject);
                }
            }

            if (_isCancelled)
            {
                throw new OperationInterruptedException();
            }
            if (_exception != null)
            {
                _exception.Throw();
            }
        }
Пример #2
0
        /// <summary>
        /// Issues an HTTP request for the current request context.
        /// </summary>
        /// <typeparam name="T">The response type for the current request.</typeparam>
        /// <param name="executionContext">The execution context, it contains the
        /// request and response context.</param>
        /// <returns>A task that represents the asynchronous operation.</returns>
        public override async System.Threading.Tasks.Task <T> InvokeAsync <T>(IExecutionContext executionContext)
        {
            IHttpRequest <TRequestContent> httpRequest = null;

            try
            {
                SetMetrics(executionContext.RequestContext);
                IRequest wrappedRequest = executionContext.RequestContext.Request;
                httpRequest = CreateWebRequest(executionContext.RequestContext);
                httpRequest.SetRequestHeaders(wrappedRequest.Headers);

                using (executionContext.RequestContext.Metrics.StartEvent(Metric.HttpRequestTime))
                {
                    // Send request body if present.
                    if (wrappedRequest.HasRequestBody())
                    {
                        System.Runtime.ExceptionServices.ExceptionDispatchInfo edi = null;
                        try
                        {
                            // In .NET Framework, there needs to be a cancellation token in this method since GetRequestStreamAsync
                            // does not accept a cancellation token. A workaround is used. This isn't necessary in .NET Standard
                            // where the stream is a property of the request.
#if BCL45
                            var requestContent = await httpRequest.GetRequestContentAsync(executionContext.RequestContext.CancellationToken).ConfigureAwait(false);
                            await WriteContentToRequestBodyAsync(requestContent, httpRequest, executionContext.RequestContext).ConfigureAwait(false);
#else
                            var requestContent = await httpRequest.GetRequestContentAsync().ConfigureAwait(false);

                            WriteContentToRequestBody(requestContent, httpRequest, executionContext.RequestContext);
#endif
                        }
                        catch (Exception e)
                        {
                            edi = System.Runtime.ExceptionServices.ExceptionDispatchInfo.Capture(e);
                        }

                        if (edi != null)
                        {
                            await CompleteFailedRequest(executionContext, httpRequest).ConfigureAwait(false);

                            edi.Throw();
                        }
                    }

                    var response = await httpRequest.GetResponseAsync(executionContext.RequestContext.CancellationToken).
                                   ConfigureAwait(false);

                    executionContext.ResponseContext.HttpResponse = response;
                }
                // The response is not unmarshalled yet.
                return(null);
            }
            finally
            {
                if (httpRequest != null)
                {
                    httpRequest.Dispose();
                }
            }
        }
Пример #3
0
        /// <summary>
        /// Adds an item to the cache.
        /// </summary>
        /// <param name="store">The store storing the cache data.</param>
        /// <param name="name">The name of the cache item.</param>
        /// <param name="content">The cached data.</param>
        /// <returns>A <see cref="Task"/> representing the asynchronous caching operation.</returns>
        public async Task Add(String name, Stream content, String store)
        {
            Contract.Requires <ArgumentNullException>(name != null);
            Contract.Requires <ArgumentNullException>(content != null);
            Contract.Requires <ArgumentNullException>(store != null);

            System.Runtime.ExceptionServices.ExceptionDispatchInfo exceptionInfo = null;
            try
            {
                long length = content.Length;
                await this.WriteToFileAsync(content, await this.OpenStore(store), name);

                cacheEventSource.ItemStored(name, store, length);
            }
            catch (IOException ex)
            {
                exceptionInfo = System.Runtime.ExceptionServices.ExceptionDispatchInfo.Capture(ex);
            }

            if (exceptionInfo != null) // Little hacky (but required!) as we can't use async / await inside a catch-block
            {
                int hresult = exceptionInfo.SourceException.HResult & 0xFFFF;
                if (hresult == 0x70 || hresult == 0x27) // HResults for disk full.
                {
                    await this.Invalidate();
                }
                else
                {
                    exceptionInfo.Throw();
                }
            }
        }
 public void SetException(System.Runtime.ExceptionServices.ExceptionDispatchInfo edi, TaskScheduler sheduler = null)
 {
     lock (_lock)
     {
         _completionAction = () => { edi.Throw(); };
         Complete(sheduler);
     }
 }
Пример #5
0
        /// <summary>
        /// Issues an HTTP request for the current request context.
        /// </summary>
        /// <typeparam name="T">The response type for the current request.</typeparam>
        /// <param name="executionContext">The execution context, it contains the
        /// request and response context.</param>
        /// <returns>A task that represents the asynchronous operation.</returns>
        public override async System.Threading.Tasks.Task <T> InvokeAsync <T>(IExecutionContext executionContext)
        {
            IHttpRequest <TRequestContent> httpRequest = null;

            try
            {
                SetMetrics(executionContext.RequestContext);
                IRequest wrappedRequest = executionContext.RequestContext.Request;
                httpRequest = CreateWebRequest(executionContext.RequestContext);
                httpRequest.SetRequestHeaders(wrappedRequest.Headers);

                using (executionContext.RequestContext.Metrics.StartEvent(Metric.HttpRequestTime))
                {
                    // Send request body if present.
                    if (wrappedRequest.HasRequestBody())
                    {
                        System.Runtime.ExceptionServices.ExceptionDispatchInfo edi = null;
                        try
                        {
                            var requestContent = await httpRequest.GetRequestContentAsync().ConfigureAwait(false);

                            WriteContentToRequestBody(requestContent, httpRequest, executionContext.RequestContext);
                        }
                        catch (Exception e)
                        {
                            edi = System.Runtime.ExceptionServices.ExceptionDispatchInfo.Capture(e);
                        }

                        if (edi != null)
                        {
                            await CompleteFailedRequest(executionContext, httpRequest).ConfigureAwait(false);

                            edi.Throw();
                        }
                    }

                    var response = await httpRequest.GetResponseAsync(executionContext.RequestContext.CancellationToken).
                                   ConfigureAwait(false);

                    executionContext.ResponseContext.HttpResponse = response;
                }
                // The response is not unmarshalled yet.
                return(null);
            }
            finally
            {
                if (httpRequest != null)
                {
                    httpRequest.Dispose();
                }
            }
        }
Пример #6
0
        /// <summary>
        /// Invokes the inner handler and performs a retry, if required as per the
        /// retry policy.
        /// </summary>
        /// <typeparam name="T">The response type for the current request.</typeparam>
        /// <param name="executionContext">The execution context, it contains the
        /// request and response context.</param>
        /// <returns>A task that represents the asynchronous operation.</returns>
        public override async System.Threading.Tasks.Task <T> InvokeAsync <T>(IExecutionContext executionContext)
        {
            var  requestContext  = executionContext.RequestContext;
            var  responseContext = executionContext.ResponseContext;
            bool shouldRetry     = false;

            await this.RetryPolicy.ObtainSendTokenAsync(executionContext, null).ConfigureAwait(false);

            do
            {
                System.Runtime.ExceptionServices.ExceptionDispatchInfo capturedException = null;

                try
                {
                    SetRetryHeaders(requestContext);
                    T result = await base.InvokeAsync <T>(executionContext).ConfigureAwait(false);

                    this.RetryPolicy.NotifySuccess(executionContext);
                    return(result);
                }
                catch (Exception e)
                {
                    capturedException = System.Runtime.ExceptionServices.ExceptionDispatchInfo.Capture(e);
                }

                if (capturedException != null)
                {
                    shouldRetry = await this.RetryPolicy.RetryAsync(executionContext, capturedException.SourceException).ConfigureAwait(false);

                    if (!shouldRetry)
                    {
                        LogForError(requestContext, capturedException.SourceException);
                        capturedException.Throw();
                    }
                    else
                    {
                        requestContext.Retries++;
                        requestContext.Metrics.SetCounter(Metric.AttemptCount, requestContext.Retries);
                        LogForRetry(requestContext, capturedException.SourceException);
                    }

                    await this.RetryPolicy.ObtainSendTokenAsync(executionContext, capturedException.SourceException).ConfigureAwait(false);
                }

                PrepareForRetry(requestContext);

                using (requestContext.Metrics.StartEvent(Metric.RetryPauseTime))
                    await RetryPolicy.WaitBeforeRetryAsync(executionContext).ConfigureAwait(false);
            } while (shouldRetry);
            throw new AmazonClientException("Neither a response was returned nor an exception was thrown in the Runtime RetryHandler.");
        }
Пример #7
0
        public static void ReadLineAndSendLoop(IApplicationClient InnerClient, Action <SecureContext> SetSecureContext, Boolean UseOld, Object Lockee)
        {
            var            NeedToExit  = false;
            AutoResetEvent NeedToCheck = new AutoResetEvent(false);

            System.Runtime.ExceptionServices.ExceptionDispatchInfo edi = null;
            InnerClient.ServerShutdown += e =>
            {
                Console.WriteLine("服务器已关闭。");
                lock (Lockee)
                {
                    NeedToExit = true;
                }
                NeedToCheck.Set();
            };
            InnerClient.Error += e =>
            {
                var m = e.Message;
                Console.WriteLine(m);
            };
            InnerClient.MessageReceived    += e => Console.WriteLine(e.Content);
            InnerClient.MessageReceivedAt2 += e =>
            {
                if (e.Title != "")
                {
                    Console.WriteLine(e.Title);
                }
                foreach (var Line in e.Lines)
                {
                    Console.WriteLine(Line);
                }
            };
            ((Func <Task>)(async() =>
            {
                var r = await InnerClient.CheckSchemaVersion(new CheckSchemaVersionRequest {
                    Hash = UseOld ? "D7FFBD0D2E5D7274" : InnerClient.Hash.ToString("X16")
                });
                if (r.OnHead)
                {
                }
                else if (r.OnSupported)
                {
                    Console.WriteLine("客户端不是最新版本,但服务器可以支持。");
                }
                else if (r.OnNotSupported)
                {
                    Console.WriteLine("客户端版本不受支持。");
                    lock (Lockee)
                    {
                        NeedToExit = true;
                    }
                    NeedToCheck.Set();
                }
                else
                {
                    throw new InvalidOperationException();
                }
            }))();
            while (true)
            {
                String Line = null;
                ThreadPool.QueueUserWorkItem(o =>
                {
                    var l = Console.ReadLine();
                    lock (Lockee)
                    {
                        Line = l;
                    }
                    NeedToCheck.Set();
                });
                while (true)
                {
                    if (NeedToExit)
                    {
                        return;
                    }
                    String l;
                    lock (Lockee)
                    {
                        l = Line;
                    }
                    if (l != null)
                    {
                        break;
                    }
                    NeedToCheck.WaitOne();
                    if (edi != null)
                    {
                        edi.Throw();
                    }
                }
                lock (Lockee)
                {
                    HandleLine(InnerClient, SetSecureContext, UseOld, Line).ContinueWith(tt =>
                    {
                        if (tt.IsFaulted)
                        {
                            edi = System.Runtime.ExceptionServices.ExceptionDispatchInfo.Capture(tt.Exception.InnerException ?? tt.Exception);
                            NeedToCheck.Set();
                            return;
                        }
                        if (!tt.Result)
                        {
                            lock (Lockee)
                            {
                                NeedToExit = true;
                            }
                            NeedToCheck.Set();
                        }
                    });
                }
            }
        }