The Terraform and OpenTofu cloud block, explained
The cloud block connects a configuration to a remote platform for state and runs. It is short, but a few details trip people up: the workspace name, where tokens come from, and how CI authenticates.
What the cloud block is
The cloud block, inside the top-level terraform block, tells OpenTofu or Terraform to keep state on a remote platform and run plans and applies there. It is the successor to the older remote backend, and any platform that implements the protocol works with it, including Terraform Cloud and StackShip.
terraform {
cloud {
hostname = "stackship.run"
organization = "acme"
workspaces {
name = "network-production"
}
}
}OpenTofu keeps the terraform block name for compatibility, so the same file works with both tools.
The arguments
| Argument | What it does |
|---|---|
hostname | The platform's host. It defaults to Terraform Cloud, so set it for any other platform. |
organization | Your organization's slug on that platform. |
workspaces.name | The one workspace this configuration uses. In StackShip, this is the Cloud workspace name, which can differ from the display name. |
The cloud block vs a backend
A backend block, such as s3, only stores state; plans and applies still run wherever you type the command. With the cloud block, tofu plan and tofu apply run remotely with the workspace's variables and credentials, and stream their output to your terminal. A configuration has one or the other, never both.
Signing in with tofu login
tofu login stackship.run
tofu inittofu login opens a browser, you sign in, and the token is saved in your CLI credentials file. Every later command, including downloads from a private module registry on the same host, uses it.
Tokens for CI: TF_TOKEN_ variables
In CI there is no browser. Store a token as a secret and expose it as an environment variable named after the host:
export TF_TOKEN_stackship_run='<token>'
tofu init -input=false
tofu plan -input=falseThe variable name is TF_TOKEN_ followed by the hostname, with dots replaced by underscores. Dashes in a hostname become double underscores. OpenTofu and Terraform both read these variables.
In StackShip, create the token on the workspace's CLI access tab and pick its purpose: Remote plan and apply for pipelines, or State migration for a one-time import. Tokens are limited to one workspace and expire after 1 to 365 days; choose the shortest that works.
Common errors
| Symptom | Usual cause |
|---|---|
init can't find the workspace | name is the display name, not the cloud workspace name, or organization is wrong. |
| Unauthorized | No login for this hostname, an expired token, or a TF_TOKEN_ variable named for a different host. |
| The apply waits and then fails to confirm | Your role can't approve runs. Ask an admin to approve it. |
| Workspace locked | Another run or command holds the lock. See state locking. |
Switching platforms
Because the protocol is shared, moving a workspace from Terraform Cloud to StackShip is a hostname change plus a state push. The migration guide has the steps, and the OpenTofu CLI docs list every command.