# イベント時間とウィンドウ処理 ## 定義 ストリームプロセッサが「直近5分間の平均」のような時間窓での集計を行う際、どの時刻を基準にするかが本質的に曖昧な問題になる。*イベント時間(event time)*はイベントが実際に発生した時刻(イベント自体に埋め込まれたタイムスタンプ)であり、*処理時間(processing time)*はストリームプロセッサがそのイベントを処理する時刻(処理マシンのローカルシステムクロック)である。多くのストリーム処理フレームワークは単純さゆえに処理時間でウィンドウを決定するが、これはイベント発生から処理までの遅延が無視できるほど短い場合にのみ妥当であり、処理遅延(キューイング・ネットワーク障害・ブローカやプロセッサでの輻輳・コンシューマの再起動・障害復旧時の再処理)が生じると破綻する。バッチ処理はイベントに埋め込まれたタイムスタンプを見るため決定的(同じ入力に対し再実行しても同じ結果)だが、処理時間ベースのウィンドウはストリーム処理の実行タイミングに依存するため非決定的になる。(Source: [[@2026__OReilly__Designing Data-Intensive Applications 2E - Chapter 12 Stream Processing]] "Reasoning About Time", "Event time versus processing time") 処理時間と混同すると誤ったメトリクスを生む典型例が、ストリームプロセッサの再起動時にバックログを一括処理することで見かけ上のリクエストスパイクが発生する現象である。実際のリクエストレートは一定でも、処理速度の変動がそのまま観測される「レート」に反映されてしまう。メッセージの到着順序もイベント時間の順序と一致しない場合がある——2台のWebサーバーが処理した2つのリクエストの発生順とメッセージブローカへの到着順が異なりうる例が典型で、書籍は『スター・ウォーズ』のエピソード公開順序(IV→V→VI→I→II→III→VII→VIII→IX)とナラティブ上のエピソード番号順の乖離をアナロジーとして挙げる。(Source: [[@2026__OReilly__Designing Data-Intensive Applications 2E - Chapter 12 Stream Processing]] "Event time versus processing time") ## ストラグラーイベントとクロックの信頼性 イベント時間でウィンドウを定義する場合、あるウィンドウの全イベントを受信し終えたかどうかを確実に知る方法はない。到着が遅れた*ストラグラー(straggler)*イベントへの対処は大きく2択に整理できる: (1) ストラグラーを無視し、破棄割合をメトリクスとして監視・アラートする、(2) *訂正(correction)*——ストラグラーを含めた更新値を発行し、必要なら以前の出力を撤回する——を行う。「これ以降 t より前のタイムスタンプのメッセージは来ない」という特別なメッセージ(watermark)でウィンドウ確定をトリガーする手法もあるが、複数プロデューサが異なる最小タイムスタンプ閾値を持つ場合、コンシューマは各プロデューサを個別に追跡する必要があり、プロデューサの追加・削除がより難しくなる。(Source: [[@2026__OReilly__Designing Data-Intensive Applications 2E - Chapter 12 Stream Processing]] "Handling straggler events") モバイルアプリのようにイベントが端末上でバッファされ、接続復旧時にまとめて送信される場合、イベント時間はユーザー操作が実際に起きた時刻(端末のローカルクロック)であるべきだが、ユーザーが制御する端末のクロックは信頼できないことがある。一方サーバー受信時刻(サーバーのクロック)はより信頼できるが、ユーザー操作の実際の発生時刻としての意味は薄れる。対処法として、(1) 端末クロックでのイベント発生時刻、(2) 端末クロックでのサーバー送信時刻、(3) サーバークロックでの受信時刻、の3つのタイムスタンプを記録し、(3)から(2)を引いてクロックオフセットを推定し、そのオフセットを(1)へ適用して真のイベント発生時刻を推定する手法がある。(Source: [[@2026__OReilly__Designing Data-Intensive Applications 2E - Chapter 12 Stream Processing]] "Whose clock are you using, anyway?") ## ウィンドウの種類 - **タンブリングウィンドウ(tumbling window)**: 固定長で重複がなく、各イベントはちょうど1つのウィンドウに属する。タイムスタンプを最も近い境界へ切り捨てることで実装できる。 - **ホッピングウィンドウ(hopping window)**: 固定長だが連続するウィンドウが重複し平滑化を提供する(例: 5分ウィンドウを1分ごとにずらす)。タンブリングウィンドウを先に計算し複数個を集約することで実装できる。 - **スライディングウィンドウ(sliding window)**: 互いに一定の時間間隔内にある全イベントを含む。固定境界を持たない点でタンブリング/ホッピングと異なり、時刻でソートしたイベントのバッファから期限切れのものを除去することで実装できる。 - **セッションウィンドウ(session window)**: 固定長を持たず、同一ユーザーの近接したイベントをグルーピングし、一定時間の非活動(例: 30分間イベントなし)でウィンドウを終了する。ウェブサイト分析のセッション化(sessionization)で一般的。 ウィンドウ操作は一時的な状態を保持する。カウントのように固定サイズの状態で済むものもあれば、スライディングウィンドウやストリームジョインのようにウィンドウ終了までイベントをバッファし続ける必要があるものもある。大きなウィンドウや高スループットのストリームは大量の一時状態を要求しうるため、処理ノードの容量計画が必要になる。(Source: [[@2026__OReilly__Designing Data-Intensive Applications 2E - Chapter 12 Stream Processing]] "Types of windows") ## 横断的知見 - (この節は今後、複数ソースの突き合わせで得られた知見を蓄積する。現時点では単一ソースからの知見のみ。) ## 未解決の問い - watermark による欠損通知(「t より前のイベントはもう来ない」)は、複数プロデューサが個別にタイムスタンプ閾値を持つ環境でどこまでスケールするか。プロデューサの動的な増減にどう対応すべきか。 - クロックオフセット推定(端末送信時刻とサーバー受信時刻の差分)は、ネットワーク遅延がタイムスタンプ精度要求と比べて無視できない場合にどれほど誤差を生むか。 - セッションウィンドウの非活動タイムアウトは、ドメインによって最適値が大きく異なりうる(例: EC サイトの30分と IoT センサーの数秒)。適切な値をデータから自動決定する手法はあるか。 ## 関連 - ソース: [[@2026__OReilly__Designing Data-Intensive Applications 2E - Chapter 12 Stream Processing]]("Reasoning About Time") - 概念: [[レイテンシ分析]] ## 出典 - [[@2026__OReilly__Designing Data-Intensive Applications 2E - Chapter 12 Stream Processing]]("Reasoning About Time" 節)