无法将 network_interface_id 解析为资源 id:Cannot 解析 AzureID:parse module.network.azurerm_network_interface.primary.id: invalidURIforrequest

Can't parse network_interface_id as a resource id:Cannot parse AzureID:parse module.network.azurerm_network_interface.primary.id: invalidURIforrequest

on modules/security_group/main.tf line 64, in resource "azurerm_network_interface_security_group_association" "primary":
      64:   resource "azurerm_network_interface_security_group_association" "primary" {

我使用 "terraform validate" 命令获得了以上输出 以下是我用于 terraform 的配置。 这是我作为模块工作的树

├── main.tf
    └── modules
        ├── network
        │   ├── main.tf
        │   ├── variable.tf
        │   └── variable.tfvars
        ├── resource
        │   ├── main.tf
        │   ├── variable.tf
        │   └── variable.tfvars
        ├── security_group
        │   ├── main.tf
        │   ├── variable.tf
        │   └── variable.tfvars
        ├── storage
        │   ├── main.tf
        │   ├── variable.tf
        │   └── variable.tfvars
        └── vm
            ├── main.tf
            ├── variable.tf
            └── variable.tfvars

main.cf :

#Select provider
    provider "azurerm" {
      subscription_id = "xxxxxxxxxxxxxxxxxxxxxxxxx"
      version = "~> 2.4"
      features {}
    }
  module "resource" {
      source = "./modules/resource"
      resource_group_name = "devops_primary"
      location = "southeastasia"
    }
   module "network" {
      source = "./modules/network"
      virtual_network = "primaryvnet"
      subnet = "primarysubnet"
      address_space = "192.168.0.0/16"
      address_prefix = "192.168.1.0/24"
      public_ip = "backendvmpip"
      location = "southeastasia"
      primary_nic = "backendvmnic"
      primary_ip_conf = "backendvm"
      resource_group_name = "devops_primary"
    }
    module "vm" {
      source = "./modules/vm"
      vm_name = "backendvm-primary"
      vm_size = "standard_d2s_v3"
      vm_storage_od_disk_name = "backend-vm-os-disk-primary"
      computer_name = "backendserver"
      username = "terraform"
      ssh_key_path = "/home/terraform/.ssh/authorized_keys"
      keys_data = "~/.ssh/id_rsa.pub"
    }
    module "security_group" {
       source = "./modules/security_group"
       sg_group_name = "primary_sg"
       primary_nic_id = ["module.network.primary_nic_id"] 
    }

这是资源的 main.cf 文件:

#Select provider
provider "azurerm" {
  subscription_id = "xxxxxxxxxxxxxxxxxxxxxx"
  version = "~> 2.2"
  features {}
}

#Create Primary Resource Group
resource "azurerm_resource_group" "primary" {
  name     = "var.resource_group_name"
  location = "var.location"
  tags = {
        environment = "Test"
    }
}
output "devops_primary" {
  value = "${azurerm_resource_group.primary.name}"
}
output "location" {
    value = "${azurerm_resource_group.primary.location}"
}

这是网络的 main.cf 文件:

#Create public IP address
resource "azurerm_public_ip" "primary" {
    name                         = "var.public_ip"
    location                     = "module.resource.azurerm_resource_group.primary.location"
    resource_group_name          = "module.resource.azurerm_resource_group.primary.name"
    allocation_method            = "Dynamic"
    tags = {
        environment = "Test"
    }
}
output "public_ip_id"{
  value = azurerm_public_ip.primary.id
  }
#Create Network Interface
resource "azurerm_network_interface" "primary" {
  name                = "var.primary_nic"
  location            = "module.resource.azurerm_resource_group.primary.location"
  resource_group_name = "module.resource.azurerm_resource_group.primary.name"
   resource_group_name = var.resource_group_name
  ip_configuration {
        name                           = "var.primary_ip_conf"
       #subnet_id                       = "${azurerm_subnet.primary.id}"
        subnet_id                       = azurerm_subnet.primary.id
        private_ip_address_allocation  = "Dynamic"
        #public_ip_address_id            = "${azurerm_public_ip.primary.id}"
        public_ip_address_id           = azurerm_public_ip.primary.id
        #public_ip_address_allocation   = "Dymanic"
    }
  tags = {
        environment = "Test"
    }
  # depends_on = [var.subnet_id_primary]
    #depends_on                     = [module.resource.azurerm_resource_group.name]
}
output "primary_nic_id"{
  description = "Primary VNET NIC Id "
  value = ["azurerm_network_interface.primary.id"]
  }
output "private_ip" {
  description = "private ip addresses of the vm nics"
  value       = "${azurerm_network_interface.primary.private_ip_address}"
}

这是 VM 的 main.cf 文件:

#Create VM in Primary resource
resource "azurerm_virtual_machine" "primary" {
  name                  = "var.vm_name"
  location              = "module.resource.azurerm_resource_group.primary.location"
  resource_group_name   = "module.resource.azurerm_resource_group.primary.name"
  vm_size               = "var.vm_size"
  network_interface_ids = ["module.resource.azurerm_network_interface.primary.id"]
  storage_os_disk {
    name              = "var.vm_storage_od_disk_name"
    os_type           = "Linux"
    caching           = "ReadWrite"
    create_option     = "FromImage"
    managed_disk_type = "Premium_LRS"
  }
storage_image_reference {
    publisher = "Canonical"
    offer     = "UbuntuServer"
    sku       = "18.04-LTS"
    version   = "latest"
  }
  os_profile {
    computer_name  = "var.computer_name"
    admin_username = "var.username"
  }
  os_profile_linux_config {
    disable_password_authentication = true
  ssh_keys {
      path     = "/home/terraform/.ssh/authorized_keys"
      key_data = file("~/.ssh/id_rsa.pub")
    }
  }
  tags = {
        environment = "Test"
    }
}

这是security_group的main.cf文件:

#Create Network Security Group
resource "azurerm_network_security_group" "primary" {
    name                = "var.sg_group_name"
    #location            = "module.resource.azurerm_resource_group.primary.location"
    #resource_group_name = "module.resource.azurerm_resource_group.primary.name"
     resource_group_name = "var.resource_group_name"
     location            = "var.location"
    #Security Rules for Security Group
    security_rule {
        name                       = "SSH"
        priority                   = 1001
        direction                  = "Inbound"
        access                     = "Allow"
        protocol                   = "Tcp"
        source_port_range          = "*"
        destination_port_range     = "22"
        source_address_prefix      = "*"
        destination_address_prefix = "*"
    }
    security_rule {
        name                       = "AppOut"
        priority                   = 1002
        direction                  = "Inbound"
        access                     = "Allow"
        protocol                   = "Tcp"
        source_port_range          = "*"
        destination_port_range     = "8040"
        source_address_prefix      = "*"
        destination_address_prefix = "*"
    }
    security_rule {
        name                       = "MySql"
        priority                   = 1003
        direction                  = "Inbound"
        access                     = "Allow"
        protocol                   = "Tcp"
        source_port_range          = "*"
        destination_port_range     = "3306"
        source_address_prefix      = "*"
        destination_address_prefix = "*"
    }
    security_rule {
        name                       = "Redis"
        priority                   = 1004
        direction                  = "Inbound"
        access                     = "Allow"
        protocol                   = "Tcp"
        source_port_range          = "*"
        destination_port_range     = "6379"
        source_address_prefix      = "*"
        destination_address_prefix = "*"
    }
    tags = {
        environment = "Test"
    }
}
variable "primary_nic_id" {}
# Connect the security group to the network interface
  resource "azurerm_network_interface_security_group_association" "primary" {
    #network_interface_id      = "${module.network.azurerm_network_interface.primary.id}"
    network_interface_id      = "module.network.azurerm_network_interface.primary.id"
    network_security_group_id = "${azurerm_network_security_group.primary.id}"
    #depends_on                = ["module.network.primary_nic_id"]
    #primary_nic_id               = ["var.primary_nic_id"]
}
#depends_on                = [module.network.primary_nic_id]
# Generate a new ID only when a new resource group is defined
 resource "random_id" "randomId" {
    keepers = {
        resource_group_name = "module.resource.azurerm_resource_group.primary.name"
    }
    byte_length = 8
}

请查看我目前正在编写的代码,我是 terraform 的新手,刚开始还是个学习者。

首先,您可以删除所有非常量表达式的引号并保留内部表达式。要开始升级您的配置,运行 terraform 0.12upgrade 命令。

Terraform 0.11 and earlier required all non-constant expressions to be provided via interpolation syntax, but this pattern is now deprecated. To silence this warning, remove the "${ sequence from the start and the }" sequence from the end of this expression, leaving just the inner expression.

Template interpolation syntax is still used to construct strings from expressions when the template includes multiple interpolation sequences or a mixture of literal strings and interpolations. This deprecation applies only to templates that consist entirely of a single interpolation sequence.

Calling a Child Module

To call a module means to include the contents of that module into the configuration with specific values for its input variables. Modules are called from within other modules using module blocks:

module "servers" {
  source = "./app-cluster"

  servers = 5
}

Accessing Module Output Values

The resources defined in a module are encapsulated, so the calling module cannot access their attributes directly. However, the child module can declare output values to selectively export certain values to be accessed by the calling module.

For example, if the ./app-cluster module exported an output value named instance_ids then the calling module can reference that result using the expression module.servers.instance_ids:

resource "aws_elb" "example" {
  # ...

  instances = module.servers.instance_ids
}

For more information about referring to named values, see Expressions.

例如,在这种情况下,您不能从模块中查询值作为您的代码

network_interface_id      = "module.network.azurerm_network_interface.primary.id"

正确的表达是module.<MODULE NAME>.<OUTPUT NAME>。它是当前模块调用的子模块中指定的 output 值的值。您应该像这样从 network 模块查询 azurerm_network_interface.primary.id network_interface_id = module.network.primary_nic_id

此外,由于模块块是在代码的根目录中声明的,因此您不能直接从子模块配置文件中引用它们。您可以使用输入变量将值从根模块传递给您的子模块。参见 output values

例如,在根目录下的模块network中,你从模块network调用模块resource输出devops_primary这样resource_group_name = module.resource.devops_primary

module "network" {
  source = "./modules/network"
  resource_group_name = module.resource.devops_primary
  location = module.resource.location
  virtual_network = "primaryvnet"
  subnet = "primarysubnet"
  address_space = ["192.168.0.0/16"]
  ...
}

在 ./modules.network 目录中,您有

#Create Virtual Network in Primary Resource Group
resource "azurerm_virtual_network" "primary" {
  name                = var.virtual_network
  resource_group_name = var.resource_group_name
  address_space       = var.address_space
  location            = var.location

}

variable "resource_group_name" {

}

variable "location" {

}

您可以按照上述规则重新编辑您的配置文件。有关更多示例,您可以搜索 azurerm modules