Terraform 模块化结构设计
Terraform 多环境管理,建议采用以下结构:
project-root/
├── components/ # 模組目錄
│ ├── 01-preserver/ # Terraform後端S3資源模組
│ │ ├── outputs.tf
│ │ ├── s3.tf
│ │ └── variables.tf
│ │
│ └── 02-network/ # 網路模組(如 VPC、Subnet)
│ ├── vpc.tf
│ ├── eip.tf
│ ├── subnet.tf
│ ├── security_group.tf
│ ├── nacl.tf
│ ├── nat_gw.tf
│ ├── igw.tf
│ ├── rtb.tf
│ ├── variables.tf
│ └── outputs.tf
│
├── environments/ # 環境變數目錄(與 components 同級)
│ ├── dev/ # 開發環境
│ │ ├── 01-preserver.tfvars
│ │ └── 02-network.tfvars
│ ├── uat/ # 預發佈環境
│ │ ├── 01-preserver.tfvars
│ │ └── 02-network.tfvars
│ └── prd/ # 生產環境
│ ├── 01-preserver.tfvars
│ └── 02-network.tfvars
│
├── versions.tf # 版本約束
└── scripts/ # 统一的脚本目录(如 apply、plan 等)
├── tf-apply.sh
├── tf-plan.sh
├── tf-init.sh
└── tf-destroy.sh
模块设计原则
components/03-eks-cluster/
├── eks.tf # 定义 EKS 资源
├── variables.tf # 模块输入变量定义
└── outputs.tf # 模块输出变量定义
环境隔离与变量管理
在 environments/dev/
中,为每个模块创建独立的 .tfvars
文件:
aws_region = "ap-east-1"
# VPC配置,定義VPC的CIDR和名稱
vpc_config = {
cidr_block = "10.x.x.0/16"
name = "vpc-dev"
}
后端配置与版本统一
tf-init.sh
初始化自动判断,自动生成对应模块独立状态文件的后端配置
(1) 模块化与复用性
- 独立性:每个模块(如
03-eks-cluster
)可独立部署和更新。 - 复用性:每个模块(如
03-eks-cluster
)可在多个组件中复用。
(2) 环境隔离
- 变量隔离:通过
.tfvars
文件实现环境特定配置。 - 状态隔离:通过 S3 后端和工作区确保环境状态独立。
(3) 可维护性
- 清晰的结构:模块、环境、共享配置分层清晰。
- 依赖明确:通过输出变量或远程状态引用其他模块的输出。
如何解决首次创建后端存储的依赖问题:
- 当使用 terraform init -backend=false 时,Terraform 会禁用远程后端(如 S3),转而使用本地 terraform.tfstate 文件存储状态。
- 如果 S3 存储桶本身是通过 Terraform 模块(如 01-preserver)创建的,那么在初始化时 S3 后端可能还不存在,导致无法直接写入状态文件。
- 因此,必须先在本地应用配置(apply),创建 S3 存储桶,再将本地状态文件 terraform.tfstate 手动推送到新创建的 S3 存储桶中。
避免循环依赖:
- 如果直接启用 S3 后端(-backend=true),Terraform 会尝试在初始化时验证 S3 存储桶是否存在。但存储桶本身可能由当前模块创建,导致初始化失败(因为存储桶还未创建)。
- 手动推送状态是解决这种 “先有鸡还是先有蛋” 问题的临时方案。