ClickHouseとのS3統合
S3からClickHouseにデータを挿入することができ、またS3をエクスポート先として使用することも可能で、「データレイク」アーキテクチャとの相互作用を実現します。さらに、S3は「コールド」ストレージ層を提供し、ストレージと計算を分離するのに役立ちます。以下のセクションでは、ニューヨーク市のタクシーデータセットを使用して、S3とClickHouseの間でデータを移動するプロセスを示し、主要な構成パラメータを特定し、パフォーマンス最適化についてのヒントを提供します。
S3テーブル関数
s3
テーブル関数を使用すると、S3互換ストレージからのファイルの読み書きが可能になります。この構文の概要は次の通りです。
ここで:
- path — ファイルのパスを含むバケットのURL。読み取り専用モードで以下のワイルドカードをサポートしています:
*
,?
,{abc,def}
および{N..M}
(ここでN
,M
は数字で、'abc'
や'def'
は文字列です)。詳細については、パスのワイルドカード使用に関するドキュメントを参照してください。 - format — ファイルの形式。
- structure — テーブルの構造。形式は
'column1_name column1_type, column2_name column2_type, ...'
。 - compression — パラメータはオプションです。サポートされている値:
none
、gzip/gz
、brotli/br
、xz/LZMA
、zstd/zst
。デフォルトでは、ファイル拡張子によって圧縮が自動的に検出されます。
パス式でワイルドカードを使用することで、複数のファイルを参照でき、並列処理を行うことが可能になります。
準備
ClickHouseにテーブルを作成する前に、S3バケット内のデータを詳しく見ることをお勧めします。これをClickHouseから直接行うには、DESCRIBE
ステートメントを使用します:
DESCRIBE TABLE
ステートメントの出力には、ClickHouseがこのデータを自動的に推測する方法が表示されます。S3バケットで表示される内容に注意してください。また、gzip圧縮形式を自動的に認識してデコンプレッションすることにも注目してください:
私たちのS3ベースのデータセットと対話するために、デフォルトのデータベースにtrips
という名前の標準MergeTree
テーブルを準備します。以下のステートメントは、推測されたデータ型の一部を変更することを選択したことに注意してください。特に、Nullable()
データ型修飾子を使用しないことにしたため、不要な追加保存データと追加のパフォーマンスオーバーヘッドを回避できます:
pickup_date
フィールドでのパーティション化の使用に注意してください。通常、パーティションキーはデータ管理のために使用されますが、後でこのキーを使用してS3への書き込みを並列化します。
タクシーデータセットの各エントリには、タクシー旅行が含まれています。この匿名化されたデータは、S3バケット https://datasets-documentation.s3.eu-west-3.amazonaws.com/ 内の nyc-taxi フォルダーに圧縮された2000万件のレコードで構成されています。データはTSV形式で、ファイルごとに約100万行があります。
S3からデータを読み取る
ClickHouse内に永続性が必要ないソースとしてS3データをクエリすることができます。次のクエリでは、10行をサンプルしています。ここではバケットが公開されているため、資格情報は必要ありません:
TabSeparatedWithNames
形式では、最初の行にカラム名がエンコードされているため、カラムをリストする必要はありません。CSV
やTSV
などの他の形式では、クエリのための自動生成されたカラム(例:c1
、c2
、c3
など)が返されます。
クエリは _path
と _file
のような仮想カラムもサポートしており、それぞれバケットパスとファイル名に関する情報を提供します。例えば:
このサンプルデータセットの行数を確認します。ファイルの展開のためにワイルドカードを使用していることに注意し、20ファイルすべてを考慮します。このクエリは、ClickHouseインスタンスのコア数によって約10秒かかります:
データをサンプリングしたり、アドホックな探索クエリを実行したりするのには便利ですが、S3から直接データを読み取ることは定期的に行うことはおすすめしません。真剣な作業の時には、データをClickHouseのMergeTree
テーブルにインポートします。
clickhouse-localの使用
clickhouse-local
プログラムを使用すると、ClickHouseサーバーを展開して構成することなく、ローカルファイルの迅速な処理を行うことができます。s3
テーブル関数を使用した任意のクエリをこのユーティリティで実行できます。例えば:
S3からのデータ挿入
ClickHouseの全機能を活用するために、次にデータを読み取ってインスタンスに挿入します。これを達成するために、s3
関数とシンプルなINSERT
文を組み合わせます。ターゲットテーブルが必要な構造を提供するため、カラムをリストする必要はありません。これにより、カラムがSELECT
句の位置に従ってマッピングされます。すべての1000万行を挿入するには数分かかる場合がありますが、応答を迅速に確保するために、ここでは100万行を挿入します。必要に応じて、それぞれのLIMIT
句やカラム選択を調整して部分的にインポートします:
ClickHouse Localを使用したリモート挿入
ネットワークのセキュリティポリシーによりClickHouseクラスターが外部接続を行うことができない場合、clickhouse-local
を使ってS3データを挿入することが可能です。以下の例では、S3バケットから読み取ってClickHouseに挿入するためにremote
関数を使用します:
安全なSSL接続を介してこれを実行するには、remoteSecure
関数を利用してください。
データのエクスポート
s3
テーブル関数を使用してS3にファイルを書き込むことができます。これには適切な権限が必要です。リクエストで必要な資格情報を渡しますが、詳細は資格情報の管理ページを参照してください。
以下の簡単な例では、ソースではなく宛先としてテーブル関数を使用します。ここでは、trips
テーブルから1万行をバケットにストリームし、lz4
圧縮とCSV
出力タイプを指定します:
ここでは、ファイルの形式は拡張子から推測されていることに注意してください。また、s3
関数内でカラムを指定する必要はなく、この情報はSELECT
から推測できます。
大きなファイルの分割
データを単一のファイルとしてエクスポートすることは考えにくいです。ClickHouseを含むほとんどのツールは、並列処理の可能性があるため、複数のファイルに対して読み書きすることでより高いスループットパフォーマンスを達成します。データのサブセットをターゲットにしてINSERT
コマンドを複数回実行することができます。ClickHouseは、PARTITION
キーを使用して自動的にファイルを分割する手段を提供しています。
以下の例では、rand()
関数の剰余を使用して10個のファイルを作成します。生成されたパーティションIDがファイル名に参照される方法に注目してください。これにより、数字のサフィックスを持つ10個のファイル(例:trips_0.csv.lz4
、trips_1.csv.lz4
など)が作成されます:
あるいは、データ内のフィールドを参照することもできます。このデータセットにおいて、payment_type
は5のカーディナリティを持つ自然なパーティショニングキーを提供します。
クラスターの利用
上記の関数はすべて、単一ノードでの実行に制限されています。読み取り速度はCPUコアとともにリニアにスケールし、他のリソース(通常はネットワーク)が飽和するまで続き、ユーザーは垂直スケーリングを行えます。ただし、このアプローチには限界があります。ユーザーは、INSERT INTO SELECT
クエリを実行する際に分散テーブルに挿入することで、リソースの圧力を一部軽減することができますが、データを読み取り、解析し、処理するのは依然として単一ノードです。この課題に対処し、読み取りを水平方向にスケーリングできるようにするために、s3Cluster関数を提供しています。
クエリを受信するノード(イニシエーターと呼ばれる)は、クラスター内のすべてのノードとの接続を作成します。どのファイルを読み取るかを決定するグロブパターンは、一連のファイルに解決されます。イニシエーターは、クラスター内のノードにファイルを配布し、これらのノードはワーカーとして機能します。これにより、読み取りを水平方向にスケールさせることが可能になります。
s3Cluster
関数は、単一ノードのバリアントと同じ形式をとりますが、ターゲットクラスターを指定する必要があります:
cluster_name
— リモートおよびローカルサーバーへのアドレスと接続パラメータを構築するために使用されるクラスターの名前。source
— ファイルまたは複数のファイルへのURL。読み取り専用モードで以下のワイルドカードをサポートします:*
、?
、{'abc','def'}
および{N..M}
(ここで N、M は数字で、abc、def は文字列です)。詳細についてはパスのワイルドカードを参照してください。access_key_id
およびsecret_access_key
— 指定されたエンドポイントで使用する資格情報を指定する鍵。オプションです。format
— ファイルの形式。structure
— テーブルの構造。形式は 'column1_name column1_type, column2_name column2_type, ...' です。
s3
関数と同様に、バケットが不正な場合は資格情報はオプションです。また、IAMロールを介してセキュリティを定義する場合も同様です。ただし、22.3.1以降は、構造をリクエストに指定する必要があります。つまり、スキーマは推測されません。
この関数は、ほとんどの場合、INSERT INTO SELECT
の一部として使用されます。この場合、通常は分散テーブルに挿入します。以下は簡単な例です。ここでtrips_all
は分散テーブルです。このテーブルはイベントクラスターを使用しますが、読み取りと書き込みに使用するノードの一貫性は要件ではありません:
挿入はイニシエーターノードに対して行われます。これにより、各ノードで読み取りが行われますが、結果の行はイニシエーターにルーティングされて配布されます。高スループットシナリオでは、これがボトルネックになる可能性があります。これに対処するために、s3cluster
関数のparallel_distributed_insert_selectパラメータを設定します。
S3テーブルエンジン
s3
関数は、S3に格納されているデータに対してアドホッククエリを実行できますが、構文が冗長です。S3
テーブルエンジンを使用することで、バケットURLや資格情報を何度も指定する必要がなくなります。ClickHouseはS3テーブルエンジンを提供しています。
path
— ファイルへのパスを持つバケットのURL。読み取り専用モードで以下のワイルドカードをサポートします:*
、?
、{abc,def}
および{N..M}
(ここで N、M は数字、'abc'、'def' は文字列です)。詳細はこちらを参照してください。format
— ファイルの形式。aws_access_key_id
,aws_secret_access_key
- AWSアカウントユーザー用の長期的な資格情報。リクエストを認証するために使用できます。このパラメータはオプションです。資格情報が指定されていない場合、設定ファイルの値が使用されます。詳細は資格情報の管理を参照してください。compression
— 圧縮タイプ。サポートされる値:none、gzip/gz、brotli/br、xz/LZMA、zstd/zst。パラメータはオプションです。デフォルトでは、ファイル拡張子によって圧縮が自動的に検出されます。
データの読み込み
以下の例では、https://datasets-documentation.s3.eu-west-3.amazonaws.com/nyc-taxi/
バケット内にある最初の10個のTSVファイルを使用して、trips_raw
という名前のテーブルを作成します。これらの各ファイルには100万行が含まれています:
{0..9}
パターンを使用して最初の10個のファイルに制限していることに注意してください。作成後、このテーブルを他のテーブルのようにクエリできます:
データの挿入
S3
テーブルエンジンは並列読み取りをサポートします。テーブル定義にグロブパターンが含まれている場合、書き込みはサポートされません。したがって、上記のテーブルでは書き込みがブロックされます。
書き込みを示すために、書き込み可能なS3バケットを指すテーブルを作成します:
行は新しいファイルにのみ挿入できることに注意してください。マージサイクルやファイル分割操作はありません。ファイルが書き込まれると、その後の挿入は失敗します。ユーザーは次の2つのオプションを持っています:
- 設定
s3_create_new_file_on_insert=1
を指定すると、各挿入ごとに新しいファイルが作成されます。各挿入操作に対して単調に増加する数値サフィックスが各ファイルの末尾に付与されます。この場合、次の挿入はtrips_1.bin
ファイルの作成を引き起こします。 - 設定
s3_truncate_on_insert=1
を指定すると、ファイルが切り捨てられます。すなわち、完了時に新しく挿入された行のみが含まれます。
これらの設定はデフォルトで0に設定されているため、ユーザーはそのいずれかを設定する必要があります。両方が設定されている場合、s3_truncate_on_insert
が優先されます。
S3
テーブルエンジンに関するいくつかの注意事項:
- 従来の
MergeTree
ファミリーテーブルとは異なり、S3
テーブルを削除した場合、基になるデータは削除されません。 - このテーブルタイプの完全な設定はこちらで確認できます。
- このエンジンを使用する際の次の制限に注意してください:
- ALTERクエリはサポートされていません。
- SAMPLE操作はサポートされていません。
- インデックス、すなわち主キーやスキップの概念はありません。
資格情報の管理
前の例では、s3
関数またはS3
テーブル定義に資格情報を渡しました。これは偶発的な使用に対しては受け入れられるかもしれませんが、ユーザーは本番環境ではより明示的な認証メカニズムを必要とします。この対処法として、ClickHouseはいくつかのオプションを提供しています:
-
接続の詳細を
config.xml
または相当の設定ファイルのconf.d
内に指定します。以下に例となるファイルの内容を示します。これはdebianパッケージを使用してのインストールを想定しています。これらの資格情報は、上記のエンドポイントが要求されたURLに対して完全に一致する場合に、すべてのリクエストで使用されます。また、この例では、アクセスキーおよび秘密キーの代わりに認証ヘッダーを宣言する能力も強調されています。サポートされる設定の完全なリストはこちらで確認できます。
-
上記の例は、設定パラメータ
use_environment_credentials
の利用可能性を強調しています。この設定パラメータは、s3
レベルでグローバルに設定することもできます:この設定を使用すると、環境からS3資格情報を取得しようとする試みが行われ、IAMロールを介してのアクセスが可能になります。具体的には、以下の取得順序が実行されます:
- 環境変数
AWS_ACCESS_KEY_ID
、AWS_SECRET_ACCESS_KEY
、およびAWS_SESSION_TOKEN
の検索 - $HOME/.aws内のチェック
- AWSセキュリティトークンサービスを介した一時的な資格情報の取得 — すなわち
AssumeRole
APIを介して - ECS環境変数
AWS_CONTAINER_CREDENTIALS_RELATIVE_URI
またはAWS_CONTAINER_CREDENTIALS_FULL_URI
およびAWS_ECS_CONTAINER_AUTHORIZATION_TOKEN
の資格情報をチェック - AWS_EC2_METADATA_DISABLEDがtrueでない場合、Amazon EC2インスタンスメタデータを介して資格情報を取得
- これらの同じ設定を、同じ接頭辞一致ルールを使用して特定のエンドポイントに対しても設定可能です。
- 環境変数
パフォーマンスの最適化
S3関数を使用して読み取りと挿入を最適化する方法については、専用のパフォーマンスガイドを参照してください。
S3ストレージの調整
内部的に、ClickHouseマージツリーは、Wide
および Compact
という2つの主要なストレージ形式を使用します。現在の実装はClickHouseのデフォルト動作(設定min_bytes_for_wide_part
および min_rows_for_wide_part
を通じて管理)が使用されていますが、S3に対する動作は今後のリリースで分岐することが期待されます。たとえば、より大きなデフォルト値のmin_bytes_for_wide_part
は、よりCompact
形式を促し、ファイル数を減少させることが期待されます。ユーザーは、専らS3ストレージを使用する場合、これらの設定を調整することを希望する場合があります。
S3バックアップMergeTree
s3
関数と関連するテーブルエンジンを使用すると、S3内のデータを馴染みのあるClickHouse構文を使用してクエリできます。ただし、データ管理機能とパフォーマンスに関しては制限があります。主インデックスのサポートがなく、キャッシュサポートもなく、ファイルの挿入はユーザーによって管理する必要があります。
ClickHouseは、S3が特に「コールド」データ上でのクエリパフォーマンスがそれほど重要でない場合、魅力的なストレージソリューションであることを認識しており、ユーザーはストレージと計算を分離することを求めています。これを達成するために、S3をMergeTreeエンジンのストレージとして使用することによるサポートが提供されており、ユーザーはS3のスケーラビリティとコスト利点、そしてMergeTreeエンジンの挿入とクエリパフォーマンスを活用できるようになります。
ストレージ Tier
ClickHouseのストレージボリュームでは、物理ディスクをMergeTreeテーブルエンジンから抽象化できます。単一のボリュームは、整然としたディスクのセットから構成される可能性があります。主に、複数のブロックデバイスがデータストレージに使用されることを許すだけでなく、この抽象化によりS3を含む他のストレージタイプも利用できるようになります。ClickHouseデータパーツは、ストレージポリシーに基づいてボリューム間で移動可能であり、フィルレートを調整することでストレージTierの概念が作成されます。
ストレージTierは、最新のデータを保持するためのホット-コールドアーキテクチャを解放します。これは通常、最もクエリされるデータも包含し、パフォーマンスが高いストレージ、例えば、NVMe SSD上で少量のスペースのみを必要とします。データが古くなるにつれて、クエリ時間のSLAは増加し、クエリ頻度も増加します。このデータのファットテールを、HDDやS3などのオブジェクトストレージなど、遅いストレージに保存できます。
ディスクの作成
S3バケットをディスクとして利用するには、まずClickHouseの設定ファイル内でそれを宣言する必要があります。config.xmlを拡張するか、好ましくはconf.dの下に新しいファイルを用意します。以下にS3ディスク宣言の例を示します:
このディスク宣言に関する設定の完全なリストはこちらで確認できます。認証情報はManaging credentialsで説明されているのと同様のアプローチを使用して管理できることに注意してください。すなわち、上記の設定ブロック内でuse_environment_credentialsをtrueに設定することでIAMロールを使用できます。
ストレージポリシーの作成
設定が完了すると、この「ディスク」はポリシー内で宣言されたストレージボリュームで使用されます。以下の例では、s3が唯一のストレージであると仮定します。これは、TTLやフィルレートに基づいてデータが移動できるより複雑なホット-コールドアーキテクチャを無視しています。
テーブルの作成
ディスクをライティングアクセスのあるバケットに設定している場合、以下の例のようにテーブルを作成できるはずです。簡潔さのために、NYCタクシーのカラムのサブセットを使用し、データを直接s3バックのテーブルにストリーミングします:
ハードウェアにより、この1百万行の挿入には数分かかることがあります。進捗はsystem.processesテーブルを使って確認できます。行数を10mの制限まで調整し、一部のサンプルクエリを試してみてください。
テーブルの変更
ユーザーは特定のテーブルのストレージポリシーを変更する必要がある場合があります。これは可能ですが、制約があります。新しいターゲットポリシーには、以前のポリシーのすべてのディスクとボリュームを含む必要があります。つまり、ポリシー変更を満たすためにデータが移行されることはありません。これらの制約を検証する際、ボリュームとディスクはその名前で識別され、違反しようとするとエラーになります。ただし、前の例を使用していると仮定すると、以下の変更は有効です。
ここでは、新しいs3_tieredポリシーの中でメインボリュームを再利用し、新しいホットボリュームを導入しています。これは、パラメータ<path>
を介して設定された1つのディスクのみで構成されるデフォルトディスクを使用します。ボリューム名とディスクは変わりません。テーブルへの新しい挿入は、thisがmove_factor * disk_sizeに達するまでデフォルトディスクに存在します。その時点でデータはS3に移転されます。
レプリケーションの管理
S3ディスクを使用したレプリケーションは、ReplicatedMergeTree
テーブルエンジンを使用して実現できます。詳細については、S3オブジェクトストレージを介して2つのAWSリージョンにわたる単一のシャードのレプリケーションガイドをご覧ください。
読み取りと書き込み
以下のノートは、ClickHouseとのS3インタラクションの実装をカバーしています。一般的には情報提供のみですが、パフォーマンスの最適化の際に読者の助けになるかもしれません:
- デフォルトでは、クエリ処理パイプラインの任意のステージで使用される最大クエリ処理スレッド数はコアの数と等しくなります。一部のステージは他のステージよりも並行性が高いため、この値は上限を提供します。データはディスクからストリーミングされるため、複数のクエリステージが同時に実行される可能性があります。したがって、クエリに使用されるスレッドの正確な数はこれを超えることがあります。max_threads設定を使用して修正できます。
- S3の読み取りはデフォルトで非同期です。この動作は
remote_filesystem_read_method
を設定することによって決定され、デフォルトではthreadpool
の値に設定されています。リクエストを処理する際、ClickHouseはストライプでグラニュールを読み取ります。これらのストライプのそれぞれには多くのカラムが含まれている可能性があります。スレッドは自身のグラニュールのカラムを一つずつ読み取ります。これを同期的に行うのではなく、データを待つ前にすべてのカラムのためにプリフェッチを行います。これにより、各カラムの同期的な待機に比べてかなりのパフォーマンス向上が得られます。ほとんどの場合、ユーザーはこの設定を変更する必要はありません - パフォーマンスの最適化をご覧ください。 - 書き込みは並行して行われ、最大100の同時ファイル書き込みスレッドがあります。
max_insert_delayed_streams_for_parallel_write
は、デフォルト値が1000です。この値は、並行して書き込まれるS3ブロブの数を制御します。書き込まれる各ファイルにバッファが必要なため(~1MB)、これはINSERTのメモリ消費を効果的に制限します。サーバーのメモリが少ないシナリオでは、この値を下げることが適切かもしれません。
ClickHouseディスクとしてS3オブジェクトストレージを使用する
バケットとIAMロールを作成するための手順を必要とする場合は、S3バケットとIAMロールの作成を展開し、次に進んでください:
S3バケットとIAMユーザーの作成
この記事では、AWS IAMユーザーを設定し、S3バケットを作成し、ClickHouseでそのバケットをS3ディスクとして使用する方法の基本を示します。使用する権限についてセキュリティチームと協力して決定し、これを出発点として考慮する必要があります。
AWS IAMユーザーの作成
この手順では、ログインユーザーではなく、サービスアカウントユーザーを作成します。
-
AWS IAM管理コンソールにログインします。
-
「ユーザー」に移動し、ユーザーの追加を選択します。

