Virtual Event
Join us for the next HashiConf Digital October 12-15, 2020 Register for Free

Collaborate using Terraform Cloud

Migrate State to Terraform Cloud

As a current user of the Terraform CLI, you are responsible for maintaining a state file as a source of truth for your cloud infrastructure. You can migrate your local state file to Terraform Cloud without interrupting or recreating your existing infrastructure.

This guide assumes that you have the following:

»Create state

Start by cloning this GitHub repository.

$ git clone https://github.com/hashicorp/learn-state-migration

Next, change into the directory.

$ cd learn-state-migration

Review the main.tf file in the working directory to get an overview of the resources you are about to create. This configuration uses the random_pet resource to generate and output a random pet name with a given number of words. The length of the name is determined by the value of the name_length variable, which defaults 3.

In a real-world configuration you may have additional variables such as cloud platform credentials defined in a .tfvars file. We'll cover how to set these values in the Terraform Cloud workspace later on in this guide, after you've migrated the state file.

## Terraform configuration

variable "name_length" {
  description = "The number of words in the pet name"
  default     = "3"
}

resource "random_pet" "pet_name" {
  length    = var.name_length
  separator = "-"
}

output "pet_name" {
  value = random_pet.pet_name.id
}

Initialize the directory.

$ terraform init

After Terraform initializes, apply the configuration and approve the run by typing "yes" at the prompt.

$ terraform apply

Terraform will output a three word randomly generated pet name.

»Set up the remote backend

Now that you have a local state file, you need to create a backend code block in your configuration. Backends tell Terraform where to load and save its state file.

Terraform uses the local backend by default if you do not explicitly define a backend code block in your configuration. The local backend saves your state as a terraform.tfstate file in the directory where you run terraform apply. To migrate state files to Terraform Cloud, define a remote backend in your configuration by adding a new code block to the beginning of your main.tf file.

terraform {
  backend "remote" {
    hostname      = "app.terraform.io"
    organization  = "<YOUR-ORG-NAME>"

    workspaces {
      name = "state-migration"
    }
  }
}

Replace the organization and workspaces attribute values with the name of your Terraform Cloud organization and desired workspace name. While the organization defined in the backend stanza must already exist, the workspace does not have to; Terraform Cloud will create it if necessary. If you opt to use a workspace that already exists, the workspace must not have any existing states.

»Authenticate with Terraform Cloud

Now that you have defined your backend, you must authenticate with Terraform Cloud in order to proceed with initialization. In order to authenticate with Terraform Cloud, run the terraform login subcommand. You will be prompted to proceed with authentication by choosing y in your terminal.

$ terraform login
Terraform will request an API token for app.terraform.io using your browser.

If login is successful, Terraform will store the token in plain text in
the following file for use by subsequent commands:
    /Users/username/.terraform.d/credentials.tfrc.json

Do you want to proceed? (y/n)

Enter y to proceed. A browser window will automatically open to the Terraform Cloud login screen. Proceed through the login procedure in the web UI and create a name for the authentication token that Terraform Cloud generates.

If your browser is not automatically opened, navigate to the URL output in your terminal or click here to be taken to the token creation UI.

Modal window in Terraform Cloud titled "Create API token". There is a text box to set a name for the token.

Click "Create API token" and Terraform Cloud will generate the authentication token.

Modal window in Terraform Cloud titled "Create API token". The window contains a token value.

Save a copy of the token in a secure location as it provides access to your Terraform Cloud organization.

Your terminal will prompt you for the generated user token.

Terraform must now open a web browser to the tokens page for app.terraform.io.

If a browser does not open this automatically, open the following URL to proceed:
    https://app.terraform.io/app/settings/tokens?source=terraform-login


---------------------------------------------------------------------------------

Generate a token using your browser, and copy-paste it into this prompt.

Terraform will store the token in plain text in the following file
for use by subsequent commands:
    /Users/username/.terraform.d/credentials.tfrc.json

Token for app.terraform.io:

Enter the user token into your terminal and you will now have access to the Terraform Cloud backend.

Retrieved token for user terraform_user


---------------------------------------------------------------------------------

Success! Terraform has obtained and saved an API token.

The new API token will be used for any future Terraform command that must make
authenticated requests to app.terraform.io.

»Migrate the state file

Once you have authenticated the remote backend, you're ready to migrate your local state file to Terraform Cloud. To begin the migration, reinitialize. This causes Terraform to recognize your changed backend configuration.

$ terraform init

Initializing the backend...
Acquiring state lock. This may take a few moments...
Do you want to copy existing state to the new backend?
  Pre-existing state was found while migrating the previous "local" backend to the
  newly configured "remote" backend. No existing state was found in the newly
  configured "remote" backend. Do you want to copy this state to the new "remote"
  backend? Enter "yes" to copy and "no" to start with an empty state.

  Enter a value:

During reinitialization, Terraform presents a prompt saying that it will copy the state file to the new backend. Enter "yes" and Terraform will migrate the state from your local machine to Terraform Cloud.

»Configure the Terraform Cloud workspace

After migrating your state to Terraform Cloud, log in to the Terraform Cloud web UI, find your workspace name as defined in your backend configuration, and click on it. Navigate to the "States" tab of the workspace, and see your first action within the workspace.

A view of the "States" tab in the Terraform Cloud workspace

Remember that your configuration has a variable that you need to add to the new workspace. Click the "Variables" tab in the workspace and then "Add variable". Enter the name of the variable, name_length, as the key. Then enter a new value, 5, and save the variable.

The Terraform Cloud workspace's "Variables" tab with a variable added

For real-world configurations, add cloud platform credentials and any other configuration variables to the workspace as well.

»Initiate a run in the new workspace

After verifying that the state was migrated to the Terraform Cloud workspace, remove the local state file.

$ rm terraform.tfstate

Apply a new run.

$ terraform apply

Terraform will stream logs from Terraform Cloud and provide a link to the run in the Terraform Cloud UI. You set a new value for the name_length variable, so the resource will be replaced with one matching the new parameters.

Image of a run waiting confirmation, the log states that the resource will be replaced

»Next steps

Destroy the resources you created for this guide by first clicking the "Settings" option in the Terraform Cloud workspace, selecting "Destruction and Deletion", ensuring the "Allow destroy plans" checkbox is checked, and then clicking "Queue destroy plan".

After the resources have been destroyed, return to the "Destruction and Deletion" page and click "Delete from Terraform Cloud" to delete the workspace.

In this guide, you migrated a state file from your local machine to a Terraform Cloud workspace. To learn how to migrate the state files of multiple local workspaces, or restrict workspace access to a particular team, see the following documentation.

If you have a large number of state files that you would like to migrate to Terraform Cloud, consider using the Terraform Cloud API to do so. For information on uploading state versions using the API, refer to the State Version API documentation.