CloudFormation Resource Import

Bringing Existing Resources Into CloudFormation Management

If you created an AWS resource outside of AWS CloudFormation management, you can bring this existing resource into AWS CloudFormation management using resource import. You can manage your resources using AWS CloudFormation regardless of where they were created without having to delete and re-create them as part of a stack.

Resources that Support Import Operations

Import operations support the following resource types. Import operations support the same resource types that drift detection supports.

Resource Import Overview

During an import operation, you create a change set that imports your existing resources into a stack or creates a new stack from your existing resources. You provide the following during import.

  • A template that describes the entire stack, including both the original stack resources and the resources you’re importing. Each resource to import must have a DeletionPolicy attribute.
  • Identifiers for the resources to import. You provide two values to identify each target resource.
    • An identifier property. This is a resource property that can be used to identify each resource type. For example, an AWS::S3::Bucket resource can be identified using its BucketName.
    • An identifier value. This is the target resource’s actual property value. For example, the actual value for the BucketName property might be MyS3Bucket.

Resource Import Validation

During an import operation, AWS CloudFormation performs the following validations.

  • The resource to import exists.
  • The properties and configuration values for each resource to import adhere to the resource type schema, which defines its accepted properties, required properties, and supported property values.
  • The required properties are specified in the template. Required properties for each resource type are listed in the Resource and Property Reference.
  • The resource to import does not belong to another stack in the same Region.

AWS CloudFormation does not check that the template configuration matches the actual configuration of resource properties.

Resource Import Status Codes

This table describes the various status types used with resource import.

Drift Detection Operation StatusDescription
IMPORT_IN_PROGRESSThe import operation is currently in progress.
IMPORT_COMPLETEThe import operation successfully completed for all resources in the stack that support resource import.
IMPORT_ROLLBACK_IN_PROGRESSImport will roll back to the previous template configuration, not necessarily the actual configuration.
IMPORT_ROLLBACK_FAILEDThe import rollback operation failed for at least one resource in the stack. Results will be available for the resources CloudFormation successfully imported.
IMPORT_ROLLBACK_COMPLETEImport successfully rolled back to the previous template configuration.

Considerations During an Import Operation

  • After the import is complete and before performing subsequent stack operations, we recommend running drift detection on imported resources. Drift detection ensures that the template configuration matches the actual configuration.
  • Import operations don’t allow new resource creations, resource deletions, or changes to property configurations.
  • Each resource to import must have a DeletionPolicy attribute for the import operation to succeed. The DeletionPolicy can be set to any possible value. Only target resources need a DeletionPolicy. Resources that are already part of the stack don’t need a DeletionPolicy.
  • You cannot import the same resource into multiple stacks.
  • You can use the cloudformation:ImportResourceTypes IAM policy condition to control which resource types IAM users can work with during an import operation.
  • The AWS CloudFormation stack limits apply when importing resources. For more information on limits, see AWS CloudFormation Limits.
  • Resource import is available in the US East (N. Virginia), US East (Ohio), US West (N. California), US West (Oregon), Canada (Central), Asia Pacific (Mumbai), Asia Pacific (Seoul), Asia Pacific (Singapore), Asia Pacific (Sydney), Asia Pacific (Tokyo), Europe (Frankfurt), Europe (Ireland), Europe (London), Europe (Paris), and South America (São Paulo) Regions.

 

Creating a Stack From Existing Resources

During this import operation, you need to provide the following.

  • A template that describes the resources that will be in the new stack and the resource configurations. Each resource in your template must have a DeletionPolicy attribute.
  • A unique identifier for each target resource. Visit the appropriate service console to obtain unique identifiers.

In this walkthrough, we provide the following example template, called templateToImport.jsonServiceTable and GamesTable are the targets of the import.

