Andrew Tanによる
ポストモーテムのパラドックス
今やすべての主要なテック企業がそれを公開しています。Stripeにはそれらが満載のステータスページがあります。Netflixは詳細なエンジニアリング分析を書いています。Uber、LinkedIn、GitHub、Cloudflare — 彼らは皆、何が間違っていたのか、そしてなぜそうなったのかを公開しています。
ここにパラドックスがあります:同じ失敗が繰り返されているのです。同じ会社ではなく、同じシステムでもありませんが、同じパターンです。DoorDashのチームが支払いデータを失ったのは、3年前にNetflixのチームが視聴メトリクスを失ったのと同じ方法です。2024年にUberのパイプラインがスキーマドリフトで壊れたのは、2021年にLinkedInのパイプラインが壊れたのと同じ方法です。
私は過去数週間、合計で数兆のイベントを処理した企業からの50の公開ポストモーテムとインシデントレポートを読みました。目的はすべての可能な失敗モードをカタログ化することではありませんでした。頻繁に現れる根本原因を見つけることでした。それらは一度限りの不運として片付けることができないほど頻繁に現れます。
4つのパターンが支配しています。そして驚いたことに、そのほとんどは運用段階ではなく設計段階で防ぐことができるのです。
50の選定方法
パターンに入る前に、方法論について簡単に説明します。私は大規模なデータインフラストラクチャを運営する企業からの公開ポストモーテムに焦点を当てました:Uber、Netflix、Stripe、LinkedIn、GitHub、Cloudflare、DoorDash、Airbnb、Spotify、AWS。セキュリティ侵害や純粋なインフラストラクチャの停止(DNS障害のようなもの)は、データパイプラインに直接影響を与えない限りスキップしました。
選定はランダムではありませんでした。以下を含むポストモーテムを優先しました:
- 技術的深度を持つ根本原因分析
- 失敗と回復のタイムライン
- データ品質またはパイプラインへの影響の明示的な言及
- 学んだ教訓やプロセスの変更
頻繁に公開する企業(Cloudflare、GitHub)もあれば、稀にしか公開しない企業(Netflix)もあります。50はバッチETL、ストリーミング、ハイブリッドアーキテクチャの断面を表しています。
パターン1: スキーマドリフト(インシデントの38%)
最も一般的な根本原因は、見た目には単純なものでした:上流システムがデータフォーマットを変更し、パイプラインがそれを知らなかったのです。
あるよく文書化されたインシデントでは、データチームが下流のデータウェアハウスが11日間にわたって破損したレコードをロードしていたことを発見しました。ソースAPIが新しいフィールドを追加しました。パイプラインのJSONパーサーはそれを予期しないキーとして扱い、レコードバッチ全体を静かに削除しました。パイプラインがクラッシュしなかったため、アラートは発生しませんでした — 期待される行数より少ない行を生成しただけで、その差は正常な変動範囲内でしたが、そうではなくなるまで。
これはエッジケースではありません。多くのデータインテグレーションツールのデフォルトの動作です。
ポストモーテムはこのパターンの3つのバリエーションを明らかにしています:
追加ドリフト
新しいフィールド、列、またはイベントタイプが現れます。パイプラインはそれを無視するか、スキーマ検証の厳しさに応じて失敗します。ほとんどのポストモーテムは、過去に厳格な検証が誤警報を引き起こしたため、パイプラインが「許容」されるように設定されていたと指摘しています。
タイプドリフト
既存のフィールドがそのタイプを変更します。文字列が数値になります。タイムスタンプがタイムゾーンを失います。これらはデータがまだ有効に見えるため、最も捉えにくいものです。あるポストモーテムは、通貨コードフィールドがISO形式から数値の列挙型に変更され、パイプラインが列挙値を乗数として解釈したため、収益メトリクスが静かに倍増したと説明しています。
セマンティックドリフト
フォーマットは同じままですが、意味が変わります。「user_id」フィールドがアカウントIDの代わりにデバイスIDを含むようになります。「status」フィールドが新しい状態を持ち、下流のロジックがそれをエラーとして扱います。データはすべての検証チェックを通過し、依然として間違っています。
驚くべきことに、これらのインシデントがスキーマレジストリやデータ契約によって捉えられることはほとんどありませんでした。ほとんどの場合、チームはレジストリを持っていました。それはパイプラインの境界で強制されていなかっただけです。スキーマはどこかに文書化されていましたが、パイプラインがそれに対して検証することは要求されていませんでした。
パターン2: バックプレッシャーと負荷スパイク(インシデントの24%)
2番目のクラスターは、通常の負荷では完璧に動作し、予期しないボリュームで崩壊するパイプラインに関するものです。トリガーは様々です — マーケティングキャンペーン、バイラルイベント、四半期ごとの報告サイクル、突然10倍のレートを発する誤設定された上流ジョブ。
失敗モードはほとんど常に同じです:パイプラインは負荷を捨てることができないので、それを落とします。
あるストリーミングプラットフォームのポストモーテムでは、製品発売中に6時間遅れたKafkaコンシューマーについて説明しています。コンシューマーグループは自動スケーリングしましたが、新しいインスタンスはそのスケールでテストされたことのないデータベース接続プールの制限に達しました。パイプラインはクラッシュしませんでした。新しいイベントの処理を停止し、古いものが保持期限を過ぎるまで。チームが気づいたときには、データは消えていました。
別のポストモーテムでは、2年間問題なく動作していたバッチETLジョブがブラックフライデーに、通常より40倍大きなファイルを発するソースシステムによって失敗したことを説明しています。ジョブは18時間実行され、一時ストレージを使い果たし、部分的な出力をクリーンアップせずに失敗しました。次のスケジュールされた実行は破損したデータの上で開始されました。
共通のスレッド:これらのパイプラインは定常状態の運用のために設計されており、境界条件のためではありませんでした。彼らは実行しているかどうかの監視を持っていましたが、どれだけ限界に近いかの監視はありませんでした。
いくつかのポストモーテムは、負荷テストが「自動スケーリングするから」と優先順位を下げられていたことを指摘しています。自動スケーリングはコンピュートには有効です。しかし、接続プール、メモリ制限、ディスクI/O、または下流APIのレート制限には効きません — 実際にパイプラインを壊すボトルネックです。
パターン3: サイレントデータロス(インシデントの19%)
これはエンジニアを夜も眠れなくするパターンです。パイプラインは成功を報告します。ダッシュボードは緑を示します。SLAは満たされています。しかし、データは不完全で、重複しているか、破損しています — そして誰もビジネスユーザーがなぜ数字が間違っているのか尋ねるまで知りません。
サイレントロスはポストモーテムでいくつかの形で現れます:
あまりにも攻撃的なフィルター
データ品質ルールが不正なパターンに一致するレコードを削除しました。ルールは破損した上流データをキャッチすることを意図していましたが、異常だが有効な値を持つ正当なレコードもキャッチしました。3週間にわたり、正当なトランザクションの12%がフィルタリングされました。
実際には一度だけではなかった
あるパイプラインは厳密に一度だけのセマンティクスを主張しましたが、非冪等なシンクを使用していました。一時的なネットワークエラーが再試行をトリガーしたとき、一部のレコードが二重に書き込まれました。重複排除ロジックは理論上存在しましたが、実際のコードパスには存在しませんでした。
保持のギャップ
ストリーミングパイプラインは24時間の保持ウィンドウを持つメッセージキューに書き込みました。下流の処理が別のインシデントのために遅れたとき、未処理のデータは回復前に期限切れになりました。パイプラインログは成功した書き込みを示しました。データは誰かが読み取ろうとしたときにはそこにありませんでした。
サイレントロスが危険なのは、従来の監視には見えないことです。パイプラインの健康メトリクス — 実行時間、スループット、エラーレート — はそれを捉えません。データ品質メトリクスが必要です:行数、基数チェック、参照整合性、分布テスト。ほとんどのポストモーテムは、これらのチェックがインシデント後に追加されたことを認めています。
パターン4: 共有状態からのカスケード障害(インシデントの14%)
最小のクラスターですが、しばしば最も壊滅的です。これらは、共有インフラストラクチャを通じて他のパイプラインを破損または無効にする1つのパイプラインの障害に関するインシデントです。
ある記憶に残るポストモーテムは、「毒薬の丸薬」イベント — 無限ループに入るパーサーを引き起こした単一の不正なレコード — を説明しています。コンシューマースレッドがハングし、パーティションがリバランスされ、新しいコンシューマースレッドもハングしました。数分以内に、コンシューマーグループ全体がオフラインになりました。パイプラインが他のサービスとKafkaクラスターを共有していたため、ブローカーのログ圧縮に影響し、無関係なパイプラインがレイテンシーの増加を見始めました。
別のポストモーテムは、複数のバッチジョブで使用されるメタデータストアを説明しています。あるジョブのスキーマ移行がメタデータテーブルを90秒間ロックしました。同じテーブルに触れる他のすべてのジョブが失敗またはタイムアウトしました。単一のチームの問題であるべきものが、会社全体のインシデントになりました。
これらのポストモーテムからの教訓は「失敗を隔離する」だけではありません。それは共有状態がしばしば見えないということです。チームはそれが失敗するまでインフラストラクチャを共有していることに気づきません。Kafkaクラスター、メタデータテーブル、共有NFSマウント — これらはパイプラインの設計の一部とは見なされていませんが、失敗ドメインの一部です。

