2013-03-22 105 views
3

我試圖保持與Windows 8音樂庫同步的數據庫,但我仍未找到有效的解決方案。我知道.NET有一個FileSystemWatcher,它不適用於Windows 8應用程序。目前,我的想法是將GetFilesAsync返回的文件列表與我的數據庫進行比較,並檢查是否修改,刪除或添加了某些內容。我知道這並不理想,但我在Windows.Storage找不到任何其他有用的東西。我的問題是,我想在音樂庫修改後自動進行這些更新。當子文件夾中發生更改時,檢查ModifiedDate文件夾是無用的。有沒有人知道是否有方法可以說明StorageFolder何時被修改?識別StorageFolder中的文件更改

回答

0

我不認爲你可以從你的Windows 8應用程序獲取這些信息。最好的辦法是異步查詢文件夾和文件,並將信息與存儲在數據庫中的信息進行比較。查看枚舉文件夾和文件here的一個示例。我知道這對你正在嘗試做的事情不是很有效。如果您發現其他更好的方法,請分享。

0

您可以使用StorageFileQueryResult及其ContentsChanged事件通知文件夾及其子文件夾上的更改。但是,該事件不包含任何實際更改的信息,因此您需要重新解析該文件夾並檢查是否有任何您感興趣的內容已被修改。

0

這個工作對我來說:

public async void ListenAsync() { 
     query = storageFolder.CreateFileQuery(); 
     query.ContentsChanged += query_ContentsChanged; 
     var files = await query.GetFilesAsync(); 
    } 

    void query_ContentsChanged(IStorageQueryResultBase sender, object args) { 
     // args has no info about what changed. check manually 
    } 
1

如果你能夠得到ContentsChanged可靠地火,然後在下面的代碼可以幫助你確定是什麼改變了。

注意,它並不快。 GetBasicPropertiesAsync似乎需要~5ms /文件...所以~10秒來區分一組1000個文件。

(我不能得到ContentsChanged可靠地火,而且,谷歌上搜索了幾個小時之後,它似乎很多人有同樣的問題)

private class DiffSet 
    { 
     public IReadOnlyList<StorageFile> Added { get; set; } 
     public IReadOnlyList<StorageFile> Deleted { get; set; } 
     public IReadOnlyList<StorageFile> Changed { get; set; } 
    } 

    private static async Task<DiffSet> Diff(IEnumerable<StorageFile> oldSet, IEnumerable<StorageFile> newSet) 
    { 
     var newAsDict = newSet.ToDictionary(sf => sf.Path); 

     var added = new List<StorageFile>(); 
     var deleted = new List<StorageFile>(); 
     var changed = new List<StorageFile>(); 

     var fromOldSet = new HashSet<string>(); 

     foreach (var oldFile in oldSet) 
     { 
      if (!newAsDict.ContainsKey(oldFile.Path)) 
      { 
       deleted.Add(oldFile); 
       continue; 
      } 

      var oldBasicProperties = await oldFile.GetBasicPropertiesAsync(); 
      var newBasicProperties = await newAsDict[oldFile.Path].GetBasicPropertiesAsync(); 

      var oldDateModified = oldBasicProperties.DateModified; 
      var newDateModified = newBasicProperties.DateModified; 

      if (oldDateModified != newDateModified) 
      { 
       changed.Add(oldFile); 
      } 

      fromOldSet.Add(oldFile.Path); 
     } 

     foreach (var newFile in newSet) 
     { 
      if (!fromOldSet.Contains(newFile.Path)) 
       added.Add(newFile); 
     } 

     return new DiffSet 
     { 
      Added = added, 
      Deleted = deleted, 
      Changed = changed 
     }; 
    } 
+0

特里斯坦,我知道這是舊的文章,但你有沒有圖瞭解如何使'ContentsChanged'可靠地啓動? – Laith 2015-08-30 08:36:24

+0

我希望。我最終編寫了一個支持SQLite的通讀緩存來保持文件系統的知識,包括一個低優先級的文件,它會檢查所有已知的文件。 – Tristan 2015-08-31 05:09:51