{
    "AWSTemplateFormatVersion": "2010-09-09",
    "Description": "Import test",
    "Resources": {
         "ServiceTable":{
           "Type":"AWS::DynamoDB::Table",
           "DeletionPolicy": "Retain",
           "Properties":{
              "TableName":"Service",
              "AttributeDefinitions":[
                 {
                    "AttributeName":"key",
                    "AttributeType":"S"
                 }
              ],
              "KeySchema":[
                 {
                    "AttributeName":"key",
                    "KeyType":"HASH"
                 }
              ],
              "ProvisionedThroughput":{
                 "ReadCapacityUnits":5,
                 "WriteCapacityUnits":1
              }
           }
        },
        "GamesTable": {
            "Type": "AWS::DynamoDB::Table",
            "DeletionPolicy": "Retain",
            "Properties": {
                "TableName": "Games",
                "AttributeDefinitions": [
                    {
                        "AttributeName": "key",
                        "AttributeType": "S"
                    }
                ],
                "KeySchema": [
                    {
                        "AttributeName": "key",
                        "KeyType": "HASH"
                    }
                ],
                "ProvisionedThroughput": {
                    "ReadCapacityUnits": 5,
                    "WriteCapacityUnis": 1
                }
            }
        }
    }
}

Create a Stack from Existing Resources Using the AWS CloudFormation Console

  1. Open the AWS CloudFormation console.
  2. On the Stacks page, choose Create stack, and then choose With existing resources (import resources).
     The Create stack from existing resources option in the console.
  3. Read the Import overview page for a list of things you’re required to provide during this operation. Then, choose Next.
  4. On the Specify template page, provide your template using one of the following methods, and then choose Next.
    • Choose Amazon S3 URL, and then specify the URL for your template in the text box.
    • Choose Upload a template file, and then browse for your template.
  5. On the Identify resources page, identify each target resource.
    1. Under Identifier property, choose the type of resource identifier. For example, the AWS::DynamoDB::Table resource can be identified using the TableName property.
    2. Under Identifier value, type the actual property value. For example, the TableName for the GamesTable resource in the example template is Games.
       The Identify resources page in the console.
    3. Choose Next.
  6. On the Specify stack details page, modify any parameters, and then choose Next. This automatically creates a change set.

    Important

    The import operation fails if you modify existing parameters that trigger a create, update, or delete operation.

  7. On the Review stack-name page, confirm that the correct resources are being imported, and then choose Import resources. This automatically runs the change set created in the last step.
  8. The Events pane of the Stack details page for your new stack displays.
     The Events tab in the console.
  9. (Optional) Run drift detection on the stack to make sure the template and actual configuration of the imported resources match. For more information about detecting drift, see Detect Drift on an Entire CloudFormation Stack.

Create a Stack from Existing Resources Using the AWS CLI

  1. Open the AWS CLI.
  2. Optionally run GetTemplateSummary to learn which properties identify each resource type in your template. For example, the AWS::DynamoDB::Table resource can be identified using the TableName property. For the GamesTable resource in the example template, the value of TableName is Games.
    > aws cloudformation get-template-summary
        --template-body 

    file://templateToImport.json

  3. Compose a list of the target resources from your template and their unique identifiers in the following format.”[{\”ResourceType\”:\”AWS::DynamoDB::Table\”,\”LogicalResourceId\”:\”GamesTable\”,\”ResourceIdentifier\”:{\”TableName\”:\”Games\”}}]”
  4. Create a change set of type IMPORT with the following parameters. --resources-to-import does not support inline YAML.
    > aws cloudformation create-change-set
        --stack-name 

    TargetStack

     --change-set-name 

    ImportChangeSet

     --change-set-type IMPORT --resources-to-import "[{\"ResourceType\":\"AWS::DynamoDB::Table\",\"LogicalResourceId\":\"GamesTable\",\"ResourceIdentifier\":{\"TableName\":\"Games\"}},{\"ResourceType\":\"AWS::DynamoDB::Table\",\"LogicalResourceId\":\"ServiceTable\",\"ResourceIdentifier\":{\"TableName\":\"Service\"}}]" --template-body 

    file://templateToImport.json

    The AWS CLI also supports text files as input for the --resources-to-import parameter, as shown in the following example.

    --resources-to-import: 

    file://resourcesToImport.txt

    In this walkthrough, file://resourcesToImport.txt contains the following.

    [
      {
          "ResourceType":"AWS::DynamoDB::Table",
          "LogicalResourceId":"GamesTable",
          "ResourceIdentifier": {
            "TableName":"Games"
          }
      },
      {
          "ResourceType":"AWS::DynamoDB::Table",
          "LogicalResourceId":"ServiceTable",
          "ResourceIdentifier": {
            "TableName":"Service"
          }
      }
    ]
  5. Review the change set to make sure the correct resources will be imported.
    > aws cloudformation describe-change-set --change-set-name 

    ImportChangeSet

  6. Run the change set to import the resources. On successful completion of the operation (IMPORT_COMPLETE), the resources are successfully imported.
    > aws cloudformation execute-change-set --change-set-name 

    ImportChangeSet

  7. (Optional) Run drift detection on the IMPORT_COMPLETE stack to make sure the template and actual configuration of the imported resources match. For more information on detecting drift, see Detect Drift on an Entire CloudFormation Stack.
    > aws cloudformation detect-stack-drift --stack-name 

    TargetStack

     { "Stack-Drift-Detection-Id" : "624af370-311a-11e8-b6b7-500cexample" } > aws cloudformation describe-stack-drift-detection-status --stack-drift-detection-id 

    624af370-311a-11e8-b6b7-500cexample

     > aws cloudformation describe-stack-resource-drifts --stackname 

    TargetStack

  8. (Optional) If your imported resources don’t match their expected template configurations, either correct the template configurations or update the resources directly. In this walkthrough, we correct the template configurations to match their actual configurations.
    1. Revert the import operation for the affected resources.
    2. Add the import targets to your template again, making sure that the template configurations match the actual configurations.
    3. Repeat steps 4-7 using the modified template to import the resources again.

 

