Skip to content

第 3 章:开了 MFA 就安全吗?攻击者可能从恢复流程拿走账号 ​

本章主线:从登录因子出发,沿认证器注册、会话延续、风险加验和账号恢复追踪完整接管路径。

开场:一道容易答快的问题 ​

系统强制所有用户启用 Passkey,是否就消除了账号接管?小安回答“基本是”,但评审继续问:邮箱能否直接重置?客服能否跳过认证?新设备绑定是否通知旧设备?旧会话是否撤销?

强认证只保护它参与的流程。攻击者会选择最弱入口,因此恢复、绑定、会话和客服流程必须作为同一认证系统设计。

学习目标 ​

能够设计密码/Passkey 认证;理解认证器注册和断言;防护会话固定、CSRF 和账号枚举;设计分层恢复;定义风险加验与认证指标。

3.1 认证因子与认证器 ​

  • 所知:密码、PIN;可被猜测、钓鱼、复用。
  • 所有:手机、安全密钥、私钥;可能被盗或克隆。
  • 所是:指纹、人脸;不可更换且涉及敏感个人信息。

多因素要求来自不同类型;“密码 + 安全问题”仍是同一类。设备解锁生物识别通常只在本地释放 Passkey 私钥,服务端不应拿到原始指纹。

3.2 密码登录全流程 ​

图 3-1:3.2 密码登录全流程

图 3-1:3.2 密码登录全流程 · 可编辑 Mermaid 源码

防护需同时覆盖在线猜测、撞库、密码喷洒和离线数据库泄漏。单 IP 限速会误伤 NAT 用户且可被代理池绕过,应组合账号、设备、网段、行为和全局信号。

3.2.1 登录接口边界 ​

输入规范化必须谨慎:邮箱域名通常不区分大小写,但本地部分和企业用户名规则需明确;不要因不同错误时间泄漏账号是否存在。成功后旋转 session ID,并把认证时间、AAL、使用的认证器和风险写入会话上下文。

示意响应只返回通用消息:

json
{
  "status": "authentication_failed",
  "message": "账号或认证信息无效",
  "request_id": "req-7d31"
}

内部审计可记录精确 reason code,但不记录输入密码或完整凭证。

3.2.2 限速策略 ​

维度作用注意
账号限制单账号猜测可被攻击者用来锁死受害者
IP/网段限制单来源NAT 误伤、代理池绕过
设备/客户端识别自动化标识可被清除或伪造
全局密码模式发现喷洒避免记录明文密码
风险动作step-up/延迟/阻断动作需可解释和申诉

3.3 MFA 的强弱 ​

短信/邮件验证码容易被 SIM swap、邮箱接管和钓鱼;TOTP 可被实时代理;Push 会遭 MFA fatigue;FIDO/WebAuthn 将签名绑定到真实站点 origin,具备更强抗钓鱼能力。

MFA 不是“启用率”就结束:要追踪实际使用覆盖、回退方式、恢复流程、高风险人群和旧协议绕过。

3.4 WebAuthn 与 Passkey ​

注册:认证器为特定 RP 创建公私钥,服务保存公钥与 credential ID。认证:服务给随机 challenge,认证器在用户验证后对 challenge 与 origin/RP 信息签名。

图 3-2:3.4 WebAuthn 与 Passkey

图 3-2:3.4 WebAuthn 与 Passkey · 可编辑 Mermaid 源码

同步 Passkey 提升可用性;设备绑定凭证适合更高管控场景。设计时考虑跨设备、共享设备、设备丢失、企业 attestation、迁移和恢复。

3.4.1 注册 ceremony ​

服务端创建一次性 challenge,包含 RP、用户句柄、算法和策略;浏览器调用认证器;服务端验证 challenge、origin、RP ID、attestation 策略,并保存 credential ID、公钥、sign counter/能力与创建上下文。

用户句柄应为不透明稳定 ID,避免直接暴露邮箱。challenge 需高熵、短期、一次性并与注册会话绑定。

3.4.2 认证 ceremony ​

服务端发 challenge;认证器经用户验证后签名 authenticator data 与 client data hash;服务端查 credential、公钥验签,并检查 origin/RP、challenge、flags 和状态。

验签成功后仍要检查账号状态、认证器是否撤销、风险和目标动作。Passkey 完成的是强认证,不是业务授权。

3.5 会话管理 ​

服务端 session ID 必须高熵、不可预测;Cookie 设置 Secure、HttpOnly、合理 SameSite、精确 Domain/Path。登录后轮换 session ID 防固定攻击;敏感动作要求近期认证。

会话生命周期包含:绝对超时、闲置超时、风险变化、密码/认证器变更、管理员撤销、全局登出。退出不仅删除浏览器 Cookie,还要使服务端状态或 token 链失效。

3.5.1 会话数据模型 ​

text
session_id_hash, subject_id, created_at, last_seen_at,
auth_time, aal, credential_id, device_id, risk_level,
absolute_expires_at, idle_expires_at, revoked_at, revoke_reason

数据库只保存 session ID 的哈希可降低泄漏直接复用。读取时更新 last_seen 要注意写放大,可用节流或分层存储。

  • Host-only 优先,避免无关子域收到;
  • __Host- 前缀要求 Secure、Path=/、无 Domain;
  • SameSite=Lax 常适合普通 Web,会影响跨站登录/嵌入流程,必须实际测试;
  • 不把 access token 暴露给不需要的前端 JavaScript。

3.6 CSRF、XSS 与点击劫持 ​

  • CSRF 利用浏览器自动携带 Cookie;用 SameSite、CSRF token、Origin 检查和重新认证。
  • XSS 可在用户上下文执行脚本;HttpOnly 能保护 Cookie 不被直接读取,但不能阻止脚本发起操作。需输出编码、CSP、避免危险 DOM API。
  • 点击劫持通过透明 iframe 诱导点击;使用 CSP frame-ancestors。

3.7 账号恢复是认证的一部分 ​

恢复通常是最弱链。安全设计:多条独立路径;恢复码只显示一次并哈希保存;高价值账号人工核验;变更认证器通知旧渠道;冷却期;撤销旧会话;记录证据和申诉。

不要依赖容易公开的安全问题。客服流程需要脚本、权限隔离和反社工训练,不能让客服绕过所有强认证。

3.7.1 分层恢复设计 ​

账号风险恢复证据附加控制
普通消费者已绑定 Passkey/恢复码/验证渠道组合通知旧渠道、撤旧会话
高价值消费者多证据 + 冷却期/人工复核限制资金与敏感变更
员工企业设备、manager/服务台流程、身份核验工单、双人控制、审计
特权管理员离线恢复材料、双人审批break-glass、实时告警

恢复后默认把账号置于受限状态,敏感动作等待冷却或再次强认证。对攻击者已控制邮箱的情况,旧邮箱通知不能作为唯一保护。

3.8 风险认证与 Step-up ​

输入包括设备绑定、IP/ASN、地理速度、登录时间、失败模式、cookie 连续性、已知恶意基础设施、行为和资源敏感度。输出最好是动作而非神秘分数:允许、限权、加验、延迟、人工复核、阻断。

对每个动作定义误报/漏报成本。新设备登录可能只需 Passkey;修改收款账户则要求近期抗钓鱼认证和交易确认。

3.8.1 Step-up 上下文绑定 ​

加验结果应绑定目标交易,而不只是给会话永久升档。例如确认内容包含收款账户、金额、币种和 nonce;完成后只授权该交易或短时间内同类有限操作,防止攻击者在加验后替换参数。

3.9 常见攻击链 ​

图 3-3:3.9 常见攻击链

图 3-3:3.9 常见攻击链 · 可编辑 Mermaid 源码

防御必须在多处截断:泄漏密码检测、抗钓鱼 MFA、token 绑定、敏感变更重认证、旧渠道通知、会话撤销和异常行为检测。

3.10 本章实验与验收 ​

实验:实现密码 + Passkey 双路径;加入设备/会话管理和全局撤销;模拟 CSRF、会话固定、MFA fatigue 与恢复方式变更。

验收:说明 Passkey 抗钓鱼的具体绑定;为何 HttpOnly 不能治愈 XSS;全局登出如何传播;恢复流程为何必须至少与正常登录同强度。

3.10.1 必测负向用例 ​

  • challenge 重放、过期或属于另一会话;
  • 错 origin/RP ID;
  • 已撤销 credential;
  • 登录前后 session ID 不变;
  • CSRF token 与会话不匹配;
  • 恢复码二次使用;
  • 攻击者控制邮箱后尝试绑定新 Passkey;
  • 全局登出后 refresh token 继续换新 token。

3.10.2 指标看板 ​

登录成功率按认证器/平台/版本分组;P95/P99;Passkey 注册与实际使用覆盖;step-up 触发/成功/放弃;恢复发起、成功、拒绝和后续欺诈;账号接管率;每万次登录工单数。

工程复盘:Passkey 上线后,攻击者改走了恢复入口 ​

团队上线 Passkey 后,登录钓鱼告警明显下降。小安正准备宣布项目完成,红队却先控制测试邮箱,再通过“忘记密码”绑定新设备,整个过程没有触发原设备确认,也没有撤销旧会话。

问题不在 Passkey,而在团队只测试了最强入口。小安把注册、登录、绑定、恢复、客服和会话撤销画成同一张状态机,并给每次认证状态变化记录 credential_id、认证强度、设备、风险、原因和审批证据。随后补齐四个关键测试:

  • 控制邮箱后不能立即绑定高强度认证器;
  • 恢复成功必须通知旧渠道并撤销旧会话;
  • 高价值动作在冷却期内仍需额外确认;
  • 客服不能以一个知识型问题绕过全部认证器。

项目指标也从“Passkey 注册率”扩展为实际使用覆盖、回退路径占比、恢复后欺诈率、撤销传播时间和每万次登录工单数。强认证是否有效,要看攻击者最终还能不能拿走账号,而不是看设置页面里亮了几个绿色开关。

面试与设计评审 ​

  • Passkey 为什么抗钓鱼?讲清 challenge、origin、RP ID 与私钥不离开认证器。
  • MFA 为什么仍会被绕过?从实时代理、Push fatigue、恢复和会话窃取回答。
  • 全局登出怎么做?区分浏览器 Cookie、服务端会话、access/refresh token 和下游传播。

本章小结 ​

认证安全由最弱的注册、登录、绑定、恢复和会话环节决定。不要只看 MFA 启用率,要看实际强认证覆盖、回退路径、撤销时间和接管结果。