3. IAM 策略语法详解:JSON格式,通配符,ARN归纳总结

好,咱们直接切入正题。
IAM 策略这东西,说白了就是一段 JSON 文本。
你把它贴到 AWS 控制台里,或者通过 API 传过去,云平台就按这个规则来判定“谁”能对“什么资源”做“什么操作”。

我刚开始接触的时候,总觉得 JSON 格式很死板。
但后来发现,只要摸清它的骨架,写策略就跟填表一样简单。

3.1 策略的 JSON 骨架

一个标准的 IAM 策略,长这样:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": "s3:ListBucket",
            "Resource": "arn:aws:s3:::my-bucket"
        }
    ]
}

核心就几个字段:

  • Version:策略语法版本。现在固定写 2012-10-17。别写错了,写老版本有些新功能不支持。
  • Statement:策略主体,是一个数组。你可以写多条语句。
  • Effect:只有两个值 —— Allow 或 Deny。Deny 的优先级永远高于 Allow。
  • Action:你要允许或拒绝的操作,比如 s3:GetObject、ec2:StartInstances。
  • Resource:操作目标,用 ARN 来描述。
我的小习惯: 每次写新策略,我都先用最小权限原则:先写一个 Deny,测试没问题了再改成 Allow。这样可以避免不小心开了大口子。

3.2 通配符:让策略活起来

你想想看,如果每次都要把所有操作列出来,策略得写多长?
AWS 很聪明,引入了通配符。

常用通配符就两个:

通配符 含义 示例
* 匹配零个或多个字符 s3:* 表示所有 S3 操作
? 匹配单个字符 ec2:Describe? 匹配 ec2:Describe 开头的 4 个字符操作

通配符可以用在 Action 和 Resource 里。
在 Action 里,s3:Get* 表示所有「获取」类操作。
在 Resource 里,arn:aws:s3:::my-bucket/* 表示桶内所有对象。

踩坑提醒: 我曾经在生产环境犯过一个错:写了一个 Resource: "*",但忘了加 Condition 限制 IP 来源。结果某个内部工具误操作,把整个 S3 桶列表暴露了出去。从那以后,我写通配符时,一定会在旁边加一个 Condition 来兜底。

3.3 ARN:资源身份证

ARN 的全称是 Amazon Resource Name。
它就像是云上每个资源的「身份证号」。

标准格式:

arn:partition:service:region:account-id:resource

拆开看:

  • partition:除了中国区是 aws-cn,其他都是 aws。
  • service:服务代号,比如 s3、ec2、iam。
  • region:区域,比如 us-east-1。有些资源不区分区域,就写 ""。
  • account-id:你的 AWS 账号 ID。IAM 角色这类全局资源经常用 "" 代替。
  • resource:资源的具体标识,可以是桶名、实例 ID、路径等。

举个例子:

arn:aws:s3:::my-bucket/path/*

这个 ARN 表示:
my-bucket 桶下 /path/ 目录里的所有对象。

核心要点:
  • S3 桶的 ARN 要写成 arn:aws:s3:::bucket-name (注意冒号个数)
  • 桶内对象要写成 arn:aws:s3:::bucket-name/*
  • IAM 用户的 ARN 是 arn:aws:iam::account-id:user/username

3.4 策略语法知识图谱

下面这张图,我把 JSON 结构、通配符、ARN 的关系理了一遍。
你看一眼,基本就能在脑子里装下整个框架:

IAM 策略语法核心结构 IAM 策略 (JSON) Version Statement [ 数组 ] Effect Action Resource Condition 通配符 (* / ?) ARN 格式剖析 Action 模糊匹配 Resource 路径匹配 arn:partition:service:region:account:resource 全局 vs 区域资源区分 Effect / Action / Resource / Condition 组成 Statement

这图把整个策略语法拆成了三层:

  1. 顶层骨架:Version + Statement 数组。
  2. 语句核心:Effect + Action + Resource + Condition。
  3. 扩展能力:通配符让 Action 和 Resource 变得灵活,ARN 让你精准锁定目标。

3.5 实例对比:完全匹配 vs 通配符

咱们看两个例子,感受一下差异:

场景 策略写法 效果
精确控制 "Action": ["s3:PutObject"], "Resource": "arn:aws:s3:::my-bucket/reports/*" 只允许上传到 reports 目录
宽松控制 "Action": ["s3:*"], "Resource": "*" 允许所有 S3 操作,所有资源。谨慎使用!

我个人的经验是:
刚开始尽量用精确写法,别嫌麻烦。等你对业务和权限模型足够熟悉了,再用通配符来简化。
但有一条底线:Resource 永远不要出现裸 *,除非你明确知道自己在做什么。

快速自查清单:
  • Version 写对了吗?
  • Effect 是 Allow 还是 Deny?
  • Action 里通配符是否太宽泛?
  • Resource 是否包含了不该开放的范围?
  • ARN 格式有没有多冒号或少冒号?
写完策略,自己对着这五条过一遍,能防住 90% 的低级错误。