$salt = $this->get_salt($username);
if (is_null($salt)) {
return FALSE;
}
$password = sha1(SITE_KEY . $password . $salt);
$sth = $this->db->prepare("SELECT id, username, active FROM user WHERE username = ? AND password = ?");
$sth->setFetchMode(PDO::FETCH_OBJ);
$sth->execute(array($username, $password));
if (($result = $sth->fetch()) !== FALSE) {
return $result;
}
return FALSE;
Run Code Online (Sandbox Code Playgroud)
这让我很担心:
我没有误解登录方法.我只是不认为它应该返回该对象.我可能错了,你在做什么都很好,但我对此表示怀疑.您将完整的用户对象从数据库,密码和所有内容返回到可能不安全的脚本.有人可能会创建一个新文件然后执行类似var_dump($ userObject)的操作; 并拥有所有这些信息
而且,我发现从某些东西返回"魔法"属性是不直观的.这只是在使用之前未经验证的另一件事.如果您要将其移动到auth类中的单独方法并让它返回"active"的值,则可以运行您需要的任何验证,而不使用login.php脚本.
:再次查看它,如果您以这种方式滥用该对象,您将需要知道登录信息.在我看来,如果存在某种泄漏,将其分开仍然会更好.不是说我知道有人能做到这一点.把它想象成一个潜在的循环漏洞.
我不会假装了解恶意用户会做些什么.我只是知道让他们更容易这样做似乎并不明智.也许它没有任何问题,我不是安全专家.我只是在讨论一些事情,如果我要写它,我会改变,因为它们对我来说似乎有害.如果您真的想知道它是否危险,我建议将该示例提交给常规的stackoverflow社区,看看他们说了什么.
他有什么看法吗?该方法将用于我拥有的页面控制器:
$user = $auth->login('username, password)
if ($user) {
//do some additional checks... set session variables
}
Run Code Online (Sandbox Code Playgroud)
不,您提供的代码不安全.
首先,您使用的是非迭代的简单哈希.有关原因的信息,请参阅此答案和此博客文章.
第二,为什么要分别储存盐?盐必须对每条记录都是唯一的,才能使其发挥作用.所以把它放在一边的逻辑地方就是密码.在这种情况下,您要进行两次查询而不是一次(假设盐不是从用户名派生的,而且确实是随机的).如果它不是随机的,它应该是.有关更多信息,请参阅此帖子
第三,你接触到针对密码哈希的定时攻击,因为数据库没有使用定时免疫比较.有关更多信息,请参阅本文和本文.
不要自己这样做.这是真的很难做安全.使用图书馆.您可以使用PHPASS或PHP-PasswordLib ...
我没有误解登录方法.我只是不认为它应该返回该对象.我可能错了,你在做什么都很好,但我对此表示怀疑.您将完整的用户对象从数据库,密码和所有内容返回到可能不安全的脚本.有人可能会创建一个新文件然后执行类似var_dump($ userObject)的操作; 并拥有所有这些信息
这是一个有效的观点.但在那时,如果用户可以注入var_dump($userObject),他可以运行$this->db->prepare("SELECT * FROM user");并获取所有用户数据,而不仅仅是他的.因此,虽然有必要指出,但尝试保护是不值得的.除非你得到真正的肛门并将其全部放入数据库中的存储过程并从表中进行有限的读取访问(因此您无法从用户表中进行选择).但在那时,您需要从头开始重新设计整个应用程序,因为除了通过SP之外,您永远无法获得任何用户信息.这很难做得很好(复杂性是安全的敌人).
最后,我想你会远好于首位服抵御脚本注入.特别是如果你没有专业的管理员可以保护你的服务器到防止那种攻击所需的可笑数量(PHP进程上的chroot jails等).
而且,我发现从某些东西返回"魔法"属性是不直观的.这只是在使用之前未经验证的另一件事.如果您要将其移动到auth类中的单独方法并让它返回"active"的值,则可以运行您需要的任何验证,而不使用login.php脚本.
有什么神奇的财产?你是直接使用这些物品吗?或者您是否使用它们来填充用户对象(然后知道如何处理数据)...?就在那个snippit,我没有看到你的朋友指向的问题......
:再次查看它,如果您以这种方式滥用该对象,您将需要知道登录信息.在我看来,如果存在某种泄漏,将其分开仍然会更好.不是说我知道有人能做到这一点.把它想象成一个潜在的循环漏洞.
实际上,由于上面发现的时间攻击,你只需要知道一个有效的用户名......
我不会假装了解恶意用户会做些什么.我只是知道让他们更容易这样做似乎并不明智.也许它没有任何问题,我不是安全专家.我只是在讨论一些事情,如果我要写它,我会改变,因为它们对我来说似乎有害.如果您真的想知道它是否危险,我建议将该示例提交给常规的stackoverflow社区,看看他们说了什么.
总的来说这是一个很好的建议.请记住,复杂性是安全的敌人.因此,如果使其变得更加困难会增加很多复杂性,那么添加新漏洞的可能性就会大大增加(例如引入的时间攻击).我在简单方面犯了错误.我有经过充分测试的库来处理复杂的部分(比如密码散列),但我编写的代码很简单.
考虑最强的加密算法:One Time Pad.算法很简单:
encrypted = plaintext XOR key
Run Code Online (Sandbox Code Playgroud)
但没有密钥就无法解密.因此,算法的安全性实际上在于秘密,而不在算法中.这是你想要的.该算法应该是公开的,安全性不应该依赖于它的保密性.否则它会通过默默无闻变得安全.在你被破解之前,这给你一种温暖的模糊感觉......
| 归档时间: |
|
| 查看次数: |
287 次 |
| 最近记录: |