0

I have a fire-and-forget Web Service that processes incoming requests. The request needs to go through number of processes that interact with the database via a single-threaded TPL pipeline.

If any process fails the message should be retried but it should be placed at the end of that block's queue. In other words the retry shouldn't be handled by the delegate; it should go to the back of the line (with its retry counter incremented).

Does TPL have this type of functionality built-in or do I need to code it myself?

Would something like this work?

// Proceed if the operation was successful
_firstProcess.LinkTo(_secondProcess, linkOptions, m => m.Succeeded == true);

// Go back to the beginning if it failed
_firstProcess.LinkTo(_firstProcess, linkOptions, m => m.Succeeded == false);

...

// Apply the same to every block.
Peter Csala
  • 17,736
  • 16
  • 35
  • 75
ilitirit
  • 16,016
  • 18
  • 72
  • 111
  • 2
    According to my understanding this approach will try to retry the requests until they finally succeed. Please note that not all types of failures are retriable. Please also note that having an upper bound on the max retry count is a good practice to avoid never completing requests. – Peter Csala Dec 30 '22 at 11:22
  • Related: [Retry policy within ITargetBlock](https://stackoverflow.com/questions/17469689/retry-policy-within-itargetblocktinput), and also [How to keep track of faulted items in TPL pipeline in (thread)safe way](https://stackoverflow.com/questions/62154993/how-to-keep-track-of-faulted-items-in-tpl-pipeline-in-threadsafe-way). – Theodor Zoulias Dec 30 '22 at 11:38
  • Are you interested for settings like `MaxAttemptsPerItem`, `MaxRetriesTotal` and `MinimumRetryDelay`? Or you are OK with infinite retries per item, and with zero delay between retrying the same item? – Theodor Zoulias Dec 30 '22 at 11:40

1 Answers1

0

I've tested and implemented and this since the time I've asked the question. The basic idea works fine. I've added retry counters and Terminal Error blocks. In simple terms, each Transform block links to itself based on the value in the "Succeeded" property, which is only if no errors occurred. If the retry counter exceeds a specified value, it links to a block that acts as a Terminal Error that requires manual intervention.

Because of the nature of the expected errors, everything that enters the block shortly afterwards is also expected to fail within that specific time window. For this purposes, a dynamic delay mechanism was added for specific blocks when a particular type of error is encountered.

ilitirit
  • 16,016
  • 18
  • 72
  • 111