关于 alibabacloud-terraform-code-generation
此 Agent Skill 将自然语言描述的 Alibaba Cloud 基础设施需求转换为 Terraform 配置,面向需要生成云资源代码的开发与运维人员。生成时从 aliyun/alicloud Provider 文档获取资源信息,并执行格式与验证流程;不会运行 terraform apply。
主要功能
- 01从自然语言提取基础设施需求
- 02按 Provider 文档生成 Terraform
- 03检查资源类型与弃用状态
- 04运行格式化和验证流程
- 05不执行 terraform apply
适用场景
- 01为新云环境生成 Terraform 配置
- 02将需求拆解为资源及依赖关系
- 03根据 Provider 文档核对资源参数
- 04生成配置并检查格式与有效性
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ aliyun/ alibabacloud-aiops-skills --skill alibabacloud-terraform-code-generation安装后在 Claude Code 中输入/alibabacloud-terraform-code-generation确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
references/alicloud-providers.mdauth-and-network.mddeprecated-fields.mdresource-patterns.mdscripts/build_alicloud_providers.pybuild_deprecated_fields.py详细介绍
Alibaba Cloud Terraform 代码生成
将自然语言描述的 Alibaba Cloud 基础设施需求转换为经过验证的
Terraform 配置,适用于当前的 aliyun/alicloud 提供商。生成时会从提供商
自己的文档中获取资源知识——无需维护本地的黄金示例。
硬性规则(绝不违反)
1. 凭证——绝不泄露,绝不要求提供
绝不在任何地方读取、打印、索取或写入 AK/SK 值——包括 HCL、注释、环境
变量声明、Shell 输出和日志。alicloud 提供商通过七种机制解析凭证(环境变量 AK/SK、共享的 config.json、ECS 实例 RAM 角色、Assume Role、OIDC/RRSA、sidecar URI、静态 HCL)——完整流程请参阅
references/auth-and-network.md。凭证均由提供商自身读取,而非此技能。不要推荐已弃用的 ALICLOUD_* /
ALIBABACLOUD_*(无下划线)环境变量名称——当前名称为
ALIBABA_CLOUD_ACCESS_KEY_ID / _ACCESS_KEY_SECRET / _SECURITY_TOKEN。
2. 如实报告——绝不声称执行了未运行的步骤
除非相应命令确实已执行并返回该状态,否则绝不报告 fmt: ok / validate: ok / plan: ok。如果跳过某个步骤(工具缺失、用户选择不执行),请说明 “SKIPPED”(或 **“FAILED”)**及原因。可以转述真实输出,但不得捏造。
3. 禁止执行 terraform apply
此技能绝不运行 terraform apply。plan 为可选步骤(第 8 步);apply 严格来说只能由用户执行。
环境(非强制建议)
- 建议使用 Terraform ≥ 1.5。不要自动安装或下载 Terraform;第 6 步会检查
terraform是否位于 PATH 中,并报告实际验证状态。 - 需要网络——第 4.2 步会通过 WebFetch 获取每种资源的提供商文档。
工作流
第 1 步:解析需求
提取:
region——默认值为cn-hangzhou。resources[]——{ alicloud_type, quantity, attributes }。- 非功能性需求:多可用区、加密、备份、高可用、IOPS。
如果需求有歧义(例如“搭个数据库”),最多提出 一个 澄清问题。
第 2 步:解析目标目录
从用户请求中提取 <target-dir>(例如明确指定的路径
myshop-infra/;若未指定,则使用当前工作目录)。之后所有 fmt / init / validate 命令均在此目录中运行。
写入任何 .tf 文件之前,必须创建该目录:
mkdir -p <target-dir>
所有文件写入路径必须以 <target-dir>/ 为前缀——绝不直接写入当前工作目录,也绝不写入通用的 outputs/ 父目录。生成完成后,验证目录结构:
ls -R <target-dir>
第 3 步:规划架构
编写任何 HCL 之前,先拟定依赖关系表——每种资源占一行:
| resource | depends on | AZ / placement |
|---|
- 扩展
resources[],加入隐含基础设施(VPC → VSwitch → SecurityGroup → 工作负载);用户解析阶段通常会遗漏这些。 - 扩展后的列表将作为第 4 步门控检查的输入。
第 4 步:HCL 前置门控(强制)
对于第 3 步中的每个不同的 alicloud_* 类型(包括资源和数据源),依次执行 4.1 → 4.2 → 4.3。每种类型的调用彼此独立——
请跨类型并行发起。
4.1 文档前查找(目录 + 模式,并行)
先并行执行两项本地查找,再使用 WebFetch:
(a) 目录查找 — 确认资源存在并检查弃用状态。
目录(references/alicloud-providers.md)约有 2600 行;不要
整份 Read — 使用 grep,它只会返回所需的行:
grep "alicloud_<name>" references/alicloud-providers.md
三种结果:
- 找到行,状态列为空 → 记下该行中的
[doc](<url>); 继续执行 4.2。 - **找到行,状态为
⚠️ 弃用 →<new_name>** → 将计划改为<new_name>并重新查找。绝不要输出已弃用的名称。常见情况:alicloud_fc_function→alicloud_fcv3_function`。 - 未找到行 → 停止。询问用户名称是否拼写有误;
不要自行编造
alicloud_<guess>。
(b) 模式查找(有条件)— 如果用户的需求符合
references/resource-patterns.md 中列出的产品专属惯用模式(例如
RDS 跨可用区高可用、OSS 非当前版本生命周期、VPC 对等连接),请阅读
相关章节。这些惯用模式不在提供商文档的 Required
列表中,但却是用户真正需要的内容(例如,文档将用于 RDS
高可用的 zone_id_slave_a 列为可选项,但要实现真正的跨可用区部署就必须设置它)。
遗漏这些内容会产生“验证通过但结果悄然错误”的输出。
找到匹配的模式章节后,该章节“Required attributes”表中列出的所有属性都必须出现在生成的 HCL 中 ——即使提供商文档将其标记为 Optional,也要将其视为必填项。
# Quick check whether a relevant pattern exists, then Read only the section:
grep -in "<keyword>" references/resource-patterns.md
4.2 获取提供商文档(WebFetch)
使用 WebFetch 获取 4.1 中的文档 URL。如果失败或未返回有用内容,
则直接根据目录行中的 doc URL 构造原始 URL。保留目录中的类型:
资源使用 website/docs/r/,数据源使用 website/docs/d/。
https://raw.githubusercontent.com/aliyun/terraform-provider-alicloud/master/website/docs/{r|d}/<doc_name>.html.markdown
如果两者都失败,则回退到
references/alicloud-providers.md 中的本地目录行。在复述标题前加上
doc unreachable: used local catalog。不要获取任何其他 URL —
只有以上两个 URL 或本地目录是可信来源。
4.3 复述(阅读证明)
编写任何 HCL 前,先输出并核实每个资源的完整摘要:
- 必填参数(逐字引用文档中的列表;如果采用 4.2 的回退,则引用本地目录)
- 2–5 个关键可选参数,与用户需求相关
- 文档“Example Usage”中的最简 HCL 代码片段(仅在采用回退时,才可省略并注明
no example available)
如果缺少必填或可选参数,请返回 4.2。跳过复述或只提供部分复述属于严重失败;WebFetch 失败时应采用 4.2 的回退方式,而不是依靠记忆。
Step 5. 生成
5.1 根据复述内容编写 HCL,而非依靠记忆
只能使用 4.3 中确认的参数。如果需要使用未列入复述摘要的参数,请重新执行 4.2 并深入查阅;不要猜测。
编写字段前,请在
references/deprecated-fields.md 中查找该资源(四种行类型及其处理规则见 §5.6):
grep '`alicloud_<resource>`' references/deprecated-fields.md
如果用户需求涉及具有特定使用模式的产品(例如 RDS 跨可用区高可用、VPC 对等连接、OSS 生命周期),还要查阅 references/resource-patterns.md,了解那些不明显的属性。
5.2 数据源强制要求(必须遵守 — 不得硬编码 ID)
必须通过 data 块解析,不得使用字面值。这些也必须通过 Step 4 的检查:
zone_id→data "alicloud_zones"(按available_resource_creation过滤)。image_id→data "alicloud_images"(按name_regex过滤,设置owners = "system"、most_recent = true)。instance_type→data "alicloud_instance_types"(按cpu_core_count、memory_size和可用区过滤)。
5.4 Provider 块(内容契约)
项目的 *.tf 文件中任意位置都必须包含以下两个 Terraform 块。Terraform 会合并目录中的所有 *.tf 文件,因此文件组织方式属于风格选择,而非契约——参见下文“文件组织”。
块 1 — terraform { required_providers {} }:
terraform {
required_version = ">= 1.5"
required_providers {
alicloud = {
source = "aliyun/alicloud"
version = "~> 1.274"
}
}
}
- Provider 版本:查询最新发布的稳定版
aliyun/alicloud1.x 版本,然后写入悲观次要版本约束(1.278.0->~> 1.278)。 按以下顺序查询:https://registry.terraform.io/v1/providers/aliyun/alicloud/versionshttps://registry.terraform.io/providers/aliyun/alicloud/latesthttps://github.com/aliyun/terraform-provider-alicloud/releases或https://github.com/aliyun/terraform-provider-alicloud/tags
- 如果查询失败,则回退到
~> 1.274。可接受的格式为来自已确认发布的 1.x 版本的~> 1.<minor>。切勿写入无上限约束(>= 1.x、>= 1.239.0)或不带约束的版本字符串。
块 2 — provider "alicloud" {},其中必须包含 region = var.region 和 configuration_source:
provider "alicloud" {
region = var.region
configuration_source = "AlibabaCloud-Agent-Skills/alibabacloud-terraform-code-generation"
}
configuration_source是归属标记——必填。region必须引用var.region,不得使用硬编码字面值。
文件组织(建议,并非必需):常见拆分方式为 terraform.tf(块 1)+ providers.tf(块 2)。也可接受:在单个 versions.tf 中包含两个块,或将任一块放在 main.tf 顶部。选择适合项目的方式——Terraform 会同等合并所有 *.tf 文件。切勿添加文件名检查;请改为运行下方的内容检查。
生成后验证(跨文件内容 grep):
# 1. required_providers has aliyun/alicloud with a ~> 1.<minor> version
awk '
/required_providers[[:space:]]*{/ { in_req=1 }
in_req && /alicloud[[:space:]]*=[[:space:]]*{/ { in_ali=1 }
in_ali && /source[[:space:]]*=[[:space:]]*"aliyun\/alicloud"/ { source=1 }
in_ali && /version[[:space:]]*=[[:space:]]*"~>[[:space:]]*1\.[0-9]+"/ { version=1 }
in_ali && /^[[:space:]]*}/ { in_ali=0 }
END { exit(source && version ? 0 : 1) }
' <target-dir>/*.tf \
&& echo OK_VERSION || echo BAD_OR_MISSING_VERSION
# 2. configuration_source attribution present somewhere
grep -Rq 'configuration_source = "AlibabaCloud-Agent-Skills/alibabacloud-terraform-code-generation"' \
<target-dir>/*.tf \
&& echo OK_CFG_SOURCE || echo MISSING_CFG_SOURCE
# 3. region uses variable, not hardcoded
grep -Rq 'region\s*=\s*var\.region' <target-dir>/*.tf \
&& echo OK_REGION_VAR || echo HARDCODED_REGION
三项都必须返回 OK。如果任一项失败,请修复相应内容并重新运行——存在失败时,切勿继续执行步骤 6。
5.5 风格基线
- 使用 2 个空格缩进;在块内对齐
=;语义化资源标签使用 snake_case(alicloud_vswitch.app_a,而非vsw1)。 - 每个支持标签的资源都应包含非空的
tags块,以保持运维规范——根据场景选择合理的键(常见选项:ManagedBy、Project、Environment、CreatedBy)。本技能不规定具体的标签键或值。
5.6 已弃用字段审计——静态 grep 检查(强制)
在需要使用 terraform 之前运行——这是对你刚刚编写的 HCL 执行的纯 grep 检查。对于本次生成的每个资源,都要根据 references/deprecated-fields.md 检查项目,并按行类型处理:
- rename 行 → 如果你刚刚编写的 HCL 中出现旧字段名,请将其替换为新字段名。最常见的示例:
alicloud_ram_role:name→role_name,document→assume_role_policy_documentalicloud_security_group:name→security_group_namealicloud_db_database:name→data_base_name
- split / soft-split 行 → 不要在父资源中编写内联字段。只有在用户需求需要该功能,或
references/resource-patterns.md指出该子资源有明确的安全默认值时,才声明替代子资源。示例:对于 OSS 存储桶,alicloud_oss_bucket_acl的默认值为private,但除非用户要求使用相关功能,否则应省略日志、CORS 和网站子资源。 - deprecated-no-replacement 行 → 停止使用该字段,不要使用替代项。
仅适用于本次生成中编写的文件——不要重构用户已有且未要求你修改的文件。
审计后验证(bash grep——必须全部返回 OK):
# Walk deprecated-fields.md row by row and check whether any deprecated
# field that applies to a generated resource is still in use.
# Uses awk to extract individual resource blocks before field matching,
# so that short field names (name, document) don't falsely match
# substrings in compound field names (role_name, policy_document).
grep '| `alicloud_' references/deprecated-fields.md | while IFS='|' read _ resource field kind _; do
resource=$(echo "$resource" | tr -d ' `')
field=$(echo "$field" | tr -d ' ')
kind=$(echo "$kind" | tr -d ' ')
# Only check if this resource exists in the generated HCL
if grep -Rq "resource \"$resource\"" <target-dir>/*.tf; then
case "$kind" in
rename|deprecated-no-replacement)
awk -v res="$resource" -v fld="$field" '
$0 ~ "resource \"" res "\"" { in_block=1; next }
in_block && /^}/ { in_block=0 }
in_block && $0 ~ "(^|[^_[:alnum:]])" fld "([^_[:alnum:]]|$)" { found=1; exit }
END { exit found ? 0 : 1 }
' <target-dir>/*.tf \
&& echo "DEPRECATED: $resource.$field" || echo "OK: $resource.$field"
;;
split|soft-split)
grep -q "\b$field\b\s*=" <target-dir>/*.tf \
&& echo "DEPRECATED: $resource.$field (inline — use standalone sub-resource)" \
|| echo "OK: $resource.$field (not inline)"
;;
esac
fi
done
硬性门槛:必须通过后才能进入步骤 6——如果上面的脚本输出了任何 DEPRECATED: 行:
- 阅读每一行
DEPRECATED:——其中会指出资源和字段。 - 在
references/deprecated-fields.md中查找对应的资源和字段,获取 Action 列(重命名目标、拆分后的子资源等)。 - 在 HCL 中应用修复。
- 重新运行验证脚本。
- 重复以上步骤,直到每一行都返回
OK:。这是必须通过的门槛——如果输出中仍有任何DEPRECATED:,不要继续步骤 6。只有在脚本全部输出OK:时,才能声称“已验证”。
步骤 6. 验证 + 提供方弃用检测
如果 terraform 位于 PATH 中:
(cd <target-dir> \
&& terraform fmt -recursive \
&& terraform init -backend=false \
&& terraform validate -json)
持续循环,直到满足两个条件(最多总共修复 3 次):
- 解析
validate -json。如果有错误 → 修复有问题的文件,然后转到步骤 3。 - 扫描
validate -json的diagnostics[].summary,查找[DEPRECATED]字符串。提供方会发出权威的弃用注释(例如,"document": "[DEPRECATED] … 请改用新字段 'assume_role_policy_document'。")。如果找到 → 修复对应字段,然后转到步骤 3。 - 重新运行
cd <target-dir> && terraform validate -json,然后返回步骤 1。
只有当 validate 报告没有错误且没有 [DEPRECATED] 诊断时,才能退出循环。尝试 3 次后仍未达到此状态:继续步骤 7,并使用 Validation: FAILED (<diagnostic excerpt>),同时在可选备注中逐字包含失败的 HCL。
如果 init 因网络错误失败(无法连接到 registry.terraform.io):
这不是配置错误。请引导用户查看 references/auth-and-network.md 中的镜像源配置,然后继续步骤 7——摘要中必须使用 Validation: SKIPPED (init failed — network/unreachable)。不要盲目重试,也不要自行编写 ~/.terraformrc。
如果缺少 terraform:跳过此步骤,并在步骤 7 的摘要中说明这一情况(硬性规则 §2),使用 Validation: SKIPPED (terraform binary not on PATH)。
步骤 7. 覆盖检查 + 总结
必须执行 — 无论生成结果如何都要运行。 即使前面的步骤被中断(初始化网络失败、验证循环耗尽、terraform 不在 PATH 中),也必须执行此步骤。Files written: 和 Validation: 行是与下游评估器之间的最终约定 — 跳过它们将导致严重失败。
覆盖检查。 枚举生成的 HCL 中的资源块,并与步骤 3 的草稿进行比较。如果草稿中有任何一行缺失,返回步骤 5 并补上 — 不要因为“用户没有明确提及”而跳过某一行。
总结模板 — 使用用户的语言打印,并且严格遵循以下结构(填写 <bracketed> 占位符,Files written: 和 Validation: 两个行标签保持原样):
Files written:
<path/to/file1>
<path/to/file2>
...
Validation: <one-of-four-exact-strings-below>
Deprecation routing: <If re-routed: `<original_name>` → `<new_name>`; else: None>
<optional: architecture notes, design decisions, deploy hints — free-form
here is fine, but NOT inside the lines above>
Validation: 行必须是以下确切字符串之一,根据步骤 6 中实际发生的情况选择。不要改写或将其合并到正文中:
Validation: terraform fmt+validate: okValidation: SKIPPED (terraform binary not on PATH)Validation: SKIPPED (<reason>)Validation: FAILED (<diagnostic excerpt>)— 重试 3 次后达到上限
边缘情况:
- 初始化超时 →
Validation: FAILED (init timed out — provider installation exceeded time limit) - 初始化网络不可达 →
Validation: SKIPPED (init failed — network/unreachable) - fmt 成功后初始化失败 → 使用上述根本原因字符串,不要使用混合状态。
步骤 8(可选)。terraform plan
仅在用户提出要求时执行。预检 references/auth-and-network.md 中的全部七种凭证路径,但不读取任何值:
(
[[ -n "${ALIBABA_CLOUD_ACCESS_KEY_ID:-}" ]] && [[ -n "${ALIBABA_CLOUD_ACCESS_KEY_SECRET:-}" ]] && echo "ready:env-ak-sk"
[[ -f "$HOME/.aliyun/config.json" ]] && echo "ready:shared-config"
{ [[ -n "${ALIBABA_CLOUD_CREDENTIALS_FILE:-}" ]] && [[ -f "${ALIBABA_CLOUD_CREDENTIALS_FILE}" ]]; } && echo "ready:custom-credentials-file"
[[ -n "${ALIBABA_CLOUD_ECS_METADATA:-}" ]] && echo "ready:ecs-ram-role"
[[ -n "${ALIBABA_CLOUD_ROLE_ARN:-}" ]] && echo "ready:assume-role"
[[ -n "${ALIBABA_CLOUD_CREDENTIALS_URI:-}" ]] && echo "ready:sidecar"
) | head -1
- 有任何输出 → 有可用的凭证路径:
(cd <target-dir> && terraform init && terraform plan -out=tfplan); 展示输出。 - 输出为空 →
NO_CREDENTIALS。告知用户所有可行路径(环境变量 AK/SK、共享的~/.aliyun/config.json+ALIBABA_CLOUD_PROFILE、ECS 实例 RAM 角色、Assume Role 链、OIDC/RRSA、sidecar URI)— 不要只推荐环境变量 AK/SK。请用户查看references/auth-and-network.md以了解完整的设置方法。然后停止。绝不要读取或打印机密值。
参考资料
| 来源 | 阅读时机 |
|---|---|
references/alicloud-providers.md(本地) | 步骤 4.1 — 资源是否存在、弃用标记、文档 URL |
| Provider 文档(通过 WebFetch 获取 4.1 中的 URL) | 步骤 4.2 — 每种资源的权威 Required / Optional 信息 |
references/deprecated-fields.md(本地) | 步骤 5.1 — terraform validate 不会标记的已知字段级重命名 |
references/resource-patterns.md(本地) | 步骤 5.1 — Provider 文档未重点说明的特定产品惯用模式(RDS HA,…) |
references/auth-and-network.md(本地) | 步骤 6 失败分支 — 镜像源配置;步骤 8 预检 — 完整凭证链 |
本地目录按每种 alicloud_* 资源和数据源各列出一个 Markdown 表格行,其中包含 [doc](<url>) 单元格;对于已弃用条目,则包含 ⚠️ 弃用 → <new_name>`` 标记。该目录由上游 Provider 仓库生成,使用的脚本是 scripts/build_alicloud_providers.py;当新的 aliyun/alicloud 版本引入或调整弃用项时,请重新运行该脚本。