- ユーザー名を入力し、認証情報の種類をアクセスキー - プログラムによるアクセスに設定し、次へ: 権限を選択します。

- ユーザーをいずれのグループにも追加しないでください; 次へ: タグを選択します。

- タグを追加する必要がない限り、次へ: 確認を選択します。

-
ユーザーの作成を選択します。
注記ユーザーに権限がないという警告メッセージは無視できます; 次のセクションでバケットに対してユーザーに権限が付与されます。

- ユーザーが作成されたので、表示をクリックして、アクセスキーとシークレットキーをコピーします。
キーは別の場所に保存してください; シークレットアクセスキーが利用可能になるのはこの時だけです。

- 閉じるをクリックし、ユーザー画面でユーザーを見つけます。
- ARN (Amazonリソースネーム) をコピーし、バケットのアクセスポリシーを設定する際に使用するために保存します。

S3バケットの作成
- S3バケットセクションで、バケットの作成を選択します。

- バケット名を入力し、他のオプションはデフォルトのままにします。
バケット名はAWS全体で一意である必要があります。組織内だけではなく、そうでなければエラーが発生します。
Block all Public Access
を有効のままにし、公的アクセスは必要ありません。

- ページの下部でバケットの作成を選択します。

-
リンクを選択し、ARNをコピーして、バケットのアクセスポリシーを設定する際に使用するために保存します。
-
バケットが作成されたら、S3バケットリストで新しいS3バケットを見つけてリンクを選択します。