Importing Existing Resources Into a Stack

During this import operation, you need to provide the following.

  • A template that describes the entire stack, including both the resources that are already part of the stack and the resources to import. Each resource to import must have a DeletionPolicy attribute in your template.
  • A unique identifier for each target resource. Visit the appropriate service console to obtain unique identifiers.

In this walkthrough, we provide the following example template, called templateToImport.jsonServiceTable is currently part of the stack, and GamesTable is the target of the import.

{
    "AWSTemplateFormatVersion": "2010-09-09",
    "Description": "Import test",
    "Resources": {
         "ServiceTable":{
           "Type":"AWS::DynamoDB::Table",
           "Properties":{
              "TableName":"Service",
              "AttributeDefinitions":[
                 {
                    "AttributeName":"key",
                    "AttributeType":"S"
                 }
              ],
              "KeySchema":[
                 {
                    "AttributeName":"key",
                    "KeyType":"HASH"
                 }
              ],
              "ProvisionedThroughput":{
                 "ReadCapacityUnits":5,
                 "WriteCapacityUnits":1
              }
           }
        },
        "GamesTable": {
            "Type": "AWS::DynamoDB::Table",
            "DeletionPolicy": "Retain",
            "Properties": {
                "TableName": "Games",
                "AttributeDefinitions": [
                    {
                        "AttributeName": "key",
                        "AttributeType": "S"
                    }
                ],
                "KeySchema": [
                    {
                        "AttributeName": "key",
                        "KeyType": "HASH"
                    }
                ],
                "ProvisionedThroughput": {
                    "ReadCapacityUnits": 5,
                    "WriteCapacityUnis": 1
                }
            }
        }
    }
}

Import an Existing Resource into a Stack Using the AWS CloudFormation Console

  1. Open the AWS CloudFormation console.
  2. On the Stacks page, choose the stack you want to import resources into.
  3. Choose Stack actions, and then choose Import resources into stack.
     The Import resources into stack option in the console.
  4. Review the Import overview page, and then choose Next.
  5. On the Specify template page, provide your updated template using one of the following methods, and then choose Next.
    • Choose Amazon S3 URL, and then specify the URL for your template in the text box.
    • Choose Upload a template file, and then browse for your template.
  6. On the Identify resources page, identify each target resource.
    1. Under Identifier property, choose the type of resource identifier. For example, the AWS::DynamoDB::Table resource can be identified using the TableName property.
    2. Under Identifier value, type the actual property value. For example, the TableName for the GamesTable resource in the example template is Games.
       The Identify resources page in the console.
    3. Choose Next.
  7. On the Specify stack details page, update any parameters, and then choose Next. This automatically creates a change set.

    Note

    The import operation fails if you modify existing parameters that trigger a create, update, or delete operation.

  8. On the Review stack-name page, review the resources to import, and then choose Import resources. This automatically runs the change set created in the last step. Any stack-level tags are applied to imported resources at this time.
  9. The Events page for the stack displays.
     The Events tab in the console.
  10. (Optional) Run drift detection on the stack to make sure the template and actual configuration of the imported resources match. For more information about detecting drift, see Detect Drift on an Entire CloudFormation Stack.

