private async Task HandleUnsuccessfulDelivery(ParallelOptions options, T message, ParallelLoopState state) { if (RetryPolicy == null) { HandleUndeliverable(message); return; } var hash = HashMessage(message); var attempts = IncrementAttempts(hash); var decision = RetryPolicy.DecideOn(message, attempts); switch (decision) { case RetryDecision.RetryImmediately: await ProductionCycle(options, message, state); break; case RetryDecision.Requeue: if (!_buffer.IsAddingCompleted && RetryPolicy?.RequeueInterval != null) { Produce(Observable.Return(message).Delay(RetryPolicy.RequeueInterval(attempts))); } else { Produce(message); } break; case RetryDecision.Backlog: HandleBacklog(message); break; case RetryDecision.Undeliverable: HandleUndeliverable(message); break; case RetryDecision.Destroy: break; default: throw new ArgumentOutOfRangeException(); } }