Overview
Terraform, an open-source infrastructure as code software tool by HashiCorp, provides a consistent CLI workflow to manage hundreds of cloud services. Terraform codifies cloud APIs into declarative configuration files. However, situations arise when executing a shell or bash script within Terraform is necessary, either to bootstrap resources, configure settings, or clean up resources. This tutorial covers how to execute shell/bash scripts in Terraform, from basic to more advanced examples.
Prerequisites:
- Basic understanding of Terraform
- Terraform installed on your machine
- Basic Shell/Bash scripting knowledge
Basic Execution Using null_resource
The null_resource
in Terraform is a versatile tool for executing scripts. Here’s a straightforward example:
resource "null_resource" "example" {
provisioner "local-exec" {
command = "echo Hello, World!"
}
}
This script simply prints “Hello, World!” on your console. The local-exec
provisioner invokes a local executable, in this case, echo
. Applying this Terraform configuration results in:
Applying plan...
null_resource.example: Creating...
null_resource.example: Provisioning with 'local-exec'...
null_resource.example (local-exec): Executing: [/bin/sh -c "echo Hello, World!"]
null_resource.example (local-exec): Hello, World!
null_resource.example: Creation complete after 0s
Apply complete! Resources: 1 added, 0 changed, 0 destroyed.
Advanced Usage: Passing Variables and Output
Let’s take it a step further by incorporating variables and capturing the output:
variable "greeting" {
description = "Greeting to display"
type = string
default = "Hello, Terraform!"
}
resource "null_resource" "advanced_example" {
provisioner "local-exec" {
command = "echo ${var.greeting} > greeting.txt"
environment = {
GREETING = var.greeting
}
}
}
This script writes the greeting message to a file named greeting.txt
. Additionally, it demonstrates how to pass environment variables to your script.
Executing Scripts From Files
Often, you’ll have bash scripts stored as files. Here’s how to execute a script file:
resource "null_resource" "script_file" {
provisioner "local-exec" {
command = "bash ${path.module}/setup.sh"
}
}
Assuming setup.sh
is a script in the same directory as your Terraform script, it will be executed. Ensure your bash script is executable (chmod +x setup.sh
).
Using remote-exec for Remote Execution
In scenarios where you need to execute a script on a remote server provisioned by Terraform, you can utilize the remote-exec
provisioner. An example:
resource "aws_instance" "web" {
ami = "ami-a1b2c3d4"
instance_type = "t2.micro"
provisioner "remote-exec" {
inline = [
"sudo apt-get update",
"sudo apt-get install -y nginx",
]
connection {
type = "ssh"
user = "ubuntu"
private_key = file("~/mykey.pem")
host = self.public_ip
}
}
}
This example updates the package lists and installs Nginx on an AWS EC2 instance. Make certain your EC2 instance allows SSH access from your IP address.
Conclusion
Executing shell/bash scripts in Terraform extends its functionality, enabling custom setup, configuration, or cleanup steps as part of your infrastructure deployment process. This article detailed methods from simple echo commands to more complex scenarios involving scripts and remote execution. Mastering these techniques can significantly enhance your Terraform projects.