1
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

AWSで監視してアラートをメール送信する(4選)

Last updated at Posted at 2021-02-22

監視の種類

  • WAFトリガーの監視(ファイアウォール監視)
  • awslogsトリガーの監視(サーバーのログ監視)
  • CodePipelineトリガーの監視(デプロイ監視)
  • CloudWatchアラームの監視(サーバーの負荷監視)

WAFトリガーの監視

WAFログを監視してリクエストがブロックされたらメッセージ送信する。

監視の流れ

WAF Logs→KinesisFirehose→S3→Lambda→SNS→Eメール
                       →CloudWatchLogs

監視内容

WAFアクション「BLOCK」だったらメッセージ送信。
(WAFルールが「AWS-AWSManagedRulesAnonymousIpList」の場合、メッセージ送信しない。)

作る

※設定値を記載していない箇所はデフォルト値を使用している。

SNS
  • waf-monitoring-publish-sns
    • タイプ:スタンダード
    • サブスクリプション
      • プロトコル:Eメール
      • エンドポイント:waf@e2info.com

エンドポイントに指定したメールアドレス宛にメールが届くので「Confirm subscription」をクリック。
サブスクリプションのステータスが「保留中の確認」となっていたのが「確認済み」となればOK

S3バケット
  • aws-waf-logs
    • 設定はデフォルトのままでいい。
Kinesis Data Firehose
  • aws-waf-logs
    • Source:Direct PUT or other sources
    • S3 destination:aws-waf-logs
    • S3 buffer conditions:128 MiB or 900 seconds
    • S3 compression:GZIP

※バッファ間隔についてはテスト時は60秒にしても構わないが、本番運用時は900秒に設定する。

WAF
  • Block-Waftest
    • ルール:/waftestにアクセスしたらブロック
    • Priority:0

作成後、Logging and metricsタブの「Logging」で「Edit logging」をクリック

  • Logging details
    • Amazon Kinesis Data Firehose Delivery Stream
      • aws-waf-logs
Lamdba
  • waf-monitoring-publish-sns
    • 一から作成
    • ランタイム:node.js 10.x

Lambda関数作成後、

  • トリガーを追加。
    • S3バケットaws-waf-logs
    • イベントタイプ:PUT
    • サフィックス:.gzを指定

関数コードindex.jsに下記をペースト

index.js
const aws = require("aws-sdk");
const s3 = new aws.S3();
const sns = new aws.SNS({region: 'ap-northeast-1'});
const zlib = require('zlib');