Import an Existing Resource into a Stack Using the AWS CLI

  1. Optionally run GetTemplateSummary to learn which properties identify each resource type in the template. For example, the AWS::DynamoDB::Table resource can be identified using the TableName property. For the GamesTable resource in the example template, the value of TableName is Games.
    > aws cloudformation get-template-summary 
        --template-body 

    file://templateToImport.json

  2. Compose a list of resources to import and their unique identifiers in the following format.”[{\”ResourceType\”:\”AWS::DynamoDB::Table\”,\”LogicalResourceId\”:\”GamesTable\”,\”ResourceIdentifier\”:{\”TableName\”:\”Games\”}}]”
  3. Create a change set of type IMPORT with the following parameters. --resources-to-import does not support inline YAML.
    > aws cloudformation create-change-set
        --stack-name 

    TargetStack

     --change-set-name 

    ImportChangeSet

     --change-set-type IMPORT --resources-to-import "[{\"ResourceType\":\"AWS::DynamoDB::Table\",\"LogicalResourceId\":\"GamesTable\",\"ResourceIdentifier\":{\"TableName\":\"Games\"}}]" --template-body 

    file://templateToImport.json

    The AWS CLI also supports text files as input for the resources-to-import parameter, as shown in the following example.

    --resources-to-import: 

    file://resourcesToImport.txt

    In this walkthrough, file://resourcesToImport.txt contains the following.

    [
      {
          "ResourceType":"AWS::DynamoDB::Table",
          "LogicalResourceId":"GamesTable",
          "ResourceIdentifier": {
            "TableName":"Games"
          }
      }
    ]
  4. Review the change set to make sure the correct resources will be imported.
    > aws cloudformation describe-change-set --change-set-name 

    ImportChangeSet

  5. Run the change set to import the resources. Any stack-level tags are applied to imported resources at this time. On successful completion of the operation (IMPORT_COMPLETE), the resources are successfully imported.
    > aws cloudformation execute-change-set --change-set-name 

    ImportChangeSet

  6. (Optional) Run drift detection on the IMPORT_COMPLETE stack to make sure the template and actual configuration of the imported resources match. For more information about detecting drift, see Detect Drift on an Entire CloudFormation Stack.
    > aws cloudformation detect-stack-drift --stack-name 

    TargetStack

     { "Stack-Drift-Detection-Id" : "624af370-311a-11e8-b6b7-500cexample" } > aws cloudformation describe-stack-drift-detection-status --stack-drift-detection-id 

    624af370-311a-11e8-b6b7-500cexample

     > aws cloudformation describe-stack-resource-drifts --stackname 

    TargetStack

  7. (Optional) If your imported resources don’t match their expected template configurations, either correct the template configurations or update the resources directly. In this walkthrough, we correct the template configurations to match their actual configurations.
    1. Revert the import operation for the affected resources.
    2. Add the import targets to your template again, making sure that the template configurations match the actual configurations.
    3. Repeat steps 3-6 using the modified template to import the resources again.

Moving Resources Between Stacks

Using the resource import feature, you can move resources between, or refactor, stacks. You need to first add a Retain deletion policy to the resource you want to move to ensure that the resource is preserved when you delete it from the source stack and import it to the target stack.