- フォルダーの作成を選択します。

- ClickHouseのS3ディスクの対象となるフォルダー名を入力し、フォルダーの作成を選択します。

- フォルダーがバケットリストに表示されるようになります。

- 新しいフォルダーのチェックボックスを選択し、URLのコピーをクリックします。コピーしたURLを、次のセクションのClickHouseストレージ設定に使用するために保存します。

- 権限タブを選択し、バケットポリシーセクションの編集ボタンをクリックします。

- バケットポリシーを追加します。以下は例です:
使用する権限を決定するためにセキュリティチームと協力する必要があります。これは出発点として考慮してください。 ポリシーと設定に関する詳細については、AWSドキュメントを参照してください: https://docs.aws.amazon.com/AmazonS3/latest/userguide/access-policy-language-overview.html
- ポリシー設定を保存します。
S3バケットをディスクとして使用するようClickHouseを設定する
以下の例は、デフォルトのClickHouseディレクトリがあるサービスとしてインストールされたLinux Debパッケージに基づいています。
- ClickHouseの
config.d
ディレクトリに新しいファイルを作成して、ストレージ設定を保存します。
- 保存先の設定に以下を追加します;先のステップからバケットパス、アクセスキー、およびシークレットキーを置き換えます。
<disks>
タグ内のs3_disk
およびs3_cache
ラベルは任意のラベルです。これらは別の名前に設定することもできますが、同じラベルを<policies>
タブの下の<disk>
タブで使用してディスクを参照する必要があります。
<S3_main>
タグも任意であり、ClickHouseでリソースを作成する際のストレージターゲットの識別子として使用されるポリシー名です。
上記の構成はClickHouseバージョン22.8以上用です。古いバージョンを使用している場合は、データの保存ドキュメントを参照してください。
S3の使用に関する詳細: 統合ガイド:S3バックのMergeTree
- ファイルのオーナーを
clickhouse
ユーザーとグループに更新します。
- 変更を反映させるためにClickHouseインスタンスを再起動します。
テスト
- ClickHouseクライアントにログインします。以下のように実行します。
- 新しいS3ストレージポリシーを指定してテーブルを作成します。
- テーブルが正しいポリシーで作成されたことを確認します。
- テスト行をテーブルに挿入します。
- 行を表示します。
- AWSコンソールで、バケットに移動し、新しいバケットとフォルダーを選択します。 次のようなものが表示されるはずです:

