Vector と ClickHouse の統合
本番環境のアプリケーションでは、ログをリアルタイムに分析できることが極めて重要です。 ClickHouse は、優れた圧縮率(ログでは最大 170x)と、大量データを高速に集計できる性能により、ログデータの保存と分析に特に優れています。
このガイドでは、広く利用されているデータパイプラインである Vector を使用して Nginx のログファイルをテールし、ClickHouse に送信する方法を説明します。 以下の手順は、任意の種類のログファイルをテールする場合にもほぼ同様に適用できます。
前提条件:
- ClickHouse がすでに稼働していること
- Vector がインストールされていること
データベースとテーブルを作成する
ログイベントを保存するためのテーブルを定義します。
- まず、
nginxdbという名前の新しいデータベースを作成します:
- ログイベント全体を1つの文字列として挿入します。もちろん、この形式はログデータを分析するのに適したものではありませんが、その点は後ほどマテリアライズドビューを使って解決していきます。
ORDER BY は、まだ主キーが不要なため、空のタプルである tuple() に設定されています。
Nginx を構成する
このステップでは、Nginx のログ出力を構成する方法を説明します。
- 次の
access_logプロパティは、ログを combined 形式で/var/log/nginx/my_access.logに出力します。 この値はnginx.confファイルのhttpセクションに記述します:
-
nginx.confを変更した場合は、必ず Nginx を再起動してください。 -
Web サーバー上のページにアクセスして、アクセスログにログイベントをいくつか生成してください。 combined 形式のログは次のようになります。
Vector を設定する
Vector はログ、メトリクス、トレース(sources と呼ばれます)を収集・変換・ルーティングし、ClickHouse を含む多数の異なるベンダー(sinks と呼ばれます)へ送信します。 Source と sink は vector.toml という名前の設定ファイルで定義します。
- 次の vector.toml ファイルでは、my_access.log の末尾を tail する file 型の source と、上で定義した access_logs テーブルを sink として定義しています。
-
上記の構成を使用して Vector を起動します。ソースおよびシンクの定義についての詳細は、Vector のドキュメントを参照してください。
-
次のクエリを実行して、アクセスログが ClickHouse に取り込まれていることを確認します。テーブル内にアクセスログが表示されるはずです。

ログをパースする
ログを ClickHouse に保存できるのは有用ですが、各イベントを 1 つの文字列として保存するだけでは、十分なデータ分析は行えません。 次に、マテリアライズドビュー を使用してログイベントをどのようにパースするかを見ていきます。
マテリアライズドビュー は、SQL における INSERT トリガーと同様に機能します。ソーステーブルにデータ行が挿入されると、マテリアライズドビューはそれらの行を変換し、その結果をターゲットテーブルに挿入します。 マテリアライズドビューを設定して、access_logs 内のログイベントのパース済み表現を生成できます。 そのようなログイベントの 1 つの例を以下に示します。
ClickHouse には、上記の文字列を解析するためのさまざまな関数があります。splitByWhitespace 関数は、文字列を空白文字で分割し、各トークンを配列で返します。
動作を確認するには、次のコマンドを実行します。
いくつかの文字列には余分な文字が含まれており、ユーザーエージェント(ブラウザ情報)は解析する必要はありませんでしたが、 結果として得られた配列は、必要なものにかなり近い形になっています。
splitByWhitespace と同様に、splitByRegexp 関数は、正規表現に基づいて文字列を配列に分割します。
次のコマンドを実行します。2 つの文字列が返されます。
2 番目に返される文字列が、ログから正常に解析されたユーザーエージェントであることに注目してください。
最終的な CREATE MATERIALIZED VIEW コマンドを見る前に、データをクリーンアップするために使用する、いくつかの関数をさらに確認しておきます。
たとえば、RequestMethod の値は先頭に不要な二重引用符が付いた "GET になっています。
この二重引用符を削除するには、trimBoth(エイリアス trim) 関数を使用できます。
時刻文字列は先頭に角括弧が付いており、ClickHouse が日付として解析できる形式にもなっていません。 しかし、区切り文字をコロン(:)からカンマ(,)に変更すると、問題なく解析できるようになります:
これでマテリアライズドビューを定義する準備が整いました。
以下の定義には POPULATE 句が含まれており、これは access_logs に既に存在する行がすぐに処理され、その場で挿入されることを意味します。
次の SQL ステートメントを実行してください:
続いて、正しく動作しているか確認します。 アクセスログが列ごとにきれいにパースされて表示されるはずです:

上記のレッスンではデータを 2 つのテーブルに保存しましたが、最初の nginxdb.access_logs テーブルを Null テーブルエンジンを使用するように変更することもできます。
パース済みデータは変わらず nginxdb.access_logs_view テーブルに格納されますが、生のデータはテーブルには保存されません。
シンプルなインストールと短時間の設定だけで利用できる Vector を使うと、Nginx サーバーからのログを ClickHouse のテーブルに送信できます。マテリアライズドビューを使用すれば、それらのログを列にパースして、より簡単に分析できるようにできます。