Working with Terraform
“Terraform is an infrastructure as code tool that lets you build, change, and version cloud and on-prem resources safely and efficiently.”
-
Access you cloud project using the Hetzner GUI interface.
-
Go to
Security
-->API Tokens
-->Generate API token
-
Provide a name and hit Generate API token.
-
Copy the generated token's value and store it in a secure location e.g. a password manager.
Caution
The Hetzner GUI blocks future access to the token.
# Define Hetzner cloud provider terraform { required_providers { hcloud = { source = "hetznercloud/hcloud" } } required_version = ">= 0.13" } # Configure the Hetzner Cloud API token provider "hcloud" { token = "your_api_token_goes_here" } # Create a server resource "hcloud_server" "helloServer" { name = "hello" image = "debian-12" server_type = "cx22" }
$ terraform init Initializing the backend... Initializing provider plugins... - Finding latest version of hetznercloud/hcloud... - Installing hetznercloud/hcloud v1.46.1... - Installed hetznercloud/hcloud v1.46.1 (signed by a HashiCorp partner, key ID 5219EACB3A77198B) ... Terraform has created a lock file .terraform.lock.hcl to record the provider selections it made above. ...
$ terraform plan Terraform used the selected providers to generate the following execution plan. Resource actions ... + create Terraform will perform the following actions: # hcloud_server.helloServer will be created + resource "hcloud_server" "helloServer" { + allow_deprecated_images = false + backup_window = (known after apply) ... } Plan: 1 to add, 0 to change, 0 to destroy.
$ terraform apply ... Plan: 1 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 hcloud_server.helloServer: Creating... hcloud_server.helloServer: Still creating... [10s elapsed] hcloud_server.helloServer: Creation complete after 14s [id=45822789] Apply complete! Resources: 1 added, 0 changed, 0 destroyed.
Guide to Managing Terraform secrets.
variables.tf |
env |
providers.tf |
---|---|---|
variable "hcloud_token" {
nullable = false
sensitive = true
} |
export TF_VAR_hcloud_token=mBSxD... |
provider "hcloud" {
token = var.hcloud_token
} |
|
Your server "hello" was created!
You can access your server with the following credentials:
IPv4 128.140.108.60
IPv6 2a01:4f8:1c1c:8e3a::/64
User root
Password rJ3pNvJXbqMp3XNTvFdq
You will be prompted to change your password on your first login.
To improve security, we recommend that you add an SSH key when creating a server.
-
Firewall blocks ssh server access:
$ ssh root@128.140.108.60 ssh: connect to host 128.140.108.60 port 22: Connection refused
Access by Vnc console login only
-
IP and (initial) credentials by email 😱
Solution:
resource "hcloud_firewall" "sshFw" { name = "ssh-firewall" rule { direction = "in" protocol = "tcp" port = "22" source_ips = ["0.0.0.0/0", "::/0"] } } ... resource "hcloud_server" "helloServer" { ... firewall_ids = [hcloud_firewall.sshFw.id] }
resource "hcloud_ssh_key" "loginUser" { name = "goik@hdm-stuttgart.de" public_key = file("~/.ssh/id_ed25519.pub") } ... resource "hcloud_server" "helloServer" { ... ssh_keys = [hcloud_ssh_key.loginUser.id] }
Note: Use the Hetzner Web GUI for removing any conflicting manually installed ssh keys beforehand.
$ terraform apply # hcloud_firewall.sshFw will be created + resource "hcloud_firewall" "sshFw" { ... # hcloud_server.helloServer will be created + resource "hcloud_server" "helloServer" { ... # hcloud_ssh_key.goik will be created + resource "hcloud_ssh_key" "loginUser" { ... Plan: 3 to add, 0 to change, 0 to destroy. ... Apply complete! Resources: 3 added, 0 changed, 0 destroyed.
See terraform output documentation:
File outputs.tf |
Result |
---|---|
|
$ terraform output hello_datacenter = "nbg1-dc3" hello_ip_addr = "159.69.152.37" |
$ terraform output hello_ip_addr "159.69.152.37" |
File outputs.tf |
terraform output -json |
---|---|
|
|
Versioned file
main.tf
:
...
provider "hcloud" { token = "xdaGfz9LmwO8SWkg ... "}
...
Solution:
-
Declare a variable
hcloud_token
in avariables.tf
file -
Add a non-versioned file
secrets.auto.tfvars
. -
Optional: Provide a versioned
secrets.auto.tfvars.template
documenting file
Declaring variable "hcloud_token" { # See secret.auto.tfvars
nullable = false
sensitive = true
} |
Defining hcloud_token="xdaGfz9LmwO8SWkg ... " |
Using provider "hcloud" { token = var.hcloud_token } |
Template file
hcloud_token="your_api_token_goes_here" |
|
Content of file
Content
of file
|
No. 12
Incrementally creating a base system
Q: |
Follow the subsequent steps creating basic server based on Terraform:
|