Terraform: A path towards getting a HashiCorp certificate pt.3

Previous Article
Table of Contents
Next Article

pt.2 IaC Concepts and Terraform’s Purpose
All Articles
pt.4 HCL (HashiCorp Configuration Language)

Terraform’s basics: basic usage

Installation

You have read through 2 lon…


This content originally appeared on DEV Community and was authored by Andrey Frol

Previous Article Table of Contents Next Article
pt.2 IaC Concepts and Terraform's Purpose All Articles pt.4 HCL (HashiCorp Configuration Language)

Terraform’s basics: basic usage

Installation

You have read through 2 long articles that explained why Terraform is a good tool and what problems it can solve. Now, let's start using it!

In this article we will cover installation and our first configuration deployment. It will be just one EC2 instance, but the goal is to show you how it works.

==============

Prerequisites

  1. Installation instructions for Terraform.
  2. Installation instructions for AWS CLI
  3. AWS account and credentials that would allow Terraform to manage resources

Once you installed Terraform, AWS CLI, and have your AWS credentials on hand we would need to add access keys environment variables. Your key will go between double-quotes, without the carets.

$ export AWS_ACCESS_KEY_ID="<YOUR_AWS_ACCESS_KEY_ID>"
$ export AWS_SECRET_ACCESS_KEY="<YOUR_AWS_SECRET_ACCESS_KEY>"

After all these steps we can start using Terraform to manage our resources!

==============

Deploying our first infrastructure

We will start with a deploy of one EC2 instance. This will introduce you to the workflow of Terraform and basic structure of configuration files.

Enter these commands in the terminal to create a directory for our demo project and go into it:

# Create folder with the name tf-demo
$ mkdir tf-demo
# Change into tf-demo folder
$ cd tf-demo

Creating our first configuration

Now that we are in our project's folder we need to create a main.tf file that will hold our configuration:

$ touch main.tf

Open main.tf file with you favourite editor and paste this code:

terraform {
  required_providers {
    aws = {
      source  = "hashicorp/aws"
      version = "~> 3.27"
    }
  }

  required_version = ">= 0.14.9"
}

provider "aws" {
  profile = "default"
  region  = "us-west-2"
}

resource "aws_instance" "app_server" {
  ami           = "ami-830c94e3"
  instance_type = "t2.micro"

  tags = {
    Name = "PathToTerraformCertInstance"
  }
}

Next we will initialize Terraform in our folder:

$ terraform init
# the output should contain this
Terraform has been successfully initialized!

If the code indentation is wrong, do not worry! Terraform provides a convenient command fmt that formats the code all nice and tidy. Let's try it:

$ terraform fmt

Next step would be to check our configuration for syntactical errors. This is done using a validate command:

$ terraform validate
# You should get this output
Success! The configuration is valid.

Before we deploy any resources it is a good idea to see what Terraform intends to do with the configuration we wrote. We will do this using plan command:

$ terraform plan
# output
Terraform used the selected providers to generate the following
execution plan. Resource actions are indicated with the following
symbols:
  + create

Terraform will perform the following actions:

  # aws_instance.app_server will be created
  + resource "aws_instance" "app_server" {
      + ami                                  = "ami-830c94e3"
      + arn                                  = (known after apply)
      + associate_public_ip_address          = (known after apply)
      + availability_zone                    = (known after apply)
      + cpu_core_count                       = (known after apply)
      + cpu_threads_per_core                 = (known after apply)
      + disable_api_termination              = (known after apply)
      + ebs_optimized                        = (known after apply)
      + get_password_data                    = false
      + host_id                              = (known after apply)
      + id                                   = (known after apply)
      + instance_initiated_shutdown_behavior = (known after apply)
      + instance_state                       = (known after apply)
      + instance_type                        = "t2.micro"
      + ipv6_address_count                   = (known after apply)
      + ipv6_addresses                       = (known after apply)
      + key_name                             = (known after apply)
      + monitoring                           = (known after apply)
      + outpost_arn                          = (known after apply)
      + password_data                        = (known after apply)
      + placement_group                      = (known after apply)
      + placement_partition_number           = (known after apply)
      + primary_network_interface_id         = (known after apply)
      + private_dns                          = (known after apply)
      + private_ip                           = (known after apply)
      + public_dns                           = (known after apply)
      + public_ip                            = (known after apply)
      + secondary_private_ips                = (known after apply)
      + security_groups                      = (known after apply)
      + source_dest_check                    = true
      + subnet_id                            = (known after apply)
      + tags                                 = {
          + "Name" = "PathToTerraformCertInstance"
        }
      + tags_all                             = {
          + "Name" = "PathToTerraformCertInstance"
        }
      + tenancy                              = (known after apply)
      + user_data                            = (known after apply)
      + user_data_base64                     = (known after apply)
      + vpc_security_group_ids               = (known after apply)

      + capacity_reservation_specification {
          + capacity_reservation_preference = (known after apply)

          + capacity_reservation_target {
              + capacity_reservation_id = (known after apply)
            }
        }

      + ebs_block_device {
          + delete_on_termination = (known after apply)
          + device_name           = (known after apply)
          + encrypted             = (known after apply)
          + iops                  = (known after apply)
          + kms_key_id            = (known after apply)
          + snapshot_id           = (known after apply)
          + tags                  = (known after apply)
          + throughput            = (known after apply)
          + volume_id             = (known after apply)
          + volume_size           = (known after apply)
          + volume_type           = (known after apply)
        }

      + enclave_options {
          + enabled = (known after apply)
        }

      + ephemeral_block_device {
          + device_name  = (known after apply)
          + no_device    = (known after apply)
          + virtual_name = (known after apply)
        }

      + metadata_options {
          + http_endpoint               = (known after apply)
          + http_put_response_hop_limit = (known after apply)
          + http_tokens                 = (known after apply)
          + instance_metadata_tags      = (known after apply)
        }

      + network_interface {
          + delete_on_termination = (known after apply)
          + device_index          = (known after apply)
          + network_interface_id  = (known after apply)
        }

      + root_block_device {
          + delete_on_termination = (known after apply)
          + device_name           = (known after apply)
          + encrypted             = (known after apply)
          + iops                  = (known after apply)
          + kms_key_id            = (known after apply)
          + tags                  = (known after apply)
          + throughput            = (known after apply)
          + volume_id             = (known after apply)
          + volume_size           = (known after apply)
          + volume_type           = (known after apply)
        }
    }

Plan: 1 to add, 0 to change, 0 to destroy.

─────────────────────────────────────────────────────────────────

Note: You didn't use the -out option to save this plan, so
Terraform can't guarantee to take exactly these actions if you
run "terraform apply" now.

As you can see the output is pretty long, a thing to note is that we can output all this data to a file for analysis.

Everything looks good. Let's deploy our first resource using Terraform!
*You will be asked to approve deployment, you'd need to type yes to begin deployment process.

$ terraform apply
# output
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

aws_instance.app_server: Creating...
aws_instance.app_server: Still creating... [10s elapsed]
aws_instance.app_server: Still creating... [20s elapsed]
aws_instance.app_server: Still creating... [30s elapsed]
aws_instance.app_server: Still creating... [40s elapsed]
aws_instance.app_server: Creation complete after 45s [id=i-02bb0dc43fdd214d3]

Apply complete! Resources: 1 added, 0 changed, 0 destroyed.

Congratulations! You have just deployed your first resource using Infrastructure as Code!

We can check the state of Terraform-managed resources:

$ terraform state list
# output
aws_instance.app_server

Great! Now it is time to take our instance down. It is done using aptly-named command destroy, you will need to approve this command with yes when prompted:

$ terraform destroy
# output
Destroy complete! Resources: 1 destroyed.

Conclusion

This was a brief introduction to Terraform. As you went through the commands you also learned about Terraform's workflow.

This workflow is as follows: write -> plan -> create. We write our configuration, we verify that Terraform will do what we want it to do, and lastly, we create our resources.

You did great following through all the way to the end! I understand that deploying a single instance may not seem all that exciting. Some may argue that it would be faster to go to AWS console and deploy this instance manually. Maybe it's true. The point of this article was to introduce reader to Terraform basics.

Later on we will be deploying a much more complicated infrastructure with several EC2 instances, public and private subnets, S3 buckets, and bucket policies. We will see how we can leverage Terraform to automatically select active AZs (Availability Zones), search for the latest AMIs, name resources based on their location and purpose, create users and policies, and run bootstrap scripts on our EC2 instances. There is so much more that I want to write about.

Thank you for reading! See you in the next article where we will learn about HashiCorp Configuration Language (HCL)!

Previous Article Table of Contents Next Article
pt.2 IaC Concepts and Terraform's Purpose All Articles pt.4 HCL (HashiCorp Configuration Language)


This content originally appeared on DEV Community and was authored by Andrey Frol


Print Share Comment Cite Upload Translate Updates
APA

Andrey Frol | Sciencx (2022-06-07T05:46:45+00:00) Terraform: A path towards getting a HashiCorp certificate pt.3. Retrieved from https://www.scien.cx/2022/06/07/terraform-a-path-towards-getting-a-hashicorp-certificate-pt-3/

MLA
" » Terraform: A path towards getting a HashiCorp certificate pt.3." Andrey Frol | Sciencx - Tuesday June 7, 2022, https://www.scien.cx/2022/06/07/terraform-a-path-towards-getting-a-hashicorp-certificate-pt-3/
HARVARD
Andrey Frol | Sciencx Tuesday June 7, 2022 » Terraform: A path towards getting a HashiCorp certificate pt.3., viewed ,<https://www.scien.cx/2022/06/07/terraform-a-path-towards-getting-a-hashicorp-certificate-pt-3/>
VANCOUVER
Andrey Frol | Sciencx - » Terraform: A path towards getting a HashiCorp certificate pt.3. [Internet]. [Accessed ]. Available from: https://www.scien.cx/2022/06/07/terraform-a-path-towards-getting-a-hashicorp-certificate-pt-3/
CHICAGO
" » Terraform: A path towards getting a HashiCorp certificate pt.3." Andrey Frol | Sciencx - Accessed . https://www.scien.cx/2022/06/07/terraform-a-path-towards-getting-a-hashicorp-certificate-pt-3/
IEEE
" » Terraform: A path towards getting a HashiCorp certificate pt.3." Andrey Frol | Sciencx [Online]. Available: https://www.scien.cx/2022/06/07/terraform-a-path-towards-getting-a-hashicorp-certificate-pt-3/. [Accessed: ]
rf:citation
» Terraform: A path towards getting a HashiCorp certificate pt.3 | Andrey Frol | Sciencx | https://www.scien.cx/2022/06/07/terraform-a-path-towards-getting-a-hashicorp-certificate-pt-3/ |

Please log in to upload a file.




There are no updates yet.
Click the Upload button above to add an update.

You must be logged in to translate posts. Please log in or register.