First, authenticate with GCP. The easiest way to do this is to run
gcloud auth application-default login
, if you already have gcloud
installed. If you don't already have it, you can install it from here.
Next, create a Terraform config file named "main.tf"
. Inside, you'll
want to include the following configuration:
provider "google" {
project = "{{YOUR GCP PROJECT}}"
region = "us-central1"
zone = "us-central1-c"
}
project
field should be your personal project id. The project
indicates the default GCP project all of your resources will be created in.
Most Terraform resources will have a project
field.region
and zone
are locations
for your resources to be created in.
region
will be used to choose the default location for regional
resources. Regional resources are spread across several zones.zone
will be used to choose the default location for zonal resources.
Zonal resources exist in a single zone. All zones are a part of a region.Not all resources require a location. Some GCP resources are global and are automatically spread across all of GCP.
A Google Compute Engine VM instance is
named google_compute_instance
in Terraform. The google
part of the name
identifies the provider for Terraform, compute
indicates the GCP product
family, and instance
is the resource name.
Google provider resources will generally, although not always, be named after
the name used in gcloud
/the REST API. For example, a VM instance is called
instance
in the API.
Most resource field names will also correspond 1:1 with their gcloud
/REST API
names.
If you look at the google_compute_instance documentation
,
you'll see that project
and zone
(VM instances are a zonal resource) are
listed as optional. When present in a resource's config block, these values will
be used. If omitted, the provider defaults will be used instead.
Add the following to your config file:
resource "google_compute_instance" "vm_instance" {
name = "terraform-instance"
machine_type = "e2-micro"
boot_disk {
initialize_params {
image = "debian-cloud/debian-11"
}
}
network_interface {
# A default network is created for all GCP projects
network = "default"
access_config {
}
}
}
Like this VM instance, nearly every GCP resource will have a name
field. They
are used as a short way to identify resources, and a resource's display name in
the Cloud Console will be the one defined in the name
field.
When linking resources in a Terraform config though, you'll primarily want to
use a different field, the self_link
of a resource. Like name
, nearly every
resource has a self_link
. They look like:
{{API base url}}/projects/{{your project}}/{{location type}}/{{location}}/{{resource type}}/{{name}}
For example, the instance defined earlier in a project named foo
will have
the self_link
:
https://www.googleapis.com/compute/v1/projects/foo/zones/us-central1-c/instances/terraform-instance
A resource's self_link
is a unique reference to that resource. When
linking two resources in Terraform, you can use Terraform interpolation to
avoid typing out the self link! Let's use a google_compute_network
to
demonstrate.
Add this block to your config:
resource "google_compute_network" "vpc_network" {
name = "terraform-network"
auto_create_subnetworks = "true"
}
This will create VPC network resource
with a subnetwork in each region. Next, change the network of the
google_compute_instance
from the "default"
network to the new network.
network_interface {
- # A default network is created for all GCP projects
- network = "default"
+ network = google_compute_network.vpc_network.self_link
access_config {
This means that when we create the VM instance, it will use
"terraform-network"
instead of the default VPC network for the project. If you
run terraform plan
, you will see that "terraform-instance"
depends on
"terraform-network"
.
Your configuration is complete. Before you can run terraform apply
though,
Terraform needs GCP credentials.
In order to make requests against the GCP API, you need to authenticate to prove that it's you making the request. The preferred method of provisioning resources with Terraform on your workstation is to use the Google Cloud SDK as we mentioned earlier.
You can also use a Google Cloud Service Account with terraform.
From the service account key page in the Cloud Console choose an existing account, or create a new one. Next, download the JSON key file. Name it something you can remember, and store it somewhere secure on your machine.
Note: Currently the only supported service account credentials are credentials downloaded from Cloud Console or generated by
gcloud
.
You supply the key to Terraform using the environment variable
GOOGLE_APPLICATION_CREDENTIALS
, setting the value to the location of the file.
export GOOGLE_APPLICATION_CREDENTIALS={{path}}
If you choose to use gcloud
-generated credentials, and you encounter
quota or billing issues which don't seem to apply to you, you may want to set
user_project_override
to true
in the provider block - see the
provider reference for more information.
You need to use a different environment variable name to store your credentials in Terraform Cloud.
GOOGLE_CREDENTIALS
in your Terraform Cloud workspace.cat CREDENTIALS.json | tr -s '\n' ' '
will remove newline characters from your JSON key file)All runs within the workspace will use the GOOGLE_CREDENTIALS
variable to authenticate with Google Cloud Platform.
By now, your config will look something like:
provider "google" {
project = "{{YOUR GCP PROJECT}}"
region = "us-central1"
zone = "us-central1-c"
}
resource "google_compute_instance" "vm_instance" {
name = "terraform-instance"
machine_type = "e2-micro"
boot_disk {
initialize_params {
image = "debian-cloud/debian-11"
}
}
network_interface {
# A default network is created for all GCP projects
network = google_compute_network.vpc_network.self_link
access_config {
}
}
}
resource "google_compute_network" "vpc_network" {
name = "terraform-network"
auto_create_subnetworks = "true"
}
With a Terraform config and with your credentials configured, it's time to provision your resources:
terraform apply
Congratulations! You've gotten started using the Google provider and provisioned a virtual machine on Google Cloud Platform. The key concepts unique to GCP are:
project
contains resources
project
in your providerregion
and zone
name
and self_link
to identify resourcesRun terraform destroy
to tear down your resources.
Afterwards, check out the provider reference for more details on configuring the provider block (including how you can eliminate it entirely!).
You can also check out the GCP Community tutorials such as: