Grafana Lokiとは?Prometheus連携・LogQL・導入方法をわかりやすく解説
Grafana Loki(グラファナ・ロキ)は、Grafana Labsが2018年に公開したオープンソースのログ集約システムです。「Prometheusのログ版」とも呼ばれ、ログ本文の全文インデックスを行わず各ログに付けたラベルだけを索引する設計により、ストレージと運用コストを大幅に抑えられるのが最大の特徴です。メトリクスを扱うPrometheusと同じラベル思想を共有するため相性がよく、Grafana上でメトリクスとログを同じ画面で相関分析できます。ログの抽出・集計には専用クエリ言語LogQLを使い、収集にはPromtail(現Grafana Alloy)などのエージェントを組み合わせます。この記事では、Grafana Lokiとは何かという基本から、Prometheusとの違いと連携、LogQLの使い方、Docker ComposeやKubernetesでの導入方法、料金までをわかりやすく整理します。
目次
- 1 まとめ:Grafana Lokiは「ラベル索引×低コスト」で選ばれるログ基盤
- 2 Grafana Lokiとは何か:Prometheus由来の設計でコスト効率に優れたログ基盤を徹底解説
- 3 Grafana Lokiの導入手順・インストール方法:Docker環境での手軽な導入からKubernetesへのデプロイまで詳しく解説
- 4 Grafana Lokiの特徴とメリット:ラベル管理による高速検索とコスト削減、スケーラブルなログ基盤の利点
- 5 Grafana Lokiのアーキテクチャ概要:ログ受信から保存・検索までの仕組みと主要コンポーネントを解説
- 6 Grafana Lokiのデータソース設定方法:Grafanaでのログデータ可視化に向けた接続手順を詳説
- 7 LogQLによるログクエリ/検索方法:ラベルフィルタとパイプライン活用による柔軟なログ抽出・分析解説
- 8 line_formatとログメッセージの分離テクニック:Lokiでメタデータと本文を見やすく表示する応用方法
- 9 Grafana LokiとKubernetes/コンテナ環境との連携:PromtailによるPodログ収集とクラスタ内統合ログ管理
- 10 Grafana Lokiの実践Tips・運用方法:ラベル設計のベストプラクティスやリテンション設定など効率的運用のポイント
- 11 Docker Composeを使ったGrafana Loki構築例:Loki・Promtail・Grafanaを活用したローカル環境でのログ基盤構築手順
- 12 Grafana Lokiに関するよくある質問
- 13 関連記事
まとめ:Grafana Lokiは「ラベル索引×低コスト」で選ばれるログ基盤
- Grafana Loki(グラファナ・ロキ)とは:Grafana Labs製のオープンソースなログ集約システム。ログ本文を全文インデックスせずラベルのみを索引するため、ElasticsearchなどのフルインデックスなログDBより低コスト・低運用負荷で運用できる。
- Prometheusとの違い・連携:Prometheusは「メトリクス」、Lokiは「ログ」を扱う別ツール。設計思想(ラベル)を共有しており、同じラベルでメトリクスとログを紐付けてGrafanaで統合可視化できる補完関係にある。
- LogQL:PromQLに似たLoki専用のクエリ言語。
{job="varlogs"}のようにラベルで対象を絞り込み、パイプラインで抽出・集計する。line_formatで表示を整形できる。 - 導入方法:学習・検証はLoki+Promtail+Grafanaを1つにまとめたDocker Composeが手軽。Kubernetes環境ではHelmチャートでデプロイし、Promtail/Alloyで各Podのログを収集する。
- 料金:OSS版は無料でセルフホストできる。マネージドで使いたい場合はGrafana Cloudに無料枠と有料プランが用意されている。
Grafana Lokiとは何か:Prometheus由来の設計でコスト効率に優れたログ基盤を徹底解説
Grafana Loki(グラファナ・ロキ)は、Grafana Labs社が2018年に公開したオープンソースのログ集約システムです。その設計は「Prometheusのログ版」とも称され、メトリクス監視ツールであるPrometheusの思想をログ管理に応用したものです。水平スケーラビリティ(スケールアウト)と高可用性を備えた分散アーキテクチャで構築されており、クラウドネイティブ環境の大規模ログ収集にも適しています。従来のログ管理システムと異なり、Lokiはログ内容の全文インデックスを行わず、各ログに付与されたメタデータ(ラベル)のみをインデックスします。これによりシステムの運用がシンプルになり、ストレージや処理コストを大幅に削減できる点が大きな特徴です。
Grafana LokiはGrafanaによる可視化との親和性も高く、いわゆる「メトリクス・ログ・トレース」の3本柱からなるモダンなオブザーバビリティスタックのログ部分を担う存在です。Prometheus(メトリクス収集)やGrafana Tempo(トレース収集)と並び、Grafanaプラットフォームの一環として開発されています。ログデータをGrafanaダッシュボードやExplore画面で可視化・検索でき、メトリクスとログを共通のラベルで紐付けて統合監視することが可能です。こうした特長から、Grafana Lokiは近年多くのエンジニアに注目され、Kubernetesをはじめとするクラウド環境でのログ管理によく採用されています。
ログ管理におけるGrafana Lokiの位置付けと役割:メトリクス連携可能な次世代ログ集約基盤について
システム運用においてログ管理は不可欠な要素ですが、Grafana Lokiはそのログ管理ツール群の中で「次世代のログ集約基盤」として位置付けられます。従来はElasticsearchやSplunkなどがログ管理の主流でしたが、LokiはPrometheusで実績のあるラベルベースのアプローチをログに適用することで、より効率的かつスケーラブルなログ管理を実現しました。Lokiは単体のログ収集サーバーではなく、Promtailなどのログ収集エージェントとGrafanaの可視化ツールと連携して使用されます。この三位一体の構成によって、ログの収集・保存・可視化まで一貫したプラットフォームを提供し、ログ監視のエコシステムを形成しています。
Grafana Lokiの役割は、大量の分散したログを一か所に集約し、素早く検索・分析できるようにすることです。その際、Lokiはログごとにラベル(メタデータ)を付与してデータを管理します。例えばサービス名、ホスト名、環境(本番/開発)などのラベルをログに付けておけば、後で特定のサービスやホストのログだけを抽出して調査することが容易になります。Lokiはこうしたラベルをインデックスに用いることで、高速な検索を可能にしつつ、インデックス構築・維持に伴うコストや複雑さを抑えているのです。
Prometheusとの関係:メトリクス監視ツールとの違いとGrafanaによるログ・メトリクス統合視覚化
Grafana LokiはPrometheusにインスパイアされたログシステムであり、「メトリクスはPrometheus、ログはLoki」と位置付けられることが多いです。Prometheusはアプリケーションやシステムから取得した数値指標(メトリクス)を時系列データベースに保存・監視しますが、Lokiはテキスト形式のログデータを収集・保存します。両者はデータ種別こそ異なりますが、共にマルチテナント対応の水平スケーラブルな設計思想やラベルによるデータモデリングなど、CNCF系のクラウド監視ツールに共通するアーキテクチャ上の特徴を備えています。
特にラベルの活用という点で、LokiとPrometheusは共通したアプローチを取ります。LokiではPrometheusと同じラベル体系を使ってログをグルーピング・検索できるため、Grafana上でメトリクスとログをシームレスに行き来することが可能です。たとえばGrafanaダッシュボードで特定のマイクロサービスのメトリクスに異常が検知された際、同じラベルを用いてLokiのログを即座に絞り込み、問題の詳細をログから調査するといった統合操作ができます。このようにGrafana LokiとPrometheusは補完関係にあり、Grafanaをハブとしてメトリクスとログの統合的な監視を実現します。
Grafana Loki誕生の背景:Grafana Labsによる開発経緯とオープンソースプロジェクトとしての進化
Grafana Lokiは2018年にGrafana Labs社によって発表されました。当時、ログ管理領域ではELKスタック(Elasticsearch + Logstash + Kibana)がデファクトスタンダードでしたが、急増するログデータに対するスケーラビリティやコストの課題が顕在化していました。Grafana LabsはPrometheusで培った知見を元に、よりコスト効率良く大規模ログを扱える新しいアプローチとしてLokiを開発しました。初期バージョンはKubeCon 2018で披露され、そのコンセプト「Prometheus for logs」は多くの注目を集めました。
オープンソースプロジェクトとしてのGrafana Lokiは活発に進化を続けています。GitHub上で公開されAGPLライセンスで提供されており、世界中のコミュニティから貢献を受け入れながら機能拡張が行われています。特にKubernetesとの親和性や、高可用性クラスタ構成のサポート、ログアラート(アラートルール)機能の充実など、実運用に耐えるための改良が重ねられてきました。また、Grafana CloudではマネージドサービスとしてLokiを提供し、クラウド上でスケーラブルにLokiを利用できるようになるなど、エコシステムも拡大しています。こうした経緯から現在では、Grafana Lokiは従来のログ基盤に代わり得る選択肢として確固たる地位を築きつつあります。
ELKスタックなど従来ツールとの違い:全文検索主体からラベルベース管理へのインデックスレスなアプローチ
Grafana Loki最大の特徴は、ElasticSearchなど従来の全文インデックス型ログシステムとは一線を画すアプローチを取っている点です。ELKスタックではログ内容を解析してインデックス(逆引き索引)を構築し、高速な全文検索を実現しています。一方でこの方式は、インデックスの構築・保持に大量のストレージ(概ねログ容量の50%程度の追加ストレージ)とCPU・メモリリソースを要し、システムに大きな負荷をかけます。ログ量が増えるほどインデックスも指数的に肥大化し、運用コストが問題となっていました。
これに対しLokiはインデックスレス(または限定的インデックス)なラベルベース管理方式を採用しています。ログ1行ごとに付与されたラベル(メタデータ)だけをインデックス化し、ログ本文自体は圧縮してオブジェクトストレージ等に順次保存します。検索時にはまずラベルで対象のログストリームを絞り込み(インデックス検索)、該当する圧縮ログチャンクを取得してから、その中で文字列マッチや構造化フィルタを行います。この方法により、従来必要だった巨大な全文インデックスを不要とし、結果としてストレージ使用量の削減(インデックス保存領域が不要)やインデックス構築負荷の低減を実現しているのです。加えて、ログデータ自体は圧縮されて低コストなオブジェクトストレージ(例:AWS S3やGCS)に保存できるため、スケーラビリティと費用対効果の面で大きなメリットがあります。
ラベルベース管理によるログ可観測性の新しい潮流:モダンな監視スタックで注目される理由とメリットについて
Grafana Lokiが注目される背景には、近年のモダンな監視スタックにおけるラベルベースの可観測性という潮流があります。従来のログ管理はキーワード検索や手作業での分析が中心でしたが、マイクロサービスやクラウドネイティブ環境ではサービス数・インスタンス数が膨大となり、ログを体系的に紐付けて管理する必要性が高まっています。その解決策として、Prometheusに倣ったラベルによるデータモデルがログにも適用され始めました。Lokiはその代表格であり、ログにメタデータを付与して分類・抽出することで、単なる全文検索では難しかったコンテキストに沿ったログ分析を容易にしています。
ラベルベースのログ管理は、例えば「あるユーザーセッションIDに関するすべてのサービスログを横断的に確認する」といった高度な分析にも威力を発揮します。各ログにユーザーIDやトランザクションIDのラベルを付与しておけば、LokiのクエリでそのIDに紐づくログだけを素早く集約できます。これにより、分散システム全体をまたいだトラブルシューティングが効率化され、開発・運用チームの生産性向上に繋がります。また、ラベルに基づくログ収集はOpenTelemetryなど他の可観測性フレームワークとも親和性が高く、メトリクス・トレースとの統合分析の基盤としてもLokiが選ばれる理由となっています。総じて、Grafana Lokiはログ可観測性の新しい潮流を担うツールとして、そのメリットが広く認知され始めているのです。
Grafana Lokiの導入手順・インストール方法:Docker環境での手軽な導入からKubernetesへのデプロイまで詳しく解説
ここからはGrafana Lokiの導入方法について、代表的な手順や環境ごとのセットアップ手法を解説します。Lokiは公式から単一バイナリを入手して実行することもできますが、Dockerコンテナを使った導入が手軽で一般的です。また、クラウドネイティブ環境向けにはHelmチャートやOperatorを用いてKubernetes上にデプロイする方法も用意されています。加えて、ログ収集エージェントであるPromtail(またはGrafana Agent Alloy)のセットアップも、Loki導入の一環として考慮する必要があります。以下ではローカル環境での簡単な起動から、より本格的なクラスタ環境への展開まで、順を追って説明します。
Grafana Lokiサーバーのインストール方法の概要:ローカルからクラウドまで様々な環境での導入オプション
Lokiサーバーのインストールには複数のオプションがあります。小規模検証やローカル環境では、公式が提供する単一バイナリ(loki-linux-amd64など)をダウンロードして即実行する方法や、Dockerイメージを取得してコンテナとして起動する方法が手軽です。一方で本番環境やクラウド上では、Docker Composeで関連コンポーネントごと起動したり、Kubernetes上にHelmチャートを使ってデプロイしたりする方法が取られます。Grafana Labsはマネージドサービス(Grafana Cloud Logs)も提供しており、クラウド上でLokiを利用する選択肢もあります。導入先の環境や目的に応じて、「バイナリ実行・Docker利用・Kubernetesデプロイ・クラウドサービス」といった様々な導入パターンを選択できます。
まず試してみたい場合はDockerによる起動が推奨されます。Docker Hub上に公式イメージが公開されており、コンテナ起動時に設定ファイルを指定するだけでLokiサーバーをすぐに立ち上げ可能です。Kubernetes環境の場合は、Helmリポジトリの「grafana/loki-stack」チャートを使うことで、Lokiおよび関連するPromtail・Grafanaをまとめてデプロイできます。いずれにせよ、Loki自体はGo言語で実装された単一バイナリで動作し、外部依存が少ない設計のため、導入のハードルは比較的低いと言えるでしょう。
Dockerイメージを用いたGrafana Lokiの簡単セットアップ手順:イメージ取得からコンテナ起動まで
Dockerを用いたLoki導入は、公式イメージを利用することで非常に簡単に行えます。まずDocker Hubから最新版のLokiイメージ(grafana/loki:latestなど)を取得します。例えばコマンドラインから:
docker pull grafana/loki:latest
でイメージをダウンロードできます。その後、Lokiの設定ファイルを用意し(後述のデフォルト設定でも動作します)、以下のようにコンテナを起動します。
docker run -d --name loki -p 3100:3100 \ -v $(pwd)/loki-config.yaml:/etc/loki/local-config.yaml \ grafana/loki:latest -config.file=/etc/loki/local-config.yaml
上記では現在のディレクトリにあるloki-config.yamlをコンテナ内の標準パスにマウントし、ポート3100を開放してLokiをバックグラウンド起動しています。これだけでLokiサーバーがローカル環境で起動し、http://localhost:3100でLokiのAPIが利用可能になります。実行後、docker psコマンドでコンテナの起動状態を確認し、curl http://localhost:3100/readyを叩いてreadyというレスポンスが返れば、Lokiが正常に起動していることが確認できます。
バイナリファイルによるLoki単体インストールと設定方法:公式リリースからのダウンロードと起動手順を解説
Grafana Lokiは単一の実行可能バイナリとして配布されているため、サーバーに直接インストールして動かすことも可能です。公式サイトやGitHubのリリースページから、使用するOS/アーキテクチャ向けのバイナリ(例:Linux AMD64版ならloki-linux-amd64.zip)をダウンロードします。バイナリを解凍し適当なディレクトリに配置したら、設定ファイルlocal-config.yaml(またはloki.yml)を用意して起動コマンドを実行します。
起動は非常にシンプルで、例えば:
./loki-linux-amd64 -config.file=loki.yaml
と実行するだけでLokiサーバーが起動します。設定ファイルでは後述するように、Lokiのサーバーポートやストレージの種類、ログの保持期間など様々な項目を指定できます。バイナリ実行の場合、自身でSystemdのサービス登録を行ってデーモン化したり、ログローテーションの設定をしたりする必要がありますが、小規模な環境やテスト目的では手軽に試せる方法です。また、依存する外部サービスが無い単一プロセスのため、コンテナを使わなくとも手間なく導入できる点がメリットです。
KubernetesへのGrafana Lokiデプロイ:HelmチャートやOperatorの活用によるクラスタログ基盤構築
本番環境や大規模なログ基盤としてGrafana Lokiを導入する場合、Kubernetes上にデプロイするケースが多くあります。Grafana Labsは公式のHelmチャート「grafana/loki-stack」を提供しており、これを使うとLoki本体に加えログ収集用のPromtail、可視化用のGrafanaをまとめてKubernetesクラスター上にセットアップ可能です。Helmのコマンド例としては:
helm repo add grafana https://grafana.github.io/helm-charts helm install loki-stack grafana/loki-stack --namespace=logging
のように実行します。これにより、デフォルト設定のLoki(StatefulSet)、Promtail(DaemonSet)、Grafana(Deployment)がクラスタ内にデプロイされ、各コンポーネントが連携したログ基盤が構築されます。Helmチャートの値をカスタマイズすれば、ストレージに使用するボリュームのサイズや保持期間、リソース割り当てなどを環境に合わせて調整できます。
また、より高度な方法としてOperator(Loki Operator)を利用する手もあります。Loki OperatorはKubernetes上でLokiのインストール・設定・スケーリングを自動管理するコントローラで、CRD(Custom Resource Definitions)を介してLokiスタックを宣言的に構築できます。いずれの方法でも、Kubernetes上にLokiをデプロイする際はクラスタ内でのログ量やレプリカ数に応じたリソース確保、ストレージクラスの選定(例:オブジェクトストレージ連携の場合はHelm値でS3等を指定)などの考慮が必要です。本番運用では、単一ノード障害に備えてIngesterやDistributorの複数レプリカ構成を取るなど、Helm値をチューニングして可用性を高めることが推奨されます。
ログ収集エージェントPromtailの導入:システムログをLokiに送信する設定とデプロイ方法を解説
Lokiを導入する際には、ログデータをLokiへ送り込むログ収集エージェントのセットアップも欠かせません。代表的なエージェントがGrafana社製のPromtail(プロムテイル)です。Promtailは各サーバー上で動作し、指定したログファイル(例:/var/log/*)を監視して新しいログエントリをリアルタイムに読み取り、Lokiにプッシュ送信します。Promtail自体もDockerイメージ(grafana/promtail:latest)が提供されており、Lokiと同様にバイナリ実行やKubernetes DaemonSetとしての展開が可能です。
Promtailを導入するにはまず設定ファイルを用意します。設定では、どのログパスを収集するか(scrape_configs)、付与するラベル(jobやホスト名、ファイルパスなど)、送信先LokiのURL(clientsセクションでurl: http://loki:3100/loki/api/v1/push)等を指定します。例えばKubernetes環境では、Promtail DaemonSetが各ノード上のコンテナログを収集し、自動的にPod名やNamespace名のラベルを付与してLokiに送ります。ローカル環境でDocker Composeを使う場合でも、Promtailコンテナを起動し/var/logをマウントすることでホストのログを集められます。
Promtail以外にも、Fluent BitやVectorなどLokiと連携できるエージェントは存在しますが、PromtailはLoki公式のエージェントとして最もシンプルに設定できるのが利点です。導入後はPromtailのログ(stdout)やLokiの受信メトリクスを確認し、ログが正しくLokiに届いていることを検証します。適切に設定が行われていれば、Grafana Lokiのデータソースから各種ログがラベル付きで参照できるようになります。
Grafana Lokiの特徴とメリット:ラベル管理による高速検索とコスト削減、スケーラブルなログ基盤の利点
ここではGrafana Lokiが持つ主な特徴と、その活用によって得られるメリットについて解説します。他のログ管理ソリューションと比べた際のLokiの強みを理解することで、なぜLokiが「コスト効率に優れたスケーラブルなログ基盤」と言われるのかが明確になるでしょう。
ログをラベルで管理するアプローチ:インデックス不要で高効率なログ検索とストレージコスト削減の実現について
Grafana Loki最大の特徴は、前述の通りログをラベルで管理するラベルベースアプローチにあります。ログデータに対して全文インデックスを作成せず、メタデータであるラベルの集合だけをインデックス化することで、検索効率とコスト削減を両立しています。この仕組みにより、Lokiはログが増大してもインデックスサイズが肥大化しにくく、ストレージ消費を抑えられるメリットがあります。実際、ElasticSearch等ではログと同程度かそれ以上の容量をインデックスが占めることもありますが、Lokiではラベル情報のみのため必要な追加ストレージ量を大幅に圧縮できます。
また、ラベルを用いた絞り込み検索は計算量が少なく、高速に実行できるのも利点です。例えば「あるアプリケーション(label: app=〇〇)のERRORレベルのログのみ検索したい」という場合、Lokiはまずlabelをキーに対象ログストリームを見つけ、そのログチャンクだけを対象にERROR文字列を探します。不要なログチャンクは最初から読まないため、検索範囲が劇的に減り、結果が短時間で返ってきます。まとめると、Lokiのラベル管理アプローチは不要なデータを持たず・探さずに済むため、システム全体の効率性が非常に高まるというわけです。
水平方向のスケーラビリティと高可用性:大規模環境での安定動作を可能にするLokiの設計と冗長化の特徴
Grafana Lokiはマイクロサービス指向の設計により、高いスケーラビリティと可用性を実現しています。Lokiは単一のプロセスとしても動作しますが、本来はDistributorやIngesterなどの役割ごとにプロセスを分割できる構成になっており、必要に応じて水平スケール(スケールアウト)が可能です。例えばログの流入量が増大した際には、Ingester(ログ取り込み担当)を複数インスタンスにスケールアウトし、分散して書き込み処理を行えます。同様にクエリ処理が重い場合はQuerierを増やすなど、読み取り・書き込み経路を独立に拡張できるのが特徴です。
さらに可用性の面でも、Lokiはデータのレプリケーションと冗長構成をサポートしています。デフォルト設定では、一つのログエントリは複数(通常3つ)のIngesterに複製されて保存されます。これにより一台のIngesterがダウンしてもデータ消失を防ぎ、クエリ時には残存するIngesterからデータを取得できます。また、Quorum(一致数)による書き込み成功判定を採用し、一定数以上のIngesterに書き込まれればログを受領済みと見なす仕組みです。このような分散システムとしての堅牢な設計により、Grafana Lokiはペタバイト級のログを扱う大規模環境でも安定動作を維持できるようになっています。
マルチテナント対応:複数チーム・サービスのログを一元管理しつつ権限分離を実現する仕組みと利点について
Grafana Lokiはマルチテナンシー(Multi-tenancy)をサポートしており、一つのLokiクラスタで複数のチームやサービスのログを隔離して管理できます。各ログデータにはテナントIDを付与でき、Lokiはテナントごとにデータを完全分離して保存・検索を行います。これにより、異なるプロジェクトや部署のログを一元集約しつつも、アクセス権限を分けて運用することが可能です。例えばテナントAのユーザはテナントBのログにアクセスできない、といったポリシーをLoki側で実現できます。
ただし注意点として、Loki本体にはユーザ認証やテナント認可機能が組み込まれていません。そのため、実際にマルチテナント運用を行う際は、認証プロキシ(例:Auth GatewayやGrafana自体の認証機能)をLokiの前段に配置し、リクエストヘッダにテナントIDを埋め込むことでテナントを識別する運用が一般的です。このひと手間は必要ですが、実装自体はヘッダ付与だけで済みLoki側は透過的に扱えます。マルチテナント対応によって、ログ基盤をサービス横断で集約し運用コストを下げつつ、データアクセスの分離も担保できる点はLokiの大きな利点です。
Grafanaとの連携とエコシステム:既存の監視ツールとの統合メリットと他OSSログクライアントとの互換性
Grafana Lokiは名前が示す通りGrafanaとの統合を前提に設計されており、そのエコシステム適合性が優れています。Grafana(バージョン6.0以降)にはLoki用のデータソースプラグインが標準搭載されており、Grafana UIからLokiにクエリを発行してログを可視化できます。メトリクスやトレースと同一のダッシュボード上にログ情報を表示したり、アラート通知もログクエリに基づいて設定することが可能です。これにより、開発・運用者はGrafanaという統一インタフェースでシステム監視の全体像を把握できるようになります。
また、Lokiはオープンソースの他ツールとも互換性を持つよう設計されています。例えばログ収集エージェントはPromtailに限らず、Fluentd/Fluent BitやLogstashなどのプラグインを介してLokiへログ転送ができます。Dockerコンテナから直接Lokiにログを送るDocker Driver、CLIでクエリを投げるlogcliツールなど、多様なクライアントが用意されています。さらに、Lokiのデータ構造やAPIは他のCNCFプロジェクトとも連携が検討されており、時系列DBであるCortex/Mimirとの併用や、OpenTelemetryログエクスポータとの連携などエコシステムが拡大中です。総じてGrafana Lokiは、既存の監視ツール群にうまく溶け込みながらログ監視部分を担う存在であり、その統合メリットは非常に大きいと言えます。
ログからメトリクス生成も可能:LogQLによるアラート設定や統計分析への活用でさらなるインサイトを得る
Grafana Lokiのもう一つの特徴として、ログからメトリクスを生成できる点が挙げられます。Lokiのクエリ言語LogQLにはログクエリだけでなくメトリクスクエリも存在し、ログデータを集計して時系列メトリクスに変換することが可能です。例えば「ある種類のエラーが一定時間内に何件発生したか」という情報は、LogQLのcount_over_time()関数を使ってログストリームを集計することで取得できます。このようにして得られたメトリクスはGrafanaの通常のグラフパネルにプロットしたり、しきい値を決めてアラートルールを設定したりできます。
ログ由来のメトリクス活用例としては、HTTPリクエストのログからステータスコード別のカウントを算出してエラーレートを監視する、ログイン失敗のログから異常な試行回数を検知するといったものがあります。従来はログ監視とメトリクス監視が別々のシステムで行われることも多かったですが、Lokiを使えばログとメトリクスの境界が融合し、ログに埋もれた重要な数値指標をリアルタイムに抽出できます。これにより、より早い障害検知や深い分析が可能となり、システムから得られるインサイト(知見)が飛躍的に向上します。Grafana Lokiは単なるログ格納庫ではなく、ログから価値ある情報を引き出すプラットフォームとして機能する点も大きな魅力なのです。
Grafana Lokiのアーキテクチャ概要:ログ受信から保存・検索までの仕組みと主要コンポーネントを解説
次に、Grafana Lokiの内部アーキテクチャについて概観します。Lokiは内部で複数のコンポーネントに役割分担された分散システムとして機能しますが、小規模では単一プロセスとしても動作します。このセクションでは、ログがLokiに届いてから保存され検索されるまでの一連の流れや、Lokiを構成する主要コンポーネントの役割、さらにはデプロイ形態の違いやストレージ構造について説明します。
Lokiの基本構成要素:ログ収集エージェント・Lokiサーバー・Grafanaの三位一体によるログ基盤
Grafana Lokiを用いたログ基盤は大きく3つの要素から構成されます。第一に、ログ収集を担うエージェント(PromtailやGrafana Agent Alloyなど)です。エージェントはアプリケーションやシステムからログを収集し、各ログにラベルを付与してLokiに送信します。第二に、ログを受け取り保存しクエリを処理するLokiサーバーそのものです。Lokiは受信したログデータを一定時間バッファし、順次ストレージ(ローカルディスクやクラウドオブジェクトストレージ)に書き込みます。同時に、クライアント(Grafanaなど)からのクエリ要求に応じて該当ログを検索・抽出する役割も担います。
そして第三に、ログデータの可視化と操作を行うGrafanaです。GrafanaはLokiに対してログクエリを発行し、その結果を人間が見やすい形で表示します。Grafana上ではダッシュボードパネルやExplore画面を通じて、Lokiに蓄積されたログをフィルタリング・整形して閲覧することができます。以上の3者、すなわち「エージェント → Loki → Grafana」が密接に連携することで、ログの収集・保存・分析が統合されたログ管理基盤が実現されます。なお、Grafana Agent Alloyは最新のエージェントで、Promtailと同様にLokiへのプッシュ送信を行うほか、メトリクスやトレース収集機能も統合されたオールインワンのエージェントとなっています。
分散アーキテクチャの役割分担:Distributor、Ingester、Querier各コンポーネントの役割
Grafana Lokiは本格的にスケールさせる場合、内部コンポーネントをマイクロサービスとして分割できます。その主なコンポーネントにはDistributor(ディストリビュータ)、Ingester(インジェスター)、Querier(クエリア)、そしてオプションのQuery Frontend、Ruler、Compactorなどがあります。基本となる3役割について説明すると、まずDistributorはLokiへの書き込みリクエスト(ログデータ)を最初に受け取るコンポーネントです。Distributorは受信したログエントリにハッシュを計算し、対応するIngesterノードに転送します。また負荷分散や重複排除、レート制限のチェックなどもDistributorが担います。
Ingesterは実際にログデータをメモリ上で受け取り、一時保持・バッチングしてストレージに書き込む役割を持ちます。Ingesterは一定時間分または一定サイズ分のログをまとめて圧縮し、チャンク(block)としてバックエンドストレージへアップロードします。同時にインデックス(ラベル→チャンク参照)も更新します。Ingesterはデフォルトで複数台にログをレプリケーションするので、一部がダウンしてもデータ損失が起きにくい設計です。次にQuerierはログクエリのリクエストを受け、必要なログデータを検索・取得して結果を返す役割です。Querierは新しいログに関してはIngesterから、古いログは長期ストレージから、それぞれデータを読み集め、クエリ条件(ラベルフィルタや全文マッチ)に従って結果を組み立てます。必要に応じて複数のIngesterやストレージから並行にデータ取得し、統合する処理も行います。
その他、Query Frontendは複雑なクエリの結果キャッシュや分散クエリの分割などを行ってクエリ処理を効率化する補助コンポーネントです。RulerはLogQLのメトリクスクエリを定期実行してアラート発報するためのコンポーネント、Compactorはストレージ上のログチャンクをマージ圧縮したり古いデータを削除したりするメンテナンス役です。これらを組み合わせ、必要なものだけデプロイすることで、Lokiは小規模から大規模まで柔軟に対応できる分散ログシステムとして機能します。
ログデータの流れ:受信からインデックスとチャンクへの変換・保存、クエリ処理までの一連のプロセスを解説
Grafana Lokiにおけるログデータ処理の流れを追ってみましょう。まずエージェント(Promtail等)から/loki/api/v1/pushエンドポイントに対し、ログエントリがHTTPで送信されます。これをDistributorが受け取り、メッセージ内のラベルセットに基づいて担当のIngesterにルーティングします。Ingesterは受け取ったログエントリをメモリ上のバッファに書き込み、一連のログストリームごとに時間順に蓄積します。同時に各ログエントリのラベル集合をキーとしてインデックスエントリを作成し、どのチャンクに格納されたかを記録します。
一定期間が経過するかチャンクサイズが閾値に達すると、Ingesterはそのチャンクを圧縮してバックエンドストレージ(例えばS3やGCSなどのオブジェクトストレージ、あるいはDynamoDBやCassandra等)に書き出します。書き出しにはチャンクデータ本体と、ラベルからチャンクへのマッピング情報(インデックス)の両方が含まれます。これ以降、ログデータは長期保存先に安定して保存され、Ingesterのメモリからは解放されます。
次にクエリ処理の流れです。Grafanaやlogcliからログクエリ(例:{app="web"} |= "error")が発行されると、まずQuery Frontend(使用している場合)がこれを受け、適宜クエリ分割やレンジの調整を行った後、Querierに渡します。Querierはまずインデックスを検索し、指定されたラベルに該当するログストリームのチャンクを特定します。新しい未永続化のログはIngesterにも問い合わせて取得します。こうして集めた対象チャンクを読み解凍し、クエリ中のパイプラインフィルタ(例えば文字列マッチや正規表現)を適用して条件に合うログエントリを抽出します。
最終的にQuerierは該当ログエントリを時間順にマージし、要求元に返答します。Grafanaではこれを受け取って画面にログ一覧を表示することになります。以上がログ受信から保存、そして検索されるまでの一連の流れです。重要な点は、Lokiはラベルインデックスでまず検索対象を絞り込んでから、必要なチャンクデータのみを読み込むため、非常に効率的にクエリを実行できるということです。
デプロイメントモードの比較:単一プロセスのスタンドアロン構成 vs マイクロサービス構成の特徴と利点
Grafana Lokiはデプロイメントモードとして、大きく「単一プロセス(スタンドアロン)モード」と「分割コンポーネント(マイクロサービス)モード」の二通りがあります。単一プロセスモードでは、前述したDistributorやIngester、Querierといった役割がすべて一つのプロセス(バイナリ)内で実行されます。これはシンプルでセットアップが容易な反面、大量のログを扱う場合に一つのプロセスに負荷が集中します。しかし、ちょっとした検証環境や小規模システムでは単一プロセスで十分実用的です。
一方、マイクロサービスモード(分割モード)では各コンポーネントが独立したサービスとして動作し、必要に応じて個別にスケールさせることができます。この構成ではそれぞれの役割が明確に分離されるため、ログ量が増大した場合にIngesterだけ増強する、クエリが増えたらQuerierを水平追加する、といった柔軟なリソース割り当てが可能です。また障害時にも一部コンポーネントの再起動や差し替えで済むため、システム全体の耐障害性も向上します。ただし、分割モードではコンポーネント間の通信やデプロイの複雑さが増すため、運用にはOrchestration(Kubernetesなど)の利用や監視の強化が必要です。
まとめると、単一プロセス構成はシンプルさと導入コストの低さが利点であり、マイクロサービス構成はスケーラビリティと堅牢性が利点となります。開発段階ではスタンドアロンで開始し、規模拡大に伴ってマイクロサービス構成に移行するといった段階的な採用も可能です。Grafana Loki自体は構成変更を比較的容易に行えるので、用途に応じたデプロイ形態を選択できる柔軟性を持っています。
ストレージ設計:インデックスとチャンクの保存先(オブジェクトストレージ活用)とデータ耐久性確保の仕組み
Lokiのデータ保存は、インデックスとチャンクの2種類に分かれています。インデックスとはラベルの値から該当ログチャンクへのポインタ情報であり、チャンクとは実際の圧縮済みログデータ本体です。Lokiはこのインデックスとチャンクを、様々なストレージバックエンドに保存できます。典型的な構成では、チャンクデータをAWS S3やGCP GCSなどのオブジェクトストレージに、インデックスを専用のインデックスDB(DynamoDBやBigtable)に保存します。しかし近年ではBoltDB Shipperという仕組みにより、インデックスもチャンクと同様にオブジェクトストレージへ保存する構成が一般化しています。この場合、LokiはローカルBoltDBに一時的にラベル索引を書き込み、定期的にそれをオブジェクトストレージへアップロードすることでインデックスを共有・永続化します。
ストレージ選択はデータの耐久性・可用性にも関わります。オブジェクトストレージは高い耐久性と自動レプリケーションを持つため、Lokiのチャンク保存先として適しています。一方、インデックス用にDynamoDBなどを使う場合もそれらはマネージドサービスとして冗長化されており、高可用性を確保できます。さらにLoki自身がIngesterレプリケーションを行っているため、ストレージ書き込み前の段階でもデータ保護が効いています。仮に一部のストレージノードが利用不能になっても、他の複製データやキャッシュから再構築が可能です。Loki管理者は、データ保持期間(Retention)の設定によって古いログを自動削除し、ストレージ消費をコントロールできます。総じて、Grafana Lokiのストレージ設計は信頼性とコストを両立すべく柔軟に構成できるようになっており、運用要件に合わせたバックエンド選択とチューニングが可能です。
Grafana Lokiのデータソース設定方法:Grafanaでのログデータ可視化に向けた接続手順を詳説
Lokiサーバーを起動しただけでは、ログの可視化や検索は行えません。ここではGrafana(バージョン6以降)においてLokiをデータソースとして追加し、実際にログを検索・表示できるようにする手順を説明します。GrafanaのUIからLokiを登録し、接続テストを行い、最後にログ表示を確認するまでの流れを順を追って見ていきます。
Grafanaでデータソース追加画面を開く:Loki連携に向けた設定開始ステップ(Connectionsメニュー)
まずGrafanaにログインし、Lokiをデータソースとして追加する作業を開始します。Grafanaの画面左上のメニュー(通称ハンバーガーメニュー)を開き、「Connections」または「設定 (Configuration)」セクションにある「Data Sources」をクリックします。これによりデータソースの一覧・追加画面が表示されます(管理者権限が必要です)。ここで右上の「Add data source」ボタンを押し、新しいデータソース追加フォームへ移動します。
Grafana v9以降ではメニュー構成が若干変わっていますが、基本的にデータソース追加画面にアクセスできればOKです。Lokiを組み込んだDocker Compose環境でGrafanaを起動した場合、デフォルトの管理者ユーザ/パスワード(admin/admin)でログイン後、パスワード変更を経てこの設定画面に到達します。組み込みGrafanaでなくGrafana Cloud等を使っている場合も、同様にData Sourcesの追加から始めます。
Lokiデータソースを選択:Grafana UIでのLoki設定オプションの確認と選択(Add Data Source)
「Add data source」の画面では、まず数多くのデータソースの種類一覧が表示されます。その中から「Loki」を探して選択します。一般に「Logging and document databases」カテゴリにLokiが含まれていることが多いです。アイコンに小さく「Loki」と書かれたものをクリックすると、Loki固有の接続設定フォームが開きます。もしプラグインが正しくロードされていれば、GrafanaにはLokiデータソースの組み込みサポートがあるため追加インストール等は不要です。
Lokiデータソースの設定画面には、接続先URLや認証情報などを入力するフィールドが並んでいます。また上部にはデータソース名(デフォルトは「Loki」)が設定可能で、複数のLokiを登録する場合に識別しやすい名前に変更することもできます。ひとまず単一のLokiを扱う場合は、名前はそのまま「Loki」で問題ありません。それでは次に具体的な接続先の設定に移りましょう。
接続先URLと詳細設定:LokiサーバーURLや認証情報の入力(HTTP設定やHeadersの指定など)
Lokiデータソースの最重要項目は接続先URLです。GrafanaからLokiのAPIにアクセスするためのURLを指定します。例えばローカルでLokiを動かしているならhttp://localhost:3100、Docker Compose内でlokiというサービス名ならhttp://loki:3100となります。通常はhttp://[Lokiのホスト名]:3100の形式で入力し、後ろに/loki/api/v1は付けない点に注意してください(Grafanaが自動でパスを付与します)。
認証が必要な場合(Basic AuthやAPIキー)も、この画面で設定できます。例えばBasic認証を有効にしたLokiなら「Basic auth」をオンにしてユーザ名・パスワードを入力します。あるいはGrafanaからのリクエストに特定のヘッダが必要なら、「Custom HTTP Headers」欄でヘッダ名と値を設定可能です。通常、Loki単体のデフォルト設定では認証不要(auth_enabled: false)になっているため、シンプルな環境では特に触る必要はありません。また「Skip TLS Verify」や「With CA Cert」等のオプションもありますが、これはLokiサーバーがHTTPSかつ自己署名証明書の場合などに使用します。
全て必須項目を入力したら、他の設定(例えば最大検索範囲や結果上限などデフォルトで十分な部分)はひとまずそのままで構いません。最後に画面下部までスクロールして保存とテストを行います。
Save & Testで接続検証:GrafanaからLokiへの接続確認方法と成功時のメッセージ表示
設定入力が完了したら、画面下部の「Save & Test」ボタンをクリックします。Grafanaが入力されたURLに対して接続を試み、Lokiのヘルスチェックエンドポイント(/ready等)にアクセスして正常性を確認します。接続が成功すると、画面上部に緑色で「Data source is working」または「Data source successfully connected.」といったメッセージが表示されます。このメッセージが出れば、GrafanaからLokiへの接続設定は完了です。
もし接続テストが失敗した場合は、赤色のエラーメッセージが表示されます。典型的なエラーとしては「Network Error: undefined」や「HTTP status 404」などがあります。原因としてはURLの間違い(ホスト名やポートのタイプミス)、GrafanaサーバーからLokiへのネットワーク到達性の問題(Docker Composeで別ネットワークにいる等)、あるいはLokiが起動していない/ポートが開いていない等が考えられます。エラーメッセージを元に設定を見直し、再度Save & Testを試みます。無事Successメッセージが出れば、次はいよいよログの表示を試してみましょう。
ログの可視化確認:設定完了後にGrafana Exploreでログが正しく表示されるかテストし確認する手順
Lokiデータソースが正常に接続できたら、GrafanaのExplore画面で実際にログを検索・可視化してみます。Grafana画面左側メニューの虫眼鏡アイコン「Explore」をクリックし、上部のデータソース選択ドロップダウンから先ほど追加した「Loki」を選択します。するとクエリ入力フィールドが表示されるので、試しに{}(すべてのログストリーム)を指定してみましょう。Lokiにログが取り込まれていれば、最新のログエントリが時系列順に一覧表示されるはずです。
さらにクエリ例として{job="varlogs"} |= "ERROR"のように入力すると、特定のラベル(ここではjob=varlogs)にマッチし、かつログ内容に「ERROR」を含むログのみがフィルタされて表示されます。ログの各行にはタイムスタンプとラベル、メッセージ本体が含まれており、ラベルは色分けされて視認性良く表示されます。もし何も表示されない場合は、Promtail側の設定やLokiへのログ送信が正しく機能しているか確認が必要です。
このようにGrafana Lokiのデータソース設定が完了すると、Grafana上でログの強力な検索・分析が可能になります。ダッシュボードパネルにログを埋め込んだり、メトリクスと関連付けて表示させることもでき、可観測性が飛躍的に向上するでしょう。
LogQLによるログクエリ/検索方法:ラベルフィルタとパイプライン活用による柔軟なログ抽出・分析解説
Grafana Lokiの強力な機能として、独自のクエリ言語LogQLがあります。LogQLを使うことで、保存されたログデータから必要な情報を高度にフィルタ・抽出したり、ログを集計してメトリクス化することも可能です。ここではLogQLクエリの基本構造や、ラベルによる検索、内容フィルタ、ログ解析・フォーマットなど、ログ検索に役立つテクニックを解説します。
LogQLの基本構文:ストリームセレクタとパイプラインからなる2部構成のクエリ形式
LogQLのクエリは、大きく分けて「ストリームセレクタ」と「パイプライン(ログパイプライン)」の2部構成になっています。ストリームセレクタは波括弧{}で囲まれた部分で、ここにラベル名="値"の形式で条件を指定して、対象とするログストリーム(ログの集合)を絞り込みます。例えば{app="frontend", level="error"}とすれば、「appラベルがfrontendかつlevelラベルがerrorのログ」に限定されます。ストリームセレクタで指定しなかったラベルは任意の値を許容します。また=の代わりに正規表現マッチ=~や否定マッチ!=、!~を使うこともできます。
ストリームセレクタに続いて|(パイプ)で繋ぐ部分がログパイプラインです。ここではストリームセレクタで抽出されたログ群に対し、さらに内容ベースのフィルタリングや変換処理を順次適用できます。パイプラインは左から右に処理が流れていき、ラインフィルタ(内容のテキストマッチ)、ラベルフィルタ(パースした結果のラベルに対する条件)、パーサー(JSONや正規表現でログを構造化)、ラインフォーマット(出力表示の整形)などのステージを組み合わせられます。各ステージは|で繋いで順に実行され、最終的に該当ログのみが出力されます。
例えば以下のLogQLクエリ例を見てみましょう。
{cluster="eks-001", pod="app-001"} |= "error" | json | status >= 500 | line_format "{{.path}} {{.status}}"
このクエリは次の処理を行います:
- ストリームセレクタで
cluster="eks-001", pod="app-001"にマッチするログを抽出 - その中から、ログ行に
errorという文字列を含むものだけにさらに絞り込み(ラインフィルタ|= "error") - 残ったログの本文を
jsonパーサーで解析し、構造化データに変換(ログにJSON形式で埋め込まれたフィールドを抽出) - パースして得られた
statusフィールドの値が500以上のログだけを残す(ラベルフィルタstatus >= 500) - 最後に
line_formatで出力フォーマットを変更し、各ログ行を{{.path}} {{.status}}の形式(パスとステータスコードのみ)で表示する
このように、LogQLクエリはフィルタリングと変換をパイプライン的に積み重ねて柔軟なログ操作を可能にしています。まずは次節以降で各要素を詳しく見ていきましょう。
ラベルセレクタによるログストリーム絞り込み:{}内でサービス名やホスト名などを指定して対象ログを選択
LogQLのストリームセレクタ({...})では、ログに付与されたラベルを活用して効率よく検索対象を絞り込めます。例えば{job="nginx", host="web-1"}とすれば、「jobラベルがnginx、かつhostラベルがweb-1」という条件を満たすログストリームのデータだけを対象にします。複数条件をカンマ区切りで指定するとAND条件となり、どれか一つでも満たせばよいOR条件とする場合は正規表現を使います(例:app=~"frontend|backend")。また、{cluster!="prod"}のように!=で特定の値を除外することも可能です。
ストリームセレクタはLokiのインデックス検索に相当するため、この段階で絞り込めれば後続処理が格段に高速になります。実際、前述のようにLokiはラベルでインデックスを構築しているため、ストリームセレクタで指定した条件にマッチするチャンクのみを読み込めばよくなります。従って、LogQLを書く際はできるだけこのラベルセレクタ部分で範囲を狭めるのがベストプラクティスです。例えば「全ログからエラーを検索」ではなく、「特定アプリのエラーを検索」とするだけでも、処理対象データ量が大幅に減ります。
なおストリームセレクタで使用できるのはインデックス済みラベル(ログ送信時に既についているラベル)のみで、パイプライン中で抽出された一時ラベル(後述のextracted label)は使えません。これはデータ構造上の制約ですが、まず既存ラベルで大まかに絞り込んでから、パイプラインで詳細な内容フィルタをするという流れに適っていると言えます。
ラインフィルタと正規表現による条件指定:|= や |~ 演算子でログ内容を検索・除外してノイズを排除
ストリームセレクタで対象を絞った後、ログの内容に着目してさらにフィルタリングするのがラインフィルタ(line filter)です。LogQLではパイプライン中に|= "文字列"を入れると、その文字列を含むログ行だけを残すことができます。逆に!= "文字列"ならその文字列を含まないログだけを残す除外フィルタです。例えば|= "ERROR"はエラーレベルのログ行を抽出するのに使えますし、!= "DEBUG"とすればデバッグログを除去する、といった使い方ができます。
さらに|~ "正規表現"という形式で正規表現マッチによるフィルタも可能です。例えば|~ "status=\d\d"と記述すれば、ログ本文に「status=4xx」または「status=5xx」というパターンが含まれる行だけを抽出できます。否定の!~も同様に利用できます。正規表現を活用することで、ログメッセージのフォーマットに合わせた柔軟な検索が可能になります。
ラインフィルタを重ねることで、ノイズとなる不要ログをどんどん排除し、目的のログだけを残していくことができます。例えばシステム全体のログから特定リクエストIDに関連するものだけ欲しい場合、まず|= "REQ123"でそのIDを含む行を抽出し、さらに!= "DEBUG"でデバッグ出力は除外し…といった具合です。ラインフィルタは内部的には単なる文字列検索のため比較的軽量であり、多量のログからでも高速に絞り込みが可能です。ただし細かいパターンを大量に組み合わせるとクエリが複雑化するため、適切な粒度で使うようにしましょう。
ログの構造解析:| json や正規表現パーサーを使ったログフィールド抽出とラベル化の手法
多くのアプリケーションログはJSON形式や決まったフォーマットで構造化データを含んでいます。LogQLでは| jsonや| pattern(正規表現パターサ)を用いて、ログ行をパースし内部のフィールドを抽出してラベル化(extracted label化)することが可能です。例えばアプリケーションが{"level":"ERROR","msg":"Failed to connect","code":500}のようなJSONログを出力している場合、LogQLクエリに| jsonと入れるだけでlevel="ERROR", msg="Failed to connect", code=500というラベルを動的に取得できます。
抽出されたラベル(extracted label)は、その後のパイプライン処理で通常のラベルと同様に扱えます。たとえば| jsonの後にcode >= 500と書けば、JSON内のcodeフィールドが500以上のログだけを残すというフィルタが可能です。また| pattern を使えば任意のログフォーマットにも対応できます。例えばNginxのログ行に対して| pattern "<:> - のようなパターンマッチを指定すれば、IPやユーザ、メソッド、パス、ステータスコードなどを抽出できます。
<time>
\"
この構造解析により、ログ内容の一部を切り出してデータとして扱うことができます。例えばHTTPステータスコードやエラーメッセージIDなどを抽出すれば、それを用いたさらなるフィルタや集計が容易になります。Lokiでは抽出ラベルも一旦生成されればインデックス付きラベルと同様にクエリ内で利用できるため、ログ内容に依存した高度な検索ロジックを組み立てられます。ただし、抽出ラベルはあくまでクエリ実行時に得られる一時的なものであり、元のログに恒久的に付与されるわけではない点には注意が必要です。
メトリクスクエリ:count_over_time等の関数でログ件数を集計しダッシュボード表示やアラートに活用
LogQLにはログを直接検索する「ログクエリ」だけでなく、結果を集計して時系列データ化する「メトリッククエリ」があります。メトリッククエリでは、ログクエリの後に集計関数を付けることで、一定区間内のログの数や割合などを算出できます。例えばcount_over_time({app="payment", level="error"}[5m])とすれば、「直近5分間におけるapp=paymentかつlevel=errorのログ件数」を時系列メトリクスとして取得できます。このデータはPrometheusのメトリクスと同様にGrafanaのグラフに表示したり、アラートルールでしきい値監視したりできます。
他にもrate()関数で単位時間あたりの発生レートを求めたり、sum by()で特定ラベルごとに集計したりと、PromQLに近い感覚でログ由来の統計値を計算できます。例えばログから抽出したstatusラベルごとにエラー率を出す場合、sum by(status)(rate({service="api", status=~"5.."}[1m]))のようなクエリが考えられます。これにより、サービス内で発生しているHTTP 5xxエラーの割合をリアルタイムにモニタリングできます。
メトリッククエリは大量のログに対して重い処理となりがちなので、複雑なものではクエリ結果上限や実行時間制限に注意が必要です。しかし適切に使えば、ログを単なるテキストではなく定量的なデータ源として活用できるようになります。Grafana Lokiはメトリクス収集ツールに匹敵する分析力をログに与えてくれるため、ログ監視とメトリクス監視の垣根を越えた包括的なオブザーバビリティが実現できるのです。
line_formatとログメッセージの分離テクニック:Lokiでメタデータと本文を見やすく表示する応用方法
Grafana Lokiにはログ表示をカスタマイズする高度なテクニックが存在します。その一つがLogQLのline_format機能を使ったログメッセージとメタデータの分離表示です。標準のログ表示では、各ログ行にタイムスタンプ・ラベル・メッセージ本体が混在して表示されますが、これを工夫することでメッセージ部分を強調し、付加情報(メタデータ)を控えめに別行に表示するといった見せ方が可能です。ここではline_formatを駆使したログ表示の改善テクニックについて紹介します。
ログ表示の課題:メタデータと本文が混在して見づらい問題
デフォルトのGrafanaにおけるログ表示では、各ログエントリがタイムスタンプ、ラベル(例えばjobやhostなど)、そしてログメッセージ本文すべて一行に表示されます。ラベルが多い場合、ログ本文よりも前に長いラベル一覧が並ぶため、肝心のメッセージが埋もれて見づらくなるという課題があります。特にPromtailでJSONログをパースして多数のフィールドをラベル化している場合、ほぼ全文に近い情報がラベルとして展開され、ログ1件が複数行にわたって表示されるケースもあります。開発者としてはパッと見で「ログレベルとメッセージだけ」を確認したいのに、余計なメタデータが視認性を下げてしまうわけです。
従来のELKスタック(Elasticsearch+Kibana)では「short message(ショートメッセージ)」という機能があり、メッセージ本体を強調表示し詳細は折りたたむUIが提供されていました。Grafana Lokiにはそのような専用UIはありませんが、LogQLクエリと表示設定の工夫によって同様の効果を得ることができます。次の節から、その具体的な解決策を見ていきましょう。
line_format機能とは:LogQLでログ出力フォーマットをテンプレート指定する仕組み
line_formatはLogQLの出力整形用の演算子で、Go言語のテンプレート記法を用いてログ行の表示内容をカスタマイズできます。通常、ログクエリの結果はtimestamp + labels + messageの形式で表示されますが、パイプラインの最後に| line_format "{{.label_name}} - {{.message_field}}"のように指定すると、出力時にそのテンプレートに従って各ログ行がフォーマットされます。{{.ラベル名}}あるいは{{.Field名}}のように書くと、該当するラベル値や抽出フィールド値が埋め込まれます。.messageと書けば元のログメッセージ全体が差し込まれます。
この機能により、ログ表示から不要な要素を除去したり、順序を入れ替えたりが自在に行えます。例えば| line_format "{{.level}} {{.msg}}"とすれば、levelラベル値(例えばERRORなど)とmsgフィールド(抽出したメッセージ本文)のみを表示することが可能です。また、テキストにANSIカラーコードを含めることで、Grafana上で文字色や太字を変えることもできます。つまりline_formatは「クエリ結果の見た目」を操作するもので、データ自体をフィルタするわけではありません。したがってクエリの最後に置く必要があり、途中で用いるとその後のパーサー処理には影響しない点に注意が必要です。
ログメッセージ本体の強調表示:line_formatで必要情報のみ抽出し整形
前述の課題に対し、line_formatを活用することでログメッセージ本体だけを太字表示するようなカスタム表示を実現できます。例えば先の例で、ログレベル(例えばlevelラベル)とメッセージ本文(例えばmsgフィールド)がある場合、以下のようなLogQLクエリを組みます。
{app="myapp"} | json | line_format "\u001B[37;1m{{.level}} {{.msg}}\u001B[0m{{ .JSON }}"
ここでは\u001B[37;1mと\u001B[0mというANSIエスケープシーケンスを使い、ログレベル+メッセージ部分を白の太字(37;1)で表示し、それ以外のJSONフィールド{{ .JSON }}部分を通常のグレー色にしています。これにより、Grafanaのログ表示上ではメインのログメッセージが目立ち、詳細なメタデータは二行目に薄い色で表示されるようになります。
ポイントは、{{.msg}}の部分にはANSIカラーコードで囲んだ形式を出力し、{{ .JSON }}(その他全フィールド)にはカラーコードを付けない(デフォルトのスタイルに任せる)ことです。これによって、メッセージ本体とレベルは強調表示され、それ以外は控えめに別行扱いとなります。結果、まるでELKのショートメッセージのように、ログの概要と詳細が見分けやすくなるというわけです。
メタデータを別行に分離表示する工夫:ANSIカラーコード活用による視認性向上
上述のように、ANSIカラーコードを用いることでGrafanaのログUI上で行内改行が発生し、メタデータを別の行に追いやるテクニックが可能です。具体的には、ログメッセージの末尾に\n改行文字や適切なスタイルリセットコードを仕込むことで、残りのフィールドを次行に描画させます。Grafanaのログ表示コンポーネントはANSIコードに対応しているため、この手法が使えます。
例えば先程のline_formatテンプレート中で{{ .JSON }}とした部分は、JSON由来のメタデータフィールド全体を表しています。これを強制的に改行して表示したければ、テンプレート内で\nを挿入することも可能です。ただしGrafanaのバージョンや設定によっては改行がそのまま扱われないケースもあるため、一般には色コードの明暗差で主情報・副情報を視覚的に分ける方法がとられます。
カラーコード例として、37;1mは白太字、30;2mは灰色薄字、といった具合に使い分けます。メタデータ部分を薄いグレーにすれば、自然と目は明るい白文字のログメッセージ本体に引き付けられるわけです。こうした工夫により、膨大なログの中から重要な部分を見逃しにくくなり、開発・運用の効率が上がることが期待できます。
line_format活用事例:ELKのショートメッセージ風表示やカスタムフォーマット例
実践的なline_format活用事例として、既に触れたショートメッセージ風表示の他にも様々な応用があります。例えばログの中で特定のフィールド(ユーザーIDやトランザクションIDなど)を先頭に持ってきて強調表示したり、複数のフィールドを組み合わせて一行メッセージを再構築することも可能です。line_formatはGoテンプレートなので、条件分岐やフォーマット関数も利用できます。そのため、値が存在する場合だけ出力する、といった柔軟な書式制御もできます。
具体例として、あるフィールドdurationが閾値以上なら太字赤色、未満なら通常色で表示する、といったこともテンプレート内で条件判定と色コードを組み合わせれば実現できます。さらに、line_formatと組み合わせてlabel_format(ラベルの付け替え)を使えば、表示用にラベル名を見やすくリネームするといった調整も可能です。これらはニッチなテクニックではありますが、現場では「ログを如何に素早く読めるか」が重要な場面で威力を発揮します。
以上、line_formatやメッセージ分離のテクニックを紹介しました。Grafana Lokiの標準UIだけでは難しかった表示上のカスタマイズも、クエリ言語の工夫で実現できることがお分かりいただけたでしょう。これらはLokiの公式ドキュメントには詳細が少ないため、コミュニティの知見を活用しつつ自環境で試してみる価値があります。
Grafana LokiとKubernetes/コンテナ環境との連携:PromtailによるPodログ収集とクラスタ内統合ログ管理
Grafana LokiはKubernetesをはじめとするコンテナ環境との親和性が高く、クラウドネイティブなログ基盤として設計されています。ここではKubernetes上でLokiを活用する際のポイントや利点について解説します。K8sのPodログを集中的に管理し、マイクロサービスの複数コンテナからのログを一元的に検索・分析できるLokiの連携方法を見ていきましょう。
Kubernetesログ管理にLokiを使う利点:ラベルでPod/Namespace毎に整理
Kubernetes環境でGrafana Lokiを使用する最大の利点は、PodやNamespaceといったK8sメタデータをラベルとしてログ管理に活用できる点です。Kubernetesではマイクロサービス毎に多数のPodがスケールしますが、Lokiは各ログに自動的に「namespace」「pod」「container」などのラベルを付与して保存できます。これにより、「特定のNamespaceのログだけ」「特定のPod(デプロイメント)のログだけ」を簡単にLogQLで抽出可能です。ラベルはKubernetesのラベル/アノテーションや名前から生成されるため、現場の認識と直感的に一致し、ログ管理が整理された形で行えます。
さらに、LokiはPrometheusのラベル体系と共通化されているため、メトリクス監視で使っているclusterやserviceといったラベルでログも管理できます。これはKubernetesにおけるObservabilityで大きな強みで、たとえばPrometheusで検出した特定Podの異常指標から、そのまま同じPodのログにジャンプして調査するといった統合運用が可能です。Kubernetesのような動的環境では、従来の静的なホスト名ベースのログ管理が通用しませんが、Grafana Lokiはラベルに基づく動的なログ分類でこの課題をクリアしています。
Promtail DaemonSetによるPodログ収集:自動でコンテナログにK8sメタデータ付与
KubernetesでLokiを使う場合、一般的には各ノードにPromtailをDaemonSetとして配置し、コンテナログを収集・転送します。PromtailはKubernetesAPIと連携しており、各コンテナのログファイルパス(/var/log/containers/*)を監視するとともに、そのログが属するPodのメタデータを自動取得してラベルに追加します。例えばcontainer_nameやnamespace、pod、さらにはPodに付与した任意のK8sラベルまで、ログラインに対応付けてLokiに送ることができます。
これにより、利用者は特別な工夫をしなくてもKubernetesの構成情報と紐づいたログ管理ができます。たとえばマイクロサービスAのログだけ見たい場合、{app="service-a"}のようにそのデプロイメントに共通のラベルで絞り込むだけでOKです。Pod名やNode名でのフィルタリングも容易です。Promtailは設定で__meta_kubernetes_プレフィックスの変数を使ってこれらをラベル化でき、設定ファイルを書く手間はあるものの、一度設定すれば新規Podにも自動対応します。
Promtail以外にも、Fluent BitのLokiプラグインを使ってDaemonSet構成にする方法もあります。Grafana Agent(Alloy)も同様の機能を持ち、より少ない構成でメトリクス・ログ両方を集約できます。重要なのは、K8sログを扱う際にラベル付与によるメタデータの継承が行われることで、後段のLokiでのクエリが飛躍的に有用になる点です。結果として、分散したPodのログを統合的に追跡し、サービス全体の動きを俯瞰することが容易になります。
LokiスタックのHelmチャート:Grafana Loki+Promtail+Grafanaをクラスタにデプロイ
Kubernetes環境向けにGrafana Labsが提供するLoki公式Helmチャート(loki-stack)は非常に便利です。このチャートを使うと、Lokiサーバー、Promtail、Grafanaの3つがまとめてクラスタ内にデプロイされ、すぐに統合ログ監視環境が手に入ります。Helmのvalues.yamlで細かい設定も可能で、例えばどの名前空間のログを収集対象にするか、Promtailで正規表現フィルタをかけて特定ログだけ送信するか、といった調整もできます。
デプロイ直後は、GrafanaにすでにLokiデータソースが登録済みで、Promtail経由でクラスタ内のすべてのPodログがLokiに集約されている状態になります。あとはGrafanaにアクセスしてExplore画面から{namespace="〇〇"}とクエリするだけで、そのNamespaceの全Podログが閲覧できます。複数クラスタをまたいだログ集約をしたい場合は、それぞれのクラスタにデプロイしたLokiを別々のデータソースとしてGrafanaに登録するか、あるいはリモート読み込み機能を検討する形になります。
HelmチャートではデフォルトでPersistence(永続ボリューム)が無効になっている場合があるため、本番利用時はストレージ設定も見直す必要があります。またログ保持期間(Retention)の設定やリソース制限も適宜チューニングしましょう。とはいえ、Helmチャート利用により相当な工数削減になるため、まず試す際には強く推奨される方法です。
Fluent Bit等他エージェントとの連携:Lokiプラグインでコンテナログを集約
Promtail以外にも、Fluent BitやFluentdといった既存のログ収集基盤からGrafana Lokiに連携するケースもあります。Fluent Bitには公式のLokiプラグイン(out_loki)が用意されており、設定ファイルでLokiのURLやラベルを指定するだけでログをLokiサービスに送り込めます。既にFluent Bitを使ってElasticSearchに送っている環境であれば、並行してLokiにも送信するよう設定することで、段階的な移行・評価が可能です。
Fluent Bitのメリットは軽量で高速なこと、および既存のフィルタ機能を活用できることです。複雑なログ変換やバッファリングをFluent Bit側で行い、最終的な整形結果をLokiに送り込むといった使い分けもできます。さらに、Docker自体にもLokiドライバがあり、コンテナの--log-driver=lokiを指定すると直接Lokiにログが行く機能もあります。このように、多様なエージェント/収集経路でLokiと連携できる柔軟性があるため、自社環境の要件に合わせて最適な構成を選択できます。
コンテナ環境でのLoki運用ベストプラクティス:リソース配置やログ量制御
Kubernetesなどコンテナ環境でGrafana Lokiを運用する際には、いくつかのベストプラクティスがあります。まずラベルのカーディナリティ管理です。動的な値(例えばリクエストIDやユーザIDなど無限に変化しうるもの)をラベルにしないよう留意します。カーディナリティの高すぎるラベルはメモリやインデックスを圧迫し、パフォーマンス問題を引き起こします。基本的にはPod名やサービス名など有限集合となる値のみをラベルとし、無限集合となるものはログ本文に残してテキスト検索で対応するのが望ましいです。
次に、ログ保持期間(Retention)やロギングレベルの制御です。Kubernetes環境ではログ量が膨大になるため、Lokiのコンパクションや削除設定で古いログを適切に削除していく必要があります。また、不要に詳細なDEBUGログまで収集しないようにPromtail側でフィルタを入れることも検討します。特定のコンテナについてはログレベルを上げない、もしくは重要部分だけメタデータを付与して残すなどの工夫も大規模運用では効果的です。
リソース面では、Lokiコンポーネント(特にIngesterとQuerier)に十分なCPU・メモリを割り当て、さらにPodDisruptionBudgetや適切なレプリカ数を設定して可用性を維持します。ログ送信エージェントであるPromtailもDaemonSetで各ノードに配置するため、こちらも障害時にログが抜け落ちないようにバッファ設定を有効にするなど配慮が必要です。最後に、実際の運用ではGrafana Loki自身のメトリクス(/metricsエンドポイントをPrometheusで収集)を監視し、Ingesterの処理遅延やクエリエラー数などをモニタリングすることも大事です。これらベストプラクティスを踏まえて運用することで、コンテナ環境においてもGrafana Lokiは安定かつ効果的なログ管理基盤として力を発揮するでしょう。
Grafana Lokiの実践Tips・運用方法:ラベル設計のベストプラクティスやリテンション設定など効率的運用のポイント
最後に、Grafana Lokiを実際に運用していく上でのTips(コツ)やベストプラクティスを紹介します。ラベル設計、ログ保持戦略、Loki自身の監視、スケールアウト時の考慮事項、セキュリティ面の対策など、効率的かつ安定したLoki運用のために知っておくべきポイントをまとめます。
ラベル設計のベストプラクティス:高カーディナリティを避け効率的なフィルタを実現
Grafana Lokiの性能とコストに大きく影響するのがラベルの設計です。適切なラベル設計により、必要なログを効率よく検索でき、無駄なリソース消費を防げます。基本指針として、ラベルの値の種類(カーディナリティ)はできるだけ低く抑えることが重要です。具体的には、数十種類程度に収まる静的な属性(例:サービス名、ホスト名、環境名など)はラベルに適していますが、リクエストIDやユーザIDのように理論上無限に増えうる値はラベルにすべきではありません。そうした動的な値をラベル化すると、インデックスが爆発的に増えてストレージやメモリを圧迫し、クエリ性能も低下します。
代替策として、カーディナリティの高い情報はログ本文に残し、検索時に|=や|~でテキストフィルタするようにします。また、Prometheusでも言われるように「静的ラベルは善、動的ラベルは悪」という考え方がLokiにも当てはまります。例えばホスト名やアプリ名は固定集合なのでラベルとして有用ですが、タイムスタンプやランダムIDなど無限集合は避けます。どうしても必要な場合はprefixを付けてある程度集合を限定する工夫も考えられます。
さらに、ラベル数そのものも増やしすぎないよう留意します。1ログストリームに関連付けるラベルキー数が多すぎると、インデックスサイズが増し管理が複雑になります。必要最低限の属性に絞り、あとは| json等で動的に引き出せば良い場合も多いです。これらラベル設計のベストプラクティスを守ることで、Lokiのパフォーマンスを最大限引き出し、運用時のトラブルを未然に防止できます。
ログ保持期間(リテンション)管理:データ量に応じた保存期間設定と削除方法
Grafana Lokiで扱うログデータは際限なく増えていくため、ログの保持期間(Retention)の設定が不可欠です。適切な保持期間を設けることで、ストレージ使用量をコントロールしコストを抑えられます。Lokiでは設定ファイルのtable_manager.retention_deletes_enabled等の項目を有効にし、retention_periodで期間を指定することで、古いログデータを自動削除できます。たとえば90日保管と決めた場合、90日を過ぎたデータはバックグラウンドで順次削除されます。
注意点として、Retention削除は即時ではなく、Compactor(またはTable Manager)が定期的に実行するクリーンアップ処理によって行われます。そのため実際の削除タイミングには多少ラグがある可能性があります。Criticalなログは長めに保持し、冗長なデバッグログは早めに捨てるなど、ログ種別に応じて期間を変えることも考えられます(現状Lokiではストリームごとに異なる保持期間を設定するのは難しいため、Promtail側でそもそも収集対象から外すのが現実的です)。
また、手動で特定期間のログを消去したい場合は、Loki APIのDelete機能もあります。テナント単位でクエリ条件を指定し、その条件にマッチするログを削除するAPIですが、使用には慎重さが求められます。一般的にはRetention設定で十分な場合が多いでしょう。適切なログ保持戦略を取ることで、Lokiクラスタのサイズ管理が容易になり、長期的な運用コストを予測可能にできます。
Loki自体の監視とメトリクス:PrometheusメトリクスでLokiのパフォーマンスを可視化
Grafana Lokiを安定運用するには、Lokiそのものの状態を監視することも重要です。LokiはPrometheus形式のメトリクスを多数エクスポートしており(/metricsエンドポイント)、これを収集・可視化することでLokiクラスタの健全性を把握できます。例えば以下のようなメトリクスが提供されています:
loki_ingester_ingested_entries_total(Ingesterが受け取ったログエントリ数)loki_ingester_chunk_store_total_failures(チャンク書き込み失敗数)loki_querier_request_duration_seconds(クエリ処理時間の分布)loki_request_duration_seconds(APIリクエスト全般のレイテンシ)loki_compactor_runs_total(Compactor実行回数と結果)
これらをPrometheusでスクレイプし、Grafanaダッシュボードでモニタリングすることで、Ingesterの負荷(受信レート)やクエリ応答性能、エラー発生状況などを追跡できます。例えば、ingested_entries_totalが通常より急増していればログ流入量増加の兆候ですし、クエリの95パーセンタイル応答時間が閾値を超えればアラート発報できます。
またLokiには専用のMixins(ダッシュボードテンプレート集)もコミュニティから提供されています。これらを使えば、Loki監視用の標準ダッシュボード(例えばIngesterのメモリ使用量、書き込みエラー数、クエリ成功率などをまとめたもの)を手早く導入できます。結局のところ、Lokiも一つのサービスであり、その挙動を可観測化することが安定運用には不可欠です。メトリクス監視を通じてボトルネックや異常を早期発見し、必要ならスケールアウトや設定変更で対処すると良いでしょう。
スケールアウト時の注意点:マイクロサービス構成への移行と各コンポーネントのリソース確保
運用中にログ量が増えたりユーザが増えてきた場合、Grafana Lokiクラスタのスケールアウトが視野に入ります。単一プロセスで動かしていたものを役割ごとに分離し、それぞれ複数レプリカにすることで性能と可用性を上げるアプローチです。スケールアウト時に注意すべきは、各コンポーネント間の設定整合性とリソース配置です。
例えばIngesterを3台にスケールするなら、Distributorの設定でReplicas=3、Quorum=2(3台中2台書き込めれば成功)などを正しく設定します。また、全Ingesterが同一データにアクセスするためにConsistent Hashリング情報を全ノードで共有する必要があります(EtcdやMemberlistで自動同期されます)。Querierを増やす場合はQuery Frontendを導入してクエリ分散処理・結果キャッシュをさせると効果的です。
リソース確保面では、各コンテナに十分なCPU・メモリを割り当て、ストレージIO帯域も考慮します。特にIngesterはメモリ上にデータを溜め込むため、OOMで落ちないよう余裕を持ったメモリ設定が必要です。Kubernetes環境ならRequests/Limitsで適切に制限します。さらに、スケールアウト時はデータの再シャーディングにも留意しましょう。例えばIngester台数変更時には一時的にデータの再配置負荷がかかるため、ログ流入が少ない時間帯に行うか、段階的に増やすといった工夫が望ましいです。
最後に、水平スケールだけでなくバージョンアップや設定変更時のローリングアップデート手順も確立しておくと安心です。一般にLokiは後方互換に気を遣ってはいますが、メジャーバージョンアップではストレージ形式変更があることもあります。その場合は移行ツールや一時的な併設運用が必要です。スケールアウトとアップデートを安全に行う手順をドキュメント化しておくことで、将来的な運用リスクを低減できるでしょう。
認証とアクセス制御:マルチテナント環境でのプロキシ認証や権限管理の実装
Grafana Lokiを社内外で提供する際には、アクセス制御とセキュリティにも配慮が必要です。前述したようにLoki自体にはユーザ認証機能が無いため、基本的にはフロントに認証プロキシを立てて保護します。たとえば、OAuth2 ProxyやIngress ControllerでOIDC認証をかけてからLokiにリクエストを転送する構成などが一般的です。Grafanaを通じてLokiを使わせる場合は、Grafana側のデータソース権限(Org単位やFolder単位の権限管理)で間接的にコントロールすることもできます。
また、マルチテナント機能を利用している場合は、正しくテナントIDが付与されるようにすること、そして各テナントのAPIキー管理を徹底することが重要です。認証プロキシがリクエストヘッダX-Scope-OrgIDに適切なテナントを設定しなければ、他テナントのログが見えてしまう恐れがあります。Grafana経由ならその辺りは抽象化されますが、直接APIを使わせる場合はドキュメントを用意しておくべきでしょう。
通信経路の暗号化も忘れてはいけません。Lokiとの通信はHTTPなので、内部利用であってもTLS終端を設けるか、ネットワークを信頼できる範囲に限定することが求められます。最後に、Lokiの設定で不要な機能(例えば一部のAPIエンドポイントやデバッグ機能)を無効化することも検討してください。デフォルトでは深刻な脆弱性は報告されていませんが、安全な構成で運用するに越したことはありません。
以上、Grafana Lokiの運用に関するTipsをいくつか紹介しました。これらを踏まえて運用することで、Lokiの利点を最大限に引き出しつつ、安全で効率的なログ管理基盤を維持できるでしょう。
Docker Composeを使ったGrafana Loki構築例:Loki・Promtail・Grafanaを活用したローカル環境でのログ基盤構築手順
最後に、Docker Composeを用いてGrafana Lokiの一式(Loki本体、Promtail、Grafana)をローカル環境に構築する具体例を紹介します。Docker Composeを使えば複数のコンテナを簡単に連携させて起動できるため、Lokiスタックのテストや検証に適しています。ここではComposeファイルの内容と各サービスの設定ポイント、起動方法を順を追って説明します。
Lokiスタックの概要:Docker ComposeでLoki+Promtail+Grafanaを構築する手順
Docker Composeを使用したLokiスタック構築では、ひとつのdocker-compose.ymlファイルにLoki、Promtail、Grafanaの3つのサービス定義を書き込みます。Composeファイルのフォーマットはバージョン3以上を使用し、各サービスにイメージと必要な設定を指定します。全体の流れとしては、Composeファイルを用意しdocker-compose up -dで一括起動、GrafanaでLokiデータソースを追加、Promtailがホストログを収集してLokiへプッシュ、Grafanaからログ確認という手順になります。以下でComposeファイルの内容を詳しく見ていきましょう。
docker-compose.yml準備:Loki・Promtail・Grafanaサービス定義と設定ファイル
まずdocker-compose.ymlを作成します。内容の例を以下に示します。
version: '3' services: loki: image: grafana/loki:latest container_name: loki ports: - "3100:3100" volumes: - ./loki-config.yml:/etc/loki/local-config.yaml command: -config.file=/etc/loki/local-config.yaml
promtail: image: grafana/promtail:latest container_name: promtail volumes: - /var/log:/var/log - ./promtail-config.yml:/etc/promtail/config.yml command: -config.file=/etc/promtail/config.yml
grafana: image: grafana/grafana:latest container_name: grafana ports: - "3000:3000" volumes: - grafana_data:/var/lib/grafana environment: - GF_SECURITY_ADMIN_PASSWORD=admin
volumes: grafana_data:
上記のCompose定義では、3つのサービスが定義されています。lokiサービスでは、最新Lokiイメージを使いポート3100をホストに公開、カレントディレクトリのloki-config.ymlをコンテナ内/etc/loki/local-config.yamlにマウントして起動しています。promtailサービスでは/var/logディレクトリ(ホストのログディレクトリ)をコンテナにマウントし、Promtail設定ファイルもマウントして起動します。grafanaサービスではGrafanaのポート3000を公開し、永続ボリュームgrafana_dataをマウントして状態保持、環境変数で初期パスワードを設定しています。
Composeファイル作成後、同じディレクトリにloki-config.ymlとpromtail-config.ymlも用意します。Lokiの設定ファイルは簡易的にはauth無効、ローカルファイルシステムにデータ保存など最小限で構いません。Promtailの設定では、先程のCompose定義ではjob: varlogs、パス/var/log/**.gz(例として圧縮ログも対象)などが記載されています。自分の環境に合わせ、例えば/var/log/*.logなど実際のログファイルパスを指定しましょう。
Lokiコンテナの設定ポイント:ポート3100とローカル設定ファイルのマウント
Lokiコンテナでは、ポート3100を開放する必要があります。3100はLokiのHTTP API(Push受信やQuery)のデフォルトポートです。Composeでは"3100:3100"と指定することで、ホスト側からlocalhost:3100でLokiにアクセス可能になります。また、設定ファイルlocal-config.yaml(またはloki-config.yml)を正しくボリュームマウントし、コマンドライン引数-config.file=/etc/loki/local-config.yamlを渡している点も重要です。これにより、コンテナ内でデフォルト設定ではなくカスタム設定が反映されます。
ローカル環境テスト用の設定では、例えば認証無効(auth_enabled: false)、ストレージはファイルシステム(filesystem指定)で./dataディレクトリに保存、Retentionなし、といったシンプルな構成にすると良いでしょう。IngesterやQuerierも単一プロセス内に収まる単純モードです。Composeで起動したLokiが正常にReadyになると、前述の通りcurl http://localhost:3100/readyがreadyを返すはずです。
Promtailコンテナの設定ポイント:ホストの/var/logマウントとジョブラベル設定
Promtailコンテナでは、ホストのログディレクトリをマウントして中のログファイルを読めるようにする必要があります。Compose例では- /var/log:/var/logとボリューム指定しており、ホストの/var/log内のファイルがコンテナ内でも同じパスで見えるようになります。これにより、例えば/var/log/syslogや/var/log/nginx/access.logといったファイルをPromtailが検出できます。
Promtailの設定ファイルではscrape_configsで読み取り対象ファイルパスやラベルを定義します。例ではjob_name: system配下にstatic_configsとしてターゲットlocalhostとラベルjob: varlogs、パターンpath: /var/log/*.gzが書かれています。これは/var/log配下のgz圧縮ファイルを対象にする設定ですが、必要に応じ.logなどに変更します。またmultiline設定でスタックトレースを一つのログにまとめる等、要件に応じて調整します。
Compose環境では、Promtailはloki:3100(Compose内のサービス名を使ったアドレス)にログを送り込むため、設定ファイルのclients.urlはhttp://loki:3100/loki/api/v1/pushとなります。Grafana Labs公式のPromtail設定例も参考に、自分のログに合わせてラベル付けやフィルタリングを工夫しましょう。
GrafanaコンテナとLoki連携確認:ポート3000で起動しデータソース接続テスト
Grafanaコンテナは、Compose起動後にlocalhost:3000でWeb UIにアクセスできます。先述のように初期ログイン後、Lokiをデータソースに追加する作業を行います。Compose例では環境変数で管理者パスワードをadminに設定しているため、ログインもスムーズです。Grafanaに入ったら、「Configuration > Data Sources」からLokiデータソースを追加し、URLをhttp://loki:3100と指定して保存・テストします。Compose内ではGrafanaコンテナから見てlokiというホスト名で通信できるので、このように設定します。
接続が成功したら、GrafanaのExploreで{job="varlogs"}などとクエリを入れてみましょう。Promtailが収集してLokiに送ったホストログが表示されるはずです。たとえばsyslogの内容や、auth.logの内容がラベルjob=varlogs付きで確認できます。これでDocker Composeを使ったローカルLoki環境の構築例は完了です。
このCompose構成はあくまでテスト・学習用途ですが、本番に近い形でLokiスタックを体験できるため非常に有用です。各コンポーネントの設定調整も容易なので、まずはこの環境で色々なLogQLクエリを試したり、Promtail設定を変更してみたりして、Grafana Lokiの挙動を掴んでみてください。
まとめ:Grafana Lokiは、ラベルベースのログ管理による高いコスト効率とスケーラビリティを持ち、モダンなクラウド環境でのログ監視に適したプラットフォームです。本記事ではその概要から導入手順、特徴、クエリの使い方、応用テクニック、運用のポイント、そして具体的な構築例まで幅広く解説しました。エンジニアの皆様がGrafana Lokiを活用して効率的なログ可観測性を実現する一助になれば幸いです。
Grafana Lokiに関するよくある質問
Grafana Lokiの読み方は?
「グラファナ・ロキ」と読みます。Lokiは北欧神話の神の名に由来し、開発元のGrafana Labsが手掛けるログ基盤の名称です。
LokiとPrometheusの違いは何ですか?
Prometheusは数値の時系列(メトリクス)を、Lokiはテキストのログを扱うツールで、役割が異なります。ただし両者ともラベルでデータを整理する設計思想を共有しているため、同じラベルでメトリクスとログを突き合わせて調査でき、Grafana上で組み合わせて使うのが一般的です。競合ではなく補完関係にあります。
LogQLとは何ですか?
LogQLはGrafana Lokiのログ検索・集計に使う専用のクエリ言語です。PrometheusのPromQLに似た構文で、まずラベルセレクタ(例:{app="nginx"})で対象ログを絞り込み、フィルタやline_format、集計関数をパイプラインでつないで抽出・可視化します。
Grafana Lokiは無料で使えますか?
OSS版のGrafana LokiはAGPLv3(オープンソースライセンス)のもとで無料で利用でき、自前のサーバーやKubernetesにセルフホストできます。運用を任せたい場合は、無料枠と有料プランを持つマネージドサービスのGrafana Cloud(Loki)を選ぶこともできます。
LokiとElasticsearch(ELK)はどう違いますか?
Elasticsearchはログ本文を全文インデックスするため高度な全文検索が得意な一方、インデックスのストレージと運用コストが大きくなりがちです。Lokiはラベルのみを索引し本文はそのまま圧縮保存するため、コストと運用負荷を抑えられます。既存のログ資産を全文検索したいならELK、コスト効率とGrafana連携を重視するならLokiが向いています。