S3オブジェクトストレージを使用して2つのAWSリージョン間で単一のシャードをレプリケートする
ClickHouse Cloudではデフォルトでオブジェクトストレージが使用されているので、ClickHouse Cloud実行中の場合はこの手順を踏む必要はありません。
デプロイメントを計画する
このチュートリアルは、AWS EC2上で2つのClickHouse Serverノードと3つのClickHouse Keeperノードをデプロイすることに基づいています。ClickHouseサーバーのデータストアはS3です。災害復旧を支援するために、各リージョンにClickHouse ServerとS3バケットを配置した2つのAWSリージョンが使用されます。
ClickHouseテーブルは2つのサーバー間、つまり2つのリージョン間でレプリケートされます。
ソフトウェアをインストールする
ClickHouseサーバーノード
ClickHouseサーバーノードのデプロイメント手順を実行する際は、インストール手順を参照してください。
ClickHouseをデプロイする
2つのホストにClickHouseをデプロイします。サンプル構成では、これらはchnode1
とchnode2
と呼ばれます。
chnode1
を1つのAWSリージョンに、chnode2
を別のリージョンに配置します。
ClickHouse Keeperをデプロイする
3つのホストにClickHouse Keeperをデプロイします。サンプル構成では、これらはkeepernode1
、keepernode2
、keepernode3
と呼ばれます。keepernode1
はchnode1
と同じリージョンにデプロイできますし、keepernode2
はchnode2
に、keepernode3
はどちらかのリージョンにデプロイできますが、そのリージョンのClickHouseノードとは異なるアベイラビリティゾーンに配置する必要があります。
ClickHouse Keeperノードのデプロイメント手順を実行する際は、インストール手順を参照してください。
S3バケットを作成する
chnode1
とchnode2
を配置した各リージョンに1つのS3バケットを作成します。
バケットとIAMロールを作成するための手順が必要な場合は、S3バケットとIAMロールの作成を展開し、次に進んでください:
S3バケットとIAMユーザーの作成
この記事では、AWS IAMユーザーを設定し、S3バケットを作成し、ClickHouseでそのバケットをS3ディスクとして使用する方法の基本を示します。使用する権限についてセキュリティチームと協力して決定し、これを出発点として考慮する必要があります。
AWS IAMユーザーの作成
この手順では、ログインユーザーではなく、サービスアカウントユーザーを作成します。
-
AWS IAM管理コンソールにログインします。
-
「ユーザー」に移動し、ユーザーの追加を選択します。

