在代码中移动文件后出现文件锁定错误

时间:2016-11-20 22:57:30

标签: c# system.io.file

我使用以下代码将文件移动到文件夹

File.Move(Source,Dest);

然后我尝试在下一个方法中打开并读取文件,但是我一直因进程错误而锁定文件。

所以我将文件移动到以下代码

public async static Task<bool> MoveFileAsync(string sourceFileName, string destinationFileName)
{
    using(FileStream sourceStream = File.Open(sourceFileName, FileMode.Open))
    {
        using(FileStream destinationStream = File.Create(destinationFileName))
        {
            try
            {
                await sourceStream.CopyToAsync(destinationStream);
                File.Delete(sourceFileName);
                return true;
            }
            catch
            {
                return false;
            }
        }
    }
}

我一直收到文件锁定的错误

关于如何防止这种情况发生的任何想法。

这都是使用FileSystemWatcher监视文件夹......代码如下。我可以确认当我将文件拖放到文件夹中时没有发生这些错误...即使我拖动多个文件...     使用系统;     使用System.Collections.Generic;     使用System.IO;     使用System.Linq;     使用System.Text;     使用System.Threading.Tasks;

namespace DocumentManager.RepositoryService
{
    internal class MonitorDropFolder
    {
        public string RepositoryPath { get; set; }
        public FileSystemWatcher Watcher { get; set; }

        public MonitorDropFolder ()
        {
            Watcher = new FileSystemWatcher();
            Watcher.Path = @"c:\Repository\DropLocation";
            Watcher.NotifyFilter = NotifyFilters.FileName;
            Watcher.Filter = "*.docx";
            Watcher.Created += new FileSystemEventHandler(OnCreatedHandler);

            StartMonitoring();
        }

        public void StartMonitoring()
        {
            Watcher.EnableRaisingEvents = true;
        }

        public void StopMonitoring()
        {
            Watcher.EnableRaisingEvents = false;
        }

        private void OnCreatedHandler(object source, FileSystemEventArgs e)
        { 
            if(e.ChangeType == WatcherChangeTypes.Created)
            {
                //don't process temporary files
                if (Path.GetFileName(e.FullPath).Substring(0, 1) == "~" || Path.GetFileName(e.FullPath).Substring(0, 1) == "$")
                    return;


                var result = convert(e.FullPath, GetDocStatus(e.Name)).Result;
                FileService.MoveNativeToDraft(e.FullPath);
            }
        }

        private async Task<bool> convert(string fileName, string docStatus)
        {
            try
            {
                ConvertWordToPDF convertor = new ConvertWordToPDF();
                var task = Task.Run(()=>convertor.Convert(fileName, docStatus));
                await task;


                return true;
            }
            catch (Exception)
            {
                return false;
            }
        }
    }
}

提前致谢

更新: 我正在调用这样的代码......

public static void MoveIntoRepository(string sourceFile)
{
    string destinationDir = @"C:\Repository\DropLocation\";
    var result = MoveFileAsync(sourceFile, Path.Combine(destinationDir, Path.GetFileName(sourceFile))).Result;
}

我也试过像这样绕过文件锁......

bool isFileLocked = isLocked(filename);
int numTries = 0;
while(isFileLocked)
{
    numTries++;
    if (numTries > 100)
        throw new Exception("FileLock Error");

    ///the following is actually in a called method
    byte[] byteArray = File.ReadAllBytes(filename);
    ///... rest of code here

    Thread.Sleep(500);
    isFileLocked = isLocked(filename);
}

调用此方法

private static bool isLocked(string filename)
{
    try 
    {           
        FileStream st = new FileStream();
        st = File.Open(filename,FileMode.Open);
        st.Close();
        return false;
    }
    catch (Exception)
    {
        return true;
        throw;
    }
}

1 个答案:

答案 0 :(得分:0)

请参阅下面的代码:

using(FileStream sourceStream = File.Open(sourceFileName, FileMode.Open))
{
    using(FileStream destinationStream = File.Create(destinationFileName))
    {
        try
        {
            await sourceStream.CopyToAsync(destinationStream);
            // The sourceFileName file is locked since you are inside the 
            // the using statement. Move statement for deleting file to
            // outside the using.
            File.Delete(sourceFileName);
            return true;
        }
        catch
        {
            return false;
        }
    }
}
// Move it here