2012-02-13 26 views
2

新しいファイルをチェックし、その内容をデータベースに保存してファイルを削除するようにFileSystemWatcherを設定しました。約10日前に、いくつかのファイルを無視し始めました。私たちは合計で50,000ファイルから約1,500ファイルを話しています。手動で別のディレクトリにファイルを移動し、監視されたディレクトリにそれらを再度移動することによって、ファイルが通知されます。FileSystemWatcherが動作しない場合があります

InternalBufferSizeは、大きなバッチを処理するために32 kBに設定されています。それは問題なく一度に300以上のファイルを処理し、現実はそれにも近くない。

プログラムは、FileSystemWatcherとは無関係の変更のために、40日以上前に最後に触れられました。今は1年以上も生産されています。サーバーの負荷にスパイクは見られません。

突然このような問題が発生する原因は何ですか? FileSystemWatcherが単にunreliableである可能性はありますか?

1000個のファイルが作成されたテストを作成しました。それを実行した後、イベントログに3000件のエントリが見つかります。だから私はバッファオーバーフローが問題外であると思う?複数の方法でプログラムをテストし、何度も何度もコードをチェック

private void button1_Click(object sender, EventArgs e) 
    { 
     fsw = new FileSystemWatcher(); 
     fsw.Path = @"C:\temp\fsw-test"; 
     fsw.IncludeSubdirectories = false; 
     fsw.NotifyFilter = NotifyFilters.FileName; 
     fsw.Created += new FileSystemEventHandler(fsw_Created_handler); 
     fsw.EnableRaisingEvents = true; 
     fsw.InternalBufferSize = 32768; 
     fsw.Error += fsw_Error_handler; 
    } 

    private void fsw_Created_handler(object sender, FileSystemEventArgs e) 
    { 
     new Thread(new ParameterizedThreadStart(work)).Start(e); 
    } 

    private void fsw_Error_handler(object sender, ErrorEventArgs e) 
    { 
     EventLog.WriteEntry("few test", e.GetException().Message); 
    } 

    private void work(object e) 
    { 
     try 
     { 
      EventLog.WriteEntry("fsw test", "Queueing File Started"); 
      Thread.Sleep(10000); 
      EventLog.WriteEntry("fsw test", ((FileSystemEventArgs)e).Name); 
      EventLog.WriteEntry("fsw test", "Queueing File Done"); 
     } 
     catch (Exception ex) 
     { 
      EventLog.WriteEntry("fsw test", "Error = " + ex.StackTrace + " *** " + ex.ToString()); 
     } 
    } 

    private void button2_Click(object sender, EventArgs e) 
    { 
     for (int i = 1; i <= 1000; i++) 
     { 
      System.IO.File.Create(@"C:\temp\fsw-test\" + i); 
     } 
    } 

編集2 ストレスは全く問題がないことを明らかにしました。だから今は再現不可能なバグです、私はそれをより頻繁にログに記録し、状況を監視するためにいくつかの変更を行います。

+0

私が与えることができる唯一のアドバイスは、 'FileSystemWatcher'のオプションのいくつかはかなりわかりにくいということです。私が使ったとき、私は読書/執筆/編集を捕まえると思ったものを設定しましたが、それはすべてを捕まえていませんでした。おそらく、ファイルがどのように「作成」されているかについての新しい「事例」が出現し、FSWがそれらをキャッチするように設定されていないかもしれませんが、働く – Origin

+0

@Originすべてのファイルは全く同じ方法でシステムに入ります。 – Stijn

+0

ウォッチャーから 'Error'イベントを監視していますか? – adrianm

答えて

0

この問題は、マルチスレッドによって引き起こされたQueueの破損であることが判明しました。

2

ファイルイベントはキューに入れられません。ファイルを処理していて、新しいファイルが作成された場合、そのイベントは欠落します。

この問題を回避する方法の1つは、新しいファイルイベントが発生したときにファイルを処理し、戻す前に新しいファイルを確認することです。ファイルが残らなくなるまで繰り返します。

+0

これが当てはまる場合、回避策が不可能な固有のレースがあります(小さすぎても)。イベントハンドラが新しいファイルがないと判断した後は、ファイルシステムの変更が発生する可能性があります。制御がイベントを開始するものに戻る前に。 –

+0

'Created'イベントのハンドラは、実際の処理を行うたびに新しいスレッドを開始します。質問に記載されているように、私はディレクトリに300以上のファイルを置くことができ、それらのすべてが処理されます。あるいは私はあなたが意味することを誤解していますか?回避策は確かに可能ですが、FileSystemWatcherを完全に削除し、ファイルのディレクトリを定期的にポーリングすることもできます。 – Stijn

+0

簡単に確認できます。イベントハンドラでは、10秒間のスリープ状態にします。そのコードがスリープしている間に、新しいファイルを作成し、別のイベントがあるかどうかを確認します。私は私たちのために働く一つの回避策を提案しました、私は確信しています。 –

関連する問題