Resources - Import
Adding import support for Terraform resources will allow existing infrastructure to be managed within Terraform. This type of enhancement generally requires a small to moderate amount of code changes.
Note: Operators are responsible for writing the appropriate configuration that will be associated with the resource import. This restriction may be removed in a future version of Terraform.
When importing, the operator will specify the Terraform configuration address for the resource they wish to import, along with an identifier for import. The import identifier may be different than the resource identifier (ResourceData.SetId()
) for compatibility reasons outlined below in the Importer State Function section.
Overview of Implementation
Implementing import support requires three changes: an Importer
State
function in the resource code, a TestStep
with ImportState: true
in the acceptance tests, and documentation of the import ID format.
Hands-on: Try the Implement Import tutorial. In this tutorial, you can implement the import functionality on an example Terraform provider.
Resource Code Implementation
In the resource code (e.g. resource_example_thing.go
), implement an Importer
State
function:
Resource Acceptance Testing Implementation
In the resource acceptance testing (e.g. resource_example_thing_test.go
), implement TestStep
s with ImportState: true
:
Resource Documentation Implementation
In the resource documentation (e.g. website/docs/r/example_thing.html.markdown
), add an Import
documentation section at the bottom of the page:
Additional Information
Recommendations for Import
The items below are coding/testing styles that should generally be followed when implementing import support.
- The
TestStep
includingImportState
testing should not be performed solely in a separate acceptance test. This duplicates testing infrastructure/time and does not check that all resource configurations import into Terraform properly. - The
TestStep
includingImportState
should be included in all applicable resource acceptance tests (except those that delete the resource in question, e.g._disappears
tests) - Import implementations should not change existing
Create
functiond.SetId()
calls. Versioning best practices for Terraform Provider development notes that changing the resource ID is considered a breaking change for a major version upgrade as it makes theid
attribute ambiguous between provider versions. ImportStateVerifyIgnore
should only be used where its not possible tod.Set()
the attribute in theRead
function (preferable) orImporter
State
function.
Importer State Function
Where possible, prefer using schema.ImportStatePassthrough
as the Importer
State
function:
This function requires the Read
function to be able to refresh the entire resource with d.Id()
ONLY. Sometimes it is possible to adjust the resource Read
function to replace d.Get()
use with d.Id()
if they exactly match or add a function that parses the resource ID into the necessary attributes:
More likely though, if the resource requires multiple attributes and they are not already in the resource ID, Importer
State
will require a custom function implementation beyond using schema.ImportStatePassthrough
, seen below. The ID passed into terraform import
should be parsed so d.Set()
can be called the required attributes to make the Read
function properly operate. The resource ID should also match the ID set during the resource Create
function via d.SetId()
.
ImportStateVerifyIgnore
NOTE: ImportStateVerifyIgnore
should be used sparingly as it means Terraform will require a followup apply to the resource after import or operators must configure lifecycle
configuration block ignore_changes
argument (especially for attributes that are ForceNew
).
Some resource attributes only exist within the context of the Terraform resource or are only used to modify an API request during resource Create
, Update
, and Delete
functions. In these cases, if implementation of the resource cannot obtain the value for the attribute in the Read
function or its not determined/defaulted to the correct value during the Importer
State
function, the acceptance testing may return an error like the following:
To have the import testing ignore this attribute's value being missing during import, the ImportStateVerifyIgnore
field can be used with the list containing the name(s) of the attributes, e.g.
Multiple Resource Import
NOTE: Multiple resource import is generally discouraged due to the implementation/testing complexity and since the resource addresses saved into the Terraform state will likely not align with the operator's configuration.
The Terraform import framework supports importing multiple resources from a single state import function (sometimes referred to as "complex" imports), by adding elements to the returned []*schema.ResourceData
. Each of those new elements must have ResourceData.SetType()
and ResourceData.SetId()
called.
Given our fictitious example resource, if the API supported many associations with it, we could perform an API lookup during the resource import function to find those associations and add them to the Terraform state during import.