首页 > 解决方案 > 尝试为 azurerm 后端创建存储容器失败,出现 404 - 指定的资源不存在

问题描述

我正在尝试使用以下 Terraform 代码设置 azurerm 后端:

模块\远程状态\main.tf

provider "azurerm" {
}

variable "env" {
  type        = string
  description = "The SDLC environment (qa, dev, prod, etc...)"
}

locals {
  extended_name = "dfpg-${lower(var.env)}-tfstate"
}

##################################################################################
# RESOURCES
##################################################################################
resource "azurerm_resource_group" "setup" {
  name     = "app505-${local.extended_name}-eastus2"
  location = "eastus2"
}

resource "azurerm_storage_account" "sa" {
  name                     = replace(local.extended_name, "-", "")
  resource_group_name      = azurerm_resource_group.setup.name
  location                 = azurerm_resource_group.setup.location
  account_tier             = "Standard"
  account_replication_type = "LRS"
}

resource "azurerm_storage_container" "ct" {
  name                 = "terraform-state"
  storage_account_name = azurerm_storage_account.sa.name
}

data "azurerm_storage_account_sas" "state" {
  connection_string = azurerm_storage_account.sa.primary_connection_string
  https_only        = true

  resource_types {
    service   = true
    container = true
    object    = true
  }

  services {
    blob  = true
    queue = false
    table = false
    file  = false
  }

  start  = timestamp()
  expiry = timeadd(timestamp(), "17520h")

  permissions {
    read    = true
    write   = true
    delete  = true
    list    = true
    add     = true
    create  = true
    update  = false
    process = false
  }
}

##################################################################################
# OUTPUT
##################################################################################

resource "null_resource" "post-config" {

  depends_on = [azurerm_storage_container.ct]

  provisioner "local-exec" {
    command = <<EOT
Set-Content -Value 'storage_account_name = "${azurerm_storage_account.sa.name}"' -Path "backend-config.txt"
Add-Content -Value 'container_name = "terraform-state"' -Path "backend-config.txt"
Add-Content -Value 'key = "terraform.tfstate"' -Path "backend-config.txt"
Add-Content -Value 'sas_token = "${data.azurerm_storage_account_sas.state.sas}"' -Path "backend-config.txt"
EOT

    interpreter = ["PowerShell", "-NoProfile", "-Command"]
  }
}

qa\bootstrap\rs\main.tf

module "bootstrap" {
    source = "../../../modules/remote-state"
    env = "qa"
}

地形初始化

C:\xyz\terraform\qa\bootstrap\rs [shelve/terraform ≡]> terraform init
Initializing modules...
- bootstrap in ..\..\..\modules\remote-state

Initializing the backend...

Initializing provider plugins...
- Checking for available provider plugins...
- Downloading plugin for provider "azurerm" (hashicorp/azurerm) 1.41.0...
- Downloading plugin for provider "null" (hashicorp/null) 2.1.2...

The following providers do not have any version constraints in configuration,
so the latest version was installed.

To prevent automatic upgrades to new major versions that may contain breaking
changes, it is recommended to add version = "..." constraints to the
corresponding provider blocks in configuration, with the constraint strings
suggested below.

* provider.azurerm: version = "~> 1.41"
* provider.null: version = "~> 2.1"

Terraform has been successfully initialized!

You may now begin working with Terraform. Try running "terraform plan" to see
any changes that are required for your infrastructure. All Terraform commands
should now work.

If you ever set or change modules or backend configuration for Terraform,
rerun this command to reinitialize your working directory. If you forget, other
commands will detect it and remind you to do so if necessary.
C:\xyz\terraform\qa\bootstrap\rs [shelve/terraform ≡]>

terraform plan -out main.tfplan

C:\xyz\terraform\qa\bootstrap\rs [shelve/terraform ≡]> terraform plan -out main.tfplan
Refreshing Terraform state in-memory prior to plan...
The refreshed state will be used to calculate this plan, but will not be
persisted to local or remote state storage.


------------------------------------------------------------------------

An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
  + create
 <= read (data resources)

