はじめに
AWSをCloudFormationで構築したものの、「急ぎだったのでAWSコンソールから変更した」
「ちょっとした修正だから手でやった」という経験はありませんか?
私もCloudFormationでインフラを管理していましたが、運用を続ける中で何度かAWSコンソールから直接設定を変更することがありました。
その結果、CloudFormationテンプレートと実際のAWS環境の内容が一致しなくなってしまいました。
今後はCloudFormationを正として運用するため、ChangeSetを利用したデプロイへ移行することにしました。
この記事ではChangeSetの概要から、既に手修正してしまった環境への適用方法まで紹介します。
CloudFormationとは
CloudFormationはAWSリソースをコードで管理するIaC(Infrastructure as Code)サービスです。
例えば、VPC、ECS、RDSなどをテンプレート(YAML/JSON)で管理できます。
理想的には
CloudFormation Template
│
▼
AWS環境
という状態になります。
なぜChangeSetを使うのか
CloudFormationを更新する際、
aws cloudformation deploy
だけでも更新できます。
しかし実際には、「どのリソースが変更されるのか」が分からないまま更新されます。
そこで利用するのがChangeSetです。
ChangeSetは 「実際には更新せず、何が変更されるかだけ確認できる機能」 になります。
イメージはGitのdiffに近いです。
Template変更
│
ChangeSet作成
│
変更内容確認
│
問題なし
│
Execute ChangeSet
│
AWS更新
ChangeSetで確認できること
例えばSecurityGroupを変更した場合
Modify
AWS::EC2::SecurityGroup
変更内容
80番ポート追加
IAM Roleを追加した場合
Add
AWS::IAM::Role
不要になったS3を削除する場合
Remove
AWS::S3::Bucket
というように
- Add
- Modify
- Remove
が一覧表示されます。
基本的な利用手順
1. テンプレート修正
例
Resources:
SampleBucket:
Type: AWS::S3::Bucket
2. ChangeSet作成
aws cloudformation create-change-set \
--stack-name sample-stack \
--template-body file://template.yaml \
--change-set-name change-001
まだAWSは変更されません。
3. 差分確認
aws cloudformation describe-change-set \
--stack-name sample-stack \
--change-set-name change-001
ここで
- Add
- Modify
- Remove
を確認します。
4. 実行
問題がなければ
aws cloudformation execute-change-set \
--stack-name sample-stack \
--change-set-name change-001
これで初めてAWS環境が更新されます。
一番困るケース
CloudFormation管理なのに手修正してしまった場合
例えば
CloudFormationでは
EC2
↓
SecurityGroup
22のみ
だったとします。
ある日、
AWSコンソールから
80追加
しました。
すると、CloudFormationは
22のみ
と思っています。実際のAWSは
22
80
です。
つまり
Template
≠
AWS
になっています。
この状態でChangeSetすると?
テンプレートを更新すると、CloudFormationは 「80番ポートはいらない」 と判断する可能性があります。
つまり、手修正した内容を元に戻してしまうケースがあります。
これがCloudFormation運用で一番怖いところです。
対応方法
私が考えている運用は次の手順です。
-
現在のAWS設定を確認
↓ -
手修正内容をテンプレートへ反映
↓ -
CloudFormationとの差分をゼロにする
↓ -
ChangeSet作成
↓ -
差分確認
↓ -
実行
つまり、CloudFormationを常に正とする運用へ戻します。
運用ルール
今後は次のルールで運用する予定です。
- AWSコンソールから直接変更しない
- テンプレートを必ず修正する
- 変更前にChangeSetを確認する
- 問題なければ実行する
- 緊急時に手修正した場合は必ずテンプレートへ反映する
これだけでも事故はかなり減らせます。
まとめ
CloudFormationは非常に便利ですが、運用を続けていると「ちょっとだけAWSコンソールから変更」をやってしまいがちです。
しかし、その積み重ねがCloudFormationとの差分を生み、予期しないリソース変更につながります。
ChangeSetを利用すると 「何が変更されるか」「どのリソースが更新されるか」「削除されるものは何か」 を事前に確認できます。
おわりに
リリースで大変な思いをしました。今後はCloudFormationを唯一の正しい構成情報(Source of Truth)として管理し、ChangeSetを利用した安全なデプロイを行っていきたいと思います。
参考(感謝)
- AIに聞きながら
