「お前には n 日間でAWSを学んでもらう」 #5 です.

前回はインスタンスを起動・終了するシェルスクリプトなんて物を作ったのですが, 今回はインスタンスを所定の時間に自動で停止するということをCloudWatch EventsおよびLambdaによって行おうと思います.

今回はAWSマネジメントコンソール使ってみます.

この記事のスコープ

  • 適切なポリシーを持ったIAMロールの作成
  • Lambda関数の作成
  • CloudWatch Eventsのルール作成

案の定「生じた損害に対しては責任は取りません」です.

目標

以下のような感じになります. 時間が来るとそれがトリガーになってLambda 関数が実行されインスタンスが停止します.

インスタンスの起動

起動しているインスタンスが無いことには自動停止を試すこともかなわないのでインスタンスを立ち上げましょう. どのような方法でも構いません.

IAMロールの作成

Lambda 関数がインスタンスを触れるようにするためにLambda用のロールを作成します.

IAM ダッシュボード のアクセス管理のところにあるロールを選択してください. その後「ロールの作成」をクリックして次のように設定しましょう.

  • 信頼されたエンティティの種類を選択
    AWSサービス -> Lambda(信頼関係ポリシーに使われると思います)
  • Attach アクセス権限ポリシー
    AmazonEC2FullAccess, CloudWatchLogsFullAccess

名前などはお好きにお決めください.

このロールが割り当てられたLambda関数はEC2に好き放題出来てしまうので実際にはもう少し良いポリシーを与えたほうがいいかもしれません.

Lambda関数の作成

実際にインスタンスを全て停止するLambda関数を作成します.

AWS Lambda ダッシュボードの関数というところを選択してください.その後「関数の作成」をクリックして次のように設定しましょう.

  • ランタイム
    Python 3.8 (僕がこれ以外では説明できないです)
  • アクセス権限
    「既存のロールを使用する」で先程作ったロールを選択

名前はお好きにお決めください. 関数を作成をクリックするとエディタ画面にすすみます.

lambda_function.py というものがあると思いますがそこに次のコードを書きましょう.

import json
import boto3

def lambda_handler(event, context):
    
    ec2 = boto3.client('ec2')
    
    response = ec2.describe_instances(
        Filters = [
            {
                'Name': 'instance-state-name',
                'Values': [
                    'running'
                ]
            },
        ],
    )
    
    target_instances = list(map(lambda instance: instance['InstanceId'], response['Reservations'][0]['Instances']))
    
    ec2.stop_instances(
        InstanceIds = target_instances    
    )

boto3 はAWSのためのSDKです. AWS CLIのコマンドと同じように使えるので良き!

やっていることとしては前回とほとんど同じで, 動いているインスタンスの全リストを取得してそのままそのリストの全件に対して停止を行っています.

CloudWatch Eventsのルール作成

あとは上記Lambdaの起動トリガーを作ってやらなければいけません.

CloudWatch ダッシュボード > イベント下 ルール を選んでください.

「ルールの作成」をクリックして次の画像のように設定しましょう.

CloudWatch イベントルールの設定画面

あとは名前を決めて有効化してやるだけです.

おわり!

すごくコンピューティング性能の高いインスタンスを使ってもないのにぶちあげたままにして高額課金されるのを避けるためにこういうのは置いといてもいいのかもしれませんね!

今日もお疲れさまでした!