为了生成32个字符的令牌以访问我们目前使用的API,我们目前使用:
$ token = md5(uniqid(mt_rand(),true));我已经读过这个方法不是加密安全的,因为它基于……
可靠的密码您只能来自 的 ASCII 强> 人物 的 一个-ZA-Z 强> 和 的 数字0-9 强> 。要做到这一点,最好的方法是使用加密安全的方法,比如 的 random_int() 强> 要么 的 random_bytes() 强> 来自PHP7。休息功能如下 的 BASE64_ENCODE() 强> 您只能使用支持函数来提高字符串的可靠性并将其更改为 的 ASCII 强> 字符。
的 mt_rand() 强> 不安全,而且很老。 从任何字符串您必须使用random_int()。从二进制字符串你应该使用 BASE64_ENCODE() 使二进制字符串可靠或bin2hex,但那么你只会将字节切换到16个位置(值)。 请参阅我对此功能的实现。 它使用所有语言。
如果你想使用openssl_random_pseudo_bytes,最好使用CrytoLib的实现,这将允许你生成所有字母数字字符,在openssl_random_pseudo_bytes周围粘贴bin2hex只会导致你获得A-F(上限)和数字。
替换路径/到/你把cryptolib.php文件放在哪里(你可以在GitHub上找到它: https://github.com/IcyApril/CryptoLib )
<?php require_once('path/to/cryptolib.php'); $token = CryptoLib::randomString(16); ?>
完整的CryptoLib文档可从以下位置获得: https://cryptolib.ju.je/ 。它涵盖了许多其他随机方法,级联加密和哈希生成和验证;但是如果你需要它就在那里。
如果您有加密安全随机数生成器,则不需要对其输出进行散列。实际上你不想这样做。 只是用
$token = openssl_random_pseudo_bytes($BYTES,true)
但是,$ BYTES需要多个字节的数据。 MD5有一个128位散列,所以16个字节就可以了。
作为旁注,您在原始代码中调用的函数都不是加密安全的,大多数都是有害的,即使与安全的其他函数结合使用,只使用一个函数会破坏不安全。 MD5存在安全问题(尽管对于此应用程序,它们可能不相关)。 Uniqid默认情况下不会生成加密随机字节(因为它使用系统时钟),所传入的附加熵使用线性全等生成器进行组合,该生成器不具有加密安全性。事实上,它可能意味着即使他们不知道您的服务器时钟的价值,也可以猜测所有API密钥的访问权限。最后,mt_rand(),你用作额外熵,也不是一个安全的随机数发生器。