This guide will help you install Terraform on Ubuntu 22.04|20.04 |18.04. Terraform is an Infrastructure as code tool which allows you to easily manage cloud resources in a versioned manner. You use Terraform to build, change, and version infrastructure deployed on popular service providers. This tool is not cloud-agnostic and it supports custom in-house solutions.
With Terraform you can manage Cloud Compute, Networking, Load Balancers, DNS and so on using simple Declarative Programming Language. See the complete list of Terraform Providers. Complex changesets can be applied to your infrastructure with minimal human interaction
Install Terraform on Ubuntu 22.04|20.04 |18.04
Terraform is distributed as a tarball on Github. Check the latest release on Terraform releases page before downloading below.There are two methods from which we can install terraform on Ubuntu22.04|20.04 |18.04.
Method 1: Install Terraform from APT repository
Terraform team offers package repositories for Debian based Linux, which allow you to install Terraform using the apt package management tool or any other APT frontend.
First, install repository addition dependencies:
sudo apt update
sudo apt install software-properties-common gnupg2 curl
Now import repository GPG key
curl https://apt.releases.hashicorp.com/gpg | gpg --dearmor > hashicorp.gpg
sudo install -o root -g root -m 644 hashicorp.gpg /etc/apt/trusted.gpg.d/
With the key imported now add Hashicorp repository to your Ubuntu system:
sudo apt-add-repository "deb [arch=$(dpkg --print-architecture)] https://apt.releases.hashicorp.com $(lsb_release -cs) main"
Expected execution output:
Repository: 'deb [arch=amd64] https://apt.releases.hashicorp.com jammy main'
Description:
Archive for codename: jammy components: main
More info: https://apt.releases.hashicorp.com
Adding repository.
Press [ENTER] to continue or Ctrl-c to cancel.
Adding deb entry to /etc/apt/sources.list.d/archive_uri-https_apt_releases_hashicorp_com-jammy.list
Adding disabled deb-src entry to /etc/apt/sources.list.d/archive_uri-https_apt_releases_hashicorp_com-jammy.list
Hit:1 https://mirror.hetzner.com/ubuntu/packages jammy InRelease
Hit:2 https://mirror.hetzner.com/ubuntu/packages jammy-updates InRelease
Hit:3 https://mirror.hetzner.com/ubuntu/packages jammy-backports InRelease
Hit:4 https://mirror.hetzner.com/ubuntu/security jammy-security InRelease
Get:5 https://apt.releases.hashicorp.com jammy InRelease [12.0 kB]
Get:6 https://apt.releases.hashicorp.com jammy/main amd64 Packages [74.4 kB]
Fetched 86.4 kB in 1s (84.6 kB/s)
Reading package lists... Done
Now install terraform on your Ubuntu Linux system:
sudo apt install terraform
Check the version of terraform installed on your system
$ terraform --version
Terraform v1.5.5
on linux_amd64
Method 2: Install Terraform Manually
The primary distribution packages for Terraform are .zip archives containing single executable files that you can extract anywhere on your system
Ensure wget and unzip packages are installed on your Ubuntu system:
sudo apt install wget unzip -y
Then download the latest terraform archive.
TER_VER=$(curl -s https://api.github.com/repos/hashicorp/terraform/releases/latest | grep tag_name | cut -d: -f2 | tr -d \"\,\v | awk '{$1=$1};1')
wget https://releases.hashicorp.com/terraform/${TER_VER}/terraform_${TER_VER}_linux_amd64.zip
Once downloaded, extract the archive:
$ unzip terraform_${TER_VER}_linux_amd64.zip
Archive: terraform_1.5.5_linux_amd64.zip
inflating: terraform
This will create a terraform binary file on your working directory. Move this file to the directory/usr/local/bin
.
sudo mv terraform /usr/local/bin/
This will make the tool accessible to all user accounts.
$ which terraform
/usr/local/bin/terraform
Confirm the version installed
$ terraform version
Terraform v1.5.5
on linux_amd64
Verify that the tool works:
$ terraform
Usage: terraform [global options] <subcommand> [args]
The available commands for execution are listed below.
The primary workflow commands are given first, followed by
less common or more advanced commands.
Main commands:
init Prepare your working directory for other commands
validate Check whether the configuration is valid
plan Show changes required by the current configuration
apply Create or update infrastructure
destroy Destroy previously-created infrastructure
All other commands:
console Try Terraform expressions at an interactive command prompt
fmt Reformat your configuration in the standard style
force-unlock Release a stuck lock on the current workspace
get Install or upgrade remote Terraform modules
graph Generate a Graphviz graph of the steps in an operation
import Associate existing infrastructure with a Terraform resource
login Obtain and save credentials for a remote host
logout Remove locally-stored credentials for a remote host
output Show output values from your root module
providers Show the providers required for this configuration
refresh Update the state to match remote systems
show Show the current state or a saved plan
state Advanced state management
taint Mark a resource instance as not fully functional
test Experimental support for module integration testing
untaint Remove the 'tainted' state from a resource instance
version Show the current Terraform version
workspace Workspace management
Global options (use these before the subcommand, if any):
-chdir=DIR Switch to a different working directory before executing the
given subcommand.
-help Show this help output, or the help for a specified subcommand.
-version An alias for the "version" subcommand.
Using Terraform to Manage Infrastructure
Now that terraform is installed, let’s create a test project.
mkdir projects
cd projects
Create Terraform main configuration file.
touch main.tf
I’m doing a Test with AWS Provider but you can use other Providers for your projects. My terraform configuration provider section is as below.
$ vim main.tf
# Provider
provider "aws" {
access_key = ""
secret_key = ""
region = "us-west-1"
}
Paste your AWS Access Key and Secret Key inside the access_key
and secret_key
sections respectively. You can also configure your AWS access credentials with AWS CLI tool.
When done, run terraform init
to initialize a Terraform working directory.
$ terraform init
Initializing the backend...
Initializing provider plugins...
- Finding latest version of hashicorp/aws...
- Installing hashicorp/aws v5.12.0...
- Installed hashicorp/aws v5.12.0 (signed by HashiCorp)
Terraform has created a lock file .terraform.lock.hcl to record the provider
selections it made above. Include this file in your version control repository
so that Terraform can guarantee to make the same selections by default when
you run "terraform init" in the future.
Terraform has been successfully initialized!
You may now begin working with Terraform. Try running "terraform plan" to see
any changes that are required for your infrastructure. All Terraform commands
should now work.
If you ever set or change modules or backend configuration for Terraform,
rerun this command to reinitialize your working directory. If you forget, other
commands will detect it and remind you to do so if necessary.
Terraform will automatically download provider configured to .terraform
directory.
Let’s now add resource section to create AWS VPC and Subnet resources by editing the main.tf
file.
# Provider
provider "aws" {
access_key = ""
secret_key = ""
region = ""
}
# Retrieve the AZ where we want to create network resources
data "aws_availability_zones" "available" {}
# VPC Resource
resource "aws_vpc" "main" {
cidr_block = "10.11.0.0/16"
enable_dns_support = true
enable_dns_hostnames = true
tags {
Name = "Test-VPC"
}
tags {
Environment = "Test"
}
}
# AWS subnet resource
resource "aws_subnet" "test" {
vpc_id = "${aws_vpc.main.id}"
cidr_block = "10.11.1.0/24"
availability_zone = "${data.aws_availability_zones.available.names[0]}"
map_public_ip_on_launch = "false"
tags {
Name = "Test_subnet1"
}
}
Save the file after adding resource definitions and setting AWS variables then generate and show an execution plan.
$ terraform plan
Refreshing Terraform state in-memory prior to plan...
The refreshed state will be used to calculate this plan, but will not be
persisted to local or remote state storage.
data.aws_availability_zones.available: Refreshing state...
------------------------------------------------------------------------
An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
+ create
Terraform will perform the following actions:
+ aws_subnet.test
id: <computed>
arn: <computed>
assign_ipv6_address_on_creation: "false"
availability_zone: "us-east-1a"
availability_zone_id: <computed>
cidr_block: "10.11.1.0/24"
ipv6_cidr_block: <computed>
ipv6_cidr_block_association_id: <computed>
map_public_ip_on_launch: "false"
owner_id: <computed>
tags.%: "1"
tags.Name: "Test_subnet1"
vpc_id: "${aws_vpc.main.id}"
+ aws_vpc.main
id: <computed>
arn: <computed>
assign_generated_ipv6_cidr_block: "false"
cidr_block: "10.11.0.0/16"
default_network_acl_id: <computed>
default_route_table_id: <computed>
default_security_group_id: <computed>
dhcp_options_id: <computed>
enable_classiclink: <computed>
enable_classiclink_dns_support: <computed>
enable_dns_hostnames: "true"
enable_dns_support: "true"
instance_tenancy: "default"
ipv6_association_id: <computed>
ipv6_cidr_block: <computed>
main_route_table_id: <computed>
owner_id: <computed>
tags.%: "2"
tags.Environment: "Test"
tags.Name: "Test-VPC"
Plan: 2 to add, 0 to change, 0 to destroy.
------------------------------------------------------------------------
Note: You didn't specify an "-out" parameter to save this plan, so Terraform
can't guarantee that exactly these actions will be performed if
"terraform apply" is subsequently run.
Finally build your Infrastructure with Terraform using terraform apply
.
$ terraform apply
data.aws_availability_zones.available: Refreshing state...
An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
+ create
Terraform will perform the following actions:
+ aws_subnet.test
id: <computed>
arn: <computed>
assign_ipv6_address_on_creation: "false"
availability_zone: "us-east-1a"
availability_zone_id: <computed>
cidr_block: "10.11.1.0/24"
ipv6_cidr_block: <computed>
ipv6_cidr_block_association_id: <computed>
map_public_ip_on_launch: "false"
owner_id: <computed>
tags.%: "1"
tags.Name: "Test_subnet1"
vpc_id: "${aws_vpc.main.id}"
...........................
Confirm changes to be made and type “yes” to initiate modifications.
Plan: 2 to add, 0 to change, 0 to destroy.
Do you want to perform these actions?
Terraform will perform the actions described above.
Only 'yes' will be accepted to approve.
Enter a value: yes
A successful terraform run should print success message at the end.
Terraform state is saved to ./terraform.tfstate
but the backend can be changed. You can confirm Infrastructure changes from AWS console.
Destroying Terraform Infrastructure
We have confirmed that our Terraform installation on Ubuntu is working as expected. destroy Terraform-managed infrastructure by running terraform destroy
command.
$ terraform destroy
aws_vpc.main: Refreshing state... (ID: vpc-0e94a7d72c02dab2b)
data.aws_availability_zones.available: Refreshing state...
aws_subnet.test: Refreshing state... (ID: subnet-0ad06c2e86542ddc1)
An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
- destroy
Terraform will perform the following actions:
- aws_subnet.test
- aws_vpc.main
Plan: 0 to add, 0 to change, 2 to destroy.
Do you really want to destroy all resources?
Terraform will destroy all your managed infrastructure, as shown above.
There is no undo. Only 'yes' will be accepted to confirm.
Enter a value: yes
If you don’t want confirmation prompt, use:
terraform destroy -auto-approve
Installing terraform on other systems:
Next Steps
Now that you have Terraform installed and tested, it is time to build infrastructure using a minimal Terraform configuration file. Terraform Use Cases is an interesting page to read for new users.
You may also be interested in:
- How to Provision VMs on KVM with Terraform
- Deploy VM Instances on Hetzner Cloud with Terraform
- Build AWS EC2 Machine Images (AMI) With Packer and Ansible