登录了,权限不会因此长出来
一句话总结
**认证(authentication)**回答“你是谁”,**授权(authorization)**回答“你可以做什么”。 云平台把二者完全分离,因此登录成功后仍然什么都做不了,是一种正常状态。
为什么需要它
无法区分 401 和 403,调试时间就会增加一倍。
| 响应 | 含义 | 应修复的位置 |
|---|---|---|
| 401 Unauthorized | 不知道你是谁 | 凭据、令牌、签名 |
| 403 Forbidden | 知道你是谁,但不允许操作 | 策略、权限 |
它们的名称容易造成混淆——401 实际表示认证失败,403 表示授权失败。
在云 API 中收到 AccessDenied,属于 403 类错误,意味着凭据本身是有效的。
重新签发密钥也不会有任何帮助。
它如何运作
主体(principal)的类型
权限不只会附加给“人”。
| 主体 | 示例 | 特点 |
|---|---|---|
| 用户(user) | 负责人账号 | 长期凭据,由人登录 |
| 组(group) | developers |
用户集合,用于集中赋予权限 |
| 角色(role) | ec2-app-role |
任何满足条件的主体都可扮演,使用临时凭据 |
| 服务 | Lambda 函数、EC2 实例 | 通过扮演角色运行 |
| 外部身份 | Google、GitHub OIDC | 通过身份联合扮演角色 |
其中,角色是核心概念。它不是一个人,而是一组权限;满足条件的主体会暂时借用它。 后续模块会详细介绍。
评估顺序——显式拒绝优先
一个主体附有多项策略时,最终结果按照以下顺序决定。
1. 명시적 Deny 가 하나라도 있으면 → 거부 (무엇도 이를 뒤집지 못한다)
2. 명시적 Allow 가 하나라도 있으면 → 허용
3. 아무것도 없으면 → 거부 (기본 거부)
有两点非常重要。
- **默认是拒绝。**只有主动增加权限,权限才会存在。这是一种安全的默认值。
- **Deny 具有绝对优先级。**即使拥有管理员权限,只要组织级策略中有一项 Deny, 操作仍会被阻止。这正是创建安全护栏的方法。
策略可以附加在两个位置
可以从两个方向得到相同结果。
- 基于身份(identity-based)——附加在主体上:“这个人可以读取那个存储桶”
- 基于资源(resource-based)——附加在资源上:“这个存储桶允许那个人读取”
在同一账号内,通常只使用基于身份的策略。跨账号访问时则两边都需要—— 另一个账号的主体要读取我们的存储桶,对方的身份策略必须允许访问,我们的存储桶 策略也必须允许访问。这正是跨账号访问经常失败的原因。
生产现场中的表现
- 收到
AccessDenied后重新签发密钥 → 属于授权问题,因此毫无效果。 - 已是管理员,却只有某个操作被阻止 → 上级组织策略中的 Deny。
- 无法跨账号访问 → 只在一侧添加了允许规则。
被拒绝时应该检查什么
收到 AccessDenied 时,如果不想毫无方向地排查,就要预先确定检查顺序。因为云平台中的一项请求,在获得允许前必须通过多道关卡。
- **我当前究竟是谁。**首先确认实际主体是否与预期一致。实例中运行的代码通常使用实例绑定的角色,但人们经常用自己的个人凭据进行测试,然后说“明明可以”。每个云平台都提供输出当前主体的命令,应当先执行它。
- **在哪一道关卡被阻止。**组织级策略、身份策略、资源策略,以及签发临时凭据时进一步收窄的范围。只要其中任何一项没有允许,请求就会被拒绝。
- **操作名称和资源名称是否准确。**策略中操作名称的拼写错误不会触发异常,只会变成无法匹配的规则。资源标识也是如此;存储桶本身与桶内对象是不同资源,很多场景需要同时声明两者。
- **是否附带条件。来源 IP、时间、标签、多因素认证状态等条件,会导致操作平时正常,只有特定情况下被阻止。大量“昨天还可以”**的报告都源于这里。
还应养成不靠猜测、而是向工具询问评估结果的习惯。主流云平台都提供实际评估“这个主体能否对这个资源执行该操作”的功能,并能指出是哪项策略作出了决定。它比人工阅读策略文档并推导结果快数倍,还会把人容易遗漏的上级组织策略纳入评估。
最后要**查看日志。**被拒绝的请求会记录在审计日志中,其中包含主体、操作、资源和时间。与开发者口头描述的症状相比,这一行记录准确得多,因此调查永远应该从它开始。
下一步内容
接下来将逐行拆解策略文档的实际结构。