修改 Cloud Storage 存储桶名称时需要注意的陷阱

由于最近经常从事数据基础架构建设的工作,我开始使用Terraform进行对GCP的操作。这次我要介绍的是在更改Cloud Storage桶名称时容易陷入困境的地方。当然,不仅仅是Cloud Storage,在其他服务或AWS上也有一些可应用的地方吧。

环境
Terraform 版本 1.1.2
运行在 darwin_arm64 上
供应商 registry.terraform.io/hashicorp/google 版本 4.15.0尚未验证其他环境是否正常运行。

由来

在创建了以下存储桶并在验证环境中应用后,我提交了PR。

resource "google_storage_bucket" "my_bucket" {
  name                        = "my-bucket"
  storage_class               = var.gcs_storage_class.coldline
  project                     = var.project_id
  location                    = var.gcs_location
  force_destroy               = false
  uniform_bucket_level_access = true

  retention_policy {
    is_locked        = true
    retention_period = 30
  }



  lifecycle_rule {
    condition {
      age = 30
    }
    action {
      type = "Delete"
    }
  }
}

接受了团队成员的审查后,他们告诉我说将存储桶名称从my-bucket改为my-bucket-hoge更好。于是我执行了terraform apply来进行该名称更改,但出现了错误。当然,在最开始的时候,我将force_destroy设置为false,因为存储桶内有对象存在,所以无法强制更改。

force_destroy - (Optional, Default: false) When deleting a bucket, this boolean option will delete all contained objects. If you try to delete a bucket that contains objects, Terraform will fail that run.

我找到了两个解决办法。

    1. 删除存储桶内的对象后,再次执行terraform apply。

完全删除存储桶。

除非有特殊原因,否则1明显更方便。如果必须完全删除此开发用存储桶,或者(像作者一样)在控制台中意外删除存储桶,则需要采取额外的措施。

桶被删除时的应对措施 shí de

首先,执行terraform plan

Error: Error acquiring the state lock
Error message: resource temporarily unavailable

由于Terraform和GCP的状态不一致,因此可以对其进行锁定。
可以使用terraform force-unlock {你的锁定ID}命令来解除锁定。这个操作非常危险,建议在确认团队成员最近是否进行了操作后再执行。

当再次执行terraform plan时,似乎会无限停留在”Refreshing state…”。根据官方文档的调查,设置环境变量并重新执行plan可以查看更详细的日志。

export TF_LOG=TRACE
terraform plan

 

---[ RESPONSE ]--------------------------------------
HTTP/2.0 404 Not Found
Content-Length: 171
Alt-Svc: h3=":443"; ma=2592000,h3-29=":443"; ma=2592000,h3-Q050=":443"; ma=2592000,h3-Q046=":443"; ma=2592000,h3-Q043=":443"; ma=2592000,quic=":443"; ma=2592000; v="46,43"
Cache-Control: no-cache, no-store, max-age=0, must-revalidate
Content-Type: application/json; charset=UTF-8
Date: Fri, 27 May 2022 01:12:48 GMT
Expires: Mon, 01 Jan 1990 00:00:00 GMT
Pragma: no-cache
Server: UploadServer
Vary: Origin
Vary: X-Origin
X-Guploader-Uploadid: xxxx

{
 "error": {
  "code": 404,
  "message": "The specified bucket does not exist.",
  "errors": [
   {
    "message": "The specified bucket does not exist.",
    "domain": "global",
    "reason": "notFound"
   }
  ]
 }
}

尽管应该存在一个存储桶,但却一直不断出现“存储桶不存在”错误消息。原因是terraform的状态仍然是旧的。幸运的是,Terraform已经提供了一个功能,可以删除旧状态,即terraform state rm命令。请使用以下命令来删除最初创建的存储桶的状态。

terraform state rm module.storage.google_storage_bucket.my_bucket

 

再次执行terraform plan将解决问题。
除了云存储外,当发生类似情况时,我们也可以利用这次的经验。
那么,再见!

广告
将在 10 秒后关闭
bannerAds