none
Getting "Unable to remove the file to be replaced." error during the call to File.Replace, if in another process FileSystemWatcher is running and for the events executing a call to Path.GetDirectoryName RRS feed

  • Question

  • Hi All,

    I have two console applications: FileReplacerr and FileSystemWatcherr.

    FileReplacer:

    using System;
    using System.Collections.Generic;
    using System.IO;
    using System.Xml;
    
    namespace ConsoleApplication1
    {
        internal static class FileReplacer
        {
            private static void Main(string[] args)
            {
                Console.WriteLine("Test Started.");
                Directory.CreateDirectory(rootPath);
                CleanUp(new List<string> { livePath, tempPath }, -1);
                for (int loopIndex = 0; loopIndex < 10000; loopIndex++)
                {
                    WriteXmlFile(livePath + loopIndex, "LiveContent");
                    WriteXmlFile(tempPath + loopIndex, "TempContent");
                    ReplaceFiles(livePath + loopIndex, tempPath + loopIndex);
                    CleanUp(new List<string> { livePath + loopIndex, tempPath + loopIndex }, loopIndex);
                }
                Console.WriteLine("---------------------------------------------");
                Console.WriteLine("Test Finished.");
                Console.WriteLine("Exception count: {0}", exceptionCount);
                Console.WriteLine("Press any key to exit");
                Console.ReadKey();
            }
    
            private static void ReplaceFiles(string replacedFile, string replacementFile)
            {
                try
                {
                    File.Replace(replacedFile, replacementFile, null);
                }
                catch (Exception ex)
                {
                    exceptionCount++;
                    string extendedErrorMessage = string.Format("Replacement of original:'{0}' and temporary:'{1}' xml file completed with error code: {2}", replacedFile, replacementFile, ex.Message);
                    Console.WriteLine("Exception happened during replace:");
                    Console.WriteLine(extendedErrorMessage);
                    Console.WriteLine("Press any key to continue");
                    Console.ReadKey();
                }
            }
    
            private static void WriteXmlFile(string filePath, string elementText)
            {
                using (FileStream fileStream = new FileStream(filePath, FileMode.Create, FileAccess.Write, FileShare.None, 32 * 1024, FileOptions.SequentialScan))
                {
                    fileStream.Seek(0, SeekOrigin.Begin);
                    fileStream.SetLength(0);
    
                    XmlWriterSettings settings = new XmlWriterSettings { CheckCharacters = false };
                    using (XmlWriter xmlWriter = XmlWriter.Create(fileStream, settings))
                    {
                        xmlWriter.WriteStartDocument();
                        xmlWriter.WriteStartElement(elementText);
                        xmlWriter.WriteEndElement();
                        xmlWriter.WriteEndDocument();
                    }
                }
            }
    
            private static void CleanUp(List<string> filePaths, int loopIndex)
            {
                foreach (string filePath in filePaths)
                {
                    File.Delete(filePath);
                }
            }
    
            private static int exceptionCount = 0;
            static readonly string rootPath = @"C:\teststorage\";
            static readonly string liveFile = "live.xml";
            static readonly string tempFile = "temp.xml.tmp";
            static readonly string livePath = rootPath + liveFile;
            static readonly string tempPath = rootPath + tempFile;
        }
    }
    


    FileSystemWatcherr:

    using System;
    using System.IO;
    
    namespace FileSystemWatcherr
    {
        class FileSystemWatcherr
        {
            static void Main(string[] args)
            {
                using (FileSystemWatcher watcher = new FileSystemWatcher
                {
                    Path = @"c:\",
                    NotifyFilter = NotifyFilters.LastWrite | NotifyFilters.DirectoryName | NotifyFilters.FileName,
                    IncludeSubdirectories = true
                })
                {
                    watcher.Changed += OnFolderStructureChanged;
                    watcher.Created += OnFolderStructureChanged;
                    watcher.Deleted += OnFolderStructureChanged;
                    watcher.Renamed += OnFolderStructureChanged;
                    watcher.EnableRaisingEvents = true;
    
                    Console.WriteLine("FileSystemWatcher is active");
                    Console.WriteLine("Press any key to stop watching and exit");
                    Console.ReadKey();
    
                    watcher.EnableRaisingEvents = false;
                    watcher.Changed -= OnFolderStructureChanged;
                    watcher.Created -= OnFolderStructureChanged;
                    watcher.Deleted -= OnFolderStructureChanged;
                    watcher.Renamed -= OnFolderStructureChanged;
                }
            }
    
            private static void OnFolderStructureChanged(object sender, FileSystemEventArgs e)
            {
                string path = string.Empty;
                switch (e.ChangeType)
                {
                    case WatcherChangeTypes.Changed:
                    case WatcherChangeTypes.Deleted:
                    case WatcherChangeTypes.Renamed:
                    case WatcherChangeTypes.Created:
                    default:
                        path = Path.GetDirectoryName(e.FullPath);
                        break;
                }
            }
        }
    }
    

    If I start the FileSystemWatcherr and then start the FileReplacerr, many times I get the following exception:

    Unable to remove the file to be replaced.

    Could someone tell me why I get this exception?

    Many thanks,

    Zsolt

    Wednesday, October 18, 2017 3:39 PM

All replies

  • @Zsolt,

    Sounds like it is the same like this thread mentioned:

    https://stackoverflow.com/questions/699538/file-access-error-with-filesystemwatcher-when-multiple-files-are-added-to-a-dire

    That the file is being used so the remove does not work. Have you tried to check the file status first? Maybe we need to use some ways to check the file status. For example, whether it is being used or already deleted.

    Best regards,

    Barry


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Thursday, October 19, 2017 9:58 AM
  • @Barry,

    For me it seems to be a different problem, as in my case the File.Replace is throwing an exception, and not the consuming of the events.

    During the File.Replace call I can not do anything. And when an event is fired I only call the Path.GetDirectoryName(e.FullPath) which should not cause a denied access.

    Another interesting thing is that the issue is comming more frequently on Win7 machines. On my Win10 machine it did not come, but running the applications on a virtual machine with Win10, the issue comes many times during 10000 loops.

    I used ProcessMonitor to see if I can find out anything, and I do not see from it's output what could be the reoot cause: Process Monitor output

    • Edited by Bartha Zsolt Thursday, October 19, 2017 11:14 AM
    Thursday, October 19, 2017 11:11 AM
  • @Bartha Zsolt,

    Well yep it is not the same. I've tried your code on my 15063 and it happened every time it reached about 8000-9000 times. Maybe your VM has a different Windows 10 version?

    Best regards,

    Barry


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Friday, October 20, 2017 7:21 AM