データベース●●●●○

結果整合性

更新が即座に全体へ反映されなくても、いずれ全レプリカが同じ値に収束するという整合性モデル。

概要

結果整合性(eventual consistency)は、「更新した瞬間に全員が最新の値を見られるわけではないが、更新が止まればいずれ全員が同じ値に落ち着く」という整合性のモデルです。データを複数のノードに複製(レプリケーション)して運用するとき、書き込みを全レプリカに反映し終えるまで応答を待つのではなく、まず一部に書いて即座に応答を返し、残りのレプリカへは裏側で少し遅れて伝播させます。この「遅れ」を許容する代わりに、応答の速さと、一部のノードが落ちても書き込みを受け付け続けられる可用性を手に入れます。

対になる概念が「強整合性(strong consistency)」で、こちらは「書き込み直後に読めば、必ず最新の値が返る」ことを保証します。分かりやすい代わりに、全レプリカの同期を待つぶん遅く、ネットワークが分断されると書き込みを止めざるを得ません。結果整合性は、SNSのタイムライン、ショッピングカート、いいね数のカウンタなど、「数百ミリ秒〜数秒の食い違いは実害が小さいが、遅延や停止は困る」という場面で選ばれます。「フォローした相手の投稿が反映されるのに一瞬タイムラグがある」といった体験の裏には、たいていこのモデルがあります。

なぜ生まれたか

1台のデータベースにすべてを載せていた時代、整合性は悩む対象ですらありませんでした。真実は1か所にしかないので、書いた値をそのまま読めば必ず最新です。ところがアクセスが世界規模になり、データを地理的に離れた複数拠点へ複製して置くようになると、事情が一変します。東京とロンドンのレプリカを常に完全同期させようとすれば、書き込みのたびに地球の裏側との往復を待つことになり、応答は目に見えて遅くなります。しかも両拠点をつなぐ回線が切れた瞬間、同期を待つ設計では書き込みそのものが止まってしまいます。

この限界を理論として突きつけたのがCAP定理です。ネットワーク分断(P)が起きたとき、強整合性(C)と可用性(A)は同時には満たせません。分断中も書き込みを受け付け続けたい(A重視の)システムは、必然的に一時的な不整合を受け入れざるを得ないのです。そこで「厳密な整合性を捨てる代わりに、可用性と速度を取り、不整合はいずれ収束させる」という発想が生まれました。これを整合性モデルとして明確に位置づけ、Amazon Dynamoの論文(2007年)などで実運用の設計として広まったものが結果整合性です。

詳細

更新が伝播して収束する様子

結果整合性の核心は「書き込みの応答を返すタイミング」と「全レプリカが揃うタイミング」がずれていることです。あるレプリカに書き込むと、システムはその1本(あるいは一部)への反映だけで完了応答を返し、他のレプリカへの伝播は非同期で追いかけます。伝播が終わるまでのわずかな時間、レプリカによって古い値と新しい値が混在します。

別の読み手レプリカBレプリカAクライアント別の読み手レプリカBレプリカAクライアントこの瞬間 Aは10 Bはまだ古い値伝播が届いて両者が10に収束在庫を 10 に更新書き込み完了 すぐ応答在庫は?9 まだ古い値が返る変更を非同期で伝播在庫は?今度は10 収束後は最新

この図の「別の読み手」が古い値を受け取る一瞬こそが結果整合性の代償です。しかしクライアントは同期完了を待たずに済み、レプリカBが一時的に落ちていても書き込みは通ります。伝播が届き、収束(convergence)したあとは、どのレプリカに読みに行っても同じ値が返るようになります。

収束を成立させる仕組み

「いずれ収束する」を実際に保証するには、伝播が届いたときに矛盾なくマージできる仕組みが要ります。代表的なのが、各更新にタイムスタンプやバージョン番号を付け、「新しい方を採用する(last-write-wins)」という規則です。より厳密には、更新の因果関係を記録するバージョンベクタや、どんな順序でマージしても同じ結果に収束するよう数学的に設計されたデータ構造(CRDT)が使われます。伝播経路には、ノード同士がランダムに情報を交換して噂話のように全体へ広める「ゴシッププロトコル」や、読み取り時に複数レプリカの値を突き合わせて古いものを直す「read repair」といった手法があります。

読み書きに関わるレプリカ数を調整して整合性の強さを段階的に選べるのも、この系統のシステムの特徴です。「書き込みを受け付けたと見なすレプリカ数(W)」と「読み取りで問い合わせるレプリカ数(R)」を、全レプリカ数(N)に対して W + R > N となるよう設定すると、読みと書きが必ず1台以上で重なるため、最新値を読めることが保証されます(クォーラム方式)。W や R を小さくすれば速く可用性は上がり、大きくすれば整合性が強まる——このダイヤルを回して要件に合わせられます。

ACIDとBASE、そして使い分け

結果整合性は、RDBMSが重んじるACID(原子性・一貫性・独立性・永続性)と対比される「BASE」という設計思想の中核です。BASE は Basically Available(基本的に可用)、Soft state(状態は揺らぐ)、Eventually consistent(結果的に整合)の頭字語で、NoSQL系のデータストアが掲げてきた立場です。両者は優劣ではなく、何を最優先に守るかの姿勢の違いです。

ACID 強整合性BASE 結果整合性常に最新を保証書いた値はすぐ読める同期を待つ遅い 分断時は止まる向く用途決済 在庫 残高いずれ収束一瞬 古い値が見える待たない速い 分断時も書ける向く用途タイムライン いいね数
ACIDとBASE — 何を最優先に守るかの姿勢の違い

実務で最も重要なのは「どのデータに結果整合性を許すか」の線引きです。銀行の残高や在庫の引き当て、二重予約が許されない座席のように、一瞬の食い違いが金銭や信頼の損失に直結するデータには強整合性を選びます。一方、閲覧数、通知、キャッシュ、ソーシャルフィードのように、数秒ずれても誰も損をしないデータは結果整合性で可用性と速度を優先します。落とし穴は「自分が書いた値を自分がすぐ読めない」ことによる混乱で、これには自分の書き込みだけは必ず最新が読める「read-your-writes」など、用途に応じた弱い保証を追加で組み合わせて対処します。結果整合性は万能の緩和策ではなく、「どこまで緩めてよいか」をデータごとに設計する判断そのものです。