用 Google 或 Apple 账号登录就能在 Sui 上发交易,听起来像是把私钥交给了互联网公司,但 Sui 的 zkLogin 官方文档给出的答案是否定的:整条流程里没有任何一方同时掌握你的两个登录要素,零知识证明恰好把“我知道某个 OAuth 账号的所有权”这句话证了出来,又不把账号身份印在链上。这篇按官方技术参考拆它的四方流程、地址推导规则和信任假设。
四个阶段:临时密钥、JWT、ZK 证明、上链
官方文档把 zkLogin 流程分成四步。第一步,应用先生成一对短生命周期的临时密钥,把临时公钥编码进 OAuth 请求的 nonce,用户完成登录后,身份提供商返回的 JWT 里就包含了这个 nonce——这一步把“这次登录”与“这把临时密钥”绑死,防止登录凭证被挪去给别的密钥背书。第二步,证明服务拿 JWT、JWT 随机性、用户盐值和最大生效纪元算出一份 Groth16 零知识证明。第三步,链上地址由 JWT 里的三个声明字段(iss 身份提供方、aud 应用、sub 用户标识)加上用户盐值推导而来,注意它是从这四元组算出来的,而不是从任何公钥推导。第四步,交易用临时私钥签名、连同证明一起提交,验证者分别校验 JWT 的 RSA 签名(规范明确只支持 RS256)与零知识证明,两者都过才执行。
2-of-2:为什么任何一方都动不了你的资产
官方文档把 zkLogin 描述为一种 2-of-2 方案:两个要素是近期一次 OAuth 登录产生的凭证,和一个不由身份提供商管理的盐值。攻击者即使盗走 Google 账号,拿不到盐值也发不出交易;反之,盐值数据库泄露但攻击者无法通过你的登录验证,同样白搭。这与 MPC 或多签有本质区别:zkLogin 不拆分任何私钥,每次登录都通过 nonce 注册一把全新的临时密钥,会话结束即可丢弃。风险重心因此从“私钥保管”转移到“盐值服务的可用性一致性”——官方集成指南明确,盐值泄露的后果是把链上地址与邮箱身份关联起来(隐私损失),而不是让第三方取得资金控制权。

验证者怎么核对身份提供商的公钥
JWT 的签名要拿提供商的公钥来验。官方文档的做法是:验证者各自独立访问各提供商公开的 JWK 端点取回密钥集,密钥列表随协议升级更新,正确性由验证者质押权益的 2f+1 法定人数保证。字段层面,JWT 头部用 kid 指明该用哪把 JWK 验签,alg 固定 RS256。也就是说,链下信任被压缩成两件事:提供商签发的 JWT 本身,和验证者网络对 JWK 集合的共识,其余环节全部由密码学校验闭合。
地址稳定性与实操边界
只要 sub、iss、aud、盐值四者不变,同一用户在同一应用下的 zkLogin 地址就稳定不变。集成指南给出两个容易踩的坑:换浏览器或换设备后,若没有找回同一份盐值,将无法再访问此前由该盐值派生的地址下的资产——盐值找回流程必须被当作资产安全的一部分设计;日志里绝不应记录 JWT、证明或盐值,它们都是敏感凭证。另外地址无法反推出邮箱:想拿到邮箱只能在 OAuth 流程内申请 email 权限并存在应用侧,链上数据里没有。
与托管钱包的距离:一条容易混淆的边界
zkLogin 常被误读为“变相托管”。区别在于资金控制权:托管钱包里平台持有可动用密钥,zkLogin 的地址由你自己的 OAuth 登录与盐值共同点亮,平台(包括钱包前端)没有可离线携带的密钥可偷——它丢掉的只是“替你登录”的通道。但也要承认光谱的存在:盐值服务若被单一运营方垄断,账号冻结加盐值滥用的组合仍可能让恢复流程依赖对方响应。官方集成指南为盐值管理单列了策略章节,具体备份与找回方案以其文本为准,落地时应把盐值恢复当作资产可恢复性设计的一部分。
边界与风险提示
支持的提供商名单、各网络启用状态属于动态信息,以 Sui 官方文档的表格为准,本文不固化。信任画像也要看清:zkLogin 免掉了助记词,但没有免掉对身份提供商可用性的依赖——账号被冻结意味着登录要素缺失。地址派生、证明系统或盐值服务的实现缺陷都属于软件风险,历史协议升级记录以官方发布说明为准。本文只做机制说明,不构成任何投资建议或资产托管建议。
发表评论
还没有评论,来说两句吧。
评论区为展示样式,提交不会被处理。