Ошибка File.Move при использовании файла File.Delete

У нас есть метод MoveFile, который обычно работает, но не работает на сайте клиента.

if (File.Exists(target))
{
    File.Delete(target);
}

File.Move(source, target);

Вызов File.Move неоднократно прерывается с помощью

System.IO.IOException: Cannot create a file when that file already exists.

   at System.IO.__Error.WinIOError(Int32 errorCode, String maybeFullPath)
   at System.IO.__Error.WinIOError()
   at System.IO.File.Move(String sourceFileName, String destFileName)

У нас есть обработка ошибок, связанных с вызовом этого метода, но мы не можем понять, почему File.Delete не работает и ничего не бросает.

Мы хотя о разрешении файла, но затем File.Delete выбрали бы UnauthorizedAccessException.

Есть ли какая-либо другая причина, которая приведет к сбою File.Move с "уже существующим файлом", когда ему предшествует удаление этого конкретного файла?

Ответ 1

Можно ли изменить логику?

File.Copy (source, target, true) 

чтобы перезаписать цель, затем

File.Delete(source)

Ответ 2

В прошлом я обнаружил, что система имеет тенденцию удалять файл "медленнее", чем ваша программа работает.

В идеале вам нужно проверить, был ли файл удален, прежде чем пытаться переместить файл на свое место. Обычно вы можете обойти это с помощью простого Thread.Sleep(200) или подобного, но, вероятно, это не самый надежный способ!

Ответ 3

Я считаю, что это может произойти, если у кого-то есть файл, открытый с опцией FileShare.Delete(т.е. разрешить удаление). В этом случае файл будет помечен для удаления, но фактически не будет удален, пока другой дескриптор не будет закрыт.

Я не уверен, какие процессы могли бы открыть файл таким образом - антивирусное программное обеспечение было бы одной возможностью.

Ответ 4

Я думаю, что вы можете получить лучшие результаты из:

System.IO.File.Copy(sourceFileName, destFileName, overwrite);

так что overwrite = true

это будет перезаписывать старый файл, если он существует, а не беспокоиться, удалив его отдельно.

Затем вы можете удалить оригинал по мере необходимости.

Ответ 5

Здесь еще лучший способ избежать копирования или опроса удаления -
Предположим, что у нас есть File_A и File_B. Мы хотим переместить File_B через File_A.
Шаги:
1) Переименуйте (переместите) File_A на третье имя, File_C.
2) Удалить File_C.
3) Переименуйте (переместите) File_B в File_A.

File.Move("File_A", "File_C");
File.Delete("File_C");
File.Move("File_B", "File_A");

Это устраняет условие гонки, когда удаляется исходный файл, когда новый файл перемещается в исходный файл.