Timeout
1. 概要
Timeout は、ソースシーケンスから前回の値(または購読開始)以降、指定した時間内に新しい値が届かなかった場合に TimeoutException でシーケンスを完了させるオペレーターです。
ネットワークリクエストの応答監視やセンサーデータの死活監視など、一定時間内にデータが届くことを保証したい場合に使用します。
2. シグネチャ
TimeSpan によるタイムアウト
csharp
public static Observable<T> Timeout<T>(
this Observable<T> source,
TimeSpan dueTime)前回の値(または購読開始)から dueTime 以内に次の値が届かなかった場合、TimeoutException で完了します。
csharp
source.Timeout(TimeSpan.FromSeconds(5))TimeSpan + TimeProvider によるタイムアウト
csharp
public static Observable<T> Timeout<T>(
this Observable<T> source,
TimeSpan dueTime,
TimeProvider timeProvider)TimeProvider を指定してタイマーの実装を差し替えられます。テスト時に FakeTimeProvider を使用して時間を手動制御できます。
csharp
source.Timeout(TimeSpan.FromSeconds(5), fakeTimeProvider)overload の使い分け
| overload | 使う場面 |
|---|---|
TimeSpan | 通常のタイムアウト監視 |
TimeSpan, TimeProvider | ユニットテストで時間を制御したい場合 |
3. マーブルダイアグラム
各値が発行されるたびにタイマーがリセットされます。指定時間内に次の値が届けばタイマーがリセットされ、シーケンスは続行されます。指定時間内に値が届かなかった場合、TimeoutException でシーケンスが完了します。
4. サンプルコード
csharp
using R3;
// API レスポンスを 10 秒でタイムアウト
apiResponseObservable
.Timeout(TimeSpan.FromSeconds(10))
.Subscribe(
response => HandleResponse(response),
error =>
{
if (error is TimeoutException)
{
Console.WriteLine("タイムアウトしました");
}
});
// センサーデータの死活監視
sensorDataObservable
.Timeout(TimeSpan.FromSeconds(30))
.Subscribe(
data => ProcessData(data),
error => AlertSensorFailure());
// FakeTimeProvider を使ったテスト
var fakeTime = new FakeTimeProvider();
Exception? caughtError = null;
var subject = new Subject<int>();
subject
.Timeout(TimeSpan.FromSeconds(5), fakeTime)
.Subscribe(
x => { },
error => caughtError = error);
subject.OnNext(1);
fakeTime.Advance(TimeSpan.FromSeconds(3));
subject.OnNext(2); // タイマーリセット
fakeTime.Advance(TimeSpan.FromSeconds(5));
// caughtError は TimeoutException