CloudWatchアラームに定時ダウンタイム設定をいれる

# 1. はじめに
* あるEC2サーバで、毎日早朝に動くバッチのCPU使用率が高く、クリティカル通知で起こされるので、バッチの時間帯だけ CPU使用率クリティカル アラートの通知を止めたかった。
* CloudWatch アラームにダウンタイム機能は提供されていないので、CloudWatch イベントと Lambda で自作する。
* ここでいう「ダウンタイム設定」とは、何時から何時までの間はアラームアクションを無効にして、アラーム状態になっても通知を飛ばさないこと。

# 2. 概要
* この自作ダウンタイム設定では、CloudWatchアラーム名に空白があると動かないので、空白がある場合はあらかじめ空白をなくした名前に変更しておく。
 * 例えば、「EC2 base CPU Utilization crit」を「EC2_base_CPU-Utilization_crit」 という感じにする。
* CloudWatch アラームの有効/無効化は、次のアクションを利用する。
 * [EnableAlarmActions](https://docs.aws.amazon.com/ja_jp/AmazonCloudWatch/latest/APIReference/API_EnableAlarmActions.html)
 * [DisableAlarmActions](https://docs.aws.amazon.com/ja_jp/AmazonCloudWatch/latest/APIReference/API_DisableAlarmActions.html)
* CloudWatch イベントで、決められた時間に指定したCloudWatchアラーム名のアラートアクションを有効/無効化する Lambda を実行する。この時、CloudWatch イベントから "CloudWatchアラーム名" と "有効/無効" の引数を Lambda へ渡す。

# 3. 設定
## 3.1. LambdaにアタッチするIAMロールを作成
* IAMポリシー: cloudwatch-alarm-downtime

```json
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "cloudwatch:EnableAlarmActions",
                "cloudwatch:DisableAlarmActions"
            ],
            "Resource": "*"
        }
    ]
}
```
* IAMロール: cloudwatch-alarm-downtime

 * 信頼されたエンティティ
     * lambda.amazonaws.com
     
 * アタッチするポリシー
     * cloudwatch-alarm-downtime
     * AWSLambdaBasicExecutionRole (AWS 管理ポリシー)

## 3.2. Lambda作成
* 関数名: cloudwatch-alarm-downtime
* ランタイム: Python 3.7
* 実行ロール: cloudwatch-alarm-downtime
* 関数

```python
import boto3
import logging
logger = logging.getLogger()
logger.setLevel(logging.INFO)
def lambda_handler(event, context):
    alarm_name=event['alarm_name']
    state=event['state']
    cloudwatch = boto3.client('cloudwatch')
    if state == 'enabled':
        cloudwatch.enable_alarm_actions (
            AlarmNames=[alarm_name]
        )
        logger.info(alarm_name)
        logger.info(state)
    elif state == 'disabled':
        cloudwatch.disable_alarm_actions(
            AlarmNames=[alarm_name]
        )
        logger.info(alarm_name)
        logger.info(state)
```

## 3.3. CloudWatchイベントルール設定
### 3.3.1. 日本時間 03:45に CloudWatch アラーム「EC2_base_CPU-Utilization_crit」のアラートアクションを無効にする
* イベントソース設定
Cron式: 10 11 * * ? * (03:45 JST)
![20200408-01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148868/830db6d8-62bd-0fe7-037e-3632ed130681.png)

* ターゲット設定
Lambda関数: CloudWatchAlarmDowntime
定数(JSON テキスト): { "alarm_name": "EC2_base_CPU-Utilization_crit", "state": "disabled" }
![20200408-02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148868/22d4015f-066e-195c-674c-3e8f0fd74db6.png)

* ルールの定義
名前: CWDowntime_EC2_base_CPU-Utilization_crit_disabled
説明: (45 18 * * ? *) disabled

### 3.3.2. 日本時間 04:15に CloudWatch アラーム「EC2_base_CPU-Utilization_crit」のアラートアクションを有効にする
* イベントソース設定
Cron式: 15 19 * * ? * (04:15 JST)
![20200408-03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148868/62136373-3946-8e11-186e-3b49e20a162a.png)

* ターゲット設定
Lambda関数: CloudWatchAlarmDowntime
定数(JSON テキスト): { "alarm_name": "EC2_base_CPU-Utilization_crit", "state": "enabled" }
![20200408-04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148868/61bd5b98-733b-38f2-a207-9cb2c32ffb4c.png)

* ルールの定義
名前: CWDowntime_EC2_base_CPU-Utilization_crit_enabled
説明: (15 19 * * ? *) enabled

# 4. 確認
## 4.1. Lambda実行ログ
* CloudWatch ロググループの 「/aws/lambda/cloudwatch-alarm-downtime」にログストリームが出力される。
![20200408-05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148868/ca9dd658-c34b-0ed4-cc33-1d8ac12dec6d.png)

## 4.2. CloudWatchアラーム 「EC2_base_CPU-Utilization_crit」 の履歴
![20200408-06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148868/f0669e58-e4c1-e54a-ee03-a068b1105e81.png)

↓
2020-04-07 18:45:15	設定の更新	Alarm "EC2_base_CPU-Utilization_crit" updated
⇒CloudWatch アラームを無効にした

2020-04-07 18:53:00	状態の更新	OKからアラーム状態に更新したアラーム
⇒CPU使用率上昇で、スタータスが OK から アラーム に変更された。
　アラート通知は飛ばない。

2020-04-07 19:02:00	状態の更新	アラーム状態からOKに更新したアラーム
⇒CPU使用率上昇で、スタータスが アラーム から OK に変更された。
　アラート通知は飛ばない。

2020-04-07 19:15:14	設定の更新	Alarm "EC2_base_CPU-Utilization_crit" updated
⇒CloudWatch アラームを有効にした