大事なことなので要確認
CloudFormationテンプレートからCloudWatchアラームを作るのではなく、すでに存在しているCloudWatchアラームからCloudFormationテンプレートを作ります。
繰り返します。アラーム設定からCloudFormationテンプレートを作ります。
アラーム数が少ない場合
CloudWatchアラームが少ない場合は手作業でソースを取得しても良い。
やり方としては、AWSコンソールより、対象となるCloudWatchアラームを選択 > アクション > ソースを表示より、JSONやYAML形式でダウンロードできます。
また、aws-cliを使うことで、取得とある程度の整形もできます。
JSONとYAMLの整形ライブラリであるjqとyqをインストールした状態で、
brew install jq python-yq
下記のようにすると、resouces以下に記述すべき内容が取得できます。このままではフォーマットがあってないため、手動で修正してください。
aws --profile <YOUR_PROFILE> cloudwatch describe-alarms | \
jq '.MetricAlarms | map({"AlarmName": .AlarmName, "AlarmDescription": .AlarmDescription, "ActionsEnabled": .ActionsEnabled, "OKActions": .OKActions, "AlarmActions": .AlarmActions, "InsufficientDataActions": .InsufficientDataActions, "MetricName": .MetricName, "Namespace": .Namespace, "Statistic": .Statistic, "Dimensions": .Dimensions, "Period": .Period, "EvaluationPeriods": .EvaluationPeriods, "DatapointsToAlarm": .DatapointsToAlarm, "Threshold": .Threshold, "ComparisonOperator": .ComparisonOperator, "TreatMissingData": .TreatMissingData})' | \
yq -y
アラーム数が多い場合
下記例では、Pythonにてアラーム設定を全件取得し、YAML形式で出力します。boto3をインストールした状態でお試しください。CloudFormationテンプレートのResources以下に全行インデントを合わせた状態で挿入してください。また、繰り返し使用するARNや環境はParameterとして定義することをオススメします。
#! /usr/bin/env python3
# -*- coding: utf-8 -*-
import yaml
from boto3.session import Session
session = Session(profile_name=YOUR_PROFILE)
cloudwatch = session.client('cloudwatch')
alarms = []
# 取得件数最大値を指定しない場合は50件が最大値となる
# 全件取得するためにループを回す
response = cloudwatch.describe_alarms()
alarms = response['MetricAlarms']
while True:
if 'NextToken' in response:
response = cloudwatch.describe_alarms(NextToken=response['NextToken'])
alarms.extend(response['MetricAlarms'])
else:
break
# CFnに必要なキー
keys = [
"AlarmName", "AlarmDescription", "ActionsEnabled", "OKActions",
"AlarmActions", "InsufficientDataActions", "MetricName", "Namespace",
"Statistic", "Dimensions", "Period", "EvaluationPeriods",
"DatapointsToAlarm", "Threshold", "ComparisonOperator", "TreatMissingData"
]
for alarm in alarms:
properties = {k: v for k, v in alarm.items() if k in keys}
# resource名として既存のAlarmNameを使用しているが適宜変更してください。
# ハイフンやアンダースコアは使えません
dic = {
alarm["AlarmName"]: {
"Type": "AWS::CloudWatch::Alarm",
"Properties": properties
}
}
resource_str = yaml.dump(dic, allow_unicode=True)
print(resource_str)
補足
作成したYAMLファイルがCloudFormationテンプレートとして文法的に正しいかどうかは下記コマンドでチェックできます。
aws cloudformation validate-template --template-body ./cloud-watch-alarm.yml
# ファイル内文字列が長い場合はS3上にアップロードする必要があります
aws cloudformation validate-template --template-url https://s3-ap-northeast-1.amazonaws.com/xxxx/cloud-watch-alarm.yml