- ユーザー名を入力し、認証情報の種類をアクセスキー - プログラムによるアクセスに設定し、次へ: 権限を選択します。

- ユーザーをいずれのグループにも追加しないでください; 次へ: タグを選択します。

- タグを追加する必要がない限り、次へ: 確認を選択します。

-
ユーザーの作成を選択します。
注記ユーザーに権限がないという警告メッセージは無視できます; 次のセクションでバケットに対してユーザーに権限が付与されます。

- ユーザーが作成されたので、表示をクリックして、アクセスキーとシークレットキーをコピーします。
キーは別の場所に保存してください; シークレットアクセスキーが利用可能になるのはこの時だけです。

- 閉じるをクリックし、ユーザー画面でユーザーを見つけます。
- ARN (Amazonリソースネーム) をコピーし、バケットのアクセスポリシーを設定する際に使用するために保存します。

S3バケットの作成
- S3バケットセクションで、バケットの作成を選択します。

- バケット名を入力し、他のオプションはデフォルトのままにします。
バケット名はAWS全体で一意である必要があります。組織内だけではなく、そうでなければエラーが発生します。
Block all Public Access
を有効のままにし、公的アクセスは必要ありません。

- ページの下部でバケットの作成を選択します。

-
リンクを選択し、ARNをコピーして、バケットのアクセスポリシーを設定する際に使用するために保存します。
-
バケットが作成されたら、S3バケットリストで新しいS3バケットを見つけてリンクを選択します。

