EC2の課金対象削減のための自動シャットダウンについて

AWSを初めて利用する時に気になるのが予期しない課金だと思います。
また、とりあえずEC2を作成したけど停止するのを忘れてしまい
予期しない課金が発生してしまうことはよくある話です。

そんな時のために作成したEC2を毎日決まった時間に停止することで
予期しない課金を防止することができます。

AWSを触り始めて最初に実施したことですが
記事に残しておこうと思います。

【使うサービス】
・EC2
・Lambda(Python3.9)
・EventBridge(CloudWatch Events)

【やること(超入門向け)】
実施順序
１．IAMポリシー作成(EC2停止とログ出力用)
２．IAMロール作成(1で作成したポリシーを付与)
３．Lambda関数作成(実行ロールに2で作成したIAMロールを付与)
４．Lambdaを用いてEC2を停止する命令を作成
５．定刻起動としてLambdaのイベントトリガーにEventBridgeを指定する
６．テスト(動作確認)

---
１．IAMポリシー作成(EC2停止とログ出力用)
---
まず、最小権限の法則に基づきEC2の停止用のIAMポリシーを作成します。
マネジメントコンソールより[IAM]-[ポリシー]と選択し
「ポリシーの作成」ボタンを押下しJSONコードで以下をコピペします。

【コード】
```JSON
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "logs:CreateLogGroup",
                "logs:CreateLogStream",
                "logs:PutLogEvents"
            ],
            "Resource": "arn:aws:logs:*:*:*"
        },
        {
            "Effect": "Allow",
            "Action": [
                "ec2:Stop*"
            ],
            "Resource": "*"
        }
    ]
}
```
---
２．IAMロール作成(1で作成したポリシーを付与)
---
作成したら次にIAMロールを作成します。
マネジメントコンソールより[IAM]-[ロール]より
「ロールの作成」ボタンを押下すると以下の画面に遷移します。

![ロール作成1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2840619/a9947908-677e-152b-17e0-30ccb23c5d70.jpeg)

ユースケースにラジオボタンの「Lambda」を選択して「次へ」を押下
許可を追加の画面にて、先ほど作成したIAMポリシーを探して選択して「次へ」を押下。
最後にロール名に適当なわかりやすい名前を付けて「ロールを作成」を押下。


---
３．Lambda関数作成(実行ロールに2で作成したIAMロールを付与)
---
マネジメントコンソールより「Lambda」を選択し
「関数の作成」を押下します。

![関数の作成.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2840619/fb711c0e-fa1d-b05c-827a-064ac477c7ad.jpeg)

・言語にPython3.9を選択
・[既存のロールを使用する]を選択して上記２で作成したIAMロールを選択します。
[関数の作成]を押下


---
４．Lambdaを用いてEC2を停止する命令を作成
---
コードは「instances」の部分を適宜、ご自身の環境に合わせて修正してから以下からコピペでお使いください。
【コード】
```Python
import boto3
region = 'ap-northeast-1'

instances = ['i-071522f85ff7ba939',
             'i-xxxxxxxxxxxxxxxxx']
ec2 = boto3.client('ec2', region_name=region)

def lambda_handler(event, context):
    ec2.stop_instances(InstanceIds=instances)
    print('stopped your instances: ' + str(instances))
```
- instances
　「i-xxxxxxxxxxxxxxxxx」複数のEC2を停止したい場合は","カンマで区切ってここにEC2のインスタンスIDを指定してあげます。
EC2のインスタンスIDは以下の部分
![EC2起動中.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2840619/8808b276-0013-72d4-7931-4e62d99c7dee.jpeg)

----
５．定刻起動としてLambdaのイベントトリガーにEventBridgeを指定する
---
関数の概要より「トリガーの追加」ボタンを押下すると以下の画面が現れますので
ソースを選択よりEventBridgeを選択します。
![トリガーの設定1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2840619/b90482fa-29a4-5f3e-f0d8-6027b09fefd4.jpeg)

次に、毎日定刻(下の図の例では日本時間の深夜0時)に起動するように設定します。
スケジュール式には以下を入力します。
指定した値の意味は右記の通り(分 時 日 月 曜日 年)
```
cron(00 15 * * ? *) 
```
![トリガーの設定2.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2840619/9caedd82-3c97-ad0d-2b3d-4101fc3e3c29.jpeg)

「適用」を押下すると下の図のようにEventBridgeが表示されているかと思います。

![Lambda.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2840619/28382b89-c4db-b87a-09a9-855a0416bfd3.jpeg)

---

ここまで設定できれば毎日JST0時に指定したEC2が自動的に停止されます。

---
６．テスト(動作確認)
---
ただ、設定しても何事も試してみないと気持ち悪いのがSEの性。
ということで即時イベントにてテストします。
下の図を参考に[テスト]タブに切り替えて
イベントJSONの部分を{}のみに修正します。

![テスト.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2840619/66043479-7b96-3ace-471d-0d9de00d9e2c.jpeg)

修正したら右上のオレンジ色の[テスト]ボタンを押下します。
![テスト結果.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2840619/0ed2f990-8f47-b268-4b7d-1015702bb36f.jpeg)

正常に停止イベントが発行されました。
念のためEC2の画面でも対象のEC2が停止されたことを確認しましょう。


さて、今回は入門用にLambdaでのEC2の自動停止についてご紹介しましたが
EC2が増えた場合に都度Lambdaのコードも追加していく必要があります。

そんな管理は面倒だ！
という方のために~~次回はEC2が増えた時の管理も自動化できる方法を記事にして紹介しようと思います。~~
↓執筆しました↓

https://qiita.com/fukuchan_milk/items/9fd1757cbabb037391e2

今回はここまでです。最後までお読みいただきありがとうございました。
コメントやいいねをいただけると励みになりますのでお願いいたします。