如果我声明一个列serial
在 PostgreSql 中,它将按序数顺序自动递增。由于回滚等原因,最终结果可能不是连续的,但它或多或少是有序的。
我有一个用户表,其中用户 ID 设置为serial
,因此从 1 开始递增......但我宁愿他们不是,因为它似乎要求某种序列号攻击。
是否有一种相对简单、相对高效的方法可以在 PostgreSQL 中创建自动人工 ID,以便 ID 随机间隔开,并且您不应该期望 ID 987654321 遵循 ID 987654320?
如果我声明一个列serial
在 PostgreSql 中,它将按序数顺序自动递增。由于回滚等原因,最终结果可能不是连续的,但它或多或少是有序的。
我有一个用户表,其中用户 ID 设置为serial
,因此从 1 开始递增......但我宁愿他们不是,因为它似乎要求某种序列号攻击。
是否有一种相对简单、相对高效的方法可以在 PostgreSQL 中创建自动人工 ID,以便 ID 随机间隔开,并且您不应该期望 ID 987654321 遵循 ID 987654320?
除了我认为您给自己一种虚假的安全感这一事实之外,您可以通过为“真实”序列保留标识符的上半部分并用随机位填充下半部分来做您想做的事情:
dbfiddle在这里
没有理由想要这个。有些人认为它增加了安全性。他们绝对错了。不要成为那些人中的一员。
如果你绝对必须做这样的事情,拥有它。生成一个有 42 亿个 id 的表,并随机化它的顺序。
我认为这些方法中的任何一种至少是朝着正确方向迈出的一步,它们不那么疯狂。
与杰克道格拉斯的答案比较
使用 MATHS 有一个叫做满射函数的想法。这意味着您将一个域映射到另一个域。以下是十进制示例:
x
对于这样的所有整数都为真0<y<1
。因此,如果您简单地截断您可以返回到x
. 这不会增加任何安全性,给定输出,
x
所有这些是什么?提示:它是 42。杰克的答案选择是随机y
的,以相同的方式(但以二进制形式)将其添加到输入中,并将其存储在数据库中。如果这就是你想要的,那就去做吧(指出杰克的顺序也是序数,即使它不是连续的,也可能是一个接一个的顺序)。我的答案列出了 int4 域中的所有值。将顺序随机化,并将它们存储在表中。如果没有该表,您将永远无法恢复原始的顺序 ID:它只是一个肤浅且无用的混淆表,您会喜欢放弃或不实施,因为它非常愚蠢。但是如果没有那个表,你永远无法获得原始值。