zuntan02のはてなブログ

備忘録的なものです。時々職場の技術者ブログにも転記してますが、メインはこちらで。

【AWS】CloudwatchのアラームをSNS→Lambda→Teamsに送るメモ

【概要】

Lambdaの既存設計図 cloudwatch-alarm-to-slack-python
をベースに以下を作成した。とりあえず届けばいい人向け。
HookURLのあたりはよくわからんのでLambdaの環境変数にそのまま持たせてます

【参考】

https://www.geekfeed.co.jp/geekblog/aws_cloudwatch_to_slack/
例によってほぼそのままです。

【詳細】

Lambdaの関数作成

  • 関数名:cloudwatch-alarm-to-teams-python
  • ランタイム:Python 3.8
  • アクセス権限:実行ロール:基本的な Lambda アクセス権限で新しいロールを作成

[設定]-[環境変数]で以下の環境変数を追加
キー:HookUrl
値:TeamsのWebHook

コード

#!/usr/bin/python3.8
import boto3
import json
import logging
import os

from urllib.request import Request, urlopen
from urllib.error import URLError, HTTPError

logger = logging.getLogger()
logger.setLevel(logging.INFO)

HOOK_URL = os.environ['HookUrl']

def lambda_handler(event, context): 

    logger.info("Event: " + str(event))
    message = json.loads(event['Records'][0]['Sns']['Message'])
    logger.info("Message: " + str(message))

    alarm_name = message['AlarmName']
    #old_state = message['OldStateValue']
    new_state = message['NewStateValue']
    reason = message['NewStateReason']
    alarm_description = message['AlarmDescription']

    alert_msg = {
        'text': "アラーム名: %s<br>ステータス: %s<br>アラーム理由: %s<br>説明: %s" % (alarm_name, new_state, reason, alarm_description)
    }
    req = Request(HOOK_URL, json.dumps(alert_msg).encode('utf-8'))
    try:
        response = urlopen(req)
        response.read()
        logger.info("Message posted")
    except HTTPError as e:
        logger.error("Request failed: %d %s", e.code, e.reason)
    except URLError as e:
        logger.error("Server connection failed: %s", e.reason)
SNSとの連携

AmazonSNSを作成し、サブスクリプションとして
プロトコルAWS Lambda
エンドポイント:作成したLambda
を設定する

SNSが呼ばれると、以下の様なメッセージがTeamsのチャンネルに届く

アラーム名: CPUUtilization_over_70Percent
ステータス: ALARM
アラーム理由: Threshold Crossed: 1 out of the last 1 datapoints [0.0 (14/04/21 09:15:00)] was less than the threshold (70.0) (minimum 1 datapoint for OK -> ALARM transition).
説明: CPUUtilization_over_70Percent