azure - 在 Azure 上使用 Terraform 部署具有托管标识的 VM 失败

标签 azure terraform azure-managed-identity

我目前正在使用 Terraform 在 Azure 上部署虚拟机。在 AzureRM 提供程序 block 中使用 client_id、subscription_id、client_secret 和tenant_id 时,VM 部署正确。但是,我想利用托管身份,这样我就不必公开 client_secret。

我尝试过的事情: 为此,我遵循了这个guide

我包含了 azuread 提供程序 block ,使用“use_msi = true”来指示应使用托管身份。还包括 azurerm_subscription block 、azurerm_Client_config 以及资源定义。然后将角色分配添加到虚拟机。

代码:

terraform {
  required_providers {
    azuread = {
      source = "hashicorp/azuread"
    }
  }
}

provider "azurerm" {
  features {}
  //client_id       = "XXXXXXXXXXXXXX"
  //client_secret   = "XXXXXXXXXXXXXX"
  //subscription_id = "XXXXXXXXXXXXXX"
  tenant_id       = "TENANT_ID"
  //use_msi         = true
}

provider "azuread" {
  use_msi   = true
  tenant_id = "TENANT_ID"

}


#Resource group definition
resource "azurerm_resource_group" "myVMachineRG" {
  name     = "testnew-resources"
  location = "westus2"
}

resource "azurerm_virtual_network" "myVNet" {
  name                = "testnew-network"
  address_space       = ["10.0.0.0/16"]
  location            = azurerm_resource_group.myVMachineRG.location
  resource_group_name = azurerm_resource_group.myVMachineRG.name
}

resource "azurerm_subnet" "mySubnet" {
  name                 = "testnew-internal-subnet"
  resource_group_name  = azurerm_resource_group.myVMachineRG.name
  virtual_network_name = azurerm_virtual_network.myVNet.name
  #256 total IPs
  address_prefixes = ["10.0.2.0/24"]
}

resource "azurerm_network_interface" "myNIC" {
  name                = "testnew-nic"
  location            = azurerm_resource_group.myVMachineRG.location
  resource_group_name = azurerm_resource_group.myVMachineRG.name

  ip_configuration {
    name                          = "testconfiguration1"
    subnet_id                     = azurerm_subnet.mySubnet.id
    private_ip_address_allocation = "Dynamic"
  }
}

#ADDED HERE:


data "azurerm_subscription" "current" {}

data "azurerm_client_config" "example" {
}

resource "azurerm_virtual_machine" "example" {
  name                  = "testnew-vm"
  location              = azurerm_resource_group.myVMachineRG.location
  resource_group_name   = azurerm_resource_group.myVMachineRG.name
  network_interface_ids = ["${azurerm_network_interface.myNIC.id}"]
  vm_size               = "Standard_F2"

  #Option to delete disks when Terraform destroy is performed. 
  #This is to ensure that we don't keep wasting balance
  delete_os_disk_on_termination    = true
  delete_data_disks_on_termination = true

  storage_image_reference {
    publisher = "Canonical"
    offer     = "UbuntuServer"
    sku       = "16.04-LTS"
    version   = "latest"
  }

  storage_os_disk {
    name              = "OSDISK"
    caching           = "Readwrite"
    create_option     = "FromImage"
    managed_disk_type = "Standard_LRS"
  }

  #Just for testing purposes, would be better to use a KeyVault reference here instead.
  os_profile {
    computer_name  = "XXXXXXXXXXXXXX"
    admin_username = "XXXXXXXXXXXXXX"
    admin_password = "XXXXXXXXXXXXXX"
  }

  #Force password to authenticate
  os_profile_linux_config {
    disable_password_authentication = false
  }

  identity {
    type = "SystemAssigned"
  }
}

data "azurerm_role_definition" "contributor" {
  name = "Contributor"
}

resource "azurerm_role_assignment" "example" {
  //name               = azurerm_virtual_machine.example.name
  scope                = data.azurerm_subscription.current.id
  role_definition_name = "Contributor"
  //role_definition_id = "${data.azurerm_subscription.current.id}${data.azurerm_role_definition.contributor.id}"
  //principal_id = azurerm_virtual_machine.example.identity[0].principal_id
  principal_id = data.azurerm_client_config.example.object_id
}

