開発環境を劇的に良くするCloudWatch術

# はじめに

開発環境でこんな経験はありませんか？

「システムのパフォーマンスが急に低下して原因がわからない…」
「Slackにエラー通知システム入れてみたけどログが分かりにくい…」
「エラーが発生したけど、どこをチェックすればいいのかわからない…」
「リアルタイムでログを監視して、即座に対応したい…」

これらの悩み、まさに多くの開発者が抱えるものですよね。

そんな皆さんに朗報です！
AWSのCloudWatchを活用すれば、これらの問題を解決し、<font color="Red">**開発環境を劇的に改善することができます。**</font>
今回は、CloudWatchの「サブスクリプションフィルター」「ライブテール」「Logsインサイト」といった機能を使って、効果的にシステムの監視を行う方法をご紹介します。

# どのようなことができるのか

例えば、CloudWatchの「サブスクリプションフィルター」を使えば、**特定のログイベントをリアルタイムでキャッチし、自動的に通知を送るシステムを作ることができます。**

![スクリーンショット 2024-07-05 10.15.29.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/5adf7dec-6335-d996-a945-7d3aaab0816c.png)

サブスクリプションフィルターを活用してLambdaでエラー通知の内容を整形することも可能です。
これにより、エラー内容がより見やすくなり、ログ調査の負担が大幅に軽減されます。

![スクリーンショット 2024-07-05 10.09.47.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/502656c0-ecf5-2b3d-21a3-31e4c6df5dff.png)



# サブスクリプションフィルター

サブスクリプションフィルターは、CloudWatch Logs内のロググループに対してリアルタイムで特定の条件に一致するログイベントをキャプチャし、他のAWSサービスに転送するための設定です。
この機能を利用することで、ログデータをリアルタイムで処理し、必要なアクションを自動化することが可能になります。
つまり、<font color="Red">**サブスクリプションフィルターは特定のログが出た時にLambdaを起動**</font>できたりします！（Lambda以外もできます。）

# 

### 基本概念
| 項目              | 説明                                                                                                                                                       |
| ----------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------- |
| **ロググループ**   | ログのコレクションをグループ化するためのコンテナ。ロググループは、アプリケーションやサービスごとに作成されます。                                           |
| **ログストリーム** | 各ロググループ内の個別のログファイル。例えば、EC2インスタンスやLambda関数ごとに作成されます。                                                               |
| **フィルターパターン** | 特定のログイベントを識別するための条件。フィルターパターンは、JSON形式のログデータを解析し、特定のフィールドや値に基づいてログイベントをキャプチャします。                                  |
| **宛先**           | フィルターパターンに一致したログイベントを送信する先。典型的な宛先には、AWS Lambda関数、Amazon Kinesisストリーム、Amazon Elasticsearch Serviceなどがあります。 |


### 使用方法
マネージドコンソールから簡単に使用することができます。
**ロググループを選択し、サブスクリプションフィルターボタンを押します。**
今回はLambdaを例に説明します。

:::note warn
事前にLambdaを作成してARNがある状態にしてください。
:::

![スクリーンショット 2024-07-03 16.45.21.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/d9514dbf-128e-4d04-f547-b5469de07de1.png)

サブスクリプションフィルターの設定は、以下のステップに従って行います。

#### Step1: ロググループの選択

サブスクリプションフィルターを設定したいロググループを選択します。

#### Step2: フィルターパターンの作成

キャプチャしたいログイベントに対応するフィルターパターンを作成します。例えば、エラーログをキャプチャする場合、ERRORや特定のエラーメッセージに一致するパターンを指定します。

#### Step3: 宛先の設定

フィルターパターンに一致したログイベントを送信する宛先を指定します。ここでは、AWS Lambda関数やKinesisストリームなどを設定します。

#### Step4: フィルターの適用

設定を保存し、サブスクリプションフィルターを有効化します。

### マネージドコンソール画面操作

LambdaのARNを設定してください。フィルターに指定した文字が出た場合にLambdaが起動します。

![スクリーンショット 2024-07-03 16.50.02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/16a18ef8-5a5d-ee95-8d48-3637ec7bb005.png)

次にフィルターの条件を指定します。今回は<font color="Red">「ERROR」</font>という文字が含まれる場合に動くようにします。

![スクリーンショット 2024-07-03 18.17.22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/dce0f9aa-8ce2-7ee8-b343-01ccbc99b32b.png)

パターンテストは実施しなくても作成することができます。今回は省略して「ストリーミングを開始」を押します。
これでサブスクリプションフィルターの設定は完了です。
<font color="Red">「ERROR」というログが出た場合に指定したLambdaが動く</font>設定ができました。

![スクリーンショット 2024-07-03 18.24.53.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/7ae32561-4d15-c30e-1911-e464ed364838.png)