残りの5%はどのようなものだったか
残りのポストモーテムは本当に一度限りのものでした:ビットを反転させる宇宙線、通知なしで動作を変更するベンダーAPI、休日の週末に期限切れになる証明書。これらは設計で回避できない失敗です。上記の95%は、回避可能です。
設計チェックリスト
これらの50のポストモーテムを読んだ後、私は同じギャップを何度も見ました。失敗はチームが才能、ツール、または認識を欠いていたために起こったのではありません。特定の設計上の質問が十分に早く問われなかったために起こったのです。
ここに、設計レビュー中に正直に答えれば、私が分析したインシデントの大部分を防ぐことができたであろう6つの質問があります:
1. スキーマが警告なしに変更された場合、何が起こりますか?
「スキーマレジストリを持っていますか?」ではありません — それはツールの質問です。設計の質問は:スキーマが期待から逸脱したとき、パイプラインは失敗しますか、それとも静かに適応しますか?適応的な動作は安全に感じますが、それが間違ったデータを生成するまでです。失敗をデフォルトにします。スキーマの不一致を大声で知らせます。
2. このパイプラインがテストされた最大負荷は何であり、それを超えたときに最初に何が壊れますか?
ほとんどのチームは正確性のためにテストします。限界のためにテストするチームははるかに少ないです。最初のボトルネック — メモリ、接続、ディスク、下流のレート制限 — を知り、それに達したときの優雅な劣化計画を持ってください。
3. データの10%を静かに失っているかどうかをどうやって知ることができますか?
これは最も重要な質問です。「ジョブが終了した」という唯一の検証があるなら、あなたは盲目で飛んでいます。出力ボリューム、分布、および主要メトリクスを過去のベースラインと比較する独立したデータ品質チェックが必要です。
4. 再試行は安全ですか?
再試行ロジックは、シンクが厳密に冪等でない限り、潜在的な重複メカニズムです。すべてのAPI呼び出し、すべてのデータベース書き込み、すべてのファイル追加を確認してください。冪等性を保証できない場合は、最大1回を保証し、保証された重複よりも時折の損失を受け入れます。
5. このシステムが失敗した場合、他のどのシステムが失敗しますか?
失敗ドメインをマップします。あなたのパイプラインがハングした場合、共有キューをブロックしますか?接続プールを使い果たしますか?他のジョブが必要とするディスクを埋めますか?復旧だけでなく、爆発半径の抑制を設計します。
6. このパイプラインを見たことがない人が午前3時にデバッグできますか?
最も早く回復したポストモーテムはすべて共通点がありました:組織的知識を必要としない可観測性。状態変化だけでなく、決定を説明するログ。システムの健康だけでなく、データの健康を示すメトリクス。症状だけでなく、根本原因を指摘するアラート。
不快な真実
50のポストモーテムを読むことは、失敗に対する免疫を与えるものではありません。しかし、それはパターンを明らかにします。そしてパターンは、ほとんどの場合、退屈です。スキーマドリフト。負荷制限。欠落した検証。共有状態。これらはエキゾチックな分散システムの問題ではありません。それらは設計の衛生です。
これらのポストモーテムを公開したチームは、データインフラストラクチャを構築する上で世界最高のチームの一つです。彼らがこれらのパターンにまだ直面しているのであれば、他のすべての人もそうです。違いは、それを設計レビューで捉えるか、午前3時に捉えるかです。
データパイプラインを設計していて、スキーマ契約を強制し、バックプレッシャーを優雅に処理し、問題が発生したときに視覚的なデバッグを提供するプラットフォームを探しているなら — それがバッチであれストリーミングであれ — layline.ioをご覧ください。Community Editionは無料で試すことができます。
Andrew Tanはシリアルアントレプレナーであり、layline.ioの創設者であり、バッチとリアルタイムの両方のワークロードをスケールで処理するエンタープライズデータ処理インフラストラクチャを構築しています。



