基本的なスレッド化/並列処理を含む最初の Windows サービス プロジェクトに取り組んでいます。これまでのところかなり苦労しましたが、ゆっくりとスレッド化を理解し始めています (それについては後で説明します...)。
疎結合の 2 つのワーカー スレッドを含む Windows サービスがあります。スレッド A は FTP サーバーからファイルをダウンロードし、それらを解凍/準備して、スレッド B が FileSystemWatcher を監視する別のディレクトリに保存します。スレッド B はファイルを解析し、データを使ってさまざまなことを行い、いくつかの http 呼び出しを行い、最後にファイルをアーカイブして作業ディレクトリから削除します。
私は仕事を始めたばかりで、現在直面している問題は、スレッド A とスレッド B の両方が戻るのを待つ方法です。私はこの質問を見ました: タイムアウトのある複数のスレッドで Thread.Joinを見て、アイデアがありました。
問題は、x 個のスレッドがそれぞれ ax 秒のタイムアウトで戻るのを待っている場合、十分な数のスレッドがあると、通常の操作でもサービスが応答していないように見える可能性があることです (SCM が 30 秒と文句を言う前にタイムアウトを読みましたよね?)。さらに、スレッドをループするときに参加するまでの残り時間を追跡することでこの問題を解決すると、ワーカーのコレクションの最初でスレッドを待機する時間が長くなればなるほど、残りのスレッドが戻るまでの時間が短くなります。十分な数のスレッドがあると、予想される時間内にすべてのスレッドが戻ってきても、サービスは応答していないように見えます。
この場合、おそらく 14 秒のタイムアウトで A と B の両方を thread.join するだけです。これは、2 つのワーカーしかなく、両方を返すのに 14 秒で十分なように思われるためです。
可変数のワーカー スレッド (たとえば > 8) がある場合、このようなことを行う価値はありますか? これは確実に機能しますか?
注: 次のものは使用しないでください。複数のレベルで使用するのは悪い考えです。回答を見る
protected override void OnStop()
{
// the service is stopping - set the event
Worker.ThreadStopEvent.Set();
// stop the threads
Parallel.ForEach(_workerThreads, t =>
{
t.Join(new TimeSpan(0, 0, 28));
});
}