看似糟糕的错误信息,例如登录失败时的模糊提示,并非源于用户体验的疏忽。实际上,这是一种在安全与可用性之间深思熟虑的权衡。因为详细的错误信息可能被攻击者用作“神谕” (oracle),通过反复试探来获取敏感数据或发动攻击,例如确认账户是否存在或破解加密。因此,设计者必须有意识地决定他们更看重什么:是为普通用户提供便利,还是为攻击者增加障碍。
令人困惑的登录报错
我们都见过这样的报错:“用户名或密码不正确。” 随后可能还会补充一句:“如果该账户存在,我们已向您发送密码重置邮件。” 这完全违背了传统用户体验(UX)设计中关于提供清晰、可操作信息的建议。
传统的UX建议是:精确描述问题,并提供建设性的解决方案。仅仅说“发生错误”是远远不够的。
那么,为什么不直接告诉用户“密码错误”或“该邮箱未注册账户”呢?
原因是,明确的提示会引发账户枚举攻击。攻击者可以利用这个功能来验证一个邮箱列表,从而确定哪些人在你的网站上拥有账户。对于涉及隐私的应用(如心理健康服务),这类信息可能非常敏感。账户枚举通常是凭证填充攻击的前奏,即攻击者使用在别处泄露的密码来尝试登录用户在其他网站上重复使用的账户。
这些模糊的“哎呀,出错了”式信息,本质上是一种安全措施。作为安全从业者,绝不希望向潜在的攻击者透露任何关于防御系统的内部信息。这个会说真话但选择保持沉默的登录页面,就是我们的第一个“神谕”。
任何有用的报错都是一种“神谕”
在密码学中,即使是错误信息也可能是危险的。以一种常见的加密方式为例,它需要对数据进行“填充”以满足特定的块大小。如果解密程序能够区分“密钥错误”和“填充错误”,会发生什么?
- 你刚刚创造了一个“填充神谕攻击” (padding oracle attack) 的漏洞。
- 解密代码的报错信息就成了“神谕”。攻击者虽然不知道正确的数据是什么,但可以向这个“神谕”提问。
- 攻击者可以一次只修改一个字节的数据,然后发送给解密程序,观察报错是“填充错误”还是其他错误。通过反复试探,他们可以逐个字节地破解出整条加密信息。
这不是理论上的好奇心,而是真实发生过的攻击,曾影响过SSL/TLS协议、Ruby on Rails等Web框架,甚至Steam游戏客户端。一个对好人有用的错误信息,对坏人同样有用。更糟糕的是,即使你将所有报错信息都统一为“出错了”,攻击者依然可以通过分析响应时间的微小差异(计时攻击)来执行同样的攻击。
“神谕”的力量:从鉴别小鸡到人工智能
尽管对普通用户来说很不方便,但“神谕”的存在提醒我们,哪怕只有一比特的信息也极其有用。只要你能稳定地获得关于目标的一点点反馈,你就能重复这个过程,直到完全解决问题。
- 鉴别小鸡性别: 刚出生的小鸡性别极难分辨。但在20世纪,专家通过反复的“猜测-验证”训练,成为了能快速准确判断的“神谕”。他们自己甚至都说不清是如何做到的,这是一种通过与“神谕”互动而习得的直觉。
- 机器学习: 同样的过程也发生在机器学习中。无论是使用带标签的数据集进行监督学习,还是通过奖励函数进行强化学习,“神谕”都在提供反馈,帮助模型在不了解具体特征的情况下学会分类。
- 内容生成: 如果一个“神谕”可以分类,那么你就可以反向利用它来创造同类的新事物。在生成对抗网络(GAN)中,一个生成器模型试图创造以假乱真的数据,而一个鉴别器模型(神谕)则负责判断其真伪。二者在对抗中共同进化。
一个系统泄露了一点点真相,就有人能利用它作为“神谕”,推导出更深层次的模式。
如何为报错信息“赋予意义”
回到登录报错的问题上。我们的目标是阻止攻击者登录他人账户。根据Jason Wei提出的“验证者法则” (Verifier's Rule):
训练AI解决一个任务的难易程度,与该任务的可验证性成正比。所有可解且易于验证的任务,都将被AI解决。
换句话说,如果我们能轻易地用一个“神谕”来检验解决方案,那么整个问题最终都能被自动化解决。这对攻击者同样适用。如果我们想让攻击者的日子更难过,就必须让我们的“神谕”变得更差劲。
我们可以从以下几个方面入手,让验证过程变得更困难:
- 可扩展性: 增加速率限制和账户锁定机制。如果每小时只能尝试几次,攻击的规模就很难扩大。
- 噪声: 使用模糊的错误信息,为反馈循环增加“噪声”,让攻击者难以判断其操作的真实结果。
- 连续奖励: 登录成功是“全有或全无”的结果,本身不提供连续的奖励反馈,这对防御有利(除了需要防范的计时攻击)。
最终,我们必须在两个目标之间做出权衡:是让真实用户知道他们输错了邮箱更有价值,还是通过增加噪声来阻碍攻击者更有价值?
这个决定还会带来连锁反应,比如模糊的报错是否会增加客服压力?这些都属于“意义构建” (meaningmaking) 的范畴——即对事物的相对价值做出主观判断。系统无法替你决定,技术栈或项目管理框架也无法回答。你必须自己定义什么是可接受的权衡,并回答那个最核心的问题:你真正看重的是什么?