名称: terraform-风格检查 描述: 遵循 HashiCorp 官方风格约定和最佳实践生成 Terraform HCL 代码。适用于编写、审核或生成 Terraform 配置时使用。 许可证: MIT
Terraform 风格指南
遵循 HashiCorp 官方风格约定和最佳实践生成和维护 Terraform 代码。
代码生成策略
当生成 Terraform 代码时:
- 从提供者配置和版本约束开始
- 在依赖资源之前创建数据源
- 按依赖顺序构建资源
- 添加关键资源属性的输出
- 对所有可配置值使用变量
文件组织
| 文件 | 用途 |
|---|---|
terraform.tf |
Terraform 和提供者版本要求 |
providers.tf |
提供者配置 |
main.tf |
主要资源和数据源 |
variables.tf |
输入变量声明(按字母顺序) |
outputs.tf |
输出值声明(按字母顺序) |
locals.tf |
局部值声明 |
示例结构
# terraform.tf
terraform {
required_version = ">= 1.7"
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.0"
}
}
}
# variables.tf
variable "environment" {
description = "目标部署环境"
type = string
validation {
condition = contains(["dev", "staging", "prod"], var.environment)
error_message = "环境必须是 dev、staging 或 prod。"
}
}
# locals.tf
locals {
common_tags = {
Environment = var.environment
ManagedBy = "Terraform"
}
}
# main.tf
resource "aws_vpc" "main" {
cidr_block = var.vpc_cidr
enable_dns_hostnames = true
tags = merge(local.common_tags, {
Name = "${var.project_name}-${var.environment}-vpc"
})
}
# outputs.tf
output "vpc_id" {
description = "创建的 VPC 的 ID"
value = aws_vpc.main.id
}
代码格式化
缩进和对齐
- 每个嵌套级别使用 两个空格(不使用制表符)
- 对齐连续参数的等号
resource "aws_instance" "web" {
ami = "ami-0c55b159cbfafe1f0"
instance_type = "t2.micro"
subnet_id = "subnet-12345678"
tags = {
Name = "web-server"
Environment = "production"
}
}
块组织
参数在块之前,元参数优先:
resource "aws_instance" "example" {
# 元参数
count = 3
# 参数
ami = "ami-0c55b159cbfafe1f0"
instance_type = "t2.micro"
# 块
root_block_device {
volume_size = 20
}
# 生命周期最后
lifecycle {
create_before_destroy = true
}
}
命名约定
- 对所有名称使用 小写下划线
- 使用 描述性名词,排除资源类型
- 具体且有意义的命名
# 差
resource "aws_instance" "webAPI-aws-instance" {}
variable "name" {}
# 好
resource "aws_instance" "web_api" {}
variable "application_name" {}
变量
每个变量必须包含 type 和 description:
variable "instance_type" {
description = "Web 服务器的 EC2 实例类型"
type = string
default = "t2.micro"
validation {
condition = contains(["t2.micro", "t2.small", "t2.medium"], var.instance_type)
error_message = "实例类型必须是 t2.micro、t2.small 或 t2.medium。"
}
}
variable "database_password" {
description = "数据库管理员用户的密码"
type = string
sensitive = true
}
输出
每个输出必须包含 description:
output "instance_id" {
description = "EC2 实例的 ID"
value = aws_instance.web.id
}
output "database_password" {
description = "数据库管理员密码"
value = aws_db_instance.main.password
sensitive = true
}
动态资源创建
优先使用 for_each 而非 count
# 差 - 使用 count 用于多个资源
resource "aws_instance" "web" {
count = var.instance_count
tags = { Name = "web-${count.index}" }
}
# 好 - 使用 for_each 并命名实例
variable "instance_names" {
type = set(string)
default = ["web-1", "web-2", "web-3"]
}
resource "aws_instance" "web" {
for_each = var.instance_names
tags = { Name = each.key }
}
count 用于条件创建
resource "aws_cloudwatch_metric_alarm" "cpu" {
count = var.enable_monitoring ? 1 : 0
alarm_name = "高 CPU 使用率"
threshold = 80
}
安全最佳实践
生成代码时,应用安全加固:
- 默认启用静态加密
- 在适用处配置私有网络
- 对安全组应用最小权限原则
- 启用日志记录和监控
- 永远不硬编码凭据或密钥
- 使用
sensitive = true标记敏感输出
示例:安全 S3 桶
resource "aws_s3_bucket" "data" {
bucket = "${var.project}-${var.environment}-data"
tags = local.common_tags
}
resource "aws_s3_bucket_versioning" "data" {
bucket = aws_s3_bucket.data.id
versioning_configuration {
status = "Enabled"
}
}
resource "aws_s3_bucket_server_side_encryption_configuration" "data" {
bucket = aws_s3_bucket.data.id
rule {
apply_server_side_encryption_by_default {
sse_algorithm = "aws:kms"
kms_master_key_id = aws_kms_key.s3.arn
}
}
}
resource "aws_s3_bucket_public_access_block" "data" {
bucket = aws_s3_bucket.data.id
block_public_acls = true
block_public_policy = true
ignore_public_acls = true
restrict_public_buckets = true
}
版本固定
terraform {
required_version = ">= 1.7"
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.0" # 允许次要更新
}
}
}
版本约束运算符:
= 1.0.0- 精确版本>= 1.0.0- 大于或等于~> 1.0- 允许最右侧组件递增>= 1.0, < 2.0- 版本范围
提供者配置
provider "aws" {
region = "us-west-2"
default_tags {
tags = {
ManagedBy = "Terraform"
Project = var.project_name
}
}
}
# 多区域别名提供者
provider "aws" {
alias = "east"
region = "us-east-1"
}
版本控制
永不提交:
terraform.tfstate,terraform.tfstate.backup.terraform/目录*.tfplan- 包含敏感数据的
.tfvars文件
始终提交:
- 所有
.tf配置文件 .terraform.lock.hcl(依赖锁文件)
验证工具
提交前运行:
terraform fmt -recursive
terraform validate
附加工具:
tflint- 代码风格和最佳实践检查checkov/tfsec- 安全扫描
代码审核清单
- [ ] 代码使用
terraform fmt格式化 - [ ] 配置使用
terraform validate验证 - [ ] 文件按标准结构组织
- [ ] 所有变量具有类型和描述
- [ ] 所有输出具有描述
- [ ] 资源名称使用描述性名词和下划线
- [ ] 版本约束明确固定
- [ ] 敏感值使用
sensitive = true标记 - [ ] 没有硬编码凭据或密钥
- [ ] 应用了安全最佳实践