AWS分销商 AWS S3 频繁报 403 Access Denied?存储桶策略与 IAM 策略冲撞排查
AWS S3 频繁报 403 Access Denied,先别急着加权限
遇到 AWS S3 403 Access Denied,很多团队第一反应是给 IAM 再补一条 Allow,但实际排查里,问题更常见于存储桶策略与 IAM 策略互相冲撞,或者被显式 Deny、KMS、VPC Endpoint、SCP、账号状态挡住。尤其是跨账号访问、ECS/EC2 角色访问、CI/CD 上传、Lambda 读写对象这类场景,只看一边策略通常会误判。
下面按实战里的顺序拆开说,尽量让你能直接决定:是改策略、改账号状态,还是找账单/风控/组织权限先处理。
先确认账号与账单侧有没有把问题放大
如果你是新开 AWS 账号、刚做企业上线,或者通过代理/团队统一开通的海外云账号,先别只盯着 S3 策略。下面这些状态会让排查方向跑偏:
- AWS分销商 支付方式未完成验证:信用卡绑定失败、付款主体不一致、账单无法扣款时,部分操作会被受限。
- AWS分销商 账号进入风控或审核状态:新账号、异常登录、频繁切换地区或支付方式后,先看控制台告警和邮件通知。
- Organizations 组织限制:成员账号可能被 SCP 禁了 s3:GetObject、s3:PutObject、kms:Decrypt 等动作。
- 资源申请受限:有些团队开的是子账号或临时环境,权限本来就只够做测试,不够直接对生产桶操作。
- 成本控制策略:如果为了省钱把角色权限、KMS 权限、跨账号访问全部收紧,后续上线很容易出现“能连上但读不出来”的情况。
实战里常见的情况是:业务方以为是 bucket policy 写错了,最后发现是账号被组织策略挡住,或者支付状态异常导致权限链路看起来正常、实际调用却一直失败。
判断 403 是谁在拦:bucket policy、IAM 还是别的层
S3 的权限不是只看一份策略。你要先判断是“没有允许”,还是“有允许但被更高优先级拒绝”。
| 现象 | 更可能的原因 | 优先检查什么 |
|---|---|---|
| 同一个角色能访问别的桶,唯独某个桶 403 | bucket policy、KMS、对象所有权 | 桶策略里是否有显式 Deny、是否限制了 Principal 或 SourceVpce |
| 控制台能看目录,程序读对象 403 | IAM 允许了 ListBucket,但没有 GetObject | 动作粒度是否写全,是否只放了 bucket ARN 没放 object ARN |
| 上传成功但下载 403 | KMS 解密权限不足 | 是否缺少 kms:Decrypt、kms:GenerateDataKey |
| 跨账号访问一直失败 | 双边策略不一致 | 桶策略和 IAM 角色策略是否同时允许,外加信任关系是否正确 |
| 同一套代码,换网络环境就失败 | VPC Endpoint policy 或条件限制 | 是否限制了 SourceVpce、SourceIp、aws:SecureTransport |
最容易冲撞的几类配置
1. IAM 允许了,但 bucket policy 有显式 Deny
这是最常见的误区。很多人只盯着角色策略,结果桶策略里写了 Deny 某个网段、某个 VPC Endpoint、某个账号,或者只允许特定前缀访问。只要命中显式 Deny,前面的 Allow 都没用。
排查时重点看:
- 是否写了只允许特定
Principal的规则 - 是否限制了
aws:SourceIp、aws:SourceVpce、aws:PrincipalArn - 是否把生产桶和测试桶共用了一份策略,条件写得过死
2. IAM 策略只允许了桶 ARN,没有允许对象 ARN
很多人写到 arn:aws:s3:::bucket-name 就停了,但实际读写对象需要的是 arn:aws:s3:::bucket-name/*。表现通常是:能列桶、看前缀、但一读对象就 403。
3. 角色本身没问题,被权限边界或 SCP 截断
企业账号里经常有这类问题:角色策略写对了,bucket policy 也放了,但组织级 SCP、Permission Boundary 还是把动作挡掉。尤其是新建成员账号、外包账号、临时项目账号,最容易出现“控制台里看着有权限,实际调用失败”。
4. 用了 SSE-KMS,但没给解密权限
如果对象是 KMS 加密,S3 的 403 不一定是 S3 本身拒绝,也可能是 KMS 不允许。常见情况是上传方能写,下载方没有 kms:Decrypt,或者跨账号时密钥策略没有放行目标角色。
AWS分销商 5. 开了 Block Public Access,却还在按“公网桶”思路写策略
如果团队原来习惯用公开访问或临时公开链接,后来又启用了 Block Public Access,旧策略会直接失效。部分用户在迁移到生产桶时,会把“匿名可读”当成默认前提,结果一改就 403。
6. 对象所有权和 ACL 不是你想的那样
跨账号上传后,文件实际 owner 可能不是当前账号。若没有启用统一对象所有权,后续读取、覆盖、删除都会出现奇怪的权限问题。这个问题在共享上传桶、日志桶、媒体处理桶里很常见。
实战排查顺序:按这个顺序改,效率最高
- 先看请求主体是谁:到底是 root、IAM 用户、AssumeRole 之后的角色,还是临时凭证。
- 确认请求动作:是
ListBucket、GetObject、PutObject、DeleteObject,还是带分片上传、版本控制、KMS 解密的复杂动作。 - 检查 IAM 是否有 Allow:动作名、资源 ARN、条件是否完整。
- 检查 bucket policy 是否有显式 Deny:尤其是条件语句、前缀限制、来源限制。
- 看是否有权限边界、SCP、Session Policy:这三层经常被忽略。
- AWS分销商 看对象是否用了 KMS:有加密就查密钥策略和 kms 权限。
- 看是否跨账号或跨 VPC:源账号、目标账号、Endpoint、Region 是否一致。
- 最后再看账号状态和账单:支付方式是否正常、账号是否被风控、是否有停用/审核提醒。
如果你每次都从“加一条允许”开始,排查会越来越乱。正确的做法是先找拒绝来自哪一层,再决定是改 IAM、改 bucket policy,还是改组织策略。
常见错误:看起来像权限问题,其实不是
- 把 bucket ARN 和 object ARN 混了:只授权了桶,没有授权对象。
- 跨账号只改了自己这边:S3 访问必须两边一起配合,单改一边经常没效果。
- 把测试环境策略直接搬到生产:来源 IP、VPC Endpoint、前缀限制写得太死。
- 忽略 KMS:看到 S3 403,就以为是 S3 策略,结果真正挡住的是密钥策略。
- 只用控制台测试,不测程序链路:控制台登录主体和应用运行角色可能不是同一个权限集。
- 忽略临时凭证过期:STS 失效后,前端或程序报错常被误认为 S3 权限冲突。
几种业务场景怎么处理更稳
场景一:EC2/ECS 上的应用访问 S3
优先用实例角色或任务角色,不要把长期密钥写进代码。出现 403 时,先确认实际生效的 role 是哪个,再去看 bucket policy 是否允许这个 role。
场景二:跨账号共享图片、日志或备份桶
这是最容易冲撞的场景。建议把允许条件写清楚:允许哪个账号、哪个角色、哪个前缀、是否允许上传后覆盖。否则后面一做权限收紧,就会出现“能上传不能读”“测试账号能用,生产账号不行”。
场景三:CI/CD 上传构建产物
流水线常用临时凭证,权限窗口短。如果 403 只在某些构建阶段出现,除了策略,还要看 token 是否过期、角色是否切换、以及仓库里是否用了旧密钥。
场景四:Lambda 处理 S3 事件
Lambda 触发链路里,经常同时涉及 S3、CloudWatch、KMS 和执行角色。403 不一定发生在触发点,也可能发生在函数读对象或写回结果对象时。
如果你要做长期稳定的权限设计,建议这样收口
- 把生产桶、测试桶、归档桶分开,不要共用一套过度复杂的条件策略。
- 优先用最小权限,但不要把前缀、来源、加密三层都同时卡死。
- 跨账号访问尽量固定角色和固定前缀,减少后续改动面。
- 上线前把 KMS、SCP、Endpoint policy 一起纳入检查清单。
- 账号开通、实名认证、企业认证、支付方式绑定、风控审核这些基础动作要先走完,避免业务上线后才发现账号处于受限状态。
- 如果是预算敏感的项目,先把日志、测试和生产分层,减少无效重试带来的请求成本和排查时间。
FAQ
Q1:IAM 已经放行了,为什么还是 403?
大概率是 bucket policy 里有显式 Deny,或者被 SCP、权限边界、KMS、VPC Endpoint 其中一层挡住了。只看 IAM 不够。
Q2:为什么同一账号下,有的目录能访问,有的目录不行?
通常是前缀级别限制、对象所有权不同,或者某些前缀绑定了更严格的条件策略。先比对能访问和不能访问对象的 ARN、加密方式、来源 IP。
Q3:跨账号读取 S3,最少要检查哪些地方?
至少检查三处:目标桶策略、访问方 IAM 角色策略、如果启用了 KMS,还要检查密钥策略。少一处都可能 403。
Q4:如果账号刚开通不久,排查顺序要变吗?
要。新账号先确认支付方式、风控审核、组织限制和资源申请是否正常,再看 S3 策略。否则你可能一直在改权限,实际上账号状态还没放开。
结论:先定位拒绝层,再决定改哪里
AWS S3 403 Access Denied 不是“权限少一点”的简单问题。真正有效的排查顺序是:先确认账号状态和组织限制,再判断是 IAM、bucket policy、KMS 还是 endpoint policy 在拒绝,最后才是细调条件和前缀。如果你是在企业环境里做海外业务部署,这个顺序能少走很多弯路,也能避免把生产桶策略改乱。