### Lambdaサンプル
AWS CloudWatch Logsのサブスクリプションフィルターを使用してログデータを処理するAWS Lambda関数のサンプルです。このLambda関数は、サブスクリプションフィルターによって送信された圧縮ログデータを受信し、解凍して解析します。

```JavaScript
exports.handler = async (event) => {
  console.log(`EVENT: ${JSON.stringify(event)}`);
  console.log(event.awslogs.data);
  const decordData = Buffer.from(event.awslogs.data, "base64");

  // GZIP 圧縮されたデータを非同期にデコード
  const decompressedData = await new Promise((resolve, reject) => {
    zlib.unzip(decordData, (err, buffer) => {
      if (err) {
        reject(err);
      } else {
        resolve(buffer.toString("utf-8")); // デコードされたデータを文字列として解析
      }
    });
  });
  console.log(decompressedData);
  const parsedData = JSON.parse(decompressedData);

  console.log("デコードされたデータ:", parsedData);
}
```

AWS CloudWatchのサブスクリプションフィルターを利用することで、ログデータをリアルタイムで処理し、効率的なログ管理と監視を実現できます。
AWS Lambdaを活用することで、特定の条件に一致するログイベントに対するリアルタイムな対応が可能となり、システムの信頼性向上や迅速な問題解決が期待できます。

# CloudWatch ライブテール

AWS CloudWatchのライブテール機能は、CloudWatch Logsでリアルタイムにログを監視するための機能です。
これにより、アプリケーションの動作状況を即座に確認し、問題が発生した際に迅速に対応することができます。開発や運用の場面で非常に有用なツールです。
つまり、<font color="Red">**CloudWatch ライブテールはログを探しに行くことなく、リアルタイムにログを監視する**</font>ことができます。
AWS SUMMIT 2024のミニステージで初めて知った機能で、使いやすく開発効率も大幅に上がったためおすすめです。

https://aws.amazon.com/jp/summits/japan/

## ライブテールの使用例

#### 1. 開発中のアプリケーションのデバッグ

新しいコードをデプロイした後、そのコードが期待通りに動作しているかをリアルタイムで確認することができます。エラーメッセージやデバッグ用のログを即座に確認できるため、問題の特定と修正が迅速に行えます。

#### 2. パフォーマンス監視

アプリケーションのパフォーマンスに関するログをリアルタイムで監視し、パフォーマンスのボトルネックや異常を早期に発見することができます。これにより、必要な調整を迅速に行うことができます。

#### 3. セキュリティ監視

セキュリティ関連のログイベント（例：アクセス拒否、異常なログイン試行など）をリアルタイムで監視することで、セキュリティインシデントに対する迅速な対応が可能になります。


### マネージドコンソール画面操作

こちらも使用方法は非常に簡単です。
AWS Management Consoleにログインし、サービス一覧から「CloudWatch」を選択します。
**CloudWatchコンソールの左側のメニューから「ライブテール」を選択します。**

![スクリーンショット 2024-07-04 15.07.02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/5c5bfc22-21d9-4d6a-6975-bfd72a30e966.png)

ライブテールで出力したいロググループを選択します。最大10個のロググループを出力することができます。

CloudWatchのライブテール機能を使うと、<font color="Red">リアルタイムで複数のロググループを一箇所に集約して監視する</font>ことができます。これは、特に複数のLambda関数や他のリソースからのログをまとめて確認したい場合に非常に便利です。

ロググループを選択したら「フィルターを適用」を押して、準備完了です。

![スクリーンショット 2024-07-04 15.56.14.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/dfce4450-8a3f-6d9d-87e8-1b4201ce97c4.png)

コードを実行すると以下のようにログがリアルタイムに出力されます。

![スクリーンショット 2024-07-04 17.12.52.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/f69abe07-6bf1-53b2-5434-f90a79c278d5.png)

また、ログイベントのフィルタリングをすることで対象の文字が入ったものだけを出力することが可能です。
今回は「test」をフィルタリングしてみました。
**「ERROR」や「test」などを仕込むことによって、必要なログ情報だけを取り出す**ことができます。

![スクリーンショット 2024-07-04 17.21.42.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/49a5f77b-f3bb-241f-6053-44b187c99b93.png)

CloudWatchのライブテール機能を使用すると、アプリケーションやシステムのログデータをリアルタイムで監視し、問題が発生した際に迅速に対応することができます。
上記の手順を参考にして、AWSマネジメントコンソールでライブテールを設定し、活用してください。

# CloudWatch Logsインサイト

ログデータをクエリして詳細な分析を行うための機能です。
ログデータから特定の情報を抽出し、視覚化することで、システムの状態やパフォーマンスの把握が容易になります。
<font color="Red">**CloudWatch Logs Insightsは欲しい条件と時間でログを抽出できます。**</font>

## 主な機能

#### 1. クエリベースのログ検索

ログデータに対してSQLライクなクエリを実行し、特定の条件に一致するログエントリを抽出します。

#### 2. 対象となるログの日時指定

検索したい日時を限定することが可能です。

