Module

Effect.Aff.Retry

#RetryStatus

newtype RetryStatus

Datatype with stats about retries made thus far

Constructors

Instances

#RetryPolicyM

newtype RetryPolicyM :: (Type -> Type) -> Typenewtype RetryPolicyM m

A 'RetryPolicyM' is a function that takes an 'RetryStatus' and possibly returns a delay in milliseconds. Iteration numbers start at zero and increase by one on each retry. A Nothing return value from the function implies we have reached the retry limit.

Please note that 'RetryPolicyM' is a 'Monoid'. You can collapse multiple strategies into one using 'mappend' or '<>'. The semantics of this combination are as follows:

  1. If either policy returns 'Nothing', the combined policy returns 'Nothing'. This can be used to @inhibit@ after a number of retries, for example.

  2. If both policies return a delay, the larger delay will be used. This is quite natural when combining multiple policies to achieve a certain effect.

Example:

One can easily define an exponential backoff policy with a limited number of retries:

Naturally, 'mempty' will retry immediately (delay 0) for an unlimited number of retries, forming the identity for the 'Monoid'.

Constructors

Instances

#RetryPolicy

type RetryPolicy = forall m. MonadAff m => RetryPolicyM m

#constantDelay

constantDelay :: forall d. Duration d => d -> RetryPolicy

Cconstant delay with unlimited retries

#exponentialBackoff

exponentialBackoff :: forall d. Duration d => d -> RetryPolicy

Grow delay exponentially each iteration. Each delay will increase by a factor of two.

#fibonacciBackoff

fibonacciBackoff :: forall d. Duration d => d -> RetryPolicy

#fullJitterBackoff

fullJitterBackoff :: forall m d. MonadAff m => Duration d => d -> RetryPolicyM m

FullJitter exponential backoff as explained in AWS Architecture Blog article. @http:\/\/www.awsarchitectureblog.com\/2015\/03\/backoff.html@ temp = min(cap, base * 2 ** attempt) sleep = temp / 2 + random_between(0, temp / 2)

#capDelay

capDelay :: forall d m. Monad m => Duration d => d -> RetryPolicyM m -> RetryPolicyM m

Set a time-upperbound for any delays that may be directed by the given policy. This function does not terminate the retrying. The policy capDelay maxDelay (exponentialBackoff n) will never stop retrying. It will reach a state where it retries forever with a delay of maxDelay between each one. To get termination you need to use one of the 'limitRetries' function variants.

#defaultRetryStatus

defaultRetryStatus :: RetryStatus

Initial, default retry status. Exported mostly to allow user code to test their handlers and retry policies. Use fields or lenses to update.

#applyAndDelay

applyAndDelay :: forall m. MonadAff m => RetryPolicyM m -> RetryStatus -> m (Maybe RetryStatus)

Apply policy and delay by its amount if it results in a retry. Returns updated status.

#applyPolicy

applyPolicy :: forall m. MonadAff m => RetryPolicyM m -> RetryStatus -> m (Maybe RetryStatus)

Apply policy on status to see what the decision would be. 'Nothing' implies no retry, 'Just' returns updated status.

#retryPolicy

retryPolicy :: (RetryStatus -> Maybe Milliseconds) -> RetryPolicy

Helper for making simplified policies that don't use the monadic context.

#limitRetries

limitRetries :: Int -> RetryPolicy

Retry immediately, but only up to @n@ times.

#limitRetriesByDelay

limitRetriesByDelay :: forall d m. Monad m => Duration d => d -> RetryPolicyM m -> RetryPolicyM m

Add an upperbound to a policy such that once the given time-delay amount per try has been reached or exceeded, the policy will stop retrying and fail. If you need to stop retrying once cumulative delay reaches a time-delay amount, use 'limitRetriesByCumulativeDelay'

#limitRetriesByCumulativeDelay

limitRetriesByCumulativeDelay :: forall d m. Monad m => Duration d => d -> RetryPolicyM m -> RetryPolicyM m

Add an upperbound to a policy such that once the cumulative delay over all retries has reached or exceeded the given limit, the policy will stop retrying and fail.

#retrying

retrying :: forall m b. MonadAff m => RetryPolicyM m -> (RetryStatus -> b -> m Boolean) -> (RetryStatus -> m b) -> m b

Retry combinator for actions that don't raise exceptions, but signal in their type the outcome has failed. Examples are the 'Maybe', 'Either' and 'EitherT' monads.

#recovering

recovering :: forall m a. MonadAff m => MonadError Error m => RetryPolicyM m -> Array (RetryStatus -> Error -> m Boolean) -> (RetryStatus -> m a) -> m a

Run an action and recover from a raised exception by potentially retrying the action a number of times.

Modules