Refactor a Stack Using the AWS Management Console

  1. In the source template, specify a Retain DeletionPolicy for the resource you want to move.In the following example source template, GamesTable is the target of this refactor.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            },
            "GamesTable": {
                "Type": "AWS::DynamoDB::Table",
                "DeletionPolicy": "Retain",
                "Properties": {
                    "TableName": "Games",
                    "AttributeDefinitions": [
                        {
                            "AttributeName": "key",
                            "AttributeType": "S"
                        }
                    ],
                    "KeySchema": [
                        {
                            "AttributeName": "key",
                            "KeyType": "HASH"
                        }
                    ],
                    "ProvisionedThroughput": {
                        "ReadCapacityUnits": 5,
                        "WriteCapacityUnis": 1
                    }
                }
            }
        }
    }
  2. Open the AWS CloudFormation console to perform a stack update to apply the deletion policy.
    1. On the Stacks page, with the stack selected, choose Update, and then choose Update stack (standard).
    2. Under Prepare template, choose Replace current template.
    3. Under Specify template, provide the updated source template with the DeletionPolicy attribute on GamesTable, and then choose Next.
      • Choose Amazon S3 URL, and then specify the URL to the updated source template in the text box.
      • Choose Upload a template file, and then browse for the updated source template file.
    4. On the Specify stack details page, no changes are required. Choose Next.
    5. On the Configure stack options page, no changes are required. Choose Next.
    6. On the Review stack_name page, review your changes. If your template contains IAM resources, select I acknowledge that this template may create IAM resources to specify that you want to use IAM resources in the template. For more information about using IAM resources in templates, see Controlling Access with AWS Identity and Access Management. Then, either update your source stack by creating a change set or update your source stack directly.
  3. Remove the resource, related parameters, and outputs from the source template, and then add them to the target template.The source template now looks like the following.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            }
        }
    }

    The following example target template currently has the PlayersTable resource, and now also contains GamesTable.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "PlayersTable": {
                "Type": "AWS::DynamoDB::Table",
                "Properties": {
                    "TableName": "Players",
                    "AttributeDefinitions": [
                        {
                            "AttributeName": "key",
                            "AttributeType": "S"
                        }
                    ],
                    "KeySchema": [
                        {
                            "AttributeName": "key",
                            "KeyType": "HASH"
                        }
                    ],
                    "ProvisionedThroughput": {
                        "ReadCapacityUnits": 5,
                        "WriteCapacityUnits": 1
                    }
                }
            },
            "GamesTable": {
                "Type": "AWS::DynamoDB::Table",
                "DeletionPolicy": "Retain",
                "Properties": {
                    "TableName": "Games",
                    "AttributeDefinitions": [
                        {
                            "AttributeName": "key",
                            "AttributeType": "S"
                        }
                    ],
                    "KeySchema": [
                        {
                            "AttributeName": "key",
                            "KeyType": "HASH"
                        }
                    ],
                    "ProvisionedThroughput": {
                        "ReadCapacityUnits": 5,
                        "WriteCapacityUnis": 1
                    }
                }
            }
        }
    }
  4. Repeat steps 2-3 to update the source stack again, this time to delete the target resource from the stack.
  5. Perform an import operation to add GamesTable to the target stack.
    1. On the Stacks page, with the parent stack selected, choose Update, and then choose Import resources into stack.
       The Import resources into stack option in the console.
    2. Read the Import overview page for a list of things you’re required to provide during this operation. Then, choose Next.
    3. On the Specify template page, do one of the following, and then choose Next.
      • Choose Amazon S3 URL, and then specify a URL in the text box.
      • Choose Upload a template file, and then browse for a file to upload.
    4. On the Identify resources page, identify the resource you’re moving (in this example, GamesTable).
      1. Under Identifier property, choose the type of resource identifier. For example, an AWS::DynamoDB::Table resource can be identified using the TableName property.
      2. Under Identifier value, type the actual property value. For example, GamesTables.
         The Identify resources page in the console.
      3. Choose Next.
    5. On the Specify stack details page, modify any parameters, and then choose Next. This automatically creates a change set.

      Important

      The import operation fails if you modify existing parameters that trigger a create, update, or delete operation.

    6. On the Review stack-name page, confirm that the correct resource is being imported, and then choose Import resources. This automatically runs the change set created in the last step. Any stack-level tags are applied to imported resources at this time.
    7. The Events pane of the Stack details page for your parent stack displays.
       The Events tab in the console.

      Note

      It’s not necessary to run drift detection on the parent stack after this import operation because the AWS::CloudFormation::Stackresource is already managed by AWS CloudFormation.

