/// <summary>
        /// Create a retry policy
        /// </summary>
        /// <param name="policy">Retry policy to use</param>
        /// <param name="options">Retry policy options</param>
        /// <returns></returns>
        public static IRetryPolicy Create(RetryPolicy policy, RetryPolicyOptions options)
        {
            switch (policy)
            {
            case RetryPolicy.ExponentialBackoff:
                return(new ExponentialBackoffPolicy(options));

            case RetryPolicy.EasedBackoff:
                return(new EasedBackoffPolicy(options));

            default:
                return(new StaticDelayPolicy(options));
            }
        }
Example #2
0
 /// <summary>
 /// Perform an synchronous retry up to the maximum specified limit
 /// </summary>
 /// <param name="action"></param>
 /// <param name="retryInterval">How often to perform the retry.</param>
 /// <param name="retryLimit">The maximum number of times to retry</param>
 /// <param name="retryPolicy">The retry policy to apply</param>
 /// <param name="retryPolicyOptions">Options to specify further configuration for a retry policy</param>
 /// <exception cref="RetryTimeoutException"></exception>
 public static void Do(RetryAction action, TimeSpan retryInterval, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions)
 => Do((iteration, max) => action.Invoke(), retryInterval, retryLimit, retryPolicy, retryPolicyOptions, null, null);
Example #3
0
 /// <summary>
 /// Perform a synchronous retry up to the maximum specified limit
 /// </summary>
 /// <typeparam name="T"></typeparam>
 /// <param name="action">The Action to call that will be retried until successful.</param>
 /// <param name="retryInterval">How often to perform the retry.</param>
 /// <param name="retryLimit">The maximum number of times to retry</param>
 /// <param name="onFailure">Will be called upon an exception thrown</param>
 /// <param name="retryPolicy">The retry policy to apply</param>
 /// <param name="retryPolicyOptions">The options to provide your retry policy</param>
 /// <param name="mustReturnTrueBeforeFail">Must evaluate to true for retry to fail</param>
 /// <param name="exceptionTypes">A list of exceptions that will be retried gracefully. All other exceptions will be rethrown.</param>
 /// <exception cref="RetryTimeoutException"></exception>
 /// <returns></returns>
 public static T Do <T>(RetryActionWithParametersAndResult <T> action, TimeSpan retryInterval, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions, Action <Exception, int, int> onFailure, Func <bool> mustReturnTrueBeforeFail, params Type[] exceptionTypes)
 => PerformAction((x, y) => action.Invoke(x, y), retryInterval, retryLimit, retryPolicy, retryPolicyOptions, onFailure, mustReturnTrueBeforeFail, exceptionTypes);
Example #4
0
 /// <summary>
 /// Perform a synchronous retry up to the maximum specified limit
 /// </summary>
 /// <param name="action">The Action to call that will be retried until successful.</param>
 /// <param name="retryInterval">How often to perform the retry.</param>
 /// <param name="retryLimit">The maximum number of times to retry</param>
 /// <param name="onFailure">Will be called upon an exception thrown</param>
 /// <param name="mustReturnTrueBeforeFail">Must evaluate to true for retry to fail. Evaluating to false will retry infinitely until true.</param>
 /// <param name="retryPolicy">The retry policy to apply</param>
 /// <param name="retryPolicyOptions">The options to provide your retry policy</param>
 /// <param name="exceptionTypes">A list of exceptions that will be retried gracefully. All other exceptions will be rethrown.</param>
 /// <exception cref="RetryTimeoutException"></exception>
 public static void Do(RetryActionWithParameters action, TimeSpan retryInterval, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions, Action <Exception, int, int> onFailure, Func <bool> mustReturnTrueBeforeFail, params Type[] exceptionTypes)
 => PerformAction <object>((x, y) => { action.Invoke(x, y); return(null); }, retryInterval, retryLimit, retryPolicy, retryPolicyOptions, onFailure, mustReturnTrueBeforeFail, exceptionTypes);
Example #5
0
 /// <summary>
 /// Perform an synchronous retry up to the maximum specified limit
 /// </summary>
 /// <typeparam name="T"></typeparam>
 /// <param name="action"></param>
 /// <param name="retryInterval">How often to perform the retry.</param>
 /// <param name="retryLimit">The maximum number of times to retry</param>
 /// <param name="retryPolicy">The retry policy to apply</param>
 /// <param name="retryPolicyOptions">Options to specify further configuration for a retry policy</param>
 /// <exception cref="RetryTimeoutException"></exception>
 /// <returns></returns>
 public static T Do <T>(RetryActionWithParametersAndResult <T> action, TimeSpan retryInterval, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions)
 => Do(action, retryInterval, retryLimit, retryPolicy, retryPolicyOptions, null, null);
