データマイグレーション失敗時のロールバック戦略と予防策
問題¶
データマイグレーションが8時間かけて実行された。しかし5万件のレコードが破損した。ロールバックが必要だが、最新バックアップは12時間前のものだ。データを失うことはできない。
回答すべき問い: 1. リカバリ戦略は何か? 2. 今後このような事態をどう防ぐか?
解答¶
リカバリ戦略¶
Step 1: 被害範囲を特定する - どの5万件が破損しているかを特定する(マイグレーション前後の状態を比較) - マイグレーションのログ・変更ログ(binlog / WAL)が残っているか確認する
Step 2: バックアップ + 差分ログで復元する
MySQLならbinlog、PostgreSQLならWAL(Write-Ahead Log)を使ってPoint-in-Time Recovery(PITR)を実施する。Step 3: 破損レコードを特定して選択的に復元する - 5万件全体をロールバックするのではなく、破損レコードのIDリストを特定し、古いDBから個別にリストア - 正常なレコードには影響を与えない
Step 4: 整合性チェック - 外部キー制約・インデックス整合性を確認 - アプリ側のバリデーションで正常性を再確認
予防策¶
1. Dry run(ステージング環境でテスト) - 本番と同等のデータ量でマイグレーションをリハーサルする - 実行時間・リソース消費・ロールバック手順を事前に確認
2. バックアップタイミングの見直し - 大規模マイグレーション直前に手動バックアップを取得する - 自動バックアップサイクルに依存しない
3. ダウンタイムなしのマイグレーション設計
このようなexpand/contract(ブルーグリーンマイグレーション)パターンを使えば、問題発生時にすぐ旧構造に戻せる。4. チェックポイント付き分割実行 - 5万件を一括処理せず、バッチ処理(例:1000件ずつ)で実行 - 各バッチ後に整合性チェックを入れ、問題があれば途中停止
5. フィーチャーフラグで段階的切り替え - 新スキーマを使う機能をフラグで制御し、一部ユーザーのみに先行適用
面接でのポイント¶
- PITRを知っているか: バックアップ + binlog/WALで任意時点に戻せることを説明できる
- ロールバック計画をマイグレーション前に立てるか: 「ロールバック手順を書いてからマイグレーションを実行する」文化を持っているか
- expand/contractパターンを知っているか: ゼロダウンタイムマイグレーションの定番パターン
- バッチ処理で分割するか: 一括実行はリスクが高い。失敗した場合のコストが大きい
- ステージング環境での検証: 本番前にリハーサルするか否か
「本番マイグレーション直前にバックアップを取る」「ロールバック手順を書いてから実行する」の2つだけでも多くの障害を防げる。