Refactor a Stack Using the AWS CLI

  1. In the source template, specify a Retain DeletionPolicy for the resource you want to move.In the following example source template, GamesTable is the target of this refactor.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            },
            "GamesTable": {
                "Type": "AWS::DynamoDB::Table",
                "DeletionPolicy": "Retain",
                "Properties": {
                    "TableName": "Games",
                    "AttributeDefinitions": [
                        {
                            "AttributeName": "key",
                            "AttributeType": "S"
                        }
                    ],
                    "KeySchema": [
                        {
                            "AttributeName": "key",
                            "KeyType": "HASH"
                        }
                    ],
                    "ProvisionedThroughput": {
                        "ReadCapacityUnits": 5,
                        "WriteCapacityUnis": 1
                    }
                }
            }
        }
    }
  2. Update the source stack to apply the deletion policy to the resource.
    update-stack --stack-name "

    source-stack-name

    "
  3. Remove the resource, related parameters, and outputs from the source template, and then add them to the target template.The source template now looks like the following.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            }
        }
    }

    The following example target template currently has the PlayersTable resource, and now also contains GamesTable.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "PlayersTable": {
                "Type": "AWS::DynamoDB::Table",
                "Properties": {
                    "TableName": "Players",
                    "AttributeDefinitions": [
                        {
                            "AttributeName": "key",
                            "AttributeType": "S"
                        }
                    ],
                    "KeySchema": [
                        {
                            "AttributeName": "key",
                            "KeyType": "HASH"
                        }
                    ],
                    "ProvisionedThroughput": {
                        "ReadCapacityUnits": 5,
                        "WriteCapacityUnits": 1
                    }
                }
            },
            "GamesTable": {
                "Type": "AWS::DynamoDB::Table",
                "DeletionPolicy": "Retain",
                "Properties": {
                    "TableName": "Games",
                    "AttributeDefinitions": [
                        {
                            "AttributeName": "key",
                            "AttributeType": "S"
                        }
                    ],
                    "KeySchema": [
                        {
                            "AttributeName": "key",
                            "KeyType": "HASH"
                        }
                    ],
                    "ProvisionedThroughput": {
                        "ReadCapacityUnits": 5,
                        "WriteCapacityUnis": 1
                    }
                }
            }
        }
    }
  4. Update the source stack to delete the GamesTable resource and its related parameters and outputs from the stack.
    aws cloudformation update-stack --stack-name "

    source-stack-name

    "
  5. Create a change set of type IMPORT with the following parameters. --resources-to-import does not support inline YAML.
    > aws cloudformation create-change-set
        --stack-name 

    TargetStack

     --change-set-name 

    ImportChangeSet

     --change-set-type IMPORT --resources-to-import "[{\"ResourceType\":\"AWS::DynamoDB::Table\",\"LogicalResourceId\":\"GamesTable\",\"ResourceIdentifier\":{\"TableName\":\"Games\"}}]" --template-body 

    file://templateToImport.json

    The AWS CLI also supports text files as input for the resources-to-import parameter, as shown in the following example.

    --resources-to-import: 

    file://resourcesToImport.txt

    In this walkthrough, file://resourcesToImport.txt contains the following.

    [
      {
          "ResourceType":"AWS::DynamoDB::Table",
          "LogicalResourceId":"GamesTable",
          "ResourceIdentifier": {
            "TableName":"Games"
          }
      }
    ]
  6. Review the change set to make sure the correct resource is being imported into the target stack.
    > aws cloudformation describe-change-set --change-set-name 

    ImportChangeSet

  7. Execute the change set to import the resource into the target stack. Any stack-level tags are applied to imported resources at this time. On successful completion of the operation (IMPORT_COMPLETE), the resource is successfully imported.
    > aws cloudformation execute-change-set --change-set-name 

    ImportChangeSet

    Note

    It’s not necessary to run drift detection on the target stack after this import operation because the resource is already managed by AWS CloudFormation.

 

Nesting an Existing Stack

Use the resource import feature to nest an existing stack within another existing stack. Nested stacks are common components that you declare and reference from within other templates. That way, you can avoid copying and pasting the same configurations into your templates and simplify stack updates. If you have a template for a common component, you can use the AWS::CloudFormation::Stack resource to reference this template from within another template. For more information on nested stacks, see Working with Nested Stacks.

AWS CloudFormation only supports one level of nesting using resource import. This means that you cannot import a stack into a child stack or import a stack that has children.

Nested Stack Import Validation

During a nested stack import operation, AWS CloudFormation performs the following validations.

  • The nested AWS::CloudFormation::Stack definition in the parent stack template matches the actual nested stack’s template.
  • The tags for the nested AWS::CloudFormation::Stack definition in the parent stack template match the tags for the actual nested stack resource.

