CathalMF
CathalMF

Reputation: 10055

System.IO.IOException: The process cannot access the file because it is being used by another process

I'm using a FileSystemWatcher to monitor a log file for changes.

The log file is written by a 3rd party application.

Once a change is triggered, I am attempting to read the file using:

using (FileStream fs = new FileStream(e.FullPath, FileMode.Open, 
    FileAccess.Read, FileShare.ReadWrite))
{
    StreamReader sr = new StreamReader(fs);
    string s = sr.ReadLine();
}

Sometimes it fails on the using line.

Other times it fails on sr.ReadLine() which I assume is happening because the 3rd party system is currently accessing the file.

I thought that by setting the FileAccess.Read I should be able to always read the file?

How can I make sure that this doesn't cause an exception, or do I need to just loop around until I can successfully read?

Upvotes: 4

Views: 6202

Answers (1)

Ulf Kristiansen
Ulf Kristiansen

Reputation: 1631

Short answer: Try Thread.Sleep(100) before you read and then read as fast as you can.

I thought that by setting the FileAccess.Read I should be able to always read the file?

By setting FileAccess.Read you are just saying that you need to read from the file. By setting FileShare.ReadWrite you are saying you are comfortable with the 3rd party reading and writing to the file while you read it. The exception means that the 3rd party is not comfortable with you reading while they are writing. Your first bet is to check if you can configure the 3rd party process to allow other processes to read while they write, but be aware that reading from a file that is being written to can be troublesome.

How can I make sure that this doesn't cause an exception, or do I need to just loop around until I can successfully read?

As long as the 3rd party require a exclusive lock there is no way to guarantee that you won't get the exception, but there are steps you can take to reduce the risk of conflict, mainly:

  • Read when they don't write
  • Read fast

Read when they don't write

Right now you are monitoring the file and reading as soon as the 3rd party write. Chances are they are still writing when you try to read, so you should wait a bit for them to finish. I would try Thread.Sleep 100 ms before reading, but it depends on the nature of the 3rd party process; i.e if it flushes the log every hour then you could wait more, but if it writes every second you wait less.

Read fast

See this question for tips on how to read fast. Also have in mind that right now you are reading the complete file repeatedly. If it's a big appending file you have the option of caching the part you have already read and Seek the last known position on next read. This way you will just skip what you have read before.

Upvotes: 4

Related Questions