0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

【初級者向け】ECSのログ収集とFireLens(Fluent Bit)入門 — なぜ標準ログだけでは足りないのか

0
Posted at

この記事で分かること

  • ECSの標準のログ機能(awslogs)で「何ができて、何ができないのか」。
  • できないことを補う FireLens(Fluent Bit) がどんな仕組みなのか。
  • 高負荷のときに「ログが消える」のはなぜか、どう備えるか。

はじめに:そもそも「ログ」って何?

アプリケーションは動いている間、「いま何をしているか」「エラーが起きた」といったメッセージを文字として出力します。これが ログ です。

プログラムが文字を出す場所は、主に次の2つです。

  • 標準出力(stdout) — 通常のメッセージを出す場所
  • 標準エラー出力(stderr) — エラーメッセージを出す場所

私たちがパソコンでプログラムを動かすと、これらは画面(ターミナル)に表示されます。
でも、AWS の ECS(コンテナを動かすサービス)の上でアプリを動かすと、画面はありません。ではログはどこへ行くのか? これを解決するのがこの記事のテーマです。

用語メモ

  • コンテナ … アプリと、その動作に必要なものを1つの箱にまとめて、どこでも同じように動かせるようにした技術。
  • ECS(Elastic Container Service) … AWS上でコンテナを動かしてくれるサービス。
  • CloudWatch Logs … AWSの「ログの保管・閲覧サービス」。ログの最終的な置き場所としてよく使われる。

1. ECS標準のログ:awslogs ドライバ

ECSには、コンテナのログを CloudWatch Logs に送る標準機能があります。これを awslogs ドライバ と呼びます。

用語メモ:ログドライバとは?
コンテナが出したログ(stdout/stderr)を「どこへ・どうやって」運ぶかを決める仕組みのこと。
「ログの宅配業者」をイメージすると分かりやすいです。awslogs は「CloudWatch Logs 専門の宅配業者」です。

awslogs はとてもシンプルで、設定もかんたんです。

アプリのログ(stdout/stderr)
   → awslogsドライバ
   → CloudWatch Logs に届く

要件がシンプルなら、これで十分です。 わざわざ次に説明する FireLens を使う必要はありません。

でも、こんな要望が出てくると困る

プロジェクトが育つと、こんな声が出てきます。

  • 「ログを CloudWatch だけでなく S3 にも 保存したい」
  • 「ログを 外部の監視サービス(SaaS) にも送りたい」
  • 「不要なログを 間引いて 料金を下げたい」
  • 「ログにフィールドを足したり、JSONとして整形 したい」
  • 「エラーのスタックトレース(複数行)を 1件のログにまとめたい

awslogs は「CloudWatch Logs にそのまま送るだけ」なので、これらは一切できません
送り先は固定、加工もできない。ここで登場するのが FireLens です。


2. FireLens とは何か(いちばん大事なところ)

初級者がまず誤解しやすいポイントです。

FireLens は「新しいログサービス」ではありません。

FireLens の正体は、次の2つを合わせた 仕組みの呼び名 です。

  1. Fluent Bit(または Fluentd)という、ログを集めて振り分けるソフトを動かす「サイドカーコンテナ」
  2. ECSが、その設定ファイルを自動で作ってくれる仕組み

用語メモ:サイドカーコンテナとは?
メインのアプリコンテナの「お供」として、同じタスク内で一緒に動く補助コンテナのこと。
バイクの横についている「サイドカー」が由来。ここでは「ログ集め係」のお供コンテナです。

用語メモ:Fluent Bit とは?
ログを「受け取って・加工して・いろんな宛先に振り分ける」ための軽量なソフト。
同種のソフトに Fluentd(Ruby製)もありますが、Fluent Bit は C言語製で軽くて速いため、ECSではこちらが主流です。

登場人物は3つ

FireLens を使うときに出てくる構成要素は、次の3つだけです。

登場人物 役割 たとえ
アプリコンテナ ログを出す本体 手紙を書く人
ログルーターコンテナ(Fluent Bit のサイドカー) ログを受け取り、振り分ける 郵便局の仕分け係
タスクIAMロール 宛先に書き込む「権限」 宛先に入るための通行証

