LoginSignup
7
7

More than 1 year has passed since last update.

EC2インスタンスの消し忘れをLINE Messaging APIで通知する

Last updated at Posted at 2022-01-03

はじめに

テストなどでEC2インスタンスを作成していろいろと検証をした後に、ついうっかり停止し忘れて余計な料金がかかってしまうことはよくあることです。
本記事では毎朝決まった時間に、起動中のEC2インスタンス情報をLINE Messaging APIを使ってLINEに通知するための仕組みを作っていきたいと思います。

構成図

構成図は以下の通り。
EC2_Notification.drawio.png
今回はAWS Lambdaを使用して実装していきます。
LambdaにてAmazon EC2インスタンスの起動情報を取得するコードを作成し、Amazon EventBridgeで毎日9:00にLine Messaging APIへ連携する構成となっています。

実装

ここからは構成図の通りに実装していきます。

①Line Messaging APIの作成

まずはLINE Developersへログインを行います。
https://developers.line.biz/ja/
※アカウントを持っていない場合は、作成から行いましょう
ログイン後は左ペインからプロバイダーを選択し、新規チャネル作成の画面へ遷移します。
※プロバイダーを作成していない場合は、ホーム画面からプロバイダーの作成を行いましょう

次にチャネルの設定タブを選択し、[新規チャネルの作成]をクリックします。
WS000003.JPG

チャネルの種類が表示されるので、[Messaging API]をクリックします。
WS000004.JPG
Messaging APIの作成画面に遷移するので、スクロールしながら必須項目の[チャネル名]、[チャネル説明]、[大業種]、[小業種]を入力します。(今回はそれぞれ、「ec2-notification」、「ec2-notification」、「個人」、「個人(IT・コンピュータ)」を入力しています)
WS000005.JPG

さらに画面をスクロールし、利用規約にチェック後、[作成]ボタンをクリックします。
WS000006.JPG

以上で[ec2-notification-to-LINEAPI]のチャネル作成が完了します。
あとは[Messaging API設定]タブから、本チャネルのQRコードを読み込んでLINE登録を行いましょう。
WS000011.JPG

また本実装では、後続のLambda関数作成で以下2つの情報が必要となります。

・ユーザーID

[チャネルの基本設定]タブを選択し、下部へスクロールすると[あなたのユーザーID]という項目があるので、この文字列をメモしておきます。
WS000009.JPG

・チャネルアクセストークン

[Messaging API設定]タブを選択し、下部へスクロールすると[チャネルアクセストークン]という項目があるので、[発行]をクリックします。
するとトークンが発行されるので、この文字列をメモしておきます。
WS0010.JPG

②EC2インスタンスの情報を取得するLambdaコードの作成

次にLambdaコードの作成を行います。
まずはAWS Lambdaのコンソールを開き、[関数を作成]をクリックします。
WS000000.JPG

次に基本的な情報を入力していきます。
今回は関数名を「ec2-notification-to-LINEAPI」とし、ランタイムは「Python 3.9」を選択して[関数の作成]をクリックします。
WS000015.JPG
以上でLambda関数が作成されます。
ここからは、「lambda_function.py」をにコードを記述していきます。

・LINE Messaging APIへのメッセージ送信方法

今回はLINE APIで時間にメッセージを送信するので、LINE Messaging APIのプッシュメッセージの送信を利用します。
https://api.line.me/v2/bot/message/push 」に対してjson形式で以下の情報をPOSTすることによって、APIにプッシュメッセージを送信することが出来ます。

'Content-Type: application/json'
'Authorization: Bearer {channel access token}'
'{
    "to": ["U4af4980629...","U0c229f96c4..."],
    "messages":[
        {
            "type":"text",
            "text":"Hello, world1"
        }
    ]
}'
・EC2インスタンス起動情報の取得

EC2インスタンスの起動情報については、Boto3ライブラリをインポートし、describe_instances()で出力することによって取得が行えます。
詳細については「boto3でec2をdescribeして値を取り出す」の記事に詳しく載っていますので、こちらをご参照ください。

以上を参考にし、「lambda_function.py」のコードを記述します。
「チャネルアクセストークン」と「ユーザーID」には、「①Line Messaging APIの作成」で控えておいたLINE Messaging APIチャネル情報を入力します。

lambda_function.py
import boto3;
import json
import urllib.request

def lambda_handler(event, context):
    #EC2インスタンス情報を取得
    ec2 = boto3.client('ec2')
    reservation = ec2.describe_instances()['Reservations']

    #起動状態のインスタンスがあればインスタンスidを配列に格納
    running_ec2_list = []
    for instance in reservation:
        state = instance['Instances'][0]['State']['Name']
        if state.__eq__('running'):
            running_ec2_list.append(instance['Instances'][0]['InstanceId'])

    #配列が空でなければLINE Botで通知
    if len(running_ec2_list) != 0:
        text = ""
        for run_ec2 in running_ec2_list:
            text = text + (run_ec2 + "のEC2インスタンスが起動中です。\n")
        text = text.rstrip("\n")
        url = 'https://api.line.me/v2/bot/message/push'
        headers = {
            'Content-Type': 'application/json',
            'Authorization': 'Bearer ' + 'チャネルアクセストークン'
        }
        body = {
            'to': "ユーザーID",
            'messages': [
                {
                    "type": "text",
                    "text": text,
                }
            ]
        }

    req = urllib.request.Request(url, data=json.dumps(body).encode(), method='POST', headers=headers)
    urllib.request.urlopen(req)

    return {
        'statusCode': 200,
    }

これでLambda関数は完成です。

③IAMロールをLambdaに付与

次にLambdaがEC2インスタンス情報を取得できるようにするため、LambdaにIAMロールを設定します。
Lambda関数の画面から、[設定] > [アクセス権限]をクリックするとデフォルトの実行ロールがあるので、こちらをクリックします。
WS000022.JPG
ロールの設定画面に遷移するので、[ポリシーをアタッチします]のボタンをクリックします。
WS000023.JPG
ポリシーの一覧から[AmazonEC2ReadOnlyAccess]を探してチェックを入れ、[ポリシーのアタッチ]ボタンをクリックします。
WS000024.JPG
ロールに[AmazonEC2ReadOnlyAccess]が追加されていれば設定は完了です。
WS000025.JPG

④Amazon EventBridgeでスケジュール設定

最後に作成したLambda関数をスケジュール実行するための設定を行います。
「ec2-notification-to-LINEAPI」関数の画面から、[トリガーを追加]をクリックします。
WS000016.JPG
トリガーの設定画面に遷移するので、リストから[EventBridge(CloudWatch Events)]を選択して[新規ルールの作成]のラジオボタンにチェックを入れます。
WS000017.JPG

ルール名に任意の名前を入力します。(今回は「ec2-instances-check」としています)
また、スケジュール式の欄には、cronの起動設定を入力します。今回はUTCで毎日0:00(ローカルタイムで毎日9:00)に起動するよう設定を行い、[追加]ボタンをクリックします。
WS000019.JPG

作成したスケジュールがトリガーに追加されれば、設定は完了です。
WS000020.JPG

動作確認

試しにC2インスタンスを起動した状態で翌朝9:00を迎えてみます。
するとLINEにて、以下のメッセージを受信することができました。
unnamed.jpg

最後に

今回はLambdaとEventBridge、LINE Messgging APIを使用してシンプルな通知の仕組みを作成してみました。
他にも工夫することで、別のAWSリソース情報の取得や別サービスへの連携を行うことが出来そうです。

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