当您使用“身份验证令牌”时,客户端对该令牌的简单表示将授予访问权限(只要该令牌被服务器视为有效)。如果您将令牌“按原样”存储在服务器的数据库中,那么可以瞥见您的数据库的攻击者将立即了解所有令牌,从而允许他以仍然存在有效令牌的所有用户的名义发送请求在数据库中。这不好。因此,建议仅存储身份验证令牌的哈希值。
关于 bcrypt用于身份验证令牌的建议是错误的。Bcrypt 与所有专用于密码散列的函数一样,旨在用于密码。密码很弱;他们很容易受到字典攻击。为了解决它们固有的弱点,密码散列函数必须加盐(以防止并行攻击和预先计算的表)并且还必须非常慢(如果内部迭代则通过大量)。这使得密码散列函数变得昂贵。所以你不想使用密码散列函数,除非你需要它,例如散列密码。
身份验证令牌不是密码;它是由计算机生成和记忆的随机值,过程中不涉及任何人脑。因此,如果您正确生成了令牌(至少 128 位,从加密安全的 PRNG获得),那么就不需要盐或迭代;只需使用普通的哈希函数(即使是 MD5 也可以)。这样会更有效率。
至于对每个请求使用随机身份验证令牌而不是登录名+密码,主要原因有两个:
性能:如上所述,可以使用简单的哈希安全地验证身份验证令牌,这将比繁重的 bcrypt 调用更有效。您希望在真正有用的时候保留宝贵的 CPU 周期,尤其是在将 bcrypt 应用于实际的人工管理密码时。
客户端存储:身份验证令牌将作为 cookie 值存储在客户端。如果登录名和密码随每个请求一起发回,则它们将作为 cookie 存储在客户端上。当他们的密码被写入文件时,人们会感到紧张——并且这种存储(从安全角度来看)不等同于身份验证令牌的存储,因为人类用户有(坏)习惯重复使用他们的密码多次系统,而身份验证令牌本质上是特定于服务器的。