Linux 世界中是否有與 .Net FileSystemWatcher 等價的東西?
我發現 .Net FileSystemWatcher 類對於編寫實用程序非常方便,這些實用程序會在文件出現在其監視的文件夾中時自動生效。*nix 世界中是否有任何與此功能等效的功能,可以讓我查看文件夾(可能還有它的所有子目錄)?
**編輯:**最好這將是不需要核心更新檔的東西。
那將是Gamin 文件更改監視器或Inotify。
編輯:Mono 確實有 Gamin 綁定——事實上,它的 FileSystemWatcher 實現使用了 Gamin。https://www.mono-project.com/docs/faq/technical/#what-are-the-issues-with-filesystemwatcher。
FileSystemWatcher 有什麼問題?
FileSystemWatcher 的 Mono 實現有許多後端,最優化的一個,依賴較少的一個是 inotify-backend(在 Mono 1.1.17 和更新版本中可用)。
有了這個後端,核心為 Mono 提供了對文件系統上文件的任何更改的更新,但它需要一個支持 inotify 的核心,只有較新的 Linux 發行版才會提供該核心。
在較舊的 Linux 系統中,您必須安裝 FAM 或 Gamin(兩者都可以使用)。您可能需要安裝 -devel 數據包。
對於 *BSD 系列,有一個基於 Kqueue 的實現,將在執行時檢測到時使用。
如果上述方法都不起作用,Mono 會退回到輪詢目錄以進行更改,這遠非最佳。
我想在 Ubuntu 10.10 的 Mono 中使用 FileSystemWatcher 分享我的觀察。這是 C# 中 FileSystemWatcher 的一個非常簡單的實現
using System; using System.Collections.Generic; using System.Collections; using System.Text; using System.IO; using System.Reflection; namespace FileSystemWatcherSandbox { public class Program { static void Main(string[] args) { foreach(DictionaryEntry de in Environment.GetEnvironmentVariables()) { Console.WriteLine("{0} = {1}",de.Key,de.Value); } string basePath = AppDomain.CurrentDomain.BaseDirectory; Console.WriteLine("watching: {0}", basePath); FileSystemWatcher fsw = new FileSystemWatcher(basePath); fsw.Changed += new FileSystemEventHandler(fsw_Changed); fsw.Created += new FileSystemEventHandler(fsw_Created); fsw.Deleted += new FileSystemEventHandler(fsw_Deleted); fsw.Error += new ErrorEventHandler(fsw_Error); fsw.Renamed += new RenamedEventHandler(fsw_Renamed); fsw.EnableRaisingEvents = true; fsw.IncludeSubdirectories = true; while (true) { WaitForChangedResult result = fsw.WaitForChanged(WatcherChangeTypes.All,10000); Console.WriteLine(result.TimedOut ? "Time out" : "hmmm"); } } static void fsw_Renamed(object sender, RenamedEventArgs e) { Console.WriteLine("({0}): {1} | {2}", MethodInfo.GetCurrentMethod().Name, e.ChangeType, e.FullPath); } static void fsw_Error(object sender, ErrorEventArgs e) { Console.WriteLine("({0}): {1}", MethodInfo.GetCurrentMethod().Name, e.GetException().Message); } static void fsw_Deleted(object sender, FileSystemEventArgs e) { Console.WriteLine("({0}): {1} | {2}", MethodInfo.GetCurrentMethod().Name, e.ChangeType, e.FullPath); } static void fsw_Created(object sender, FileSystemEventArgs e) { Console.WriteLine("({0}): {1} | {2}", MethodInfo.GetCurrentMethod().Name, e.ChangeType, e.FullPath); } static void fsw_Changed(object sender, FileSystemEventArgs e) { Console.WriteLine("({0}): {1} | {2}", MethodInfo.GetCurrentMethod().Name, e.ChangeType, e.FullPath); } } }此程式碼經過測試,可在 Windows XP 和 Ubuntu 10.10 上執行。但是,我想指出,在 Ubuntu 10.10(也可能是更早的版本)下,FileSystemWatcher 的行為是獨一無二的。
如果正在監視的目錄不包含子目錄,則呼叫 FileSystemWatcher 並將 IncludeSubdirectories 屬性設置為 true 將導致 FileSystemWatcher 忽略事件。但是,如果目標目錄中有子目錄,則將 IncludeSubdirectories 設置為 true 將按預期工作。
如果 IncludeSubdirectories 設置為 false,則始終有效。在這種情況下,FileSystemWatcher 將只監視目標目錄。
我希望這對希望跨不同作業系統使用 Mono 並呼叫 FileSystemWatcher 類型的程序員有用。