Nest an Existing Stack Using the AWS Management Console

  1. Add the AWS::CloudFormation::Stack resource to the parent stack template with a Retain DeletionPolicy. In the following example parent template, NestedStack is the target of the import.
    {
      "AWSTemplateFormatVersion" : "2010-09-09",
      "Resources" : {
        "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            },
        "NestedStack" : {
          "Type" : "AWS::CloudFormation::Stack",
          "DeletionPolicy": "Retain",
          "Properties" : {
          "TemplateURL" : "https://s3.amazonaws.com/cloudformation-templates-us-east-2/EC2ChooseAMI.template",
            "Parameters" : {
              "InstanceType" : "t1.micro",
              "KeyName" : "mykey"
            }
          }
        }
      }
    }
  2. Open the AWS CloudFormation console.
  3. On the Stacks page, with the parent stack selected, choose Stack actions, and then choose Import resources into stack.
     The Import resources into stack option in the console.
  4. Read the Import overview page for a list of things you’re required to provide during this operation. Then, choose Next.
  5. On the Specify template page, provide the updated parent template using one of the following methods, and then choose Next.
    • Choose Amazon S3 URL, and then specify the URL for your template in the text box.
    • Choose Upload a template file, and then browse for your template.
  6. On the Identify resources page, identify the AWS::CloudFormation::Stack resource.
    1. Under Identifier property, choose the type of resource identifier. For example, an AWS::CloudFormation::Stack resource can be identified using the StackName property.
    2. Under Identifier value, type the actual property value. For example, my_stack.
       The Identify resources page in the console.
    3. Choose Next.
  7. On the Specify stack details page, modify any parameters, and then choose Next. This automatically creates a change set.

    Important

    The import operation fails if you modify existing parameters that trigger a create, update, or delete operation.

  8. On the Review stack-name page, confirm that the correct resource is being imported, and then choose Import resources. This automatically executes the change set created in the last step. Any stack-level tags are applied to imported resources at this time.
  9. The Events pane of the Stack details page for your parent stack displays.
     The Events tab in the console.

    Note

    It’s not necessary to run drift detection on the parent stack after this import operation because the AWS::CloudFormation::Stackresource was already managed by AWS CloudFormation.

Nest an Existing Stack Using the AWS CLI

  1. Add the AWS::CloudFormation::Stack resource to the parent stack template with a Retain DeletionPolicy. In the following example parent template, NestedStack is the target of the import.
    {
      "AWSTemplateFormatVersion" : "2010-09-09",
      "Resources" : {
        "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            },
        "NestedStack" : {
          "Type" : "AWS::CloudFormation::Stack",
          "DeletionPolicy": "Retain",
          "Properties" : {
          "TemplateURL" : "https://s3.amazonaws.com/cloudformation-templates-us-east-2/EC2ChooseAMI.template",
            "Parameters" : {
              "InstanceType" : "t1.micro",
              "KeyName" : "mykey"
            }
          }
        }
      }
    }
  2. Create a change set of type IMPORT with the following parameters. --resources-to-import does not support inline YAML.
    > aws cloudformation create-change-set
        --stack-name 

    TargetParentStack

     --change-set-name 

    ImportChangeSet

     --change-set-type IMPORT --resources-to-import "[{\"ResourceType\":\AWS::CloudFormation::Stack\",\"LogicalResourceId\":\"MyStack\",\"ResourceIdentifier\":{\"StackId\":\"arn:aws:cloudformation:us-east-2:123456789012:stack/mystack-mynestedstack-sggfrhxhum7w/f449b250-b969-11e0-a185-5081d0136786\"}}] --template-body 

    file://templateToImport.json

    The AWS CLI also supports text files as input for the resources-to-import parameter, as shown in the following example.

    --resources-to-import: 

    file://resourcesToImport.txt

    In this walkthrough, file://resourcesToImport.txt contains the following.

    [
      {
          "ResourceType":"AWS::CloudFormation::Stack",
          "LogicalResourceId":"MyStack",
          "ResourceIdentifier": {
            "StackId":"arn:aws:cloudformation:us-east-2:123456789012:stack/mystack-mynestedstack-sggfrhxhum7w/f449b250-b969-11e0-a185-5081d0136786"
          }
      }
    ]
  3. Review the change set to make sure the correct stack is being imported.
    > aws cloudformation describe-change-set --change-set-name 

    ImportChangeSet

  4. Execute the change set to import the stack into the source parent stack. Any stack-level tags are applied to imported resources at this time. On successful completion of the import operation (IMPORT_COMPLETE), the stack is successfully nested.
    > aws cloudformation execute-change-set --change-set-name 

    ImportChangeSet

    Note

    It’s not necessary to run drift detection on the parent stack after this import operation because the AWS::CloudFormation::Stackresource was already managed by AWS CloudFormation.

     

