ホスティング プロセスがクラッシュしないように、タスクで使用できる C# 拡張メソッドを使用して、スローされた例外が最小限に抑えられるようにします。.NET4.5 では、動作がわずかに変更されたため、これは発生しませんが、監視されていない例外イベントは引き続きトリガーされます。ここでの私の課題は、拡張メソッドが機能することを証明するテストを作成することです。私は NUnit テスト フレームワークを使用しており、ReSharper がテスト ランナーです。
私が試してみました:
var wasUnobservedException = false;
TaskScheduler.UnobservedTaskException += (s, args) => wasUnobservedException = true;
var res = TaskEx.Run(() =>
{
throw new NaiveTimeoutException();
return new DateTime?();
});
GC.Collect();
GC.WaitForPendingFinalizers();
Assert.IsTrue(wasUnobservedException);
でのテストは常に失敗しますAssert.IsTrue
。このテストを LINQPad などで手動で実行すると、期待どおりの動作がwasUnobservedException
返されtrue
ます。
TaskScheduler.UnobservedTaskException
テストフレームワークが例外をキャッチし、それがトリガーされないように監視していると推測しています。
次のようにコードを変更してみました。
var wasUnobservedException = false;
TaskScheduler.UnobservedTaskException += (s, args) => wasUnobservedException = true;
var res = TaskEx.Run(async () =>
{
await TaskEx.Delay(5000).WithTimeout(1000).Wait();
return new DateTime?();
});
GC.Collect();
GC.WaitForPendingFinalizers();
Assert.IsTrue(wasUnobservedException);
このコードで試みたのは、例外がスローされる前にタスクが GC されるようにすることでした。これにより、ファイナライザーはキャッチされず、監視されていない例外を確認できます。ただし、これにより、上記と同じ失敗が発生しました。
実際、テスト フレームワークによって何らかの例外ハンドラが接続されているのでしょうか。もしそうなら、それを回避する方法はありますか?それとも、私は何かを完全に台無しにしていて、これを行うためのより良い/簡単/クリーンな方法がありますか?