テーブルのシャードとレプリカ
ClickHouseにおけるテーブルのシャードとは?
このトピックはClickHouse Cloudには適用されません。ここでは、Parallel Replicasが従来の共有無しClickHouseクラスタにおける複数のシャードと同じ目的を果たします。
従来の共有無し ClickHouseクラスタでは、シャーディングは①データが単一サーバーでは大きすぎる場合、または②単一サーバーのデータ処理が遅すぎる場合に使用されます。次の図は、uk_price_paid_simpleテーブルが単一のマシンの容量を超えるケース①を示しています:

このような場合、データはテーブルのシャードとして複数のClickHouseサーバーに分割できます:

各シャードはデータのサブセットを保持し、独立してクエリ可能な通常のClickHouseテーブルとして機能します。ただし、クエリはそのサブセットのみを処理し、データの分布に応じて有効なユースケースになる場合があります。通常、分散テーブル(サーバーごとにしばしば)により、フルデータセットの統一されたビューが提供されます。これはデータを自体で保存せず、すべてのシャードにSELECTクエリを転送し、結果を集約してINSERTをルーティングし、データを均等に分配します。
分散テーブルの作成
SELECTクエリの転送とINSERTのルーティングを説明するために、2つのClickHouseサーバー間で分割されたWhat are table partsの例のテーブルを考えます。まず、この設定のために対応する分散テーブルを作成するDDLステートメントを示します:
ON CLUSTER
句はDDLステートメントを分散DDLステートメントにし、ClickHouseにtest_cluster
クラスタ定義に列挙されたすべてのサーバーでテーブルを作成するよう指示します。分散DDLにはKeeperコンポーネントがクラスタアーキテクチャで必要です。
分散エンジンのパラメータでは、クラスタ名(test_cluster
)、シャードされた対象テーブルのデータベース名(uk
)、シャードされた対象テーブルの名前(uk_price_paid_simple
)、INSERTルーティングのためのシャーディングキーを指定します。この例では、rand関数を使用して行をシャードにランダムに割り当てています。ただし、ユースケースに応じて、任意の式(複雑な場合でも)がシャーディングキーとして使用できます。次のセクションではINSERTルーティングの動作を説明します。
INSERTルーティング
以下の図は、ClickHouseにおける分散テーブルへのINSERTの処理方法を示しています:

①分散テーブルを対象とするINSERT(単一の行を含む)が、このテーブルをホストするClickHouseサーバーに、直接、または負荷分散装置を介して送信されます。
②INSERTからの各行(ここでは1つ)について、ClickHouseはシャーディングキー(ここではrand())を評価し、その結果をシャードサーバーの数で割った余りを計算し、これをターゲットサーバーIDとして使用します(IDは0から始まり、1ずつ増加します)。その後、行は転送され、③対応するサーバーのテーブルシャードに挿入されます。
次のセクションでは、SELECT転送の動作を説明します。
SELECT転送
この図は、ClickHouseの分散テーブルを使用したSELECTクエリの処理方法を示しています:

①分散テーブルを対象とするSELECT集計クエリが、直接、または負荷分散装置を介して対応するClickHouseサーバーに送信されます。
②分散テーブルは、対象テーブルのシャードをホストしているすべてのサーバーにクエリを転送し、各ClickHouseサーバーがそのローカル集計結果を並行して計算します。
次に、最初にターゲットされた分散テーブルをホストするClickHouseサーバーが、③すべてのローカル結果を収集し、④それらを最終的なグローバル結果にマージし、⑤クエリ送信者に返します。
ClickHouseにおけるテーブルのレプリカとは?
ClickHouseにおけるレプリケーションは、データの整合性とフェイルオーバーを保証するために、複数のサーバーにわたってシャードデータのコピーを維持します。ハードウェア障害は避けられないため、レプリケーションは各シャードが複数のレプリカを持つことでデータ損失を防ぎます。書き込みは、直接または分散テーブルを介して任意のレプリカに向けることができ、そこで操作のためのレプリカを選択します。変更は他のレプリカに自動的に伝播され、障害やメンテナンスが発生した場合でも、他のレプリカでデータは利用可能であり、障害が発生したホストが回復すると、自動的に同期して最新の状態を保ちます。
レプリケーションには、Keeperコンポーネントがクラスタアーキテクチャで必要です。
以下の図は、6つのサーバーを持つClickHouseクラスタを示しています。前述のShard-1
とShard-2
の2つのテーブルシャードにはそれぞれ3つのレプリカがあります。このクラスタにクエリが送信されます:

クエリ処理はレプリカ無しの設定と同様に機能し、各シャードの単一のレプリカのみがクエリを実行します。
レプリカはデータの整合性とフェイルオーバーを保証するだけでなく、異なるレプリカ間で複数のクエリを並行して実行できるため、クエリ処理のスループットを向上させます。
①分散テーブルを対象とするクエリが、直接または負荷分散装置を介して対応するClickHouseサーバーに送信されます。
②分散テーブルは、各シャードから1つのレプリカにクエリを転送し、選択されたレプリカをホストする各ClickHouseサーバーがそのローカルクエリ結果を並行して計算します。
残りは、レプリカ無しの設定での同様な動作をし、上記の図には示されていません。最初にターゲットされた分散テーブルをホストするClickHouseサーバーが、すべてのローカル結果を収集し、それらを最終的なグローバル結果にマージし、クエリ送信者に返します。
ClickHouseは②のクエリ転送戦略を設定可能であることに注意してください。デフォルトでは、上記の図とは異なり、分散テーブルは—利用可能な場合は—ローカルレプリカを優先しますが、他の負荷分散戦略も使用可能です。
さらなる情報を見つけるには
テーブルのシャードとレプリカに関するこの高レベルの紹介以外の詳細については、デプロイメントおよびスケーリングガイドをご覧ください。
ClickHouseのシャードとレプリカについてより深く掘り下げるには、このチュートリアルビデオも強くお勧めします: