同時実行性制御をアプリケーションで解決しようとすると深刻な問題が発生する~業務システムをRDBなしで作れるのか?(後編) エンジニアサポートCROSS 2016
数年前にNoSQLが登場した当時、NoSQLにはデータの一貫性を保証してくれるトランザクション機能などが十分に備わっていないため、業務システムのバックエンドとして使うのは容易ではないと考えられていました。
しかしその後、NoSQLをバックエンドにした業務アプリケーションは現実にはいくつか登場してきています。ワークスアプリケーションズが2014年に発表したERPの「HUE」もCassandraをバックエンドに採用した、本格的な業務アプリケーションです。
そのHUEの開発に関わるスタッフが、どういう実装ならばNoSQLが業務アプリケーションのバックエンドに使えるのか、それにはどういう意味があるのか、などについて議論したセッション「業務システムをRDBなしで作れるのか?」が2月に横浜で開催されたイベント「エンジニアサポートCROSS 2016」で行われました。
セッションでは、アプリケーションレベルでのトランザクション管理や分散データベースにおけるデータの一貫性についてなど、技術的に興味深い議論がなされました。本記事ではその内容のダイジェストを次の3本の記事で紹介します。
前編:トランザクションの実装にはRDB/NoSQLにかかわらず教科書的な定番がある
中編:アプリケーションのレベルでこそ要求に合ったトランザクションが実装できる
後編:同時実行性制御をアプリケーションで解決しようとすると深刻な問題が発生する
いまお読みの記事は後編です。
アプリで一貫性を制御するデメリットとは
ワークスアプリケーションズ 劉氏。
アプリケーションの複雑さは、システムにおけるデータのConsistency(一貫性)に依存しています。
Eventual Consistencyでアプリケーションを開発するときの最大のチャレンジは、データ操作の途中の状態についても見えてしまうので、その状態のときの処理までアプリケーションで考えなければならないということです。
同時にデータを書き込んでいるときなど、そういうときのことも必ずアプリケーション開発者が解決しなければなりません。
これは一般に、とても難しい問題です。しかも、あるケースでの解決方法がべつのケースでそのまま使えることはまずありません。
その意味で、NoSQLのうえにも、何らかのトランザクション処理のフレームワークが必要だと思います。
Consisutencyの問題がどういうところで発生するかというと、3つのレイヤで発生します。
1つはオブジェクトレベルのConsistencyで、Cassandraのような分散データベースでは1つのオブジェクトには実際には複数のレプリカが存在します。これらのレプリカ間で一貫性を保証したいために、CassandraはQuorumなどを使っています。
もう1つはセッションレベルのConsistency。これを保証するには1回の読み書きをシングルプロセスとして処理する必要があります。
いちばん複雑なのがプロセスレベルのConsistencyです。複数のデータに複数のプロセスがアクセスするときのConsistencyの問題は分散RDBでも発生します。
こうした同時実行性制御をアプリケーションで解決しようとすると、性能や複雑性について深刻な問題が発生することになります。
アプリケーションレベルではデータベース内のデータの読み書きの低レイヤでのコントロールができず制御の粒度が大きくなりがちで、粒度が大きいと性能が落ちます。
またアプリケーションレイヤではデータベース全体の状況を把握する視点を持てず、自分のプロセスでの状況しか分からないので、高い性能を実現することは困難です。
最適化もアプリケーション開発者が行わなければなりませんが、それは開発者の経験や技術レベルに依存するうえに、一般にアプリケーション開発者は納期に追われており、最適化などの複雑な問題を解決する時間がほとんどなく、悪い結果になりやすいでしょう。
適切なアイソレーションレベルを利用すればいいのでは?
堤氏。
データベースのレベルでトランザクション処理をした方がオーバーヘッドが小さくなるのは自明です。ただ、私のケースのところで挙げたような、ケースごとに最適化したトランザクションをデータベースでしてくれるか、というのが気になるところですね。
井上氏。
給与計算バッチでいうと、そもそも計算中に入力値が変わらないから、それによる失敗はほぼない、というように制約をゆるめて解決を簡単にする、というところなどですね。
劉氏。
簡単な問題には簡単なソリューションも複雑なソリューションも存在しますが、複雑な問題には簡単なソリューションはありません。
もともとトランザクションにはConsistencyの強さの異なるアイソレーションレベルが用意されています。
アイソレーションレベルが低い方が性能が高いものです。このようなアイソレーションレベルをデータベースが提供すれば、アプリケーション開発者は適切なレベルを選んで利用できます。
(NoSQLでよく使われている)Eventual Consistencyはこの4つのアイソレーションレベルよりもさらに下にあります。
分散データベースにおけるアイソレーション
井上氏。
NoSQLの分散データベースにもEventual Consistency以外のアイソレーションレベルがあって、それらについても、劉さんに説明してもらいます。
劉氏。
One-copy Serializabilityを備えている分散データベースは、レプリカのないデータベースと同等です。この分散データベースのACIDトランザクションは、いちばん強いデータの正確性を保証できます。
この実装のためには2 Phase CommitやPaxosなどを使いますが、これらを使用するとオーバーヘッドは大きくなります。
もしCassandraがこのOne-copy Serializabilityを実装すると、オーバーヘッドが大きくて遅くなるでしょう。
井上氏。
分散データベースでも同時実行性制御の強いものはコーディネーションも必要なので、性能も落ちていくというわけですね。
劉氏。
そこで現実的なConsistency Modelとしては、Snapshot Isolationがよく使われています。これはスナップショットを用いるのでリードをブロックしないため性能も高いです。 ANSIのRepeatable Readよりアイソレーションレベルも強いので、アプリケーションからも使いやすい。
そしてもう1つ重要な点として、分散システムで実装しやすいことがあげられます。
Causal Consistencyはもっとリラックスしたアイソレーションを提供します。それは、依存性のあるリードとライトの操作だけ順番を保証するというものです。
いまの高可用性分散データベースで重要なモデルです。
これらのアイソレーションレベルの評価です。Causual-SIは僕のイメージとしては高可用な分散データベースの発展の1つの方向だと考えています。
Publickeyによる補足:NoSQLの進化
劉氏の説明は、前半はアプリケーション側でトランザクションを実装することのデメリットを示すことによる、堤氏の議論への直接的な反論。
後半では、今後はNoSQLの分散データベースにおいても、ある程度しっかりしたデータの一貫性などが提供できるようになるのではないか、という見通しが指摘されました。
これについて劉氏は、さらに次のように補足しています。
「HBase、Cassandra、DynamoDBなどは第1世代ビッグデータ向け分散NoSQLデータベースですが、本格なデータベースとしては、クエリ言語、トランザクション管理、一貫性保証などの重要な機能がいろいろ欠如しています。
Googleが開発したMegaStore、Spannerなどはより強い機能(外部一貫性 externally-consistent、ACIDトランザクション処理など)を実現しましたが、低遅延の保証がなく、第1.5世代のNoSQLと言えます。
今後のトランザクションは、機能性、可用性と遅延性の最適的なバランスを取るために、より適切な一貫性モデル上に実装すべきだと思います。また、ソフトウェア側だけの努力ではなく、新型のハードウェア(SSD、RDMA、HTM)との結合も重要なポイントです」
これらの説明は、一般にNoSQLが持つ高可用性や高速性、耐障害性を備えつつ、業務アプリケーションのバックエンドとしてもそれなりに充実したトランザクション性能を備えた分散データベースが普及してくることに期待を持たせるものではないでしょうか。
あわせて読みたい
VMwareからKVMへ、ワンクリックで変換を実現。「脱VMware」へ向かう「Acropolis 4.6」をNutanixが発表
≪前の記事
アプリケーションのレベルでこそ要求に合ったトランザクションが実装できる~業務システムをRDBなしで作れるのか?(中編) エンジニアサポートCROSS 2016