GNU/Linux >> Znalost Linux >  >> Linux

Existuje ve světě Linuxu ekvivalent k .Net FileSystemWatcher?

Jak již bylo řečeno, Mono má třídu "System.IO.FileSystemWatcher", toto je příslušný odkaz:http://www.go-mono.com/docs/monodoc.ashx?link=T%3aSystem.IO. FileSystemWatcher

"Implementace aplikace TheFileSystemWatcher společnosti Mono má několik backendů. To je nezbytné, protože ne všechny operační systémy podporované společností Mono mají všechny funkce nezbytné k poskytování funkcí očekávaných aplikacemi."

Pokud jádro operačního systému podporuje sledování adresářů (inotifyon Linux, KEvents na BSD nebo OSX), tato funkce se použije; V opačném případě se vrátí k používání Gamin nebo FAMlibraries (tyto knihovny poskytují rozhraní API pro sledování adresářů) a pokud žádná z těchto funkcí není k dispozici, Mono bude dotazovat každých 750 milisekund sledovaných adresářů.

Chování dotazování můžete vynutit (místo použití podpory jádra) nastavením proměnné prostředí MONO_MANAGED_WATCHER před spuštěním vaší aplikace. To může být užitečné pro souborové systémy, které nepodporují inotify a přesto vyžadují dotazování k detekci změn."


To by byl Gamin the File Alteration Monitor nebo Inotify.

Edit:Mono má vazby Gamin - ve skutečnosti jeho implementace FileSystemWatcher používá Gamin. https://www.mono-project.com/docs/faq/technical/#what-are-the-issues-with-filesystemwatcher.

Jaké jsou problémy s FileSystemWatcher?

Mono implementace FileSystemWatcher má řadu backendů, nejoptimálnější, ten s méně závislostmi, je inotify-backend (dostupný v Mono 1.1.17 a novějších verzích).

S tímto backendem jádro poskytuje Mono aktualizace o jakýchkoli změnách souborů v souborovém systému, ale vyžaduje jádro s povolenou inotify, které dodávají pouze novější distribuce Linuxu.

Ve starších systémech Linux musíte mít nainstalovaný FAM nebo Gamin (bude fungovat s oběma). Možná budete muset nainstalovat pakety -devel.

Pro rodinu *BSD existuje implementace založená na Kqueue, která bude použita při detekci za běhu.

Pokud nic z výše uvedeného nefunguje, Mono se vrátí k dotazování na změny v adresářích, což zdaleka není optimální.


Rád bych se podělil o svá pozorování pomocí FileSystemWatcher v Mono v Ubuntu 10.10. Zde je velmi jednoduchá implementace FileSystemWatcher v C#

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);
        }
    }
}

Tento kód byl testován a funguje na Windows XP i Ubuntu 10.10. Rád bych však upozornil, že pod Ubuntu 10.10 (možná i dřívější verze) se FileSystemWatcher chová jedinečně.
Pokud sledovaný adresář neobsahuje podadresáře, vyvolání FileSystemWatcher s vlastností IncludeSubdirectories nastavenou na true povede k tomu, že FileSystemWatcher bude události ignorovat. Pokud však v cílovém adresáři existují podadresáře, bude IncludeSubdirectories nastavená na hodnotu true fungovat podle očekávání.
Vždy bude fungovat, pokud je IncludeSubdirectories nastavena na hodnotu false. V tomto případě bude FileSystemWatcher sledovat pouze cílový adresář.
Doufám, že to bude užitečné pro programátory, kteří chtějí používat Mono v různých operačních systémech a vyvolat typ FileSystemWatcher.


Linux
  1. Začínáme s linuxovým příkazem cat

  2. Co je linuxový ekvivalent pozastavení DOSu?

  3. Linux ekvivalent příkazu otevřít Mac OS X

  1. Existuje způsob, jak zkontrolovat aktuální rpath v Linuxu?

  2. Jaký by byl ekvivalent Win32 API v linuxu?

  3. Existuje Windows ekvivalent příkazu Unix strings?

  1. Fedora – Existuje ve světě Fedory ekvivalent služby Ppa?

  2. Existuje STDCALL v Linuxu?

  3. Jaký je linuxový ekvivalent Windows Startup?