编码库按预期工作。让我们看一下默认的 mcrypt_encode() 方法:
function mcrypt_encode($data, $key)
{
$init_size = mcrypt_get_iv_size($this->_get_cipher(), $this->_get_mode());
$init_vect = mcrypt_create_iv($init_size, MCRYPT_RAND);
return $this->_add_cipher_noise($init_vect.mcrypt_encrypt($this->_get_cipher(), $key, $data, $this->_get_mode(), $init_vect), $key);
}
请注意编码内部发生的随机因素,并且噪声被添加到加密中。尝试将您生成的 10 个密钥存储到一个数组中并解密它们。你会正确地恢复你的价值观。
如果您正在寻找严格的单向编码并产生一致的结果,我建议在 PHP 中使用 hash() 方法(从 5.1.2 开始可用):http ://www.php.net/manual/ro/function .hash.php
生成哈希的一种安全方法是创建一个随机种子值,然后将其连接到用户的密码。这可以保护您免受彩虹桌开裂和其他事情的影响。
hash('sha512', $seed . $password);
更新:这个想法是使用加密类以便能够编码和解码一些字符串。这样想——这不是一个安全的例子,但它可以帮助理解这一点:你想在你的网站上存储一个人的信用卡信息。当然,您希望确保这些信息的安全,这样如果有人闯入您的数据库,这并不是什么大不了的事,因为所有这些信息都是加密的。您当然还希望能够解码该信息并将其显示给用户,以防他们再次从您的网站订购商品,而不是让他们手动输入数据,因此您还需要能够解密该数据。
一般来说,根据经验,我的理解是,如果加密算法是双向的(即可以编码和解码),那么它不如单向加密算法(仅编码数据)。
例如,如果您要存储用户登录凭据,那么您将永远不希望能够解码用户的密码,因为用户可以轻松地重置密码。您永远不想在帐户上显示用户密码,因此您始终将其牢牢锁定。这是您使用单向加密算法的地方 - 您在创建条目时对数据进行一次编码,然后在您在数据库中查找条目时对数据进行编码,而不是运行类似的东西:
SELECT *
FROM user
WHERE user.password = 'STAR_WARS'
你会运行类似的东西:
SELECT *
FROM user
WHERE user.password = '5badcaf789d3d1d09794d8f021f40f0e'
以上可以通过对您第一次从用户那里收到的数据进行编码来实现,当您设置他们的帐户时,然后每当您检查登录凭据时,您只需在他们的字符串上运行编码算法提供。
作为创建新帐户的工作流程:
- 用户使用密码“starwars”创建一个新帐户。
- 用户使用密码“5badcaf789d3d1d09794d8f021f40f0e”保存在数据库中,该密码是通过对用户提供的密码运行 md5() 获得的。
验证用户的工作流程:
- 用户通过登录表单发送密码“starwars”。
- 密码编码为“5badcaf789d3d1d09794d8f021f40f0e”。
- 我们检查我们的数据库条目,其中的密码是“5badcaf789d3d1d09794d8f021f40f0e”。
在上面的系统中,我们从不存储用户的原始密码——只存储加密数据。
现在这本身看起来很简单,但是MD5作为一种加密算法已经被完全破解了——也就是说,因为可能的字符串组合只有这么多,大部分值都被颠倒了,所以黑客取了值'5badcaf789d3d1d09794d8f021f40f0e'然后他们通过列出可能的登录密码的脚本运行它,这些密码都映射到“5badcaf789d3d1d09794d8f021f40f0e”,其中我们还会找到“星球大战”。
重要的是不要让您的密码生成尽可能长或模糊,而是尽可能随机。这就是为什么在上面的示例中,我们生成了一个种子,用于向密码添加随机元素,并且我们使用了更强大的加密算法。
所以种子可能是字符串:'sajuh27ahjs'。
当用户创建一个新帐户时,我们将种子与他们的原始密码连接起来。因此,对于我们的星球大战示例,用户在加密之前的原始密码将是:
'sajuh27ahjsstarwars'
种子存储在数据库中,没有加密,一目了然,因为我们稍后需要它来解码。好的,现在我们用强的东西加密密码,比如 SHA512。因此我们得到:
hash('sha512', $seed . $password);
请注意这种攻击是如何很难破解的,因为种子添加了一个随机元素,这使得破解者很难理解我们将种子放在哪里,即使有了这些知识,它也需要构建一个值映射表可以生成的每个特定随机种子(很多)。
希望能解决一些问题,否则请随时提出更多问题!