0

Before I elaborate on my question - I am not a professional programmer/coder but a recent project which involves a fair amount of reading files, writing files, moving files into folders etc has got be wondering how to best handle exceptions from multiple sources (all of which are file/folder reads/writes).

The project has a basic 'retry' facility on some file-based operations, where it will sleep for a second or 2 and then retry up to X times - then it will throw a message box basically stating it couldn't do it.

Is there a way to take any/all file/folder access exceptions, create a single 'retry' routine for it - having it retry what it tried to do before (and failed) before finally giving up and alerting someone - or is this something that should be done a per file-operation basis?

I guess what I'm thinking is that for many applications, if an operation fails - the application knows what it was doing previously and can retry it - but rather than write the same 'retry' code (with modified code based on what operation was attempted) - is it possible to have a single routine to retry it?

I'm not even sure it's possible, let alone recommended.

The 'retry' code is very basic and is similar to below:

int retrycount = 3;
int retries = 0;

while (retries < retrycount)
{
   try
   {
      File.Copy(SomeFile, SomeOtherFile);
   }
   catch (Exception e)
   {
      // Try Again
      retries++;
   }

   if (File.Exists(SomeOtherFile) == true)
   {
      break;
   }
}

Later, 'retries' is used to determine if it failed completely (retries == retrycount) and to alert if this happens.

If anyone can offer any words of advice or even if it's just to tell me that what I'm thinking of is possible - it is not recommended, would be helpful.

Kurubaran
  • 8,696
  • 5
  • 43
  • 65
Arkane
  • 3
  • 3

2 Answers2

4

You can do that by passing an Action:

public void Retry(Action action, int retryCount)
{
    int retries = 0;

    while (retries < retryCount)
    {
       try
       {
          action();
          return;
       }
       catch (Exception e)
       {
          // Try Again
          retries++;
       }
    }
}


Retry(() => File.Copy(SomeFile, SomeOtherFile), 3);

Edit: and of course that's been asked before, see How to implement re-try n times in case of exception in C#?.

Community
  • 1
  • 1
CodeCaster
  • 147,647
  • 23
  • 218
  • 272
  • 1
    I would slightly change this by using a `for`, saving some lines of code, and not declaring `e`, as that would provoke a warning. – Andrew Jan 06 '15 at 13:55
  • 1
    @Andrew you're right, but when answering I tend to keep the code as close to OP's code as possible. From an entire rewrite they tend to learn less. ;) – CodeCaster Jan 06 '15 at 14:01
  • Would this sort of thing work for other things like DB access - for example attempting to insert records? – Arkane Jan 06 '15 at 14:04
  • It would work for anything. You just may want to add a delay between retries in cases like that. A third parameter would be a good option. – Andrew Jan 06 '15 at 14:06
1

One way of doing it:

  • 1 Create a Queue of {File, LastAttempt, Attempts}
  • 2 Add all your files to the queue
  • 3 Fetch an entry from the list
  • 4 If not enough time has passed since the last attempt, wait
  • 5 Attempt the operation, increment Attempts
  • 6 If the operation fails, update LastAttempt to DateTime.Now, add back to end of queue (unless Attempts is larger than some threshold, in which case you add the file to a list of failed files)
  • 7 If there are still entries in the queue, repeat from 3
Chris
  • 5,442
  • 17
  • 30