Partilhar via


Início rápido: configurar backup protegido em cofre para um cluster do Serviço de Kubernetes do Azure (AKS) usando o Terraform

Este guia de início rápido descreve como configurar o backup em cofre para um cluster do Serviço Kubernetes do Azure (AKS) usando o Terraform.

O Backup do Azure para AKS é um serviço de backup centrado em aplicativos, pronto para a empresa e nativo da nuvem que permite configurar rapidamente o backup para clusters AKS.

Nota

As etapas incluídas neste artigo sobre como implantar um cluster e protegê-lo com o AKS Backup são apenas para fins de avaliação.

Antes de implantar um cluster pronto para produção e utilizar configurações avançadas de backup, recomendamos que você se familiarize com nossa arquitetura de referência de linha de base para considerar como ela se alinha aos seus requisitos de negócios.

Pré-requisitos

Coisas a garantir antes de configurar o backup do AKS:

  • Este início rápido assume que possui um entendimento básico dos conceitos do Kubernetes. Para obter mais informações, consulte [Kubernetes core concepts for Azure Kubernetes Service (AKS)][kubernetes-concepts].

  • Você precisa de uma conta do Azure com uma assinatura ativa. Se você não tiver uma, crie uma conta gratuitamente.

  • Instale e configure o Terraform.

Nota

Certifique-se de que a versão Terraform que está sendo usada é 3.99 ou posterior

Iniciar sessão na conta do Azure

Faça logon na sua conta do Azure e autentique-se usando um dos seguintes métodos:

O Terraform só dá suporte à autenticação no Azure com a CLI do Azure. Não há suporte para autenticação usando o Azure PowerShell. Portanto, embora você possa usar o módulo do Azure PowerShell ao fazer seu trabalho Terraform, primeiro precisa se autenticar no Azure.

Implementar o código Terraform

Para implementar o código Terraform para o fluxo de backup AKS, execute os seguintes scripts:

  1. Crie um diretório que você pode usar para testar o código Terraform de exemplo e torná-lo seu diretório atual.

  2. Crie um arquivo chamado providers.tf e insira o seguinte código:

    terraform {
      required_providers {
        azurerm = {
          source = "hashicorp/azurerm"
          version = "3.99.0"
        }
      }
    }
    
    provider "azurerm" {
       features {}
       subscription_id   = "<azure_subscription_id>"
       tenant_id = "<azure_subscription_tenant_id>"
    }
    
  3. Crie um arquivo chamado main.tf e insira o seguinte código:

     #Get Subscription and Tenant Id from Config
    
    data "azurerm_client_config" "current" {
    }
    
    #Create a Resource Group where Backup Vault and AKS Cluster will be created
    resource "azurerm_resource_group" "rg" {
      location = var.resource_group_location
      name     = var.resource_group_name
    }
    
    #Create a Resource Group where Storage Account and Snapshots related to backup will be created
    resource "azurerm_resource_group" "backuprg" {
      location = var.backup_resource_group_location
      name = var.backup_resource_group_name
    }
    
    #Create an AKS Cluster 
    resource "azurerm_kubernetes_cluster" "akscluster" {
      resource_group_name = azurerm_resource_group.rg.name
      name           = var.aks_cluster_name
      location       = azurerm_resource_group.rg.location
      dns_prefix     = var.dns_prefix
    
      identity {
        type = "SystemAssigned"
      }
    
      default_node_pool {
        name       = "agentpool"
        vm_size    = "Standard_D2_v2"
        node_count = var.node_count
      }
    
      network_profile {
        network_plugin    = "kubenet"
        load_balancer_sku = "standard"
      }
    
      depends_on = [azurerm_resource_group.rg,azurerm_resource_group.backuprg]
    }
    
    #Create a Backup Vault
    resource "azurerm_data_protection_backup_vault" "backupvault" {
      name                = var.backupvault_name
      resource_group_name = resource.azurerm_resource_group.rg.name
      location            = resource.azurerm_resource_group.rg.location
      datastore_type      = var.datastore_type
      redundancy          = var.redundancy
    
      identity {
        type = "SystemAssigned"
      }
      depends_on = [azurerm_kubernetes_cluster.akscluster]
    }
    
    #Create a Backup Policy with 4 hourly backups and 7 day retention duration
    resource "azurerm_data_protection_backup_policy_kubernetes_cluster" "policy" {
      name                = var.backuppolicy_name
      resource_group_name = var.resource_group_name
      vault_name          = var.backupvault_name
    
      backup_repeating_time_intervals = ["R/2024-04-14T06:33:16+00:00/PT4H"]
      default_retention_rule {
        life_cycle {
          duration        = "P7D"
          data_store_type = "OperationalStore"
        }
      }
    depends_on = [resource.azurerm_data_protection_backup_vault.backupvault]
    }
    
    #Create a Trusted Access Role Binding between AKS Cluster and Backup Vault
    resource "azurerm_kubernetes_cluster_trusted_access_role_binding" "trustedaccess" {
      kubernetes_cluster_id = azurerm_kubernetes_cluster.akscluster.id
      name                  = "backuptrustedaccess"
      roles                 = ["Microsoft.DataProtection/backupVaults/backup-operator"]
      source_resource_id    = azurerm_data_protection_backup_vault.backupvault.id
      depends_on = [resource.azurerm_data_protection_backup_vault.backupvault, azurerm_kubernetes_cluster.akscluster]
    }
    
    #Create a Backup Storage Account provided in input for Backup Extension Installation
    resource "azurerm_storage_account" "backupsa" {
      name                     = "tfaksbackup1604"
      resource_group_name      = azurerm_resource_group.backuprg.name
      location                 = azurerm_resource_group.backuprg.location
      account_tier             = "Standard"
      account_replication_type = "LRS"
      depends_on = [azurerm_kubernetes_cluster_trusted_access_role_binding.trustedaccess]
    }
    
    #Create a Blob Container where backup items will stored
    resource "azurerm_storage_container" "backupcontainer" {
      name                  = "tfbackup"
      storage_account_name  = azurerm_storage_account.backupsa.name
      container_access_type = "private"
      depends_on = [azurerm_storage_account.backupsa]
    }
    
    #Create Backup Extension in AKS Cluster
    resource "azurerm_kubernetes_cluster_extension" "dataprotection" {
      name = var.backup_extension_name
      cluster_id = azurerm_kubernetes_cluster.akscluster.id
      extension_type = var.backup_extension_type
      configuration_settings = {
        "configuration.backupStorageLocation.bucket" = azurerm_storage_container.backupcontainer.name
         "configuration.backupStorageLocation.config.storageAccount" = azurerm_storage_account.backupsa.name
         "configuration.backupStorageLocation.config.resourceGroup" = azurerm_storage_account.backupsa.resource_group_name
         "configuration.backupStorageLocation.config.subscriptionId" =  data.azurerm_client_config.current.subscription_id
         "credentials.tenantId" = data.azurerm_client_config.current.tenant_id
         "configuration.backupStorageLocation.config.useAAD" = true
         "configuration.backupStorageLocation.config.storageAccountURI" = azurerm_storage_account.backupsa.primary_blob_endpoint
        }
      depends_on = [azurerm_storage_container.backupcontainer]
    }
    
    #Assign Role to Extension Identity over Storage Account
    resource "azurerm_role_assignment" "extensionrole" {
      scope                = azurerm_storage_account.backupsa.id
      role_definition_name = "Storage Blob Data Contributor"
      principal_id         = azurerm_kubernetes_cluster_extension.dataprotection.aks_assigned_identity[0].principal_id
      depends_on = [azurerm_kubernetes_cluster_extension.dataprotection]
    }
    
    #Assign Role to Backup Vault over AKS Cluster
    resource "azurerm_role_assignment" "vault_msi_read_on_cluster" {
      scope                = azurerm_kubernetes_cluster.akscluster.id
      role_definition_name = "Reader"
      principal_id         = azurerm_data_protection_backup_vault.backupvault.identity[0].principal_id
      depends_on = [azurerm_kubernetes_cluster.akscluster,resource.azurerm_data_protection_backup_vault.backupvault]
    }
    
    #Assign Role to Backup Vault over Snapshot Resource Group
    resource "azurerm_role_assignment" "vault_msi_read_on_snap_rg" {
      scope                = azurerm_resource_group.backuprg.id
      role_definition_name = "Reader"
      principal_id         = azurerm_data_protection_backup_vault.backupvault.identity[0].principal_id
      depends_on = [azurerm_kubernetes_cluster.akscluster,resource.azurerm_data_protection_backup_vault.backupvault]
    }
    
    #Assign Role to AKS Cluster over Snapshot Resource Group
    resource "azurerm_role_assignment" "cluster_msi_contributor_on_snap_rg" {
      scope                = azurerm_resource_group.backuprg.id
      role_definition_name = "Contributor"
      principal_id         = try(azurerm_kubernetes_cluster.akscluster.identity[0].principal_id,null)
      depends_on = [azurerm_kubernetes_cluster.akscluster,resource.azurerm_kubernetes_cluster.akscluster,resource.azurerm_resource_group.backuprg]
    }
    
    #Create Backup Instance for AKS Cluster
    resource "azurerm_data_protection_backup_instance_kubernetes_cluster" "akstfbi" {
      name                         = "example"
      location                     = azurerm_resource_group.backuprg.location
      vault_id                     = azurerm_data_protection_backup_vault.backupvault.id
      kubernetes_cluster_id        = azurerm_kubernetes_cluster.akscluster.id
      snapshot_resource_group_name = azurerm_resource_group.backuprg.name
      backup_policy_id             = azurerm_data_protection_backup_policy_kubernetes_cluster.policy.id
    
      backup_datasource_parameters {
        excluded_namespaces              = []
        excluded_resource_types          = []
        cluster_scoped_resources_enabled = true
        included_namespaces              = []
        included_resource_types          = []
        label_selectors                  = []
        volume_snapshot_enabled          = true
      }
    
      depends_on = [
        resource.azurerm_data_protection_backup_vault.backupvault,
        azurerm_data_protection_backup_policy_kubernetes_cluster.policy,
        azurerm_role_assignment.extensionrole,
        azurerm_role_assignment.vault_msi_read_on_cluster,
        azurerm_role_assignment.vault_msi_read_on_snap_rg,
        azurerm_role_assignment.cluster_msi_contributor_on_snap_rg
      ]
    }
    
  4. Crie um arquivo chamado variables.tf e insira o seguinte código:

    variable "aks_cluster_name" {
      type        = string
      default     = "Contoso_AKS_TF"
      description = "Name of the AKS Cluster."
    }
    
    variable "backup_extension_name" {
      type        = string
      default     = "azure-aks-backup"
      description = "Name of the AKS Cluster Extension."
    }
    
    variable "backup_extension_type" {
      type        = string
      default     = "microsoft.dataprotection.kubernetes"
      description = "Type of the AKS Cluster Extension."
    }
    
    variable "dns_prefix" {
      type        = string
      default     = "contoso-aks-dns-tf"
      description = "DNS Name of AKS Cluster made with Terraform"
    }
    
    variable "node_count" {
      type        = number
      description = "The initial quantity of nodes for the node pool."
      default     = 3
    }
    
    variable "resource_group_location" {
      type        = string
      default     = "eastus"
      description = "Location of the resource group."
    }
    
    variable "backup_resource_group_name" {
      type        = string
      default     = "Contoso_TF_Backup_RG"
      description = "Location of the resource group."
    }
    
    variable "backup_resource_group_location" {
      type        = string
      default     = "eastus"
      description = "Location of the resource group."
    }
    
    variable "resource_group_name" {
      type        = string
      default     = "Contoso_TF_RG"
      description = "Location of the resource group."
    }
    
    variable "cluster_id" {
      type        = string
      default     = "/subscriptions/c3d3eb0c-9ba7-4d4c-828e-cb6874714034/resourceGroups/Contoso_TF_RG/providers/Microsoft.ContainerService/managedClusters/Contoso_AKS_TF"
      description = "Location of the resource group."
    }
    
    variable "backupvault_name" {
      type        = string
      default     = "BackupVaultTF"
      description = "Name of the Backup Vault"
    }
    
    variable "datastore_type" {
      type        = string
      default     = "OperationalStore"
    }
    
    variable "redundancy" {
      type        = string
      default     = "LocallyRedundant"
    }
    
    variable "backuppolicy_name" {
      type        = string
      default     = "aksbackuppolicytfv1"
    }
    
  5. Crie um arquivo chamado outputs.tf e insira o seguinte código:

     output "aks_resource_group" {
       value = azurerm_resource_group.rg.name
     }
    
     output "snapshot_resource_group" {
       value = azurerm_resource_group.backuprg.name
     }
    
     output "kubernetes_cluster_name" {
       value = azurerm_kubernetes_cluster.akscluster.name
     }
    
     output "backup_vault_name" {
       value = azurerm_data_protection_backup_vault.backupvault.name
     }
    
     output "backup_instance_id" {
       value = azurerm_data_protection_backup_instance_kubernetes_cluster.akstfbi.id
     }
    

Inicializar Terraform

Execute terraform init para inicializar a implantação do Terraform. Este comando baixa o provedor do Azure necessário para gerenciar seus recursos do Azure.

terraform init -upgrade

Pontos principais:

  • O -upgrade parâmetro atualiza os plug-ins de provedor necessários para a versão mais recente que está em conformidade com as restrições de versão da configuração.

Criar um plano de execução do Terraform

Execute terraform plan para criar um plano de execução.

terraform plan -out main.tfplan

Pontos principais:

  • O terraform plan 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 a configuração especificada em seus arquivos de configuração. Esse padrão permite que você verifique se o plano de execução corresponde às suas expectativas antes de fazer quaisquer alterações nos recursos reais.
  • O parâmetro opcional -out permite especificar um arquivo de saída para o plano. O uso do -out parâmetro garante que o plano revisado seja exatamente o que é aplicado.

Aplicar um plano de execução do Terraform

Execute terraform apply para aplicar o plano de execução à sua infraestrutura de nuvem.

terraform apply main.tfplan

Pontos principais:

  • O comando de exemplo terraform apply pressupõe que anteriormente executou terraform plan -out main.tfplan.
  • Se você especificou um nome de arquivo diferente para o -out parâmetro, use esse mesmo nome de arquivo na chamada para terraform apply.
  • Se você não usou o -out parâmetro, ligue terraform apply sem nenhum parâmetro.

Solucionar problemas do Terraform no Azure

Ao usar o Terraform no Azure, você pode encontrar problemas comuns. Saiba como solucionar problemas.

Próximo passo

Neste guia de início rápido, você aprendeu como implantar um cluster Kubernetes, criar um cofre de backup e configurar o backup para o cluster Kubernetes.

Saiba mais sobre: