CloudwatchLogsのロググループ設計には気をつけよう
ロググループとログストリーム
CloudWatch logsにはロググループとログストリームという概念があり、公式ドキュメントでは以下のように定義されています。
ログストリームは、同じソースを共有する一連のログイベントです。CloudWatch Logs でのログの各ソースで各ログストリームが構成されます。 ロググループは、保持、監視、アクセス制御について同じ設定を共有するログストリームのグループです。ロググループを定義して、各グループに入れるストリームを指定することができます。
ロググループとログストリームの操作 - Amazon CloudWatch ログより
実際のログはログストリームに蓄積され、それらを集約したものがロググループとなります。
機能としてできること・できないこと
- ロググループに含まれるすべてのログストリームを横断して閲覧・フィルタリングすることができます。
- 単一のログストリームを閲覧・フィルタリングすることができます。
- 任意の複数のログストリームを横断して閲覧・フィルタリングすることはできません。
- 複数のロググループを横断してログを検索することができます。(Logs Insightsを利用)
おすすめの設計方針
ログの種類ごとにロググループを作成し、ログを出力するアプリケーションのインスタンスごとにストリームを作成することをおすすめします。要は、lambdaと同じ構成ですね。
ロググループ=アプリケーション、ストリーム=ログの種類(リクエストログ/エラーログ/etc.)と管理したくなる場合もありますが、後述のトラブルが起こりやすいのでおすすめしません。 もちろん、それらのトラブルパターンを回避や許容できる場合はこの限りではありません。
トラブルパターン1 : 対象のログを絞り込めず余計なログを検索してしまう
ログの検索範囲は、ストリーム単体かロググループに含まれるすべてのストリームを横断しての検索となります。ユースケースを想定してストリームを検討しないと、ログ検索がストレスとなってしまいます。
トラブルパターン2 : ログの書き込みでエラーが出る
ログストリームにログの出力を行う場合、sequence tokenを利用した書き込み順の管理が必要にになります。sequence tokenは直前のPutLogEventsかDescribeLogStreamsを利用して取得することができ、書き込みを行うたびに新しいsequence tokenが発行されます。 そのため、一つのログストリームに対して複数のインスタンスなどから同時にログの出力を行おうとした場合、sequence token取得のタイミングによってはエラーとなりログの出力を行うことができません。
そのため、Lambdaの同時実行などで複数インスタンスからログの出力を行いたい場合は、同一のログストリームに対して同時に複数のログ出力が行われないようにしましょう。 例えば、Lambdaのログ出力は関数ごとにロググループが生成され、関数のインスタンスごとにログストリームが生成されています。
トラブルパターン3 : クォータ制限にかかってしまう
CloudwatchLogsのPutEvents(≒ログ書き込み)にはクォータが設定されています。
CloudWatch Logs クォータ - Amazon CloudWatch Logs
特に、ログストリームあたりの毎秒5イベントは上限緩和できないので、スケーリングされたアプリケーションから同時に書き込みを行おうとするとすぐにこの上限にかかってしまいます。
おわりに
いかがだったでしょうか。自分も今回の記事を書くにあたって調べて見たところ、見落としていた内容もあったため勉強になりました。ログの構成は、一度決めてしまうとなかなか変えづらいと思います。この記事が少しでも皆さんの役に立っていただければ幸いです。