- フォルダーの作成を選択します。

- ClickHouseのS3ディスクの対象となるフォルダー名を入力し、フォルダーの作成を選択します。

- フォルダーがバケットリストに表示されるようになります。

- 新しいフォルダーのチェックボックスを選択し、URLのコピーをクリックします。コピーしたURLを、次のセクションのClickHouseストレージ設定に使用するために保存します。

- 権限タブを選択し、バケットポリシーセクションの編集ボタンをクリックします。

- バケットポリシーを追加します。以下は例です:
使用する権限を決定するためにセキュリティチームと協力する必要があります。これは出発点として考慮してください。 ポリシーと設定に関する詳細については、AWSドキュメントを参照してください: https://docs.aws.amazon.com/AmazonS3/latest/userguide/access-policy-language-overview.html
- ポリシー設定を保存します。
構成ファイルは/etc/clickhouse-server/config.d/
に配置されます。ここに1つのバケットのサンプル構成ファイルがあります。他のバケットも類似していますが、3つのハイライトされた行が異なります。
このガイドの多くの手順では、/etc/clickhouse-server/config.d/
に構成ファイルを配置するように求められます。これは、Linuxシステムでの構成オーバーライドファイルのデフォルトの場所です。これらのファイルをそのディレクトリに入れると、ClickHouseは内容を使用してデフォルトの構成をオーバーライドします。これをオーバーライドディレクトリに配置することで、アップグレード中に構成が失われるのを防ぎます。
ClickHouse Keeperを設定する
ClickHouse Keeperをスタンドアロンで実行する場合(ClickHouseサーバーとは別に)、構成は単一のXMLファイルです。このチュートリアルでは、ファイルは/etc/clickhouse-keeper/keeper_config.xml
です。すべての3つのKeeperサーバーは同じ構成を使用し、1つの設定が異なります;<server_id>
。
server_id
は、構成ファイルが使用されるホストに割り当てるIDを示します。以下の例では、server_id
は3
であり、ファイルの下部にある<raft_configuration>
セクションを確認すると、サーバー3のホスト名はkeepernode3
であることがわかります。これは、ClickHouse Keeperプロセスがリーダーを選択する際や他のすべての活動において、どの他のサーバーに接続するかを知る方法です。
ClickHouse Keeperの構成ファイルを配置し、<server_id>
を設定することを忘れないでください:
ClickHouseサーバーを設定する
クラスターを定義する
ClickHouseクラスターは、構成の<remote_servers>
セクションで定義されます。このサンプルでは、cluster_1S_2R
という1つのクラスターが定義されており、単一のシャードに2つのレプリカが含まれています。レプリカはホストchnode1
とchnode2
に配置されています。
クラスターとともに作業する際に便利なマクロを定義すると、DDLクエリにクラスター、シャード、およびレプリカの設定が自動的に入力されます。このサンプルでは、shard
およびreplica
の詳細を指定せずに複製テーブルエンジンを使用することを可能にします。テーブルを作成する際、shard
とreplica
のマクロがsystem.tables
をクエリすることでどのように使用されるかがわかります。
上記のマクロはchnode1
用であり、chnode2
ではreplica
をreplica_2
に設定してください。
ゼロコピーのレプリケーションを無効にする
ClickHouseのバージョン22.7およびそれ以下では、設定allow_remote_fs_zero_copy_replication
は、S3およびHDFSディスクに対してデフォルトでtrue
に設定されています。この設定は、この災害復旧シナリオではfalse
に設定する必要があり、バージョン22.8以上ではデフォルトでfalse
に設定されています。
この設定は次の2つの理由からfalseに設定する必要があります:1)この機能は本番環境での使用に適していない;2)災害復旧シナリオでは、データとメタデータの両方が複数のリージョンに保存する必要があります。allow_remote_fs_zero_copy_replication
をfalse
に設定します。
ClickHouse Keeperは、ClickHouseノード間でデータのレプリケーションを調整する責任があります。ClickHouseにClickHouse Keeperノードを知らせるには、各ClickHouseノードに構成ファイルを追加します。
ネットワーキングの設定
AWSでセキュリティ設定を構成する際にサーバー間で通信できるように、ネットワークポートのリストを参照してください。また、サーバーが相互に通信し、S3と通信できるように、すべての3つのサーバーはネットワーク接続を待ち受ける必要があります。デフォルトでは、ClickHouseはループバックアドレスのみにリスンしているため、これを変更する必要があります。これは/etc/clickhouse-server/config.d/
で設定されています。以下は、ClickHouseとClickHouse KeeperがすべてのIP v4インターフェースにリスンするように構成するサンプルです。詳細な情報は、ドキュメントまたはデフォルトの設定ファイル/etc/clickhouse/config.xml
を参照してください。
サーバーを起動する
ClickHouse Keeperを実行する
各Keeperサーバーで、オペレーティングシステムに応じたコマンドを実行します。例えば:
ClickHouse Keeperの状態を確認する
netcat
を用いてClickHouse Keeperにコマンドを送信します。例えば、mntr
はClickHouse Keeperクラスターの状態を返します。各Keeperノードでこのコマンドを実行した場合、1つはリーダーになり、他の2つはフォロワーになります:
ClickHouseサーバーを実行する
各ClickHouseサーバーで次のコマンドを実行します。
ClickHouseサーバーを検証する
クラスター設定を追加した際、2つのClickHouseノードにわたって複製された単一のシャードが定義されました。この検証ステップでは、ClickHouseが起動したときにクラスターが構築されたことを確認し、そのクラスターを使用して複製テーブルを作成します。
-
クラスターが存在することを確認します:
-
ReplicatedMergeTree
テーブルエンジンを使用してクラスター内にテーブルを作成します: -
前述のマクロの使用方法を理解する
マクロ
shard
およびreplica
は、クラスターを定義する際に定義されました、次のハイライトされた行では、これらの値が各ClickHouseノードで置き換えられる様子が示されています。加えて、値uuid
も使用されます。uuid
はシステムによって生成されるため、マクロには定義されていません。注記上記に示された
'clickhouse/tables/{uuid}/{shard}
のZooKeeperパスは、default_replica_path
およびdefault_replica_name
を設定することによりカスタマイズできます。ドキュメントはここにあります。
テスト
これらのテストは、データが2つのサーバー間でレプリケートされていること、またそれがローカルディスクではなくS3バケットに保存されていることを確認します。
-
ニューヨーク市タクシーデータセットからデータを追加します:
-
データがS3に保存されていることを確認します。
このクエリは、ディスク上のデータのサイズ、どのディスクが使用されたかを判断するためのポリシーを示します。
ローカルディスク上のデータのサイズを確認します。上記から、ストレージされた百万行のサイズは36.42MiBです。これはS3上にあり、ローカルディスク上には存在しないはずです。上記のクエリも、データとメタデータがローカルディスク上に保存されている場所を示します。ローカルデータを確認します:
各S3バケット内のS3データを確認します(合計は示されていませんが、挿入後に両方のバケットに約36MiBが保存されています):


S3Express
S3Expressは、Amazon S3内の新しい高性能な単一アベイラビリティゾーンのストレージクラスです。
このブログを参照すると、ClickHouseでのS3Expressのテスト経験について読むことができます。
S3Expressはデータを単一のAZ内に保存します。これは、AZの障害が発生した場合にデータが利用できなくなることを意味します。
S3ディスク
S3Expressバケットにバックアップされたストレージでテーブルを作成するには、以下の手順を実行します:
Directory
タイプのバケットを作成する- 必要なすべての権限をS3ユーザーに付与するために適切なバケットポリシーをインストールする(例:
"Action": "s3express:*"
は無制限のアクセスを許可します) - ストレージポリシーを設定する際に
region
パラメータを指定してください
ストレージ設定は通常のS3と同様で、次のようになります:
次に、新しいストレージ上にテーブルを作成します:
S3ストレージ
S3ストレージもサポートされていますが、Object URL
パスの場合のみです。例:
設定でバケットリージョンを指定する必要があります:
バックアップ
上記で作成したディスクにバックアップを保存することができます: