Gerir segredos com o Bicep

Muitas vezes, as implementações requerem que os segredos sejam armazenados e propagados de forma segura em todo o ambiente do Azure. O Bicep e o Azure fornecem muitas funcionalidades para o ajudar a gerir segredos nas suas implementações.

Evitar segredos onde pode

Em muitas situações, é possível evitar a utilização de segredos. Muitos recursos do Azure suportam identidades geridas, que lhes permitem autenticar e estar autorizados a aceder a outros recursos no Azure, sem que precise de processar ou gerir quaisquer credenciais. Além disso, alguns serviços do Azure podem gerar certificados HTTPS automaticamente, evitando o processamento de certificados e chaves privadas. Utilize identidades geridas e certificados geridos pelo serviço sempre que possível.

Utilizar parâmetros seguros

Quando precisar de fornecer segredos às implementações do Bicep como parâmetros, utilize o @secure() decorador. Quando marca um parâmetro como seguro, o Azure Resource Manager evita registar o valor ou apresentá-lo na portal do Azure, CLI do Azure ou Azure PowerShell.

Evitar saídas de segredos

Não utilize saídas do Bicep para dados seguros. As saídas são registadas no histórico de implementações e qualquer pessoa com acesso à implementação pode ver os valores das saídas de uma implementação.

Se precisar de gerar um segredo numa implementação do Bicep e disponibilizá-lo ao autor da chamada ou a outros recursos, considere utilizar uma das seguintes abordagens.

Procurar segredos dinamicamente

Por vezes, tem de aceder a um segredo de um recurso para configurar outro recurso.

Por exemplo, pode ter criado uma conta de armazenamento noutra implementação e ter de aceder à respetiva chave primária para configurar uma aplicação Funções do Azure. Pode utilizar a existing palavra-chave para obter uma referência fortemente escrita à conta de armazenamento pré-criada e, em seguida, utilizar o método da conta de listKeys() armazenamento para criar uma cadeia de ligação com a chave primária:

O exemplo seguinte faz parte de um exemplo maior. Para obter um ficheiro Bicep que possa implementar, veja o ficheiro completo.

resource storageAccount 'Microsoft.Storage/storageAccounts@2021-06-01' existing = {
  name: storageAccountName
}

var storageAccountConnectionString = 'DefaultEndpointsProtocol=https;AccountName=${storageAccount.name};EndpointSuffix=${environment().suffixes.storage};AccountKey=${listKeys(storageAccount.id, storageAccount.apiVersion).keys[0].value}'

resource functionApp 'Microsoft.Web/sites@2021-02-01' = {
  name: functionAppName
  location: location
  kind: 'functionapp'
  properties: {
    httpsOnly: true
    serverFarmId: appServicePlan.id
    siteConfig: {
      appSettings: [
        {
          name: 'APPINSIGHTS_INSTRUMENTATIONKEY'
          value: applicationInsights.properties.InstrumentationKey
        }
        {
          name: 'AzureWebJobsStorage'
          value: storageAccountConnectionString
        }
        {
          name: 'FUNCTIONS_EXTENSION_VERSION'
          value: '~3'
        }
        {
          name: 'FUNCTIONS_WORKER_RUNTIME'
          value: 'dotnet'
        }
        {
          name: 'WEBSITE_CONTENTAZUREFILECONNECTIONSTRING'
          value: storageAccountConnectionString
        }
      ]
    }
  }
}

Ao utilizar esta abordagem, evita transmitir segredos para dentro ou para fora do seu ficheiro Bicep.

Também pode utilizar esta abordagem para armazenar segredos num cofre de chaves.

Utilizar Key Vault

O Azure Key Vault foi concebido para armazenar e gerir dados seguros. Utilize um cofre de chaves para gerir os seus segredos, certificados, chaves e outros dados que precisam de ser protegidos e partilhados.

Pode criar e gerir cofres e segredos com o Bicep. Defina os cofres ao criar um recurso com o tipo Microsoft.KeyVault/vaults.

Quando cria um cofre, tem de determinar quem e o que podem aceder aos respetivos dados. Se planear ler os segredos do cofre a partir de um ficheiro Bicep, defina a enabledForTemplateDeployment propriedade como true.

Adicionar segredos a um cofre de chaves

Os segredos são um recurso subordinado e podem ser criados com o tipo Microsoft.KeyVault/vaults/secrets. O exemplo seguinte demonstra como criar um cofre e um segredo:

O exemplo seguinte faz parte de um exemplo maior. Para obter um ficheiro Bicep que possa implementar, veja o ficheiro completo.

resource keyVault 'Microsoft.KeyVault/vaults@2019-09-01' = {
  name: keyVaultName
  location: location
  properties: {
    enabledForTemplateDeployment: true
    tenantId: tenant().tenantId
    accessPolicies: [
    ]
    sku: {
      name: 'standard'
      family: 'A'
    }
  }
}

resource keyVaultSecret 'Microsoft.KeyVault/vaults/secrets@2019-09-01' = {
  parent: keyVault
  name: 'MySecretName'
  properties: {
    value: 'MyVerySecretValue'
  }
}

Dica

Quando utiliza pipelines de implementação automatizados, por vezes pode ser difícil determinar como iniciar o arranque de segredos do cofre de chaves para as suas implementações. Por exemplo, se lhe tiver sido fornecida uma chave de API para utilizar ao comunicar com uma API externa, o segredo tem de ser adicionado a um cofre antes de poder ser utilizado nas suas implementações.

Quando trabalha com segredos provenientes de terceiros, poderá ter de adicioná-los manualmente ao seu cofre e, em seguida, pode referenciar o segredo para todas as utilizações subsequentes.

Utilizar um cofre de chaves com módulos

Quando utiliza módulos bicep, pode fornecer parâmetros seguros com a getSecret função.

Também pode referenciar um cofre de chaves definido noutro grupo de recursos com as existing palavras-chave e scope em conjunto. No exemplo seguinte, o ficheiro Bicep é implementado num grupo de recursos denominado Rede. O valor do parâmetro mySecret do módulo é definido num cofre de chaves com o nome contosonetworkingsecrets localizado no grupo de recursos Segredos :

resource networkingSecretsKeyVault 'Microsoft.KeyVault/vaults@2019-09-01' existing = {
  scope: resourceGroup('Secrets')
  name: 'contosonetworkingsecrets'
}

module exampleModule 'module.bicep' = {
  name: 'exampleModule'
  params: {
    mySecret: networkingSecretsKeyVault.getSecret('mySecret')
  }
}

Utilizar um cofre de chaves num ficheiro .bicepparam

Quando utiliza .bicepparam o formato de ficheiro, pode fornecer valores seguros aos parâmetros com a getSecret função .

Faça referência ao KeyVault ao fornecer o ID da subscrição, o nome do grupo de recursos e o nome do cofre de chaves. Pode obter o valor do segredo ao fornecer o nome do segredo. Opcionalmente, pode fornecer a versão secreta. Se não fornecer a versão secreta, é utilizada a versão mais recente.

using './main.bicep'

param secureUserName = az.getSecret('<subscriptionId>', '<resourceGroupName>', '<keyVaultName>', '<secretName>', '<secretVersion>')
param securePassword = az.getSecret('<subscriptionId>', '<resourceGroupName>', '<keyVaultName>', '<secretName>')

Trabalhar com segredos em pipelines

Quando implementa os seus recursos do Azure através de um pipeline, tem de ter cuidado para processar os seus segredos adequadamente.

  • Evite armazenar segredos no seu repositório de código. Por exemplo, não adicione segredos a ficheiros de parâmetros nem aos ficheiros YAML de definição de pipeline.
  • No GitHub Actions, utilize segredos encriptados para armazenar dados seguros. Utilize a análise de segredos para detetar quaisquer consolidações acidentais de segredos.
  • Nos Pipelines do Azure, utilize variáveis secretas para armazenar dados seguros.