0Pricing
Cryptology Academy · 课时

PKCE:保护公共客户端

了解代码交换证明密钥,以及它如何防止授权码拦截攻击。

PKCE:保护公共客户端 是 CoddyKit 上的免费 Cryptology Academy 课时。 这是第 2 节课,共 4 节。 你可以在下方免费阅读本课时的完整内容 — 然后在浏览器中使用内置代码编辑器和全天候 AI 导师进行实践。 这是 Cryptology Academy 学习路径的一部分,你的进度在网页和 CoddyKit 应用中同步。 Cryptology Academy 课程共包含 4 节课。

授权码拦截

如果没有 PKCE,移动应用容易受到授权码拦截攻击。当授权服务器将授权码重定向到应用注册的自定义 URI 方案(例如 myapp://callback)时,同一设备上任何注册了相同 URI 方案的恶意应用都可以拦截该重定向并窃取授权码。

拦截攻击的原理

攻击过程如下:恶意应用注册与合法应用相同的自定义 URI 方案。当授权服务器将代码重定向到 myapp://callback 时,OS 可能会将两个应用都显示为处理程序。如果用户选择了恶意应用,或者 OS 默认使用恶意应用,攻击者就会收到授权码,并且无需知道客户端密钥即可用它交换令牌。

PKCE 代码验证器

PKCE(RFC 7636)会向授权码流程添加一个动态生成的秘密值。在启动流程之前,客户端会生成一个由密码学安全随机字符串组成的代码验证器,其长度为 43-128 个字符。该字符串对于每个授权请求都是唯一的,并且在令牌交换步骤之前不会被传输。

代码挑战值的计算

客户端根据验证器计算代码挑战值:code_challenge = BASE64URL(SHA256(code_verifier))。RFC 7636 要求使用 SHA256 方法(直接发送验证器的 "plain" 方法不推荐使用)。代码挑战值是验证器的单向转换结果,因此知道代码挑战值并不能推导出验证器。

在授权请求中包含代码挑战值

授权请求会包含两个额外参数:"code_challenge=BASE64URL(SHA256(verifier))&code_challenge_method=S256"。授权服务器会保存与已签发授权码相关联的代码挑战值。在此阶段不会向服务器传输任何可能被拦截的秘密值。

使用代码验证器交换令牌

在令牌交换过程中(向令牌端点发送 POST),客户端会在授权码旁附带 "code_verifier=ORIGINAL_RANDOM_STRING"。授权服务器会计算 BASE64URL(SHA256(code_verifier)),并验证其是否与保存的 code_challenge 匹配。只有生成了该验证器的合法客户端才能通过此检查。

PKCE 如何防止拦截攻击

如果攻击者拦截了授权码,他只能获得代码和代码挑战值(该值是公开的)。要用代码交换令牌,他还必须提供代码验证器。由于验证器由合法客户端生成,并且直到安全进行令牌交换时才会被传输,攻击者无法计算或获取该验证器。

PKCE 防止代码注入

PKCE 还可防止授权码注入攻击:攻击者在重定向过程中用窃取的代码替换有效代码。窃取代码的挑战值与受害者客户端将提交的验证器不匹配,导致令牌交换失败。PKCE 可同时针对多种攻击向量提供纵深防御。

所有客户端均使用 PKCE

尽管 RFC 7636 最初被描述为面向公共客户端(没有客户端密钥的客户端)的解决方案,但 OAuth 安全最佳实践(BCP)和 OAuth 2.1 要求所有客户端都使用 PKCE,包括拥有客户端密钥的机密客户端。PKCE 提供独立于客户端身份验证的保护,因此对所有客户端都有益。

OAuth 2.1 中的 PKCE

OAuth 2.1(draft-ietf-oauth-v2-1)将 OAuth 2.0 安全 BCP 中的安全最佳实践整合到一份文档中。它要求所有授权码流程都使用 PKCE,弃用隐式流程,并要求刷新令牌轮换。对于任何新的 OAuth 2.0 实现,PKCE 实际上都是必需的基线。

实现说明

正确实现 PKCE 需要:使用密码学安全的随机生成器生成验证器(至少 32 个随机字节,然后进行 base64url 编码);将验证器安全地存储在客户端中(而不是存放在 URL 或日志中);使用 S256 方法(而不是 plain);并确保在令牌交换后丢弃验证器。大多数现代 OAuth 库都会自动处理 PKCE。

PKCE 代码验证器检查

在 PKCE 中,代码验证器与代码挑战值之间是什么关系?

课程回顾:PKCE 安全

PKCE(RFC 7636)通过将每个代码绑定到只有合法客户端知道的动态生成代码验证器,防止授权码被拦截。验证器经过哈希处理后生成代码挑战值(公开发送)。令牌交换需要原始验证器。PKCE 同时防止拦截攻击和注入攻击。OAuth 2.1 要求所有授权码流程都使用 PKCE。

常见问题解答

「PKCE:保护公共客户端」课时是免费的吗?

是的 — 「PKCE:保护公共客户端」的完整文本可在网页上免费阅读。要进行交互式练习(内置代码编辑器和全天候 AI 导师)并解锁 Cryptology Academy 课程的其余内容,请升级到 CoddyKit PRO。 Cryptology Academy 课程共包含 4 节课。

「PKCE:保护公共客户端」这节课中我会学到什么?

了解代码交换证明密钥,以及它如何防止授权码拦截攻击。 你通过在浏览器中直接运行的动手代码来练习 Cryptology Academy,全天候 AI 导师会在你学习这节课的过程中回答你的问题。

学习 Cryptology Academy 需要有经验吗?

无需任何先前经验。CoddyKit 上的 Cryptology Academy 课程适合初学者到高级学习者,你可以从这里开始或从头开始,按照自己的节奏学习。 这是第 2 节课,共 4 节。

「PKCE:保护公共客户端」课时需要多长时间?

大多数 CoddyKit 课程大约需要 5–10 分钟。每节课都很精短且互动,所以你能稳步进步,并在网页和应用中从离开的地方继续。

我能在这节 Cryptology Academy 课中编写并运行代码吗?

能。每节 Cryptology Academy 课都包含内置代码编辑器,你可以在浏览器中直接编写并运行真实代码,并获得即时 AI 反馈 — 无需本地设置。

此课程中的所有课时

  1. OAuth 2.0 流程与令牌类型
  2. PKCE:保护公共客户端
  3. OpenID Connect 声明与 ID 令牌
  4. OAuth 漏洞与攻击模式
← 返回 Cryptology Academy