UWP - 如果另一个应用程序打开文件,则无法打开文件进行读取

时间:2017-02-17 22:25:55

标签: c# uwp windows-store

2018编辑:如下所示和其他来源,定位创建者的更新或更高版本允许对另一个进程打开以供写入的文件进行只读文件访问。万岁!

在尝试为桌面开发Windows应用商店应用时,我似乎遇到了困难。我正在尝试打开另一个应用程序已打开的大型(100 + MB)日志文件,并在将最新事件写入文件时对其进行实时处理。

使用常规的非沙盒C#,这非常简单:

;WITH children AS
(
   SELECT 
     ParentNode,
    CAST(ISNULL(ParentNode + '/' ,'')  + node AS VARCHAR(4000)) AS PathValue
   FROM dashConfigurationSchema
   WHERE node =  'Value1'
 UNION ALL
   SELECT 
     t.ParentNode,
     list= CAST(ISNULL(t.ParentNode  + '/' ,'')  + d.PathValue AS VARCHAR(4000))
   FROM dashConfigurationSchema t
   INNER JOIN children  AS d
        ON t.Node = d.ParentNode
 )

SELECT PathValue from children c WHERE ParentNode IS NULL

不幸的是,在UWP中,每当我尝试打开另一个应用程序正在使用的文件时,我都会收到“UnauthorizedAccessException”。我已经尝试过我能找到的每种组合中的每一种API,但运气不好,所以我来这里寻求一些建议。

我尝试过的一些内容:

System.IO.FileStream stream = File.Open("LOGFILE PATH HERE", System.IO.FileMode.Open, FileAccess.Read, FileShare.ReadWrite);

快速重新评估:

打开PowerShell窗口,然后运行此命令以在主目录中保持打开“test.txt”:

Windows.Storage.Pickers.FileOpenPicker picker = new Windows.Storage.Pickers.FileOpenPicker();
picker.ViewMode = Windows.Storage.Pickers.PickerViewMode.List;
//Prompt the user to open the log file:
Windows.Storage.StorageFile logFile = await picker.PickSingleFileAsync();
picker.FileTypeFilter.Add(".txt");

//This won't work in any case, because it doesn't use the handle that the user picked,
// so the UWP sandboxing blocks it:
new FileStream(logFile.Path, FileMode.OpenOrCreate, FileAccess.Read);

//EDIT: These don't work if the file is open either, I must have made a mistake earlier
await FileIO.ReadBufferAsync(logFile);
await FileIO.ReadLinesAsync(logFile);

//These work if the file is not open by another app, but fail if another app has the file open
await logFile.OpenAsync( Windows.Storage.FileAccessMode.Read);
await logFile.OpenStreamForReadAsync();

1 个答案:

答案 0 :(得分:1)

我做了一个简单的测试,它应该工作。测试是这样的:    - 用记事本打开一个file.txt,该文件只包含一行文字,    - 使用下面的代码运行应用程序,    - 选择仍在记事本中打开的文件,    - 你应该在调试输出中看到第一行和第二行。

代码:

public async Task GetFile()
{
    Windows.Storage.Pickers.FileOpenPicker picker = new Windows.Storage.Pickers.FileOpenPicker();
    picker.ViewMode = Windows.Storage.Pickers.PickerViewMode.List;
    picker.FileTypeFilter.Add(".txt");
    //Prompt the user to open the log file:
    Windows.Storage.StorageFile logFile = await picker.PickSingleFileAsync();

    try
    {
        using (var stream = await logFile.OpenStreamForReadAsync())
        using (var reader = new StreamReader(stream))
        {
            var line = await reader.ReadLineAsync();
            Debug.WriteLine($"The first line: {line} - waiting");
            await Task.Delay(10000);
            line = await reader.ReadLineAsync();
            Debug.WriteLine($"The next line: {line} - waiting");
        }
    }
    catch (Exception exc)
    {
        Debug.WriteLine($"Exception {exc.Message}");
    }
}

在第二个测试中,我已经在记事本中修改了文件并将其保存,而上面的代码命中await Task.Delay(),然后在尝试读取第二行时,您可能会得到:'异常句柄与此oplock相关联的已关闭。 oplock现在坏了。'。

我看到你没有处理流,也许问题出在这里?您是否尝试将using用于 Idisposable