用語メモ:IAMロールとは?
AWSで「このリソースは、こういう操作をしてよい」という権限のまとまり。
ログを S3 や Firehose に送るには「送ってよい」という許可(権限)が必要です。これが無いと、いくら設定しても送れません。


3. ログはどんな道を通るのか(経路)

FireLens を使ったとき、ログは次のように流れます。

アプリのログ(stdout/stderr)
  → awsfirelens(ログドライバ)
  → ログルーターコンテナ(Fluent Bit)が受け取る
  → Fluent Bit が一時的にためる(バッファ)
  → 複数の宛先へ振り分け(CloudWatch / S3 / Firehose / 監視SaaS など)

ポイントは「ログルーター(仕分け係)がいったんログを受け取り、必要なら加工して、複数の宛先へ配る」という流れです。
awslogs(CloudWatch直行便)と違い、行き先を増やしたり加工したりできるのが分かります。

用語メモ:バッファとは?
受け取ったものを、すぐに送らずいったん貯めておく場所のこと。
宅配で言えば「集荷した荷物を、トラックが出発するまで置いておく倉庫」。
Fluent Bit はログを少しずつまとめて(chunk=かたまり、という単位で)宛先へ送ります。

おまけ:勝手に付くメタデータ

FireLens を使うと、各ログに「どのクラスタ・どのタスクから来たか」といった情報が自動で付きます。あとから「これはどのコンテナのログ?」と追跡しやすくなります。

付くキー 内容
ecs_cluster クラスタ名
ecs_task_arn タスクの識別子(ARN)
ecs_task_definition タスク定義名とリビジョン
ec2_instance_id 動いているEC2のID(※EC2起動タイプのときだけ。Fargateでは付かない)

出典
 Amazon ECS タスク定義の例: FireLens にログをルーティングする


4. 高負荷のときに「ログが消える」のはなぜ?

FireLens 運用で最大の落とし穴がこれです。
大量のログが一気に流れると、ログが消えてしまうことがあります。 なぜでしょうか。

たとえ話:倉庫がパンクする

ログルーター(仕分け係)は、受け取ったログをいったん メモリ(作業机の上) にためてから宛先へ送ります。

  • 普段はすぐ送れるので、机の上はすぐ片付く。
  • でも、ログが大量に来たり、宛先が混んでいて送れないと、机の上に荷物がどんどん積み上がる。
  • 机のスペース(Mem_Buf_Limit)を超えると、新しい荷物を受け取れなくなり、あふれた分は捨てられます。 = ログ欠落。

Fluent Bit のログにはこんなメッセージが出ます。

[input] forward.1 paused (mem buf overlimit)

これは「メモリがいっぱいで受付を一時停止(pause)した」という意味です。pause している間のログは失われます。

さらに困ったことに、受付が止まるとアプリ側にも「ちょっと待って」という圧力(バックプレッシャー)がかかり、アプリの処理速度まで落ちることがあります。

用語メモ:メモリとディスクの違い

  • メモリ : 速いけど消えやすい作業スペース(机の上)。コンテナが再起動すると中身は消える。
  • ディスク(ファイルシステム) : 遅いけど消えにくい保管場所(引き出し)。再起動しても残る。

もうひとつの落とし穴:OOM(メモリ不足で強制終了)

宛先がダウンして送れない状態が続くと、メモリ上にログがたまり続けます。
やがてメモリを使い切ると、ログルーターコンテナが強制終了(OOMKill) され、メモリ上にあったログは丸ごと消えます。

用語メモ:OOM(Out Of Memory)とは?
「メモリが足りなくなった」状態。AWS/Linux はメモリを使いすぎたコンテナを強制終了して、システム全体を守ります。これを OOMKill と呼びます。


5. 解決策:メモリではなく「ディスク」にためる

ここまでの問題は、ほとんどが「メモリにためているから」起きています。
解決の方向性はシンプルで、ためる場所をメモリからディスク(ファイルシステム)に変えることです。

