# How to Use DigitalOcean Spaces as a Terraform Remote State Backend Spaces Object Storage is an S3-compatible service for storing and serving large amounts of data. The built-in Spaces CDN minimizes page load times, improves performance, and reduces bandwidth and infrastructure costs. Terraform is an open-source tool that allows you to build, version, and automate the deployment of cloud infrastructure. You can use Terraform to set up basic or complex architectures for your applications. [DigitalOcean Terraform Provider Reference](https://docs.digitalocean.com/reference/terraform/reference/index.html.md): A complete reference for the DigitalOcean Terraform provider. By default, Terraform stores state files locally in the directory where Terraform is run. This works well if you’re using Terraform on your own, but it becomes a problem in a team environment where multiple people need to access the state files. With [remote state](https://developer.hashicorp.com/terraform/language/state/remote), instead of keeping the state files on your own machine, Terraform stores them in a central location that everyone on your team can access. ## Prerequisites This guide requires the following resources: - A Spaces bucket. For instructions, follow [How to Create a Spaces Bucket](https://docs.digitalocean.com/products/spaces/how-to/create/index.html.md). - A Spaces access key and secret key. For instructions, follow [Sharing Access to Buckets with Access Keys](https://docs.digitalocean.com/products/spaces/how-to/manage-access/index.html.md#access-keys). ## Set the Access Key Environment Variables You can pass your Spaces access key to Terraform in multiple ways. We strongly recommend using environment variables. Other methods, like using `terraform init -backend-config` or hardcoding key values in the backend configuration, cause Terraform to include those values in your `.terraform` folder and plan files, potentially leaking your credentials. Using environment variables helps keep your key private. Terraform uses `AWS_...` environment variables for all S3-compatible backend providers. Export your keys to your current shell environment. In Bash shells, for example, use `export`: ```shell export AWS_ACCESS_KEY_ID="" export AWS_SECRET_ACCESS_KEY="" ``` Replace the `` and `` placeholders with your actual keys. ## Configure the Backend The following Terraform configuration sets up an `s3` backend and configures it to use a DigitalOcean Spaces bucket. You need Terraform version `1.6.3` or higher to use it. ```terraform terraform { required_version = ">= 1.6.3" backend "s3" { endpoints = { s3 = "https://.digitaloceanspaces.com" } bucket = "" key = "" # Deactivate a few AWS-specific checks skip_credentials_validation = true skip_requesting_account_id = true skip_metadata_api_check = true skip_region_validation = true skip_s3_checksum = true region = "us-east-1" } } ``` There are three settings to update: - `s3`: Update `` with the region of your bucket. For example, a bucket in the NYC3 datacenter has the URL `https://nyc3.digitaloceanspaces.com` here. - `bucket`: Change `` to the name of your bucket. - `key`: This is the key (or filename) your Terraform state is stored under. Change `` to the key you’d like to use. In many S3-compatible clients, these are treated as file paths and can contain forward slashes (`/`) for directories and periods for file extensions. For example, a value of `test/example.tfstate` would place an `example.tfstate` file inside the `test` directory in the root of your bucket. Update these variables, then save your configuration in a `.tf` file. ## Initialize and Apply the Terraform Configuration You can apply this Terraform configuration as is, but it only sets up the bucket as a backend. At this point, add configuration for any additional resources you want to manage. See our [Terraform Reference](https://docs.digitalocean.com/reference/terraform/index.html.md) for information on creating DigitalOcean resources using Terraform. Once your backend and any optional resources are configured, initialize the configuration using the `terraform init` command: ```shell terraform init ``` Terraform outputs some status messages indicating that the backend is configured: ``` Initializing the backend... Successfully configured the backend "s3"! Terraform will automatically use this backend unless the backend configuration changes. ... Terraform has been successfully initialized! ``` You may now create the plan and apply the changes: ```shell terraform plan terraform apply ``` The `terraform apply` command updates your resources to match the plan and then saves its state to your Spaces bucket. Any collaborators with the same configuration and access to the bucket are able to use your shared state when applying their own changes. ## Use State Locking with Spaces In Terraform, state locking is a mechanism that prevents multiple concurrent operations from modifying the state file simultaneously. Without state locking, running multiple Terraform processes concurrently could lead to state corruption, resulting in infrastructure drift, inconsistent deployments, or failed updates. Before Terraform performs operations that modify the state file, it attempts to acquire a lock. If another process has already acquired the lock, Terraform waits until the lock is released before proceeding. If the lock cannot be acquired, Terraform fails with an error. To lock state in a DigitalOcean Spaces bucket, Terraform must create a lock file in the same bucket as the state file. To enable Spaces state locking, add `use_lockfile = true` to your Terraform configuration: ```terraform terraform { required_version = "~> 1.11" backend "s3" { endpoints = { s3 = "https://.digitaloceanspaces.com" } bucket = "" key = "" # Deactivate a few AWS-specific checks skip_credentials_validation = true skip_requesting_account_id = true skip_metadata_api_check = true skip_region_validation = true skip_s3_checksum = true region = "us-east-1" # Enable state locking with a lockfile use_lockfile = true } } ```