2

为什么开发人员会为他们的“用户”对象使用 ID,或者为什么 Twitter 使用Snowflake作为消息 ID……?换句话说:为什么顺序 ID 在浏览器中很明显是不好的?它代表安全漏洞还是只是隐私问题?如果是安全漏洞,顺序 ID 会暴露哪些漏洞?如果这是一个隐私问题,如果最终用户可以识别顺序 ID,那么如何侵犯隐私?

4

1 回答 1

3

创建唯一 ID 的三种常用方法是

  • 使它们连续
  • 选择一个相当大的随机数
  • 选择 UUID,即尝试“个性化”数字,以便不会再次创建它

安全方面

如果您将会话之类的内容与 ID 相关联,这肯定是一个安全问题。在这种情况下,您不希望任何恶意用户能够预测这样的 ID。顺序 ID 可以轻松预测,UUID 需要更多努力但也不是一个好主意,它会留下随机数。即使对他们来说,您也必须确保使用加密安全的随机数生成器,否则仍有可预测的空间。

作为一个为什么这很严重的例子,请考虑 URL 中包含的旧的“jsessionid”或任何其他典型的会话 ID。攻击者将登录并像普通用户一样行事,记下分配给他的会话 ID,然后开始预测更多 ID,并通过在地址栏中输入它们,有效地劫持其他用户的会话。

并发/扩展问题

但从 Snowflake 在其描述中所说的来看,似乎没有与之相关的固有安全问题,该方法似乎属于第三类,即 UUID 类别。在文本中,它说他们正在从 MySQL 迁移到 Cassandra,并且他们过去使用的是 MySQL 顺序 ID。但是如果你仔细想想,当你尝试扩展你的系统时,这很快就会成为一个瓶颈:每个 ID 生成都需要同步以防止竞争条件。

如果您不同步此过程,则此类竞争条件的一个示例可能是两个独立实例同时增加 ID,因此实际上只将计数器增加了 1,而实际上它应该增加了 2。现在通常,如果您只有一个数据库实例,数据库将为您执行同步。但显然这并不能扩展,太多的客户端将处于空闲状态,而数据库处于重负载状态。多个数据库是一种选择,但复制 ID 可能会使您回到相同的情况。

无锁唯一 ID

因此,如果您希望在不需要同步(无锁)的情况下生成 ID,您要么学会使用非唯一 ID(这或多或少是矛盾的,而不是真正的解决方案),要么您必须想办法消除瓶颈。我们曾经做过的事情,以及对一些数据库实例效果很好的事情:

  • 对于两个实例,一个 DB 只会生成奇数 ID,另一个只会生成偶数 ID。
  • 对于 n 个实例,选择 n 个互质数,并将给定实例的 ID 与这些互质数之一相乘。在三个数据库的情况下,例如选择 2、3 和 5。基本数论确保不会有重复。

但在许多情况下,这将成为一个真正的数论问题,因此您必须寻求不同的解决方案。一种出路是走 UUID 路线,这通常是可以的,但缺点是完全取决于可能随时间变化的外部因素。从我所见,我猜这就是雪花的目标。

为了完整起见,我想提另一个解决方案,它可以很好地扩展并且本身就是 IMO 漂亮的。它也不受外部因素的影响,并且可以在任何地方工作,尽管一开始是违反直觉的。这个想法是选择足够大(比如说 20 个字节)的加密安全随机数。它必须是那些,非加密随机数生成器通常在生成一定数量的数字后重复,当然我们不希望这样。除此之外,这就是你所需要的。

起初,我认为这永远行不通,如果我们得到相同的数字怎么办?但是,如果您进行数学计算,您将意识到赔率是多少。生日悖论告诉我们,您会发现时间上的冲突大约为 O(2^(n/2)),其中 n 是您的随机数的位数。所以 20 字节 = 160 位,你应该在 2^80 时间内发现冲突。这与 SHA-1 的安全裕度相同,到目前为止,没有人在那里发现过碰撞。问题是,你运气好并在 2^30 中通过“机会”或类似的方式发现碰撞的可能性很小。概率对你不利。这与在同一天成为总统同时赢得多个彩票大致相同。

于 2012-04-30T12:55:02.570 回答