bauer's diary

凡人の凡人による凡人のための備忘録

AWS LambdaでサーバーレスにEC2メンテナンスをslackに通知する 〜その3〜

登場人物おさらい

この記事では4を行っていきます。

  1. Lambdaを実行するIAMにアタッチするポリシー
  2. スケジュール実行に必要なCloudWatch Events設定
  3. SlackのIncoming Webhooks設定/Webhook URL取得
  4. Lambda Functionの作成・実装


Lambda前提知識

  1. メモリはデフォルト128MBで、64MBごとに最大1.5GBまで指定可能
  2. タイムアウト時間はデフォルト3秒で、最大5分まで指定可能
  3. ステートレスに実装する必要あり。永続化したい場合はDynamoDBやS3などを利用する。
  4. ディスクIOは/tmp領域のみ読み書き可能
  5. リクエスト数、遅延、可用性とエラー率のメトリクスはCloudWatchに、実行時のログはCloudWatch Logsに保存され、後から参照可能

AWSコンソールからLambda Functionの作成

サービス一覧から Lambda を選択します。
f:id:kitakitabauer:20161211111959p:plain

Create a Lambda function を選択します。
f:id:kitakitabauer:20161211114337p:plain

Select blueprint ではLambdaのワークフローにおいて、様々なテンプレートが用意されています。
今回は関連するサービスを一から選択するので、Blank Function を選択します。
f:id:kitakitabauer:20161211114554p:plain

Configure triggers では下記の通り選択していきます。
f:id:kitakitabauer:20161211114922p:plain
トリガーにはプルダウンから CloudWatch Events - Schedule を選択します。

  • Rule name:イベントのルール名を決めます。
  • Rule description:イベントルールの詳細を入力します。
  • Schedule expression:実行間隔を指定します。
  • Enable trigger:実装が完了するまでは無効にしておかないと、途中状態のコードで実行されてしまうので注意してください。

作成したら関数 → トリガー一覧に、下記のようなトリガーが作成されます。
f:id:kitakitabauer:20170406232429p:plain

Lambda Function作成

細かい設定を行っていきます。
f:id:kitakitabauer:20170413233321p:plain

  • 名前:関数名を指定します。
  • 説明:この関数の説明を記述します。
  • ランタイム:Lambdaの実行環境です。ここではNode.js 6.10を指定します。

ランタイムは2017/04/12時点で他に、下記の環境を指定することができます。

コードエントリタイプについて

コンソール上の説明に記述されたとおり、aws-sdk以外のカスタムライブラリ以外が必要ない場合は、インライン編集で十分かと思います。

  • コードをインラインで編集
  • .ZIP ファイルをアップロード:ライブラリ毎固めてzipファイルでアップロードします。
  • Amazon S3 からのファイルアップロード:選択すると、S3 リンクのURLが指定できるようになります。

今回はlodashやslack-nodeなどの外部モジュールを使いたかったので、
node_modules込みでzip形式でアップロードしました。

環境変数

コードの再利用性を考えて、環境変数にアクセス先などを指定しています。
f:id:kitakitabauer:20170413221755p:plain

  • SLACK_CHANNEL:通知したいslackのチャンネル名です。
  • SLACK_ICON_EMOJI:slackに通知したときのアイコンです。ここではoctodexに投稿された画像をアイコンとして使っています。
  • SLACK_USERNAME:slackに通知したときのユーザ名です。
  • REGION:LambdaやEC2を用意しているリージョンです。
  • WEBHOOK_URI:前回の記事の3.で取得したSlackのIncoming Webhooks URLです。
Lambda 関数ハンドラおよびロール

f:id:kitakitabauer:20170412212604p:plain

  • ハンドラ:index.handler
  • ロール:既存のロールを選択
  • 既存のロール:lambda_basic_execution

ハンドラはindex.js内のexports.handlerを呼び出すのでこのままでよいです。
ロールは前回の記事の1.で作成したロールを指定します。

f:id:kitakitabauer:20170406231459p:plain
タイムアウトはデフォルトの3秒から10秒に変更します。
このぐらいの処理であれば3秒のままでも正常終了はしますが、エラーが表示されたためです。

ネットワーク・セキュリティ

f:id:kitakitabauer:20170412214210p:plain
VPC内で実行するため、VPCとサブネット、セキュリティグループをそれぞれ指定しています。
尚、同じVPC内ではなくても、APIのリクエスト次第で指定したサブネット以外の全インスタンスのステータスが取れたので、開発環境を指定するとよいかと思います。

実行結果

以上、1〜4 まで全ての設定を行うことで、このように朝10時にチェックが走り、その結果を通知するようになりました。
尚、メンテナンスイベントが何もない場合は通知しないようにしています。
f:id:kitakitabauer:20170407101232p:plain

InstanceStateはそれぞれ、

  • 0 (pending)
  • 16 (running)
  • 32 (shutting-down)
  • 48 (terminated)
  • 64 (stopping)
  • 80 (stopped)

を示しています。
この例でいくと、instance-stop イベントなので、稼働中のインスタンスにおいて再起動が必要です。
予定された日時に停止してかまわなければこのままでよいですが、対処しないと同じ通知が飛ぶので、基本的には手動で停止 → 起動を行ったほうがよさそうです。

尚、AWSコンソールからも同じ内容が確認できました。
f:id:kitakitabauer:20170407101241p:plain


大変長い記事となってしまいましたが、
最後に次回の記事で、実際のコードと解説・及び困ったことを紹介していきます。

次回の記事はこちら。
kitakitabauer.hatenablog.com