Example #6
0
 /// <summary>
 /// Perform an synchronous retry up to the maximum specified limit
 /// </summary>
 /// <param name="action"></param>
 /// <param name="retryInterval">How often to perform the retry.</param>
 /// <param name="retryLimit">The maximum number of times to retry</param>
 /// <param name="retryPolicy">The retry policy to apply</param>
 /// <param name="retryPolicyOptions">Options to specify further configuration for a retry policy</param>
 /// <exception cref="RetryTimeoutException"></exception>
 public static void Do(RetryActionWithParameters action, TimeSpan retryInterval, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions)
 => Do(action, retryInterval, retryLimit, retryPolicy, retryPolicyOptions, null, null);
Example #7
0
        private static async Task <T> PerformActionAsync <T>(RetryActionWithParametersAndResultAsync <T> action, TimeSpan retryInterval, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions, CancellationToken?cancellationToken, Action <Exception, int, int> onFailure, Func <bool> mustReturnTrueBeforeFail, params Type[] exceptionTypes)
        {
            var exceptions     = new List <Exception>();
            var startTime      = DateTime.Now;
            var retryIteration = 0;

            do
            {
                try
                {
                    // invoke the action
                    return(await InvokeAsync(action, retryIteration, retryLimit, cancellationToken));
                }
                catch (Exception ex)
                {
                    exceptions.Add(ex);
                    await HandleExceptionAsync(ex, startTime, retryInterval, retryIteration, retryLimit, retryPolicy, retryPolicyOptions, onFailure, exceptionTypes);
                }
                retryIteration++;
            } while (MustContinue(mustReturnTrueBeforeFail) || (retryIteration < retryLimit && (!cancellationToken.HasValue || !cancellationToken.Value.IsCancellationRequested)));

            throw new RetryTimeoutException(exceptions, retryLimit);
        }
Example #8
0
        private static async Task WaitOrThrowAsync(Exception ex, DateTime startTime, TimeSpan retryInterval, int retryIteration, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions, params Type[] exceptionTypes)
        {
            if (exceptionTypes == null || exceptionTypes.Length == 0 || exceptionTypes.Contains(ex.GetType()))
            {
                if (retryIteration - 1 < retryLimit)
                {
                    var sleepValue = RetryPolicyFactory
                                     .Create(retryPolicy, retryPolicyOptions)
                                     .ApplyPolicy(RetryParameters.Create(startTime, retryInterval, retryIteration, retryLimit));
                    if (sleepValue.TotalMilliseconds < 0)
                    {
                        throw new ArgumentOutOfRangeException();
                    }

                    // use Task.Delay for asynchronous waits
                    await Task.Delay(sleepValue);
                }
            }
            else
            {
                throw ex;
            }
        }
Example #9
0
        private static async Task HandleExceptionAsync(Exception ex, DateTime startTime, TimeSpan retryInterval, int retryIteration, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions, Func <Exception, int, int, Task> onFailure, params Type[] exceptionTypes)
        {
            await Task.Yield();

            if (onFailure != null)
            {
                await onFailure(ex, retryIteration, retryLimit);
            }
            await WaitOrThrowAsync(ex, startTime, retryInterval, retryIteration, retryLimit, retryPolicy, retryPolicyOptions, exceptionTypes);
        }
Example #10
0
        private static async Task HandleExceptionAsync(Exception ex, DateTime startTime, TimeSpan retryInterval, int retryIteration, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions, Action <Exception, int, int> onFailure, params Type[] exceptionTypes)
        {
            await Task.Yield();

            onFailure?.Invoke(ex, retryIteration, retryLimit);
            await WaitOrThrowAsync(ex, startTime, retryInterval, retryIteration, retryLimit, retryPolicy, retryPolicyOptions, exceptionTypes);
        }
Example #11
0
        private static T PerformAction <T>(RetryActionWithParametersAndResult <T> action, TimeSpan retryInterval, int retryLimit, RetryPolicy retryPolicy, RetryPolicyOptions retryPolicyOptions, Action <Exception, int, int> onFailure, Func <bool> mustReturnTrueBeforeFail, params Type[] exceptionTypes)
        {
            var exceptions     = new List <Exception>();
            var startTime      = DateTime.Now;
            var retryIteration = 0;

            do
            {
                try
                {
                    // invoke the action
                    return(action(retryIteration, retryLimit));
                }
                catch (Exception ex)
                {
                    exceptions.Add(ex);
                    HandleException(ex, startTime, retryInterval, retryIteration, retryLimit, retryPolicy, retryPolicyOptions, onFailure, exceptionTypes);
                }
                retryIteration++;
            } while (MustContinue(mustReturnTrueBeforeFail) || retryIteration < retryLimit);

            throw new RetryTimeoutException(exceptions, retryLimit);
        }