Reverting an Import Operation

To revert an import operation, specify a Retain deletion policy for the resource you want to remove from the template to ensure that it’s preserved when you delete it from the stack.

Revert an Import Operation Using the AWS Management Console

  1. Specify a Retain DeletionPolicy for the resources you want to remove from your stack. In the following example template, GamesTable is the target of this revert operation.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            },
            "GamesTable": {
                "Type": "AWS::DynamoDB::Table",
                "DeletionPolicy": "Retain",
                "Properties": {
                    "TableName": "Games",
                    "AttributeDefinitions": [
                        {
                            "AttributeName": "key",
                            "AttributeType": "S"
                        }
                    ],
                    "KeySchema": [
                        {
                            "AttributeName": "key",
                            "KeyType": "HASH"
                        }
                    ],
                    "ProvisionedThroughput": {
                        "ReadCapacityUnits": 5,
                        "WriteCapacityUnis": 1
                    }
                }
            }
        }
    }
  2. Open the AWS CloudFormation console to perform a stack update to apply the deletion policy.
    1. On the Stacks page, with the stack selected, choose Update, and then choose Update stack (standard).
    2. Under Prepare template, choose Replace current template.
    3. Under Specify template, provide the updated source template with the DeletionPolicy attribute on GamesTable, and then choose Next.
      • Choose Amazon S3 URL, and then specify the URL to the updated source template in the text box.
      • Choose Upload a template file, and then browse for the updated source template file.
    4. On the Specify stack details page, no changes are required. Choose Next.
    5. On the Configure stack options page, no changes are required. Choose Next.
    6. On the Review stack_name page, review your changes. If your template contains IAM resources, select I acknowledge that this template may create IAM resources to specify that you want to use IAM resources in the template. For more information about using IAM resources in templates, see Controlling Access with AWS Identity and Access Management. Then, either update your source stack by creating a change set or update your source stack directly.
  3. Remove the resource, related parameters, and outputs from the stack template. In this example, the template now looks like the following.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            }
        }
    }
  4. Repeat step 2 to delete the resource (GamesTable) and its related parameters and outputs from the stack.

Revert an Import Operation Using the AWS CLI

  1. Specify a Retain DeletionPolicy for the resources you want to remove from your stack. In the following example template, GamesTable is the target of this revert operation.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            },
            "GamesTable": {
                "Type": "AWS::DynamoDB::Table",
                "DeletionPolicy": "Retain",
                "Properties": {
                    "TableName": "Games",
                    "AttributeDefinitions": [
                        {
                            "AttributeName": "key",
                            "AttributeType": "S"
                        }
                    ],
                    "KeySchema": [
                        {
                            "AttributeName": "key",
                            "KeyType": "HASH"
                        }
                    ],
                    "ProvisionedThroughput": {
                        "ReadCapacityUnits": 5,
                        "WriteCapacityUnis": 1
                    }
                }
            }
        }
    }
  2. Update the stack to apply the deletion policy to the resource.
    update-stack --stack-name "

    stack-name

    "
  3. Remove the resource, related parameters, and outputs from the stack template. In this example, the template now looks like the following.

    Example JSON

    {
        "AWSTemplateFormatVersion": "2010-09-09",
        "Description": "Import test",
        "Resources": {
            "ServiceTable":{
               "Type":"AWS::DynamoDB::Table",
               "Properties":{
                  "TableName":"Service",
                  "AttributeDefinitions":[
                     {
                        "AttributeName":"key",
                        "AttributeType":"S"
                     }
                  ],
                  "KeySchema":[
                     {
                        "AttributeName":"key",
                        "KeyType":"HASH"
                     }
                  ],
                  "ProvisionedThroughput":{
                     "ReadCapacityUnits":5,
                     "WriteCapacityUnits":1
                  }
               }
            }
        }
    }
  4. Update the stack to delete the resource (GamesTable) and its related parameters and outputs from the stack.
    update-stack --stack-name "stack name"