Terraform will perform the following actions:

  # module.bootstrap.data.azurerm_storage_account_sas.state will be read during apply
  # (config refers to values not yet known)
 <= data "azurerm_storage_account_sas" "state"  {
      + connection_string = (sensitive value)
      + expiry            = (known after apply)
      + https_only        = true
      + id                = (known after apply)
      + sas               = (sensitive value)
      + start             = (known after apply)

      + permissions {
          + add     = true
          + create  = true
          + delete  = true
          + list    = true
          + process = false
          + read    = true
          + update  = false
          + write   = true
        }

      + resource_types {
          + container = true
          + object    = true
          + service   = true
        }

      + services {
          + blob  = true
          + file  = false
          + queue = false
          + table = false
        }

      + timeouts {
          + read = (known after apply)
        }
    }

  # module.bootstrap.azurerm_resource_group.setup will be created
  + resource "azurerm_resource_group" "setup" {
      + id       = (known after apply)
      + location = "eastus2"
      + name     = "app505-dfpg-qa-tfstate-eastus2"
      + tags     = (known after apply)
    }

  # module.bootstrap.azurerm_storage_account.sa will be created
  + resource "azurerm_storage_account" "sa" {
      + access_tier                       = (known after apply)
      + account_encryption_source         = "Microsoft.Storage"
      + account_kind                      = "Storage"
      + account_replication_type          = "LRS"
      + account_tier                      = "Standard"
      + account_type                      = (known after apply)
      + enable_advanced_threat_protection = (known after apply)
      + enable_blob_encryption            = true
      + enable_file_encryption            = true
      + id                                = (known after apply)
      + is_hns_enabled                    = false
      + location                          = "eastus2"
      + name                              = "dfpgqatfstate"
      + primary_access_key                = (sensitive value)
      + primary_blob_connection_string    = (sensitive value)
      + primary_blob_endpoint             = (known after apply)
      + primary_blob_host                 = (known after apply)
      + primary_connection_string         = (sensitive value)
      + primary_dfs_endpoint              = (known after apply)
      + primary_dfs_host                  = (known after apply)
      + primary_file_endpoint             = (known after apply)
      + primary_file_host                 = (known after apply)
      + primary_location                  = (known after apply)
      + primary_queue_endpoint            = (known after apply)
      + primary_queue_host                = (known after apply)
      + primary_table_endpoint            = (known after apply)
      + primary_table_host                = (known after apply)
      + primary_web_endpoint              = (known after apply)
      + primary_web_host                  = (known after apply)
      + resource_group_name               = "app505-dfpg-qa-tfstate-eastus2"
      + secondary_access_key              = (sensitive value)
      + secondary_blob_connection_string  = (sensitive value)
      + secondary_blob_endpoint           = (known after apply)
      + secondary_blob_host               = (known after apply)
      + secondary_connection_string       = (sensitive value)
      + secondary_dfs_endpoint            = (known after apply)
      + secondary_dfs_host                = (known after apply)
      + secondary_file_endpoint           = (known after apply)
      + secondary_file_host               = (known after apply)
      + secondary_location                = (known after apply)
      + secondary_queue_endpoint          = (known after apply)
      + secondary_queue_host              = (known after apply)
      + secondary_table_endpoint          = (known after apply)
      + secondary_table_host              = (known after apply)
      + secondary_web_endpoint            = (known after apply)
      + secondary_web_host                = (known after apply)
      + tags                              = (known after apply)

      + blob_properties {
          + delete_retention_policy {
              + days = (known after apply)
            }
        }

      + identity {
          + principal_id = (known after apply)
          + tenant_id    = (known after apply)
          + type         = (known after apply)
        }

      + network_rules {
          + bypass                     = (known after apply)
          + default_action             = (known after apply)
          + ip_rules                   = (known after apply)
          + virtual_network_subnet_ids = (known after apply)
        }

      + queue_properties {
          + cors_rule {
              + allowed_headers    = (known after apply)
              + allowed_methods    = (known after apply)
              + allowed_origins    = (known after apply)
              + exposed_headers    = (known after apply)
              + max_age_in_seconds = (known after apply)
            }

          + hour_metrics {
              + enabled               = (known after apply)
              + include_apis          = (known after apply)
              + retention_policy_days = (known after apply)
              + version               = (known after apply)
            }

          + logging {
              + delete                = (known after apply)
              + read                  = (known after apply)
              + retention_policy_days = (known after apply)
              + version               = (known after apply)
              + write                 = (known after apply)
            }

          + minute_metrics {
              + enabled               = (known after apply)
              + include_apis          = (known after apply)
              + retention_policy_days = (known after apply)
              + version               = (known after apply)
            }
        }
    }

  # module.bootstrap.azurerm_storage_container.ct will be created
  + resource "azurerm_storage_container" "ct" {
      + container_access_type   = "private"
      + has_immutability_policy = (known after apply)
      + has_legal_hold          = (known after apply)
      + id                      = (known after apply)
      + metadata                = (known after apply)
      + name                    = "terraform-state"
      + properties              = (known after apply)
      + resource_group_name     = (known after apply)
      + storage_account_name    = "dfpgqatfstate"
    }

  # module.bootstrap.null_resource.post-config will be created
  + resource "null_resource" "post-config" {
      + id = (known after apply)
    }

Plan: 4 to add, 0 to change, 0 to destroy.

------------------------------------------------------------------------

This plan was saved to: main.tfplan

To perform exactly these actions, run the following command to apply:
    terraform apply "main.tfplan"

C:\xyz\terraform\qa\bootstrap\rs [shelve/terraform ≡]>

到目前为止,一切都很好。现在申请:

