1

在 WinRT 应用程序中访问 mp3 文件时出现问题。

当应用程序尝试在与 FileOpenPicker 返回的文件相同的文件夹中按名称打开 mp3 文件时,会发生“System.UnauthorizedAccessException”。换句话说,用户在 Documents 中选择一个与 mp3 文件同名的信息文件。应用程序打开信息文件很好,但无法打开 mp3 文件。

例如:我有一对文件(file1.info)和(file1.mp3)。文件选择器允许选择 (*.info) 文件。

用户选择(file1.info)。然后应用程序同时打开 (file1.info) 和 (file1.mp3)。这两个文件都位于 DocumentsLibrary 文件夹中,但不在 MusicLibrary 中。问题是当我尝试打开(file1.mp3)时,我得到了“UnauthorizedAccessException”。

准备问题:

文件:将 mp3 文件复制到 Documents。创建一个与 mp3 文件具有相同基本名称的文本文件,并将其扩展名更改为 .info。

在 Package.appxmanifest > Declarations 添加一个“文件类型关联”声明。检查“打开是安全的”。添加

支持的文件类型“.mp3”和“.info”。将“内容类型”留空。

代码:

Dim file as StorageFile
Dim fileopenpicker As FileOpenPicker
Dim infofile As StorageFile
Dim mp3file As StorageFile 
Dim filename As String
fileopenpicker = New FileOpenPicker()
fileopenpicker.FileTypeFilter.Add(".info")
fileopenpicker.FileTypeFilter.Add(".mp3")
fileopenpicker.SuggestedStartLocation = PickerLocationId.DocumentsLibrary
file = Await fileopenpicker.PickSingleFileAsync()
If file.Path.EndsWith(".info") Then
    infofile = file
    filename = file.Path.Substring(0, file.Path.Length - 4) & "mp3"
    ' This command fails with 'System.UnauthorizedAccessException'
    mp3file = Await StorageFile.GetFileFromPathAsync(filename)
Else 'file is an mp3 file
    mp3file = file
    filename = file.Path.Substring(0, file.Path.Length - 3) & "info"
    ' This command succeeds!
    infofile = Await StorageFile.GetFileFromPathAsync(filename)
End If

因此,当 fileopenpicker 未实际选择文件时,打开 mp3 文件似乎存在一些特定问题。

4

1 回答 1

2

我使用具有文档库功能和声明的文件类型 .mp3 和 .info 的应用程序检查了这个问题。我发现这似乎是一个非常奇怪的错误。如果在打开 FileOpenPicker 后使用大写驱动器号将路径传递到文档库文件夹,则会收到 UnauthorizedAccessException。使用带有小写驱动器号的路径有效。奇怪的是,您可以在打开 FileOpenPicker 之前使用大写驱动器号。

所以解决方法是将路径小写。

这是我使用的代码(C#):

// Trying to get some files from the documents library
// Note: F:\Program Data is my primary documents library folder
string mp3FilePath = @"F:\Program Data\2Mann1Maus.mp3";

// This works even if the drive letter is uppercase
StorageFile file1 = await StorageFile.GetFileFromPathAsync(mp3FilePath);

// It also works with a lowercase drive letter
string infoFilePath = @"f:\Program Data\2Mann1Maus.info";
StorageFile file2 = await StorageFile.GetFileFromPathAsync(infoFilePath);

FileOpenPicker fileopenpicker = new FileOpenPicker();
fileopenpicker.FileTypeFilter.Add(".info");
fileopenpicker.FileTypeFilter.Add(".mp3");
fileopenpicker.SuggestedStartLocation = PickerLocationId.DocumentsLibrary;
StorageFile file = await fileopenpicker.PickSingleFileAsync();
if (file.Path.EndsWith(".info"))
{
   string filename = file.Path.Substring(0, file.Path.Length - 4) + "mp3";   

   // This works
   string testFileName1 = filename.Substring(0, 1).ToLower() + 
      filename.Substring(1,  filename.Length - 1);
   StorageFile mp3file1 = await StorageFile.GetFileFromPathAsync(testFileName1);

   // This works as well
   string testFileName2 = filename.ToLower();
   StorageFile mp3file2 = await StorageFile.GetFileFromPathAsync(testFileName2); 

   // This does cause an UnauthorizedAccessException
   StorageFile mp3file3 = await StorageFile.GetFileFromPathAsync(filename);
}
else
{
   StorageFile mp3file = file;
   String filename = file.Path.Substring(0, file.Path.Length - 3) + "info"; 

   // This works
   string testFileName1 = filename.Substring(0, 1).ToLower() + 
      filename.Substring(1, filename.Length - 1);
   StorageFile infoFile1 = await StorageFile.GetFileFromPathAsync(testFileName1); 

   // This works as well
   string testFileName2 = filename.ToLower();
   StorageFile infoFile2 = await StorageFile.GetFileFromPathAsync(testFileName2); 

   // This does cause an UnauthorizedAccessException
   StorageFile infoFile3 = await StorageFile.GetFileFromPathAsync(filename);
}
于 2012-10-22T08:05:35.180 回答