尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

terraform-provider-aws 数据源解析:aws_billing_service_account 与 AWS 账单服务账号权限配置

terraform-provider-aws 数据源解析:aws_billing_service_account 与 AWS 账单服务账号权限配置 terraform-provider-aws 数据源解析aws_billing_service_account 与 AWS 账单服务账号权限配置【免费下载链接】terraform-provider-awsThe AWS Provider enables Terraform to manage AWS resources.项目地址: https://gitcode.com/GitHub_Trending/te/terraform-provider-aws本指南以 terraform-provider-aws 中aws_billing_service_account数据源为主题讲解如何通过该数据源获取 AWS Billing and Cost Management 服务账号的 Account ID 与 ARN并将其用于 S3 存储桶策略以授权 AWS 写入计费日志。阅读完成后你将掌握该数据源的使用方法、无参数调用的设计原理以及它在 S3 计费日志归档场景中的完整落地配置。数据源是什么一个无需 AWS API 调用的静态账号查询aws_billing_service_account是 terraform-provider-aws 提供的一个特殊数据源它不向任何 AWS API 发起请求也不依赖任何参数而是直接返回 AWS 官方公布的 Billing and Cost Management 服务账号信息。在 AWS 的计费架构中当你为 S3 存储桶开启计费日志Billing Reports / Cost Usage Report写入时写日志的服务账号是一个 AWS 官方维护的固定账号而非你的个人账号。要在 S3 存储桶策略中授权该账号写入就需要在策略的Principal中引用这个固定账号的 ARN。该数据源存在的意义就是避免你在 Terraform 配置中硬编码这一串官方账号 ID。根据官方文档其核心用途描述为使用此数据源获取 AWS Billing and Cost Management 服务账号的 Account ID用于在 S3 存储桶策略中放行该账号。对应文档website/docs/d/billing_service_account.html.markdown。示例用法为 S3 计费日志桶授权 AWS 账单服务账号以下是官方文档给出的完整示例它展示了从创建存储桶、设置 ACL到用aws_iam_policy_document构造桶策略、再挂载策略的完整链路data aws_billing_service_account main {} resource aws_s3_bucket billing_logs { bucket my-billing-tf-test-bucket } resource aws_s3_bucket_acl billing_logs_acl { bucket aws_s3_bucket.billing_logs.id acl private } data aws_iam_policy_document allow_billing_logging { statement { effect Allow principals { type AWS identifiers [data.aws_billing_service_account.main.arn] } actions [ s3:GetBucketAcl, s3:GetBucketPolicy, ] resources [aws_s3_bucket.billing_logs.arn] } statement { effect Allow principals { type AWS identifiers [data.aws_billing_service_account.main.arn] } actions [s3:PutObject] resources [${aws_s3_bucket.billing_logs.arn}/*] } } resource aws_s3_bucket_policy allow_billing_logging { bucket aws_s3_bucket.billing_logs.id policy data.aws_iam_policy_document.allow_billing_logging.json }这段配置中有两个值得注意的细节第一个 statement授权账单服务账号对存储桶本身执行s3:GetBucketAcl和s3:GetBucketPolicy这是 AWS 写日志前读取桶配置所必需的最小权限第二个 statement授权s3:PutObject写入桶内的对象资源为arn/*桶下所有对象这是实际写入计费日志对象所需的权限。两条语句的Principal都引用了data.aws_billing_service_account.main.arn从而避免了硬编码官方账号 ARN。Argument Reference零参数设计该数据源不支持任何参数This data source does not support any arguments.这与它的实现方式直接相关。查看源码 internal/service/billing/billing_service_account_data_source.go其 Schema 中仅定义了两个计算属性Computed: true没有Optional的入参response.Schema schema.Schema{ Attributes: map[string]schema.Attribute{ names.AttrARN: schema.StringAttribute{ Computed: true, }, names.AttrID: schema.StringAttribute{ Optional: true, Computed: true, }, }, }声明数据源时甚至不需要写data aws_billing_service_account main {}之外的任何配置块。Attribute Referenceid 与 arn数据源导出以下属性属性说明idAWS 账单服务账号的 Account IDarnAWS 账单服务账号的 ARN在源码实现中这两个值的来源非常清晰。Read方法内直接硬编码了官方服务账号 ID并通过全局 ARN 构造方法生成 ARN// See http://docs.aws.amazon.com/awsaccountbilling/latest/aboutv2/billing-getting-started.html#step-2 const serviceAccountID 386209384616 data.ARN fwflex.StringValueToFrameworkLegacy(ctx, d.Meta().GlobalARNWithAccount(ctx, iam, serviceAccountID, root)) data.ID fwflex.StringValueToFrameworkLegacy(ctx, serviceAccountID)也就是说id固定返回386209384616arn由GlobalARNWithAccount构造服务名为iam、账号 ID 为386209384616、资源为root得到形如arn:aws:iam::386209384616:root的全局 ARN。GlobalARNWithAccount定义在 internal/conns/awsclient.go其底层通过arn.ARN结构体拼接出无 Region、指定账号 ID的 ARN// GlobalARNWithAccount returns a global (no Region) ARN for the specified service namespace, resource and account ID. func (c *AWSClient) GlobalARNWithAccount(ctx context.Context, service, accountID, resource string) string { return c.arn(ctx, service, , accountID, resource) }arn方法则负责填充 Partition、Service、Region、AccountID、Resource 五个字段并调用.String()序列化见 internal/conns/awsclient.go。因此该 ARN 会随 Provider 配置的分区如aws、aws-cn、aws-us-gov自动适配这也是它比硬编码字符串更健壮的原因之一。源码层面的实现细节基于 Terraform Plugin Framework 实现从源码结构看该数据源是基于terraform-plugin-framework实现的新一代数据源。文件头部的生成器注释与注册逻辑可以佐证// FrameworkDataSource(aws_billing_service_account, nameService Account) func newServiceAccountDataSource(context.Context) (datasource.DataSourceWithConfigure, error) { d : billingServiceAccountDataSource{} return d, nil }其注册信息位于 internal/service/billing/service_package_gen.go注意其中Region: inttypes.ResourceRegionDisabled()的标记——这表示该数据源与 Region 无关全局资源因为账单服务账号在全球范围内是同一个固定账号不随调用 Region 变化。不发起任何 AWS API 调用Read方法内没有创建任何 AWS 服务客户端也没有调用List*/Get*之类的 API而是直接向 State 写入常量值。这也是文档中零参数、无 API 依赖设计的直接体现。与同包内需要调用 Billing API 的aws_billing_views数据源见 internal/service/billing/views_data_source.go 中d.Meta().BillingClient(ctx)的用法相比aws_billing_service_account是一个纯本地计算的数据源运行时不会产生任何计费或网络开销。测试用例对输出的约束该数据源的行为由接受测试严格锁定。测试文件 internal/service/billing/billing_service_account_data_source_test.go 中func TestAccBillingServiceAccountDataSource_basic(t *testing.T) { ctx : acctest.Context(t) dataSourceName : data.aws_billing_service_account.test billingAccountID : 386209384616 ... Check: resource.ComposeTestCheckFunc( resource.TestCheckResourceAttr(dataSourceName, names.AttrID, billingAccountID), acctest.CheckResourceAttrGlobalARNAccountID(dataSourceName, names.AttrARN, billingAccountID, iam, root), ), ... }测试明确断言id必须等于386209384616arn必须是一个全局无 Region、账号 ID 为386209384616、服务为iam、资源为root的 ARN即arn:aws:iam::386209384616:root。这为文章开头的结论提供了可验证的依据如果你在配置中看到data.aws_billing_service_account.main.arn它解析出来的就是 AWS 官方账单服务账号的 IAM root ARN。实际使用注意事项只能用于放行 AWS 账单服务该账号是 AWS 官方用于写计费日志的专用账号不能把它当作自己的 AWS 账号使用也不要试图用它做资源授权以外的操作。配合aws_iam_policy_document使用更佳示例中先构造aws_iam_policy_document再通过aws_s3_bucket_policy挂载避免手写 JSON 策略字符串也便于把arn作为变量直接引用。权限最小化官方示例给出了读桶属性s3:GetBucketAcl、s3:GetBucketPolicy与写对象s3:PutObject两组权限实际生产环境建议仅开启确实需要的动作。无需 provider 的 AWS 凭证也能 plan由于该数据源不调用 API即使本地凭证权限有限terraform plan阶段也能正常解析出arn与id。总结aws_billing_service_account是 terraform-provider-aws 中一个小而精的全局数据源零参数、零 API 调用通过 internal/service/billing/billing_service_account_data_source.go 中硬编码的官方账号 ID386209384616与全局 ARN 构造逻辑稳定输出id与arn两个属性专门服务于 S3 计费日志桶的策略授权场景。理解它的实现方式也有助于举一反三凡是这类官方固定账号/固定标识的查询需求都可以参考此模式用常量输出 全局 ARN 构造的方式在 Provider 中实现从而避免用户在配置中硬编码魔法数字。【免费下载链接】terraform-provider-awsThe AWS Provider enables Terraform to manage AWS resources.项目地址: https://gitcode.com/GitHub_Trending/te/terraform-provider-aws创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表