Security 如何制作一个;“安全随机”;Haskell中的字符串标记?
我想生成字符串令牌来实现web应用程序的密码重置功能。它们可以是,但不是必需的 我希望每个令牌都是安全随机的。应该为每个生成的令牌对系统的熵池进行采样 我找到了生成v4 UUID的包。文件提到 我们使用System.Random StdGen作为随机源 但我不清楚这是否足够Security 如何制作一个;“安全随机”;Haskell中的字符串标记?,security,haskell,random,cryptography,Security,Haskell,Random,Cryptography,我想生成字符串令牌来实现web应用程序的密码重置功能。它们可以是,但不是必需的 我希望每个令牌都是安全随机的。应该为每个生成的令牌对系统的熵池进行采样 我找到了生成v4 UUID的包。文件提到 我们使用System.Random StdGen作为随机源 但我不清楚这是否足够 是否有其他库可以替代?对每个生成的令牌进行系统熵池采样的要求听起来很可疑。熵通常是一种稀缺资源 让我们同意,/dev/random绝对是不可能的。其他进程可能需要它,它可能会导致潜在的拒绝服务等。但首先,当它认为熵池不足时,
是否有其他库可以替代?对每个生成的令牌进行系统熵池采样的要求听起来很可疑。熵通常是一种稀缺资源 让我们同意,
/dev/random
绝对是不可能的。其他进程可能需要它,它可能会导致潜在的拒绝服务等。但首先,当它认为熵池不足时,/dev/random
会在读取时阻塞,因此这是一个确定的数字。另一方面,/dev/urandom
应该是完全正确的。有人说它在一些奇怪的情况下有问题(例如在无盘机器上启动之后),但我们不要去那里
请注意,在大多数系统上,/dev/[u]random
都使用相同的算法。不同之处在于,/dev/uradom
从不阻塞,但也不一定在每次读取时使用任何新的熵。因此,如果使用/dev/uradom
算作“对系统熵池进行采样”,那么您拥有的任何正确使用它的解决方案都可能是好的
然而,它是以杂质为代价的。阅读/dev/uradom
迫使我们进入IO
。作为Haskeles,我们必须至少考虑替代方案,如果我们放弃熵样本的要求,那么我们就很幸运了。
相反,我们可以使用加密安全的确定性RNG,并且只能从/dev/random
中对其进行种子设定。cryptonite是DJB的一个实现,它将是一个不错的选择。由于它是确定性的,我们只需要IO
就可以得到初始种子。之后的一切都是纯洁的
Cryptonite提供,因此您可以调整令牌的长度以满足您的需要。如果您查看
nextRandom
的源代码(单击右侧的source
),您将看到它只对每个数字调用Crypto.Random.Entropy.getEntropy
,并根据“此模块用于实例化加密强确定性随机位生成器”,因此我相信您应该是安全的。如果您存储在数据库中并使用诸如persistent之类的库,那么您可以通过内部postgres方法本身来实现。@Sibi我使用的是MySQL,从文档判断,其UUID函数不是“安全随机的”:应该对每个生成的令牌对系统熵池进行采样的要求听起来可疑“我同意。问题是我正在尝试实现一个typeclass接口,它没有留下任何维护状态的空间,除非我尝试一些unsafePerformIO
技巧来初始化一个全局引用…嗯。。。确定性RNG确实需要将其状态存储在某个地方。如果我们不允许这样做,并且我们不希望显式的IO
,那么您唯一的选择可能就是通过unsafePerformIO
读取/dev/uradom
。不过这似乎是最后的选择。我可以执行显式的IO
,但我必须每次对/dev/uradom
进行采样,或者使用“unsafePerformIO”跟踪全局状态。