C:\xyz\terraform\qa\bootstrap\rs [shelve/terraform ≡]> terraform.exe apply .\main.tfplan
module.bootstrap.azurerm_resource_group.setup: Creating...
module.bootstrap.azurerm_resource_group.setup: Creation complete after 3s [id=/subscriptions/*SUB-GUID*/resourceGroups/app505-dfpg-qa-tfstate-eastus2]
module.bootstrap.azurerm_storage_account.sa: Creating...
module.bootstrap.azurerm_storage_account.sa: Still creating... [10s elapsed]
module.bootstrap.azurerm_storage_account.sa: Still creating... [20s elapsed]
module.bootstrap.azurerm_storage_account.sa: Still creating... [30s elapsed]
module.bootstrap.azurerm_storage_account.sa: Creation complete after 32s [id=/subscriptions/*SUB-GUID*/resourceGroups/app505-dfpg-qa-tfstate-eastus2/providers/Microsoft.Storage/storageAccounts/dfpgqatfstate]
module.bootstrap.data.azurerm_storage_account_sas.state: Refreshing state...
module.bootstrap.azurerm_storage_container.ct: Creating...

Error: Error creating Container "terraform-state" (Account "dfpgqatfstate" / Resource Group "app505-dfpg-qa-tfstate-eastus2"): containers.Client#Create: Failure responding to request: StatusCode=404 -- Original Error: autorest/azure: Service returned an error. Status=404 Code="ResourceNotFound" Message="The specified resource does not exist.\nRequestId:4dcdd560-901e-005e-130d-d3a867000000\nTime:2020-01-24T23:26:53.6811230Z"

  on ..\..\..\modules\remote-state\main.tf line 29, in resource "azurerm_storage_container" "ct":
  29: resource "azurerm_storage_container" "ct" {


C:\xyz\terraform\qa\bootstrap\rs [shelve/terraform ≡ +1 ~0 -0 !]>

现在运行第二次工作:

C:\xyz\terraform\qa\bootstrap\rs [shelve/terraform ≡ +1 ~0 -0 !]> terraform.exe apply .\main.tfplan
module.bootstrap.azurerm_resource_group.setup: Creating...
module.bootstrap.azurerm_resource_group.setup: Creation complete after 2s [id=/subscriptions/*SUB-GUID*/resourceGroups/app505-dfpg-qa-tfstate-eastus2]
module.bootstrap.azurerm_storage_account.sa: Creating...
module.bootstrap.azurerm_storage_account.sa: Creation complete after 7s [id=/subscriptions/*SUB-GUID*/resourceGroups/app505-dfpg-qa-tfstate-eastus2/providers/Microsoft.Storage/storageAccounts/dfpgqatfstate]
module.bootstrap.data.azurerm_storage_account_sas.state: Refreshing state...
module.bootstrap.azurerm_storage_container.ct: Creating...
module.bootstrap.azurerm_storage_container.ct: Creation complete after 1s [id=https://dfpgqatfstate.blob.core.windows.net/terraform-state]
module.bootstrap.null_resource.post-config: Creating...
module.bootstrap.null_resource.post-config: Provisioning with 'local-exec'...
module.bootstrap.null_resource.post-config (local-exec): Executing: ["PowerShell" "-NoProfile" "-Command" "Set-Content -Value 'storage_account_name = \"dfpgqatfstate\"' -Path \"backend-config.txt\"\r\nAdd-Content -Value 'container_name = \"terraform-state\"' -Path \"backend-config.txt\"\r\nAdd-Content -Value 'key = \"terraform.tfstate\"' -Path \"backend-config.txt\"\r\nAdd-Content -Value 'sas_token = \"?sv=2017-07-29&ss=b&srt=sco&sp=rwdlac&se=2022-01-23T23:29:47Z&st=2020-01-24T23:29:47Z&spr=https&sig=***\"' -Path \"backend-config.txt\"\r\n"]
module.bootstrap.null_resource.post-config: Creation complete after 1s [id=5713483326668430483]

Apply complete! Resources: 4 added, 0 changed, 0 destroyed.

The state of your infrastructure has been saved to the path
below. This state is required to modify and destroy your
infrastructure, so keep it safe. To inspect the complete state
use the `terraform show` command.

State path: terraform.tfstate
C:\xyz\terraform\qa\bootstrap\rs [shelve/terraform ≡ +2 ~0 -0 !]>

但是为什么我必须运行它两次?我究竟做错了什么?

编辑 1

我在我的笔记本电脑上尝试了几次(当然是在中间破坏)并且一直失败。然后我激活了跟踪日志,5分钟后它第一次通过了。不知道为什么花了5分钟。网络对我来说似乎很好。

我的笔记本电脑在 VPN 上工作。我现在将在没有 VPN 的情况下从工作站尝试。

编辑 2

在办公室的工作站上试过。第一次成功了,但我很怀疑,我销毁并重试,第二次失败了。

编辑 3

我们安装了 ZScaler。

标签: azureterraformterraform-provider-azure

解决方案


推荐阅读