错误:

Error: building AzureRM Client: obtain subscription() from Azure CLI: parsing json result from the Azure CLI: waiting for the Azure CLI: exit status 1: ERROR: Please run 'az login' to setup account.
│
│   with provider["registry.terraform.io/hashicorp/azurerm"],
│   on main.tf line 9, in provider "azurerm":
│    9: provider "azurerm" {

我不明白为什么当我尝试使用托管身份登录时它仍然要求使用 az login。

出于安全目的,编辑了tenantID。

任何帮助将不胜感激:)

最佳答案

我尝试在我的环境中重现相同的要求,并成功部署它。

如果您通过 terraform 中的托管身份进行身份验证,则需要提供托管身份的名称。

添加 msi_name azureread 提供程序下。

注意:正如您所给出的,请确保托管身份应具有足够的权限(贡献者角色)来进行身份验证和创建资源,否则部署将失败。

ma​​in.tf

data "azurerm_subscription" "current" {}
variable "subscription_id" {
  default = "xxxxxxxxxxxx"
}
provider "azurerm"{
features{}
subscription_id = var.subscription_id
}
provider "azuread"{
features{}
use_msi = true
msi-name = "jahnaviidentity" //Give Name of the Managed identity 
}

resource "azurerm_resource_group" "example" {
  name     = "example-resources"
  location = "West Europe"
}

resource "azurerm_virtual_network" "main" {
  name                = "main-network"
  address_space       = ["10.0.0.0/16"]
  location            = azurerm_resource_group.example.location
  resource_group_name = azurerm_resource_group.example.name
}

resource "azurerm_subnet" "internal" {
  name                 = "internal"
  resource_group_name  = azurerm_resource_group.example.name
  virtual_network_name = azurerm_virtual_network.main.name
  address_prefixes     = ["10.0.2.0/24"]
}

resource "azurerm_network_interface" "main" {
  name                = "main-nic"
  location            = azurerm_resource_group.example.location
  resource_group_name = azurerm_resource_group.example.name

  ip_configuration {
    name                          = "<configurationname>"
    subnet_id                     = azurerm_subnet.internal.id
    private_ip_address_allocation = "Dynamic"
  }
}

resource "azurerm_virtual_machine" "main" {
  name                  = "main-vm"
  location              = azurerm_resource_group.example.location
  resource_group_name   = azurerm_resource_group.example.name
  network_interface_ids = [azurerm_network_interface.main.id]
  vm_size               = "Standard_DS1_v2"


  storage_image_reference {
    publisher = "Canonical"
    offer     = "UbuntuServer"
    sku       = "16.04-LTS"
    version   = "latest"
  }
  storage_os_disk {
    name              = "osdisk"
    caching           = "ReadWrite"
    create_option     = "FromImage"
    managed_disk_type = "Standard_LRS"
  }
  os_profile {
    computer_name  = "<computername>"
    admin_username = "<admin/username>"
    admin_password = "xxxxxx"
  }
  os_profile_linux_config {
    disable_password_authentication = false
  }
  identity {
    type = "SystemAssigned"
  }
}

输出:

terraform初始化:

enter image description here

地形计划:

enter image description here

地形应用:

enter image description here

已在 Azure 门户中成功部署:

enter image description here

关于azure - 在 Azure 上使用 Terraform 部署具有托管标识的 VM 失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/75227193/

相关文章:

azure - 使用 Azure Functions 和存储帐户的托管身份

azure - Windows Azure Development Fabric 图标未显示在系统托盘上

java - 如何将日期时间字段保存到cosmosdb "SQL API/DocumentDb"?

python - 如何从 Azure Databricks Spark 中的 DataFrame 获取特定行和列

amazon-web-services - 如何转义包含 ${aws :username} in "Resource" section? 的 HCL 字符串

azure - "count"值取决于资源属性,这些属性在应用之前无法确定,因此Terraform无法预测将创建多少个实例

terraform - 如何以编程方式获取 Terraform 模块名称?

azure - 二头肌中用户分配身份的输出参数?

Azure 实例元数据服务

asp.net-mvc - 使用 Azure AD 和 ADAL 3 的 MVC 应用程序 - 身份验证 Cookie 在 1 小时后过期