exports.handler = (event, context, callback) => {
    const params = {
        Bucket: process.env.S3_BUCKET,
        Key: event.Records[0].s3.object.key
    };
    s3.getObject(params, (err, getData) => {
        if (err) {
            callback(err);
            return;
        }

        const body = getData.Body;

        zlib.gunzip(body, (err, data) => {
            if (err) {
                callback(err);
                return;
            }

            // gzip展開したデータを分割
            const logs = data.toString("utf-8").split('\n');

            // 通知対象のログをフィルタリング
            const blockLogs = logs.filter(function (evt) {
                return evt.match(/BLOCK|COUNT/);
            }).filter(function (evt) {

                let jsonEvt = JSON.parse(evt);
                let evtCountry = jsonEvt.httpRequest.country;
                let evtHost = null;
                let evtUA = null;
                let evtUri = jsonEvt.httpRequest.uri;
                let evtClientIP = jsonEvt.httpRequest.clientIp;
                for (const header in jsonEvt.httpRequest.headers) {
                    if (jsonEvt.httpRequest.headers[header].name == 'Host') {
                        evtHost = jsonEvt.httpRequest.headers[header].value;
                    }
                    if (jsonEvt.httpRequest.headers[header].name == 'User-Agent') {
                        evtUA = jsonEvt.httpRequest.headers[header].value;
                    }
                }

                console.log(evtCountry + "/" + evtHost + "/" + evtUA + "/" + evtUri + "/" + evtClientIP);

                if (evtCountry != 'JP') {
                    console.log('Not Notify(Country):' + evtCountry);
                    return false;
                }

                // このIPアドレスに対するブロックは通知しない(完全一致)
                if (process.env.DONT_NOTIFY_IPADDRESSES && evtClientIP) {
                    const dont_nofity_ipaddresses = process.env.DONT_NOTIFY_IPADDRESSES.split(',');
                    for (var dont_nofity_ipaddress of dont_nofity_ipaddresses) {
                        if (dont_nofity_ipaddress.indexOf(evtClientIP) != -1) {
                            console.log('Not Notify(IP):' + evtClientIP);
                            return false;
                        }
                    }
                }

                // このUAに対するブロックは通知しない(
                if (process.env.DONT_NOTIFY_USERAGENTS && evtUA) {
                    if (evtUA.indexOf(process.env.DONT_NOTIFY_USERAGENTS) != -1) {
                        console.log('Not Notify(UA):' + evtUA);
                        return false;
                    }
                }

                // このホストに対するブロックは通知しない
                if (process.env.DONT_NOTIFY_HOSTS && evtHost) {
                    if (evtHost.indexOf(process.env.DONT_NOTIFY_HOSTS) != -1) {
                        console.log('Not Notify(Host):' + evtHost);
                        return false;
                    }
                }

                return true;

            }).filter(function (evt) {
                return !evt.match(/$^/);
            }).map(function (evt) {
                return evt;
            });
            
            console.log('blockLogs length:' + blockLogs.length);

            if (blockLogs.length == 0) {
                callback();
                return;
            }

            const subject = 'Notify From AWS WAF Logs';
            let payload = {default: ''};
            for (const logIndex in blockLogs) {
                const log = JSON.parse(blockLogs[logIndex]);

                // このルールは通知しない
                if (process.env.DONT_NOTIFY_RULES) {
                    if (log.terminatingRuleId.indexOf(process.env.DONT_NOTIFY_RULES) != -1) {
                        console.log('Not Notify(RULE):' + log.terminatingRuleId);
                        continue;
                    }
                }

                // BLOCK以外は通知しない
                if (log.action != 'BLOCK') {
                    console.log('Not Notify(Action is not BLOCK):' + log.action);
                    continue;
                }

                payload['default'] += log.terminatingRuleId;
                payload['default'] += '|';
                payload['default'] += log.httpRequest.clientIp;
                payload['default'] += '|';
                payload['default'] += log.httpRequest.country;
                payload['default'] += '|';
                for (const header in log.httpRequest.headers) {
                    if (log.httpRequest.headers[header].name == 'Host') {
                        payload['default'] += log.httpRequest.headers[header].value;
                    }
                }
                payload['default'] += '|';
                payload['default'] += log.httpRequest.uri;
                payload['default'] += '|';
                payload['default'] += log.httpRequest.httpMethod;
                payload['default'] += '|';
                payload['default'] += log.httpRequest.args;
                payload['default'] += '|';
                payload['default'] += log.httpRequest.httpVersion;
                payload['default'] += '\n';
                for (const header in log.httpRequest.headers) {
                    if (log.httpRequest.headers[header].name == 'User-Agent') {
                        payload['default'] += log.httpRequest.headers[header].value;
                    }
                }
                payload['default'] += '|';
                payload['default'] += log.action;
                payload['default'] += '\n';
                payload['default'] += '---';
                payload['default'] += '\n';
            }
            // payload['default'] += blockLogs.join('\n---\n');
            console.log('payload:' + JSON.stringify(payload));
            if (payload['default'] !== ''){
                sns.publish({
                    Subject: subject,
                    Message: JSON.stringify(payload),
                    MessageStructure: 'json',
                    TargetArn: process.env.SNS_ARN
                }, function (err, data) {
                    if (err) callback(err);
                    else callback(null, data);
                });
            }
            
            callback(null);
        });
    });
};

「Deploy」

  • 環境変数の追加

    • DONT_NOTIFY_IPADDRESSES:空
    • DONT_NOTIFY_RULES:AWS-AWSManagedRulesAnonymousIpList
    • DONT_NOTIFY_USERAGENTS:空
    • S3_BUCKET:aws-waf-logs
    • SNS_ARN:作成したSNSwaf-monitoring-publish-snsのARNをコピペ
  • 基本設定

    • メモリ:256
    • タイムアウト:0分10秒
  • IAM

    • Lambda関数waf-monitoring-publish-sns作成時にIAMロールが作成されているので、そのロールにアクセス権限を追加する
      • AmazonS3ReadOnlyAccess
      • AmazonSNSFullAccess
動作確認
  • ブラウザから対象のホスト/waftestにアクセス。403エラーが表示される。エンドポイントに指定したメールアドレスにメールが送信されればOK
  • Cloud Watch Logs>/aws/lambda/waf-monitoring-publish-snsにログが出力されていればOK

awlogsトリガーの監視

監視の流れ

awslogs→CloudWatchサブスクリプションフィルタ→Lambda→SNS→Eメール
                               →CloudWatchLogs

監視内容

対象ログ出力内容に「ERRORまたはFATALまたはEXCEPTIONまたはErrorまたはFatalまたはException」が含まれていたらメッセージ送信。

作る

※設定値を記載していない箇所はデフォルト値を使用している。

SNS
  • monitoring-publish-sns
    • タイプ:スタンダード
    • サブスクリプション
      • プロトコル:Eメール
      • エンドポイント:awslogs@e2info.com
awslogsエージェント

参考:
クイックスタート: 実行中の EC2 Linux インスタンスに CloudWatch Logs エージェントをインストールして設定する

サーバーにsshアクセスする

yumアップデート

sudo yum update -y

awslogsパッケージをインストール

sudo yum install -y awslogs

awscli.confで東京リージョンを指定

cd /etc/awslogs/
sudo vim awscli.conf

[default]
region = ap-northeast-1

awslogs.confでCloudWatchLogsに出力するログを指定(設定値は各自のサーバー設定に置き換えてください。)

[messages]
file = /var/log/messages
log_stream_name = {hostname}_messages
datetime_format = %b %d %H:%M:%S
log_group_name = /aws/ec2/messages

[httpd-access_log]
datetime_format = %d/%b/%Y:%H:%M:%S %z
file = /var/log/httpd/hoge-access_log
buffer_duration = 5000
log_stream_name = {hostname}_httpd_hoge-access-log
initial_position = start_of_file
log_group_name = /aws/ec2/hoge/apache/accesslog

[httpd-error_log]
datetime_format = %d/%b/%Y:%H:%M:%S %z
file = /var/log/httpd/hoge-error_log
buffer_duration = 5000
log_stream_name = {hostname}_httpd_hoge-error-log
initial_position = start_of_file
log_group_name = /aws/ec2/hoge/apache/errorlog

[laravel_log]
datetime_format = [%Y/%m/%d %H:%M:%S.%S]
file = /var/www/hoge/storage/logs/laravel*.log
buffer_duration = 5000
log_stream_name = {hostname}_laravel
initial_position = start_of_file
log_group_name = /aws/ec2/hoge/laravel

awslogs起動

sudo systemctl start awslogsd

awslogs再起動ON

sudo systemctl enable awslogsd.service

Cloud Watch Logs にlog_group_nameで指定した名前のロググループが作成されていればOK

Lambda
  • monitoring-publish-sns
    • 一から作成
    • ランタイム:node.js 10.x

Lambda関数作成後、

  • トリガーを追加
    • Cloud Watch Logs
      • 先程作成したロググループを選択

関数コードindex.jsに下記をペースト

var zlib = require('zlib');
var aws = require('aws-sdk');
var sns = new aws.SNS({ region: 'ap-northeast-1' });
exports.handler = function(input, context, callback) {
var data = Buffer.from(input.awslogs.data, 'base64');

console.log("リクエスト受信");

  zlib.gunzip(data, function(e, result) {
    if (e) {
      callback(e);
    } else {
      result = JSON.parse(result.toString('utf-8'));
      var logs = result['logEvents']
                     .filter(function(evt) { return evt['message'].match(/ERROR|FATAL|EXCEPTION|Error|Fatal|Exception/) ;})
                     .filter(function(evt) { return !evt['message'].match(/$^/) ;})
                     .map(function(evt) { return evt['message'] });

console.log('processing' + logs.length + '/' + result['logEvents'].length + ' events.');

      if (logs.length === 0) {
console.log("通知対象外");

        callback();
        return;
      }


      var logString = logs.join('\n---\n');

      // 指定文字列が含まれる場合は通知しない
      if (process.env.DONT_NOTIFY_STRING && logString) {
console.log("debug:DONT_NOTIFY_STRING1");
          const dont_nofity_strings = process.env.DONT_NOTIFY_STRING.split(',');
console.log("debug:DONT_NOTIFY_STRING2");
          for (var dont_nofity_string of dont_nofity_strings) {
console.log("debug:DONT_NOTIFY_STRING3:dont_nofity_string:" + dont_nofity_string);
              if (logString.indexOf(dont_nofity_string) != -1) {
console.log("debug:DONT_NOTIFY_STRING4:logString.indexOf(dont_nofity_string):" + logString.indexOf(dont_nofity_string));
                  console.log('Not Notify(DONT_NOTIFY_STRING)' + dont_nofity_string);
                  callback();
                  return;
              }
          }
      }


console.log("通知");

      var subject = 'Notify From CloudWatch Logs';
      var payload = { default: '' };
      payload['default'] += 'NotifyAt: ' + new Date() + '\n';
      payload['default'] += 'Log: ' + result['logGroup'] + ' - ' + result['logStream'] + '\n';
      payload['default'] += 'Filter: ' + result['subscriptionFilters'] + '\n';
      payload['default'] += 'Messages:\n';
      payload['default'] += logString;
      sns.publish({
        Subject: subject,
        Message: JSON.stringify(payload),
        MessageStructure: 'json',
        TargetArn: process.env.SNS_ARN
      }, function(err, data) {
        if (err) callback(err);
        else callback(null, data);
      });
    }
  });
};

「Deploy」

  • 環境変数の追加

    • DONT_NOTIFY_STRING:Error: websocket: close 1006
    • SNS_ARN:作成したSMSmonitoring-publish-snsのARNをコピペ
  • 基本設定

    • メモリ:256
    • タイムアウト:0分10秒
  • IAM

    • Lambda関数monitoring-publish-sns作成時にIAMロールが作成されているので、そのロールにポリシーを追加する。
      • AmazonSNSFullAccess
Cloud Watch Lambda サブスクリプションフィルタ
  • Lambdaサブスクリプションフィルタ
    • /aws/ec2/messages
      • 送信先:monitoring-publish-sns
      • フィルタのパターン:?ERROR ?Error ?FATAL ?Fatal ?EXCEPTION ?Exception
      • フィルター名:LambdaStream_monitoring-publish-sns
    • /aws/ec2/hoge/apache/accesslog
      • 上と同じ
    • /aws/ec2/hoge/apache/errorlog
      • 上と同じ
    • /aws/ec2/hoge/laravel
      • 上と同じ
動作確認

対象ファイルにechoコマンドでファイルに追記
フィルタパターン(?ERROR ?Error ?FATAL ?Fatal ?EXCEPTION ?Exception)を追記したときに、メッセージ送信されること

echo 追記する文字列 >> 書き込みたいファイル

// フィルタパターンテスト
echo Error test >> /var/log/httpd/hoge-error_log
echo ERROR test >> /var/log/httpd/hoge-error_log
echo Fatal test >> /var/log/httpd/hoge-error_log
echo FATAL test >> /var/log/httpd/hoge-error_log
echo Exception test >> /var/log/httpd/hoge-error_log
echo EXCEPTION test >> /var/log/httpd/hoge-error_log
echo Error test >> /var/log/messages
echo Error test >> /var/log/httpd/hoge-access_log
echo Error test >> /var/www/hoge/storage/logs/laravel-2021-02-22.log

フィルタパターンを対象ファイルに追記してメール送信されればOK
Cloud Wacth ロググループに/aws/lambda/monitoring-publish-snsが生成されていればOK

CI_CDトリガーの監視

監視の流れ

CodePipeline→SNS→Eメール

監視内容

CodePipeline実行して、「リリース失敗」したらerrorメッセージ送信して「リリース成功」したらsuccessメッセージ送信する。

作る

※CodePipelineリソースは事前に作成してあるものとする。
※設定値を記載していない箇所はデフォルト値を使用している。

SNS
  • cicd-error-publish-sns
    • タイプ:スタンダート
    • サブスクリプション
      • プロトコル:Eメール
      • エンドポイント:cicd-erro@e2info.com
  • cicd-success-publish-sns
    • タイプ:スタンダード
    • サブスクリプション
      • プロトコル:Eメール
      • エンドポイント:cicd-success@e2info.com
CodePipeline 通知ルール
  • pipeline-success
    • 通知をトリガーするイベント
      • Pipeline execution:Succeeded
      • Manual approval:Succeeded
    • ターゲット
      • SNSトピック:SNScicd-success-publish-snsのARN
  • pipeline-error
    • 通知をトリガーするイベント
      • Action execution:Failed
      • Stage execution:Failed
      • Pipeline execution:Failed
      • Manual approval:Failed
    • ターゲット
      • SNSトピック:SNScicd-error-publish-snsのARN
IAM
  • CodePipelinehoge-pipeline作成時にIAMロールが作成されているのでそのロールにポリシーを追加する
    • AmazonSNSFullAccess

ポリシーアタッチ手順:CodePipeline>パイプライン>パイプラインを選択>設定>全般タブ>サービスロール>ポリシーをアタッチ

動作確認

1.Succeededメッセージ送信確認
CodePipeline>パイプライン>hoge-pipeline>変更をリリース

パイプラインの実行成功時に指定したメールアドレス(cicd-success@e2info.com)にメッセージ送信されること。

メッセージ送信されない
調査:通知ターゲットのステータスが「到達できない」となっている。
原因:SNSトピックを作成してからCodePipeline通知ルール作成時にターゲットを指定する流れではポリシーがうまいことセットされないらしい。参考
解決:CodePipeline通知ルールを作成時にSNSトピックを作成する。またはSNSトピックのアクセスポリシーを編集する。

SNSトピックのアクセスポリシーを編集する

{
  "Version": "2008-10-17",
  "Statement": [
    {
      "Sid": "CodeNotification_publish",
      "Effect": "Allow",
      "Principal": {
        "Service": "codestar-notifications.amazonaws.com"
      },
      "Action": "SNS:Publish",
      "Resource": "作成したSNSトピックのARN"
    }
  ]
}

メッセージ送信された。

2.Errorメッセージ送信確認

通知をトリガーするイベント「Faild」の場合、CodePipeline設定値を壊さなければメッセージ送信テストできない。AWSマネージドなトリガーのため厳密なテストは不要と判断し、テスト時のみ、通知をトリガーするイベントに「Succeeded」を追加する。

CodePipeline>パイプライン>hoge-pipeline>変更をリリース

パイプラインの実行停止時に指定したメールアドレス(cicd-error@e2info.com)にメッセージ送信されること。
テスト終了後、通知をトリガーするイベント「Succeeded」のチェックを外す。

CloudWatchアラームの監視

監視の流れ

CloudWatchアラーム→SNS→Eメール

監視内容

対象リソースの負荷状況に応じてメッセージ送信する。

作る

SNS
  • metrics-alarm-publish-sns
    • タイプ:スタンダード
    • サブスクリプション
      • プロトコル:Eメール
      • エンドポイント:metrics-alarm@e2info.com
Cloud Watch エージェント

EC2のメモリやディスク容量の監視を行うために必要。

サーバーアクセスし、CloudWatchエージェントをインストールする

sudo yum install amazon-cloudwatch-agent

再起動設定ON

sudo systemctl enable awslogsd.service

ウィザードを使って設定ファイルを作成する

sudo /opt/aws/amazon-cloudwatch-agent/bin/amazon-cloudwatch-agent-config-wizard

操作ログ
今回取得したいデータは、ディスク使用率とメモリ使用率のみ。
StatsD、CollectDから取得できるメトリクスは不要。

On which OS are you planning to use the agent?
1. linux
2. windows
default choice: [1]:
1
Trying to fetch the default region based on ec2 metadata...
Are you using EC2 or On-Premises hosts?
1. EC2
2. On-Premises
default choice: [1]:
1
Which user are you planning to run the agent?
1. root
2. cwagent
3. others
default choice: [1]:
1
Do you want to turn on StatsD daemon?
1. yes
2. no
default choice: [1]:
2
Do you want to monitor metrics from CollectD?
1. yes
2. no
default choice: [1]:
2
Do you want to monitor any host metrics? e.g. CPU, memory, etc.
1. yes
2. no
default choice: [1]:
1
Do you want to monitor cpu metrics per core? Additional CloudWatch charges may apply.
1. yes
2. no
default choice: [1]:
1
Do you want to add ec2 dimensions (ImageId, InstanceId, InstanceType, AutoScalingGroupName) into all of your metrics if the info is available?
1. yes
2. no
default choice: [1]:
1
Would you like to collect your metrics at high resolution (sub-minute resolution)? This enables sub-minute resolution for all metrics, but you can customize for specific metrics in the output json file.
1. 1s
2. 10s
3. 30s
4. 60s
default choice: [4]:
4
Which default metrics config do you want?
1. Basic
2. Standard
3. Advanced
4. None
default choice: [1]:
1
Current config as follows:
{
        "agent": {
                "metrics_collection_interval": 60,
                "run_as_user": "root"
        },
        "metrics": {
                "append_dimensions": {
                        "AutoScalingGroupName": "${aws:AutoScalingGroupName}",
                        "ImageId": "${aws:ImageId}",
                        "InstanceId": "${aws:InstanceId}",
                        "InstanceType": "${aws:InstanceType}"
                },
                "metrics_collected": {
                        "disk": {
                                "measurement": [
                                        "used_percent"
                                ],
                                "metrics_collection_interval": 60,
                                "resources": [
                                        "*"
                                ]
                        },
                        "mem": {
                                "measurement": [
                                        "mem_used_percent"
                                ],
                                "metrics_collection_interval": 60
                        }
                }
        }
}
Are you satisfied with the above config? Note: it can be manually customized after the wizard completes to add additional items.
1. yes
2. no
default choice: [1]:
1
Do you have any existing CloudWatch Log Agent (http://docs.aws.amazon.com/AmazonCloudWatch/latest/logs/AgentReference.html) configuration file to import for migration?
1. yes
2. no
default choice: [2]:
1
What is the file path for the existing cloudwatch log agent configuration file?
default choice: [/var/awslogs/etc/awslogs.conf]
/etc/awslogs/awslogs.conf // 各々の設定値を書く。
Do you want to monitor any log files?
1. yes
2. no
default choice: [1]:
2
Saved config file to /opt/aws/amazon-cloudwatch-agent/bin/config.json successfully.
Current config as follows:
{
        "agent": {
                "metrics_collection_interval": 60,
                "run_as_user": "root"
        },
        "logs": {
                "force_flush_interval": 5,
                "logs_collected": {
                        "files": {
                                "collect_list": [
                                        // 各々のサーバー設定が書かれている。
                                ]
                        }
                }
        },
        "metrics": {
                "append_dimensions": {
                        "AutoScalingGroupName": "${aws:AutoScalingGroupName}",
                        "ImageId": "${aws:ImageId}",
                        "InstanceId": "${aws:InstanceId}",
                        "InstanceType": "${aws:InstanceType}"
                },
                "metrics_collected": {
                        "disk": {
                                "measurement": [
                                        "used_percent"
                                ],
                                "metrics_collection_interval": 60,
                                "resources": [
                                        "*"
                                ]
                        },
                        "mem": {
                                "measurement": [
                                        "mem_used_percent"
                                ],
                                "metrics_collection_interval": 60
                        }
                }
        }
}
Please check the above content of the config.
The config file is also located at /opt/aws/amazon-cloudwatch-agent/bin/config.json.
Edit it manually if needed.
Do you want to store the config in the SSM parameter store?
1. yes
2. no
default choice: [1]:
1
What parameter store name do you want to use to store your config? (Use 'AmazonCloudWatch-' prefix if you use our managed AWS policy)
default choice: [AmazonCloudWatch-linux]
AmazonCloudWatch-from-metrics-alarm-to-sns
Trying to fetch the default region based on ec2 metadata...
Which region do you want to store the config in the parameter store?
default choice: [ap-northeast-1]

Which AWS credential should be used to send json config to parameter store?
1. *********(From SDK)
2. Other
default choice: [1]:

Successfully put config to parameter store AmazonCloudWatch-from-metrics-alarm-to-sns.
Program exits now.

設定ファイルの確認

less /opt/aws/amazon-cloudwatch-agent/bin/config.json

CloudWatchエージェント起動

sudo systemctl start amazon-cloudwatch-agent

起動確認

sudo systemctl status amazon-cloudwatch-agent

ログの場所:/opt/aws/amazon-cloudwatch-agent/logs/amazon-cloudwatch-agent.log

別サーバーでCloudWatchエージェントを上記コマンドで起動しようとしたところ、起動しない。下記コマンドで起動できた。

sudo /opt/aws/amazon-cloudwatch-agent/bin/amazon-cloudwatch-agent-ctl -m ec2 -a start
sudo /opt/aws/amazon-cloudwatch-agent/bin/amazon-cloudwatch-agent-ctl -m ec2 -a status

CloudWatch>メトリクス
「CWAgent」が追加されていればOK

参考:
はじめてのCloudWatch Agent導入
CloudWatch エージェントを使用して Amazon EC2 インスタンスとオンプレミスサーバーからメトリクスとログを収集する

Cloud Watch アラーム
  • ec2-hoge-Memory-80

    • メトリクスの選択
      • CWAgent>ImageId,InstanceId,InstanceType
      • インスタンス名:hoge
      • path:/
      • メトリクス名:mem_used_percent
    • 統計:平均値
    • 期間:5分
    • しきい値の種類:静的
    • disk_used_percent が次の時...:より大きい
    • ... よりも:80
    • アラーム状態トリガー:アラーム状態
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
    • アラーム状態トリガー:OK
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
  • ec2-hoge-Disk-70

    • メトリクスの選択
      • CWAgent>ImageId,InstanceId,InstanceType,device,fstype,path
      • インスタンス名:hoge
      • path:/
      • メトリクス名:disk_used_percent
    • 統計:平均値
    • 期間:5分
    • しきい値の種類:静的
    • disk_used_percent が次の時...:より大きい
    • ... よりも:70
    • アラーム状態トリガー:アラーム状態
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
    • アラーム状態トリガー:OK
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
  • ec2-hoge-CPU-70

    • メトリクスの選択
      • インスタンス名:hoge
      • メトリクス名:CPUUtilization
    • 統計:平均値
    • 期間:5分
    • しきい値の種類:静的
    • CPUUtilization が次の時...:以上
    • ... よりも:70
    • アラーム状態トリガー:アラーム状態
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
    • アラーム状態トリガー:OK
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
  • ec2-hoge-status

    • メトリクスの選択
      • インスタンス名:hoge
      • メトリクス名:StatusCheckFailed
    • 統計:平均値
    • 期間:1分
    • しきい値の種類:静的
    • StatusCheckFailed が次の時...:以上
    • ... よりも:0.99
    • アラーム状態トリガー:アラーム状態
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
    • アラーム状態トリガー:OK
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
  • aurora-instance-hoge-CPU-70

    • メトリクスの選択
      • インスタンス名:hoge
      • メトリクス名:CPUUtilization
    • 統計:平均値
    • 期間:5分
    • しきい値の種類:静的
    • CPUUtilization が次の時...:以上
    • ... よりも:70
    • アラーム状態トリガー:アラーム状態
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
    • アラーム状態トリガー:OK
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
  • aurora-cluster-hoge-CPU-70

    • メトリクスの選択
      • DBClusterIdentifier:hoge
      • メトリクス名:CPUUtilization
    • 統計:平均値
    • 期間:5分
    • しきい値の種類:静的
    • CPUUtilization が次の時...:以上
    • ... よりも:70
    • アラーム状態トリガー:アラーム状態
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns
    • アラーム状態トリガー:OK
    • 既存のSNSトピックを選択:metrics-alarm-publish-sns

参考:
Amazon CloudWatch でのアラームの使用
CloudWatch メトリクスの使用状況のモニタリング
インスタンスの利用可能な CloudWatch メトリクスのリスト表示

動作確認

サーバーにアクセスし、下記コマンドを入力。メッセージ送信されること。

aws cloudwatch set-alarm-state --alarm-name アラーム名 --state-value 状態(OK、ALARM、INSUFFICIENT_DATA) --state-reason "コマンド実行理由"

// EC2インスタンスCPU使用率70以上
aws cloudwatch set-alarm-state --alarm-name ec2-hoge-CPU-70 --state-value ALARM --state-reason "test" 

// AuroraクラスターCPU使用率70以上
aws cloudwatch set-alarm-state --alarm-name aurora-cluster-hoge-CPU-70 --state-value ALARM --state-reason "test"

// 上記の要領で他のテストも実行する。

コマンド実行後、マネジメントコンソールから対象のアラームがアラーム状態になったことを確認し、メッセージ送信されていること。
その数秒後に対象のアラームがOK状態に戻り、メッセージ送信されていること。

参考:
設定した CloudWatch Alarm をテストする方法

1
3
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
1
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?