メモリにためる(既定) ディスクにためる(推奨)
速さ 速い やや遅い
大量ログ あふれると 欠落 ディスクに退避できる
宛先ダウン時 メモリ枯渇 → OOMで全消失 ディスクに貯めてゆるやかに耐える
再起動時 消える 残る

つまり、本番環境ではディスク(ファイルシステム)バッファが推奨です。

設定イメージ(いまは「こういう設定を足すんだな」と眺めるだけでOK):

[SERVICE]
    storage.path             /var/log/flb-storage/   # ディスクにためる場所
    storage.max_chunks_up    32                       # メモリに置く量の上限(OOM防止)
    storage.backlog.flush_on_shutdown On              # 停止時に残りを送り切る

[INPUT]
    Name forward
    storage.type filesystem   # ★ ここでディスクにためる指定
    threaded true

[OUTPUT]
    Name cloudwatch_logs
    Match *
    region us-west-2
    log_group_name /aws/ecs/my-app
    retry_limit 15                  # 送信失敗時のリトライ回数
    storage.total_limit_size 10G    # ディスク使用の上限(超えたら古い順に破棄)

ポイントだけ言葉にすると:

  • storage.type filesystem … ログをディスクにためる(これが一番大事)。
  • storage.max_chunks_up … メモリに置く量を絞ってOOMを防ぐ。
  • retry_limit / storage.total_limit_size … 宛先が落ちても粘れるようにする。

出典
 Amazon ECS で Fluent Bit のバッファ制限を構成する(公式の高スループット構成)
 ※ storage.max_chunks_up でOOMを防ぐ考え方は、AWS公式サンプル oomkill-prevention も参考になります(いまは「公式にもお手本があるんだな」とだけ覚えておけばOK)。

注意

Mem_Buf_Limit(メモリの上限)を大きくするのは、あくまで一時しのぎです。
根本対策は「ディスクにためる」こと。一時回避と恒久対策は分けて考えましょう。


6. トラブルが起きたら、まずどこを見る?

「アプリのログが宛先に届かない!」というとき、まず確認する順番です。

確認の基本ステップ:

  1. ログルーターコンテナがちゃんと起動しているか(アプリより先に立ち上がる設定になっているか)。
  2. IAMロールに、宛先へ書き込む権限があるか(権限が無いとそもそも送れない)。
  3. ログルーター自身のログpaused / retry / 権限エラーが出ていないか。
  4. 宛先側(CloudWatch や Firehose)が混雑(スロットリング)していないか。

大事な前提
FireLens/Fluent Bit には、AWS標準のCloudWatchメトリクスがありません
だから「ログルーター自身のログ」を見られるように、ログルーターコンテナにも awslogs を設定して、自分のログをCloudWatchに出しておくのが鉄則です。これを忘れると、トラブル時に何も見えません。


7. セキュリティで1つだけ覚えておくこと

Fluent Bit はログを受け取るために、内部的に ポート24224 を使います。

このポート24224を、外部からアクセスできるように開けてはいけません。

同じタスク内のアプリから内部的に使われるだけなので、外(インターネットや他サーバー)に開放する必要はありません。セキュリティグループで ingress(外からの受信)を開けないのが正解です。

出典
 Amazon ECS タスク定義の例: FireLens にログをルーティングする


まとめ

  1. awslogs … CloudWatch Logs に「そのまま送るだけ」の標準機能。シンプルな用途ならこれで十分。
  2. FireLens … 「複数の宛先に送りたい」「加工したい」「間引きたい」となったときに使う。正体は Fluent Bit のサイドカー + ECSの設定自動生成で、新しいサービスではない。
  3. ログの流れ … アプリ → ログルーター(Fluent Bit)→ いったんためる → 複数宛先へ。
  4. 高負荷でログが消えるのは、メモリにためていてあふれる(pause)か、メモリ不足で強制終了(OOM)するから。本番は ディスク(ファイルシステム)バッファ が推奨。
  5. トラブル時は ログルーター自身のログ を見る。そのためにログルーターにも awslogs を仕込んでおくこと。
  6. ポート 24224 は外に開けない

関連記事

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?