#### 3. 保存されたクエリ

頻繁に使用するクエリを保存しておくことができ、再利用が容易になります。

## マネージドコンソール画面操作

AWS Management Consoleにログインし、サービス一覧から「CloudWatch」を選択します。
**CloudWatchコンソールの左側のメニューから「ログのインサイト」を選択します。**

![スクリーンショット 2024-07-04 18.19.25.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/77f3257b-17df-fcde-14e4-12e94ea490c9.png)

クエリを実行したいロググループを選択します。複数のロググループを同時に選択することも可能です。

### グループとクエリの設定

ログデータに対して実行したいクエリを作成します。Logs Insightsのクエリ言語は、SQLに似た簡潔な文法を持っています。以下にクエリ例を示します。
**「test」という文字が含まれたログを検索**します。

```
fields @timestamp, @message, @logStream, @log
| sort @timestamp desc
| filter @message like /test/
```

![スクリーンショット 2024-07-04 18.40.02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/94ae229e-8773-4c92-cfa2-2d732da1f0c4.png)


### 対象となるログの日時指定

**時間の設定は相対値と絶対値**で選択することができます。

![スクリーンショット 2024-07-04 18.35.46.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/c03455d2-837f-12ae-357c-7c6e30c0a9d7.png)

#### 相対値

CloudWatch Logs Insightsでは、クエリの実行範囲を簡単に設定するために、デフォルトの時間範囲を指定するオプションがあります。
これには、1時間、3時間、12時間、1日、3日、1週間などのプリセットが用意されています。
カスタムを選択することでより詳細な設定が可能です。

![スクリーンショット 2024-07-04 18.47.59.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/f14c5198-4d76-dec6-fa72-3ccfa94813e0.png)

#### 絶対値

カレンダーと時間選択ツールを使用して、クエリの開始時間と終了時間を設定します。
例えば、「開始時間」を2024年6月17日午前00:00、「終了時間」を2024年6月23日午後23:59と設定します。
検索したいログの日時がわかっている場合はこちらを使うことをおすすめします。

![スクリーンショット 2024-07-04 18.54.13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/0d7ae030-7ccd-c9df-3dee-39006becc774.png)

### クエリの実行

ロググループの選択、クエリの設定、時間範囲の選択が完了したら「適用」を実行することでログの検索ができます。

![スクリーンショット 2024-07-04 19.01.39.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/f8935d33-c448-b1d3-f683-a52aea2e4cd4.png)

クエリの実行結果です。
結果を視覚的に理解しやすくするため、グラフやチャートとして表示することができます。

クエリの実行結果がリスト形式で表示されます。**各ログエントリにはタイムスタンプ、メッセージ、その他のフィールド**が含まれます。
この検索は分散処理されるため、膨大な量のログデータでも迅速に処理されます。

![スクリーンショット 2024-07-04 19.06.58.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/7997bae5-afdb-2a14-4c8c-ca12f5b078db.png)

### クエリの保存

実行したクエリを保存して、後で再利用できるようにします。
クエリ実行の横にある「保存」ボタンをクリックし、クエリの名前と詳細を入力して保存します。

![スクリーンショット 2024-07-04 19.16.35.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/d4812ab7-bca7-e6da-5dc8-7bffa7568013.png)

「保存」ボタンをクリックすると、クエリの保存ダイアログが表示されます。ここで、以下の情報を入力します。

| 項目           | 説明                                                                                                                         |
| -------------- | ---------------------------------------------------------------------------------------------------------------------------- |
| **名前**       | 保存するクエリの名前を入力します。この名前はクエリを識別するために使用されます。                                                |
| **ロググループ** | クエリが適用されるロググループを選択します。複数のロググループにまたがるクエリを保存する場合は、それぞれのロググループを選択します。 |
| **クエリ** | 実際のクエリテキストが表示されます。このクエリテキストを編集することも可能です。                                             |


![スクリーンショット 2024-07-04 19.17.50.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/114ac0a4-1ed7-c3ba-d532-b87ac0adb17f.png)

### 保存したクエリの参照

ログインサイトの画面の右側に「クエリ」というセクションがあります。
ここに、以前保存したすべてのクエリが表示されます。

先ほど保存したクエリ「test」をクリックします。この操作により、「test」という名前で保存されたクエリの詳細が表示されます。
これにより、保存されたクエリを再利用してログデータを効率的に分析できます。

![スクリーンショット 2024-07-04 19.26.09.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1991303/bd84651a-f30f-73f4-bd23-ba3019211da3.png)

# まとめ

AWS CloudWatchのサブスクリプションフィルター、ライブテール、ログインサイトの機能を活用することで、ログ管理とリアルタイムモニタリングを効果的に行うことができます。
これにより、**開発効率を大幅に向上させ、迅速なデバッグやインシデント対応が可能となります。**
これらの機能を効果的に活用して、より信頼性の高いシステム運用を目指しましょう。