← 回所有專案

DevOps / SRE ‧ 房仲業 · 2025

AWS 基礎設施即程式碼(Terraform 模組)

依環境切分的 Terraform 專案結構,附上 Terraform Registry 風格的模組文件(Requirements/Providers/Inputs/Outputs)與 Go(Terratest)整合測試。

TerraformAWSGoTerratestDynamoDBS3IAMEC2CloudFrontALB
AWS 基礎設施即程式碼(Terraform 模組)

專案概述

建立公司的 Terraform 標準規範:一套遠端 State 後端,以及一系列可重複使用、附 完整文件與測試的模組,讓各團隊能以一致的方式建置 AWS 基礎設施,而非各自土法 煉鋼。

專案結構

text
infrastracture/
  global/         # 只需要存在一份的共用資源:State 後端、鎖表、IAM Role
  development/
  stage/
  production/
modules/
  aws/
    alb/
    cloudfront/
    ec2/
    s3/

global 存放 Terraform 自身需要的基礎設施——狀態儲存與鎖定機制,development /stage/production 則各自獨立,同一份模組在不同環境用不同的變數值套用, 彼此的 State 完全隔離。

遠端後端與存取控制

Bootstrap 一次性建立好 Terraform 自己需要的基礎設施後,往後所有模組都指向同 一組遠端後端:

Terraform
terraform {
  backend "s3" {
    bucket         = "tom-terraform-backend"
    key            = "global/s3/tom-terraform-backend/terraform.tfstate"
    region         = "ap-northeast-1"
    dynamodb_table = "tom-terraform-backend-lock"
    encrypt        = true
    assume_role = {
      role_arn    = "arn/S_Terraform_Role"
      policy_arns = ["arn/S_Terraform_Role-policy"]
    }
  }
}
  • S3 儲存 State、DynamoDB 做 State Lock,避免多人同時 apply 造成競 爭寫入
  • 所有操作都透過 assume_role 走一個專屬的 Terraform 執行角色,而不是用長期 存在的 IAM User AccessKey,降低憑證外洩風險

模組文件(Terraform Registry 風格)

每個模組(ALB、CloudFront、EC2、S3)都附上 Registry 慣用的四段式文件:

項目說明
Usagemodule 區塊的最小可用範例
RequirementsTerraform/Provider 版本限制
Inputs每個變數的型別、預設值、是否必填
Outputs模組回傳的屬性(如 ARN、ID)

以 S3 模組為例,Inputs 包含 s3_bucket_name(必填)、 s3_bucket_versioning(預設開啟版本控制)、prevent_destroy(預設鎖住刪 除,避免誤刪正式環境的 bucket),呼叫端不需要讀原始碼就知道怎麼用。

用 Go(Terratest)驗證模組

不是只做 terraform validate,而是每個模組都有一支 Go 整合測試,實際 apply 一份範例設定、檢查輸出的屬性符合預期、再 destroy 乾淨:

Go
func TestS3Example(t *testing.T) {
    ops := &terraform.Options{TerraformDir: "../example"}
    defer terraform.Destroy(t, ops)

    terraform.InitAndApply(t, ops)

    bucketArn := terraform.Output(t, ops, "bucket_arn")
    bucketTags := terraform.OutputMap(t, ops, "tags")
    assert.NotNil(t, bucketArn)
    assert.Equal(t, "expected-bucket-name", bucketTags["Name"])
}

這讓模組的正確性不是靠人工檢查 .tf 檔案,而是每次修改都能重新驗證「這個模組 套用後,AWS 上真的長出預期的資源與屬性」。

實作內容

  • 使用 S3 + DynamoDB + IAM 建立 Terraform 遠端後端,並以 tfvars 管理可編輯人員
  • 製作 ALB、CloudFront、EC2、S3 等可重複使用模組,依環境(development/ stage/production)切分
  • 用 Go(Terratest)為模組撰寫 Apply → Assert → Destroy 的整合測試
  • 撰寫 Registry 風格的模組使用說明文件與內部 Terraform 教學訓練
  • 盤點並調整公司現有 IAM User,改用 AssumeRole 降低常駐憑證數量

成果

讓每個團隊都能以一致、經過測試的方式建置 AWS 基礎設施,取代過去各專案各自為 政、缺乏文件與遠端後端管理的 Terraform 用法。