Provisionar uma máquina virtual Linux usando o Terraform
Terraform implementa e controla uma infraestrutura de destino usando arquivos de configuração que descrevem o estado desejado de seus componentes. O formato básico dos arquivos e sua sintaxe geral, expressa na HCL (Hashicorp Configuration Language), são os mesmos, independentemente da escolha da nuvem. No entanto, as descrições de componentes individuais dependem da nuvem, conforme determinado pelo provedor Terraform correspondente.
Embora existam vários provedores Terraform que dão suporte ao gerenciamento de infraestrutura do Azure, o AzureRM é de particular relevância. O provedor AzureRM facilita o provisionamento e a configuração de recursos comuns de IaaS do Azure, como máquinas virtuais, contas de armazenamento e interfaces de rede. Há também provedores adicionais não específicos da nuvem que você pode querer incorporar em suas implantações. Estes incluem o provedor aleatório, que ajuda a evitar conflitos de nomenclatura de recursos gerando cadeias de caracteres pseudoaleatórias; e o provedor tls, que simplifica o gerenciamento de chaves assimétricas para proteger a autenticação do Linux.
Terraform está disponível como um único binário que você pode baixar do site Hashicorp. Este binário implementa a interface de linha de comando (CLI) Terraform, que você pode invocar a partir de uma sessão de shell para inicializar o Terraform e processar arquivos de configuração. Você pode usar a CLI do Terraform a partir de qualquer um dos shells que dão suporte à CLI do Azure.
Nota
Ao usar o Azure Cloud Shell, certifique-se de executar a versão atual do Terraform seguindo as instruções fornecidas em Configurar o Terraform no Azure Cloud Shell com Bash.
Implantar uma VM Linux usando o Terraform
O Terraform permite definir, visualizar e implantar recursos em uma infraestrutura de nuvem específica do provedor. O processo de provisionamento começa com a criação de arquivos de configuração que usam a sintaxe HCL, que permite designar o ambiente de nuvem de destino, como o Azure, e os recursos que compõem sua infraestrutura de nuvem. Depois que todos os arquivos de configuração relevantes estiverem instalados (normalmente no mesmo local do sistema de arquivos), você poderá gerar um plano de execução que permita visualizar as alterações de infraestrutura resultantes antes da implantação real. Isso requer que você inicialize o Terraform para baixar os módulos de provedor necessários para implementar recursos de nuvem. Depois de validar as alterações, você pode aplicar o plano de execução para implantar a infraestrutura.
Nota
A geração de um plano de execução é opcional, mas recomendamos que você faça isso porque permite identificar qualquer impacto da implantação planejada sem afetar o ambiente de destino. Quando você implanta recursos do Azure interativamente, o Terraform dá suporte à autenticação da CLI do Azure de forma transparente, reutilizando suas credenciais para acessar a assinatura de destino do Azure.
O processo de provisionamento de uma VM do Azure executando Linux usando o Terraform normalmente envolve a seguinte sequência de etapas de alto nível:
- Identifique a imagem de VM adequada.
- Identifique o tamanho adequado da VM.
- Crie arquivos de configuração que definem o recurso de VM do Azure com suas dependências.
- Inicialize o Terraform.
- Gere um plano de execução Terraform.
- Inicie uma implantação do Terraform.
Para identificar a imagem e o tamanho adequados da VM, siga as etapas descritas na Unidade 4 deste módulo. Esta unidade concentra-se em tarefas específicas da Terraform.
Criar arquivos de configuração
Nota
Os nomes de arquivo escolhidos para seus arquivos Terraform são arbitrários, embora seja uma boa prática escolher um nome que reflita o conteúdo ou a finalidade do arquivo. Você deve usar ".tf" para a extensão do arquivo.
Para implantar uma VM Linux usando o Terraform, você começa criando um diretório para hospedar arquivos de configuração. Em seguida, crie um arquivo chamado providers.tf que imponha a versão do Terraform e designe os provedores nos quais você confiará ao definir os recursos incluídos em sua implantação. Esse arquivo deve ter o conteúdo exibido no seguinte trecho de código:
terraform {
required_version = ">=0.12"
required_providers {
azurerm = {
source = "hashicorp/azurerm"
version = "~>2.0"
}
random = {
source = "hashicorp/random"
version = "~>3.0"
}
tls = {
source = "hashicorp/tls"
version = "~>4.0"
}
}
}
provider "azurerm" {
features {}
}
No mesmo diretório, crie um arquivo chamado main.tf usando o código a seguir, que define a configuração da VM do Azure e suas dependências:
resource "random_pet" "rg_name" {
prefix = var.resource_group_name_prefix
}
resource "azurerm_resource_group" "rg" {
location = var.resource_group_location
name = random_pet.rg_name.id
}
# Create virtual network
resource "azurerm_virtual_network" "terraform_network" {
name = "lnx-tf-vnet"
address_space = ["10.1.0.0/16"]
location = azurerm_resource_group.rg.location
resource_group_name = azurerm_resource_group.rg.name
}
# Create subnet
resource "azurerm_subnet" "terraform_subnet" {
name = "subnet0"
resource_group_name = azurerm_resource_group.rg.name
virtual_network_name = azurerm_virtual_network.terraform_network.name
address_prefixes = ["10.1.0.0/24"]
}
# Create public IPs
resource "azurerm_public_ip" "terraform_public_ip" {
name = "lnx-tf-pip"
location = azurerm_resource_group.rg.location
resource_group_name = azurerm_resource_group.rg.name
allocation_method = "Dynamic"
}
# Create Network Security Group and rule
resource "azurerm_network_security_group" "terraform_nsg" {
name = "lnx-tf-nsg"
location = azurerm_resource_group.rg.location
resource_group_name = azurerm_resource_group.rg.name
security_rule {
name = "ssh"
priority = 300
direction = "Inbound"
access = "Allow"
protocol = "Tcp"
source_port_range = "*"
destination_port_range = "22"
source_address_prefix = "*"
destination_address_prefix = "*"
}
}
# Create network interface
resource "azurerm_network_interface" "terraform_nic" {
name = "lnx-tf-nic"
location = azurerm_resource_group.rg.location
resource_group_name = azurerm_resource_group.rg.name
ip_configuration {
name = "nic_configuration"
subnet_id = azurerm_subnet.terraform_subnet.id
private_ip_address_allocation = "Dynamic"
public_ip_address_id = azurerm_public_ip.terraform_public_ip.id
}
}
# Connect the security group to the network interface
resource "azurerm_network_interface_security_group_association" "lnx-tf-nic-nsg" {
network_interface_id = azurerm_network_interface.terraform_nic.id
network_security_group_id = azurerm_network_security_group.terraform_nsg.id
}
# Generate random text for a unique storage account name
resource "random_id" "random_id" {
keepers = {
# Generate a new ID only when a new resource group is defined
resource_group = azurerm_resource_group.rg.name
}
byte_length = 8
}
# Create storage account for boot diagnostics
resource "azurerm_storage_account" "storage_account" {
name = "diag${random_id.random_id.hex}"
location = azurerm_resource_group.rg.location
resource_group_name = azurerm_resource_group.rg.name
account_tier = "Standard"
account_replication_type = "LRS"
}
# Create (and display) an SSH key
resource "tls_private_key" "lnx-tf-ssh" {
algorithm = "RSA"
rsa_bits = 4096
}
# Create virtual machine
resource "azurerm_linux_virtual_machine" "lnx-tf-vm" {
name = "lnx-tf-vm"
location = azurerm_resource_group.rg.location
resource_group_name = azurerm_resource_group.rg.name
network_interface_ids = [azurerm_network_interface.terraform_nic.id]
size = "Standard_F4s"
os_disk {
name = "lnx-tf-vm-osdisk"
caching = "ReadWrite"
storage_account_type = "Premium_LRS"
}
source_image_reference {
publisher = "Canonical"
offer = "0001-com-ubuntu-server-jammy"
sku = "22_04-lts-gen2"
version = "latest"
}
computer_name = "lnx-tf-vm"
admin_username = "azureuser"
disable_password_authentication = true
admin_ssh_key {
username = "azureuser"
public_key = tls_private_key.lnx-tf-ssh.public_key_openssh
}
boot_diagnostics {
storage_account_uri = azurerm_storage_account.storage_account.primary_blob_endpoint
}
}
No mesmo diretório, crie outro arquivo chamado variables.tf usando o código a seguir, que atribui o valor às variáveis que aparecem no arquivo main.tf :
variable "resource_group_location" {
default = "eastus"
description = "Location of the resource group"
}
variable "resource_group_name_prefix" {
default = "rg"
description = "Prefix of the resource group name that's combined with a random ID so name is unique in your Azure subscription"
}
Por fim, crie um arquivo chamado outputs.tf usando o código a seguir, que determina a saída exibida após uma implantação bem-sucedida:
output "resource_group_name" {
value = azurerm_resource_group.rg.name
}
output "public_ip_address" {
value = azurerm_linux_virtual_machine.lnx-tf-vm.public_ip_address
}
output "tls_private_key" {
value = tls_private_key.lnx-tf-ssh.private_key_pem
sensitive = true
}
Inicializar o Terraform
Para inicializar a implantação do Terraform, execute o seguinte comando no prompt do shell:
terraform init
Este comando baixa os módulos do Azure necessários para provisionar e gerenciar recursos do Azure.
Gerar um plano de execução
Após a inicialização, crie um plano de execução executando o plano de terraforme. O comando cria um plano de execução, mas não o executa. Em vez disso, ele determina quais ações são necessárias para criar os recursos definidos em seus arquivos de configuração. O parâmetro opcional -out
permite especificar um arquivo de saída para o plano, que pode ser referenciado durante a implantação real. O uso desse arquivo garante que o plano revisado corresponda ao resultado exato da implantação. Use o seguinte comando para gerar um plano de execução:
terraform plan -out <terraform_plan>.tfplan
Iniciar uma implantação
Quando estiver pronto para aplicar o plano de execução ao seu ambiente do Azure, execute terraform apply
, incluindo o nome do arquivo gerado na etapa anterior. Você terá outra chance de rever o resultado esperado. Terraform solicita a confirmação para prosseguir, embora você possa eliminar o prompt adicionando o -auto-approve
switch. Use o seguinte comando para iniciar a implantação:
terraform apply <terraform_plan>.tfplan
A VM do Azure começará a ser executada em breve, normalmente dentro de alguns minutos. A terraform apply
saída do comando inclui a lista de saídas, mas terraform substituirá o valor de tls_private_key
com o <rótulo sensível> :
Apply complete! Resources: 12 added, 0 changed, 0 destroyed.
Realizações:
public_ip_address = "74.235.10.136"
resource_group_name = "rg-flexible-shark"
tls_private_key = <sensitive>
Para usar a chave privada gerada automaticamente para autenticar sua conexão SSH, armazene-a em um arquivo e defina as permissões do arquivo para garantir que ele não seja acessível por outras pessoas. Para fazer isso, execute os seguintes comandos:
terraform output -raw tls_private_key > id_rsa
chmod 600 id_rsa
Neste ponto, você poderá se conectar à VM do Azure executando o seguinte comando (depois de substituir o espaço reservado <public_ip_address> pelo endereço IP identificado na saída gerada por aplicação de terraforme):
ssh -i id_rsa azureuser@<public_ip_address>