internal Task <bool> MoveTransmissionsAndWaitForSender(CancellationToken cancellationToken)
        {
            if (cancellationToken.IsCancellationRequested)
            {
                return(TaskEx.FromCanceled <bool>(cancellationToken));
            }

            TaskStatus senderStatus            = TaskStatus.Canceled;
            bool       isStorageEnqueueSuccess = false;

            try
            {
                this.Storage.IncrementFlushAsyncCounter();
                isStorageEnqueueSuccess = MoveTransmissions(this.Buffer.Dequeue, this.Storage.Enqueue, this.Buffer.Size, cancellationToken);
                TelemetryChannelEventSource.Log.MovedFromBufferToStorage();
                senderStatus = this.Sender.WaitForPreviousTransmissionsToComplete(cancellationToken).ConfigureAwait(false).GetAwaiter().GetResult();
            }
            catch (Exception exp)
            {
                senderStatus = TaskStatus.Faulted;
                TelemetryChannelEventSource.Log.TransmissionFlushAsyncWarning(exp.ToString());
            }
            finally
            {
                this.Storage.DecrementFlushAsyncCounter();
            }

            if (senderStatus == TaskStatus.Canceled)
            {
                return(TaskEx.FromCanceled <bool>(cancellationToken));
            }

            return(senderStatus == TaskStatus.RanToCompletion && isStorageEnqueueSuccess ? this.successTask : this.failedTask);
        }
Beispiel #2
0
 public static void TaskExGenericFromCanceledIsCanceled()
 {
     using (var source = new CancellationTokenSource())
     {
         source.Cancel();
         var task = TaskEx.FromCanceled <bool>(source.Token);
         Assert.IsTrue(task.IsCanceled);
     }
 }
Beispiel #3
0
        /// <summary>
        /// Asynchronously flushes the telemetry buffer.
        /// </summary>
        /// <returns>
        /// Returns true when telemetry data is transferred out of process (application insights server or local storage) and are emitted before the flush invocation.
        /// Returns false when transfer of telemetry data to server has failed with non-retriable http status code.
        /// </returns>
        public Task <bool> FlushAsync(CancellationToken cancellationToken)
        {
            if (!this.isInitialized)
            {
                TelemetryChannelEventSource.Log.StorageNotInitializedError();
            }

            TelemetryChannelEventSource.Log.TelemetryChannelFlushAsync();
            return(cancellationToken.IsCancellationRequested ? TaskEx.FromCanceled <bool>(cancellationToken) : this.TelemetryBuffer.FlushAsync(cancellationToken));
        }
        /// <summary>
        /// Passes all <see cref="ITelemetry"/> items to the <see cref="TelemetrySerializer"/>, empties the queue and returns a task.
        /// </summary>
        public virtual Task <bool> FlushAsync(CancellationToken cancellationToken)
        {
            List <ITelemetry> telemetryToFlush = this.GetBufferTelemetryAndResetBuffer();

            if (!cancellationToken.IsCancellationRequested)
            {
                return(this.serializer.SerializeAsync(telemetryToFlush, cancellationToken));
            }

            return(TaskEx.FromCanceled <bool>(cancellationToken));
        }
        internal Task <bool> FlushAsync(Transmission transmission, CancellationToken cancellationToken)
        {
            TaskStatus taskStatus = TaskStatus.Canceled;

            if (!cancellationToken.IsCancellationRequested)
            {
                transmission.IsFlushAsyncInProgress = true;
                this.Enqueue(transmission);

                try
                {
                    this.Storage.IncrementFlushAsyncCounter();
                    taskStatus = this.MoveTransmissionsAndWaitForSender(transmission.FlushAsyncId, cancellationToken);
                }
                catch (Exception exp)
                {
                    taskStatus = TaskStatus.Faulted;
                    TelemetryChannelEventSource.Log.TransmissionFlushAsyncWarning(exp.ToString());
                }
                finally
                {
                    this.Storage.DecrementFlushAsyncCounter();
                }
            }

            Task <bool> flushTaskStatus = null;

            if (taskStatus == TaskStatus.Canceled)
            {
                flushTaskStatus = TaskEx.FromCanceled <bool>(cancellationToken);
            }
            else if (taskStatus == TaskStatus.RanToCompletion && transmission.IsFlushAsyncInProgress)
            {
                flushTaskStatus = this.successTask;
            }
            else
            {
                flushTaskStatus = this.failedTask;
            }

            return(flushTaskStatus);
        }
Beispiel #6
0
        private async Task <string> ReceiveLoopAsync(BufferingContext bufferingContext, CancellationToken cancellationToken, int loop)
        {
            using (bufferingContext)
            {
                var encoding    = bufferingContext.Encoding;
                var bufferBytes = bufferingContext.BufferBytes;
                var bufferChars = bufferingContext.BufferChars;
                var sb          = bufferingContext.StringBuilder;

                try
                {
                    string response = null;
                    while ((loop == -1 || --loop >= 0) && !cancellationToken.IsCancellationRequested)
                    {
                        response = await ReceiveMessageAsync(cancellationToken, bufferBytes, bufferChars, encoding, sb);

                        sb = sb.Clear();
                    }

                    if (cancellationToken.IsCancellationRequested)
                    {
                        return(await TaskEx.FromCanceled <string>(cancellationToken));
                    }
                    return(response);
                }
                catch (AggregateException ex)
                {
                    ErrorReceived?.Invoke(this, new SocketErrorEventArgs {
                        Exception = ex.Flatten()
                    });
                }
                catch (Exception ex)
                {
                    ErrorReceived?.Invoke(this, new SocketErrorEventArgs {
                        Exception = ex
                    });
                }
            }
            return(await Task.FromResult(string.Empty));
        }
        /// <summary>
        /// Creates a new entry and queues it to this wait queue. If the cancellation token is already canceled, this method immediately returns a canceled task without modifying the wait queue.
        /// </summary>
        /// <param name="this">The wait queue.</param>
        /// <param name="mutex">A synchronization object taken while cancelling the entry.</param>
        /// <param name="token">The token used to cancel the wait.</param>
        /// <returns>The queued task.</returns>
        public static Task <T> Enqueue <T>(this IAsyncWaitQueue <T> @this, object mutex, CancellationToken token)
        {
            if (token.IsCancellationRequested)
#if NET451
            { return(TaskEx.FromCanceled <T>(token)); }
#else
            { return(Task.FromCanceled <T>(token)); }
#endif

            var ret = @this.Enqueue();
            if (!token.CanBeCanceled)
            {
                return(ret);
            }

            var registration = token.Register(() =>
            {
                lock (mutex)
                    @this.TryCancel(ret, token);
            }, useSynchronizationContext: false);
            ret.ContinueWith(_ => registration.Dispose(), CancellationToken.None, TaskContinuationOptions.ExecuteSynchronously, TaskScheduler.Default);
            return(ret);
        }
Beispiel #8
0
        private Task <string> ReceiveLoopAsync(BufferingContext bufferingContext, CancellationToken cancellationToken, int loop)
        {
            string response = null;

            return(TaskEx.AsyncLoopTask(() =>
            {
                cancellationToken.ThrowIfCancellationRequested();

                if (loop == -1 || --loop >= 0)
                {
                    return TaskEx.FromResult(Flow <string> .Return(response));
                }
                var encoding = bufferingContext.Encoding;
                var bufferBytes = bufferingContext.BufferBytes;
                var bufferChars = bufferingContext.BufferChars;
                var sb = bufferingContext.StringBuilder;

                return ReceiveMessageAsync(cancellationToken, bufferBytes, bufferChars, encoding, sb).ContinueWith(t =>
                {
                    response = t.Result;
                    sb.Length = 0;
                    return Flow <string> .Continue();
                }, cancellationToken);
            }).ContinueWithTask(task =>
            {
                if (cancellationToken.IsCancellationRequested)
                {
                    return TaskEx.FromCanceled <string>(cancellationToken);
                }
                return TaskEx.FromResult(task.Result);
            }, cancellationToken)
                   .CatchWith <string, Exception>(ex => ErrorReceived?.Invoke(this, new SocketErrorEventArgs {
                Exception = ex
            }))
                   .UsingWith(bufferingContext));
        }
Beispiel #9
0
 public static void TaskExGenericFromCanceledThrowsOnNonCanceledToken()
 {
     Assert.Throws <ArgumentOutOfRangeException, Task <bool> >(() => TaskEx.FromCanceled <bool>(CancellationToken.None));
 }