【アップデート】ついに来た!CloudFormationで手動で作成したリソースをStackにインポート可能になりました
大栗です。
ついにCloudFormation以外で作成したリソースもCloudFormationの管理化にできるアップデートが来ました!!!長期的にCloudFormationで環境を管理すると辛くなってくる部分を解消できると思います。早速レポートします。
- New – Import Existing Resources into a CloudFormation Stack
- AWS CloudFormation Launches Resource Import
- Bringing Existing Resources Into CloudFormation Management
既存リソースのインポート
CloudFormationはInfrastructure as Codeを実現する良いサービスなのですが、緊急の場合などにどうしてもCloudFormationを使わずにCLIや手動でリソースを作成してしまうことがありCloudFormationによる環境の管理を挫折せざるを得なくなることがあります。今回のアップデートにより、別途作成したリソースをCloudFormationnスタックの管理に組み込めるようになります。
既存のリソースをスタックへ組み込む場合は、以下のような手順で行います。
- テンプレート上に既存リソースと同様の内容を追加する
-
- で変更したテンプレートと追加するリソースのIDを指定して、インポート操作を行う
- スタックに既存リソースが追加される
インポートは、新規でスタックを作成する事も、既存のスタックに追加することも可能です。
注意点
インポートするリソースは、テンプレート上でDeletionPolicyをRetainにする必要があります。
また、インポートできるものはドリフト検出ができるリソースのみです。具体的なリソースは以下のドキュメントで確認して下さい。
Resources that Support Import Operations
やってみた
以下のような流れで試してみます。リソースをスタックに追加して、最終的にCloudFormation経由で削除してみます。
- DynamoDBをCloudFormationを使わずに作成する
- DynamoDBをインポートしつつ新規にCloudFormationスタックを作成する
- EC2とSecurity GroupをCloudFormationを使わずに作成する
- EC2とSecurity Groupをインポートしつつ新規にCloudFormationスタックを作成する
- CloudFormationのDeletionPolicyを変更する
- CloudFormationと共にリソースを削除する
前提として、東京リージョンで実行しています。
DynamoDBをCloudFormationを使わずに作成する
まずDynamoDBを作成します。ここではAWS CLIで作成します。ここでは2個のテーブルを作成します。aws dynamodb create-tableコマンドで作成します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 | $ aws dynamodb create-table \> --region ap-northeast-1 \> --attribute-definitions AttributeName=key,AttributeType=S \> --table-name Service \> --key-schema AttributeName=key,KeyType=HASH \> --billing-mode PAY_PER_REQUEST{ "TableDescription": { "TableArn": "arn:aws:dynamodb:ap-northeast-1:123456789012:table/Service", "AttributeDefinitions": [ { "AttributeName": "key", "AttributeType": "S" } ], "ProvisionedThroughput": { "NumberOfDecreasesToday": 0, "WriteCapacityUnits": 0, "ReadCapacityUnits": 0 }, "TableSizeBytes": 0, "TableName": "Service", "BillingModeSummary": { "BillingMode": "PAY_PER_REQUEST" }, "TableStatus": "CREATING", "TableId": "12345678-1234-1234-1234-123456789012", "KeySchema": [ { "KeyType": "HASH", "AttributeName": "key" } ], "ItemCount": 0, "CreationDateTime": 1573712546.942 }} |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 | $ aws dynamodb create-table \> --region ap-northeast-1 \> --attribute-definitions AttributeName=key,AttributeType=S \> --table-name Games \> --key-schema AttributeName=key,KeyType=HASH \> --billing-mode PAY_PER_REQUEST{ "TableDescription": { "TableArn": "arn:aws:dynamodb:ap-northeast-1:123456789012:table/Games", "AttributeDefinitions": [ { "AttributeName": "key", "AttributeType": "S" } ], "ProvisionedThroughput": { "NumberOfDecreasesToday": 0, "WriteCapacityUnits": 0, "ReadCapacityUnits": 0 }, "TableSizeBytes": 0, "TableName": "Service", "BillingModeSummary": { "BillingMode": "PAY_PER_REQUEST" }, "TableStatus": "CREATING", "TableId": "12345678-1234-1234-1234-123456789012", "KeySchema": [ { "KeyType": "HASH", "AttributeName": "key" } ], "ItemCount": 0, "CreationDateTime": 1573712546.942 }} |
DynamoDBをインポートしつつ新規にCloudFormationスタックを作成する
作成したDynamoDBと同じ内容のテンプレートを作成して、インポートします。
作成したDynamoDBと同様のテンプレートを用意します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | ---AWSTemplateFormatVersion: '2010-09-09'Description: Import testResources: ServiceTable: Type: AWS::DynamoDB::Table DeletionPolicy: Retain Properties: TableName: Service AttributeDefinitions: - AttributeName: key AttributeType: S BillingMode: PAY_PER_REQUEST KeySchema: - AttributeName: key KeyType: HASH GamesTable: Type: AWS::DynamoDB::Table DeletionPolicy: Retain Properties: TableName: Games AttributeDefinitions: - AttributeName: key AttributeType: S BillingMode: PAY_PER_REQUEST KeySchema: - AttributeName: key KeyType: HASH |
ここでCloudFormationのコンソールを開きます。スタックの作成から既存のリソースを使用 (リソースをインポート)をクリックします。
次へをクリックします。
用意したテンプレートをアップロードして次へをクリックします。
作成したDynamoDBのIDを以下の様に入力して次へをクリックします。
| リソース論理ID | 識別子の値 |
|---|---|
| GamesTable | Games |
| ServiceTable | Service |
スタックの名前に任意の名前を入力して次へをクリックします。ここではImportStackと入力しています。
一番下の変更で、アクションがImportになっていることを確認して、リソースをインポートをクリックします。
少しすると、リソースがインポートされます。
スタック上でリソースが見えてます。
EC2とSecurity GroupをCloudFormationを使わずに作成する
次はEC2とSecurity Groupをスタックに追加するためにAW CLIで作成します。
Security Groupを作成します。
1 2 3 4 5 6 7 | $ aws ec2 create-security-group \ --description cfn-import-test \ --group-name cfn-import-test \ --vpc-id vpc-abcdefgh{ "GroupId": "sg-1234567890abcdefg"} |
EC2を作成します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | $ aws ec2 run-instances --image-id ami-0064e711cbc7a825e \ --instance-type m5.large \ --subnet-id subnet-12345678 \ --security-group-ids sg-1234567890abcdefg \{ "Instances": [ { "Monitoring": { "State": "disabled" }, "PublicDnsName": "", "StateReason": { "Message": "pending", "Code": "pending" }, ・・・ } ], "ReservationId": "r-abcdefg1234567890", "Groups": [], "OwnerId": "123456789012"} |
EC2とSecurity Groupをインポートしつつ新規にCloudFormationスタックを作成する
EC2とSecurity Groupを追加したテンプレートを用意します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 | ---AWSTemplateFormatVersion: '2010-09-09'Description: Import testParameters: VPCID: Type: String GROUPID: Type: String SUBNETID: Type: StringResources: ServiceTable: Type: AWS::DynamoDB::Table DeletionPolicy: Retain Properties: TableName: Service AttributeDefinitions: - AttributeName: key AttributeType: S BillingMode: PAY_PER_REQUEST KeySchema: - AttributeName: key KeyType: HASH GamesTable: Type: AWS::DynamoDB::Table DeletionPolicy: Retain Properties: TableName: Games AttributeDefinitions: - AttributeName: key AttributeType: S BillingMode: PAY_PER_REQUEST KeySchema: - AttributeName: key KeyType: HASH TestGroup: Type: AWS::EC2::SecurityGroup DeletionPolicy: Retain Properties: GroupDescription: cfn-import-test GroupName: cfn-import-test VpcId: !Ref VPCID TestInstance: Type: AWS::EC2::Instance DeletionPolicy: Retain Properties: ImageId: ami-0064e711cbc7a825e InstanceType: m5.large SecurityGroupIds: - !Ref GROUPID SubnetId: !Ref SUBNETID |
ここでCloudFormationのコンソールを開きます。対象のスタックを選択して、スタックアクションからスタックへのリソースのインポートをクリックします。
次へをクリックします。
用意したテンプレートをアップロードして次へをクリックします。
作成したEC2のIDを以下の様に入力して次へをクリックします。
| リソース論理ID | 識別子の値 |
|---|---|
| TestInstance | <作成したEC2のID> |
| TestGroup | <作成したSecurity GroupのID> |
パラメータを入力して次へをクリックします。
| リソース論理ID | 識別子の値 |
|---|---|
| GROUPID | <作成したSecurity GroupのID> |
| SUBNETID | <EC2を配置したサブネットのID> |
| VPCID | <作成したSecurity GroupのVPC> |
一番下の変更で、アクションがImportになっていることを確認して、リソースをインポートをクリックします。
少しすると、リソースがインポートされます。
スタックを新規作成したときと同様に、スタック上でリソースが見えてます。
CloudFormationのDeletionPolicyを変更する
リソースを削除するために、DeletionPolicyを削除したテンプレートを用意します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 | ---AWSTemplateFormatVersion: '2010-09-09'Description: Import testParameters: VPCID: Type: String GROUPID: Type: String SUBNETID: Type: StringResources: ServiceTable: Type: AWS::DynamoDB::Table DeletionPolicy: Delete Properties: TableName: Service AttributeDefinitions: - AttributeName: key AttributeType: S BillingMode: PAY_PER_REQUEST KeySchema: - AttributeName: key KeyType: HASH GamesTable: Type: AWS::DynamoDB::Table DeletionPolicy: Delete Properties: TableName: Games AttributeDefinitions: - AttributeName: key AttributeType: S BillingMode: PAY_PER_REQUEST KeySchema: - AttributeName: key KeyType: HASH TestGroup: Type: AWS::EC2::SecurityGroup DeletionPolicy: Delete Properties: GroupDescription: cfn-import-test GroupName: cfn-import-test VpcId: !Ref VPCID TestInstance: Type: AWS::EC2::Instance DeletionPolicy: Delete Properties: ImageId: ami-0064e711cbc7a825e InstanceType: m5.large SecurityGroupIds: - !Ref GROUPID SubnetId: !Ref SUBNETID |
ここでCloudFormationのコンソールを開きます。対象のスタックを選択して、更新するをクリックします。
既存テンプレートを置き換えるを選択して、更新したテンプレートをアップロードして次へをクリックします。
パラメータを変更せずに次へをクリックします。
次へをクリックします。
変更セットのプレビューに何もないことを確認して、スタックの更新をクリックします。
UPDATE_COMPLETE になるのを待ちます。
CloudFormationと共にリソースを削除する
CloudFormationスタックを削除して、インポートしたリソースも消えることを確認します。
削除前のリソースを確認します。
DynamoDBにテーブルが2個あります。
Security Groupです。
EC2です。
ここでスタックを削除します。ここでCloudFormationのコンソールで対象のスタックを選択して、削除をクリックします。
スタックの削除をクリックします。
スタックが削除されていきます。
各リソースもDELETE_COMPLETEになっています。
各々の画面でも確認してみます。
DynamoDBのテーブルが消えています。
Security Groupも消えています。
EC2もterminatedになっています。
CloudFormationの管理として削除できました。
さいごに
既存リソースのインポートは、ずっと待っていてようやく出てきた機能でした。これがあると環境をCloudFormationで管理して長期で運用することがしやすくなると思われます。私にもいくつかCloudFormationで管理している環境が、手動で作成してしまった場合は、一旦削除してCloudFormationで再作成したりといった大変手間がかかる運用となっていました。今回のアップデートをどんどん使っていきたいと思います。