Directory.CreateDirectory Latency Issue?

2020-08-18 06:00发布

问题:

I'm trying to create a remote directory, and then write a file to it. Every great once in a while, the application fails with a System.IO.DirectoryNotFoundException while trying to write the file.

When I write the file, I'm using the returned DirectoryInfo object to help create the file path, so the application seems to think that the directory has been created. However, the directory does not exist.

Is there any chance that I'm trying to write to the directory before Windows has finished creating it? I would think that the Directory.CreateDirectory would not return until this task was finished.

回答1:

Answer - Yes. The behavior, when file/directory creation is lagging is expected. Ordinary solution as proposed by other commenter is to use retries with some timeout. The behavior is the same whatever file functions are used: Findfirst, CreateFile, WaitForSingleObject etc.

Another solution will be to use new transactional functions of API found on Vista and later Windows OSes.

The problem is nasty and was never understood by developers of file-intensive projects made on other platforms and moved to Windows: like DOS/CMD scripts, SVN clients, Cygwin, perl, various java applications, various installers etc.



回答2:

I just had this problem and for me the situation was like this:

if(!exportDirectory.Exists)
    exportDirectory.Create();

Then later when in another class that has this same DirectoryInfo object passed to it I do a:

if (!exportDirectory.Exists)
    throw new DirectoryNotFoundException(exportDirectory.FullName);

And the directory apparently still doesn't exist (although I have the parent directory open in windows and of course I can see it right in front of me).

The solution I found is after the initial creation of the directory I should be calling:

exportDirectory.Refresh();

From Microsoft:

Refreshes the state of the object. (Inherited from FileSystemInfo.)



回答3:

While I have never experienced this behavior and cannot explain it, a pragmatic solution is to setup a loop around your call accessing the directory. Catch DirectoryNotFoundException inside that loop, and retry access a few times after a short pause each time. Rethrow the exception if the retry count is exceeded.

Adding detailed logging at this point may help you determine the actual cause of the problem.